Skip to main content
vibld

Template

Sowfield

A referral page in a freelancer invoicing and payments app. Freelancers invite peers by typing several email addresses or sharing a link, then track each referral's status and earnings in an activity table.

Freelancer referral dashboard with email-chip invites and activity table · App screen: referral · Small tools and apps · full-stack app (auth + DB)

A mock-up of the screen, drawn from its layout, palette and typefaces. A build follows the full prompt below.

Start from this screenRead the build prompt

Typefaces

The catalog's own faces. A screen composed into a template is drawn in that template's typefaces.

  • InterHeadings: Inter 700, 32px page title; 18px banner headline (600)
  • InterBody: Inter 400 16px body; 14px instruction and sub lines; 15px table cells

Patterns

  • deep-teal gradient banner with line illustration and secondary CTA
  • multi-email chip input with inline Invite button
  • share-link strip with social icon buttons
  • activity section with status filter select + search
  • filled pill-shaped sidebar active item
  • bold page title
  • warm grey filled inputs

States it is designed for

  • Empty activity ("No referrals yet. Your invites will appear here.")
  • Invalid email chips
  • Already invited or already a member (chip warning)
  • Sending / partial failure with retry
  • Table loading skeleton
  • No results for filter/search
  • Bonus paid row (green badge)
  • Daily invite limit reached

Who it is for

  • Freelancers and independent contractors
  • Agencies paying freelancers
  • Community managers running referral programs

Layout

  1. Left sidebar (~185px): wordmark with product sub-label; Home, Invoices, Agreements, Clients, Referral (active filled teal), Projects, Settings; user card with chevron at bottom
  2. Main: H1 "Referral"
  3. Teal banner: handshake line illustration, headline + two-line description with bold bonus, dark "Program conditions" button right
  4. Instruction line; wide chip input + dark "Invite" button
  5. Share strip: text left, copy-link / social icon buttons right
  6. Referral activity: H2 + subline; filter select and search side by side; table (friend, invited on, status, earnings)
  7. Mobile: banner stacks; input and button stack; table becomes cards

Palette

confident, sturdy, professional, supportive. A money tool that treats referrals as a real earnings channel.

  • page background#ffffff
  • banner, active nav, buttons#00413c
  • banner gradient end#034d51
  • text on teal#ffffff
  • secondary text on teal#d6e6e3
  • primary text#1f2a2a
  • sub lines, placeholders on white#5c6b6b
  • filled input background#ebebe6
  • placeholder on filled input#5f6360
  • share strip background#f7f7fa
  • paid status#1d7a4a

Every checked pair, measured again

SampleWhereRatioNeeds
Aabody text14.76:14.5:1
Aamuted text5.57:14.5:1
Aabanner text11.53:14.5:1
Aabanner secondary text8.94:14.5:1
Aaplaceholder on filled input5.10:14.5:1
Aashare strip text13.80:14.5:1
Aapaid status text5.34:14.5:1
focus ring11.53:13:1
Aabanner gradient end text9.61:14.5:1

As vibld’s tokens

The palette on the fifteen colour tokens vibld styles a project with, each text colour 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
Inter 700, 32px page title; 18px banner headline (600)
Body
Inter 400 16px body; 14px instruction and sub lines; 15px table cells

Similar to the observed grotesk; nav 15px 600. Amounts use tabular numerals.

Spacing and imagery

Roomy: 8px base; 32px page padding; 24px between blocks; inputs 48px tall; radius 6px inputs, banner and buttons 8px; banner has no shadow; buttons flat.

One white line illustration (handshake) on the banner; monochrome social glyphs in the share strip; filled nav icons.

Components

  • Sidebar with filled active pill
  • Gradient banner with CTA
  • Email chip input (paste, comma, space, Enter separators)
  • Invite button with loading
  • Share strip with icon buttons
  • Status filter select
  • Search input
  • Referral activity table with status badges
  • Program conditions dialog

Interactions

  • Typing a comma, space or Enter converts text to a chip; invalid emails turn the chip red with an error icon
  • Backspace in an empty input removes last chip
  • Invite sends all valid chips and shows per-address result
  • Copy link icon copies and shows toast; social buttons open prefilled share windows
  • Filter and search update the table instantly (debounced 200ms)

