October DealsAmazon USOctober deal check: compare before you payAmazon US: current deals, useful picks and tech finds.Check DealsPC HealthRecommendedCrashes, freezes, slowdowns? Check your PC nowSpot repairable issues before they interrupt work.Check PCOctober DealsAmazon USDeal season is back - check today's better picksAmazon US: current deals, useful picks and tech finds.See Picks×
Skip to content
html2canvas

How to Render SVGs in PDFs with pdfmake and html2canvas

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

Use pdfmake’s native svg node when you already have SVG artwork. It preserves the vector source in the PDF workflow and avoids an unnecessary rasterization step. Use html2canvas instead when the thing you need in the PDF is a rendered DOM component—HTML, CSS, and an SVG mixed together. html2canvas turns that element into a canvas image, so its result is raster data and is not a pixel-perfect browser screenshot.

The choice depends on your input and runtime: standalone SVG favors pdfmake; arbitrary DOM favors html2canvas in a browser. The examples below show both paths, including dimensions, remote-image restrictions, large-canvas limits, and a server-side alternative.

Choose the rendering path first

Situation Recommended path What enters the PDF Main constraint
You have an SVG string or an existing browser SVGElement pdfmake svg node SVG artwork handled directly by pdfmake The SVG needs valid dimensions, either inside the SVG or on the node
You need an HTML/CSS component, including inline SVG inside it html2canvas, then pdfmake image data A rasterized canvas image Only CSS properties implemented by html2canvas render correctly
The code runs only in Node.js Use a browser context for html2canvas, or choose another server-capable renderer Depends on the renderer html2canvas requires browser APIs such as window and document

These are different interfaces, not interchangeable “SVG converters.” pdfmake expects a valid SVG value; html2canvas reconstructs an image from the DOM information it can read.

Render an SVG directly with pdfmake

This is the shortest and usually the highest-quality route for logos, diagrams, icons, charts, and other artwork that already exists as SVG. The current pdfmake SVG documentation shows SVG markup as a string and, in a browser, an SVGElement. The documented SVG feature page uses pdfmake 0.3.2; passing an SVGElement requires 0.3.1 or later.

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

Use an SVG string

const svg = `<svg xmlns="http://www.w3.org/2000/svg" width="640" height="240" viewBox="0 0 640 240">
  <rect width="640" height="240" rx="24" fill="#111827"/>
  <circle cx="100" cy="120" r="52" fill="#38bdf8"/>
  <text x="180" y="138" fill="white" font-size="52" font-family="Arial">Report</text>
</svg>`;

const docDefinition = {
  content: [
    { text: 'Quarterly report', style: 'heading' },
    { svg, width: 320 }
  ],
  styles: { heading: { fontSize: 18, bold: true, marginBottom: 12 } }
};

pdfMake.createPdf(docDefinition).download('report.pdf');

Give the SVG a real width and height, as in the example, or set dimensions on the node. The viewBox describes the artwork’s coordinate system; it does not by itself guarantee that pdfmake knows the rendered size.

Use a browser SVGElement

const element = document.querySelector('#logo');

if (!(element instanceof SVGElement)) {
  throw new Error('Expected an SVGElement');
}

const docDefinition = {
  content: [{ svg: element, fit: [360, 160] }]
};

pdfMake.createPdf(docDefinition).open();

An SVGElement is a browser object, so this form belongs in a browser application. If you need to support older pdfmake versions, pass serialized markup instead and confirm the version’s SVG support.

Control size without distortion

  • Set only width or only height to scale proportionally.
  • Use fit: [maxWidth, maxHeight] to place the SVG inside a bounding box while preserving its aspect ratio.
  • Set both width and height only when stretching to those exact dimensions is intentional.
  • If pdfmake reports a missing or invalid SVG, check that the value is a complete SVG element with the SVG namespace and that its dimensions are present.

The pdfmake 0.3.2 changelog specifically notes that SVG width and height must be specified in the SVG string or element, or on the svg node.

Render a DOM component with html2canvas, then add it to pdfmake

Choose this path when your source is a page component rather than a standalone SVG: for example, a styled invoice card containing text, CSS backgrounds, and inline graphics. html2canvas returns a promise for a canvas representing the selected DOM element. It does not read the browser’s final screen pixels; it rebuilds a representation from DOM and supported CSS properties.

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

Complete browser example

import html2canvas from 'html2canvas';

async function exportCard() {
  const target = document.querySelector('#invoice-card');
  if (!target) throw new Error('Invoice element was not found');

  // Wait for fonts and images that affect layout.
  if (document.fonts?.ready) await document.fonts.ready;
  await Promise.all(
    [...target.querySelectorAll('img')].map(img =>
      img.complete ? Promise.resolve() : new Promise(resolve => {
        img.addEventListener('load', resolve, { once: true });
        img.addEventListener('error', resolve, { once: true });
      })
    )
  );

  const canvas = await html2canvas(target, {
    backgroundColor: '#ffffff',
    scale: Math.min(window.devicePixelRatio || 1, 2),
    useCORS: true,
    logging: false
  });

  const imageData = canvas.toDataURL('image/png');
  const docDefinition = {
    pageMargins: [36, 36, 36, 36],
    content: [{ image: imageData, width: 520 }]
  };

  pdfMake.createPdf(docDefinition).download('invoice.pdf');
}

