Template
Murkbell
A fast desktop calendar for people who live in meetings. The week view shows timed events as tinted blocks with coloured accent bars, all-day items in a strip, and a red now-line; the sidebar holds a mini month with week numbers and the list of connected calendars that can be toggled.
Dark week-view calendar with calendar list and colour-coded events · App screen: calendar · 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 600, 16px for month title; 15px 600 event titles
- InterBody: Inter 400, 15px/1.5 (dense calendar), 16px in dialogs; hour labels 12px tabular muted; week numbers 12px
Patterns
- dark week view with hour grid
- mini month with week numbers
- calendar list with coloured checkboxes
- find calendar or room search
- all-day row with banner event
- current-time line with dot and time label
- coloured event chips with left accent bar
- availability and quick-meet actions in top bar
States it is designed for
- loading week skeleton
- empty week
- overlapping events laid out side by side
- all-day overflow (+N more)
- calendar account disconnected (warning in list)
- sync in progress indicator
- event save failed (revert with toast)
- read-only calendar (no drag handles)
Who it is for
- founders and managers with dense schedules
- sales teams
- power users who prefer keyboard-driven tools
Layout
- Sidebar (~200px): collapse icon, mini month (month + year muted, up/down arrows, week-number column, today highlighted), search 'Search calendars and rooms' with shortcut key, 'My calendars' list with coloured checkboxes, 'Connect another account'
- Top bar: month + year, prev/next arrows; right: quick-actions icon, overflow, 'Availability' text button, accent 'Quick call' button
- Day header row: timezone label, 7 day columns with today's date in an accent pill
- All-day row
- Hour grid (08:00 onward) with 1px lines, events as blocks, red now-line with time label
- Below 1024px sidebar collapses; below 768px switches to 3-day then 1-day view
Palette
Sleek, focused, night-friendly. Deep greys with muted tinted events keep long days calm.
- bg
#1c1c1e - sidebar
#1f1f1f - grid-line
#2c2c2e - text
#ececef - muted
#a1a1a8 - accent
#7857ff - on-accent
#ffffff - now
#ff4d5e - event-blue-bg
#1d4a5c - event-green-bg
#1e5a3c - event-red-bg
#6a2a22 - focus
#a996ff
Every checked pair, measured again
| Sample | Where | Ratio | Needs |
|---|---|---|---|
| Aa | body text on bg | 14.43:1 | 4.5:1 |
| Aa | muted hour label on bg | 6.63:1 | 4.5:1 |
| Aa | today pill label | 4.56:1 | 4.5:1 |
| Aa | event title on blue fill | 8.15:1 | 4.5:1 |
| Aa | event title on green fill | 6.90:1 | 4.5:1 |
| Aa | event title on red fill | 9.05:1 | 4.5:1 |
| now line on bg | 5.25:1 | 3:1 | |
| focus ring on bg | 6.88: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
- Inter 600, 16px for month title; 15px 600 event titles
- Body
- Inter 400, 15px/1.5 (dense calendar), 16px in dialogs; hour labels 12px tabular muted; week numbers 12px
Similar to the observed neo-grotesk. No uppercase except weekday initials (12px, +0.05em).
Spacing and imagery
Dense; 4px base; hour rows 36px; day columns flexible; event blocks 4px radius with 3px left accent bar; sidebar 12px padding; radius 6px buttons, 999px today pill; no shadows except the event popover.
No imagery; small icons for quick actions and a lightning glyph for focus blocks.
Components
- mini month with week numbers
- calendar search with shortcut
- calendar list with coloured checkboxes
- add account button
- week header with today pill
- all-day strip
- event block
- now line
- availability panel
- quick meet button
- event popover and editor
Interactions
- Drag on empty grid to create an event; drag edges to resize; drag body to move (15-minute snap)
- Click an event to open a popover; double-click to edit
- Keyboard: J/K next/prev week, T today, C create, / search
- Checkbox toggles a calendar's visibility instantly
- Availability opens a panel to copy free slots as text
- Now-line updates every minute
Data
CalendarAccount{id, user_id, provider_label, status (connected|error)}Calendar{id, account_id, name, color, visible bool, read_only bool}Event{id, calendar_id, title, starts_at, ends_at, all_day bool, location, kind (meeting|focus|personal)}
Guardrails
Experience
- Make today and now unmistakable
- Show week numbers for planning-heavy users
- Keep event text readable on tinted fills (never on saturated fills)
- Snap moves to 15 minutes and show the time while dragging
- Offer an undo toast after moves and deletes
- Surface disconnected accounts in the calendar list
Accessibility
- Event blocks have accessible names with title, day and time
- Drag interactions have keyboard equivalents via the event editor
- Checkbox colour is paired with the calendar name
- Now-line label is text
- Grid is navigable with arrow keys across time slots
- Focus ring light violet 2px on all dark surfaces
Security
- RLS: calendars and events belong to the user's accounts only
- Provider tokens stored server-side encrypted, never sent to the browser
- Validate event times and lengths server-side
- Availability sharing exposes free/busy only, never titles
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 **Murkbell**, a dark, keyboard-friendly week calendar. The sidebar has a mini month with week numbers, a calendar search and a list of connected calendars with coloured checkboxes; the main area is a seven-day hour grid with an all-day strip, tinted event blocks and a red now-line.
### Stack
React 18 + TypeScript + Vite, Tailwind CSS, shadcn/ui (Popover, Dialog, Checkbox, Command, Toast), lucide-react, date-fns, dnd-kit for move/resize, TanStack Query. Supabase Auth and Postgres, plus an Edge Function that syncs external calendars through a generic calendar API adapter.
### Pages & layout
1. **/calendar/week/:date** (this screen): sidebar (mini month 'September 2026' with week numbers 35-40, search 'Search calendars and rooms' with 'C' hint, My calendars: work address, Birthdays, Public holidays, Week numbers; Connect another account); top bar ('Sep 2026', arrows, quick actions, overflow, Availability, Quick call); grid Tue-Mon with today pill, all-day strip with a 'Week 39' banner, events such as a daily 'Team stand-up', 'Lunch', 'Product review'.
2. **Event editor dialog**: title, time, calendar select, location, notes.
3. **Availability panel**: pick range, copy slots as text.
4. Responsive: collapse sidebar under 1024px; 3-day view under 768px; 1-day under 480px.
### Design system
- Colors: `--bg: #1c1c1e`, `--sidebar: #1f1f1f`, `--grid-line: #2c2c2e`, `--text: #ececef`, `--muted: #a1a1a8`, `--accent: #7857ff`, `--on-accent: #ffffff`, `--now: #ff4d5e`, `--event-blue-bg: #1d4a5c`, `--event-green-bg: #1e5a3c`, `--event-red-bg: #6a2a22`, `--focus: #a996ff`.
- Fonts: Inter (similar to observed). Month title 16px/600; event titles 15px/600; body 15px/1.5 in grid, 16px in dialogs; hour labels 12px.
- Spacing: 4px base; 36px hour rows; 12px sidebar padding.
- Radius: events 4px, buttons 6px, today pill full.
- Event style: tinted fill (`--event-*-bg`) plus 3px left bar in the calendar's saturated colour.
- Motion: 120ms; drag follows pointer; reduced motion disables smooth scrolling.
### Components & interactions
`MiniMonth` (week numbers, today, selected week), `CalendarSearch` (Command), `CalendarList` (coloured Checkbox, name, error badge), `WeekHeader` (TodayPill), `AllDayStrip`, `HourGrid` (NowLine), `EventBlock` (accent bar, title, time, icon for focus kind), `EventPopover`, `EventEditor`, `AvailabilityPanel`, `MeetButton`.
### Data & state
Tables per data model. Visible-range query `events_between(from, to)` filtered by visible calendars. Optimistic move/resize with rollback. Mock a week with daily stand-ups, a lunch, a two-hour review and an all-day banner.
### Accessibility
Events are buttons with names like 'Product review, Friday 14:00 to 15:30, Work calendar'. Keyboard shortcut list in a help dialog; shortcuts disabled when typing. All text on event fills meets 4.5:1. Now-line has a visible time label.
Verified contrast: body text on bg: #ececef on #1c1c1e = 14.43:1; muted hour label on bg: #a1a1a8 on #1c1c1e = 6.63:1; today pill label: #ffffff on #7857ff = 4.56:1; event title on blue fill: #ececef on #1d4a5c = 8.15:1; event title on green fill: #ececef on #1e5a3c = 6.9:1; event title on red fill: #ececef on #6a2a22 = 9.05:1; now line on bg: #ff4d5e on #1c1c1e = 5.25:1; focus ring on bg: #a996ff on #1c1c1e = 6.88:1.
### Security
RLS on accounts, calendars, events: `user_id = auth.uid()` through account ownership. External tokens encrypted at rest in a server-only table, never selectable by the client. Availability export contains only free slots. Validate times server-side.
### Performance & SEO
Render only the visible week; virtualise hour rows on mobile. Prefetch adjacent weeks. Memoise overlap layout. Noindex.
### Guardrails
- Invented events, addresses and calendars
- No saturated full-fill events with small text
- Undo for destructive moves and deletes
- Typed code, errors surfaced
- Acceptance criteria: (1) drag create/move/resize works and snaps; (2) calendar checkboxes toggle visibility; (3) keyboard shortcuts navigate weeks; (4) RLS isolates users; (5) 1-day view at 390px.