chore: snapshot main sync
This commit is contained in:
89
data/skills/booskills/boo-building-ui/SKILL.md
Normal file
89
data/skills/booskills/boo-building-ui/SKILL.md
Normal file
@@ -0,0 +1,89 @@
|
||||
---
|
||||
name: boo-building-ui
|
||||
description: >
|
||||
Builds new frontend UI (pages, screens, components, flows) to high-end design
|
||||
standards: deliberate color strategy, typography, layout, motion, full
|
||||
interaction-state coverage, accessibility, and an AI-slop self-check before
|
||||
handoff. Use for "build a landing page," "add a settings screen," "create
|
||||
this component," "make the frontend for X." Do NOT use to critique or grade
|
||||
existing UI; use boo-critiquing-frontend. Do NOT use for OpenSpec
|
||||
change-folder work; use boo-implementing-changes.
|
||||
metadata:
|
||||
version: "1.0"
|
||||
---
|
||||
|
||||
# Building UI
|
||||
|
||||
## Size
|
||||
|
||||
Classify small/medium/large from surface count: small = one component or section, medium = a full screen or 2-4 related components, large = a multi-screen flow or a new design-system surface. Default: small. Announce with one-line justification. Accept `$size` override.
|
||||
|
||||
## Process
|
||||
|
||||
1. Read `references/design-guidance.md` for the canonical design rules (color, typography, layout, motion, interaction, absolute bans, AI slop test). Every build decision defers to it.
|
||||
2. Recon the existing surface: run `ls frontend/src/components/ui/` (or the project's equivalent primitives path) and read the token/theme source (tailwind config, CSS custom properties, theme file). Only import primitives that exist; if the primitives directory is missing, stop and report.
|
||||
3. Extending an existing surface? Extract its conventions first (spacing scale, type ramp, radius, motion idiom) and match them. New surface with no prior design? Write the one-sentence physical scene (who uses this, where, under what ambient light, in what mood) and pick a color strategy (restrained / committed / full palette / drenched) before writing any markup.
|
||||
4. Build incrementally: structure and hierarchy first, then spacing and type, then color, then motion last. One component or section per pass.
|
||||
5. Cover every interactive state: hover, focus-visible, active, disabled, loading, empty, error. A component without designed states is not done.
|
||||
6. Accessibility pass: keyboard reachability and focus order, contrast >=4.5:1 body / >=3:1 large text, labels on inputs, `prefers-reduced-motion` alternative for every animation.
|
||||
7. Self-check against the absolute bans and the two-altitude AI slop test in references/design-guidance.md. Anything matching a ban gets rebuilt with different structure, not tweaked in place.
|
||||
8. Verify rendering when tooling exists (dev server plus browser tool or screenshot). If verification is not possible, say so explicitly in the report.
|
||||
9. At medium+, dispatch `user-experience-designer` for a post-build audit and fix what it finds before handoff.
|
||||
|
||||
## What NOT to do
|
||||
|
||||
- Do not critique or grade existing UI; that is boo-critiquing-frontend's job.
|
||||
- Do not implement OpenSpec change folders here; use boo-implementing-changes.
|
||||
- Do not invent primitives or import components that do not exist in the project.
|
||||
- Do not hardcode colors, spacing, or z-index values where tokens or scales exist.
|
||||
- Do not ship a build that fails the AI slop test on a promise of polishing later.
|
||||
|
||||
## Gotchas
|
||||
|
||||
- **BooLab primitive rule**: run `ls frontend/src/components/ui/` and only import primitives that exist. If missing, stop and report.
|
||||
- **States are scope, not polish**: empty, loading, and error states are part of the build, never follow-up work.
|
||||
- **Slop test runs at two altitudes**: check first-order (theme guessable from category alone) and second-order (aesthetic guessable from category plus anti-references) per references/design-guidance.md.
|
||||
<!-- standing-rules:pi:start -->
|
||||
- **Subagent visibility**: when the Paseo MCP tools (`mcp__paseo__*`) are available, spawn each agent persona as an attached Paseo subagent with `create_agent` (`detached: false`, `notifyOnFinish: true`; for an opencode provider also pass `settings.modeId: "build"` and `settings.features.auto_accept: true`) so every persona appears in the operator's Paseo agent track. Resolve each persona's provider/model from the active preset's `agents` map in `~/.paseo/orchestration-preferences.json`; supervise on the finish notification (never poll) and read each result with `get_agent_activity`.
|
||||
- **Subagent fallback**: when the Paseo MCP tools are not available, use the platform's native subagent dispatch. On a platform with no subagent dispatch at all (for example Pi), read each `agents/<name>.md` persona and apply its lens in sequential passes.
|
||||
- **Subagent concurrency**: honor the active preset's `concurrency` value in `~/.paseo/orchestration-preferences.json`. When it is `1` (local heavy-weight presets, around 27b/35b or larger on a single llama-swap server), dispatch subagents STRICTLY ONE AT A TIME: launch one, wait for its finish notification and read its result, then launch the next. This overrides any parallel fan-out. Absent or higher `concurrency` means parallel fan-out is fine.
|
||||
<!-- standing-rules:pi:end -->
|
||||
<!-- standing-rules:core:start -->
|
||||
- **No commit**: never commit, push, or stage changes; never `git add -A`. Prove any edits with `git diff --stat`.
|
||||
- **No em dashes**: never use em dashes (U+2014) in output or files you write.
|
||||
<!-- standing-rules:core:end -->
|
||||
|
||||
## Output format
|
||||
|
||||
```
|
||||
# UI Build: <target>
|
||||
|
||||
## What was built
|
||||
<components/screens with file paths>
|
||||
|
||||
## Design decisions
|
||||
- Scene sentence: <one sentence> (new surfaces only)
|
||||
- Color strategy: <restrained | committed | full palette | drenched>
|
||||
- <other load-bearing choices, one line each>
|
||||
|
||||
## State coverage
|
||||
|
||||
| Component | hover | focus | disabled | loading | empty | error |
|
||||
|-----------|-------|-------|----------|---------|-------|-------|
|
||||
|
||||
## Verification
|
||||
<how rendering was verified, or why it could not be>
|
||||
|
||||
## Slop self-check
|
||||
<bans checked and result; both slop-test altitudes>
|
||||
|
||||
## Claims I did not verify
|
||||
- <anything assumed or not checked>
|
||||
```
|
||||
|
||||
## Failure modes
|
||||
|
||||
- **No frontend toolchain**: the repo has no frontend source or build setup. Report and stop; never scaffold a framework unasked.
|
||||
- **Primitives directory missing**: report the actual path checked and stop.
|
||||
- **Design guidance cannot be loaded**: references/design-guidance.md is missing. Report and stop.
|
||||
- **Rendering cannot be verified**: no dev server or browser tooling available. Deliver the build and flag verification as not done.
|
||||
@@ -0,0 +1,77 @@
|
||||
# Design Guidance
|
||||
|
||||
Ported from forks/impeccable/skill/SKILL.src.md. Substantive design rules preserved verbatim; provider-specific tags and placeholder syntax removed.
|
||||
|
||||
## General rules
|
||||
|
||||
### Color
|
||||
|
||||
- **Verify contrast.** Body text must hit >=4.5:1 against its background; large text (>=18px or bold >=14px) needs >=3:1. Placeholder text needs the same 4.5:1, not the muted-gray default. The most common failure: muted gray body text on a tinted near-white. If the contrast is even close, bump the body color toward the ink end of the ramp; light gray "for elegance" is the single biggest reason AI designs feel hard to read.
|
||||
- Gray text on a colored background looks washed out. Use a darker shade of the background's own hue, or a transparency of the text color.
|
||||
|
||||
### Typography
|
||||
|
||||
- Cap body line length at 65-75ch.
|
||||
- Don't pair fonts that are similar but not identical (two geometric sans-serifs, two humanist sans-serifs). Pair on a contrast axis (serif + sans, geometric + humanist) or use one family in multiple weights.
|
||||
- Hero / display heading ceiling: clamp() max <= 6rem (~96px). Above that the page is shouting, not designing.
|
||||
- Display heading letter-spacing floor: >= -0.04em. Anything tighter and letters touch; cramped, not "designed".
|
||||
- Use `text-wrap: balance` on h1-h3 for even line lengths; `text-wrap: pretty` on long prose to reduce orphans.
|
||||
|
||||
### Layout
|
||||
|
||||
- Vary spacing for rhythm.
|
||||
- Cards are the lazy answer. Use them only when they're truly the best affordance. Nested cards are always wrong.
|
||||
- Flexbox for 1D, Grid for 2D. Don't default to Grid when `flex-wrap` would be simpler.
|
||||
- For responsive grids without breakpoints: `repeat(auto-fit, minmax(280px, 1fr))`.
|
||||
- Build a semantic z-index scale (dropdown, sticky, modal-backdrop, modal, toast, tooltip). Never arbitrary values like 999 or 9999.
|
||||
|
||||
### Motion
|
||||
|
||||
- Motion should be intentional, and not be an afterthought. Consider it as part of the build.
|
||||
- Don't animate CSS layout properties unless truly needed.
|
||||
- Ease out with exponential curves (ease-out-quart / quint / expo). No bounce, no elastic.
|
||||
- Use libraries for more advanced motion needs (e.g. motion, GSAP, anime.js, Lenis etc).
|
||||
- Reduced motion is not optional. Every animation needs a `@media (prefers-reduced-motion: reduce)` alternative: typically a crossfade or instant transition.
|
||||
- Staggering the items within one list is legitimate. The tell is the uniform reflex (one identical entrance applied to every section), not motion itself; each reveal should fit what it reveals. Suppressing the reflex is never a reason to ship a page with no motion at all.
|
||||
- Reveal animations must enhance an already-visible default. Don't gate content visibility on a class-triggered transition; transitions pause on hidden tabs and headless renderers, so the reveal never fires and the section ships blank.
|
||||
- Premium motion materials are not just transform/opacity. Blur, backdrop-filter, clip-path, mask, and shadow/glow are part of the palette when they materially improve the effect and stay smooth.
|
||||
|
||||
### Interaction
|
||||
|
||||
- Dropdowns rendered with `position: absolute` inside an `overflow: hidden` or `overflow: auto` container will be clipped. Use the native `<dialog>` / popover API, `position: fixed`, or a portal to escape the stacking context.
|
||||
|
||||
## New projects only (when no prior work exists)
|
||||
|
||||
### Color & Theme
|
||||
|
||||
- Use OKLCH.
|
||||
- **The cream / sand / beige body bg is the saturated AI default of 2026.** The whole warm-neutral band (OKLCH L 0.84-0.97, C < 0.06, hue 40-100) reads as cream/sand/paper/parchment regardless of what you call it. Token names like `--paper`, `--cream`, `--sand`, `--bone`, `--flour`, `--linen`, `--parchment`, `--wheat`, `--biscuit`, `--ivory` are tells in themselves. If the brief is "warm, traditional, family-coastal-Italian" or "magazine-warm" or "editorial-restraint", DO NOT translate that into a near-white warm-tinted bg; that's the AI move. Pick: (a) a saturated brand color as the body (terracotta, oxblood, deep ochre, near-black), (b) a true off-white at chroma 0 (or chroma toward the brand's own hue, not toward warmth-by-default), or (c) a darker mid-tone tinted neutral that's clearly the brand's own. "Warmth" in the brand is carried by accent + typography + imagery, not by body bg.
|
||||
- Tinted neutrals: add 0.005-0.015 chroma toward the brand's hue. Don't default-tint toward warm or cool "because the brand feels that way"; that's the cross-project monoculture move.
|
||||
- When picking a theme: Dark vs. light is never a default. Not dark "because tools look cool dark." Not light "to be safe." Before choosing, write one sentence of physical scene: who uses this, where, under what ambient light, in what mood. If the sentence doesn't force the answer, it's not concrete enough. Add detail until it does.
|
||||
- Pick a **color strategy** before picking colors. Four steps on the commitment axis:
|
||||
- **Restrained**: tinted neutrals + one accent <=10%. Product default; brand minimalism.
|
||||
- **Committed**: one saturated color carries 30-60% of the surface. Brand default for identity-driven pages.
|
||||
- **Full palette**: 3-4 named roles, each used deliberately. Brand campaigns; product data viz.
|
||||
- **Drenched**: the surface IS the color. Brand heroes, campaign pages.
|
||||
|
||||
## Absolute bans
|
||||
|
||||
Match-and-refuse. If you're about to write any of these, rewrite the element with different structure.
|
||||
|
||||
- **Side-stripe borders.** `border-left` or `border-right` greater than 1px as a colored accent on cards, list items, callouts, or alerts. Never intentional. Rewrite with full borders, background tints, leading numbers/icons, or nothing.
|
||||
- **Gradient text.** `background-clip: text` combined with a gradient background. Decorative, never meaningful. Use a single solid color. Emphasis via weight or size.
|
||||
- **Glassmorphism as default.** Blurs and glass cards used decoratively. Rare and purposeful, or nothing.
|
||||
- **The hero-metric template.** Big number, small label, supporting stats, gradient accent. SaaS cliche.
|
||||
- **Identical card grids.** Same-sized cards with icon + heading + text, repeated endlessly.
|
||||
- **Tiny uppercase tracked eyebrow above every section.** The 2023-era kicker (small all-caps text with wide tracking, "ABOUT" "PROCESS" "PRICING" above each heading) is now the saturated AI scaffold. One named kicker as a deliberate brand system is voice; an eyebrow on every section is AI grammar. Choose a different cadence.
|
||||
- **Numbered section markers as default scaffolding (01 / 02 / 03).** Numbers earn their place when the section actually IS a sequence (a real 3-step process, an ordered flow, a typed timeline) and the order carries information the reader needs. One deliberate numbered sequence on one page is voice; numbered eyebrows on every section across the site is AI grammar.
|
||||
- **Text that overflows its container.** Long heading words plus large clamp scales plus narrow grids cause headline overflow on tablet/mobile. Test the heading copy at every breakpoint; if it overflows, reduce the clamp max or rewrite the copy.
|
||||
|
||||
## The AI slop test
|
||||
|
||||
If someone could look at this interface and say "AI made that" without doubt, it's failed. Cross-register failures are the absolute bans above. Register-specific failures live in each reference.
|
||||
|
||||
**Category-reflex check.** Run at two altitudes; the second one catches what the first one misses.
|
||||
|
||||
- **First-order:** if someone could guess the theme + palette from the category alone, it's the first training-data reflex. Rework the scene sentence and color strategy until the answer isn't obvious from the domain.
|
||||
- **Second-order:** if someone could guess the aesthetic family from category-plus-anti-references ("AI workflow tool that's not SaaS-cream, editorial-typographic", "fintech that's not navy-and-gold, terminal-native dark mode"), it's the trap one tier deeper. The first reflex was avoided; the second wasn't. Rework until both answers are not obvious.
|
||||
Reference in New Issue
Block a user