·SavePage Team

The Technical Challenges of Full Page Screenshot Capture

engineeringfull-pagechrome

A full page screenshot captures the entire scrollable content of a web page as a single image. It sounds simple: scroll to the bottom, take a picture. In practice, it involves a series of technical challenges that we had to solve one by one.

Determining page height

The first challenge is figuring out how tall the page actually is. You might think document.body.scrollHeight gives you the answer, but it is unreliable. Different layout modes, overflow settings, and CSS properties can cause the reported height to be wrong.

We use a combination of measurements:

const height = Math.max(
  document.body.scrollHeight,
  document.body.offsetHeight,
  document.documentElement.scrollHeight,
  document.documentElement.offsetHeight
);

Even this is not perfect. Some pages have content that is absolutely positioned outside the normal flow, which is not captured by scroll height measurements.

Lazy loading

Modern websites load images and content as the user scrolls. If you take a full page screenshot without scrolling, you get placeholder images and empty sections below the fold.

Our approach is to simulate scrolling before capture. The renderer scrolls through the page in increments, pausing at each position to trigger lazy loading. After reaching the bottom, it scrolls back to the top and waits for any remaining network requests to complete.

This adds time to the capture process. A page that takes 2 seconds for a viewport screenshot might take 8-10 seconds for a full page capture.

Infinite scroll

Some pages never end. Social media feeds, search results, and content aggregators load more content as you scroll. If the renderer keeps scrolling, it never reaches the bottom.

We handle this with a height cap. If the page height exceeds a configurable maximum (default: 15,000 pixels), we stop and capture what we have. The API response includes the actual captured height so the caller knows if the page was truncated.

Fixed and sticky elements

Navigation bars, cookie banners, and floating action buttons use position: fixed or position: sticky in CSS. In a full page screenshot, these elements appear at every scroll position, creating visual artifacts.

For fixed elements, we temporarily change their position to absolute before capture so they only appear at their natural location on the page. Sticky elements are handled similarly. This produces a cleaner full page image.

Memory constraints

A full page screenshot of a long page at 1440px wide can produce very large images. A 15,000 pixel tall page at 1440px wide and 32 bits per pixel requires about 82 MB of uncompressed bitmap data. At 2x scale, that quadruples to 328 MB.

The Chromium renderer has memory limits for screenshot buffers. We manage this by:

  • Capping the maximum page height
  • Limiting the device scale factor for full page captures
  • Compressing to PNG or JPEG immediately after capture
  • Monitoring memory usage per render process

The results

Despite these challenges, full page capture works reliably for the vast majority of websites. The edge cases are handled gracefully with truncation, timeouts, and clear error messages. The fullpage=true parameter is one of our most-used features.