Tap-or-Scan Card

Create one self-contained HTML card that people can scan from another device or click on the device already in their hand.

Clickable rich format

Card settings

Enter a valid destination

See the full story

Scan from another device or tap below to open it here.

Open now
Advertisement

One destination. Two ways to open it.

The QR code handles camera scanning while the HTML action handles the current device. The downloaded card keeps both routes together without pretending a PNG or JPEG can contain a clickable region.

01

Share the HTML file

Use the downloadable rich card wherever an HTML attachment or hosted page is supported.

02

Keep the QR visible

The embedded QR remains a standard high-contrast code for another phone to scan.

03

Use the action here

The button opens the same permanent destination directly on the current device.

Verified October 2026

What the tool makes

The Tap-or-Scan tool takes one destination address, a title, a supporting message, an action label and an accent colour, and writes a single HTML file carrying two routes to the same place: a QR code, embedded as an image, for a camera on another device, and a button — an ordinary link — for the device the card is already open on. The copy above gives the reason: a PNG or JPEG cannot contain a clickable region, so a card that must be both scannable and tappable has to be a document.

This page is about the mechanism. The QR codes on promos guide covers sizing, contrast and placement of the code itself; the package anatomy guide shows where the card sits among the Studio’s other files; the methodology states the engine rules behind every tool. Every example below is fictional; every figure is computed from the card builder at build time or read from the site’s dated specs registry.

One destination, checked before anything is drawn

Everything hangs off a single address, and the tool refuses to draw until it can parse one. The destination field goes to the browser’s own URL parser; the parsed address must use http or https, and anything else is turned away with the notice Enter a complete http or https address. while the preview reads Enter a valid destination and the download stays disabled. The QR and the button are built from the parsed form, not the typed text.

The parser writes the address back in its normal form: a fictional https://tide-and-timber.example becomes https://tide-and-timber.example/, and the trailing slash is what the QR encodes. A scheme-less tide-and-timber.example/open-studio does not parse (parses as an address: no), and mailto:hello@tide-and-timber.example parses but carries the scheme mailto:, which the rule rejects: web destinations only. The builder’s contract is a single destination, placed exactly 1 timein the markup as the button’s link while the QR carries the same string as pixels; the card cannot send a scanner one place and a tapper another.

The QR inside the card

The card builder does not encode a QR code. It embeds a finished image handed to it as a data URL: here, one the tool encodes from the validated destination in your browser; in the Studio, the Studio’s own. The tool does not use the site’s QR engine for that image: it encodes it with a separate browser encoder whose request mirrors the engine’s rules and is fixed — error-correction level H, a margin of four modules, dark modules in the site’s ink colour on the Studio’s default content background, at a fixed pixel width. That request lives in the tool’s own component, so this page reads it back from the component’s source when the site is built and checks it against the standards registry, the QR engine’s constants and the Studio’s default design; the figures below are those three sources, and the build fails if the request stops matching them.

Level H is the highest of the four levels — ≈30% of codewords recoverable, as the reference encoder states (verified 2 October 2026). The card has no logo to spend that on and asks for H regardless; the guide’s trade-off still applies — more recovery means a denser code for the same address — so keep the destination short. The site’s own QR engine has a fuller rule: its render engine defaults to M (≈15%, verified 2 October 2026) without a logo and forces H whenever a logo is present, and its artistic engine requires H for every artistic style, rejecting any model encoded lower.

The margin is the quiet zone — “QR Code requires a four-module wide margin at all sides of a symbol.” (verified 2 October 2026) — the width the site’s QR engine always draws, 4 modules on every side, and never lets a caller disable; the tool’s separate encoder is asked for 4 modules, the same width, and the build checks the two agree. On the card the image sits on a white pad in the accent panel at 190 CSS pixels wide, keeping the accent away from the modules.

The colours the tool asks its encoder for are #14201c on #fbfcfa, the Studio’s default title-on-content pair, #14201c on #fbfcfa: 16.28:1 by the QR engine’s own WCAG calculation, applied here to the pair as a comparison — dark on light, as the guide insists, and well above the engine’s warning line of 4.5:1, the WCAG AA text threshold (verified 2 October 2026). The accent never touches the QR; it colours the panel, the button and, on the event variant, the Add to calendar link, which the builder writes in the accent (#7a3b1e on the fictional event card).

Every value is escaped

5characters have meaning in HTML, and every value the builder places — title, message, action label, destination, event line, venue, calendar link — passes through one escaper:

TypedWritten into the file
&&
<&lt;
>&gt;
"&quot;
'&#039;

So a fictional title of Tide & Timber's "Open Studio" <preview> is written as Tide &amp; Timber&#039;s &quot;Open Studio&quot; &lt;preview&gt;, 2 times: as the document title in the browser tab and as the heading; the raw string appears 0 times. The destination https://tide-and-timber.example/open-studio?src=card&ref=poster goes into the button as https://tide-and-timber.example/open-studio?src=card&amp;ref=poster, its ampersand escaped so the query string survives inside an attribute. The QR data URL is not escaped, because it came from the encoder rather than a text field. This is why a quote mark or an angle bracket in a title cannot close an attribute or open a tag.

The design the card inherits

The card’s type and colours are the Studio’s design settings, run through the Studio’s normaliser — colour format, font list, size range, weight set — with anything missing filled from the defaults; the standalone tool passes no design, so its cards get the defaults. Two translations happen on the way in: the title is written at half the Studio’s title size, rounded, so the default of 72 becomes a heading of 36px; and because the Studio names its web fonts through a CSS variable the standalone file does not define, the default face goes in as Arial, sans-serif.

