{ "$schema": "https://ui.shadcn.com/schema/registry.json", "name": "whiskeyjack", "homepage": "https://whiskeyjack.net", "items": [ { "name": "action-pill", "type": "registry:ui", "title": "ActionPill", "description": "Toolbar pill of icon actions that collapse and grow as the page's context changes.", "categories": [ "navigation", "actions" ], "dependencies": [ "class-variance-authority" ], "registryDependencies": [ "https://whiskeyjack.net/r/utils.json" ], "files": [ { "path": "components/ui/action-pill.tsx", "type": "registry:ui" } ] }, { "name": "app-panes", "type": "registry:ui", "title": "AppPanes", "description": "The three-phase content row below a floating header: optional left sidebar, main region, optional right rail, each gated on the layout variants.", "categories": [ "navigation", "layout" ], "registryDependencies": [ "https://whiskeyjack.net/r/scroll-indicator.json", "https://whiskeyjack.net/r/utils.json" ], "files": [ { "path": "components/ui/app-panes.tsx", "type": "registry:ui" } ] }, { "name": "app-shell", "type": "registry:ui", "title": "AppShell", "description": "The app layout skeleton: a fixed-height shell or a document scroller, with a frosted header, nav pills, and the main scroll region.", "categories": [ "navigation", "layout" ], "registryDependencies": [ "https://whiskeyjack.net/r/scroll-indicator.json", "https://whiskeyjack.net/r/utils.json" ], "files": [ { "path": "components/ui/app-shell.tsx", "type": "registry:ui" } ] }, { "name": "badge", "type": "registry:ui", "title": "Badge", "description": "Tone-tinted pill label on the semantic color scales, for status and classification at a glance.", "categories": [ "display" ], "dependencies": [ "class-variance-authority" ], "registryDependencies": [ "https://whiskeyjack.net/r/utils.json" ], "files": [ { "path": "components/ui/badge.tsx", "type": "registry:ui" } ] }, { "name": "bottom-drawer", "type": "registry:ui", "title": "BottomDrawer", "description": "Bottom sheet on mobile, centered dialog on desktop. Swipe, backdrop, Escape, and hardware Back all dismiss it.", "categories": [ "overlays" ], "registryDependencies": [ "https://whiskeyjack.net/r/scroll-indicator.json", "https://whiskeyjack.net/r/use-focus-trap.json", "https://whiskeyjack.net/r/utils.json" ], "files": [ { "path": "components/ui/bottom-drawer.tsx", "type": "registry:ui" } ] }, { "name": "bottom-nav", "type": "registry:ui", "title": "BottomNav", "description": "Pill-shaped frosted bottom navigation, hand-composed from BottomNavItem and BottomNavAction.", "categories": [ "navigation" ], "registryDependencies": [ "https://whiskeyjack.net/r/utils.json" ], "files": [ { "path": "components/ui/bottom-nav.tsx", "type": "registry:ui" } ] }, { "name": "button-row", "type": "registry:ui", "title": "ButtonRow", "description": "Side-by-side buttons that share a row and stack full-width when they no longer fit.", "categories": [ "actions", "layout" ], "registryDependencies": [ "https://whiskeyjack.net/r/utils.json" ], "files": [ { "path": "components/ui/button-row.tsx", "type": "registry:ui" } ] }, { "name": "button", "type": "registry:ui", "title": "Button", "description": "The action button. Labels wrap to two lines rather than overflowing, so long translated text stays inside the pill.", "categories": [ "actions" ], "dependencies": [ "class-variance-authority" ], "registryDependencies": [ "https://whiskeyjack.net/r/utils.json" ], "files": [ { "path": "components/ui/button.tsx", "type": "registry:ui" } ] }, { "name": "calendar-heatmap", "type": "registry:ui", "title": "CalendarHeatmap", "description": "GitHub-contributions-style activity heatmap, in squares or check-in dots.", "categories": [ "display" ], "registryDependencies": [ "https://whiskeyjack.net/r/utils.json" ], "files": [ { "path": "components/ui/calendar-heatmap.tsx", "type": "registry:ui" } ] }, { "name": "card", "type": "registry:ui", "title": "Card", "description": "The elevated surface primitive, with header, title, description, content, and footer slots.", "categories": [ "display", "layout" ], "dependencies": [ "class-variance-authority" ], "registryDependencies": [ "https://whiskeyjack.net/r/utils.json" ], "files": [ { "path": "components/ui/card.tsx", "type": "registry:ui" } ] }, { "name": "checkbox-group", "type": "registry:ui", "title": "CheckboxGroup", "description": "Pick-any tile grid: the multi-select counterpart to ToggleGroup.", "categories": [ "forms" ], "registryDependencies": [ "https://whiskeyjack.net/r/merge-refs.json", "https://whiskeyjack.net/r/option-tile.json", "https://whiskeyjack.net/r/utils.json" ], "files": [ { "path": "components/ui/checkbox-group.tsx", "type": "registry:ui" } ] }, { "name": "color-input", "type": "registry:ui", "title": "ColorInput", "description": "Focusable swatch button that opens the OS-native color picker and returns the chosen hex.", "categories": [ "forms" ], "registryDependencies": [ "https://whiskeyjack.net/r/utils.json" ], "files": [ { "path": "components/ui/color-input.tsx", "type": "registry:ui" } ] }, { "name": "confirm-button", "type": "registry:ui", "title": "ConfirmButton", "description": "Tap-again-to-confirm destructive button, with the armed state announced to assistive tech.", "categories": [ "actions" ], "registryDependencies": [ "https://whiskeyjack.net/r/announce.json", "https://whiskeyjack.net/r/button.json", "https://whiskeyjack.net/r/use-input-type.json" ], "files": [ { "path": "components/ui/confirm-button.tsx", "type": "registry:ui" } ] }, { "name": "drawer-action", "type": "registry:ui", "title": "DrawerAction", "description": "A single action in a BottomDrawer footer: plain, form-submit, or tap-again-confirm.", "categories": [ "actions", "overlays" ], "registryDependencies": [ "https://whiskeyjack.net/r/announce.json", "https://whiskeyjack.net/r/utils.json" ], "files": [ { "path": "components/ui/drawer-action.tsx", "type": "registry:ui" } ] }, { "name": "empty-state", "type": "registry:ui", "title": "EmptyState", "description": "Centered icon tile, title, subtitle, and optional call to action for an empty list or a fresh install.", "categories": [ "overlays", "display" ], "registryDependencies": [ "https://whiskeyjack.net/r/button.json", "https://whiskeyjack.net/r/utils.json" ], "files": [ { "path": "components/ui/empty-state.tsx", "type": "registry:ui" } ] }, { "name": "input", "type": "registry:ui", "title": "Input", "description": "Labeled text field that wires a real label to the input for you.", "categories": [ "forms" ], "registryDependencies": [ "https://whiskeyjack.net/r/utils.json" ], "files": [ { "path": "components/ui/input.tsx", "type": "registry:ui" } ] }, { "name": "mobile-bottom-nav", "type": "registry:ui", "title": "MobileBottomNav", "description": "Data-driven bottom nav that collapses its items into a hamburger menu when they and the toolbar would overflow the viewport.", "categories": [ "navigation" ], "registryDependencies": [ "https://whiskeyjack.net/r/use-focus-trap.json", "https://whiskeyjack.net/r/utils.json" ], "files": [ { "path": "components/ui/mobile-bottom-nav.tsx", "type": "registry:ui" } ] }, { "name": "notice", "type": "registry:ui", "title": "Notice", "description": "Inline tone-tinted status box for context-bound messages, with each tone setting its own ARIA live-region role.", "categories": [ "overlays", "feedback" ], "dependencies": [ "class-variance-authority" ], "registryDependencies": [ "https://whiskeyjack.net/r/utils.json" ], "files": [ { "path": "components/ui/notice.tsx", "type": "registry:ui" } ] }, { "name": "page-title-context", "type": "registry:ui", "title": "PageTitleProvider", "description": "React context that lets any page set the desktop header title.", "categories": [ "navigation" ], "files": [ { "path": "components/ui/page-title-context.tsx", "type": "registry:ui" } ] }, { "name": "progress-bar", "type": "registry:ui", "title": "ProgressBar", "description": "The accent progress primitive: determinate fill, open-ended indicator, or segment accumulation against a tally.", "categories": [ "display" ], "dependencies": [ "class-variance-authority" ], "registryDependencies": [ "https://whiskeyjack.net/r/use-reduced-motion.json", "https://whiskeyjack.net/r/utils.json" ], "files": [ { "path": "components/ui/progress-bar.tsx", "type": "registry:ui" } ] }, { "name": "pull-to-refresh-indicator", "type": "registry:ui", "title": "PullToRefreshIndicator", "description": "Frosted pill and spinner that slides down as you pull; the visual companion to usePullToRefresh.", "categories": [ "overlays", "feedback" ], "registryDependencies": [ "https://whiskeyjack.net/r/utils.json" ], "files": [ { "path": "components/ui/pull-to-refresh-indicator.tsx", "type": "registry:ui" } ] }, { "name": "reorder-list", "type": "registry:ui", "title": "ReorderList", "description": "Drag-to-reorder list with an accessible arrow-button fallback, so it works by pointer, touch, and keyboard.", "categories": [ "forms" ], "registryDependencies": [ "https://whiskeyjack.net/r/merge-refs.json", "https://whiskeyjack.net/r/use-drag-reorder.json", "https://whiskeyjack.net/r/use-reduced-motion.json", "https://whiskeyjack.net/r/use-scroll-fade.json", "https://whiskeyjack.net/r/utils.json" ], "files": [ { "path": "components/ui/reorder-list.tsx", "type": "registry:ui" } ] }, { "name": "scroll-indicator", "type": "registry:ui", "title": "ScrollIndicator", "description": "Read-only auto-hiding scroll thumb for scrollers whose native scrollbar would run behind floating chrome.", "categories": [ "display" ], "registryDependencies": [ "https://whiskeyjack.net/r/use-scroll-indicator.json", "https://whiskeyjack.net/r/utils.json" ], "files": [ { "path": "components/ui/scroll-indicator.tsx", "type": "registry:ui" } ] }, { "name": "segmented-control", "type": "registry:ui", "title": "SegmentedControl", "description": "Compact pick-one control: one bordered strip, divided into segments.", "categories": [ "forms" ], "registryDependencies": [ "https://whiskeyjack.net/r/compact-control.json", "https://whiskeyjack.net/r/merge-refs.json", "https://whiskeyjack.net/r/utils.json" ], "files": [ { "path": "components/ui/segmented-control.tsx", "type": "registry:ui" } ] }, { "name": "select", "type": "registry:ui", "title": "Select", "description": "Styled native select for a one-of-n choice with more options than a segmented control can show.", "categories": [ "forms" ], "registryDependencies": [ "https://whiskeyjack.net/r/utils.json" ], "files": [ { "path": "components/ui/select.tsx", "type": "registry:ui" } ] }, { "name": "sidebar-tabs", "type": "registry:ui", "title": "SidebarTabs", "description": "TabBar's wide-layout counterpart: a vertical tab rail for a desktop sidebar, with each item's progress pinned to its bottom edge.", "categories": [ "navigation" ], "registryDependencies": [ "https://whiskeyjack.net/r/merge-refs.json", "https://whiskeyjack.net/r/progress-bar.json", "https://whiskeyjack.net/r/tab-bar.json", "https://whiskeyjack.net/r/utils.json" ], "files": [ { "path": "components/ui/sidebar-tabs.tsx", "type": "registry:ui" } ] }, { "name": "slider", "type": "registry:ui", "title": "Slider", "description": "Range input with an optional mono value readout beside its label.", "categories": [ "forms" ], "registryDependencies": [ "https://whiskeyjack.net/r/utils.json" ], "files": [ { "path": "components/ui/slider.tsx", "type": "registry:ui" } ] }, { "name": "tab-bar", "type": "registry:ui", "title": "TabBar", "description": "Metro-style pivot tabs with a sliding accent underline that doubles as each tab's progress bar.", "categories": [ "navigation" ], "registryDependencies": [ "https://whiskeyjack.net/r/direction.json", "https://whiskeyjack.net/r/progress-bar.json", "https://whiskeyjack.net/r/use-reduced-motion.json", "https://whiskeyjack.net/r/use-tab-bar-fade.json", "https://whiskeyjack.net/r/utils.json" ], "files": [ { "path": "components/ui/tab-bar.tsx", "type": "registry:ui" } ] }, { "name": "toast", "type": "registry:ui", "title": "Toast", "description": "Floating notification pill fixed below the header, for app-level messages.", "categories": [ "overlays" ], "registryDependencies": [ "https://whiskeyjack.net/r/utils.json" ], "files": [ { "path": "components/ui/toast.tsx", "type": "registry:ui" } ] }, { "name": "toggle-group", "type": "registry:ui", "title": "ToggleGroup", "description": "Segmented tile control for one-of-n choices, such as a light / dark / system theme picker.", "categories": [ "forms" ], "registryDependencies": [ "https://whiskeyjack.net/r/merge-refs.json", "https://whiskeyjack.net/r/option-tile.json", "https://whiskeyjack.net/r/utils.json" ], "files": [ { "path": "components/ui/toggle-group.tsx", "type": "registry:ui" } ] }, { "name": "toggle", "type": "registry:ui", "title": "Toggle", "description": "Switch control with a label and optional description, for a single on/off setting.", "categories": [ "forms" ], "registryDependencies": [ "https://whiskeyjack.net/r/utils.json" ], "files": [ { "path": "components/ui/toggle.tsx", "type": "registry:ui" } ] }, { "name": "accent-foreground", "type": "registry:lib", "title": "applyAccentColor", "description": "Retint the whole UI from one accent color, with a WCAG-legible foreground picked automatically.", "categories": [ "utils" ], "files": [ { "path": "lib/accent-foreground.ts", "type": "registry:lib" } ] }, { "name": "announce", "type": "registry:lib", "title": "announce", "description": "Announce a message to assistive technology through a shared live region.", "categories": [ "utils", "accessibility" ], "files": [ { "path": "lib/announce.ts", "type": "registry:lib" } ] }, { "name": "compact-control", "type": "registry:lib", "title": "compactControlClass", "description": "The geometry of a compact control: a small pill, chip or segment that sits on a line with body text.", "categories": [ "utilities" ], "registryDependencies": [ "https://whiskeyjack.net/r/utils.json" ], "files": [ { "path": "lib/compact-control.ts", "type": "registry:lib" } ] }, { "name": "direction", "type": "registry:lib", "title": "isRTL", "description": "Detect right-to-left direction for JS-driven interactions that CSS cannot reach.", "categories": [ "utils", "i18n" ], "files": [ { "path": "lib/direction.ts", "type": "registry:lib" } ] }, { "name": "merge-refs", "type": "registry:lib", "title": "useMergedRefs", "description": "Combine an internal ref with a forwarded one.", "categories": [ "utils" ], "files": [ { "path": "lib/merge-refs.ts", "type": "registry:lib" } ] }, { "name": "option-tile", "type": "registry:lib", "title": "optionTileClass", "description": "The selectable-tile class recipe shared by ToggleGroup and CheckboxGroup.", "categories": [ "utilities" ], "registryDependencies": [ "https://whiskeyjack.net/r/utils.json" ], "files": [ { "path": "lib/option-tile.ts", "type": "registry:lib" } ] }, { "name": "use-drag-reorder", "type": "registry:hook", "title": "useDragReorder", "description": "Drag-to-reorder list logic with an accessible keyboard path, behind ReorderList.", "categories": [ "hooks" ], "files": [ { "path": "hooks/use-drag-reorder.ts", "type": "registry:hook" } ] }, { "name": "use-focus-trap", "type": "registry:hook", "title": "useFocusTrap", "description": "Trap focus inside an overlay while it is open, and restore it to the trigger on close.", "categories": [ "hooks", "accessibility" ], "files": [ { "path": "hooks/use-focus-trap.ts", "type": "registry:hook" } ] }, { "name": "use-input-type", "type": "registry:hook", "title": "useInputType", "description": "Detect touch versus mouse input, for controls that phrase or size themselves differently.", "categories": [ "hooks" ], "files": [ { "path": "hooks/use-input-type.ts", "type": "registry:hook" } ] }, { "name": "use-layout-gate", "type": "registry:hook", "title": "useLayoutGate", "description": "Read the wide / xlwide layout gates in JS, for a decision CSS cannot express.", "categories": [ "hooks", "layout" ], "files": [ { "path": "hooks/use-layout-gate.ts", "type": "registry:hook" } ] }, { "name": "use-pull-to-refresh", "type": "registry:hook", "title": "usePullToRefresh", "description": "Touch pull-to-refresh that coexists with tab swipes and overscroll-behavior: none.", "categories": [ "hooks" ], "registryDependencies": [ "https://whiskeyjack.net/r/announce.json" ], "files": [ { "path": "hooks/use-pull-to-refresh.ts", "type": "registry:hook" } ] }, { "name": "use-reduced-motion", "type": "registry:hook", "title": "useReducedMotion", "description": "Respect the user's reduced-motion preference in JS-driven motion.", "categories": [ "hooks", "accessibility" ], "files": [ { "path": "hooks/use-reduced-motion.ts", "type": "registry:hook" } ] }, { "name": "use-route-focus", "type": "registry:hook", "title": "useRouteFocus", "description": "Move focus to the main content on route change, so keyboard and screen-reader users land in the new page.", "categories": [ "hooks", "accessibility" ], "files": [ { "path": "hooks/use-route-focus.ts", "type": "registry:hook" } ] }, { "name": "use-scroll-fade", "type": "registry:hook", "title": "useScrollFade", "description": "Vertical edge-fade masks for a height-capped scrollable panel; returns the CSS class to apply.", "categories": [ "hooks" ], "files": [ { "path": "hooks/use-scroll-fade.ts", "type": "registry:hook" } ] }, { "name": "use-scroll-indicator", "type": "registry:hook", "title": "useScrollIndicator", "description": "Scroll metrics (thumb size, position, visibility) that drive ScrollIndicator.", "categories": [ "hooks" ], "files": [ { "path": "hooks/use-scroll-indicator.ts", "type": "registry:hook" } ] }, { "name": "use-swipe-navigation", "type": "registry:hook", "title": "useSwipeNavigation", "description": "Swipe between tabs with an axis-locked touch gesture that flips direction under RTL.", "categories": [ "hooks" ], "registryDependencies": [ "https://whiskeyjack.net/r/direction.json", "https://whiskeyjack.net/r/use-reduced-motion.json" ], "files": [ { "path": "hooks/use-swipe-navigation.ts", "type": "registry:hook" } ] }, { "name": "use-tab-bar-fade", "type": "registry:hook", "title": "useTabBarFade", "description": "Edge-fade masks for a horizontally overflowing tab strip; returns the CSS class to apply.", "categories": [ "hooks" ], "registryDependencies": [ "https://whiskeyjack.net/r/direction.json" ], "files": [ { "path": "hooks/use-tab-bar-fade.ts", "type": "registry:hook" } ] }, { "name": "use-theme", "type": "registry:hook", "title": "useTheme", "description": "The theme engine: light, dark, system, and OLED, with persistence and theme-color meta kept in sync.", "categories": [ "hooks" ], "files": [ { "path": "hooks/use-theme.ts", "type": "registry:hook" } ] }, { "name": "utils", "type": "registry:lib", "title": "cn", "description": "Tailwind class merging (clsx plus tailwind-merge).", "categories": [ "utils" ], "dependencies": [ "clsx", "tailwind-merge" ], "files": [ { "path": "lib/utils.ts", "type": "registry:lib" } ] } ] }