Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.

Some links on this page are affiliate links: if you buy through them we may earn a commission, at no extra cost to you.

Use a browser automation library such as Playwright to open a page and capture it from Node.js. A normal screenshot shows the current viewport; set fullPage: true for the scrollable page, or use Playwright’s locator screenshot method to capture one element. Save directly to a file with path, or capture image bytes when you need to upload or process them.

Capture a website with Playwright

Playwright’s Page API provides the basic flow: launch a browser, navigate to a URL, capture the page, then close the browser. Install the package and its Chromium browser in your project:

npm install playwright
npx playwright install chromium

Save this as screenshot.js and run it with node screenshot.js:

Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.
const { chromium } = require('playwright');

(async () => {
  const browser = await chromium.launch();
  try {
    const page = await browser.newPage();
    await page.goto('https://example.com');
    await page.screenshot({ path: 'screenshot.png', fullPage: true });
  } finally {
    await browser.close();
  }
})();

The path option writes the image to a file. The finally block closes the browser even if navigation or capture fails, avoiding a browser process left running. The example uses Playwright’s documented page workflow and combines it with the documented full-page option; it is an illustrative pattern, not a report of a local test. Playwright Page API · Playwright Screenshots guide.

Choose when navigation is considered complete

page.goto() navigates to the URL before capture. For pages that continue loading content after their initial document appears, select a readiness condition that fits the site rather than assuming that an early screenshot includes every image or widget. You can wait for a known element before taking the shot:

await page.goto('https://example.com');
await page.locator('main').waitFor();
await page.screenshot({ path: 'screenshot.png' });

Waiting for a selector helps when the page has a clear element that indicates the content you need is present. It does not guarantee that every image, animation, or third-party resource has finished changing; make the readiness check specific to the page and purpose.

Choose viewport, full-page, or element capture

Viewport screenshot

Without a full-page option, a screenshot captures the visible browser viewport. Use this for a particular above-the-fold state or when the output should match what a user sees at a chosen window size.

Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.

Full-page screenshot

Set fullPage: true to capture the page’s full scrollable content:

await page.screenshot({ path: 'full-page.png', fullPage: true });

This is useful for archiving a long page or reviewing its overall layout. Some pages load content as you scroll or have sticky elements whose appearance depends on scroll position. A full-page option does not itself prove that all lazy content has loaded; verify the target page’s behavior if completeness matters.

Element screenshot

Use a locator when only one component matters, such as a banner, chart, or product card:

await page.locator('.header').screenshot({ path: 'header.png' });

Replace .header with a selector that uniquely identifies the desired element. If a locator matches more than one element or the target is not yet rendered, wait for or refine the locator before capturing.

Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.

Save to a file or capture bytes

Use path when the output should be a file. When a later step will upload, compare, or transform the screenshot, capture it in memory instead. Playwright’s screenshot method can return a buffer:

const image = await page.screenshot({ fullPage: true });
// Pass image to an uploader or image-processing function.

The exact handling after capture depends on the receiving library; the bytes can be passed directly to code that accepts a Node.js buffer. The Playwright guide documents both file-path and buffer capture examples: Screenshots guide.

Use Puppeteer if it fits your project

Puppeteer is another browser automation library with a page screenshot API. It may be a natural choice if your application already uses Puppeteer; the available documentation does not establish a universal winner between it and Playwright. Its screenshot method returns a Uint8Array by default, or a base64 string when base64 encoding is requested. Set path to save an image file.

const puppeteer = require('puppeteer');

(async () => {
  const browser = await puppeteer.launch();
  try {
    const page = await browser.newPage();
    await page.goto('https://example.com');
    await page.screenshot({ path: 'screenshot.png', fullPage: true });
  } finally {
    await browser.close();
  }
})();

Puppeteer documents options including fullPage, clip, type, quality, and omitBackground. PNG is the default; when a path has an image extension, the type can be inferred from that extension. Its quality setting applies to formats other than PNG. omitBackground can be used for a transparent background. See Puppeteer Page.screenshot and ScreenshotOptions for the precise API options for your installed version.

Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.

Control output dimensions and appearance

The screenshot reflects the browser page’s rendering conditions. For repeatable output, decide on the viewport and other browser settings that matter to your use case, then keep them consistent. Choose the capture mode according to the desired artifact:

  • Visible screen: use the default viewport screenshot.
  • Scrollable page: enable fullPage.
  • One component: capture a locator in Playwright, or use a clipped region where supported by the library.
  • Transparent output: Puppeteer documents omitBackground; confirm the output format and downstream image handling.
  • Bytes for further processing: omit the output path and use the returned data.

Do not assume that a filename extension alone controls every output detail. Puppeteer documents type inference from a path extension, while also exposing an explicit type option; check the selected library’s API if exact format behavior matters.

Make visual screenshots comparable

Screenshot-based visual checks are sensitive to the rendering environment. Playwright notes that operating system, browser version, settings, hardware, power source, and headless mode can all affect screenshot output. Generate and compare baselines in a consistent environment, and inspect baseline updates instead of accepting them blindly. Playwright visual comparisons.

