CSS paged media turns a continuous HTML document into discrete page boxes for paper or PDF. Use @media print for print-specific presentation (such as hiding navigation), and @page for page dimensions, margins and page-level rules. Then control breaks, render in the exact browser or PDF engine you will ship, and inspect the resulting pages. Standards describe the model, but browser support remains feature- and version-dependent.
The CSS page model
In paged media, content is split across discrete pages. Each page has a page box, a page area where content is laid out, and a surrounding margin area. CSS paged-media specifications also define page selectors, breaks and widow/orphan controls. The CSS Paged Media Level 3 specification is a Working Draft dated 14 September 2023, so it describes an evolving standard rather than a promise that every renderer implements every feature.
Think of the model in layers:
- Document content: your HTML elements and normal layout.
- Print presentation: rules inside
@media print. - Page geometry:
@pagesize, margins and page selectors. - Pagination: break properties, widows/orphans and the renderer’s own algorithms.
@media print versus @page
Use @media print for document presentation
This media query applies when a user prints or saves to PDF. It is the right place to remove interactive controls, alter colors, simplify navigation and adjust ordinary elements.
@media print {
nav,
.screen-only,
.chat-widget,
button {
display: none !important;
}
body {
color: #000;
background: #fff;
font: 10.5pt/1.45 Georgia, serif;
}
a {
color: inherit;
text-decoration: none;
}
}
Use @page for page-level layout
@page sets the paper or PDF page size and its margins. It does not select arbitrary HTML descendants or replace normal layout rules.
Do these 3 things before closing this tab:
1Clear out junk files and repair common Windows errors2Scan for outdated or missing drivers - takes under a minute3Repair Windows errors before they cause bigger problems#1 Best Overall
- HTML CSS Design and Build Web Sites
- Comes with secure packaging
- It can be a gift option
@page {
size: A4 portrait;
margin: 20mm;
}
@page :first {
margin-top: 28mm;
}
@page :left {
margin-left: 22mm;
margin-right: 18mm;
}
@page :right {
margin-left: 18mm;
margin-right: 22mm;
}
Use physical units deliberately, but verify the result: browser print dialogs can apply scaling, selectable paper sizes and margin settings that alter the final output.
A practical print stylesheet
Start with a screen document that has semantic headings, lists and tables. Add a print stylesheet that defines page geometry, removes screen-only UI and protects important blocks.
@page {
size: A4;
margin: 18mm 18mm 22mm;
}
@media print {
* {
box-shadow: none !important;
text-shadow: none !important;
}
nav, aside, .screen-only, video, form {
display: none !important;
}
h1, h2, h3 {
break-after: avoid;
}
h1, h2, h3, figure, table, pre {
break-inside: avoid;
}
.chapter {
break-before: page;
}
p, li {
orphans: 3;
widows: 3;
}
img {
max-width: 100%;
height: auto;
}
a[href^="http"]::after {
content: " (" attr(href) ")";
overflow-wrap: anywhere;
}
}
Legacy aliases such as page-break-before still appear in older stylesheets, but the modern break-before, break-after and break-inside properties express the intent more clearly. If an older target requires an alias, include both and test the output.
How to control page breaks when printing a webpage
- Mark logical starts. Add a class such as
chapterto sections that should begin on a fresh page. - Prevent damaging splits. Apply
break-inside: avoidto figures, callouts, code samples and short tables. It is a request; if an element is taller than a page, it must split or overflow. - Keep headings with content. Use
break-after: avoidon headings and consider a small top margin on the following block. - Control table behavior. Use repeating table headers where the target engine supports them, keep rows reasonably short, and avoid placing a giant unbreakable row on the page.
- Handle long code. Set a print font size, allow wrapping where acceptable, or deliberately permit horizontal overflow for source listings that must remain exact.
- Check widows and orphans. These properties improve paragraph endings but cannot override every layout constraint.
Do not force a break after every heading. Excessive forced breaks create nearly empty pages and make small content changes cascade into a different document.
Quick wins for a faster PC:
Repair Windows errors before they cause bigger problemsFix Now →Fix the driver behind crashes, sound loss and screen glitchesFind Drivers →Rank #2
How do I add page numbers or headers and footers to a PDF with CSS?
Page-margin boxes are the standards-oriented mechanism for content in page margins. Support varies substantially. Chrome for Developers documents that Chrome 131 added generated content in page margins by targeting margin at-rules; that milestone does not mean universal support for running headers, footnotes, counters, bleed or all Level 3 features.
@page {
@top-right {
content: "Technical guide";
font-size: 9pt;
color: #666;
}
@bottom-center {
content: "Page " counter(page) " of " counter(pages);
font-size: 9pt;
}
}
Whether this renders depends on the browser or dedicated engine. Test page counters, named pages, left/right selectors and margin content in the exact version used for production. If the target cannot generate reliable running content, put a footer element in the document as a fallback, accept that it will not repeat on every page, or use a pagination engine with documented support.
Does my browser support CSS page-margin boxes?
There is no useful blanket answer such as “supports CSS Paged Media.” Chrome and Firefox support @page according to Chrome’s developer documentation, while individual features have different histories. Chrome 131 is a concrete milestone for generated page-margin content. Browser print settings, fonts, platform, page size and document content can still change output.
- Pin the browser or renderer version in automated builds.
- Test with the actual fonts installed or bundled in production.
- Check print-background and scale settings in the print dialog or headless command.
- Inspect first, middle and last pages, facing pages, long tables, images and forced breaks.
- Keep a PDF fixture in CI and compare it when changing CSS or the rendering engine.
A repeatable browser-to-PDF workflow
- Define the physical page. Choose size, orientation, margins and whether left/right pages need different geometry.
- Separate print presentation. Hide navigation and controls, set readable print colors and remove screen-only decoration inside
@media print. - Annotate break decisions. Add classes for chapters, figures and callouts; use modern break properties sparingly.
- Render in the target environment. Use the browser version, fonts, locale, viewport and print settings that your users or build server will use.
- Inspect the PDF visually and structurally. Look for clipped content, blank pages, missing backgrounds, split headings, orphan lines, unreadable URLs and broken links.
- Automate only after visual acceptance. A headless command makes output repeatable, but it does not make unsupported CSS work.
Choosing an output engine
| Option | Best fit | Important constraint |
|---|---|---|
| Native browser printing | Simple print styles, page size, margins and manageable breaks; maximum fidelity to what users see in a browser | Behavior depends on browser implementation and print settings |
| Paged.js | Paginated browser previews and a scriptable HTML/CSS-to-PDF workflow | It is a JavaScript polyfill; its CLI uses a headless browser, so browser handling of @page { size } can remain limiting |
| Prince | Workflows needing documented page rules and page-margin regions for headers, footers and other page content | Evaluate current compatibility and commercial terms against your requirements |
| Antenna House Formatter | Print-publishing workflows that need a dedicated CSS formatter | The cited AH Formatter V6.6 reference is historical; verify the current release and terms directly |
Choose by required page features (counters, facing pages, footnotes, specialized regions), browser fidelity, automation and licensing. A dedicated renderer may provide stronger pagination controls, while a browser remains the right choice when matching live web rendering is the priority.
Free tools Windows power users keep installed
One-click scans. No signup required.
Rank #3
- Brand: Wiley
- Set of 2 Volumes
- A handy two-book set that uniquely combines related technologies Highly visual format and accessible language makes these books highly effective learning tools Perfect for beginning web designers and front-end developers
Paged.js in a build
Paged.js paginates in the browser and documents both print styles and a headless-browser CLI path to PDF. A typical workflow is to load your HTML and stylesheet, let pagination complete, then export the resulting document. Treat its output as browser-dependent and test page size, fonts, margin content and breaks in the same environment used by CI.
Performance, reliability and cost considerations
- Reduce layout surprises: reserve image dimensions, optimize large images and avoid scripts that continually mutate the DOM during capture.
- Make resources deterministic: bundle or pin fonts and stylesheets, and wait for images and web fonts before printing.
- Keep documents modular: very long files are easier to debug when chapters can be rendered independently.
- Measure the right failure: a successful HTTP response can still contain a blank page, missing font or clipped table; inspect rendered pages.
- Budget for the engine: native printing has no separate renderer license, Paged.js is open source under the MIT license, and commercial engines require checking current pricing and terms directly.
Or skip the browser setup
ScreenshotNeo is a website screenshot API and MCP server. One request can return PNG, JPEG, WebP or PDF, while its capture pipeline accepts cookie and consent banners and removes more than 60 known consent platforms, newsletter popups and chat widgets before capture. Bot checks, CAPTCHAs, blank pages, timeouts, failed loads and cache hits are not billed, and response headers identify the page verdict and billing status.
For a PDF or image of a URL, use the API documented at https://screenshotneo.com/docs/:
curl -G "https://api.screenshotneo.com/v1/shot" -d access_key=YOUR_API_KEY --data-urlencode url=https://example.com -o shot.webp
import requests
r = requests.get("https://api.screenshotneo.com/v1/shot", params={"access_key": "YOUR_API_KEY", "url": "https://example.com"}, timeout=90)
open("shot.webp", "wb").write(r.content)
const q = new URLSearchParams({ access_key: 'YOUR_API_KEY', url: 'https://example.com' });
const res = await fetch(`https://api.screenshotneo.com/v1/shot?${q}`);
It also offers an MCP server for Claude, Cursor and other MCP clients, with take_screenshot, get_page_info and capture_pdf. Features include full-page capture with lazy images loaded, CSS-selector element capture, custom CSS and JavaScript, waiting for selectors or network idle, request blocking, cookies and headers, device presets, PDF margins and page ranges, asynchronous jobs and bulk capture.
The Free plan includes 1,000 screenshots per month with no card. Paid plans start at $5 for 3,000 shots; every feature is on every plan. Create a free ScreenshotNeo account to try it.
Rank #4
Troubleshooting common failures
Everything prints on one continuous sheet
Confirm the print preview is actually using print media and that the target is a paged output. Check that the browser’s paper size and margins are not set to a custom continuous format.
A forced break is ignored
Inspect the element for display: inline, transforms, overflow containers or an ancestor that the engine cannot fragment. Move the break to a block-level wrapper and test break-before: page plus the legacy alias if an older engine is involved.
Headers or page numbers are missing
Verify that the target engine implements the specific margin at-rule and counter you use. Chrome 131’s documented milestone is not evidence of universal support. Remove unsupported rules or switch to a renderer with documented page-margin capabilities.
PC Slower Than It Used to Be?
A free scan shows the junk files, broken settings and background clutter dragging Windows down - then fixes them in one click.Free scan · Windows 10 & 11Crashes, No Sound, or Screen Glitches?
Random freezes, missing sound and display glitches usually trace back to one bad driver. Find and replace yours safely.Free scan · under a minuteImages or fonts are absent
Use absolute, reachable URLs or bundle assets, wait for fonts and images before export, and check cross-origin and authentication requirements. Reserve image dimensions to prevent late reflow.
Best Value
The PDF has unexpected blank pages
Look for consecutive forced breaks, a chapter that already starts after an automatic break, oversized unbreakable blocks or an :left/:right selector forcing a parity page. Remove one constraint at a time.
Content is clipped
Check print scaling, page margins, fixed heights, transforms and overflow. Replace fixed pixel widths with print-friendly widths and allow long URLs or code to wrap where fidelity permits.
Validation checklist
- Correct paper size and orientation.
- Margins match the specification and printer-safe area.
- Every chapter, heading, figure and table starts or splits intentionally.
- Fonts, colors, backgrounds and images survive PDF export.
- Page numbers, headers, footers and links work in the target engine.
- Long content, RTL or non-Latin text, and missing assets have been tested where relevant.
- The exact browser or renderer version and print settings are recorded for reproducibility.
Frequently Asked Questions
Can CSS guarantee identical PDFs in Chrome, Firefox and a dedicated renderer?
No. The standards define the page model, but implementations differ by feature and version. Validate the engine, fonts, settings and content used for delivery.
When should I move beyond native browser printing?
Stay with native printing for straightforward page geometry and breaks. Evaluate Paged.js or a dedicated renderer when you need repeatable automation, browser previews, advanced margin content, footnotes, facing-page logic or specialized page regions.
Does break-inside: avoid guarantee that an element stays on one page?
No. It is a fragmentation preference. An element taller than the page, or one constrained by other layout rules, must still split or overflow.
Quick Recap
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.

