How to Take Playwright Screenshots with Reduced Motion Enabled
Emulate the reduced-motion preference for a Playwright screenshot, configure it across tests, and distinguish it from disabling animations during capture.
To take a Playwright screenshot with the page’s reduced-motion preference enabled, call page.emulateMedia({ reducedMotion: 'reduce' }) before capturing. For a one-off capture:
await page.emulateMedia({ reducedMotion: 'reduce' });
await page.screenshot({ path: 'screenshot.png' });
This tells the browser to report prefers-reduced-motion: reduce to the page. The site decides how to respond; the preference does not automatically remove every animation. If you need the screenshot operation itself to suppress animations, use the separate animations: 'disabled' screenshot option. See Playwright’s Page API documentation.
1. Capture one page with reduced motion
Here is a runnable Node.js example using Playwright. Install Playwright in your project with npm install playwright, then save this as screenshot.js and run node screenshot.js.
const { chromium } = require('playwright');
(async () => {
const browser = await chromium.launch();
try {
const page = await browser.newPage();
await page.emulateMedia({ reducedMotion: 'reduce' });
await page.goto('https://example.com', { waitUntil: 'load' });
await page.screenshot({ path: 'screenshot.png', fullPage: true });
} finally {
await browser.close();
}
})();
Set the media preference before navigation when you want page scripts to observe it as the site initializes. Calling it after navigation still changes the emulated media feature for subsequent rendering, but any earlier script behavior has already occurred. Capture to a file with path, or omit path to receive an image buffer:
const image = await page.screenshot();
2. Apply reduced motion to a Playwright Test project
When every page in a project should use the same preference, declare it in the Playwright Test configuration. The documented default is no-preference; valid values are reduce, no-preference, and null. See the TestOptions reference.
import { defineConfig } from '@playwright/test';
export default defineConfig({
use: {
reducedMotion: 'reduce',
},
});
A test can then capture a visual snapshot without repeating the media setting:
import { test, expect } from '@playwright/test';
test('reduced-motion view', async ({ page }) => {
await page.goto('https://example.com');
await expect(page).toHaveScreenshot();
});
Prefer project configuration for a consistent project-wide setting. Use page.emulateMedia() when only a particular operation or test needs it, or when making the preference explicit next to the capture helps explain the test.
3. Reduced-motion preference versus disabled animations
These controls solve related but different problems:
| Control | What it changes | Use it when |
|---|---|---|
reducedMotion: 'reduce' via emulateMedia() or test config |
The browser’s prefers-reduced-motion media preference, which page CSS and JavaScript may read |
You want to capture or test the site’s reduced-motion presentation |
animations: 'disabled' on page.screenshot() |
CSS animations, CSS transitions, and Web Animations during the screenshot | You want to suppress those animations while taking the image, regardless of how the page responds to the preference |
Combine them when the goal is both to have the site render its reduced-motion experience and to prevent supported animations from affecting the captured image:
await page.emulateMedia({ reducedMotion: 'reduce' });
await page.screenshot({
path: 'screenshot.png',
animations: 'disabled',
});
Use only the preference when you are testing the site’s accessibility behavior. Use only screenshot-time suppression when you need a still image but are not testing the site’s reduced-motion response. Playwright also allows reducedMotion: 'no-preference' to emulate the standard preference and null to disable emulation.
4. Keep visual screenshots stable
For visual regression checks, a reduced-motion preference can make the page’s intended presentation more predictable, but it does not guarantee pixel-identical output. Playwright’s visual comparison documentation notes that rendering can vary with the operating system, browser version, settings, hardware, power source, and headless mode. Keep baseline creation and comparison runs in a consistent environment where practical. See Playwright’s visual comparisons guide.
toHaveScreenshot() waits for two consecutive screenshots to match during initial baseline creation, then saves the last one. If a page still changes between captures, inspect other sources of variation such as asynchronous content, timestamps, randomized data, fonts, and image loading; reduced motion only addresses the media preference and animation behavior described above.
5. Troubleshooting
| Symptom | Likely cause | Fix |
|---|---|---|
| The screenshot still contains motion or an animated-looking frame | The site does not change its behavior for prefers-reduced-motion, or the effect is not controlled by CSS animations, transitions, or Web Animations |
Check the site’s reduced-motion implementation. For supported animations during capture, add animations: 'disabled'. |
| The site behaves as if motion is allowed | The preference was set after page code already made a one-time decision | Emulate reduced motion before page.goto(), or set use.reducedMotion in Playwright Test configuration. |
| Visual snapshots differ on another machine or CI run | Rendering environment differences can change pixels even when the test code is unchanged | Use a consistent operating system, browser version, settings, and execution mode for baselines and comparisons. |
| Configuration has no effect on a standalone script | use.reducedMotion is a Playwright Test option, not a setting automatically applied to every standalone Playwright script |
Call page.emulateMedia({ reducedMotion: 'reduce' }) in the script. |
| Screenshot returns data instead of creating a file | No screenshot path was supplied | Pass { path: 'screenshot.png' } to write a file, or use the returned buffer directly. |
6. Performance, reliability, and cost
Reduced-motion emulation is a browser setting, not a separate screenshot service or a guarantee that the page will finish loading sooner. Navigation, page scripts, network requests, and rendering still determine when the page is ready. Use the readiness condition that matches the page and test what the site actually renders with the preference enabled.
For reliable visual comparisons, pin the browser and keep the execution environment consistent with the one used to create the baseline. If you intentionally change the browser version, operating system, or rendering mode, expect that the visual baseline may need review. Browser automation also means maintaining a browser runtime and handling page navigation in your own environment.
7. Or skip the browser setup
If you need a screenshot through an API instead of managing a Playwright browser, ScreenshotNeo takes a screenshot from one GET request. See the API documentation for its request options. This is a service-side capture workflow; it does not expose Playwright’s reducedMotion option, so use Playwright above when specifically testing that browser media preference.
curl -G "https://api.screenshotneo.com/v1/shot" -d access_key=YOUR_API_KEY --data-urlencode url=https://example.com -o shot.webp
Cookie and consent banners, newsletter popups, and chat widgets are removed before the shot; each cleanup step can be turned off. Bot checks, blank pages, failed loads, timeouts, and cache hits are not billed, and response headers report the page verdict and billing status. ScreenshotNeo also provides an MCP server with take_screenshot, get_page_info, and capture_pdf tools for AI agents. The free plan includes 1,000 screenshots a month with no card; paid plans start at $5 for 3,000 screenshots.
Sign up for ScreenshotNeo’s free plan and get 1,000 screenshots a month with no card.
8. FAQ
What does reducedMotion: 'reduce' emulate?
It makes the browser report the prefers-reduced-motion: reduce media preference to the page. The page determines how to respond.
Can I turn reduced-motion emulation off?
Yes. Use page.emulateMedia({ reducedMotion: null }) in a page operation, or set the Playwright Test option to null.
Should I use animations: 'disabled' for every screenshot?
No. Add it when the capture should suppress supported animations. It is separate from emulating the user’s reduced-motion preference.
Can I use the setting for a single Playwright Test?
Yes. Call page.emulateMedia() in that test before the screenshot. Configure use.reducedMotion when the preference should apply across a project.


