On your page
Marks on the real elements of your running page. They follow scroll and resize. You need no file.
annotate()
Circle, underline and point at things on a page, an image or a chart. Play them step by step.
npm i @oblik/inkmark
Install the package.
npm i @oblik/inkmark
Or use a script tag. The global name is Inkmark.
<script src="inkmark.iife.js"></script>
<script>
Inkmark.annotate('#total', 'circle').show()
</script>
Labels use the font Permanent Marker. Load it on your page, or set font.src in a style.
inkmark draws in two ways. Pick the one that fits.
Marks on the real elements of your running page. They follow scroll and resize. You need no file.
annotate()
Marks on a picture: a screenshot, a chart or an HTML file. Play them step by step, show them all at once, or export PNG and MP4.
createPlayer()
Give a selector and a mark type. Call show().
import { annotate, annotateGroup } from '@oblik/inkmark'
const tour = annotateGroup([
annotate('#checkout-discount', 'highlight'),
annotate('#checkout-code', { type: 'box', color: 'accent' }),
annotate('#checkout-total', 'circle'),
annotate('#checkout-pay', { type: 'arrow', from: 'bottom' }),
annotate('#checkout', { type: 'label', text: 'Best value', side: 'top' }),
])
tour.show()A scene is one JSON file: a background and a list of steps. Each step has up to three marks. See the examples.
import { createPlayer } from '@oblik/inkmark'
const scene = await (await fetch('scene.json')).json()
createPlayer(document.querySelector('#box'), scene)Each example is one scene file. Click the dots to go step by step. The scene JSON is under each one.
A mark is one drawing: a circle, a line, an arrow or a note. Each box below is drawn live with the style panel.
There are nine types. Every mark also has id, with, duration, delay, color and seed. Marks on your page can use eight of them: all but scribble.
| Mark | Use it to | Key options |
|---|---|---|
circle | Loop around a thing | target pad loops |
box | Draw a rectangle | target pad |
underline | Draw a line below text | target offset double |
highlight | Add a marker band | target opacity |
strike | Cross out text | target crossed |
bracket | Frame one or more sides | target sides pad |
arrow | Point at a thing | from to bend head |
label | Write a short text | text at side maxWidth size |
scribble | Draw a free line | points thickness |
A target says where a mark goes. Use one key: selector, anchor, box, point or mark. A selector or an anchor is exact. A box or a point is a guess. Details: Scene reference.
A style is a set of tokens: pen, colors, font, stroke and timing. Ten styles are built in. Each box uses your panel colors. Click a box to use that style on this page, or copy it.
Marks name color tokens such as ink, accent and highlight. They never use hex values. Make your own style from a built-in one:
createPlayer(el, scene, {
styles: { brand: { extends: 'marker', colors: { ink: '#D6336C' } } },
})
Set "overlay": true on a scene or a step to dim the background and leave holes around the targets. Pass scheme: 'light' | 'dark' | 'auto' to follow light and dark. Details: Styles.
Turn a scene into one PNG per step, an MP4 or one HTML file. The command line tool does it: node cli/index.ts <command>.
node cli/index.ts preview scene.json --out png
node cli/index.ts play scene.json --out player.html
node cli/index.ts render scene.json --out scene.mp4 --fps 30
The same tool also checks a scene and finds targets for you.
| Command | Output |
|---|---|
preview | One PNG per step |
render | An MP4 (needs ffmpeg) |
play | One self-contained HTML player |
validate | Errors and warnings for a scene |
targets | Selectors or anchors you can point at |
grid | An image copy with a labeled grid |
Node 22.18 or newer is needed. A Chromium browser is needed for preview and render.
Copy a prompt. Paste it into any AI chat or coding agent.
Use it to mark elements on a live page.
Use it to get a scene JSON for a player, PNGs or an MP4.
Coding agents: add skill/SKILL.md to your project. Or read the Agent page. It has this whole doc as one Markdown file.
| Function | What it does |
|---|---|
annotate(target, mark, options?) | Makes one live mark. Returns an Annotation with show(), hide() and remove(). |
annotateGroup(list, options?) | Shows many live marks one after the other. Options: overlay, gap. |
createPlayer(el, scene, options?) | Mounts a scene with step dots and a Play button. |
mountScene(el, scene, options?) | Mounts a paused scene with no controls. |
validate(scene) | Checks a scene. |
resolveStyle(style) | Resolves a style name or a partial style. |
Player options: controls, autoplay, loop, keyboard, baseUrl, style, styles, scheme, overlay. A player has next(), back(), play(), pause(), current and onStep().