Both become plain role="checkbox"/role="switch" buttons driven by
useVModel, matching the existing Input.vue controlled-value pattern.
Classes and data-state/aria-checked contract are unchanged.
15 tasks: 5 shared composables (Primitive/Slot, focus-trap,
dismissable-layer, roving-focus, popover-position) with unit tests,
then component-by-component rewrites (Button, Checkbox, Switch,
RadioGroup, Dialog, Select) verified against the existing regression
suite in packages/library/tests/, then dropping the dependency itself.
Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
Plans a hand-rolled replacement for reka-ui across Button, Checkbox,
Switch, RadioGroup, Dialog, and Select to drop the dependency (and its
peerDependency burden on consumers) while preserving the current public
API and visual design exactly.
Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
Two independent fixes:
1. Alert titles used text-<severity> directly on a bg-<severity>/15 tinted
background. For danger (a very dark base hue) this reads as near-invisible
text-on-tinted-background. The original PrimeVue-era Message design kept
body/title text neutral and only accented the icon/left-border with the
severity color -- restore that: alert text stays text-foreground, severity
shows via a border-l-4 accent stripe instead of tinted text.
2. Root-caused why none of the last several fixes were showing up without a
full `bun run build`: @nychthemeron/library's package.json exports its "."
entry as ./dist/index.js unconditionally, and every story imports from the
bare package specifier. So Storybook's dev server was always resolving to
whatever the dist bundle looked like at last build time, never live
source -- editing packages/library/src and restarting `bun run dev` (even
with caches cleared) never picked up changes. Vite auto-injects a
"development" resolution condition during `vite dev`/serve (and
"production" during build), which is the standard fix for exactly this
monorepo dev-vs-published split: added a "development" condition to the
"." export pointing at src/index.ts, matching the pattern the "./components"
sub-export already used. Also added the matching "@" alias to
packages/playground/vite.config.ts, since resolving straight to library
source pulls in its "@/lib/utils"-style internal imports, which playground's
own Vite instance didn't previously know how to resolve.
Verified both paths: dev server now reflects source edits without a
library rebuild, and `bun run build` still produces a correct dist bundle
with the same fix baked in.
Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
The @keyframes nych-spin rule and NychLoadingIcon's wreath fill/stroke
colors lived in the old nychthemeron.css, which got deleted in the Task 13
cleanup as "fully superseded" -- but this component-specific animation was
never actually ported over to the new tailwind.css, so the icon rendered
static instead of spinning. Restored, verified live via computed
animationPlayState/animationName on the wreath element (previously
untestable via the compiled-CSS-only checks used for the earlier fixes).
Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
Cinzel/IBM Plex Sans/IBM Plex Mono were loaded via a Google Fonts CDN
@import, unchanged from the original PrimeVue-era CSS. Any environment
without outbound network access (or that can't reach fonts.googleapis.com)
silently fell back to a generic system sans-serif, which is what surfaced
as "text still off" after the border/heading-font fixes. Switch to
@fontsource's self-hosted packages so the font files ship as real build
assets (26 woff2 files bundled) instead of a runtime network dependency.
Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
The CLI's default style uses a very subtle ring-foreground/10 (10%-opacity
ring) instead of a real border for Card, DialogContent, and SelectContent,
which reads as invisible against our dark Hades theme. Swap to a real
border-border + shadow, matching the original PrimeVue-era design's
visible borders.
Also: CardTitle/DialogTitle/AlertTitle referenced a `cn-font-heading`
class that is never defined anywhere (dead weight from the CLI's default
style template), so titles silently fell back to the body font instead of
our --font-serif (Cinzel) heading font. Replaced with the real `font-serif`
utility. Also drops another dead class, `cn-menu-translucent`, from
SelectContent.
Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
- Delete packages/library/src/engine/ and engine.spec.ts; LoadingIcon is
now exported directly instead of routed through a generic theming engine.
- Remove primevue from every package.json (root devDependencies, library
peerDependencies, playground dependencies) and from vite.config.ts's
externalized/global Rollup config; add reka-ui as the library's peer dep.
- Delete the hand-written nychthemeron.css/theme.css, now fully superseded
by the Tailwind entry CSS; both library exports (./style, ./theme) point
at it.
- Drop the PrimeVue plugin install from Storybook's preview.ts.
- Add a `@source "../../";` directive to tailwind.css: Tailwind's automatic
content detection is scoped to whichever Vite project runs it, so when
the playground consumes this CSS file it never scanned the sibling
packages/library/src tree for class usage -- every component rendered
with zero utility classes applied until this was added (verified via the
compiled Storybook CSS output going from ~2KB/no .bg-primary rule to
~40KB with the full utility set, and the pre-fix screenshot that
surfaced it: buttons and other components with a real background color
showing as bare, near-invisible text on white).
Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
Also: fixes DialogContent/DialogFooter's close/action buttons to use our
actual Button variant set (secondary) instead of the CLI's default
ghost/outline variants, which don't exist on our re-themed Button.
Adds an eslint override so shadcn-vue's single-word ui/ component names
(Button.vue, Dialog.vue, ...) aren't flagged by vue/multi-word-component-names.
This was the last PrimeVue-wrapped component, so lib/index.ts no longer
imports anything from primevue or uses the ptThemeable helper.
Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
CheckboxGroup is hand-built (no shadcn-vue stock equivalent) as a simple
name/layout provider via provide/inject, matching RadioGroup's pattern --
it does not coordinate an array modelValue across children the way
PrimeVue's did, since each Checkbox now owns its own boolean v-model.
Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>