Render QR codes in the browser
Browser applications can render a QR code as an SVG string, a PNG-backed Image element, or a Canvas element. Choose the output for what the page needs to do next, then insert or compose the returned value with standard browser APIs.
Choose a browser output
Section titled “Choose a browser output”| Choose | Package | Return value | Best fit |
|---|---|---|---|
| SVG | @qrcodesdk/core |
string |
Scalable inline markup and the recommended browser default |
| Image | @qrcodesdk/browser |
HTMLImageElement |
A familiar, accessible DOM image backed by PNG data |
| Canvas | @qrcodesdk/browser |
HTMLCanvasElement |
Drawing, compositing, pixel access, or manual PNG export |
Start with SVG unless the next browser API specifically needs an Image or Canvas element. SVG stays
sharp when resized and does not require Canvas support. Image and Canvas output require both
@qrcodesdk/core and @qrcodesdk/browser.
SVG string
Section titled “SVG string”QRCodeSVGRenderer returns complete SVG markup. It is not a DOM node, so insert it into an existing
element or pass it to the browser-side template system that owns the page.
Insert it into the DOM
Section titled “Insert it into the DOM”Render into a container when the SVG should participate in the page as inline markup:
import {QRCodeSVGRenderer, qrcode} from '@qrcodesdk/core';
const svg = qrcode('https://qrcodesdk.dev').render( QRCodeSVGRenderer({ ariaLabel: 'Scan to open qrcodesdk.dev', }),);
const container = document.querySelector('#qrcode');
if (container) { container.innerHTML = svg;}<div id="qrcode"></div>Only insert the string as HTML when the renderer and its options are inside your application’s trust boundary.
Include it in browser-generated markup
Section titled “Include it in browser-generated markup”The returned string can be interpolated into HTML generated by a browser-side template:
import {QRCodeSVGRenderer, qrcode} from '@qrcodesdk/core';
const svg = qrcode('https://qrcodesdk.dev').render( QRCodeSVGRenderer({ ariaLabel: 'Scan to open qrcodesdk.dev', }),);
const html = ` <section> <h2>Scan this QR code</h2> ${svg} </section>`;Apply layout styles to the inserted root SVG through its container:
#qrcode > svg { display: block; width: min(100%, 20rem); height: auto;}Image element
Section titled “Image element”QRCodeImageRenderer synchronously returns a new HTMLImageElement whose src contains the
rendered PNG as a data URL. Use it when the QR code should behave like an ordinary image in the DOM.
Insert and style it
Section titled “Insert and style it”The returned value is already an HTMLImageElement, so it can be appended and styled like any
other image:
import {QRCodeImageRenderer} from '@qrcodesdk/browser';import {qrcode} from '@qrcodesdk/core';
const image = qrcode('https://qrcodesdk.dev').render( QRCodeImageRenderer({ alt: 'QR code for qrcodesdk.dev', ariaLabel: 'Scan to open qrcodesdk.dev', title: 'QR code for qrcodesdk.dev', }),);
image.className = 'qrcode';document.querySelector('#qrcode')?.append(image);<div id="qrcode"></div>.qrcode { display: block; width: min(100%, 20rem); height: auto;}Use the PNG data URL
Section titled “Use the PNG data URL”Read src when another browser API needs the encoded PNG rather than the element:
import {QRCodeImageRenderer} from '@qrcodesdk/browser';import {qrcode} from '@qrcodesdk/core';
const image = qrcode('https://qrcodesdk.dev').render(QRCodeImageRenderer());const response = await fetch(image.src);const png = await response.blob();
await navigator.clipboard.write([ new ClipboardItem({ 'image/png': png, }),]);The Clipboard API requires a secure context and may require a user gesture or permission.
Canvas element
Section titled “Canvas element”QRCodeCanvasRenderer synchronously returns a new HTMLCanvasElement. Use Canvas when code needs
to draw onto the output, combine it with other graphics, inspect pixels, or export it manually.
Insert it into the DOM
Section titled “Insert it into the DOM”Give the Canvas its own accessible name, then append it wherever the QR code should appear:
import {QRCodeCanvasRenderer} from '@qrcodesdk/browser';import {qrcode} from '@qrcodesdk/core';
const canvas = qrcode('https://qrcodesdk.dev').render(QRCodeCanvasRenderer({size: 8, margin: 4}));
canvas.setAttribute('role', 'img');canvas.setAttribute('aria-label', 'Scan to open qrcodesdk.dev');document.querySelector('#qrcode')?.append(canvas);<div id="qrcode"></div>Draw it into another Canvas
Section titled “Draw it into another Canvas”Use the QR Canvas as a source for a larger composition:
import {QRCodeCanvasRenderer} from '@qrcodesdk/browser';import {qrcode} from '@qrcodesdk/core';
const qrCanvas = qrcode('https://qrcodesdk.dev').render(QRCodeCanvasRenderer());const target = document.querySelector<HTMLCanvasElement>('#target');const context = target?.getContext('2d');
if (target && context) { target.width = qrCanvas.width; target.height = qrCanvas.height; context.drawImage(qrCanvas, 0, 0);}Replace a rendered QR code
Section titled “Replace a rendered QR code”Each render creates a new string or element. When the payload changes, render again and replace the old output so the container does not accumulate QR codes:
import {QRCodeImageRenderer} from '@qrcodesdk/browser';import {qrcode} from '@qrcodesdk/core';
const container = document.querySelector('#qrcode');
export function updateQRCode(data: string) { const image = qrcode(data).render( QRCodeImageRenderer({alt: '', ariaLabel: `Scan to open ${data}`}), );
container?.replaceChildren(image);}If application state changes frequently, avoid recreating output for unrelated updates. Framework users can instead use the React, Vue, Svelte, or Angular components, which integrate rendering with their normal component lifecycle.
Keep browser output reliable
Section titled “Keep browser output reliable”- Keep the default four-module margin clear of nearby text, borders, and other UI.
- Give meaningful SVG, Image or Canvas output an accessible label.
- Use CSS to shrink output responsively, but do not enlarge Image or Canvas output beyond its
rendered pixel dimensions. Increase the renderer’s
sizewhen more raster resolution is needed. - Scan-test the final page at its smallest supported viewport and after any CSS transforms, browser zoom, screenshots, or image compression.
Result and next step
Section titled “Result and next step”The QR code now uses the browser output that matches its next operation and is mounted with normal DOM APIs. Follow Customize appearance for shared visual options, Add a center image for prepared image sources, or Download or save to turn the output into a file.