Skip to main content
Triggers are inline commands in narration using double-brace syntax: {{verb: arguments}}. They fire at the word position where they appear in the text. TTS timing aligns trigger execution to the spoken narration.

Visibility Control

show

Reveal a named visualization block on stage.
{{show: block-name}}
{{show: block-name slide 0.5s ease-out}}
Parameters:
ParameterTypeRequiredDescription
targetstringYesBlock name. Must match a named block defined in the same step.
animationtokensNoOptional effect, duration, easing. See Animations.
Behavior:
  • In split mode: Appends block alongside existing blocks. Deduplicates if already shown.
  • In normal mode: Replaces whatever is currently displayed.
Example:
{{show: hash-fn typewriter 2s linear}} Here's our hash function.

show-group

Reveal multiple blocks at once.
{{show-group: block-a,block-b fade 0.4s}}
Parameters:
ParameterTypeRequiredDescription
targetsstringYesComma-separated block names (no spaces).
animationtokensNoApplied to all targets.
Use when: The concept requires simultaneous context, not sequential buildup. Example:
{{show-group: input-tree,output-tree grow 0.5s spring}} Here's the before and after.

hide

Remove a named block from stage.
{{hide: block-name}}
{{hide: block-name fade 0.3s}}
Parameters:
ParameterTypeRequiredDescription
targetstringYesBlock name.
animationtokensNoOptional exit animation.
Behavior:
  • If the block isn’t currently shown, silently does nothing.
Example:
{{hide: old-code fade 0.3s}} Let's remove the previous version.

hide-group

Remove multiple blocks at once.
{{hide-group: block-a,block-b fade 0.3s}}
Parameters:
ParameterTypeRequiredDescription
targetsstringYesComma-separated block names (no spaces).
animationtokensNoApplied to all targets.
Example:
{{hide-group: diagram-a,diagram-b}} Clear the comparison.

clear

Remove all blocks and reset the entire scene. Hard scene break.
{{clear}}
{{clear: slide}}
{{clear: fade 0.5s ease-in-out}}
{{clear: instant}}
Parameters:
ParameterTypeRequiredDescription
transitionfade | slide | instantNoTransition style. Default: fade.
animationtokensNoOptional duration and easing override.
What clear resets:
  • Slots (all visible blocks)
  • Focus
  • Flow
  • Annotations
  • Zoom (back to 1x)
  • Pulse
  • Trace
  • Pan
  • Draw
  • Epoch (incremented)
Use between conceptual sections, not within a section. Example:
{{zoom: 1x}} {{focus: none}} That's the complete picture.

{{clear: slide}}

{{show: next-thing}} Now let's look at...

transform

Morph one block into another with visual continuity.
{{transform: block-a->block-b fade 0.4s}}
Parameters:
ParameterTypeRequiredDescription
from->tostringYesSource and destination block names, separated by ->.
animationtokensNoOptional animation tokens.
Use when: Two views are logically the same concept evolving (e.g., abstract diagram becoming concrete, tree before/after rotation). Example:
{{focus: unbalanced}} This node is unbalanced.
{{transform: avl-v0->avl-v1}} A right rotation fixes it.

Layout Control

split

Enable multi-panel mode. Subsequent show commands add blocks side-by-side.
{{split}}
Parameters: None. Behavior:
  • Stays active until {{unsplit}} or {{clear}}.
  • Maximum two panels.
  • Convention: left = code/explanation, right = visual/preview.
Example:
{{split}} {{show: source slide 0.3s}} {{show: preview slide 0.5s spring}} Here's the code and what it produces.

unsplit

Return to single-panel mode. Keeps only the last-shown block.
{{unsplit}}
Parameters: None. Example:
{{unsplit}} Now just the code.

Attention Control

focus

Highlight a specific region within a block. Everything else dims.
{{focus: region-name}}
{{focus: none}}
Parameters:
ParameterTypeRequiredDescription
targetstringYesA region name defined in the block’s region footer, or none.
Behavior:
  • Only one focus active at a time. New focus replaces previous.
  • none clears focus (everything returns to normal brightness).
  • Focus persists across paragraphs until changed.
Example:
{{focus: signature}} It takes a string and returns a number.
{{focus: loop}} The loop processes each character.
{{focus: none}} Step back and look at the whole function.

pulse

Briefly emphasize a region without changing focus state.
{{pulse: region-name}}
Parameters:
ParameterTypeRequiredDescription
targetstringYesRegion name.
Behavior:
  • Visual flash/emphasis effect with a sound cue.
  • Does not alter the current focus.
  • Use to call out a detail in passing.
Example:
{{pulse: swap-pair}} Compare parent and child.

trace

Animate a path through edges or connections in a data structure or diagram.
{{trace: path-region}}
{{trace: none}}
Parameters:
ParameterTypeRequiredDescription
targetstringYesRegion name representing a path (edges between nodes), or none.
Use for:
  • Showing request flow through a system
  • Algorithm traversal paths
Example:
{{trace: request-path}} The request flows from client to gateway to service.
{{trace: none}} Clear the trace.

annotate

Attach a text label to a region. Renders as a floating callout.
{{annotate: region-name "Explanation text"}}
Parameters:
ParameterTypeRequiredDescription
targetstringYesRegion name.
textstringYesQuoted string. Keep to 2-5 words.
Behavior:
  • Annotations persist until the next {{clear}}.
  • One annotation per target. Re-annotating the same target replaces the previous text.