Colours are honoured exactly — the site’s colour doctrine. A body colour of #e4e9e6 on the default content background #fbfcfa survives normalisation as #e4e9e6and is written as given, although the QR engine’s calculation puts the pair at 1.19:1, below the 4.5:1 line; the Studio shows that as a live advisory while you pick, this tool shows none, and the builder never rewrites a colour. Every colour has the same format rule: anything but a six-digit hex colour falls back to its default. The normaliser applies it to each colour it carries, so a body colour of rgb(122, 59, 30) comes out as the default body colour, #65706b; the card builder applies it to the accent itself before the normaliser runs, so the same string as an accent falls back to the engine’s default accent, #3f6f63. The action label is drawn in #ffffff on the accent: 8.50:1 on the fictional #7a3b1e, but a pale accent would be honoured just the same.

The event variant the Studio sends

The builder accepts 3event values the standalone tool never sends (besides the design settings covered above) — an event date line, a venue and a calendar link — supplied by the Studio for event campaigns, whose event module formats the line from the start time and time zone: a fictional open-studio evening at 2026-11-14T19:30:00Z in Europe/London becomes Sat, Nov 14 · 7:30 PM (London). The calendar link is a Google Calendar URL the same module builds from title, times, venue and destination; on the card it reads Add to calendar beneath the message, after the event line and venue.

The markup changes only when they are present. The plain card has an event block: no; a calendar link: no; 1 link and 1 web address, the destination. The event card has an event block: yes; a calendar link: yes; 2 links and 2 web addresses, the calendar link escaped so its query string is written with &amp;between parameters. A venue without a start time still shows; a start time the module cannot format produces no line rather than a broken date. The ICS file travels separately in the ZIP — the README lists it as - *-event.ics — attach or share this calendar event so viewers can save the date. — and the package anatomy guide explains both.

How to read the preview and the download

The preview is the card — accent panel, QR on its white pad, heading, message and action bar — redrawn as you type; its button is live and opens the parsed destination in a new tab, a direct check that the card carries the address you meant. The download is disabled until the destination parses and the QR has finished encoding; the 3 text fields each carry a fixed character limit.

The file is named from the title through the site’s shared slug rule — lower-cased, runs of anything outside letters and digits collapsed to one hyphen, edges trimmed — plus the card suffix, so the fictional title downloads as tide-timber-s-open-studio-preview-tap-or-scan.html. The Studio names its copy the same way, and the package README describes it as - *-tap-or-scan.html — clickable on the current device and scannable from another device; it is self-contained.

Where it stops

  • No script and no request of its own: the fictional card holds 0 script elements, 1 image— the embedded QR — and 1 link, the button.
  • No encoding in the builder: it embeds the image it is handed, and this page always embeds the tool’s fixed request.
  • No hosting, shortening, redirecting or counting: the parsed address is what is encoded and linked, with no record of taps or scans; parsing confirms it is well formed, not that anything answers at it.
  • No logo, colour or size for the QR: those controls live in the QR tool, whose engine computes contrast, caps the logo area and exports PNG and SVG for print; the card’s QR is for a screen.
  • No platform figures: the 4standards figures here — quiet zone, two error-correction levels, WCAG threshold — are read from the site’s registry with their dates; how a mail client, messaging app or link hub treats an HTML file is not in that registry, and this page does not say.

Common misreadings

  • “The QR and the button can point to different places.” One destination is written into both routes.
  • “The HTML file is the QR code.” The QR is a PNG inside it, drawn at 190 CSS pixels for a screen; print codes come from the QR tool.
  • “Changing the accent recolours the QR.” The accent colours the panel, the button and, on the event variant, the Add to calendar link; the QR stays #14201c on #fbfcfa, the Studio’s default title-on-content pair, which the build checks the tool’s fixed request still matches.
  • “The card checks my colours.” They are honoured exactly with no advisory here; the Studio shows one while you pick.
  • “The event details come from this page.” The standalone tool has no event fields; the Studio sends them.

Questions

Does downloading the card send anything anywhere?
No. The card is assembled in your browser from the fields on the page, the QR is encoded there too, and the download is written from memory to a file on your device. The file contains no script and makes no request of its own when opened.
Why is the card an HTML file rather than an image?
Because a PNG or JPEG cannot contain a clickable region. Only a document can be both scannable from another device and tappable on this one; the QR is embedded in it as an image.
Why does the card ask for error-correction level H?
That is the tool's fixed request: H is the highest of the four levels, ≈30% of codewords recoverable (verified 2 October 2026), and the card has no logo to spend it on. More recovery means a denser code for the same address, so keep the destination short.
Can I change the QR's colours, add a logo or pick its size?
Not here. The card's QR is fixed at level H, a margin of four modules (verified 2 October 2026), #14201c on #fbfcfa, drawn at 190 CSS pixels. Logos, colours, PNG sizes and SVG export live in the QR tool.
What happens if I type a bare domain?
Without a scheme it does not parse, so the notice shows and the download stays disabled. Once it parses, the address is written in its normal form: https://tide-and-timber.example is encoded and linked as https://tide-and-timber.example/, trailing slash included.
Where does the card go in the Studio package?
One file in the ZIP, named from the campaign title with the suffix -tap-or-scan.html; the README describes it as: - *-tap-or-scan.html — clickable on the current device and scannable from another device; it is self-contained. Event packages add the date line, venue and calendar link and ship the ICS file separately.

Everything here runs in your browser: the tools compute on your device and the Studio’s package is assembled on the device. The methodology documents every rule the tools apply.