@spavn/ui 0.0.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (399) hide show
  1. package/cli/commands/add.d.ts +5 -0
  2. package/cli/commands/add.d.ts.map +1 -0
  3. package/cli/commands/add.js +104 -0
  4. package/cli/commands/add.js.map +1 -0
  5. package/cli/commands/init.d.ts +5 -0
  6. package/cli/commands/init.d.ts.map +1 -0
  7. package/cli/commands/init.js +129 -0
  8. package/cli/commands/init.js.map +1 -0
  9. package/cli/index.d.ts +3 -0
  10. package/cli/index.d.ts.map +1 -0
  11. package/cli/index.js +27 -0
  12. package/cli/index.js.map +1 -0
  13. package/cli/registry.d.ts +12 -0
  14. package/cli/registry.d.ts.map +1 -0
  15. package/cli/registry.js +1112 -0
  16. package/cli/registry.js.map +1 -0
  17. package/dist/index.js +7492 -0
  18. package/dist/index.umd.cjs +122 -0
  19. package/dist/style.css +1 -0
  20. package/mcp-server/index.d.ts +3 -0
  21. package/mcp-server/index.d.ts.map +1 -0
  22. package/mcp-server/index.js +1266 -0
  23. package/mcp-server/index.js.map +1 -0
  24. package/package.json +91 -0
  25. package/src/index.ts +432 -0
  26. package/src/lib/accordion/Accordion.test.ts +109 -0
  27. package/src/lib/accordion/Accordion.vue +11 -0
  28. package/src/lib/accordion/AccordionContent.vue +23 -0
  29. package/src/lib/accordion/AccordionItem.vue +16 -0
  30. package/src/lib/accordion/AccordionTrigger.vue +37 -0
  31. package/src/lib/accordion/index.ts +4 -0
  32. package/src/lib/alert/Alert.test.ts +144 -0
  33. package/src/lib/alert/Alert.vue +17 -0
  34. package/src/lib/alert/AlertDescription.vue +15 -0
  35. package/src/lib/alert/AlertTitle.vue +15 -0
  36. package/src/lib/alert/variants.test.ts +47 -0
  37. package/src/lib/alert/variants.ts +19 -0
  38. package/src/lib/alert-dialog/AlertDialog.vue +11 -0
  39. package/src/lib/alert-dialog/AlertDialogAction.vue +23 -0
  40. package/src/lib/alert-dialog/AlertDialogCancel.vue +24 -0
  41. package/src/lib/alert-dialog/AlertDialogContent.vue +33 -0
  42. package/src/lib/alert-dialog/AlertDialogDescription.vue +16 -0
  43. package/src/lib/alert-dialog/AlertDialogFooter.vue +17 -0
  44. package/src/lib/alert-dialog/AlertDialogHeader.vue +17 -0
  45. package/src/lib/alert-dialog/AlertDialogOverlay.vue +21 -0
  46. package/src/lib/alert-dialog/AlertDialogPortal.vue +11 -0
  47. package/src/lib/alert-dialog/AlertDialogTitle.vue +16 -0
  48. package/src/lib/alert-dialog/AlertDialogTrigger.vue +11 -0
  49. package/src/lib/alert-dialog/index.ts +11 -0
  50. package/src/lib/aspect-ratio/AspectRatio.vue +11 -0
  51. package/src/lib/aspect-ratio/index.ts +1 -0
  52. package/src/lib/avatar/Avatar.test.ts +58 -0
  53. package/src/lib/avatar/Avatar.vue +20 -0
  54. package/src/lib/avatar/AvatarFallback.vue +20 -0
  55. package/src/lib/avatar/AvatarImage.vue +10 -0
  56. package/src/lib/avatar/index.ts +3 -0
  57. package/src/lib/badge/Badge.test.ts +77 -0
  58. package/src/lib/badge/Badge.vue +20 -0
  59. package/src/lib/badge/index.ts +2 -0
  60. package/src/lib/badge/variants.test.ts +73 -0
  61. package/src/lib/badge/variants.ts +26 -0
  62. package/src/lib/breadcrumb/Breadcrumb.vue +13 -0
  63. package/src/lib/breadcrumb/BreadcrumbEllipsis.vue +35 -0
  64. package/src/lib/breadcrumb/BreadcrumbItem.vue +15 -0
  65. package/src/lib/breadcrumb/BreadcrumbLink.vue +21 -0
  66. package/src/lib/breadcrumb/BreadcrumbList.vue +22 -0
  67. package/src/lib/breadcrumb/BreadcrumbPage.vue +20 -0
  68. package/src/lib/breadcrumb/BreadcrumbSeparator.vue +34 -0
  69. package/src/lib/breadcrumb/index.ts +7 -0
  70. package/src/lib/button/Button.test.ts +84 -0
  71. package/src/lib/button/Button.vue +63 -0
  72. package/src/lib/button/index.ts +2 -0
  73. package/src/lib/button/variants.test.ts +128 -0
  74. package/src/lib/button/variants.ts +66 -0
  75. package/src/lib/button-group/ButtonGroup.vue +25 -0
  76. package/src/lib/button-group/index.ts +1 -0
  77. package/src/lib/calendar/Calendar.vue +58 -0
  78. package/src/lib/calendar/CalendarCell.vue +22 -0
  79. package/src/lib/calendar/CalendarCellTrigger.vue +28 -0
  80. package/src/lib/calendar/CalendarGrid.vue +16 -0
  81. package/src/lib/calendar/CalendarGridBody.vue +11 -0
  82. package/src/lib/calendar/CalendarGridHead.vue +11 -0
  83. package/src/lib/calendar/CalendarGridRow.vue +16 -0
  84. package/src/lib/calendar/CalendarHeadCell.vue +16 -0
  85. package/src/lib/calendar/CalendarHeader.vue +16 -0
  86. package/src/lib/calendar/CalendarHeading.vue +16 -0
  87. package/src/lib/calendar/CalendarNext.vue +37 -0
  88. package/src/lib/calendar/CalendarPrev.vue +37 -0
  89. package/src/lib/calendar/index.ts +12 -0
  90. package/src/lib/card/Card.test.ts +202 -0
  91. package/src/lib/card/Card.vue +36 -0
  92. package/src/lib/card/CardContent.vue +15 -0
  93. package/src/lib/card/CardDescription.vue +15 -0
  94. package/src/lib/card/CardFooter.vue +16 -0
  95. package/src/lib/card/CardHeader.vue +15 -0
  96. package/src/lib/card/CardTitle.vue +15 -0
  97. package/src/lib/card/index.ts +6 -0
  98. package/src/lib/carousel/Carousel.vue +73 -0
  99. package/src/lib/carousel/CarouselContent.vue +55 -0
  100. package/src/lib/carousel/CarouselItem.vue +25 -0
  101. package/src/lib/carousel/CarouselNext.vue +40 -0
  102. package/src/lib/carousel/CarouselPrevious.vue +40 -0
  103. package/src/lib/carousel/index.ts +6 -0
  104. package/src/lib/carousel/useCarousel.ts +24 -0
  105. package/src/lib/checkbox/Checkbox.test.ts +45 -0
  106. package/src/lib/checkbox/Checkbox.vue +39 -0
  107. package/src/lib/code-preview/CodePreview.vue +95 -0
  108. package/src/lib/collapsible/Collapsible.test.ts +95 -0
  109. package/src/lib/collapsible/Collapsible.vue +11 -0
  110. package/src/lib/collapsible/CollapsibleContent.vue +21 -0
  111. package/src/lib/collapsible/CollapsibleTrigger.vue +11 -0
  112. package/src/lib/collapsible/index.ts +3 -0
  113. package/src/lib/command/Command.vue +21 -0
  114. package/src/lib/command/CommandDialog.vue +25 -0
  115. package/src/lib/command/CommandEmpty.vue +16 -0
  116. package/src/lib/command/CommandGroup.vue +21 -0
  117. package/src/lib/command/CommandInput.vue +35 -0
  118. package/src/lib/command/CommandItem.vue +23 -0
  119. package/src/lib/command/CommandLabel.vue +16 -0
  120. package/src/lib/command/CommandList.vue +16 -0
  121. package/src/lib/command/CommandSeparator.vue +14 -0
  122. package/src/lib/command/index.ts +9 -0
  123. package/src/lib/context-menu/ContextMenu.vue +11 -0
  124. package/src/lib/context-menu/ContextMenuCheckboxItem.vue +45 -0
  125. package/src/lib/context-menu/ContextMenuContent.vue +31 -0
  126. package/src/lib/context-menu/ContextMenuGroup.vue +11 -0
  127. package/src/lib/context-menu/ContextMenuItem.vue +24 -0
  128. package/src/lib/context-menu/ContextMenuLabel.vue +16 -0
  129. package/src/lib/context-menu/ContextMenuRadioGroup.vue +11 -0
  130. package/src/lib/context-menu/ContextMenuRadioItem.vue +44 -0
  131. package/src/lib/context-menu/ContextMenuSeparator.vue +14 -0
  132. package/src/lib/context-menu/ContextMenuShortcut.vue +11 -0
  133. package/src/lib/context-menu/ContextMenuSub.vue +11 -0
  134. package/src/lib/context-menu/ContextMenuSubContent.vue +28 -0
  135. package/src/lib/context-menu/ContextMenuSubTrigger.vue +36 -0
  136. package/src/lib/context-menu/ContextMenuTrigger.vue +11 -0
  137. package/src/lib/context-menu/index.ts +14 -0
  138. package/src/lib/data-table/DataTable.vue +226 -0
  139. package/src/lib/date-range-picker/DateRangePicker.vue +201 -0
  140. package/src/lib/date-time-picker/DateTimePicker.vue +159 -0
  141. package/src/lib/dialog/Dialog.test.ts +87 -0
  142. package/src/lib/dialog/Dialog.vue +14 -0
  143. package/src/lib/dialog/DialogClose.vue +11 -0
  144. package/src/lib/dialog/DialogContent.vue +56 -0
  145. package/src/lib/dialog/DialogDescription.vue +15 -0
  146. package/src/lib/dialog/DialogFooter.vue +17 -0
  147. package/src/lib/dialog/DialogHeader.vue +17 -0
  148. package/src/lib/dialog/DialogOverlay.vue +20 -0
  149. package/src/lib/dialog/DialogPortal.vue +11 -0
  150. package/src/lib/dialog/DialogTitle.vue +15 -0
  151. package/src/lib/dialog/DialogTrigger.vue +11 -0
  152. package/src/lib/dialog/index.ts +10 -0
  153. package/src/lib/direction/Direction.vue +13 -0
  154. package/src/lib/drawer/Drawer.vue +11 -0
  155. package/src/lib/drawer/DrawerClose.vue +11 -0
  156. package/src/lib/drawer/DrawerContent.vue +31 -0
  157. package/src/lib/drawer/DrawerDescription.vue +16 -0
  158. package/src/lib/drawer/DrawerFooter.vue +15 -0
  159. package/src/lib/drawer/DrawerHeader.vue +15 -0
  160. package/src/lib/drawer/DrawerOverlay.vue +21 -0
  161. package/src/lib/drawer/DrawerTitle.vue +16 -0
  162. package/src/lib/drawer/DrawerTrigger.vue +11 -0
  163. package/src/lib/drawer/index.ts +9 -0
  164. package/src/lib/dropdown-menu/DropdownMenu.test.ts +146 -0
  165. package/src/lib/dropdown-menu/DropdownMenu.vue +11 -0
  166. package/src/lib/dropdown-menu/DropdownMenuCheckboxItem.vue +45 -0
  167. package/src/lib/dropdown-menu/DropdownMenuContent.vue +31 -0
  168. package/src/lib/dropdown-menu/DropdownMenuGroup.vue +11 -0
  169. package/src/lib/dropdown-menu/DropdownMenuItem.vue +24 -0
  170. package/src/lib/dropdown-menu/DropdownMenuLabel.vue +16 -0
  171. package/src/lib/dropdown-menu/DropdownMenuRadioGroup.vue +11 -0
  172. package/src/lib/dropdown-menu/DropdownMenuRadioItem.vue +44 -0
  173. package/src/lib/dropdown-menu/DropdownMenuSeparator.vue +14 -0
  174. package/src/lib/dropdown-menu/DropdownMenuShortcut.vue +11 -0
  175. package/src/lib/dropdown-menu/DropdownMenuSub.vue +11 -0
  176. package/src/lib/dropdown-menu/DropdownMenuSubContent.vue +27 -0
  177. package/src/lib/dropdown-menu/DropdownMenuSubTrigger.vue +36 -0
  178. package/src/lib/dropdown-menu/DropdownMenuTrigger.vue +11 -0
  179. package/src/lib/dropdown-menu/index.ts +14 -0
  180. package/src/lib/empty/Empty.vue +11 -0
  181. package/src/lib/empty/EmptyDescription.vue +11 -0
  182. package/src/lib/empty/EmptyIcon.vue +8 -0
  183. package/src/lib/empty/EmptyTitle.vue +11 -0
  184. package/src/lib/empty/index.ts +4 -0
  185. package/src/lib/feature-card/FeatureCard.vue +177 -0
  186. package/src/lib/feature-card/README.md +139 -0
  187. package/src/lib/feature-card/index.ts +1 -0
  188. package/src/lib/field/Field.vue +15 -0
  189. package/src/lib/field/FieldDescription.vue +15 -0
  190. package/src/lib/field/FieldError.vue +15 -0
  191. package/src/lib/field/FieldLabel.vue +24 -0
  192. package/src/lib/field/index.ts +4 -0
  193. package/src/lib/hover-card/HoverCard.vue +11 -0
  194. package/src/lib/hover-card/HoverCardContent.vue +31 -0
  195. package/src/lib/hover-card/HoverCardTrigger.vue +11 -0
  196. package/src/lib/hover-card/index.ts +3 -0
  197. package/src/lib/icon/Icon.vue +33 -0
  198. package/src/lib/input/Input.test.ts +71 -0
  199. package/src/lib/input/Input.vue +85 -0
  200. package/src/lib/input/index.ts +1 -0
  201. package/src/lib/input-group/InputGroup.vue +24 -0
  202. package/src/lib/input-group/InputGroupAddon.vue +25 -0
  203. package/src/lib/input-group/InputGroupInput.vue +38 -0
  204. package/src/lib/input-group/index.ts +3 -0
  205. package/src/lib/input-otp/InputOTP.vue +16 -0
  206. package/src/lib/input-otp/InputOTPGroup.vue +11 -0
  207. package/src/lib/input-otp/InputOTPSeparator.vue +8 -0
  208. package/src/lib/input-otp/InputOTPSlot.vue +20 -0
  209. package/src/lib/input-otp/index.ts +4 -0
  210. package/src/lib/kbd/Kbd.vue +11 -0
  211. package/src/lib/kbd/index.ts +1 -0
  212. package/src/lib/label/Label.test.ts +38 -0
  213. package/src/lib/label/Label.vue +20 -0
  214. package/src/lib/label/index.ts +1 -0
  215. package/src/lib/layout/AppFooter.vue +18 -0
  216. package/src/lib/layout/AppHeader.vue +22 -0
  217. package/src/lib/layout/AppLayout.vue +13 -0
  218. package/src/lib/layout/AppMain.vue +22 -0
  219. package/src/lib/layout/AppSidebar.vue +50 -0
  220. package/src/lib/menubar/Menubar.vue +21 -0
  221. package/src/lib/menubar/MenubarCheckboxItem.vue +45 -0
  222. package/src/lib/menubar/MenubarContent.vue +30 -0
  223. package/src/lib/menubar/MenubarGroup.vue +11 -0
  224. package/src/lib/menubar/MenubarItem.vue +24 -0
  225. package/src/lib/menubar/MenubarLabel.vue +16 -0
  226. package/src/lib/menubar/MenubarMenu.vue +11 -0
  227. package/src/lib/menubar/MenubarRadioGroup.vue +11 -0
  228. package/src/lib/menubar/MenubarRadioItem.vue +44 -0
  229. package/src/lib/menubar/MenubarSeparator.vue +14 -0
  230. package/src/lib/menubar/MenubarShortcut.vue +11 -0
  231. package/src/lib/menubar/MenubarSub.vue +11 -0
  232. package/src/lib/menubar/MenubarSubContent.vue +26 -0
  233. package/src/lib/menubar/MenubarSubTrigger.vue +36 -0
  234. package/src/lib/menubar/MenubarTrigger.vue +21 -0
  235. package/src/lib/menubar/index.ts +15 -0
  236. package/src/lib/modal/Modal.test.ts +81 -0
  237. package/src/lib/modal/Modal.vue +12 -0
  238. package/src/lib/modal/ModalClose.vue +9 -0
  239. package/src/lib/modal/ModalContent.vue +32 -0
  240. package/src/lib/modal/ModalTrigger.vue +11 -0
  241. package/src/lib/multi-select/MultiSelect.vue +186 -0
  242. package/src/lib/multi-select/MultiSelectItem.vue +47 -0
  243. package/src/lib/native-select/NativeSelect.vue +41 -0
  244. package/src/lib/native-select/index.ts +1 -0
  245. package/src/lib/navigation-menu/NavigationMenu.vue +23 -0
  246. package/src/lib/navigation-menu/NavigationMenuContent.vue +21 -0
  247. package/src/lib/navigation-menu/NavigationMenuIndicator.vue +21 -0
  248. package/src/lib/navigation-menu/NavigationMenuItem.vue +11 -0
  249. package/src/lib/navigation-menu/NavigationMenuLink.vue +23 -0
  250. package/src/lib/navigation-menu/NavigationMenuList.vue +21 -0
  251. package/src/lib/navigation-menu/NavigationMenuTrigger.vue +36 -0
  252. package/src/lib/navigation-menu/NavigationMenuViewport.vue +24 -0
  253. package/src/lib/navigation-menu/index.ts +8 -0
  254. package/src/lib/pagination/Pagination.vue +16 -0
  255. package/src/lib/pagination/PaginationContent.vue +16 -0
  256. package/src/lib/pagination/PaginationEllipsis.vue +27 -0
  257. package/src/lib/pagination/PaginationFirst.vue +25 -0
  258. package/src/lib/pagination/PaginationItem.vue +11 -0
  259. package/src/lib/pagination/PaginationLast.vue +25 -0
  260. package/src/lib/pagination/PaginationLink.vue +31 -0
  261. package/src/lib/pagination/PaginationNext.vue +24 -0
  262. package/src/lib/pagination/PaginationPrev.vue +24 -0
  263. package/src/lib/pagination/index.ts +9 -0
  264. package/src/lib/popover/Popover.test.ts +97 -0
  265. package/src/lib/popover/Popover.vue +11 -0
  266. package/src/lib/popover/PopoverContent.vue +31 -0
  267. package/src/lib/popover/PopoverTrigger.vue +11 -0
  268. package/src/lib/popover/index.ts +3 -0
  269. package/src/lib/progress/Progress.test.ts +59 -0
  270. package/src/lib/progress/Progress.vue +41 -0
  271. package/src/lib/progress/index.ts +1 -0
  272. package/src/lib/radio-group/RadioGroup.test.ts +45 -0
  273. package/src/lib/radio-group/RadioGroup.vue +16 -0
  274. package/src/lib/radio-group/RadioGroupItem.vue +35 -0
  275. package/src/lib/radio-group/index.ts +2 -0
  276. package/src/lib/resizable/ResizableHandle.vue +38 -0
  277. package/src/lib/resizable/ResizablePanel.vue +11 -0
  278. package/src/lib/resizable/ResizablePanelGroup.vue +16 -0
  279. package/src/lib/resizable/index.ts +3 -0
  280. package/src/lib/scroll-area/ScrollArea.vue +29 -0
  281. package/src/lib/scroll-area/ScrollBar.vue +26 -0
  282. package/src/lib/scroll-area/index.ts +2 -0
  283. package/src/lib/select/Select.vue +11 -0
  284. package/src/lib/select/SelectContent.vue +48 -0
  285. package/src/lib/select/SelectGroup.vue +11 -0
  286. package/src/lib/select/SelectItem.vue +41 -0
  287. package/src/lib/select/SelectLabel.vue +16 -0
  288. package/src/lib/select/SelectScrollDownButton.vue +29 -0
  289. package/src/lib/select/SelectScrollUpButton.vue +29 -0
  290. package/src/lib/select/SelectSeparator.vue +14 -0
  291. package/src/lib/select/SelectTrigger.vue +37 -0
  292. package/src/lib/select/SelectValue.vue +11 -0
  293. package/src/lib/select/index.ts +10 -0
  294. package/src/lib/separator/Separator.test.ts +47 -0
  295. package/src/lib/separator/Separator.vue +23 -0
  296. package/src/lib/separator/index.ts +1 -0
  297. package/src/lib/sheet/Sheet.test.ts +118 -0
  298. package/src/lib/sheet/Sheet.vue +11 -0
  299. package/src/lib/sheet/SheetClose.vue +11 -0
  300. package/src/lib/sheet/SheetContent.vue +68 -0
  301. package/src/lib/sheet/SheetDescription.vue +16 -0
  302. package/src/lib/sheet/SheetFooter.vue +15 -0
  303. package/src/lib/sheet/SheetHeader.vue +15 -0
  304. package/src/lib/sheet/SheetOverlay.vue +21 -0
  305. package/src/lib/sheet/SheetTitle.vue +16 -0
  306. package/src/lib/sheet/SheetTrigger.vue +11 -0
  307. package/src/lib/sheet/index.ts +9 -0
  308. package/src/lib/sidebar/Sidebar.vue +19 -0
  309. package/src/lib/sidebar/SidebarContent.vue +11 -0
  310. package/src/lib/sidebar/SidebarFooter.vue +11 -0
  311. package/src/lib/sidebar/SidebarGroup.vue +11 -0
  312. package/src/lib/sidebar/SidebarGroupLabel.vue +11 -0
  313. package/src/lib/sidebar/SidebarHeader.vue +11 -0
  314. package/src/lib/sidebar/SidebarInset.vue +11 -0
  315. package/src/lib/sidebar/SidebarMenu.vue +11 -0
  316. package/src/lib/sidebar/SidebarMenuButton.vue +20 -0
  317. package/src/lib/sidebar/SidebarMenuItem.vue +9 -0
  318. package/src/lib/sidebar/SidebarProvider.vue +23 -0
  319. package/src/lib/sidebar/SidebarSeparator.vue +9 -0
  320. package/src/lib/sidebar/SidebarTrigger.vue +24 -0
  321. package/src/lib/sidebar/context.ts +8 -0
  322. package/src/lib/sidebar/useSidebar.ts +10 -0
  323. package/src/lib/skeleton/Skeleton.test.ts +36 -0
  324. package/src/lib/skeleton/Skeleton.vue +9 -0
  325. package/src/lib/skeleton/index.ts +1 -0
  326. package/src/lib/slider/Slider.test.ts +63 -0
  327. package/src/lib/slider/Slider.vue +67 -0
  328. package/src/lib/slider/index.ts +1 -0
  329. package/src/lib/sonner/Toaster.vue +29 -0
  330. package/src/lib/spinner/Spinner.vue +34 -0
  331. package/src/lib/spinner/index.ts +1 -0
  332. package/src/lib/stats-card/StatsCard.vue +179 -0
  333. package/src/lib/stats-card/index.ts +2 -0
  334. package/src/lib/styles.ts +133 -0
  335. package/src/lib/switch/Switch.test.ts +52 -0
  336. package/src/lib/switch/Switch.vue +43 -0
  337. package/src/lib/table/Table.test.ts +150 -0
  338. package/src/lib/table/Table.vue +13 -0
  339. package/src/lib/table/TableBody.vue +11 -0
  340. package/src/lib/table/TableCaption.vue +11 -0
  341. package/src/lib/table/TableCell.vue +11 -0
  342. package/src/lib/table/TableFooter.vue +11 -0
  343. package/src/lib/table/TableHead.vue +11 -0
  344. package/src/lib/table/TableHeader.vue +11 -0
  345. package/src/lib/table/TableRow.vue +11 -0
  346. package/src/lib/table/index.ts +8 -0
  347. package/src/lib/tabs/Tabs.test.ts +150 -0
  348. package/src/lib/tabs/Tabs.vue +11 -0
  349. package/src/lib/tabs/TabsContent.vue +21 -0
  350. package/src/lib/tabs/TabsList.vue +21 -0
  351. package/src/lib/tabs/TabsTrigger.vue +21 -0
  352. package/src/lib/tabs/index.ts +4 -0
  353. package/src/lib/textarea/Textarea.test.ts +41 -0
  354. package/src/lib/textarea/Textarea.vue +36 -0
  355. package/src/lib/theme-selector/README.md +154 -0
  356. package/src/lib/theme-selector/ThemeSelector.vue +279 -0
  357. package/src/lib/theme-selector/index.ts +2 -0
  358. package/src/lib/time-picker/TimePicker.vue +162 -0
  359. package/src/lib/time-picker/TimePickerSegment.vue +176 -0
  360. package/src/lib/toast/Toast.test.ts +80 -0
  361. package/src/lib/toast/Toast.vue +56 -0
  362. package/src/lib/toast/ToastAction.vue +23 -0
  363. package/src/lib/toast/ToastClose.vue +38 -0
  364. package/src/lib/toast/ToastDescription.vue +12 -0
  365. package/src/lib/toast/ToastProvider.ts +65 -0
  366. package/src/lib/toast/ToastTitle.vue +12 -0
  367. package/src/lib/toast/ToastViewport.vue +18 -0
  368. package/src/lib/toast/Toaster.vue +50 -0
  369. package/src/lib/toast/index.ts +7 -0
  370. package/src/lib/toggle/Toggle.vue +21 -0
  371. package/src/lib/toggle/index.ts +2 -0
  372. package/src/lib/toggle/variants.test.ts +87 -0
  373. package/src/lib/toggle/variants.ts +21 -0
  374. package/src/lib/toggle-group/ToggleGroup.vue +24 -0
  375. package/src/lib/toggle-group/ToggleGroupItem.vue +33 -0
  376. package/src/lib/toggle-group/index.ts +2 -0
  377. package/src/lib/tooltip/Tooltip.test.ts +87 -0
  378. package/src/lib/tooltip/Tooltip.vue +11 -0
  379. package/src/lib/tooltip/TooltipContent.vue +30 -0
  380. package/src/lib/tooltip/TooltipProvider.vue +11 -0
  381. package/src/lib/tooltip/TooltipTrigger.vue +11 -0
  382. package/src/lib/tooltip/index.ts +4 -0
  383. package/src/lib/typography/TypographyBlockquote.vue +11 -0
  384. package/src/lib/typography/TypographyH1.vue +11 -0
  385. package/src/lib/typography/TypographyH2.vue +11 -0
  386. package/src/lib/typography/TypographyH3.vue +11 -0
  387. package/src/lib/typography/TypographyH4.vue +11 -0
  388. package/src/lib/typography/TypographyInlineCode.vue +11 -0
  389. package/src/lib/typography/TypographyLarge.vue +11 -0
  390. package/src/lib/typography/TypographyLead.vue +11 -0
  391. package/src/lib/typography/TypographyMuted.vue +11 -0
  392. package/src/lib/typography/TypographyP.vue +11 -0
  393. package/src/lib/typography/TypographySmall.vue +11 -0
  394. package/src/lib/typography/index.ts +11 -0
  395. package/src/lib/utils.test.ts +45 -0
  396. package/src/lib/utils.ts +14 -0
  397. package/src/lib/variants.ts +45 -0
  398. package/src/theme.css +203 -0
  399. package/src/vite-env.d.ts +6 -0