Example:
{{annotate: region-name "Greedy choice"}} This is the key step.

zoom

Scale the visualization. Centers on the targeted region.
{{zoom: 1.2x}}
{{zoom: region-name 1.5x}}
{{zoom: 1x}}
Parameters:
ParameterTypeRequiredDescription
scalestringYesMultiplier in Nx format: 0.5x, 1x, 1.2x, 1.3x, 2x, etc.
targetstringNoOptional region name. If omitted, scales the whole block.
Zoom scales:
ScalePurpose
0.8xZoom out to show more context (rare)
1xNormal. Full block visible. Reset between focus jumps.
1.1xSlight emphasis on current context
1.2xStandard zoom for code walkthrough
1.3xDramatic zoom for critical moments
1.5x+Extreme single-line emphasis (rare)
Best practices:
  • Any code block over 15 lines MUST have zoom choreography.
  • Always reset to 1x before jumping to a distant region.
  • 1x resets to normal scale.
Example:
{{focus: pick}} Now the key step. {{zoom: 1.2x}} Pick the unvisited node.
{{zoom: 1x}} {{focus: return-val}} {{zoom: 1.2x}} Down at the bottom, the return value.

flow

Mark a path or set of elements as “active.” Used in data structures and diagrams to show execution flow.
{{flow: path-name}}
{{flow: none}}
Parameters:
ParameterTypeRequiredDescription
targetstringYesRegion name representing a path (node IDs, edge set), or none.
Use for:
  • Algorithm traces
  • Request flows
  • Data movement
Example:
{{flow: obvious-path}} A to B costs 4, B to D costs 3, D to F costs 5.
{{flow: none}} Clear the flow.

pan

Translate the viewport to center on a named region.
{{pan: region-name}}
{{pan: none}}
Parameters:
ParameterTypeRequiredDescription
targetstringYesRegion name to center on, or none.
Behavior:
  • Orthogonal to zoom — pan translates, zoom scales. They compose when both active.
  • none resets pan (center on default position).
Use for:
  • Navigating large visualizations (wide diagrams, long code blocks).
  • Pan and zoom can be combined: {{pan: far-region}} {{zoom: 1.3x}}
Example:
{{pan: far-cluster}} {{zoom: 1.3x}} Now look at this distant cluster.
{{pan: none}} {{zoom: 1x}} Step back to see the full picture.

draw

Animate edges drawing themselves like a pen stroke. One-shot effect (not looping like flow/trace).
{{draw: region-name}}
{{draw: none}}
Parameters:
ParameterTypeRequiredDescription
targetstringYesRegion name representing edges to draw, or none.
Behavior:
  • Edges animate from source to target with a trailing arrowhead that fades in after the stroke completes.
  • Unlike flow (looping dash animation) or trace (highlighted path), draw is a one-shot reveal.
Use for:
  • Revealing graph connections one at a time
  • Algorithm edge discovery
  • Building up a path incrementally
Example:
{{draw: edge-a-b}} First, connect A to B.
{{draw: edge-b-c}} Then B to C.
{{draw: none}} {{flow: full-path}} Now the full path is flowing.

Sequence Control

play

Execute a named sequence block and expand its output into the narration stream.
{{play: seq-name}}
Parameters:
ParameterTypeRequiredDescription
targetstringYesName of a seq block defined in the same step.
Behavior:
  • Expands at parse time into interleaved narration text and triggers.
  • Generator runs once during parsing, output is static.
Example:
{{show: my-graph grow 0.5s spring}} Here's our graph.

{{play: bfs-walk}} Watch BFS in action.

{{focus: none}} {{zoom: 1x}} That's the complete traversal.
See the sequence blocks documentation for authoring seq blocks.

advance

Bare text triggers or explicit {{advance}}. Creates a timeline marker without a visual change.
{{advance}}
{{This text is spoken and advances the scene}}
Note: In practice, verb triggers replace advance for all modern courses. This is primarily for backward compatibility.

TypeScript Definition

From src/types/lesson.ts:
export type TriggerVerb =
  | { readonly verb: "show"; readonly target: string; readonly animation: AnimationOverride }
  | { readonly verb: "show-group"; readonly targets: readonly string[]; readonly animation: AnimationOverride }
  | { readonly verb: "hide"; readonly target: string; readonly animation: AnimationOverride }
  | { readonly verb: "hide-group"; readonly targets: readonly string[]; readonly animation: AnimationOverride }
  | { readonly verb: "transform"; readonly from: string; readonly to: string; readonly animation: AnimationOverride }
  | { readonly verb: "clear"; readonly transition: TransitionKind; readonly animation: AnimationOverride }
  | { readonly verb: "split" }
  | { readonly verb: "unsplit" }
  | { readonly verb: "focus"; readonly target: string }
  | { readonly verb: "pulse"; readonly target: string }
  | { readonly verb: "trace"; readonly target: string }
  | { readonly verb: "annotate"; readonly target: string; readonly text: string }
  | { readonly verb: "zoom"; readonly scale: number; readonly target: string }
  | { readonly verb: "flow"; readonly target: string }
  | { readonly verb: "pan"; readonly target: string }
  | { readonly verb: "draw"; readonly target: string }
  | { readonly verb: "play"; readonly target: string }
  | { readonly verb: "advance" };

Build docs developers (and LLMs) love