Data

  • Freelancer{id, name, email}
  • ReferralInvite{id, referrer_id, email, sent_at, status (sent|signed_up|qualified|paid|expired)}
  • ReferralEarning{id, invite_id, amount, currency, paid_at}
  • ProgramRule{id, bonus_amount, currency, conditions_md}

Guardrails

Experience

  • Accept pasted lists of emails and split them automatically
  • Show per-address results after sending instead of a single toast
  • Keep the conditions one click away from the banner
  • Default the activity filter to "All" and remember the last choice
  • Show earnings totals above the table once any exist

Accessibility

  • Chip input exposes each chip as a button "Remove name@example.com"
  • Invalid chips are described by an error message, not colour alone
  • Table uses real <table> with scope headers and a caption
  • Social icon buttons have aria-labels ("Share on a professional network")
  • Status badges include text

Security

  • Validate emails with zod client and server; cap invites per day
  • Send invites via a transactional email service from a server function; never expose API keys
  • RLS: freelancers read only their own invites and earnings
  • Do not reveal whether an email already has an account (generic "already invited or registered")

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
Paste an entry's build prompt into your coding agent as the first message. Each prompt names its own stack, tokens and acceptance criteria; the rules below apply to all of them and can be prepended once per project.

### Engineering baseline
- TypeScript strict mode, no `any`, small typed components, feature folders, and one source of truth for design tokens (CSS variables consumed by Tailwind).
- Validate every input with a shared zod schema on the client and again on the server or edge function. Never trust client-side checks alone.
- Show loading, empty and error states for every async view. Surface errors in plain language with a retry, and log details to the console in development only.
- Keep secrets out of the bundle. Only publishable keys (for example a Supabase anon key) belong in client code; service-role keys, API keys and webhooks live in server or edge-function environment variables.

### Data and auth baseline (full-stack entries)
- Enable Row Level Security on every table before inserting data. Default-deny, then add owner-scoped policies (`auth.uid() = user_id`) and explicit role checks for admin views.
- Store roles in a separate table checked by a security-definer function, never in a user-editable profile field.
- Upload files to private storage buckets with size and MIME limits, and serve them through signed URLs.
- Rate-limit public endpoints (forms, auth, AI calls) and add a honeypot field or captcha to anonymous forms.
- Take payments through a hosted checkout and verify webhooks by signature. Never handle raw card data.

### Accessibility and UX baseline
- Target WCAG 2.2 AA: 4.5:1 contrast for normal text and 3:1 for large text, input borders, focus rings and meaningful icons or chart lines. Every palette in this catalog lists its verified pairs; re-check with a contrast tool after any colour change.
- Keep body text at 16px or larger with 1.5 line height, nothing below 12px, no light weights under 24px, and uppercase only for short labels.
- Give every interactive element a visible focus ring, full keyboard support, semantic landmarks, labelled form fields, and alt text on meaningful images.
- Respect `prefers-reduced-motion` for every animation. Give drag-and-drop and carousels keyboard and button alternatives.
- Build mobile-first and test at 375px, 768px and 1280px.

### Content guardrails
- Use original copy, fictional sample data and placeholder or licensed imagery. Do not reuse another product's name, logo, screenshots or marketing text.
- Label demo testimonials and metrics as samples. Collect the minimum personal data the feature needs.

### SaaS screen baseline
- Design every screen for its full set of states: first-run empty, loading skeleton, partial data, error with retry, permission-denied, and success feedback. Each entry lists the states its screen needs.
- Keep destructive actions (delete, revoke, downgrade, remove member) behind a confirmation that names the object, and prefer undo over a second dialog where the action is reversible.
- Enforce authorisation on the server for every action a screen exposes. Hiding a button is not access control; check the role again in the API or RLS policy.
- Never show secrets (API keys, tokens) in full after creation. Show them once, then mask them, and offer rotate and revoke.
- Keep the app shell (navigation, workspace switcher, account menu) consistent across screens, and preserve filters, sort and scroll position when the user navigates back.
### Goal
Build **Sowfield**, the referral page of a freelancer invoicing app. Freelancers enter several email addresses at once or share a link, and then follow each referral's status and bonus in an activity table.

### Stack
React + TypeScript + Vite, Tailwind CSS, shadcn/ui (Select, Dialog, Toast, Skeleton) on Radix, lucide-react, TanStack Query and TanStack Table, react-hook-form + zod. Supabase for auth and data; an Edge Function sends invites through a transactional email service.

