QR Code Styling
JavaScript library for generating QR codes with customizable styling in browser or Node.js
Plugins
Extend the functionality of QR Code Styling with official and community plugins.
Data plugins
These plugins help you create rich QR code content that users can directly use after scanning.
| Plugin | Description | Use Case | Import Example |
|---|---|---|---|
| WiFi | Generates a QR code that lets users connect to a WiFi network automatically without typing credentials | Guest WiFi at cafes, offices, events, hotels | import WiFiPlugin from '@liquid-js/qr-code-styling/wifi-plugin' |
| VCard | Creates a digital business card (contact) that can be saved directly to the phone’s contacts app | Networking, business cards, conferences | import VCardPlugin from '@liquid-js/qr-code-styling/vcard-plugin' |
| Event | Generates calendar events (.ics / vCalendar) that users can add to their calendar with one scan | Meetups, webinars, appointments, reminders | import EventPlugin from '@liquid-js/qr-code-styling/event-plugin' |
Styling & decoration plugins
| Plugin | Description | Key Features |
|---|---|---|
| Border | Adds custom borders, frames, and decorative text around the QR code | Rounded corners, text on borders |
| Custom Shape | Create your own plugins to draw unique dots, corners, or patterns | Advanced customisation of shapes with SVG |
Usage example
Example – stylish WiFi QR code:
import BorderPlugin from '@liquid-js/qr-code-styling/border-plugin'
import WiFiPlugin from '@liquid-js/qr-code-styling/wifi-plugin'
import FontFacesPlugin from '@liquid-js/qr-code-styling/font-faces-plugin'
const options = {
plugins: [
new WiFiPlugin({
ssid: "MyNetwork",
password: "SuperSecret123",
encryption: "WPA",
}),
new BorderPlugin({
round: 0.8,
size: 0.15,
proportional: true,
color: '#000000',
text: {
color: '#ffffff',
top: {
content: 'MyNetwork'
},
bottom: {
content: 'Scan to connect'
}
}
}),
/**
* Embed fonts used with BorderPlugin
*
* Not needed when using standard or local fonts, but recommended for portability
* and consistency; use subsetting if possible to reduce the generated file size.
*/
new FontFacesPlugin([{
font: 'sans-serif',
src: `url(data:font/otf;base64,d09GMgABAA...)`
}])
]
}Example – custom shapes:
import BorderPlugin from '@liquid-js/qr-code-styling/border-plugin'
const options = {
plugins: [
{
drawDot: (args: DrawArgs): SVGElement | undefined => {
const { size, x, y, document } = args
const element = document.createElementNS('http://www.w3.org/2000/svg', 'path')
// Insert your own SVG path definition, or implement neighbour-aware logic through args.getNeighbor()
element.setAttribute(
'd',
svgPath`M ${x} ${y + (size - size) / 2}
v ${size}
h ${size / 2}
a ${size / 2} ${size / 2} 0 0 0 0 ${-size}
z`
)
return element
}
}
]
}Tip: see Border plugin and figures for further reference
Benefits of Using Plugins
- Better User Experience – One scan = instant action (connect to WiFi, save contact, add to calendar)
- No server needed – Everything runs client-side
- Highly customizable – Combine data plugins with styling plugins
- Extensible – Easy to create your own custom plugins
Backwards compatibility
Before @liquid-js/qr-code-styling version 5.0.0, the generator only supported a single postProcess hook via applyExtension. Existing extensions can still be used, but should be included as plugins: [{ postProcess: extensionFn }] to maintain forwards compatibility once the deprecated extension interface is removed.