Fix a Footer Cut Off in a Full-Page Website Screenshot
When a full-page screenshot cuts off the footer, check the capture mode, scroll container, CSS ancestors and content loading before changing the page.
If a website footer is missing from a full-page screenshot, first confirm that you used a full-page capture mode. In Chrome, choose Capture a full size screenshot from the Device Mode menu. In Playwright, use page.screenshot({ fullPage: true }). If the footer is still absent, identify which element actually scrolls, inspect the footer and its ancestors in DevTools, and make sure content that loads on scroll has finished loading before capturing.
There is no single CSS change that fixes every cut-off footer. A page can scroll inside a nested panel, an ancestor can clip content, or the footer can be missing from the rendered page at capture time. The steps below help distinguish these cases. The workflow is the same for developers in India; the cited browser documentation does not establish a country-specific difference.
1. Confirm that you are taking a full-page screenshot
Chrome DevTools: manual capture
- Open the page in Chrome and open DevTools.
- Turn on Device Mode.
- Open the Device Mode More options menu.
- Select Capture a full size screenshot.
Chrome documents this option for capturing content outside the visible viewport. The regular screenshot command captures the visible viewport, so it can omit a footer simply because the page was not captured in full-size mode. See Chrome DevTools’ Device Mode documentation.
If you use the browser’s visible-viewport capture, scroll down and take another image to inspect the footer, but treat that as a diagnostic image rather than a single full-page capture.
Playwright: repeatable capture
Install Playwright and its Chromium browser, then save the following as capture.mjs. Replace the example URL with the page you need to capture.
npm init -y
npm install -D playwright
npx playwright install chromium
// capture.mjs
import { chromium } from 'playwright';
const url = process.argv[2] ?? 'https://example.com';
const browser = await chromium.launch({ headless: true });
try {
const page = await browser.newPage({ viewport: { width: 1440, height: 900 } });
await page.goto(url, { waitUntil: 'networkidle', timeout: 60000 });
await page.screenshot({ path: 'page.png', fullPage: true });
console.log('Saved page.png');
} finally {
await browser.close();
}
node capture.mjs https://example.com
Playwright describes fullPage: true as capturing the full scrollable page. For just the footer, use a locator screenshot instead: await page.locator('footer').screenshot({ path: 'footer.png' });. The locator must match an element that exists on the page. See Playwright’s screenshot documentation.
networkidle is a useful starting point, but it is not proof that every site-specific animation, delayed request, or lazy-loaded image has completed. If a page keeps network activity open, navigate with waitUntil: 'domcontentloaded' and explicitly wait for a page-specific ready condition, such as a selector or application state, before capture. Avoid adding arbitrary delays unless you have confirmed that the page needs them.
2. Find the element that actually scrolls
A full-page capture is intended to cover the document’s scrollable page. Some web apps instead keep the document fixed while an inner panel scrolls. In that case, the footer or remaining content may belong to a nested scrolling area rather than the document’s full-page height. Determine which element scrolls before changing screenshot settings.
- Try scrolling over the main page and then over the area that contains the content.
- In DevTools, inspect the suspected content area and its ancestors.
- In the Console, compare the document and element scroll dimensions. Replace the selector with the likely panel selector.
const panel = document.querySelector('.scroll-panel');
console.log({
documentHeight: document.documentElement.scrollHeight,
documentViewport: document.documentElement.clientHeight,
panelHeight: panel?.scrollHeight,
panelViewport: panel?.clientHeight,
panelScrollTop: panel?.scrollTop
});
If the panel’s scrollHeight is greater than its clientHeight, it has content beyond its own visible area. The measurements are clues, not a diagnosis by themselves. Confirm by scrolling the page and panel and observing which one moves.
For an automated workflow, you may need to scroll the actual panel to reveal content and trigger loading before taking a screenshot. That does not guarantee that a full-page screenshot will stitch the panel’s entire contents as you expect. For a panel-specific capture, consider taking an element screenshot after bringing the panel to the relevant state, or adjust the capture approach to the application’s DOM and layout.
3. Inspect the footer and its ancestors in DevTools
When the correct capture mode still omits the footer, inspect the rendered page instead of guessing at a CSS fix.
- Open the Elements panel and select the footer. You can right-click the visible footer and choose Inspect, or search the DOM for its element.
- Walk up its parent elements and identify the page or panel that scrolls.
- In the Styles tab, review the rules applying to the footer and each relevant ancestor.
- In the Computed tab, check the resolved styles. Pay particular attention to dimensions, positioning, visibility, and overflow-related properties.
- Temporarily toggle a suspected rule in DevTools to see whether it changes the rendered result. Make a permanent code change only after the responsible element and rule are clear.
Chrome’s CSS features reference explains how to use Styles and Computed to inspect CSS rules and the values actually applied to an element.
Clipping or hiding by an ancestor, layout constraints, and positioning are things to investigate, not conclusions that can be drawn without the page’s DOM and CSS. Do not assume that adding a large height, changing position, or setting overflow: visible is the right fix; each can change page layout or fail to address the actual scroll container.
4. Make sure below-the-fold content has loaded
Some pages load images or sections as the visitor scrolls. A capture made before those elements load may show a blank area or omit content near the bottom. Scroll through the page before capturing, wait for the relevant content, and then take the full-page screenshot. This is a diagnostic precaution for pages with lazy or dynamic content, not a guarantee that every page requires a manual scroll.
For a Playwright script, wait on a selector that represents the content you need, if the site provides one:
await page.goto(url, { waitUntil: 'domcontentloaded', timeout: 60000 });
await page.locator('footer').waitFor({ state: 'visible', timeout: 15000 });
await page.screenshot({ path: 'page.png', fullPage: true });
If the footer is visible but images within it are not ready, wait for those specific images or the site’s own ready signal. A generic fixed sleep can make captures slower without ensuring the right content loaded.
5. Choose the right diagnostic or capture method
| Method | Use it when | What it tells you |
|---|---|---|
| Chrome DevTools full-size screenshot | You need a quick manual capture in Chrome. | Whether the document’s off-viewport content appears in a full-size capture. |
| Playwright full-page screenshot | You need a repeatable automated capture. | Whether the full scrollable page is captured after your chosen navigation and wait steps. |
| Playwright locator screenshot | You want to isolate the footer for inspection. | Whether the footer element itself is present and rendered. |
| DevTools Styles and Computed | The correct capture mode still misses or clips content. | Which CSS rules apply to the footer and its ancestors. |
6. Troubleshooting common symptoms
| Symptom | Likely area to check | Next step |
|---|---|---|
| The screenshot ends at the viewport bottom. | Capture mode. | Use Chrome’s full-size screenshot or Playwright’s fullPage: true. |
| The document is short but a content panel has a scrollbar. | Nested scrolling. | Identify and inspect the scrolling panel; trigger its content loading before capture. |
| The footer exists in the DOM but is not visible. | CSS or layout on the footer or an ancestor. | Inspect Styles and Computed, then test suspected rules in DevTools. |
| The bottom section or images are blank. | Lazy loading or delayed content. | Scroll to the relevant area, wait for its content, and capture again. |
Playwright reports that footer was not found. |
The page may use a different element, load the footer later, or not include one on that route. | Inspect the DOM and use a selector that matches the actual page; wait for a real readiness condition. |
Navigation times out waiting for networkidle. |
The page may keep requests active. | Use a less restrictive navigation condition and wait for the specific content needed for capture. |
| The footer appears in a separate element screenshot but not in the full-page image. | Page versus nested scroll area or full-page layout behavior. | Check which element scrolls and how the footer relates to that container. |
7. Reliability, performance, and cost considerations
- Use explicit readiness checks. Waiting for the exact footer or page content makes the capture workflow easier to diagnose than relying only on a delay.
- Keep captures repeatable. Set a known viewport and use the same browser configuration when comparing results. A different viewport can change responsive layout and page height.
- Expect long pages to take more resources. Full-page captures cover a larger rendered surface than viewport captures. Very long pages and high-resolution output can increase memory use and capture time. No universal timing or memory figure applies across sites and machines.
- Retry only transient failures. If navigation or rendering fails temporarily, a bounded retry can help. Repeating captures will not fix a deterministic clipping rule or the wrong scroll container.
- Account for the page’s own behavior. Dynamic content, consent banners, and page scripts can affect what appears. Use a stable page state appropriate to your use case.
- Track the cost of your setup. A local Playwright script uses your own runtime and infrastructure; its cost depends on where and how often it runs. A screenshot API has provider-specific pricing and billing rules, so check those before scaling.
Or skip the browser setup
For a hosted capture, ScreenshotNeo is a website screenshot API and MCP server. Its full-page option loads lazy images. Cookie and consent banners, newsletter popups, and chat widgets are removed before capture; each step can be turned off. Bot checks, blank pages, timeouts, failed loads, and cache hits are not billed, and responses include page-verdict and billing headers.
One GET request returns the image. See the ScreenshotNeo API documentation for the request options and configuration.
curl -G "https://api.screenshotneo.com/v1/shot" \
-d access_key=YOUR_API_KEY \
--data-urlencode url=https://example.com \
-d full_page=true \
-o shot.webp
import requests
r = requests.get(
"https://api.screenshotneo.com/v1/shot",
params={
"access_key": "YOUR_API_KEY",
"url": "https://example.com",
"full_page": "true",
},
timeout=90,
)
r.raise_for_status()
open("shot.webp", "wb").write(r.content)
const q = new URLSearchParams({
access_key: 'YOUR_API_KEY',
url: 'https://example.com',
full_page: 'true',
});
const res = await fetch(`https://api.screenshotneo.com/v1/shot?${q}`);
if (!res.ok) throw new Error(`Screenshot request failed: ${res.status}`);
await import('node:fs/promises').then(({ writeFile }) =>
writeFile('shot.webp', Buffer.from(await res.arrayBuffer()))
);
ScreenshotNeo also has an MCP server for AI agents, with screenshot, page-info, and PDF capture tools. The free plan includes 1,000 screenshots per month with no card; paid plans start at $5 for 3,000 screenshots. Sign up for 1,000 free screenshots a month, with no card.
FAQ
Does “full page” include every scrollable panel?
Do not assume it does. Confirm which element scrolls and whether the footer is part of the document or an inner panel.
Should I change the footer CSS to fix the screenshot?
Only if inspection shows a CSS rule or ancestor layout is causing the problem. First verify the capture mode and scroll container.
Why is the footer missing from an automated screenshot but visible when I browse?
The automated capture may run before the footer or its content is ready, or it may not reflect the same scroll state. Wait for a page-specific ready condition and inspect the resulting DOM.
Is this issue specific to websites in India?
The available browser guidance describes general capture and CSS inspection workflows; it does not establish a distinct India-specific cause.