### Pages & layout
1. **Sidebar**: invented wordmark with a "Talent" sub-label; Home, Invoices, Agreements, Clients, Referral (active: a filled teal pill with white text), Projects, Settings; a user card at the bottom.
2. **Title**: "Referral".
3. **Banner** (teal gradient, 8px radius): white handshake line illustration; headline "Invite a peer, both earn"; a two-line description with a bold "$30 each"; a dark "Program conditions" button on the right that opens a dialog.
4. **Invite row**: helper line ("Separate addresses with a comma, a space or Enter"); a wide warm-grey chip input; a dark "Invite" button.
5. **Share strip**: light grey panel with text on the left and copy-link and three social icon buttons on the right.
6. **Referral activity**: H2 and subline; status Select (All, Sent, Signed up, Paid) and a search input; a table with friend, invited on, status and bonus columns.
7. Mobile: the banner and invite row stack, and table rows become cards.

### Design system
- Colors: `--bg: #ffffff` (page background), `--brand: #00413c` (banner, active nav, buttons), `--brand-2: #034d51` (banner gradient end), `--on-brand: #ffffff` (text on teal), `--on-brand-muted: #d6e6e3` (secondary text on teal), `--fg: #1f2a2a` (primary text), `--muted: #5c6b6b` (sub lines, placeholders on white), `--field: #ebebe6` (filled input background), `--placeholder: #5f6360` (placeholder on filled input), `--strip: #f7f7fa` (share strip background), `--success: #1d7a4a` (paid status).
- Fonts: Inter (similar to the observed grotesk): title 32px/700, banner headline 18px/600, body 16px/1.5, helper 14px, table 15px, nav 15px/600.
- Spacing: 8px scale; 32px page padding; 24px block gap; 48px input height.
- Radius: 6px inputs; 8px banner, buttons and strip; sidebar active item 8px.
- Shadows: none.
- Motion: chip add/remove 120ms scale; toast slide; table row fade on filter.

### Components & interactions
Sidebar, ReferralBanner, ConditionsDialog, EmailChipInput (parse on comma, space, Enter and paste; Backspace removes the last chip; invalid chips shown in red with an icon and message), InviteButton (loading, then per-address results list), ShareStrip (copy with toast; social share URLs opened in a popup), ActivityFilters, ReferralTable (sortable, empty, loading, no-results), StatusBadge, EarningsSummary.

### Data & state
Tables: `referral_invites(id, referrer_id, email, sent_at, status)`, `referral_earnings(id, invite_id, amount, currency, paid_at)`, `program_rules(id, bonus_amount, currency, conditions_md)`. Mock six invites across statuses with invented names. Handle states: empty activity, invalid chips, already invited, sending/partial failure, loading, no results, paid, daily limit.

### Accessibility
Each chip is a removable button labelled with its address; errors are linked with aria-describedby. The table has a caption and header scopes. Social buttons are labelled generically. Badges always include text. Focus ring: 2px teal with a 2px white offset.
Verified contrast: body text: #1f2a2a on #ffffff = 14.76:1; muted text: #5c6b6b on #ffffff = 5.57:1; banner text: #ffffff on #00413c = 11.53:1; banner secondary text: #d6e6e3 on #00413c = 8.94:1; placeholder on filled input: #5f6360 on #ebebe6 = 5.10:1; share strip text: #1f2a2a on #f7f7fa = 13.80:1; paid status text: #1d7a4a on #ffffff = 5.34:1; focus ring: #00413c on #ffffff = 11.53:1; banner gradient end text: #ffffff on #034d51 = 9.61:1.

### Security
Validate and deduplicate emails with zod on the client and in the Edge Function; cap at 20 addresses per request and 50 per day per user. Keep email service credentials in function secrets. RLS: users read and insert only their own invites; earnings are server-written. Responses never reveal whether an address already has an account.

### Performance & SEO
Paginate activity server-side (25 rows). Debounce search. Lazy-load the conditions dialog. The app is noindex.

### Guardrails
- Invented wordmark, names and bonus amounts; generic social icons without brand names in labels.
- Never send invites without explicit button press.
- Acceptance criteria: (1) pasted lists become chips and invalid ones are flagged; (2) Invite shows per-address results; (3) filter and search work together; (4) every state renders; (5) contrast and keyboard checks pass.

Open the builderAll templatesThis palette on its own