Playwright Test also has a screenshot assertion, toHaveScreenshot(). It belongs to the Playwright Test runner rather than being a general assertion added to every script. The documented behavior waits for two consecutive screenshots to match before comparing the last capture against the expectation. This stability step helps avoid comparing an intermediate frame, but it does not remove the need for consistent environments. See PageAssertions API.

Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.

Or skip the browser setup

If you need a screenshot endpoint rather than managing a browser process, ScreenshotNeo accepts a URL in one GET request and returns a PNG, JPEG, WebP, or PDF. For Node.js, the documented request pattern is:

const q = new URLSearchParams({ access_key: 'YOUR_API_KEY', url: 'https://example.com' });
const res = await fetch(`https://api.screenshotneo.com/v1/shot?${q}`);

Replace YOUR_API_KEY with your key. The call uses Node.js’s built-in fetch; use a recent Node.js release that provides it, or your project’s HTTP client if needed. The response body can be written to a file or passed into the next step of your workflow. See the ScreenshotNeo API documentation for request options and response details.

  • Cookie/consent banners, newsletter popups, and chat widgets are removed before capture; each of those cleanup steps can be turned off.
  • Bot checks/CAPTCHAs, blank pages, timeouts, failed loads, and cache hits are not billed. Response headers indicate the page verdict and billing status.
  • An MCP server provides take_screenshot, get_page_info, and capture_pdf tools for AI agents and other MCP clients.
  • The Free plan includes 1,000 screenshots per month with no card; paid plans start at $5 for 3,000 shots.

Sign up for ScreenshotNeo’s free plan to start with 1,000 screenshots a month and no card.

Independent reader supportYour contribution helps us test, update, and keep practical guides available for everyone.Support on Ko-Fi

Troubleshoot common capture problems

The screenshot is blank or shows an incomplete page

Check whether navigation completed and whether the content you need appears only after a script, selector, or user interaction. Wait for a page-specific element before capture. For content loaded on scroll, test whether the site requires scrolling to trigger it; the full-page setting alone is not a guarantee that every lazy-loaded image has loaded.

Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.

The saved image has the wrong size

Confirm whether you intended the visible viewport, a full page, or a single element. The default viewport capture is not equivalent to a full-page capture. For element capture, confirm that the chosen locator identifies the intended component.

The output format or transparency is unexpected

In Puppeteer, PNG is the default screenshot type, the type can be inferred from a path extension, and quality applies to non-PNG formats. Set the explicit type and relevant options when format matters; use omitBackground for the documented transparent-background behavior. Check the actual bytes or open the output in the tool that will consume it.

A visual test fails despite no intended change

Keep the operating system, browser version, settings, and headless mode consistent with the environment that generated the baseline. Review changed snapshots to determine whether the difference is an actual interface change or a rendering variation. Playwright’s visual comparison documentation describes these sources of variation: Visual comparisons.

The Node.js process does not exit

Ensure that the browser is closed after capture, including on an error path. A try/finally around navigation and screenshot work, as in the examples above, makes cleanup explicit.

What’s actually slowing this PC down?

Pick the symptom - the matching free tool is one click away.

Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.

Performance, reliability, and cost considerations

With Playwright or Puppeteer, your code launches and controls a browser, so your application is responsible for the browser runtime and its cleanup. That approach gives you direct control over the page workflow and output handling, but the capture is subject to the target page’s loading behavior and the environment in which the browser runs. Reusing an existing library can avoid adding a second automation stack to a project; a hosted endpoint can be more convenient when you do not want to run browser infrastructure yourself.

No speed, reliability, or cost benchmark between Playwright and Puppeteer is established here. Their APIs both support the core screenshot workflow, and the right choice depends on what your project already uses and whether you need a direct browser workflow or a hosted capture endpoint. For screenshot cost planning with ScreenshotNeo, consult its current plan information at ScreenshotNeo; the listed monthly allowances and prices are Free 1,000 at no card, Starter $5 for 3,000, Growth $15 for 15,000, Pro $39 for 60,000, Scale $99 for 250,000, and Business $249 for 1,000,000. Yearly billing gives two months free, and every feature is on every plan.

Choose a method for your use case

Need Good fit Why
One-off capture or custom browser interaction Playwright or Puppeteer Run navigation and capture directly in your Node.js program.
Save an image for later use Either library with a path option The screenshot is written to a file during capture.
Upload or process image data in code Either library’s in-memory result Avoid writing a temporary file when the next step accepts bytes.
Viewport, full-page, or element image Choose based on the required region Use the default viewport, fullPage, or a Playwright locator screenshot as appropriate.
Automated visual regression checks Playwright Test Its screenshot assertion and baseline workflow are designed for snapshot comparisons.
Capture without managing a local browser ScreenshotNeo Send a URL to a screenshot API; its billing headers identify whether a response was billed.

Frequently Asked Questions

Can I take a screenshot without saving it to disk?

Yes. Playwright can return screenshot bytes when you omit the path, and Puppeteer returns a Uint8Array by default.

Does Playwright’s screenshot assertion work in any Node.js script?

No. The documented `toHaveScreenshot()` assertion is part of Playwright Test.

Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.

Product prices and availability are accurate as of the date/time indicated and are subject to change. Any price and availability information displayed on Amazon at the time of purchase will apply.