@@ -0,0 +1,150 @@
1
+ import { describe, it, expect } from 'vitest'
2
+ import { mount } from '@vue/test-utils'
3
+ import Tabs from './Tabs.vue'
4
+ import TabsList from './TabsList.vue'
5
+ import TabsTrigger from './TabsTrigger.vue'
6
+ import TabsContent from './TabsContent.vue'
7
+
8
+ describe('Tabs', () => {
9
+ it('renders correctly', () => {
10
+ const wrapper = mount(Tabs, {
11
+ props: { defaultValue: 'tab1' },
12
+ })
13
+ expect(wrapper.exists()).toBe(true)
14
+ })
15
+
16
+ it('renders slot content', () => {
17
+ const wrapper = mount(Tabs, {
18
+ props: { defaultValue: 'tab1' },
19
+ slots: { default: '<div>Tabs content</div>' },
20
+ })
21
+ expect(wrapper.text()).toContain('Tabs content')
22
+ })
23
+
24
+ it('renders with TabsList and TabsTrigger', () => {
25
+ const wrapper = mount(Tabs, {
26
+ props: { defaultValue: 'tab1' },
27
+ slots: {
28
+ default: {
29
+ template: `
30
+ <TabsList>
31
+ <TabsTrigger value="tab1">Tab 1</TabsTrigger>
32
+ <TabsTrigger value="tab2">Tab 2</TabsTrigger>
33
+ </TabsList>
34
+ `,
35
+ components: { TabsList, TabsTrigger },
36
+ },
37
+ },
38
+ })
39
+ expect(wrapper.text()).toContain('Tab 1')
40
+ expect(wrapper.text()).toContain('Tab 2')
41
+ })
42
+
43
+ it('renders full tabs with content', () => {
44
+ const wrapper = mount(Tabs, {
45
+ props: { defaultValue: 'tab1' },
46
+ slots: {
47
+ default: {
48
+ template: `
49
+ <TabsList>
50
+ <TabsTrigger value="tab1">First</TabsTrigger>
51
+ <TabsTrigger value="tab2">Second</TabsTrigger>
52
+ </TabsList>
53
+ <TabsContent value="tab1">First content</TabsContent>
54
+ <TabsContent value="tab2">Second content</TabsContent>
55
+ `,
56
+ components: { TabsList, TabsTrigger, TabsContent },
57
+ },
58
+ },
59
+ })
60
+ expect(wrapper.text()).toContain('First')
61
+ expect(wrapper.text()).toContain('First content')
62
+ })
63
+
64
+ it('shows correct content for defaultValue', () => {
65
+ const wrapper = mount(Tabs, {
66
+ props: { defaultValue: 'tab2' },
67
+ slots: {
68
+ default: {
69
+ template: `
70
+ <TabsList>
71
+ <TabsTrigger value="tab1">Tab 1</TabsTrigger>
72
+ <TabsTrigger value="tab2">Tab 2</TabsTrigger>
73
+ </TabsList>
74
+ <TabsContent value="tab1">Content 1</TabsContent>
75
+ <TabsContent value="tab2">Content 2</TabsContent>
76
+ `,
77
+ components: { TabsList, TabsTrigger, TabsContent },
78
+ },
79
+ },
80
+ })
81
+ expect(wrapper.text()).toContain('Content 2')
82
+ })
83
+ })
84
+
85
+ describe('TabsList', () => {
86
+ it('renders correctly inside Tabs', () => {
87
+ const wrapper = mount(Tabs, {
88
+ props: { defaultValue: 'tab1' },
89
+ slots: {
90
+ default: {
91
+ template: '<TabsList><span>List</span></TabsList>',
92
+ components: { TabsList },
93
+ },
94
+ },
95
+ })
96
+ expect(wrapper.text()).toContain('List')
97
+ })
98
+
99
+ it('applies custom class', () => {
100
+ const wrapper = mount(Tabs, {
101
+ props: { defaultValue: 'tab1' },
102
+ slots: {
103
+ default: {
104
+ template: '<TabsList class="custom-list"><span>List</span></TabsList>',
105
+ components: { TabsList },
106
+ },
107
+ },
108
+ })
109
+ expect(wrapper.html()).toContain('custom-list')
110
+ })
111
+ })
112
+
113
+ describe('TabsTrigger', () => {
114
+ it('renders trigger text', () => {
115
+ const wrapper = mount(Tabs, {
116
+ props: { defaultValue: 'tab1' },
117
+ slots: {
118
+ default: {
119
+ template: `
120
+ <TabsList>
121
+ <TabsTrigger value="tab1">My Tab</TabsTrigger>
122
+ </TabsList>
123
+ `,
124
+ components: { TabsList, TabsTrigger },
125
+ },
126
+ },
127
+ })
128
+ expect(wrapper.text()).toContain('My Tab')
129
+ })
130
+ })
131
+
132
+ describe('TabsContent', () => {
133
+ it('renders content for active tab', () => {
134
+ const wrapper = mount(Tabs, {
135
+ props: { defaultValue: 'active' },
136
+ slots: {
137
+ default: {
138
+ template: `
139
+ <TabsList>
140
+ <TabsTrigger value="active">Active</TabsTrigger>
141
+ </TabsList>
142
+ <TabsContent value="active">Active content</TabsContent>
143
+ `,
144
+ components: { TabsList, TabsTrigger, TabsContent },
145
+ },
146
+ },
147
+ })
148
+ expect(wrapper.text()).toContain('Active content')
149
+ })
150
+ })
@@ -0,0 +1,11 @@
1
+ <script setup lang="ts">
2
+ defineOptions({ inheritAttrs: false })
3
+
4
+ import { TabsRoot } from 'radix-vue'
5
+ </script>
6
+
7
+ <template>
8
+ <TabsRoot v-bind="$attrs">
9
+ <slot />
10
+ </TabsRoot>
11
+ </template>
@@ -0,0 +1,21 @@
1
+ <script setup lang="ts">
2
+ defineOptions({ inheritAttrs: false })
3
+ import { TabsContent } from 'radix-vue'
4
+ import { cn } from '@/lib/utils'
5
+
6
+ const props = defineProps<{ class?: string }>()
7
+ </script>
8
+
9
+ <template>
10
+ <TabsContent
11
+ v-bind="$attrs"
12
+ :class="
13
+ cn(
14
+ 'mt-2 ring-offset-background focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring focus-visible:ring-offset-2',
15
+ props.class
16
+ )
17
+ "
18
+ >
19
+ <slot />
20
+ </TabsContent>
21
+ </template>
@@ -0,0 +1,21 @@
1
+ <script setup lang="ts">
2
+ defineOptions({ inheritAttrs: false })
3
+ import { TabsList } from 'radix-vue'
4
+ import { cn } from '@/lib/utils'
5
+
6
+ const props = defineProps<{ class?: string }>()
7
+ </script>
8
+
9
+ <template>
10
+ <TabsList
11
+ v-bind="$attrs"
12
+ :class="
13
+ cn(
14
+ 'inline-flex h-10 items-center justify-center rounded-md bg-muted p-1 text-muted-foreground shadow-depth-1',
15
+ props.class
16
+ )
17
+ "
18
+ >
19
+ <slot />
20
+ </TabsList>
21
+ </template>
@@ -0,0 +1,21 @@
1
+ <script setup lang="ts">
2
+ defineOptions({ inheritAttrs: false })
3
+ import { TabsTrigger } from 'radix-vue'
4
+ import { cn } from '@/lib/utils'
5
+
6
+ const props = defineProps<{ class?: string }>()
7
+ </script>
8
+
9
+ <template>
10
+ <TabsTrigger
11
+ v-bind="$attrs"
12
+ :class="
13
+ cn(
14
+ 'inline-flex items-center justify-center whitespace-nowrap rounded-sm px-3 py-1.5 text-sm font-medium ring-offset-background transition-all focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring focus-visible:ring-offset-2 disabled:pointer-events-none disabled:opacity-50 data-[state=active]:bg-background data-[state=active]:text-foreground data-[state=active]:shadow-sm',
15
+ props.class
16
+ )
17
+ "
18
+ >
19
+ <slot />
20
+ </TabsTrigger>
21
+ </template>
@@ -0,0 +1,4 @@
1
+ export { default as Tabs } from './Tabs.vue'
2
+ export { default as TabsList } from './TabsList.vue'
3
+ export { default as TabsTrigger } from './TabsTrigger.vue'
4
+ export { default as TabsContent } from './TabsContent.vue'
@@ -0,0 +1,41 @@
1
+ import { describe, it, expect } from 'vitest'
2
+ import { mount } from '@vue/test-utils'
3
+ import Textarea from './Textarea.vue'
4
+
5
+ describe('Textarea', () => {
6
+ it('renders correctly', () => {
7
+ const wrapper = mount(Textarea)
8
+ expect(wrapper.exists()).toBe(true)
9
+ expect(wrapper.element.tagName).toBe('TEXTAREA')
10
+ })
11
+
12
+ it('binds modelValue to textarea value', () => {
13
+ const wrapper = mount(Textarea, {
14
+ props: { modelValue: 'hello world' },
15
+ })
16
+ expect((wrapper.element as HTMLTextAreaElement).value).toBe('hello world')
17
+ })
18
+
19
+ it('emits update:modelValue on input', async () => {
20
+ const wrapper = mount(Textarea, {
21
+ props: { modelValue: '' },
22
+ })
23
+ await wrapper.setValue('new text')
24
+ expect(wrapper.emitted('update:modelValue')).toBeTruthy()
25
+ expect(wrapper.emitted('update:modelValue')![0]).toEqual(['new text'])
26
+ })
27
+
28
+ it('sets placeholder attribute', () => {
29
+ const wrapper = mount(Textarea, {
30
+ props: { placeholder: 'Type here...' },
31
+ })
32
+ expect(wrapper.attributes('placeholder')).toBe('Type here...')
33
+ })
34
+
35
+ it('is disabled when disabled prop is true', () => {
36
+ const wrapper = mount(Textarea, {
37
+ props: { disabled: true },
38
+ })
39
+ expect(wrapper.attributes('disabled')).toBeDefined()
40
+ })
41
+ })
@@ -0,0 +1,36 @@
1
+ <script setup lang="ts">
2
+ import { cn } from '@/lib/utils'
3
+
4
+ interface Props {
5
+ class?: string
6
+ disabled?: boolean
7
+ placeholder?: string
8
+ modelValue?: string
9
+ }
10
+
11
+ const props = defineProps<Props>()
12
+
13
+ defineEmits<{
14
+ 'update:modelValue': [value: string]
15
+ }>()
16
+ </script>
17
+
18
+ <template>
19
+ <textarea
20
+ :class="
21
+ cn(
22
+ 'flex min-h-[80px] w-full rounded-md border border-input bg-background px-3 py-2 text-sm',
23
+ 'ring-offset-background',
24
+ 'placeholder:text-muted-foreground',
25
+ 'focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring focus-visible:ring-offset-2',
26
+ 'disabled:cursor-not-allowed disabled:opacity-50',
27
+ 'shadow-depth-1 focus-visible:shadow-depth-2 transition-elevation',
28
+ props.class
29
+ )
30
+ "
31
+ :disabled="disabled"
32
+ :placeholder="placeholder"
33
+ :value="modelValue"
34
+ @input="$emit('update:modelValue', ($event.target as HTMLTextAreaElement).value)"
35
+ />
36
+ </template>
@@ -0,0 +1,154 @@
1
+ # ThemeSelector Component
2
+
3
+ A Vue 3 component for selecting visual themes with a beautiful card-based interface.
4
+
5
+ ## Files Created
6
+
7
+ 1. **`/packages/components/src/lib/theme-selector/ThemeSelector.vue`** — Main component file
8
+ 2. **`/packages/components/src/lib/theme-selector/index.ts`** — Export file
9
+ 3. **Updated `/packages/components/src/index.ts`** — Added exports
10
+
11
+ ## Installation
12
+
13
+ The component is now available in the @spavn/ui library:
14
+
15
+ ```typescript
16
+ import { ThemeSelector, type ThemeOption } from '@spavn/ui'
17
+ ```
18
+
19
+ ## Usage Examples
20
+
21
+ ### Basic Usage (Light/Dark)
22
+
23
+ ```vue
24
+ <script setup>
25
+ import { ref } from 'vue'
26
+ import { ThemeSelector } from '@spavn/ui'
27
+
28
+ const currentTheme = ref('light')
29
+ </script>
30
+
31
+ <template>
32
+ <ThemeSelector v-model="currentTheme" />
33
+ </template>
34
+ ```
35
+
36
+ ### With Custom Options
37
+
38
+ ```vue
39
+ <script setup>
40
+ import { ref } from 'vue'
41
+ import { ThemeSelector } from '@spavn/ui'
42
+
43
+ const currentTheme = ref('system')
44
+
45
+ const themeOptions = [
46
+ { value: 'light', label: 'Light', preview: 'light' },
47
+ { value: 'dark', label: 'Dark', preview: 'dark' },
48
+ { value: 'system', label: 'System', preview: 'light' },
49
+ { value: 'midnight', label: 'Midnight', preview: 'dark' }
50
+ ]
51
+ </script>
52
+
53
+ <template>
54
+ <ThemeSelector
55
+ v-model="currentTheme"
56
+ :options="themeOptions"
57
+ />
58
+ </template>
59
+ ```
60
+
61
+ ### With System Theme Option
62
+
63
+ ```vue
64
+ <script setup>
65
+ import { ref } from 'vue'
66
+ import { ThemeSelector } from '@spavn/ui'
67
+
68
+ const theme = ref('system')
69
+ </script>
70
+
71
+ <template>
72
+ <ThemeSelector
73
+ v-model="theme"
74
+ :options="[
75
+ { value: 'light', label: 'Light', preview: 'light' },
76
+ { value: 'dark', label: 'Dark', preview: 'dark' },
77
+ { value: 'system', label: 'System', preview: 'light' }
78
+ ]"
79
+ />
80
+ </template>
81
+ ```
82
+
83
+ ## Props
84
+
85
+ | Prop | Type | Default | Description |
86
+ |------|------|---------|-------------|
87
+ | `modelValue` | `string` | **required** | Currently selected theme value |
88
+ | `options` | `ThemeOption[]` | Light/Dark | Array of theme options to display |
89
+ | `class` | `string` | - | Additional CSS classes for the container |
90
+
91
+ ## ThemeOption Interface
92
+
93
+ ```typescript
94
+ interface ThemeOption {
95
+ /** Unique identifier for the theme */
96
+ value: string
97
+ /** Display label for the theme */
98
+ label: string
99
+ /** Visual preview type */
100
+ preview: 'light' | 'dark' | 'custom'
101
+ /** Optional icon name */
102
+ icon?: string
103
+ }
104
+ ```
105
+
106
+ ## Features
107
+
108
+ ### Visual Design
109
+ - **Light Card**: White background with blue selection indicator
110
+ - **Dark Card**: Gray-800 background with amber/yellow selection indicator
111
+ - **Watermark**: "COLORS" text watermark behind the cards
112
+ - **Preview Content**: Shows mini UI elements including "Aa" text and sample bars
113
+
114
+ ### Interactions
115
+ - Click to select
116
+ - Radio-style selection (only one at a time)
117
+ - Hover effects with shadow elevation
118
+ - Scale animation on selection indicator
119
+ - Ring highlight on selected state
120
+
121
+ ### Keyboard Navigation
122
+ - `ArrowRight` / `ArrowDown` — Move focus to next option
123
+ - `ArrowLeft` / `ArrowUp` — Move focus to previous option
124
+ - `Enter` / `Space` — Select focused option
125
+ - `Home` — Move focus to first option
126
+ - `End` — Move focus to last option
127
+
128
+ ### Accessibility
129
+ - `role="radiogroup"` on container
130
+ - `role="radio"` on each option
131
+ - `aria-checked` attribute indicating selection state
132
+ - `aria-label` on each option
133
+ - Tabindex management for keyboard focus
134
+ - Focus-visible styles with ring
135
+
136
+ ### Dark Mode Support
137
+ The component adapts to dark mode:
138
+ - Watermark color changes (gray-200/50 → gray-800/50)
139
+ - Label colors adapt
140
+ - Hover states are adjusted
141
+
142
+ ## Styling
143
+
144
+ The component uses Tailwind CSS classes:
145
+ - Cards: `rounded-2xl`, `shadow-depth-2`
146
+ - Selection indicator: 24px circle with scale animation
147
+ - Gap between options: 16px
148
+ - Card size: 120px × 100px
149
+
150
+ ## Events
151
+
152
+ | Event | Payload | Description |
153
+ |-------|---------|-------------|
154
+ | `update:modelValue` | `string` | Emitted when selection changes (for v-model) |