Template
Ballotbox
An internal feature-request board where team members submit ideas, upvote or downvote them, discuss in threads, and watch status move from new to shipped. It helps product owners prioritise by visible consensus without adopting a heavy feedback tool.
Feature request voting board · App · Small tools and apps · full-stack app (auth + DB)
A mock-up of the homepage, drawn from this design’s layout, palette and typefaces. A build follows the full prompt below.
Start from this templateRead the build prompt
Typefaces
The design relies on Manrope's variable weight for its richer body colour, so it keeps Manrope while most other templates move off it.
- ManropeHeadings: headings 56px 700 at -1.12px
- ManropeBody: body 16px at an intermediate ~460 weight
Who it is for
- Product managers gathering requests
- Startup founders prioritising
- Internal teams voting on improvements
- Moderators managing feedback
Layout
- Split hero on white with faint pink/lavender corner glow and dot grid: black rounded logo tile + wordmark above a bold 3-line headline, subcopy, lavender primary + outline secondary buttons
- Right: floating 'Feature ideas' card listing requests with up/down vote pills, status chip and category tag; decorative circular thumbs-up and heart badges around it
- Dark rounded 'Three steps' band (submit, vote & discuss, watch it ship)
- Prioritisation features two-column: heading/subcopy left, 2x2 outlined feature cards right
- Dark rounded CTA panel with lavender button
- Minimal footer; sticky white nav on scroll with 'How it works' and black 'Get started'
- App: board list with search, sort, category filters; request detail with comments; submit dialog; admin status controls
Palette
Friendly, crisp, collaborative, modern, playful accents. Soft lavender and pink punctuate a mostly neutral, confident layout.
- background
#ffffff - text (warm black)
#1e1a16 - dark band / primary
#1e1a16 - accent lavender
#c3b9ff - secondary sand
#eee7dd - highlight pink
#e5559b - border
#e0d9d2
Every checked pair, measured again
| Sample | Where | Ratio | Needs |
|---|---|---|---|
| Aa | body text on background | 17.29:1 | 4.5:1 |
| Aa | muted text on background | 5.90:1 | 4.5:1 |
| Aa | light text on dark primary button | 16.77:1 | 4.5:1 |
| Aa | dark text on lavender CTA | 9.64:1 | 4.5:1 |
| Aa | text on sand secondary | 14.09:1 | 4.5:1 |
| Aa | white text on dark band | 17.29:1 | 4.5:1 |
| lavender button on dark band (boundary) | 9.64:1 | 3:1 | |
| focus ring on background | 3.51:1 | 3:1 | |
| focus ring on muted surface | 3.06:1 | 3:1 | |
| pink highlight badge icon on background | 3.44:1 | 3:1 | |
| input border on background | 3.05:1 | 3: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
- Manrope 700, 56px with -1.12px tracking
- Body
- Manrope ~460 weight at 16px, warm grey secondary
Single Manrope family using an intermediate body weight for a slightly richer text colour. Accessibility: body copy 16px or larger at 1.5+ line height with a ~70ch max measure; no text below 12px; weights under 400 only at 32px+; uppercase reserved for short labels with 0.05em+ tracking.
Spacing and imagery
1100px container, split hero with generous gutters, 8px radius chips and cards, 24px radius on dark bands, tidy outlined cards.
No photos; a UI mock of the voting list with floating circular icon badges; subtle radial glows and dot-grid texture.
Components
- Logo tile + wordmark
- Split hero with floating UI mock
- Vote pill buttons (up/down with counts)
- Status chips (new, under review, planned, in progress, shipped)
- Category tags
- Dark rounded section bands
- Outlined feature cards
- Submit idea dialog
- Search, sort and category filter bar
- Request detail with threaded comments
- Admin status dropdown
- Google sign-in
Interactions
- Upvote/downvote toggles with optimistic count update
- Real-time vote and status updates
- Sort by most votes or newest
- Filter by category, clear all filters
- Threaded replies; delete own comment
- Admin/moderator status changes
- Submit dialog validation
- Sticky nav appears on scroll
Data
Profile{user_id, name, avatar_url}UserRole{user_id, role: admin|moderator|user}Request{id, author_id, title, description, category, status, score, created_at}Vote{request_id, user_id, value: 1|-1}Comment{id, request_id, parent_id, author_id, body, created_at}
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 a template'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 templates) - 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.
### Goal Build **Ballotbox**, an internal feature-request and voting board for product teams. Anyone on the team submits an idea, votes it up or down, and discusses it; admins and moderators move ideas through New → Under review → Planned → In progress → Shipped. The board makes priorities visible and gives everyone a voice. ### Stack React 18 + TypeScript + Vite, Tailwind CSS, shadcn/ui (Radix), lucide-react. TanStack Query with optimistic updates, react-hook-form + zod for submissions and comments, Framer Motion for vote bumps and list reordering, date-fns for relative times. Supabase: Auth (email + Google), Postgres (votes, comments, requests), Realtime subscriptions for live vote counts and status changes. ### Pages & layout 1. **Landing**: split hero on white with soft pink/lavender glows and a faint dot grid -- logo tile and wordmark, large three-line headline, subcopy, lavender primary and outlined secondary button; on the right a floating mock list of ideas with vote pills, status and category chips, plus circular icon badges around it. A dark rounded band with three steps; a two-column features block (heading left, 2×2 outlined cards right); a dark rounded CTA; small footer. The nav turns sticky and white on scroll. 2. **Board**: toolbar with search, sort (Top / Newest), category chips and "Clear filters"; list of request rows (vote column, title, excerpt, status chip, category tag, author, comment count); "Submit idea" button. 3. **Request detail**: title, description, author, status (editable for admins/moderators), vote control, threaded comments with reply. 4. **Profile**: name, avatar, my ideas and votes. 5. **Admin**: users and roles; categories. ### Design system Light. Tokens: `--background: #ffffff`, `--foreground: #1e1a16`, `--primary: #121130` (dark buttons) with `--primary-foreground: #f4f5f8`, `--accent: #c3b9ff`, `--secondary: #eee7dd`, `--muted: #f3efea`, `--border: #e0d9d2`, `--ring: #8874ff`; status colours new grey, review amber, planned indigo, in progress blue, shipped green. Font: Manrope 400/500/700 (body at 460 if variable). Scale 12/14/16/20/36/56. Radius 8px, 24px for dark bands. Shadow on floating mock `0 20px 50px rgb(30 26 22 / .08)`. Motion 180ms; vote count pops with a small scale spring. `--ring` is `#8874ff` (the pale `#c3b9ff` lavender stays a fill with dark text). Add `--muted-foreground: #6b635b` and `--input-border: #a5907c`. ### Components & interactions Vote pill: neutral, upvoted (filled lavender), downvoted (filled pink), disabled when signed out (tooltip prompts sign-in), pending. List reorders smoothly when sort is by votes. Submit dialog: title required (≤120 chars), description (≤2000), category select; submit disabled while posting. Comments show loading skeleton, empty state, and error retry. Status changes toast and appear in the activity line. ### Data & state Profile, UserRole, Request(score cached), Vote(unique per user/request, value ±1), Comment(parent_id for threads). Maintain `score` with a trigger on votes. Server state via TanStack Query; Realtime invalidates affected rows. Filters in URL. Seed ~20 fictional ideas across Design, Backend, Frontend, Integrations and Analytics. ### Accessibility Vote buttons have `aria-pressed` and labels like "Upvote: 24". Status chips include text. Lavender CTA uses dark text for contrast. Comment threads use nested lists with proper headings. Focus ring uses `--ring` at 2px with offset. Motion reduced when requested. Type: body 16px+, line height 1.5+, max ~70ch, nothing under 12px. Verified contrast: body text #1e1a16 on #ffffff = 17.29:1; muted text #6b635b on #ffffff = 5.9:1; light text #f4f5f8 on #121130 = 16.77:1; dark text #1e1a16 on #c3b9ff = 9.64:1. ### Security RLS: authenticated users read requests and comments; users insert their own requests, votes and comments; only authors edit/delete their own content; status updates allowed only for admin/moderator via a `has_role()` security-definer check. Unique constraint prevents double voting. Validate text length with zod and DB checks; render comments as plain text or sanitized markdown. Rate-limit submissions and comments per user. Restrict sign-up to your email domain if the board is internal. ### Performance & SEO Paginate or infinite-scroll the board; index score and created_at. Debounce search. Landing meta/OG; board `noindex` if private. ### Guardrails - Original copy and fictional sample ideas; no third-party product logos. - No invented testimonials. - Typed components, no `any`, visible errors. - Done when: a user can submit, vote once (toggle/switch), and comment; counts update live in a second browser; admins change status and users can't; filters and sort combine correctly; users can delete only their own comments.