Building Recipes
A recipe is a declarative, multi-step brand interaction that an agent composes from this library and cooker renders. This page bridges the two: the phase contract, how each phase type resolves to components, how an agent assembles and brands one, and a fully decomposed live example.
1 The recipe model
Every recipe follows one phase contract: Hook → Challenge → Reward → Offer. The funnel stage sets the emphasis — awareness recipes lean on a fast Hook + Reward; conversion recipes weight the Offer. Cooker loads a recipe as JSON; each phase carries a type and props. The four phase renderers map that type to library components.
| Phase | Flow role | Renderer | Resolves to | Purpose |
|---|---|---|---|---|
| Hook | entry | HookRenderer | WelcomeScreen | First exposure. Set the brand frame and invite the user in. |
| Challenge | core | ChallengeRenderer | a switch over the challenge type → SurveyModule / BingoModule / SpinWheelModule / … | The interaction itself — quiz, pick, scratch, spin, swipe, match. |
| Reward | reward | RewardRenderer | Burst | Pay off the effort. Celebrate and reveal what was earned. |
| Offer | exit | OfferRenderer | ProductRevealCard | Convert attention into action — a product, coupon, or landing. |
Shaping by funnel stage
funnelStage is metadata now, not navigation, but it still tunes how a recipe is shaped — its duration, mechanic, and how it lands.
Awareness
Keep total duration under 20s. High-dopamine mechanics (flip / scratch / spin / stories). One core interaction only. Brand visible but not dominating. Always end on a tangible reward — points or a coupon.
Consideration
30–120s or multi-session. Knowledge-building mechanics (quiz / swipe / bingo / missions). Collect preference data through the choices, reward progressively each step, and end on a personalized recommendation.
Conversion
Under 15s. Skip or minimize the entry animation. Urgency mechanics (countdown / timed offer / flash deal). Always include a copy-able coupon code or a clear CTA that navigates to purchase or claim.
Writing the wait
When a phase hands off to a longer, full-screen transition (app → external browser, a deep-link landing, an ad-click load), reach for BrandTransition rather than a bare spinner: a publisher-branded overlay with reward icons raining down. Its subtitle reframes the wait as earning, not waiting. Write to the value that is coming, never to the delay.
- ✓ “Preparing your rewards …” — value is coming
- ✓ “Charging your points …” — 점수 충전중, a Korean idiom
- ✓ “Unlocking rewards from Toss …” — brand + action
- ✗ “Loading …” — too generic, no value signal
- ✗ “Please wait” — passive, no reward framing
2 Anatomy — how a type resolves to a Module
Hook, Reward, and Offer resolve to a fixed component. The Challenge phase is a switch over the challenge type: each type resolves to a promoted library Module implementing ModuleProps<Config>. The Module owns its recipe-state orchestration and fires onComplete — cooker no longer wraps a bare engine to supply that state. Several quiz/survey families collapse onto one Module (the indirection that makes SurveyModule live).
Challenge type | Module |
|---|---|
| ox-quiz / multi-quiz / survey / preference-pick / swipe-deck | SurveyModule |
| review-pick | ReviewPickModule |
| scratch | ScratchModule |
| memory-match | MemoryMatchModule |
| bingo | BingoModule |
| spin-wheel | SpinWheelModule |
| product-explore | ProductExploreModule |
| link-list | LinkListModule |
| countdown-deal | CountdownDealModule |
| flash-offer | FlashOfferModule |
| timing-game | TimingGameModule |
The consumption map traces this whole chain — recipe type → renderer → Module → transitive library render graph — so every component a recipe touches is tagged live and back-linked. See Component Registry.
3 How an agent composes one
- Query the manifest. Use the Query API to select components by
funnelStage,intent, andcomplexity. - Assemble the phases. Order one component per role (entry → core → reward → exit), each with an
exitTrigger(tap/completion/automatic). - Apply brand. Pass a
TokenSeedfor color/type/imagery and set thepersonalitydial; per-stepbrandCustomizationsmap a brand aspect to a specific prop.personalityis the provider-level brand motion dial. A brand sets it once onThemeProvider personality="…"and every interaction’s feel inherits the tone — press, selection, and celebration all retune.smooth(default) decelerates, confident;bounceovershoots with a visible second bound;swiftsnaps and settles immediately. Components read the dial automatically viausePersonality()(hooks likeusePressMotion/useSelectionMotionand theBurstcomponent) — no per-component prop needed. An explicitpersonalityoverride always wins. - Validate. Composition rules (see Composition Rules) confirm the flow is well-formed before cooker renders it.
4 Worked example — product-showcase
Brand with personalized product catalog (e.g. Wadiz campaign). User browses 3 slides, answers a quiz, lands on a product offer.
| # | Role | Component | Exit | What it does |
|---|---|---|---|---|
| 1 | entry | WelcomeScreen live | tap | Hook phase rendered by HookRenderer → WelcomeScreen. Neutral layout (no background image). Auto-starts after 4s per smooth personality. |
| 2 | core | PersonalizedProductShowcase live | completion | Challenge phase: ProductShowcaseChallenge wraps PersonalizedProductShowcase from the library. Shows 3 slides with appeal-point callouts, then a quiz question. Correct answer = full reward; each wrong attempt decays by rewardDecay array. |
| 3 | reward | Burst live | automatic | Reward phase: RewardRenderer fires Burst (kind=confetti, full-width shower) + Burst (kind=radial, centered radial). Uses slot-machine animation for randomized reward display. |
| 4 | reward | Burst live | automatic | Radial particle burst rendered alongside confetti Burst in the reward phase. |
| 5 | exit | ProductRevealCard live | tap | Offer phase rendered by OfferRenderer → ProductRevealCard. Surfaces 1 product. Reward trigger: after-challenge (reward already settled before offer). External browser opens on product tap. |
Brand customization points
- •
step 1.brandName(name) — Brand display name shown in hook - •
step 1.title(tone) — Hook headline - •
step 1.subtitle(tone) — Hook sub-headline - •
step 2.config.slides(imagery) — 3 product slides: imgUrl, appealPoint, imgText - •
step 2.config.quiz(product) — Quiz question, options, correct answer, explanation - •
step 2.config.rewardDecay(product) — Reward values per attempt [1st, 2nd, ...] in smallest currency unit - •
step 2.product(product) — Product shown in loader and offer: thumbnail, name, brand - •
step 5.products(product) — Product(s) surfaced in offer card
5 Spec'ing a new recipe
- 1. Pick the funnel stage and write the one-line useCase.
- 2. Choose one component per phase role (entry / core / reward / exit); reuse existing engines before adding components.
- 3. Set each step's exitTrigger and the realistic totalDuration range.
- 4. List brandCustomizations — every brand-variable prop, mapped to its brand aspect.
- 5. Land it in cooker with a tier (prod / mock / lab); add the matching allRecipes entry with tier live / demo / experimental.
A tier:"live" allRecipes entry automatically produces the live badge and "used in N recipes" backlinks on every component it touches — the catalog stays honest because the recipe is the source of truth.