document.querySelector('#export').addEventListener('click', exportCard);

In this example, the SVG is captured as part of the component and becomes PNG data. Inspect the PDF at its intended display or print size: increasing scale increases pixel dimensions and memory use, but does not add CSS features that html2canvas does not implement.

Capture only the SVG as a canvas

If the SVG is inside a larger component but you deliberately want raster output, select the SVG’s container:

const svgWrapper = document.querySelector('#chart-wrapper');
const canvas = await html2canvas(svgWrapper, { backgroundColor: null });
const dataUrl = canvas.toDataURL('image/png');

pdfMake.createPdf({
  content: [{ image: dataUrl, width: 400 }]
}).download('chart.pdf');

For an SVG that is already complete artwork, the native pdfmake route is generally preferable because it avoids this raster step.

Dimensions, quality, and page layout

Fit the PDF page deliberately

pdfmake measures image placement in PDF points. A canvas has pixels. Setting width on the pdfmake image controls its displayed size; it does not change the canvas’s underlying pixel count. Pick a CSS width that matches the intended component size, choose a moderate capture scale, and then set a PDF width that fits between the page margins.

Free tools Windows power users keep installed

One-click scans. No signup required.

Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.
Rank #2
Sale
Adobe Acrobat 6 PDF For Dummies
  • Used Book in Good Condition

Preserve aspect ratio

For native SVG, one dimension or fit preserves proportions. For a canvas image, provide a width and let pdfmake derive the height, or calculate the ratio yourself. Avoid forcing unrelated width and height values, which will visibly stretch charts and logos.

Large captures

Canvas maximum dimensions and total-area limits vary by browser and platform. Oversized elements can produce blank or truncated canvases without a useful exception. Reduce the target’s CSS dimensions, lower scale, split a long component into pages, or capture sections separately and add several images to the document.

Remote images, CORS, and security boundaries

Images loaded from another origin can taint the canvas. html2canvas cannot override the browser’s same-origin policy or content security policy. For each remote image, use one of these approaches:

  • Serve the image from the same origin as the page.
  • Configure the image server to return appropriate CORS headers and set useCORS: true.
  • Use a suitable proxy that is permitted by your application’s security policy.
  • Replace the remote asset with an inline data URL or same-origin copy when that is acceptable.

If a cross-origin image fails, the canvas may be unusable when you call toDataURL. CORS permission must come from the server hosting the image; JavaScript in the page cannot grant itself access.

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

html2canvas options that matter

  • useCORS: true asks the browser to request eligible cross-origin images with CORS. It does not bypass missing response headers.
  • scale controls the rendered pixel density. Higher values can improve sharpness but increase memory and canvas-limit risk.
  • backgroundColor sets the canvas background; use null when transparency is required and supported by the rest of your PDF workflow.
  • foreignObjectRendering is available but defaults to false. Enabling it is not a universal compatibility fix; test the target browsers and content.
  • Element and viewport options can constrain what is rendered. Keep the capture rectangle no larger than the content you actually need.

Browser versus Node.js

html2canvas depends on browser APIs such as window and document. Importing it in a plain Node.js process does not turn it into a server renderer. Run the capture in a real browser context—such as the browser application that owns the DOM—or select a server-capable browser automation/rendering approach and then feed its output to your PDF pipeline.

pdfmake itself can be used in browser and server-oriented setups, but the input type still matters: an SVGElement is browser-only, while an SVG string can be produced in either environment if your pdfmake setup supports it.

Performance and reliability checklist

  1. Choose native svg for standalone artwork; do not rasterize without a reason.
  2. Wait for fonts, images, and asynchronous chart rendering before calling html2canvas.
  3. Capture the smallest useful element, not the entire document.
  4. Use a bounded scale and test on the browsers and devices you support.
  5. Resolve same-origin or CORS requirements before production export.
  6. Check the resulting PDF at actual print or display size, including thin lines and small labels.
  7. For long documents, capture page-sized sections rather than one extremely tall canvas.
  8. Keep a fallback for failed asset loads so one missing image does not leave the user with an empty export.
Independent reader supportYour contribution helps us test, update, and keep practical guides available for everyone.Support on Ko-Fi

Troubleshooting common failures

“The SVG is missing” or pdfmake rejects it

Confirm that the value is a complete SVG string or an SVGElement, not an HTML wrapper or an object returned by another library. Add explicit SVG dimensions or set width, height, or fit on the pdfmake node. Verify that your pdfmake version meets the documented SVG support: the SVG feature page uses 0.3.2, and SVGElement support requires 0.3.1 or later.

