Template
Mellowquill
A general AI assistant's conversation view tuned for reading. Answers are set in a comfortable serif on a warm paper-like canvas with small inline source chips, while the composer floats at the bottom with attachments, a model selector and voice input.
Reading-first AI chat feed with serif answers and inline citations · App screen: chat · 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.
- Source Serif 4Headings: Source Serif 4 400, 17px/1.65 for assistant prose (reading size)
- InterBody: Inter 400, 16px/1.5 for UI, user bubbles and composer; chips 12px 500; caption 12px
Patterns
- thin icon rail
- conversation title dropdown with share button
- right-aligned beige user bubble
- serif long-form assistant typography
- web-search activity disclosure
- inline source chips inside prose
- floating composer card with model picker and voice
- disclaimer caption under composer
States it is designed for
- new chat greeting
- streaming with brand glyph pulse
- searching sources (live list)
- answer with citations
- source unavailable (chip shows warning)
- regenerated versions (1/2 arrows)
- share link created / revoked
- attachment uploading / too large
- usage limit reached message
- offline
Who it is for
- knowledge workers
- researchers and writers
- anyone asking quick questions
Layout
- Icon rail (~30px): sidebar toggle, new chat, search, chats, projects, artifacts, code; bottom: download, avatar
- Header: conversation title with dropdown; Share button right
- Thread column (~450px): user bubble right, web-search activity disclosure, serif answer paragraphs with inline source chips, action icons (copy, up, down, retry), brand mark as typing indicator
- Composer card (~460px) floating above bottom: placeholder 'Ask a follow-up...', + attach, model selector, voice button
- Caption under composer about checking sources
- Below 768px rail becomes a top-left menu; composer full width
Palette
Warm, literate, unhurried. Paper tones and a book serif make long answers feel like reading, not chatting.
- canvas
#faf9f5 - surface
#ffffff - user-bubble
#f0eee6 - text
#1f1e1b - muted
#6a6862 - chip-bg
#efede6 - border
#dedcd4 - icon
#73716a - accent-mark
#d97757 - primary
#1f1e1b - focus
#2c6ecb
Every checked pair, measured again
| Sample | Where | Ratio | Needs |
|---|---|---|---|
| Aa | serif body on canvas | 15.82:1 | 4.5:1 |
| Aa | user bubble text | 14.35:1 | 4.5:1 |
| Aa | muted caption on canvas | 5.29:1 | 4.5:1 |
| Aa | citation chip text | 4.76:1 | 4.5:1 |
| action icon on canvas | 4.64:1 | 3:1 | |
| focus ring on canvas | 4.75:1 | 3:1 | |
| Aa | composer text on white | 16.67:1 | 4.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
- Source Serif 4 400, 17px/1.65 for assistant prose (reading size)
- Body
- Inter 400, 16px/1.5 for UI, user bubbles and composer; chips 12px 500; caption 12px
Serif similar to the observed transitional book face; Inter similar to the observed UI sans.
Spacing and imagery
Airy; 8px base; thread max 680px; 20px between paragraphs; composer padding 12px 16px, radius 20px, soft shadow; user bubble radius 16px; chips radius 6px; icon buttons 32px.
No imagery; a small star-like brand glyph in coral as the typing indicator (decorative).
Components
- icon rail
- conversation title menu (rename, star, delete)
- share button and dialog
- user bubble
- tool activity disclosure
- serif answer body
- inline citation chip with source popover
- message actions
- composer with attach, model select, voice
- disclaimer caption
Interactions
- Citation chips show a source preview popover on hover/focus and open the source in a new tab on click
- The web-search disclosure lists queries and sources
- Retry regenerates with the same prompt, keeping version arrows
- Share creates a read-only link after confirmation
- Voice button toggles dictation with a live waveform
- Enter sends; Shift+Enter newline; Up arrow edits last message
Data
Conversation{id, user_id, title, starred, created_at}Message{id, conversation_id, role, content_md, model, version, parent_id}Citation{id, message_id, url, title, domain_label, snippet}ShareLink{id, conversation_id, token_hash, created_at, revoked_at}
Guardrails
Experience
- Set long answers in a reading serif at 17px+ with a 680px measure
- Keep citation chips small but always legible and focusable
- Make shared links read-only and revocable
- Show which tools ran (web search) before the answer
- Keep the composer reachable without covering the last line (bottom padding)
- Tell users to verify cited sources in a quiet caption
Accessibility
- Citation chips are links with accessible names including the source title
- Popovers open on focus and close with Escape
- Thread is a log; streaming announced when complete
- Model select and voice button labelled
- Serif body meets 4.5:1 on the warm canvas
- Focus ring blue 2px visible on warm backgrounds
Security
- RLS: conversations, messages, citations owned by the user; share links resolve through a security-definer function returning a read-only snapshot
- Share tokens stored hashed; revocation immediate
- Sanitise markdown; external links rel=noopener noreferrer
- Attachment uploads: type/size limits, private bucket
- Rate-limit message creation
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 **Mellowquill**, the conversation view of a general AI assistant designed for reading. Answers render in a book serif on a warm canvas with inline source chips; tool activity (web search) is disclosed above the answer; the composer floats at the bottom with attach, model select and voice.
### Stack
React 18 + TypeScript + Vite, Tailwind CSS, shadcn/ui (Popover, DropdownMenu, Dialog, Select, Tooltip, Toast), lucide-react, react-markdown + remark-gfm with a custom citation node, TanStack Query, zod. Supabase Auth, Postgres, Storage for attachments, an Edge Function streaming from a hosted model API with a web-search tool.
### Pages & layout
1. **Shell**: 48px icon rail.
2. **/chat/:id** (this screen): header 'Trail running basics' with dropdown and Share; user bubble 'What is a good first trail race distance?'; disclosure 'Web search: 4 sources'; three serif paragraphs with inline chips like 'source' labels; action icons; composer 'Ask a follow-up...' with + and a model select 'Standard'; caption 'Answers can be wrong. Check the cited sources.'
3. **Share dialog** and **/s/:token** read-only view.
4. Responsive: rail to menu under 768px; composer full width with safe-area padding.
### Design system
- Colors: `--canvas: #faf9f5`, `--surface: #ffffff`, `--user-bubble: #f0eee6`, `--text: #1f1e1b`, `--muted: #6a6862`, `--chip-bg: #efede6`, `--border: #dedcd4`, `--icon: #73716a`, `--accent-mark: #d97757`, `--primary: #1f1e1b`, `--focus: #2c6ecb`.
- Fonts: Source Serif 4 for answers 17px/1.65; Inter for UI 16px/1.5; chips and caption 12px (minimum).
- Spacing: 8px base; thread 680px max; paragraph gap 20px.
- Radius: composer 20px, bubble 16px, chips 6px.
- Shadows: composer `0 4px 20px rgba(31,30,27,.08)`.
- Motion: brand glyph slow rotate while streaming (off with reduced motion); 150ms popovers.
### Components & interactions
`IconRail`, `ConversationHeader` (TitleMenu, ShareButton), `UserBubble`, `ToolDisclosure`, `AnswerBody` (serif markdown, CitationChip with Popover), `MessageActions` (copy, up, down, retry, version arrows), `Composer` (AttachButton, Textarea, ModelSelect, VoiceButton), `Disclaimer`, `ShareDialog`.
### Data & state
Tables per data model. Streaming via server-sent events; citations stored per message. Share snapshot generated on demand. Mock conversation with three citations from invented sources ('Trail Runner Weekly', 'Coach notes').
### Accessibility
Chips are `<a>` elements with names like 'Source: Trail Runner Weekly'. Popovers keyboard accessible. Log region for thread. Serif and chip colours verified on the warm canvas. Voice button announces recording state.
Verified contrast: serif body on canvas: #1f1e1b on #faf9f5 = 15.82:1; user bubble text: #1f1e1b on #f0eee6 = 14.35:1; muted caption on canvas: #6a6862 on #faf9f5 = 5.29:1; citation chip text: #6a6862 on #efede6 = 4.76:1; action icon on canvas: #73716a on #faf9f5 = 4.64:1; focus ring on canvas: #2c6ecb on #faf9f5 = 4.75:1; composer text on white: #1f1e1b on #ffffff = 16.67:1.
### Security
RLS on all tables by `user_id = auth.uid()`. Share view served by a security-definer function that checks an unrevoked hashed token and returns sanitized content only. Attachments in a private bucket with signed URLs. Sanitised markdown. Rate limits per user.
### Performance & SEO
Stream tokens; defer loading the markdown renderer; self-host fonts with `font-display: swap`. Shared pages get title and description; app routes noindex.
### Guardrails
- Invented topics and sources
- Never present citations without a source link
- Share links read-only and revocable
- Typed code, visible errors
- Acceptance criteria: (1) answers render in serif with working citation popovers; (2) tool disclosure lists search sources; (3) share link works logged out and can be revoked; (4) RLS isolates users; (5) works at 390px.