@vestow/vue 0.1.0
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.
- package/README.md +233 -0
- package/index.ts +8 -0
- package/package.json +68 -0
- package/src/components/accordion/Accordion.vue +45 -0
- package/src/components/accordion/AccordionContent.vue +31 -0
- package/src/components/accordion/AccordionItem.vue +26 -0
- package/src/components/accordion/AccordionTrigger.vue +39 -0
- package/src/components/accordion/index.ts +18 -0
- package/src/components/alert/Alert.vue +17 -0
- package/src/components/alert/AlertDescription.vue +12 -0
- package/src/components/alert/AlertTitle.vue +12 -0
- package/src/components/alert/index.ts +5 -0
- package/src/components/avatar/Avatar.vue +32 -0
- package/src/components/avatar/AvatarFallback.vue +23 -0
- package/src/components/avatar/AvatarImage.vue +18 -0
- package/src/components/avatar/index.ts +3 -0
- package/src/components/badge/Badge.vue +25 -0
- package/src/components/badge/index.ts +3 -0
- package/src/components/breadcrumb/Breadcrumb.vue +14 -0
- package/src/components/breadcrumb/BreadcrumbItem.vue +12 -0
- package/src/components/breadcrumb/BreadcrumbLink.vue +19 -0
- package/src/components/breadcrumb/BreadcrumbPage.vue +12 -0
- package/src/components/breadcrumb/BreadcrumbSeparator.vue +15 -0
- package/src/components/breadcrumb/index.ts +5 -0
- package/src/components/button/Button.vue +55 -0
- package/src/components/button/index.ts +3 -0
- package/src/components/button-group/ButtonGroup.vue +29 -0
- package/src/components/button-group/ButtonGroupSeparator.vue +30 -0
- package/src/components/button-group/ButtonGroupText.vue +29 -0
- package/src/components/button-group/SplitButton.vue +103 -0
- package/src/components/button-group/SplitButtonItems.vue +50 -0
- package/src/components/button-group/index.ts +34 -0
- package/src/components/calendar/Calendar.vue +120 -0
- package/src/components/calendar/RangeCalendar.vue +127 -0
- package/src/components/calendar/index.ts +2 -0
- package/src/components/card/Card.vue +12 -0
- package/src/components/card/CardAction.vue +12 -0
- package/src/components/card/CardContent.vue +12 -0
- package/src/components/card/CardDescription.vue +12 -0
- package/src/components/card/CardFooter.vue +12 -0
- package/src/components/card/CardHeader.vue +15 -0
- package/src/components/card/CardTitle.vue +12 -0
- package/src/components/card/index.ts +7 -0
- package/src/components/carousel/Carousel.vue +164 -0
- package/src/components/carousel/CarouselContent.vue +43 -0
- package/src/components/carousel/CarouselDots.vue +42 -0
- package/src/components/carousel/CarouselItem.vue +58 -0
- package/src/components/carousel/CarouselNext.vue +45 -0
- package/src/components/carousel/CarouselPrevious.vue +45 -0
- package/src/components/carousel/index.ts +44 -0
- package/src/components/cascade-select/CascadeSelect.vue +314 -0
- package/src/components/cascade-select/index.ts +11 -0
- package/src/components/chart/AreaChart.vue +201 -0
- package/src/components/chart/BarChart.vue +389 -0
- package/src/components/chart/ChartContainer.vue +127 -0
- package/src/components/chart/ChartCrosshair.vue +92 -0
- package/src/components/chart/ChartLegend.vue +63 -0
- package/src/components/chart/ChartTooltipCard.vue +49 -0
- package/src/components/chart/LineChart.vue +214 -0
- package/src/components/chart/PieChart.vue +280 -0
- package/src/components/chart/RadarChart.vue +291 -0
- package/src/components/chart/RadialChart.vue +354 -0
- package/src/components/chart/index.ts +30 -0
- package/src/components/chart/polar.ts +5 -0
- package/src/components/chart/tooltip.ts +5 -0
- package/src/components/chart/types.ts +52 -0
- package/src/components/chart/useChartSeries.ts +138 -0
- package/src/components/chart/xy-label.ts +5 -0
- package/src/components/checkbox/Checkbox.vue +81 -0
- package/src/components/checkbox/CheckboxField.vue +129 -0
- package/src/components/checkbox/CheckboxGroup.vue +62 -0
- package/src/components/checkbox/index.ts +21 -0
- package/src/components/chip/Chip.vue +73 -0
- package/src/components/chip/index.ts +3 -0
- package/src/components/code-block/CodeBlock.vue +100 -0
- package/src/components/code-block/index.ts +4 -0
- package/src/components/collapsible/Collapsible.vue +15 -0
- package/src/components/collapsible/CollapsibleContent.vue +26 -0
- package/src/components/collapsible/CollapsibleTrigger.vue +12 -0
- package/src/components/collapsible/index.ts +3 -0
- package/src/components/combobox/Combobox.vue +23 -0
- package/src/components/combobox/ComboboxAnchor.vue +20 -0
- package/src/components/combobox/ComboboxEmpty.vue +21 -0
- package/src/components/combobox/ComboboxGroup.vue +23 -0
- package/src/components/combobox/ComboboxInput.vue +32 -0
- package/src/components/combobox/ComboboxItem.vue +38 -0
- package/src/components/combobox/ComboboxList.vue +43 -0
- package/src/components/combobox/ComboboxSeparator.vue +18 -0
- package/src/components/combobox/ComboboxTrigger.vue +12 -0
- package/src/components/combobox/index.ts +9 -0
- package/src/components/command/Command.vue +54 -0
- package/src/components/command/CommandDialog.vue +41 -0
- package/src/components/command/CommandEmpty.vue +19 -0
- package/src/components/command/CommandGroup.vue +28 -0
- package/src/components/command/CommandInput.vue +25 -0
- package/src/components/command/CommandItem.vue +40 -0
- package/src/components/command/CommandList.vue +13 -0
- package/src/components/command/CommandSeparator.vue +11 -0
- package/src/components/command/CommandShortcut.vue +13 -0
- package/src/components/command/index.ts +34 -0
- package/src/components/command-block/CommandBlock.vue +90 -0
- package/src/components/command-block/index.ts +2 -0
- package/src/components/confirm-dialog/ConfirmDialog.vue +37 -0
- package/src/components/confirm-dialog/index.ts +1 -0
- package/src/components/confirm-popup/ConfirmPopup.vue +123 -0
- package/src/components/confirm-popup/index.ts +1 -0
- package/src/components/context-menu/ContextMenu.vue +15 -0
- package/src/components/context-menu/ContextMenuCheckboxItem.vue +30 -0
- package/src/components/context-menu/ContextMenuContent.vue +36 -0
- package/src/components/context-menu/ContextMenuGroup.vue +12 -0
- package/src/components/context-menu/ContextMenuItem.vue +32 -0
- package/src/components/context-menu/ContextMenuLabel.vue +21 -0
- package/src/components/context-menu/ContextMenuRadioGroup.vue +15 -0
- package/src/components/context-menu/ContextMenuRadioItem.vue +30 -0
- package/src/components/context-menu/ContextMenuSeparator.vue +19 -0
- package/src/components/context-menu/ContextMenuShortcut.vue +13 -0
- package/src/components/context-menu/ContextMenuSub.vue +15 -0
- package/src/components/context-menu/ContextMenuSubContent.vue +26 -0
- package/src/components/context-menu/ContextMenuSubTrigger.vue +26 -0
- package/src/components/context-menu/ContextMenuTrigger.vue +12 -0
- package/src/components/context-menu/index.ts +14 -0
- package/src/components/data-table/DataTable.vue +458 -0
- package/src/components/data-table/DataTableFacetedFilter.vue +97 -0
- package/src/components/data-table/DataTablePagination.vue +103 -0
- package/src/components/data-table/DataTableViewOptions.vue +69 -0
- package/src/components/data-table/features.ts +87 -0
- package/src/components/data-table/index.ts +27 -0
- package/src/components/data-table/pagination-adapter.ts +67 -0
- package/src/components/data-table/selection-column.ts +48 -0
- package/src/components/data-table/types.ts +36 -0
- package/src/components/data-view/DataView.vue +136 -0
- package/src/components/data-view/index.ts +1 -0
- package/src/components/date-picker/DatePicker.vue +117 -0
- package/src/components/date-picker/DateRangePicker.vue +122 -0
- package/src/components/date-picker/index.ts +2 -0
- package/src/components/deferred/Deferred.vue +80 -0
- package/src/components/deferred/index.ts +1 -0
- package/src/components/dialog/Dialog.vue +15 -0
- package/src/components/dialog/DialogClose.vue +12 -0
- package/src/components/dialog/DialogContent.vue +46 -0
- package/src/components/dialog/DialogDescription.vue +19 -0
- package/src/components/dialog/DialogFooter.vue +12 -0
- package/src/components/dialog/DialogHeader.vue +12 -0
- package/src/components/dialog/DialogTitle.vue +19 -0
- package/src/components/dialog/DialogTrigger.vue +12 -0
- package/src/components/dialog/index.ts +10 -0
- package/src/components/doc-example/DocExample.vue +41 -0
- package/src/components/doc-example/index.ts +1 -0
- package/src/components/doc-text/DocText.vue +64 -0
- package/src/components/doc-text/index.ts +1 -0
- package/src/components/dropdown-menu/DropdownMenu.vue +15 -0
- package/src/components/dropdown-menu/DropdownMenuCheckboxItem.vue +33 -0
- package/src/components/dropdown-menu/DropdownMenuContent.vue +36 -0
- package/src/components/dropdown-menu/DropdownMenuGroup.vue +12 -0
- package/src/components/dropdown-menu/DropdownMenuItem.vue +32 -0
- package/src/components/dropdown-menu/DropdownMenuLabel.vue +24 -0
- package/src/components/dropdown-menu/DropdownMenuRadioGroup.vue +15 -0
- package/src/components/dropdown-menu/DropdownMenuRadioItem.vue +33 -0
- package/src/components/dropdown-menu/DropdownMenuSeparator.vue +19 -0
- package/src/components/dropdown-menu/DropdownMenuShortcut.vue +13 -0
- package/src/components/dropdown-menu/DropdownMenuSub.vue +15 -0
- package/src/components/dropdown-menu/DropdownMenuSubContent.vue +29 -0
- package/src/components/dropdown-menu/DropdownMenuSubTrigger.vue +26 -0
- package/src/components/dropdown-menu/DropdownMenuTrigger.vue +12 -0
- package/src/components/dropdown-menu/index.ts +14 -0
- package/src/components/editable/Editable.vue +41 -0
- package/src/components/editable/EditableArea.vue +22 -0
- package/src/components/editable/EditableCancelTrigger.vue +40 -0
- package/src/components/editable/EditableEditTrigger.vue +40 -0
- package/src/components/editable/EditableInput.vue +28 -0
- package/src/components/editable/EditablePreview.vue +34 -0
- package/src/components/editable/EditableSubmitTrigger.vue +40 -0
- package/src/components/editable/index.ts +17 -0
- package/src/components/empty/Empty.vue +17 -0
- package/src/components/empty/EmptyActions.vue +14 -0
- package/src/components/empty/EmptyDescription.vue +12 -0
- package/src/components/empty/EmptyMedia.vue +16 -0
- package/src/components/empty/EmptyTitle.vue +17 -0
- package/src/components/empty/index.ts +7 -0
- package/src/components/field/Field.vue +22 -0
- package/src/components/field/FieldDescription.vue +20 -0
- package/src/components/field/FieldGroup.vue +22 -0
- package/src/components/field/FieldLabel.vue +27 -0
- package/src/components/field/FieldSeparator.vue +28 -0
- package/src/components/field/index.ts +7 -0
- package/src/components/fieldset/Fieldset.vue +126 -0
- package/src/components/fieldset/index.ts +1 -0
- package/src/components/file-upload/FileUpload.vue +149 -0
- package/src/components/file-upload/index.ts +8 -0
- package/src/components/float-label/FloatLabel.vue +26 -0
- package/src/components/float-label/index.ts +3 -0
- package/src/components/form/Form.vue +126 -0
- package/src/components/form/FormDescription.vue +12 -0
- package/src/components/form/FormField.vue +127 -0
- package/src/components/form/FormItem.vue +12 -0
- package/src/components/form/FormLabel.vue +14 -0
- package/src/components/form/FormMessage.vue +31 -0
- package/src/components/form/context.ts +54 -0
- package/src/components/form/errors.ts +6 -0
- package/src/components/form/index.ts +7 -0
- package/src/components/form/types.ts +55 -0
- package/src/components/hover-card/HoverCard.vue +27 -0
- package/src/components/hover-card/HoverCardContent.vue +36 -0
- package/src/components/hover-card/HoverCardTrigger.vue +12 -0
- package/src/components/hover-card/index.ts +3 -0
- package/src/components/ifta-label/IftaLabel.vue +26 -0
- package/src/components/ifta-label/index.ts +1 -0
- package/src/components/index.ts +89 -0
- package/src/components/input/Input.vue +87 -0
- package/src/components/input/index.ts +1 -0
- package/src/components/input-color/ColorArea.vue +36 -0
- package/src/components/input-color/ColorField.vue +32 -0
- package/src/components/input-color/ColorSlider.vue +31 -0
- package/src/components/input-color/InputColor.vue +65 -0
- package/src/components/input-color/index.ts +16 -0
- package/src/components/input-group/InputGroup.vue +26 -0
- package/src/components/input-group/InputGroupAddon.vue +32 -0
- package/src/components/input-group/InputGroupInput.vue +33 -0
- package/src/components/input-group/index.ts +17 -0
- package/src/components/input-number/InputNumber.vue +82 -0
- package/src/components/input-number/index.ts +1 -0
- package/src/components/input-otp/InputOtp.vue +186 -0
- package/src/components/input-otp/index.ts +1 -0
- package/src/components/input-password/InputPassword.vue +116 -0
- package/src/components/input-password/index.ts +5 -0
- package/src/components/input-tags/InputTags.vue +38 -0
- package/src/components/input-tags/InputTagsClear.vue +39 -0
- package/src/components/input-tags/InputTagsInput.vue +27 -0
- package/src/components/input-tags/InputTagsItem.vue +40 -0
- package/src/components/input-tags/InputTagsItemDelete.vue +32 -0
- package/src/components/input-tags/InputTagsItemText.vue +18 -0
- package/src/components/input-tags/index.ts +16 -0
- package/src/components/kbd/Kbd.vue +17 -0
- package/src/components/kbd/KbdGroup.vue +15 -0
- package/src/components/kbd/index.ts +4 -0
- package/src/components/label/Label.vue +23 -0
- package/src/components/label/index.ts +1 -0
- package/src/components/listbox/Listbox.vue +42 -0
- package/src/components/listbox/ListboxContent.vue +22 -0
- package/src/components/listbox/ListboxFilter.vue +34 -0
- package/src/components/listbox/ListboxGroup.vue +31 -0
- package/src/components/listbox/ListboxItem.vue +46 -0
- package/src/components/listbox/index.ts +19 -0
- package/src/components/mask/Mask.vue +205 -0
- package/src/components/mask/index.ts +15 -0
- package/src/components/menubar/Menubar.vue +26 -0
- package/src/components/menubar/MenubarCheckboxItem.vue +30 -0
- package/src/components/menubar/MenubarContent.vue +52 -0
- package/src/components/menubar/MenubarGroup.vue +12 -0
- package/src/components/menubar/MenubarItem.vue +32 -0
- package/src/components/menubar/MenubarLabel.vue +21 -0
- package/src/components/menubar/MenubarMenu.vue +12 -0
- package/src/components/menubar/MenubarRadioGroup.vue +15 -0
- package/src/components/menubar/MenubarRadioItem.vue +30 -0
- package/src/components/menubar/MenubarSeparator.vue +12 -0
- package/src/components/menubar/MenubarShortcut.vue +13 -0
- package/src/components/menubar/MenubarSub.vue +15 -0
- package/src/components/menubar/MenubarSubContent.vue +26 -0
- package/src/components/menubar/MenubarSubTrigger.vue +26 -0
- package/src/components/menubar/MenubarTrigger.vue +30 -0
- package/src/components/menubar/index.ts +29 -0
- package/src/components/navigation-menu/NavigationMenu.vue +43 -0
- package/src/components/navigation-menu/NavigationMenuContent.vue +63 -0
- package/src/components/navigation-menu/NavigationMenuIndicator.vue +31 -0
- package/src/components/navigation-menu/NavigationMenuItem.vue +20 -0
- package/src/components/navigation-menu/NavigationMenuLink.vue +34 -0
- package/src/components/navigation-menu/NavigationMenuList.vue +23 -0
- package/src/components/navigation-menu/NavigationMenuTrigger.vue +38 -0
- package/src/components/navigation-menu/NavigationMenuViewport.vue +34 -0
- package/src/components/navigation-menu/index.ts +18 -0
- package/src/components/order-list/OrderList.vue +168 -0
- package/src/components/order-list/SelectableList.vue +200 -0
- package/src/components/order-list/index.ts +1 -0
- package/src/components/pagination/Pagination.vue +133 -0
- package/src/components/pagination/index.ts +1 -0
- package/src/components/panel/Panel.vue +69 -0
- package/src/components/panel/index.ts +1 -0
- package/src/components/pick-list/PickList.vue +211 -0
- package/src/components/pick-list/index.ts +1 -0
- package/src/components/popover/Popover.vue +15 -0
- package/src/components/popover/PopoverAnchor.vue +12 -0
- package/src/components/popover/PopoverContent.vue +39 -0
- package/src/components/popover/PopoverTrigger.vue +12 -0
- package/src/components/popover/index.ts +4 -0
- package/src/components/progress/Progress.vue +39 -0
- package/src/components/progress/index.ts +1 -0
- package/src/components/props-table/PropsTable.vue +62 -0
- package/src/components/props-table/index.ts +2 -0
- package/src/components/radio-group/RadioGroup.vue +52 -0
- package/src/components/radio-group/RadioGroupItem.vue +80 -0
- package/src/components/radio-group/RadioGroupItemField.vue +128 -0
- package/src/components/radio-group/index.ts +21 -0
- package/src/components/rating/Rating.vue +70 -0
- package/src/components/rating/RatingItem.vue +26 -0
- package/src/components/rating/RatingItemIndicator.vue +28 -0
- package/src/components/rating/RatingStar.vue +16 -0
- package/src/components/rating/index.ts +13 -0
- package/src/components/scroll-area/ScrollArea.vue +52 -0
- package/src/components/scroll-area/index.ts +1 -0
- package/src/components/search-input/SearchInput.vue +46 -0
- package/src/components/search-input/index.ts +1 -0
- package/src/components/select/Select.vue +15 -0
- package/src/components/select/SelectContent.vue +67 -0
- package/src/components/select/SelectGroup.vue +20 -0
- package/src/components/select/SelectItem.vue +59 -0
- package/src/components/select/SelectLabel.vue +20 -0
- package/src/components/select/SelectSeparator.vue +18 -0
- package/src/components/select/SelectTrigger.vue +101 -0
- package/src/components/select/SelectValue.vue +46 -0
- package/src/components/select/index.ts +8 -0
- package/src/components/separator/Separator.vue +25 -0
- package/src/components/separator/index.ts +1 -0
- package/src/components/sheet/Sheet.vue +15 -0
- package/src/components/sheet/SheetClose.vue +12 -0
- package/src/components/sheet/SheetContent.vue +45 -0
- package/src/components/sheet/SheetDescription.vue +19 -0
- package/src/components/sheet/SheetFooter.vue +12 -0
- package/src/components/sheet/SheetHeader.vue +12 -0
- package/src/components/sheet/SheetTitle.vue +19 -0
- package/src/components/sheet/SheetTrigger.vue +12 -0
- package/src/components/sheet/index.ts +10 -0
- package/src/components/sidebar/Sidebar.vue +108 -0
- package/src/components/sidebar/SidebarContent.vue +19 -0
- package/src/components/sidebar/SidebarFooter.vue +19 -0
- package/src/components/sidebar/SidebarGroup.vue +19 -0
- package/src/components/sidebar/SidebarGroupAction.vue +28 -0
- package/src/components/sidebar/SidebarGroupContent.vue +19 -0
- package/src/components/sidebar/SidebarGroupLabel.vue +25 -0
- package/src/components/sidebar/SidebarHeader.vue +19 -0
- package/src/components/sidebar/SidebarInput.vue +15 -0
- package/src/components/sidebar/SidebarInset.vue +22 -0
- package/src/components/sidebar/SidebarMenu.vue +19 -0
- package/src/components/sidebar/SidebarMenuAction.vue +41 -0
- package/src/components/sidebar/SidebarMenuBadge.vue +24 -0
- package/src/components/sidebar/SidebarMenuButton.vue +94 -0
- package/src/components/sidebar/SidebarMenuItem.vue +19 -0
- package/src/components/sidebar/SidebarMenuSkeleton.vue +36 -0
- package/src/components/sidebar/SidebarMenuSub.vue +22 -0
- package/src/components/sidebar/SidebarMenuSubButton.vue +39 -0
- package/src/components/sidebar/SidebarMenuSubItem.vue +19 -0
- package/src/components/sidebar/SidebarProvider.vue +114 -0
- package/src/components/sidebar/SidebarRail.vue +37 -0
- package/src/components/sidebar/SidebarSeparator.vue +15 -0
- package/src/components/sidebar/SidebarTrigger.vue +27 -0
- package/src/components/sidebar/context.ts +39 -0
- package/src/components/sidebar/index.ts +34 -0
- package/src/components/skeleton/Skeleton.vue +10 -0
- package/src/components/skeleton/index.ts +1 -0
- package/src/components/skip-link/SkipLink.vue +45 -0
- package/src/components/skip-link/index.ts +1 -0
- package/src/components/slider/Slider.vue +57 -0
- package/src/components/slider/index.ts +3 -0
- package/src/components/speed-dial/SpeedDial.vue +362 -0
- package/src/components/speed-dial/index.ts +28 -0
- package/src/components/spinner/Spinner.vue +20 -0
- package/src/components/spinner/index.ts +1 -0
- package/src/components/splitter/Splitter.vue +24 -0
- package/src/components/splitter/SplitterHandle.vue +51 -0
- package/src/components/splitter/SplitterPanel.vue +30 -0
- package/src/components/splitter/index.ts +14 -0
- package/src/components/stepper/Stepper.vue +34 -0
- package/src/components/stepper/StepperItem.vue +113 -0
- package/src/components/stepper/index.ts +2 -0
- package/src/components/switch/Switch.vue +35 -0
- package/src/components/switch/index.ts +1 -0
- package/src/components/table/Table.vue +24 -0
- package/src/components/table/TableBody.vue +12 -0
- package/src/components/table/TableCell.vue +12 -0
- package/src/components/table/TableEmpty.vue +20 -0
- package/src/components/table/TableHead.vue +17 -0
- package/src/components/table/TableHeader.vue +12 -0
- package/src/components/table/TableRow.vue +19 -0
- package/src/components/table/index.ts +7 -0
- package/src/components/tabs/Tabs.vue +23 -0
- package/src/components/tabs/TabsContent.vue +23 -0
- package/src/components/tabs/TabsList.vue +26 -0
- package/src/components/tabs/TabsTrigger.vue +30 -0
- package/src/components/tabs/index.ts +4 -0
- package/src/components/textarea/Textarea.vue +25 -0
- package/src/components/textarea/index.ts +1 -0
- package/src/components/theme-controls/LocaleMenu.vue +95 -0
- package/src/components/theme-controls/PaletteMenu.vue +155 -0
- package/src/components/theme-controls/ThemeToggle.vue +21 -0
- package/src/components/theme-controls/index.ts +15 -0
- package/src/components/timeline/Timeline.vue +20 -0
- package/src/components/timeline/TimelineItem.vue +68 -0
- package/src/components/timeline/index.ts +15 -0
- package/src/components/toast/Toaster.vue +62 -0
- package/src/components/toast/index.ts +4 -0
- package/src/components/toast/toast.ts +57 -0
- package/src/components/toggle/Toggle.vue +32 -0
- package/src/components/toggle/ToggleGroup.vue +56 -0
- package/src/components/toggle/ToggleGroupItem.vue +33 -0
- package/src/components/toggle/index.ts +18 -0
- package/src/components/token-table/TokenTable.vue +67 -0
- package/src/components/token-table/index.ts +2 -0
- package/src/components/toolbar/Toolbar.vue +34 -0
- package/src/components/toolbar/ToolbarButton.vue +33 -0
- package/src/components/toolbar/ToolbarSeparator.vue +21 -0
- package/src/components/toolbar/index.ts +3 -0
- package/src/components/tooltip/Tooltip.vue +15 -0
- package/src/components/tooltip/TooltipContent.vue +38 -0
- package/src/components/tooltip/TooltipProvider.vue +16 -0
- package/src/components/tooltip/TooltipTrigger.vue +12 -0
- package/src/components/tooltip/index.ts +4 -0
- package/src/components/tree/Tree.vue +53 -0
- package/src/components/tree/TreeItem.vue +59 -0
- package/src/components/tree/index.ts +21 -0
- package/src/components/tree-select/TreeSelect.vue +141 -0
- package/src/components/tree-select/index.ts +1 -0
- package/src/components/tree-table/TreeTable.vue +302 -0
- package/src/components/tree-table/features.ts +49 -0
- package/src/components/tree-table/index.ts +3 -0
- package/src/components/video-player/VideoPlayer.vue +472 -0
- package/src/components/video-player/index.ts +20 -0
- package/src/composables/index.ts +15 -0
- package/src/composables/useBase.ts +32 -0
- package/src/composables/useChartPalette.ts +33 -0
- package/src/composables/useColorMode.ts +29 -0
- package/src/composables/useConfirm.ts +81 -0
- package/src/composables/useDelayedFlag.ts +62 -0
- package/src/composables/useI18n.ts +107 -0
- package/src/composables/useIsMobile.ts +34 -0
- package/src/composables/useMenuAccent.ts +32 -0
- package/src/composables/useMenuAppearance.ts +31 -0
- package/src/composables/useMenuColor.ts +31 -0
- package/src/composables/usePalette.ts +30 -0
- package/src/composables/useStyle.ts +35 -0
- package/src/composables/useSurface.ts +30 -0
- package/src/composables/useTableQuery.ts +73 -0
- package/src/composables/useThemeController.ts +48 -0
- package/src/i18n/README.md +68 -0
- package/src/i18n/controller.ts +233 -0
- package/src/i18n/dictionary.ts +43 -0
- package/src/i18n/index.ts +34 -0
- package/src/i18n/registry.ts +64 -0
- package/src/i18n/ui/en/ui.json +114 -0
- package/src/i18n/ui/en/zod.json +16 -0
- package/src/i18n/ui/index.ts +48 -0
- package/src/i18n/ui/vi/ui.json +114 -0
- package/src/i18n/ui/vi/zod.json +16 -0
- package/src/lib/date.ts +24 -0
- package/src/lib/focus.ts +12 -0
- package/src/lib/icons.ts +345 -0
- package/src/lib/menu-styles.ts +16 -0
- package/src/lib/menu.ts +20 -0
- package/src/lib/platform.ts +5 -0
- package/src/lib/types.ts +6 -0
- package/src/lib/utils.ts +9 -0
- package/src/lib/zod-messages.ts +127 -0
- package/src/styles/chart.css +30 -0
- package/src/styles/index.css +18 -0
- package/src/variants/README.md +55 -0
- package/src/variants/components/accordion.ts +71 -0
- package/src/variants/components/alert.ts +20 -0
- package/src/variants/components/badge.ts +76 -0
- package/src/variants/components/button-group.ts +136 -0
- package/src/variants/components/button.ts +160 -0
- package/src/variants/components/checkbox.ts +67 -0
- package/src/variants/components/chip.ts +51 -0
- package/src/variants/components/code-block.ts +22 -0
- package/src/variants/components/dialog.ts +28 -0
- package/src/variants/components/empty.ts +60 -0
- package/src/variants/components/field.ts +35 -0
- package/src/variants/components/float-label.ts +95 -0
- package/src/variants/components/input-group.ts +73 -0
- package/src/variants/components/input-password.ts +68 -0
- package/src/variants/components/kbd.ts +47 -0
- package/src/variants/components/picker-trigger.ts +30 -0
- package/src/variants/components/radio-group.ts +63 -0
- package/src/variants/components/sheet.ts +23 -0
- package/src/variants/components/sidebar.ts +33 -0
- package/src/variants/components/slider.ts +49 -0
- package/src/variants/components/timeline.ts +45 -0
- package/src/variants/components/toggle.ts +58 -0
- package/src/variants/index.ts +35 -0
- package/src/variants/lib/chart/polar.ts +139 -0
- package/src/variants/lib/chart/tooltip.ts +101 -0
- package/src/variants/lib/chart/types.ts +172 -0
- package/src/variants/lib/chart/xy-label.ts +42 -0
- package/src/variants/lib/focus.ts +66 -0
- package/src/variants/lib/form-errors.ts +59 -0
- package/src/variants/lib/highlight.ts +548 -0
- package/src/variants/lib/list-move.ts +63 -0
- package/src/variants/lib/mask.ts +106 -0
- package/src/variants/lib/media.ts +56 -0
- package/src/variants/lib/menu-styles.ts +71 -0
- package/src/variants/lib/platform.ts +68 -0
- package/src/variants/lib/tree.ts +119 -0
- package/src/variants/lib/upload.ts +58 -0
- package/src/variants/lib/utils.ts +11 -0
package/README.md
ADDED
|
@@ -0,0 +1,233 @@
|
|
|
1
|
+
# `@vestow/vue`
|
|
2
|
+
|
|
3
|
+
89 component Vue 3, phần lớn dựng trên [Reka UI](https://reka-ui.com), tô bằng Tailwind v4 và
|
|
4
|
+
`@vestow/theme`. Bộ này là phần Vue của WoodBlock.
|
|
5
|
+
|
|
6
|
+
Nó mang theo hai tầng mà trước đây là package riêng, và mang vì cùng một lý do — chúng
|
|
7
|
+
không dùng được nếu thiếu component đọc chúng:
|
|
8
|
+
|
|
9
|
+
| trong package | là gì |
|
|
10
|
+
|---|---|
|
|
11
|
+
| `src/variants` | 27 bảng `cva`, `cn()`, vòng focus, class menu, hình học chart |
|
|
12
|
+
| `src/i18n` | locale controller + 126 khoá mà chính component phát ra (`aria-label` của Carousel, nút Đóng của Dialog, lỗi Zod) |
|
|
13
|
+
|
|
14
|
+
Thứ đứng riêng là `@vestow/theme`: Design Token dạng CSS thuần cộng registry chín trục.
|
|
15
|
+
App nào chỉ cần token — kể cả app không dùng Vue — nạp mình nó là đủ.
|
|
16
|
+
|
|
17
|
+
Package **export thẳng `.vue` source**, không qua build — app mới là bên biên dịch. Đó là
|
|
18
|
+
chủ ý: Tailwind phải quét được class thật, và app tự quyết mức tree-shake. Kéo theo vài
|
|
19
|
+
ràng buộc ở phần cài đặt bên dưới, đọc kỹ ba mục có dấu ⚠.
|
|
20
|
+
|
|
21
|
+
## Cài
|
|
22
|
+
|
|
23
|
+
```bash
|
|
24
|
+
pnpm add @vestow/vue @vestow/theme
|
|
25
|
+
pnpm add -D typescript tailwindcss @tailwindcss/vite @vitejs/plugin-vue
|
|
26
|
+
```
|
|
27
|
+
|
|
28
|
+
### ⚠ `typescript` là bắt buộc, kể cả app JavaScript thuần
|
|
29
|
+
|
|
30
|
+
`@vue/compiler-sfc` cần TypeScript để phân giải type trong `defineProps<T>`, mà component
|
|
31
|
+
ở đây khai props bằng type import từ `reka-ui`. Thiếu nó thì build đổ hàng loạt với đúng
|
|
32
|
+
một câu, lặp lại cho từng file:
|
|
33
|
+
|
|
34
|
+
```
|
|
35
|
+
[@vue/compiler-sfc] Failed to load TypeScript, which is required for
|
|
36
|
+
resolving imported types.
|
|
37
|
+
```
|
|
38
|
+
|
|
39
|
+
Đã đo: 297 lỗi, tất cả cùng gốc này.
|
|
40
|
+
|
|
41
|
+
### ⚠ Và `typescript` phải là **6.x**, không phải 7
|
|
42
|
+
|
|
43
|
+
Cái bẫy tệ hơn, vì `pnpm add -D typescript` hôm nay kéo về **7.x** và mọi thứ trông như đã
|
|
44
|
+
đúng cho tới lúc build:
|
|
45
|
+
|
|
46
|
+
```
|
|
47
|
+
[@vue/compiler-sfc] No fs option provided to `compileScript` in non-Node environment.
|
|
48
|
+
File system access is required for resolving imported types.
|
|
49
|
+
```
|
|
50
|
+
|
|
51
|
+
Đo trên một app trống cài từ tarball: `typescript@7.0.2` → **298 lỗi**; hạ xuống
|
|
52
|
+
`typescript@6.0.3` → build xanh, không sửa gì khác.
|
|
53
|
+
|
|
54
|
+
```bash
|
|
55
|
+
pnpm add -D "typescript@~6.0.2"
|
|
56
|
+
```
|
|
57
|
+
|
|
58
|
+
**Nguyên nhân, đo chứ không đoán.** `typescript@7` là bản viết lại bằng Go, và entry mặc
|
|
59
|
+
định của nó chỉ còn hai trường:
|
|
60
|
+
|
|
61
|
+
```js
|
|
62
|
+
require('typescript') // -> { version: '7.0.2', versionMajorMinor: '7.0' }
|
|
63
|
+
```
|
|
64
|
+
|
|
65
|
+
Toàn bộ compiler API dời sang `typescript/unstable/*` với **hình dạng khác hẳn** — một lớp
|
|
66
|
+
`API`/`Project`/`Program` thay cho namespace `ts.*` phẳng. Còn `@vue/compiler-sfc` gọi
|
|
67
|
+
thẳng API cũ: `ts.sys` để đọc file, rồi `ts.findConfigFile` / `ts.resolveModuleName` để
|
|
68
|
+
tìm ra `reka-ui` khi bạn viết `defineProps<AccordionTriggerProps>`. Với TS 7 thì `ts.sys`
|
|
69
|
+
là `undefined`, và câu "non-Node environment" ở trên là compiler-sfc suy ra nhầm rằng nó
|
|
70
|
+
đang chạy trong trình duyệt.
|
|
71
|
+
|
|
72
|
+
**Cấp `fs` thủ công KHÔNG cứu được** — đã thử, vì nó chỉ chữa được nửa đầu:
|
|
73
|
+
|
|
74
|
+
| | lỗi |
|
|
75
|
+
|---|---|
|
|
76
|
+
| TS 7 | 298 |
|
|
77
|
+
| TS 7 + `vue({ script: { fs } })` | **168** — `ts2.findConfigFile is not a function` |
|
|
78
|
+
| TS 6 | 0 |
|
|
79
|
+
|
|
80
|
+
`fs` lo được import **tương đối** (`../../lib/types`); import **bare** (`reka-ui`) thì
|
|
81
|
+
bắt buộc đi qua bộ phân giải module của TypeScript, và bộ đó không tồn tại ở TS 7.
|
|
82
|
+
|
|
83
|
+
Nên đây không phải lựa chọn của package này: chừng nào `@vue/compiler-sfc` chưa port sang
|
|
84
|
+
API mới thì **mọi** thư viện Vue ship `.vue` source đều đứng ở TS 6.
|
|
85
|
+
|
|
86
|
+
### Vẫn dùng được TS 7 — cài song song, cách chính thức của Microsoft
|
|
87
|
+
|
|
88
|
+
Ràng buộc thật không phải "cấm TS 7", mà là **`require('typescript')` phải trả về API 6.x**.
|
|
89
|
+
TypeScript 7.0 (08/07/2026) phát hành có chủ ý mà **không có API** — bản thay thế hẹn ở
|
|
90
|
+
7.1 — và ghi thẳng trong thông báo phát hành: *"Projects using Vue, MDX, Astro, Svelte, and
|
|
91
|
+
others will need to continue using TypeScript 6.0 for now."* Kèm theo là gói tương thích
|
|
92
|
+
`@typescript/typescript6`.
|
|
93
|
+
|
|
94
|
+
Đo trên app thử ở trên, và nó chạy:
|
|
95
|
+
|
|
96
|
+
```bash
|
|
97
|
+
pnpm add -D "typescript@npm:@typescript/typescript6@6.0.2" "typescript7@npm:typescript@7.0.2"
|
|
98
|
+
```
|
|
99
|
+
|
|
100
|
+
| | kết quả |
|
|
101
|
+
|---|---|
|
|
102
|
+
| `vite build` (compiler-sfc thấy API 6.x) | **xanh**, CSS đủ class |
|
|
103
|
+
| `vue-tsc --noEmit` | chạy |
|
|
104
|
+
| `tsc --version` | **7.0.2** — binary đến từ gói TS 7 |
|
|
105
|
+
| `tsc --noEmit` trên file `.ts` thuần | bắt lỗi bằng TS 7 |
|
|
106
|
+
|
|
107
|
+
Tức phần TypeScript thuần của bạn chạy TS 7, chỉ riêng đường biên dịch SFC là đọc API 6.x.
|
|
108
|
+
(Microsoft bày chiều ngược lại — `typescript` là 7 còn gói tương thích cấp `tsc6` — nhưng
|
|
109
|
+
với một dự án Vue thì phải để tên `typescript` cho bản 6, vì compiler-sfc không cho đổi chỗ
|
|
110
|
+
nó tìm.)
|
|
111
|
+
|
|
112
|
+
**Mốc cần theo dõi: TypeScript 7.1**, kế hoạch phát hành stable **24/11/2026**, trong đó có
|
|
113
|
+
mục "Stabilize API". Port `compiler-sfc` sang API đó là việc của Vue và chưa có mốc; issue
|
|
114
|
+
TS-native ở `vuejs/language-tools` đã đóng với nhãn `upstream: typescript`. Theo dõi phía
|
|
115
|
+
Vue và phía TS, đừng theo dõi phía đây.
|
|
116
|
+
|
|
117
|
+
Cả hai ràng buộc TypeScript ở mục này là cái giá trực tiếp của việc export `.vue` source.
|
|
118
|
+
Một package build sẵn ra `.js` + `.d.ts` thì không dính cái nào — đó cũng là đường thoát
|
|
119
|
+
nếu ngày nào TS 6 hết đường lùi.
|
|
120
|
+
|
|
121
|
+
### ⚠ pnpm 11 phải cho `vue-demi` chạy build script
|
|
122
|
+
|
|
123
|
+
`reka-ui` (qua `@floating-ui/vue`) và `@tanstack/vue-form` đều dùng nó, và postinstall của
|
|
124
|
+
nó là thứ chọn shim đúng cho Vue 3. Trong `pnpm-workspace.yaml`:
|
|
125
|
+
|
|
126
|
+
```yaml
|
|
127
|
+
allowBuilds:
|
|
128
|
+
vue-demi: true
|
|
129
|
+
esbuild: true
|
|
130
|
+
# maplibre-gl đi kèm @unovis/ts cho phần bản đồ. Không dùng bản đồ thì để chặn.
|
|
131
|
+
maplibre-gl: false
|
|
132
|
+
```
|
|
133
|
+
|
|
134
|
+
## Nạp CSS
|
|
135
|
+
|
|
136
|
+
Đúng hai dòng, và thứ tự có ý nghĩa:
|
|
137
|
+
|
|
138
|
+
```css
|
|
139
|
+
@import "@vestow/vue/styles.css";
|
|
140
|
+
@source "./";
|
|
141
|
+
```
|
|
142
|
+
|
|
143
|
+
### ⚠ Đừng khai `@source` trỏ vào `node_modules`
|
|
144
|
+
|
|
145
|
+
`@vestow/vue/styles.css` đã tự khai `@source "../"` cho chính nó, mà Tailwind phân giải
|
|
146
|
+
`@source` **tương đối theo file CSS chứa nó** — nên nằm trong `node_modules` nó vẫn trỏ
|
|
147
|
+
đúng vào source của mình. Bạn chỉ cần khai vùng của **app bạn**.
|
|
148
|
+
|
|
149
|
+
Nó cũng đã `@import "tailwindcss" source(none)` và nạp sẵn token. Viết thêm
|
|
150
|
+
`@import "tailwindcss"` ở file của bạn là nạp hai lần — đo được, dư 19 KB CSS thô.
|
|
151
|
+
|
|
152
|
+
Nghiệm thu không phải bằng mắt: build xong grep file CSS tìm `ui-button` và `--focus-ring`.
|
|
153
|
+
Có thì `@source` đúng; DOM render đủ mà sạch class là dấu hiệu vùng quét bị hụt.
|
|
154
|
+
|
|
155
|
+
## Dùng
|
|
156
|
+
|
|
157
|
+
```ts
|
|
158
|
+
// main.ts
|
|
159
|
+
import { createApp } from 'vue'
|
|
160
|
+
import { themeController } from '@vestow/theme'
|
|
161
|
+
import App from './App.vue'
|
|
162
|
+
import './style.css'
|
|
163
|
+
|
|
164
|
+
themeController.init()
|
|
165
|
+
createApp(App).mount('#app')
|
|
166
|
+
```
|
|
167
|
+
|
|
168
|
+
```vue
|
|
169
|
+
<script setup lang="ts">
|
|
170
|
+
import { Badge, Button, Card, CardContent } from '@vestow/vue'
|
|
171
|
+
</script>
|
|
172
|
+
|
|
173
|
+
<template>
|
|
174
|
+
<Card>
|
|
175
|
+
<CardContent>
|
|
176
|
+
<Button variant="destructive" tone="soft">Xoá</Button>
|
|
177
|
+
<Badge>Mới</Badge>
|
|
178
|
+
</CardContent>
|
|
179
|
+
</Card>
|
|
180
|
+
</template>
|
|
181
|
+
```
|
|
182
|
+
|
|
183
|
+
`themeController.init()` là thứ đọc `localStorage` và áp ba trục giao diện lên `<html>`.
|
|
184
|
+
Không gọi thì component vẫn chạy, chỉ luôn ở bảng màu mặc định và không nhớ lựa chọn.
|
|
185
|
+
|
|
186
|
+
## Hai trục của Button và Badge
|
|
187
|
+
|
|
188
|
+
| prop | giá trị | nghĩa |
|
|
189
|
+
|---|---|---|
|
|
190
|
+
| `variant` | default, secondary, destructive, success, warning, info, outline, ghost, link | **màu** |
|
|
191
|
+
| `tone` | solid (mặc định), soft | **kiểu tô** |
|
|
192
|
+
|
|
193
|
+
Kính không phải một `tone`. Bật `data-surface="glass"` trên `<html>` (hoặc
|
|
194
|
+
`themeController.setSurface('glass')`) là **mọi** nút tự thành kính, không nút nào phải
|
|
195
|
+
khai gì.
|
|
196
|
+
|
|
197
|
+
## Import lẻ
|
|
198
|
+
|
|
199
|
+
`exports` mở sẵn ba nhánh con, dùng khi không muốn kéo cả `index.ts`:
|
|
200
|
+
|
|
201
|
+
```ts
|
|
202
|
+
import Button from '@vestow/vue/components/button/Button.vue'
|
|
203
|
+
import { cn } from '@vestow/vue/lib/utils'
|
|
204
|
+
import { useI18n } from '@vestow/vue/composables/useI18n'
|
|
205
|
+
|
|
206
|
+
// Hai tầng không-Vue, dùng được mà không kéo component nào:
|
|
207
|
+
import { buttonVariants } from '@vestow/vue/variants/components/button'
|
|
208
|
+
import { i18nController, locales } from '@vestow/vue/i18n'
|
|
209
|
+
```
|
|
210
|
+
|
|
211
|
+
## Peer
|
|
212
|
+
|
|
213
|
+
`vue` là peer dependency (`^3.5.42`). `@vestow/theme` là dependency thật — cài
|
|
214
|
+
`@vestow/vue` là có luôn.
|
|
215
|
+
|
|
216
|
+
## Publish
|
|
217
|
+
|
|
218
|
+
Không có bước build: `files` đóng gói `index.ts` + `src/`, và `exports` trỏ thẳng vào
|
|
219
|
+
source ở cả chế độ phát triển lẫn sau khi publish. Đóng gói thử mà không cần registry:
|
|
220
|
+
|
|
221
|
+
```bash
|
|
222
|
+
pnpm -F @vestow/vue pack --pack-destination /tmp
|
|
223
|
+
```
|
|
224
|
+
|
|
225
|
+
Muốn thử cài tarball ở một project khác thì `@vestow/theme` cũng phải có mặt — nó là
|
|
226
|
+
dependency thật, nên pnpm sẽ đi tìm trên registry. Trỏ nó về tarball local bằng
|
|
227
|
+
`overrides` trong `pnpm-workspace.yaml` của project đó, hoặc dựng một registry local
|
|
228
|
+
(`npx verdaccio`) rồi publish cả hai vào đó.
|
|
229
|
+
|
|
230
|
+
```yaml
|
|
231
|
+
overrides:
|
|
232
|
+
'@vestow/theme': file:/đường/dẫn/woodblock-theme-0.1.0.tgz
|
|
233
|
+
```
|
package/index.ts
ADDED
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
export * from './src/components'
|
|
2
|
+
export * from './src/composables'
|
|
3
|
+
export * from './src/lib/date'
|
|
4
|
+
export * from './src/lib/menu'
|
|
5
|
+
export * from './src/lib/platform'
|
|
6
|
+
export * from './src/lib/types'
|
|
7
|
+
export * from './src/lib/utils'
|
|
8
|
+
export * from './src/lib/zod-messages'
|
package/package.json
ADDED
|
@@ -0,0 +1,68 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "@vestow/vue",
|
|
3
|
+
"type": "module",
|
|
4
|
+
"version": "0.1.0",
|
|
5
|
+
"description": "Bộ component Vue 3 của WoodBlock: 89 component trên nền Reka UI, kèm 27 bảng cva và bộ chuỗi i18n của chính thư viện. Token và theme ở @vestow/theme.",
|
|
6
|
+
"license": "MIT",
|
|
7
|
+
"sideEffects": [
|
|
8
|
+
"**/*.css"
|
|
9
|
+
],
|
|
10
|
+
"exports": {
|
|
11
|
+
".": "./index.ts",
|
|
12
|
+
"./styles.css": "./src/styles/index.css",
|
|
13
|
+
"./icons": "./src/lib/icons.ts",
|
|
14
|
+
"./i18n": "./src/i18n/index.ts",
|
|
15
|
+
"./variants": "./src/variants/index.ts",
|
|
16
|
+
"./variants/*": "./src/variants/*.ts",
|
|
17
|
+
"./lib/*": "./src/lib/*",
|
|
18
|
+
"./components/*": "./src/components/*",
|
|
19
|
+
"./composables/*": "./src/composables/*"
|
|
20
|
+
},
|
|
21
|
+
"files": [
|
|
22
|
+
"README.md",
|
|
23
|
+
"index.ts",
|
|
24
|
+
"src"
|
|
25
|
+
],
|
|
26
|
+
"publishConfig": {
|
|
27
|
+
"access": "public"
|
|
28
|
+
},
|
|
29
|
+
"peerDependencies": {
|
|
30
|
+
"vue": "^3.5.42"
|
|
31
|
+
},
|
|
32
|
+
"dependencies": {
|
|
33
|
+
"@internationalized/date": "^3.12.3",
|
|
34
|
+
"@tanstack/vue-form": "^1.33.5",
|
|
35
|
+
"@tanstack/vue-table": "^9.2.4",
|
|
36
|
+
"@tanstack/vue-virtual": "^3.13.36",
|
|
37
|
+
"@unovis/ts": "^1.6.7",
|
|
38
|
+
"@unovis/vue": "^1.6.7",
|
|
39
|
+
"@vestow/theme": "0.1.0",
|
|
40
|
+
"class-variance-authority": "^0.7.1",
|
|
41
|
+
"clsx": "^2.1.1",
|
|
42
|
+
"embla-carousel": "^8.6.0",
|
|
43
|
+
"embla-carousel-vue": "^8.6.0",
|
|
44
|
+
"lucide-vue-next": "^1.0.0",
|
|
45
|
+
"reka-ui": "^2.10.4",
|
|
46
|
+
"tailwind-merge": "^3.6.0",
|
|
47
|
+
"tailwindcss": "^4.3.3",
|
|
48
|
+
"tw-animate-css": "^1.4.0",
|
|
49
|
+
"vue-sonner": "^2.0.9",
|
|
50
|
+
"zod": "^4.5.4"
|
|
51
|
+
},
|
|
52
|
+
"devDependencies": {
|
|
53
|
+
"@types/node": "^24.13.3",
|
|
54
|
+
"@vitejs/plugin-vue": "^6.0.8",
|
|
55
|
+
"@vue/test-utils": "^2.5.0",
|
|
56
|
+
"happy-dom": "^20.14.3",
|
|
57
|
+
"typescript": "~6.0.2",
|
|
58
|
+
"vite": "^8.2.2",
|
|
59
|
+
"vitest": "^5.0.0",
|
|
60
|
+
"vue": "^3.5.42",
|
|
61
|
+
"vue-tsc": "^3.3.11"
|
|
62
|
+
},
|
|
63
|
+
"scripts": {
|
|
64
|
+
"test": "vitest run",
|
|
65
|
+
"test:watch": "vitest",
|
|
66
|
+
"typecheck": "vue-tsc --noEmit -p tsconfig.json"
|
|
67
|
+
}
|
|
68
|
+
}
|
|
@@ -0,0 +1,45 @@
|
|
|
1
|
+
<script setup lang="ts">
|
|
2
|
+
import type { AccordionRootEmits, AccordionRootProps } from 'reka-ui'
|
|
3
|
+
import type { ClassProps } from '../../lib/types'
|
|
4
|
+
import type { AccordionVariants } from './index'
|
|
5
|
+
import { AccordionRoot, useForwardPropsEmits } from 'reka-ui'
|
|
6
|
+
import { computed } from 'vue'
|
|
7
|
+
import { cn } from '../../lib/utils'
|
|
8
|
+
import { accordionVariants, provideAccordionContext } from './index'
|
|
9
|
+
|
|
10
|
+
const props = withDefaults(
|
|
11
|
+
defineProps<AccordionRootProps & ClassProps & {
|
|
12
|
+
variant?: AccordionVariants['variant']
|
|
13
|
+
}>(),
|
|
14
|
+
{
|
|
15
|
+
type: 'single',
|
|
16
|
+
variant: 'plain',
|
|
17
|
+
/**
|
|
18
|
+
* Reka mặc định `false` cho `collapsible` — mở một mục rồi thì không đóng
|
|
19
|
+
* lại được, luôn phải có đúng một mục mở. Đó là khuôn của tab, không phải
|
|
20
|
+
* của accordion: người đọc mong bấm lại vào tiêu đề thì nó gập.
|
|
21
|
+
*/
|
|
22
|
+
collapsible: true,
|
|
23
|
+
},
|
|
24
|
+
)
|
|
25
|
+
|
|
26
|
+
const emits = defineEmits<AccordionRootEmits>()
|
|
27
|
+
|
|
28
|
+
const delegated = computed(() => {
|
|
29
|
+
const { class: _class, variant: _variant, ...rest } = props
|
|
30
|
+
return rest
|
|
31
|
+
})
|
|
32
|
+
|
|
33
|
+
const forwarded = useForwardPropsEmits(delegated, emits)
|
|
34
|
+
|
|
35
|
+
provideAccordionContext({ variant: computed(() => props.variant) })
|
|
36
|
+
</script>
|
|
37
|
+
|
|
38
|
+
<template>
|
|
39
|
+
<AccordionRoot
|
|
40
|
+
v-bind="forwarded"
|
|
41
|
+
:class="cn(accordionVariants({ variant: props.variant }), props.class)"
|
|
42
|
+
>
|
|
43
|
+
<slot />
|
|
44
|
+
</AccordionRoot>
|
|
45
|
+
</template>
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
<script setup lang="ts">
|
|
2
|
+
import type { AccordionContentProps } from 'reka-ui'
|
|
3
|
+
import type { ClassProps } from '../../lib/types'
|
|
4
|
+
import { AccordionContent } from 'reka-ui'
|
|
5
|
+
import { computed } from 'vue'
|
|
6
|
+
import { cn } from '../../lib/utils'
|
|
7
|
+
import { accordionContentVariants, injectAccordionContext } from './index'
|
|
8
|
+
|
|
9
|
+
const props = defineProps<AccordionContentProps & ClassProps>()
|
|
10
|
+
|
|
11
|
+
const accordion = injectAccordionContext(null)
|
|
12
|
+
|
|
13
|
+
const delegated = computed(() => {
|
|
14
|
+
const { class: _class, ...rest } = props
|
|
15
|
+
return rest
|
|
16
|
+
})
|
|
17
|
+
</script>
|
|
18
|
+
|
|
19
|
+
<template>
|
|
20
|
+
<AccordionContent
|
|
21
|
+
v-bind="delegated"
|
|
22
|
+
:class="cn(accordionContentVariants({ variant: accordion?.variant.value }))"
|
|
23
|
+
>
|
|
24
|
+
<!-- Padding đặt ở lớp TRONG, không phải trên chính AccordionContent: phần
|
|
25
|
+
tử đó đang bị animate `height`, thêm padding vào nó thì lúc đóng chiều
|
|
26
|
+
cao chạy về 0 mà padding vẫn còn, khối giật một nhịp ở cuối. -->
|
|
27
|
+
<div :class="cn('pb-3.5 leading-relaxed', accordion?.variant.value === 'contained' && 'px-4', props.class)">
|
|
28
|
+
<slot />
|
|
29
|
+
</div>
|
|
30
|
+
</AccordionContent>
|
|
31
|
+
</template>
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
<script setup lang="ts">
|
|
2
|
+
import type { AccordionItemProps } from 'reka-ui'
|
|
3
|
+
import type { ClassProps } from '../../lib/types'
|
|
4
|
+
import { AccordionItem } from 'reka-ui'
|
|
5
|
+
import { computed } from 'vue'
|
|
6
|
+
import { cn } from '../../lib/utils'
|
|
7
|
+
import { accordionItemVariants, injectAccordionContext } from './index'
|
|
8
|
+
|
|
9
|
+
const props = defineProps<AccordionItemProps & ClassProps>()
|
|
10
|
+
|
|
11
|
+
const accordion = injectAccordionContext(null)
|
|
12
|
+
|
|
13
|
+
const delegated = computed(() => {
|
|
14
|
+
const { class: _class, ...rest } = props
|
|
15
|
+
return rest
|
|
16
|
+
})
|
|
17
|
+
</script>
|
|
18
|
+
|
|
19
|
+
<template>
|
|
20
|
+
<AccordionItem
|
|
21
|
+
v-bind="delegated"
|
|
22
|
+
:class="cn(accordionItemVariants({ variant: accordion?.variant.value }), props.class)"
|
|
23
|
+
>
|
|
24
|
+
<slot />
|
|
25
|
+
</AccordionItem>
|
|
26
|
+
</template>
|
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
<script setup lang="ts">
|
|
2
|
+
import type { AccordionTriggerProps } from 'reka-ui'
|
|
3
|
+
import type { ClassProps } from '../../lib/types'
|
|
4
|
+
import { AccordionHeader, AccordionTrigger } from 'reka-ui'
|
|
5
|
+
import { computed } from 'vue'
|
|
6
|
+
import { ChevronDown } from '../../lib/icons'
|
|
7
|
+
import { cn } from '../../lib/utils'
|
|
8
|
+
import { accordionTriggerVariants, injectAccordionContext } from './index'
|
|
9
|
+
|
|
10
|
+
const props = defineProps<AccordionTriggerProps & ClassProps>()
|
|
11
|
+
|
|
12
|
+
const accordion = injectAccordionContext(null)
|
|
13
|
+
|
|
14
|
+
const delegated = computed(() => {
|
|
15
|
+
const { class: _class, ...rest } = props
|
|
16
|
+
return rest
|
|
17
|
+
})
|
|
18
|
+
</script>
|
|
19
|
+
|
|
20
|
+
<template>
|
|
21
|
+
<!-- `AccordionHeader` render thẻ h3 mang role="heading": trình đọc màn hình
|
|
22
|
+
liệt kê được các mục như một dàn ý, không chỉ là một dãy nút. -->
|
|
23
|
+
<AccordionHeader class="flex">
|
|
24
|
+
<AccordionTrigger
|
|
25
|
+
v-bind="delegated"
|
|
26
|
+
:class="cn(accordionTriggerVariants({ variant: accordion?.variant.value }), props.class)"
|
|
27
|
+
>
|
|
28
|
+
<slot />
|
|
29
|
+
|
|
30
|
+
<!-- Mũi tên nằm ngoài slot nên nội dung tiêu đề dài bao nhiêu cũng không
|
|
31
|
+
đẩy nó đi; `mt-0.5` cho nó thẳng hàng với DÒNG ĐẦU của tiêu đề, vì
|
|
32
|
+
tiêu đề có thể xuống hai dòng còn mũi tên thì không. -->
|
|
33
|
+
<ChevronDown
|
|
34
|
+
class="mt-0.5 size-4 shrink-0 text-muted-foreground transition-transform duration-(--duration-base) group-data-[state=open]/accordion-trigger:rotate-180 motion-reduce:transition-none"
|
|
35
|
+
aria-hidden="true"
|
|
36
|
+
/>
|
|
37
|
+
</AccordionTrigger>
|
|
38
|
+
</AccordionHeader>
|
|
39
|
+
</template>
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
import type { ComputedRef } from 'vue'
|
|
2
|
+
import type { AccordionVariants } from '../../variants/components/accordion'
|
|
3
|
+
import { createContext } from 'reka-ui'
|
|
4
|
+
|
|
5
|
+
export { accordionContentVariants, accordionItemVariants, accordionTriggerVariants, accordionVariants, type AccordionVariants } from '../../variants/components/accordion'
|
|
6
|
+
export { default as Accordion } from './Accordion.vue'
|
|
7
|
+
export { default as AccordionContent } from './AccordionContent.vue'
|
|
8
|
+
export { default as AccordionItem } from './AccordionItem.vue'
|
|
9
|
+
|
|
10
|
+
/** Kiểu trình bày khai một lần ở gốc, mọi phần con đọc lại từ đây. */
|
|
11
|
+
export interface AccordionContext {
|
|
12
|
+
variant: ComputedRef<AccordionVariants['variant']>
|
|
13
|
+
}
|
|
14
|
+
|
|
15
|
+
export const [injectAccordionContext, provideAccordionContext]
|
|
16
|
+
= createContext<AccordionContext>('Accordion')
|
|
17
|
+
|
|
18
|
+
export { default as AccordionTrigger } from './AccordionTrigger.vue'
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
<script setup lang="ts">
|
|
2
|
+
import type { ClassProps } from '../../lib/types'
|
|
3
|
+
import type { AlertVariants } from './index'
|
|
4
|
+
import { cn } from '../../lib/utils'
|
|
5
|
+
import { alertVariants } from './index'
|
|
6
|
+
|
|
7
|
+
const props = defineProps<ClassProps & { variant?: AlertVariants['variant'] }>()
|
|
8
|
+
</script>
|
|
9
|
+
|
|
10
|
+
<template>
|
|
11
|
+
<div role="alert" :class="cn(alertVariants({ variant }), props.class)">
|
|
12
|
+
<slot name="icon" />
|
|
13
|
+
<div class="col-start-2 flex flex-col gap-1">
|
|
14
|
+
<slot />
|
|
15
|
+
</div>
|
|
16
|
+
</div>
|
|
17
|
+
</template>
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
<script setup lang="ts">
|
|
2
|
+
import type { ClassProps } from '../../lib/types'
|
|
3
|
+
import { cn } from '../../lib/utils'
|
|
4
|
+
|
|
5
|
+
const props = defineProps<ClassProps>()
|
|
6
|
+
</script>
|
|
7
|
+
|
|
8
|
+
<template>
|
|
9
|
+
<div :class="cn('text-sm text-muted-foreground [&_p]:leading-relaxed', props.class)">
|
|
10
|
+
<slot />
|
|
11
|
+
</div>
|
|
12
|
+
</template>
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
<script setup lang="ts">
|
|
2
|
+
import type { ClassProps } from '../../lib/types'
|
|
3
|
+
import { cn } from '../../lib/utils'
|
|
4
|
+
|
|
5
|
+
const props = defineProps<ClassProps>()
|
|
6
|
+
</script>
|
|
7
|
+
|
|
8
|
+
<template>
|
|
9
|
+
<div :class="cn('font-medium leading-none tracking-tight', props.class)">
|
|
10
|
+
<slot />
|
|
11
|
+
</div>
|
|
12
|
+
</template>
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
<script setup lang="ts">
|
|
2
|
+
import type { AvatarRootProps } from 'reka-ui'
|
|
3
|
+
import type { ClassProps } from '../../lib/types'
|
|
4
|
+
import { AvatarRoot } from 'reka-ui'
|
|
5
|
+
import { computed } from 'vue'
|
|
6
|
+
import { cn } from '../../lib/utils'
|
|
7
|
+
|
|
8
|
+
const props = withDefaults(
|
|
9
|
+
defineProps<AvatarRootProps & ClassProps & { size?: 'sm' | 'default' | 'lg' }>(),
|
|
10
|
+
{ size: 'default' },
|
|
11
|
+
)
|
|
12
|
+
|
|
13
|
+
const delegated = computed(() => {
|
|
14
|
+
const { class: _class, size: _size, ...rest } = props
|
|
15
|
+
return rest
|
|
16
|
+
})
|
|
17
|
+
|
|
18
|
+
const sizeClass = computed(() => ({
|
|
19
|
+
sm: 'size-7 text-xs',
|
|
20
|
+
default: 'size-9 text-sm',
|
|
21
|
+
lg: 'size-12 text-base',
|
|
22
|
+
}[props.size]))
|
|
23
|
+
</script>
|
|
24
|
+
|
|
25
|
+
<template>
|
|
26
|
+
<AvatarRoot
|
|
27
|
+
v-bind="delegated"
|
|
28
|
+
:class="cn('relative flex shrink-0 overflow-hidden rounded-full', sizeClass, props.class)"
|
|
29
|
+
>
|
|
30
|
+
<slot />
|
|
31
|
+
</AvatarRoot>
|
|
32
|
+
</template>
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
<script setup lang="ts">
|
|
2
|
+
import type { AvatarFallbackProps } from 'reka-ui'
|
|
3
|
+
import type { ClassProps } from '../../lib/types'
|
|
4
|
+
import { AvatarFallback } from 'reka-ui'
|
|
5
|
+
import { computed } from 'vue'
|
|
6
|
+
import { cn } from '../../lib/utils'
|
|
7
|
+
|
|
8
|
+
const props = defineProps<AvatarFallbackProps & ClassProps>()
|
|
9
|
+
|
|
10
|
+
const delegated = computed(() => {
|
|
11
|
+
const { class: _class, ...rest } = props
|
|
12
|
+
return rest
|
|
13
|
+
})
|
|
14
|
+
</script>
|
|
15
|
+
|
|
16
|
+
<template>
|
|
17
|
+
<AvatarFallback
|
|
18
|
+
v-bind="delegated"
|
|
19
|
+
:class="cn('flex size-full items-center justify-center rounded-full bg-muted font-medium text-muted-foreground', props.class)"
|
|
20
|
+
>
|
|
21
|
+
<slot />
|
|
22
|
+
</AvatarFallback>
|
|
23
|
+
</template>
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
<script setup lang="ts">
|
|
2
|
+
import type { AvatarImageProps } from 'reka-ui'
|
|
3
|
+
import type { ClassProps } from '../../lib/types'
|
|
4
|
+
import { AvatarImage } from 'reka-ui'
|
|
5
|
+
import { computed } from 'vue'
|
|
6
|
+
import { cn } from '../../lib/utils'
|
|
7
|
+
|
|
8
|
+
const props = defineProps<AvatarImageProps & ClassProps>()
|
|
9
|
+
|
|
10
|
+
const delegated = computed(() => {
|
|
11
|
+
const { class: _class, ...rest } = props
|
|
12
|
+
return rest
|
|
13
|
+
})
|
|
14
|
+
</script>
|
|
15
|
+
|
|
16
|
+
<template>
|
|
17
|
+
<AvatarImage v-bind="delegated" :class="cn('size-full object-cover', props.class)" />
|
|
18
|
+
</template>
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
<script setup lang="ts">
|
|
2
|
+
import type { PrimitiveProps } from 'reka-ui'
|
|
3
|
+
import type { ClassProps } from '../../lib/types'
|
|
4
|
+
import type { BadgeVariants } from './index'
|
|
5
|
+
import { Primitive } from 'reka-ui'
|
|
6
|
+
import { cn } from '../../lib/utils'
|
|
7
|
+
import { badgeVariants } from './index'
|
|
8
|
+
|
|
9
|
+
const props = withDefaults(
|
|
10
|
+
defineProps<PrimitiveProps & ClassProps & {
|
|
11
|
+
variant?: BadgeVariants['variant']
|
|
12
|
+
/** Cỡ: `xs` cho nhãn phụ 9px, `default` là cỡ thường. */
|
|
13
|
+
size?: BadgeVariants['size']
|
|
14
|
+
/** Kiểu tô: `solid` đặc, `soft` nền pha loãng. */
|
|
15
|
+
tone?: BadgeVariants['tone']
|
|
16
|
+
}>(),
|
|
17
|
+
{ as: 'span' },
|
|
18
|
+
)
|
|
19
|
+
</script>
|
|
20
|
+
|
|
21
|
+
<template>
|
|
22
|
+
<Primitive :as="as" :as-child="asChild" :class="cn(badgeVariants({ variant, size, tone }), props.class)">
|
|
23
|
+
<slot />
|
|
24
|
+
</Primitive>
|
|
25
|
+
</template>
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
<script setup lang="ts">
|
|
2
|
+
import type { ClassProps } from '../../lib/types'
|
|
3
|
+
import { cn } from '../../lib/utils'
|
|
4
|
+
|
|
5
|
+
const props = defineProps<ClassProps>()
|
|
6
|
+
</script>
|
|
7
|
+
|
|
8
|
+
<template>
|
|
9
|
+
<nav aria-label="breadcrumb">
|
|
10
|
+
<ol :class="cn('flex flex-wrap items-center gap-1.5 text-sm text-muted-foreground', props.class)">
|
|
11
|
+
<slot />
|
|
12
|
+
</ol>
|
|
13
|
+
</nav>
|
|
14
|
+
</template>
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
<script setup lang="ts">
|
|
2
|
+
import type { ClassProps } from '../../lib/types'
|
|
3
|
+
import { cn } from '../../lib/utils'
|
|
4
|
+
|
|
5
|
+
const props = defineProps<ClassProps>()
|
|
6
|
+
</script>
|
|
7
|
+
|
|
8
|
+
<template>
|
|
9
|
+
<li :class="cn('inline-flex items-center gap-1.5', props.class)">
|
|
10
|
+
<slot />
|
|
11
|
+
</li>
|
|
12
|
+
</template>
|