The PDF contains a blank canvas

Check that the target has non-zero dimensions and is actually rendered when capture starts. Wait for fonts and images, reduce the capture area or scale, and test again. Very large canvases can exceed browser limits without throwing an error.

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

External images disappear

Inspect the image response for CORS headers, use useCORS: true, or move the asset behind a permitted same-origin/proxy path. html2canvas cannot bypass origin policy or CSP.

Styles do not match the page

This is an html2canvas limitation, not necessarily a pdfmake defect. The library implements CSS properties individually, and unsupported properties cannot render correctly. Simplify the component for export, add an export-specific stylesheet, or use native SVG for the artwork that needs exact vector treatment.

Text or SVG looks blurry

You are viewing raster output. Increase the capture scale modestly, keep the PDF display width reasonable, and avoid enlarging a small canvas. If the source is standalone SVG, switch to pdfmake’s native SVG node to retain the vector path.

Or skip the browser setup

When you need a clean website capture rather than a DOM-to-canvas implementation, ScreenshotNeo provides a single GET request that returns PNG, JPEG, WebP, or PDF. It accepts cookie and consent banners before capture and removes more than 60 known consent platforms, newsletter popups, and chat widgets. Bot checks, blank pages, timeouts, failed loads, and cache hits are not billed, and the response identifies the page verdict and billing status in X-Page-Verdict and X-Billed headers. Its MCP server exposes take_screenshot, get_page_info, and capture_pdf to Claude, Cursor, and other MCP clients.

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

cURL

curl -G "https://api.screenshotneo.com/v1/shot" -d access_key=YOUR_API_KEY --data-urlencode url=https://stripe.com -o shot.webp

Python

import requests
r = requests.get("https://api.screenshotneo.com/v1/shot", params={"access_key": "YOUR_API_KEY", "url": "https://stripe.com"}, timeout=90)
r.raise_for_status()
open("shot.webp", "wb").write(r.content)

Node.js

const q = new URLSearchParams({ access_key: 'YOUR_API_KEY', url: 'https://stripe.com' });
const res = await fetch(`https://api.screenshotneo.com/v1/shot?${q}`);
if (!res.ok) throw new Error(`${res.status} ${res.statusText}`);
const data = Buffer.from(await res.arrayBuffer());
require('node:fs').writeFileSync('shot.webp', data);

See the complete option list and request details in the ScreenshotNeo documentation. You can request full-page captures with lazy images loaded, CSS-selector elements, dark mode, device presets or custom viewports, retina scale, PDF paper settings, custom CSS and JavaScript, clicks, waits, blocked resources, headers, cookies, user agents, authorization, timezone, geolocation, transparent backgrounds, resizing, TTL caching, signed links, asynchronous webhooks, bulk capture of up to 100 URLs per call, usage data, and an OpenAPI specification. Parameter names used by other screenshot APIs also work, which can simplify migration.

The Free plan includes 1,000 screenshots per month with no card. Paid plans start at $5 for 3,000 screenshots; every feature is available on every plan, and yearly billing gives two months free. Sign up free to try it without a card.

Which approach should you use?

  • Standalone SVG and vector-quality output: use pdfmake’s svg node, with explicit dimensions.
  • HTML/CSS component in a browser: use html2canvas, then pass the canvas data URL to pdfmake, while accepting its CSS and raster limitations.
  • Server-side capture: do not call html2canvas in plain Node.js; use a browser context or another server-capable renderer.
  • Public web pages where consent UI and failed captures are operational concerns: use a screenshot service such as ScreenshotNeo instead of maintaining browser setup yourself.

Frequently Asked Questions

Can pdfmake preserve an SVG as vector content?

Yes. Pass valid SVG markup to the pdfmake svg node, or pass an SVGElement in a supported browser version. html2canvas, by contrast, produces raster canvas data.

Can html2canvas run in a Node.js script?

Not by itself. It requires browser APIs, so run it in a browser context or choose a server-capable rendering approach.

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

Does foreignObjectRendering make every CSS rule work?

No. It is an optional setting, not a universal compatibility fix. Test the exact component and browsers you support.

Quick Recap

SaleBestseller No. 2
Adobe Acrobat 6 PDF For Dummies
Adobe Acrobat 6 PDF For Dummies
Used Book in Good Condition
$13.00

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.

Leave a Reply

Your email address will not be published. Required fields are marked *

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

Read next

Recommended PC Tool
Recommended PC Tool
Windows Errors? Fix Them Before They SpreadFree repair scan
Outdated Drivers Are Slowing You DownFree scan - exact matches

Two free Windows tools

One Free Minute Could Fix That PC

Before you go - each of these free tools takes about a minute and tackles what quietly slows a Windows PC down.

Special offer. View Outbyte info, uninstall instructions, EULA, and Privacy Policy.