Template
14 Larkspur Lane
a site for one house for sale that shows it room by room, gives every fact a buyer needs, books showings and takes open house sign-ins, with the listing agent one tap away.
Single-property listing site with open house sign-in · Website · Small business site · 4 pages
A mock-up of the homepage, drawn from this design’s layout, palette and typefaces. A build follows the full prompt below.
Add app screens
Pick up to 6 screens, such as a dashboard, settings or an empty state. Each is built in this design’s own palette and typefaces, with its states and guardrails.
Start from this templateRead the build prompt
Typefaces
Italiana’s thin, wide capitals read like an architect’s title block; Onest keeps prices and measurements clear.
- ItalianaHeadings: the address, room names and headlines
- OnestBody: facts, body and forms
Who it is for
- Buyers who saw the sign or the listing and want the full picture
- Buyers’ agents sending it to clients
- Visitors at the open house signing in on a tablet
Layout
- Minimal top bar: the address, Photos, Details, and Book a showing
- Full-bleed photo hero with the address, price and status chip
- Key facts stats row: beds, baths, square feet, lot, year built, price
- Room by room gallery: tabs for each room with two or three photos and a caption
- Floor plan: the plan image with a room list beside it
- Features list in three columns (inside, outside, systems)
- Neighborhood: walk times to places as a list, with a map link
- Open house times and a showing request form, then the agent card
- Footer with brokerage name, license number and the equal housing statement
Palette
Architectural and calm, like a magazine spread on a well-made house: warm white, charcoal, an olive accent, generous photography.
- warm white
#faf8f5 - charcoal
#262421 - olive
#4b5a3a - sand
#e8dcc6
Every checked pair, measured again
| Sample | Where | Ratio | Needs |
|---|---|---|---|
| Aa | body text on the page | 14.60:1 | 4.5:1 |
| Aa | text on cards | 13.01:1 | 4.5:1 |
| Aa | secondary text on muted surfaces | 5.66:1 | 4.5:1 |
| Aa | secondary text on the page | 6.59:1 | 4.5:1 |
| Aa | label on the primary action | 7.02:1 | 4.5:1 |
| Aa | label on secondary surfaces | 13.01:1 | 4.5:1 |
| Aa | label on the accent | 11.41:1 | 4.5:1 |
| Aa | error label | 5.46:1 | 4.5:1 |
| primary action against the page | 7.02:1 | 3:1 |
As vibld’s tokens
The palette on the 15+ color tokens vibld styles a project with, each text color on the fill it is read on. Marked tokens are solved from the palette, because no swatch held that role at 4.5:1.
- background
- card *
- muted *
- primary
- secondary *
- accent
- destructive *
Type scale
- Display
- Italiana, the address, room names and headlines
- Body
- Onest, facts, body and forms
Spacing and imagery
Editorial: full-bleed photos, text in a narrow column, 104px between sections.
The house’s own photography in natural light, wide and level; a floor plan drawing; a few neighborhood details (the park, the main street).
Components
- Status chip (Coming soon, For sale, Under contract, Sold) the agent changes in content
- Room tabs with keyboard support and swipe on phones
- Agent card: photo, name, brokerage, phone and email as tap targets
Interactions
- The open house page uses large fields and resets itself after each sign-in for the next visitor
- Room tabs keep the chosen room in the address
Data
rooms: a room: name, floor, size, photos with alt text, captionopen-houses: an open house: date, start, end, host agentform showing-request: name, email, phone, preferred days and times, working with an agent (yes or no), agent name, messageform open-house-sign-in: name, email, phone, working with an agent (yes or no), agent name, how you heard, may we follow up (yes or no)
Build prompt
The baseline every prompt in the catalog assumes, then this design’s own ten sections, from goal to guardrails.
The baseline
### How to use these prompts
Each niche site prompt describes a whole small site for one kind of owner: its pages, the records it keeps, the forms it collects and the tools it links to. The rules below apply to every one of them.
### Niche site principles
- The site does the one job its owner needs most (a sign-up, an RSVP, a request, a visit) on the first screen, and every page leads back to it.
- Records the owner adds often (sermons, events, listings, galleries, menus, tour dates) are content collections in `src/content/`, each record with a slug, so a new record gets its page with no code change.
- Tools the owner already pays for or uses (giving, tickets, booking, listing search, ordering) are linked, or framed in an `<iframe>` whose address is in `content.ts`, never rebuilt. With no address, a plain button links out instead, and nothing pretends to work.
- Copy is written for the owner's visitors, specific and plain. Dates, times and places are real fields, never baked into prose.
- The design is this site's own. Its layout, type and motion follow the brief, not a shared template.
### Forms
Every form is a plain HTML form, `<form method="post" action="/__vibld/forms/<name>">`, named as the brief names it (lowercase letters, digits and hyphens). Fields are ordinary named inputs; checkboxes repeat their name; no file uploads. Add a hidden `_next` input with the path to land on, and show a thank-you there when the address has `?submitted=<name>`. Add an empty hidden `_gotcha` input. A script may post it instead with `fetch(form.action, { method: 'POST', body: new FormData(form), headers: { accept: 'application/json' } })`, which answers `{ ok: true }` or `{ ok: false, error }`. A form with limited places lists them in `public/vibld.forms.json` (`{"forms":{"<name>":{"slots":{"field":"<field>","options":{"<value>":<places>}}}}}`), the field a select or radio whose values match those keys exactly; `GET /__vibld/forms/<name>/slots` returns `{ field, options: [{ value, capacity, taken, left }] }`, which the page reads to show what is left and disable full options. vibld adds bot protection when the page is served.
### Engineering baseline
- TypeScript strict mode, small typed components, and one source of truth for design tokens (CSS variables consumed by Tailwind).
- All copy lives in typed content files, so the owner can edit words without touching layout.
- Every form validates on the client, says what went wrong in plain words beside the field, and never claims success it has not had.
- No secrets in the bundle and no third-party scripts beyond Google Fonts; an owner's tool comes in only as a link or a framed page.### Goal
Build **14 Larkspur Lane**: a site for one house for sale that shows it room by room, gives every fact a buyer needs, books showings and takes open house sign-ins, with the listing agent one tap away.
### Stack
React + TypeScript + Vite, Tailwind CSS and React Router, one route per page. Content collections in `src/content/`, forms posting to vibld (see Forms in the baseline). No backend of its own.
### Pages & layout
- `/` The house: hero, key facts, room by room, floor plan, features, neighborhood, open house, agent
- `/photos` Photos: every photo by room
- `/open-house` Open house sign-in: a large, tablet-friendly sign-in form
- `/details` Details and disclosures: taxes, fees, systems, disclosures download, fair housing statement
Home, top to bottom:
1. Minimal top bar: the address, Photos, Details, and Book a showing.
2. Full-bleed photo hero with the address, price and status chip.
3. Key facts stats row: beds, baths, square feet, lot, year built, price.
4. Room by room gallery: tabs for each room with two or three photos and a caption.
5. Floor plan: the plan image with a room list beside it.
6. Features list in three columns (inside, outside, systems).
7. Neighborhood: walk times to places as a list, with a map link.
8. Open house times and a showing request form, then the agent card.
9. Footer with brokerage name, license number and the equal housing statement.
Copy to start from, in `content.ts`: headline "14 Larkspur Lane", subcopy "A 1928 brick colonial on a quiet street, four bedrooms, a deep garden, ten minutes’ walk to the station.", primary action "Book a showing".
### Design system
Mood: Architectural and calm, like a magazine spread on a well-made house: warm white, charcoal, an olive accent, generous photography.
Palette: warm white `#faf8f5`, charcoal `#262421`, olive `#4b5a3a`, sand `#e8dcc6`. Tokens: background `#faf8f5`, foreground `#262421`, primary `#4b5a3a` with `#faf8f5` labels, cards `#edebe8`, accent `#e8dcc6`.
Type: Italiana for the address, room names and headlines; Onest for facts, body and forms. Load both from https://fonts.googleapis.com/css2?family=Italiana&family=Onest:wght@400;600&display=swap.
Corners: 2px on controls, 6px on cards, 12px on large panels. Spacing: Editorial: full-bleed photos, text in a narrow column, 104px between sections.
Imagery: The house’s own photography in natural light, wide and level; a floor plan drawing; a few neighborhood details (the park, the main street). Use the owner's photos where the project has them. Without them, use the project's stock photos, or shapes and color from the palette; never a stock photo of people at desks.
### Components & interactions
- Status chip (Coming soon, For sale, Under contract, Sold) the agent changes in content
- Room tabs with keyboard support and swipe on phones
- Agent card: photo, name, brokerage, phone and email as tap targets
Motion:
- The open house page uses large fields and resets itself after each sign-in for the next visitor
- Room tabs keep the chosen room in the address
The signature motion is: room photos crossfade slowly as tabs change, with the room name sliding in like a caption on a gallery wall. Keep it to that one; everything else is a 150 to 300ms state change. With prefers-reduced-motion, it and every reveal are still.
### Data & state
Collections:
- `src/content/rooms.json`: a room: name, floor, size, photos with alt text, caption
- `src/content/open-houses.json`: an open house: date, start, end, host agent
Forms:
- `showing-request`: A buyer asks to see the house. Fields: name, email, phone, preferred days and times, working with an agent (yes or no), agent name, message.
- `open-house-sign-in`: A visitor signs in at the open house. Fields: name, email, phone, working with an agent (yes or no), agent name, how you heard, may we follow up (yes or no).
Linked tools:
- The listing on the MLS-fed portals, linked by the agent if they wish; the site itself shows only what the agent enters.
- Disclosures as a PDF the agent uploads.
### Accessibility
WCAG 2.2 AA. Every control has a visible focus ring and a 44px target, every form field a visible label, and errors are announced. Dates and times are written out ("Sunday, March 8, 10:30 AM"), not only shown in a grid. Images have alt text that says what is in them. Verified contrast: body text on the page #262421 on #faf8f5 14.60:1; text on cards #262421 on #edebe8 13.00:1; secondary text on muted surfaces #5b5956 on #e9e7e4 5.65:1; secondary text on the page #5b5956 on #faf8f5 6.58:1; label on the primary action #faf8f5 on #4b5a3a 7.01:1; label on secondary surfaces #262421 on #edebe8 13.00:1; label on the accent #262421 on #e8dcc6 11.41:1; error label #ffffff on #c62f2f 5.45:1; primary action against the page #4b5a3a on #faf8f5 7.01:1.
### Security
No third-party scripts other than Google Fonts. Framed tools are `<iframe>`s from the owner's own address with a `title`, `loading="lazy"` and `referrerpolicy="strict-origin-when-cross-origin"`. Forms cap input length and carry the empty `_gotcha` field.
### Performance & SEO
Images as AVIF or WebP with width and height, the first one eager and the rest lazy. Preconnect to Google Fonts. Each page has its own title and description from content, and records' pages take theirs from the record. Structured data where it fits: RealEstateAgent, and Place for a listing.
### Guardrails
- Avoid: IDX search or any other listings on this site, a mortgage calculator promising rates, stock lifestyle photos, and the word "dream".
- One primary action per screen, one accent color, at most six top-level links.
- No carousel in the hero, no mega menu, no emoji or clip-art icons, no hard offset shadows, no purple-to-blue gradient.
- The names in it are invented. Use no real organization's or person's name, logo or trademark.