Files
famapp/docs/tasks/76-shadcn-tiers.md
T
ginnoir a312d4ce39
CI / checks (push) Successful in 12m55s
CI / build (push) Successful in 15m16s
fix: tighten sharing and shadcn composition
2026-06-13 05:20:01 -05:00

115 lines
5.6 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
# 76 — Shadcn component implementation (Tiers 13)
## Goal
Implement the three shadcn component adoption tiers that replace ad-hoc UI patterns across the app with shadcn/ui primitives. This is the **execution** phase — components are already installed (see `2026-06-13-shadcn-component-install.md`).
| Tier | Name | Tasks | Files touched |
| ---- | ------------------------------------------------------------------------- | ----------- | ------------------------------------------------------------------------------------------------------ |
| 1 | Garden badges → Badge, topbar avatar → Avatar, + fallback, semantic token | 5 sub-tasks | topbar.tsx, sidebar.tsx, plant-detail.tsx, push-opt-in.tsx, care-schedule-editor.tsx, plant-widget.tsx |
| 2 | Skeleton loading, Tabs nav, Sonner toasts, FieldGroup audit, Separator | 5 sub-tasks | d/[slug]/page.tsx, plant-detail.tsx, container-detail.tsx, layout.tsx, notify-channel-toggles.tsx |
| 3 | Garden empty-state, Switch for notify channels | 2 sub-tasks | plant-list.tsx, container-list.tsx, notify-channel-toggles.tsx |
## Depends on
- `2026-06-13-shadcn-component-install.md` — components are already in `src/components/ui/`
- The shadcn migration map at `2026-06-13-shadcn-migration.md`
## Scope by tier
### Tier 1 (detailed brief: `docs/tasks/1a-badges-avatars.md`)
**Task 1a — Garden health badges → `<Badge>`**
- File: `src/modules/garden/components/plant-detail.tsx` lines 44-48, 119-123
- Replace hand-crafted `badge-success/danger/warning` classes with shadcn `<Badge variant="default|destructive|secondary">`
- Delete the `healthBadgeClass()` helper function
**Task 1b — Topbar avatar → `<Avatar>`**
- File: `src/components/topbar.tsx` lines 60-75
- Replace manual `<span className="avatar">` with `<Avatar><AvatarImage/><AvatarFallback/></Avatar>`
**Task 1c — HouseholdPill avatars → `<Avatar>`**
- File: `src/components/sidebar.tsx` lines 106-120
- Replace inner span elements with Avatar components (keep avatarColor hash for fallback background)
**Task 1d — Generic AvatarFallbackWithName component**
- New file: `src/components/avatar-fallback.tsx`
- Thin wrapper that handles the Image/Fallback pattern with name/initial logic
- Imported by both topbar.tsx and sidebar.tsx to remove duplication
**Task 1e — share-green → semantic token**
- Files: push-opt-in.tsx (line ~104), care-schedule-editor.tsx (line ~185), plant-widget.tsx urgencyLabel, plus any other green-600/green-500 in garden components
- Add `--c-success` CSS variable to the global theme
- Replace all hardcoded green-600 references with `var(--c-success)`
### Tier 2 (detailed brief: `docs/tasks/1b-skeleton-tabs-toasts.md`)
**Task 2a — Skeleton loading states**
- d/[slug]/page.tsx inline animate-pulse → `<Skeleton>` components
- plant-detail.tsx & container-detail.tsx uploadingImage → skeleton overlay
- Any other animate-pulse patterns outside skeleton.tsx itself
**Task 2b — Settings/garden Tabs navigation → `<Tabs>`**
- File: `src/modules/garden/components/plant-detail.tsx` lines 162-180
- File: `src/modules/garden/components/container-detail.tsx` lines 138-155
- Replace manual button-based tabs with shadcn Tabs/TabsList/TabsTrigger/TabsContent
**Task 2c — Toast notifications via sonner**
- Add `<Toaster>` to app layout (`src/app/layout.tsx`)
- Convert delete confirmations, calendar schedule success/error, and share-link actions to `toast.success()`/`toast.error()` calls
**Task 2d — Form FieldGroup audit**
- Audit: container-form.tsx, plant-form.tsx, household edit forms
- Check consistency of Label + Input + error pattern
- Fix any non-shadcn form fields found
**Task 2e — Manual separators → `<Separator>`**
- Remove border-bottom on garden detail tab bars, replace with shadcn Separator (usually alongside the Tabs component)
### Tier 3 (detailed brief: `docs/tasks/1c-emptystate-switch.md`)
**Task 3a — Garden empty-state component**
- File: `src/modules/garden/components/plant-list.tsx` line 22 → use EmptyState from ui/empty.tsx
- File: `src/modules/garden/components/container-list.tsx` line 39 → use EmptyState
- Use appropriate icons (Sprout for plants, Container for containers)
**Task 3b — Notify channel toggles → `<Switch>`**
- File: `src/components/notify-channel-toggles.tsx`
- Replace native `<input type="checkbox">` with shadcn `<Switch>` component
- Keep server action integration (setNotifChannel)
- Disabled state for ntfy when unconfigured
## Acceptance criteria (all tiers)
1. Zero `badge-success`, `badge-danger`, `badge-warning` class names remain in garden code
2. All avatars rendered via shadcn Avatar components (verified by DOM/JSX inspection)
3. All loading states use `<Skeleton>` — no animate-pulse patterns outside skeleton.tsx
4. Garden detail pages use shadcn Tabs component (not manual buttons)
5. Toaster rendered in app layout, delete/cancel actions show toasts
6. EmptyState used in all garden list pages (no ad-hoc empty text paragraphs)
7. Notification channels use shadcn Switch components
8. `pnpm lint` passes with zero errors/warnings
9. `pnpm typecheck` passes with zero errors
## Execution order
Execute tiers sequentially: 1 → 2 → 3. Each tier builds on the previous one's patterns and fixes foundational issues before adding polish.
Detailed task briefs are in:
- Tier 1: `docs/tasks/1a-badges-avatars.md`
- Tier 2: `docs/tasks/1b-skeleton-tabs-toasts.md`
- Tier 3: `docs/tasks/1c-emptystate-switch.md`