Repository navigation
Home: new top - hero rewrite and consumer how-it-works [MICHAEL 2026-10-14] #180
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,48 @@ | ||
| # Intent: new home page top (hero and consumer how-it-works) | ||
|
|
||
| Author: Claude (working with Michael) | ||
| Date: 2026-10-14 | ||
| Status: draft (accepted when Danny merges the PR that adds it) | ||
| Product: zzThis (`Zero-State-LLC/zzthis`) | ||
|
|
||
| ## Problem / why now | ||
|
|
||
| First-time visitors, mostly on mobile, were not grasping what zzThis is from the current hero. Michael wants them to get it within the first screen and one swipe. [verified: Michael, 2026-10-14] | ||
|
|
||
| ## Proposed outcome | ||
|
|
||
| Hero, in order [MICHAEL 2026-10-14]: | ||
|
|
||
| - Eyebrow: "The next evolution of the barcode". | ||
| - Headline: "A barcode/QR code you can write by hand". | ||
| - Sub-headline: the barcode/QR comparison with `zz-Kathy-found-dog-zz` set in mono and accent orange. | ||
| - The two hero buttons stay, right under the sub-headline, now with How it works first (primary) and See field logistics second [MICHAEL 2026-10-15, at Danny's request]. | ||
| - Two photos: the Kathy cork-board polaroid and the phone showing "Record found" (new assets under `public/images/hero/`). | ||
| - Hero body: the roadmap caveats (typed-only prototype, camera in v1, voice later) are removed; the paragraph now ends "zzThis makes things readable-writable-smart." | ||
|
|
||
| New section right under the hero: "How it works - consumer" [MICHAEL 2026-10-14]: | ||
|
|
||
| - Eyebrow "Physical-to-digital addressing"; headline "Skip the printer. Grab a marker." (Michael wrote "Ditch the printer" and asked for a less casual verb; swap back if preferred). | ||
| - His protocol sub-headline, the lead line, and the three steps (Create it / Write it / Look it up). No button in this block [MICHAEL 2026-10-15]. | ||
|
|
||
| The home "How it works" section heading becomes "How it works - field" to distinguish the two. The rest of the page is unchanged, same sequence. | ||
|
|
||
| ## Constraints and flags for Danny | ||
|
|
||
| - The hero no longer states that the prototype is typed-lookup only; the sub-headline and steps say "scan". Michael chose to move caveats off the top of the page. If a Status/Roadmap note is still wanted lower on the page, that is a follow-up. | ||
| - "highly secure" in the consumer sub-headline is Michael's wording. | ||
| - No em dash; spaced hyphens used. Copy lives in `src/content/hero.ts`. | ||
|
|
||
| ## Affected users / systems | ||
|
|
||
| `src/content/hero.ts`, `src/content/workflows.ts`, `src/pages/index.astro`, `src/styles/b-base.css`, `public/images/hero/` (2 images), `tests/content.test.ts`, `tests/hero.test.ts` (new, for the max-lines rule). | ||
|
|
||
| ## Claims | ||
|
|
||
| | Claim | Label | | ||
| |---|---| | ||
| | All headline, sub-headline, step and body wording is Michael's, as given or minimally cleaned | `[verified: Michael's doc, 2026-10-14]` | | ||
|
|
||
| ## Next | ||
|
|
||
| Danny reviews and merges. Merging the PR that adds this file accepts it. |
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -1,15 +1,27 @@ | ||
| // [MICHAEL 2026-10-14] Home top restructured: eyebrow, new headline, the | ||
| // barcode/QR comparison sub-headline with the Kathy code, two photos, the | ||
| // two hero buttons (How it works first), and the roadmap caveats removed from the hero body. | ||
| export interface HeroAction { | ||
| label: string; | ||
| path: string; | ||
| variant: "primary" | "secondary"; | ||
| } | ||
|
|
||
| export interface HeroPhoto { | ||
| src: string; | ||
| width: number; | ||
| height: number; | ||
| alt: string; | ||
| } | ||
|
|
||
| export interface HeroContent { | ||
| eyebrow: string; | ||
| title: string; | ||
| subline: string; | ||
| subline: { before: string; code: string; after: string }; | ||
| paragraph: { before: string; code: string; after: string }; | ||
| imageCaption: string; | ||
| photos: readonly HeroPhoto[]; | ||
| actions: readonly HeroAction[]; | ||
| imageCaption: string; | ||
| } | ||
|
|
||
| export interface TextBlock { | ||
|
|
@@ -22,25 +34,67 @@ export interface LinkBlock extends TextBlock { | |
| } | ||
|
|
||
| export const hero: HeroContent = { | ||
| // Q62 [DANNY 2026-10-03, revised]: v1.0 headline, spaced hyphen, no em dash. | ||
| title: | ||
| "Barcodes made things scannable. zzThis makes things readable-writable - and smart.", | ||
| subline: "Write a code on a thing; type it to find its record.", | ||
| eyebrow: "The next evolution of the barcode", | ||
| title: "A barcode/QR code you can write by hand", | ||
| subline: { | ||
| before: | ||
| "Barcodes use bars. QR codes use dots. zzThis uses everyday words. Just wrap your words in double z’s - like ", | ||
| code: "zz-Kathy-found-dog-zz", | ||
| after: | ||
| " - write it on anything with a marker, and scan it to open its digital record. The “zz” ends tell our scanner exactly where to look, just like the three corner dots on a QR code.", | ||
|
Comment on lines
+43
to
+44
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
For every visitor to the new home page, this now says they can “scan it to open” a record and refers to “our scanner,” although the canonical capability boundary says typed lookup is the only implemented path and on-device recognition is not built ( AGENTS.md reference: AGENTS.md:L32-L37 Useful? React with 👍 / 👎. |
||
| }, | ||
| paragraph: { | ||
| before: | ||
| "zzThis is a human-readable, human-writable code for the physical world. Write a ", | ||
| code: "zz-code", | ||
| after: | ||
| " on tape, a crate, a parcel, an envelope, or a sign, or embed it in text or program code. The prototype supports typed lookup to a digital record. On-device camera recognition is planned for v1 but is not implemented in this build. Voice recognition is planned for a future release, not v1.", | ||
| " on tape, a crate, a parcel, an envelope, or a sign, or embed it in text or program code. zzThis makes things readable-writable-smart.", | ||
| }, | ||
| imageCaption: "Word code on blue tape beside an obscured barcode.", | ||
| photos: [ | ||
| { | ||
| src: "images/hero/kathy-corkboard.webp", | ||
| width: 509, | ||
| height: 492, | ||
| alt: "A polaroid pinned to a cork board: a plush corgi wearing a zz tag, captioned zz-Kathy-found-dog-zz.", | ||
| }, | ||
| { | ||
| src: "images/hero/kathy-phone-record.webp", | ||
| width: 594, | ||
| height: 570, | ||
| alt: "A hand holds a phone scanning the plush corgi; the screen reads zz-Kathy-found-dog-zz, Record found, and the record link.", | ||
| }, | ||
| ], | ||
| // [MICHAEL 2026-10-15] Buttons restored at Danny's request, How it works first. | ||
| actions: [ | ||
| { label: "How it works", path: "#how-it-works", variant: "primary" }, | ||
| { | ||
| label: "See field logistics", | ||
| path: "#field-logistics", | ||
| variant: "primary", | ||
| variant: "secondary", | ||
| }, | ||
| ], | ||
| imageCaption: "Word code on blue tape beside an obscured barcode.", | ||
| }; | ||
|
|
||
| // [MICHAEL 2026-10-14] "How it works - consumer" block, right under the hero. | ||
| export const consumerHow = { | ||
| eyebrow: "Physical-to-digital addressing", | ||
| heading: "Skip the printer. Grab a marker.", | ||
| text: "zzThis is a structurally constrained, human-readable tagging protocol. By bounding ordinary words with a “zz” prefix and suffix, we turn handwriting into a highly secure, scannable data link, from austere environments and logistics to everyday tracking.", | ||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
Calling the link “highly secure” is unsupported: the accepted product spec explicitly says the codebook is unvalidated and recognition and resolver security are untested ( AGENTS.md reference: AGENTS.md:L32-L37 Useful? React with 👍 / 👎. |
||
| lead: "zzThis protocol words connect things to their online information.", | ||
| steps: [ | ||
| { | ||
| title: "Create it.", | ||
| text: "Choose or create your words and link them to information.", | ||
| }, | ||
| { | ||
| title: "Write it.", | ||
| text: "Put the zz-code on your item or sign.", | ||
| }, | ||
| { | ||
| title: "Look it up.", | ||
| text: "Scan the words to open the linked information.", | ||
| }, | ||
| { label: "How it works", path: "#how-it-works", variant: "secondary" }, | ||
| ], | ||
| }; | ||
|
|
||
|
|
||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -9,32 +9,27 @@ import Pipeline from "../components/Pipeline.astro"; | |
| import ComparisonCards from "../components/ComparisonCards.astro"; | ||
| import { comparisonHeading } from "../content/comparison"; | ||
| import Tour from "../components/Tour.astro"; | ||
| import { aboutTeaser, contactAction, hero } from "../content/hero"; | ||
| import { aboutTeaser, consumerHow, contactAction, hero } from "../content/hero"; | ||
| import { contactEmail } from "../content/navigation"; | ||
| import { url } from "../lib/url"; | ||
| import BaseLayout from "../layouts/BaseLayout.astro"; | ||
|
|
||
| const splitAt = hero.title.indexOf(". "); | ||
| const setup = hero.title.slice(0, splitAt + 1); | ||
| const claim = hero.title.slice(splitAt + 2); | ||
| const phrase = "readable-writable"; | ||
| const phraseAt = claim.indexOf(phrase); | ||
| const claimBefore = claim.slice(0, phraseAt); | ||
| const claimAfter = claim.slice(phraseAt + phrase.length); | ||
| const description = | ||
| hero.subline.before + hero.subline.code + hero.subline.after; | ||
| --- | ||
|
|
||
| <BaseLayout title="zzThis" description={hero.subline} home> | ||
| <BaseLayout title="zzThis" description={description} home> | ||
| <section class="hero" id="top" aria-labelledby="hero-title"> | ||
| <div class="hero__copy"> | ||
| <p class="eyebrow">{hero.eyebrow}</p> | ||
| <h1 class="hero__title" id="hero-title"> | ||
| <span class="hero__setup">{setup}</span>{" "} | ||
| <span class="hero__claim"> | ||
| {claimBefore} | ||
| <span class="nowrap">{phrase}</span> | ||
| {claimAfter} | ||
| </span> | ||
| <span class="hero__claim">{hero.title}</span> | ||
| </h1> | ||
| <p class="hero__sub">{hero.subline}</p> | ||
| <p class="hero__sub"> | ||
| {hero.subline.before} | ||
| <code class="hero__code">{hero.subline.code}</code> | ||
| {hero.subline.after} | ||
| </p> | ||
| <div class="hero__actions"> | ||
| {hero.actions.map((action) => ( | ||
| <a | ||
|
|
@@ -45,6 +40,18 @@ const claimAfter = claim.slice(phraseAt + phrase.length); | |
| </a> | ||
| ))} | ||
| </div> | ||
| <div class="hero__photos"> | ||
| {hero.photos.map((photo) => ( | ||
| <img | ||
|
Comment on lines
+43
to
+45
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
These images are rendered without any visible status label even though the Kathy found-dog set is classified as concept imagery ( AGENTS.md reference: AGENTS.md:L10-L15 Useful? React with 👍 / 👎. |
||
| src={url(photo.src)} | ||
| width={photo.width} | ||
| height={photo.height} | ||
| alt={photo.alt} | ||
| loading="eager" | ||
| decoding="async" | ||
| /> | ||
| ))} | ||
| </div> | ||
| <p class="hero__body"> | ||
| {hero.paragraph.before} | ||
| <code>{hero.paragraph.code}</code> | ||
|
|
@@ -53,6 +60,19 @@ const claimAfter = claim.slice(phraseAt + phrase.length); | |
| </div> | ||
| <Console /> | ||
| </section> | ||
| <section class="consumer" aria-labelledby="consumer-title"> | ||
| <p class="eyebrow">{consumerHow.eyebrow}</p> | ||
| <h2 id="consumer-title">{consumerHow.heading}</h2> | ||
| <p class="consumer__text">{consumerHow.text}</p> | ||
| <p class="consumer__lead">{consumerHow.lead}</p> | ||
| <ol class="consumer__steps"> | ||
| {consumerHow.steps.map((step) => ( | ||
| <li> | ||
| <strong>{step.title}</strong> {step.text} | ||
| </li> | ||
| ))} | ||
| </ol> | ||
| </section> | ||
| <Anatomy /> | ||
| <section class="compare" aria-labelledby="compare-title"> | ||
| <h2 id="compare-title">{comparisonHeading}</h2> | ||
|
|
||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,51 @@ | ||
| import { describe, expect, it } from "vitest"; | ||
| import { consumerHow, featured, hero } from "../src/content/hero"; | ||
|
|
||
| // Moved from content.test.ts for the max-lines rule. | ||
| describe("hero and featured statement (spec 3.2, home top 2026-10-14)", () => { | ||
| it("matches the hero copy", () => { | ||
| // [MICHAEL 2026-10-14] New home top: eyebrow, headline, the barcode/QR | ||
| // comparison sub-headline, two photos, no hero buttons, and the roadmap | ||
| // caveats removed from the hero body. | ||
| expect(hero.eyebrow).toBe("The next evolution of the barcode"); | ||
| expect(hero.title).toBe("A barcode/QR code you can write by hand"); | ||
| const sub = hero.subline; | ||
| expect(sub.code).toBe("zz-Kathy-found-dog-zz"); | ||
| expect(sub.before + sub.code + sub.after).toBe( | ||
| "Barcodes use bars. QR codes use dots. zzThis uses everyday words. Just wrap your words in double z’s - like zz-Kathy-found-dog-zz - write it on anything with a marker, and scan it to open its digital record. The “zz” ends tell our scanner exactly where to look, just like the three corner dots on a QR code.", | ||
| ); | ||
| const { before, code, after } = hero.paragraph; | ||
| expect(before + code + after).toBe( | ||
| "zzThis is a human-readable, human-writable code for the physical world. Write a zz-code on tape, a crate, a parcel, an envelope, or a sign, or embed it in text or program code. zzThis makes things readable-writable-smart.", | ||
| ); | ||
| expect(code).toBe("zz-code"); | ||
| expect(hero.photos.map((photo) => photo.src)).toEqual([ | ||
| "images/hero/kathy-corkboard.webp", | ||
| "images/hero/kathy-phone-record.webp", | ||
| ]); | ||
| // [MICHAEL 2026-10-15] Buttons restored, How it works first. | ||
| expect(hero.actions.map((action) => action.label)).toEqual([ | ||
| "How it works", | ||
| "See field logistics", | ||
| ]); | ||
| }); | ||
|
|
||
| it("matches the consumer how-it-works block", () => { | ||
| expect(consumerHow.eyebrow).toBe("Physical-to-digital addressing"); | ||
| expect(consumerHow.heading).toBe("Skip the printer. Grab a marker."); | ||
| expect(consumerHow.steps.map((step) => step.title)).toEqual([ | ||
| "Create it.", | ||
| "Write it.", | ||
| "Look it up.", | ||
| ]); | ||
| }); | ||
|
|
||
| it("matches the featured statement", () => { | ||
| expect(featured.heading).toBe( | ||
| "The shortest, smartest distance between a physical thing, its digital record, and the work that comes next.", | ||
| ); | ||
| expect(featured.text).toBe( | ||
| "A zz code gives people a way to create the mark themselves, wherever the work happens. Future AI-assisted workflows could help identify what a camera sees, count what remains, suggest how an item should be handled, and prepare the next task; those capabilities are explorations, not shipped v1 behavior. The same visible code connects the item, its history, and the people responsible for it. It bridges physical things and their digital control. AI may serve as an interface and connector, not as the authority that defines or resolves a zz code.", | ||
| ); | ||
| }); | ||
| }); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The accepted marketing spec still requires the previous H1 character-for-character and defines the existing Home sequence (
specs/001-marketing-site/spec.md:31-33), while this commit adds only an intent markedStatus: draftand immediately changes both implementation and regression tests. Landing this leaves the tested product contract contradicting the authoritative spec; promote and update the spec through the required intent/spec sequence before replacing the H1, or retain the specified copy.AGENTS.md reference: AGENTS.md:L10-L15
Useful? React with 👍 / 👎.