@geniusdynamics/ns8-ui-lib 1.0.6 → 1.0.7
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/dist/ns8-ui-lib.css +1 -1
- package/dist/ns8-ui-lib.es.js +222 -222
- package/dist/ns8-ui-lib.es.js.map +1 -1
- package/dist/ns8-ui-lib.umd.js +3 -3
- package/dist/ns8-ui-lib.umd.js.map +1 -1
- package/package.json +2 -2
- package/src/App.vue +3 -4
- package/src/components/HelloWorld.vue +2 -2
- package/src/components/NS/CompleteDemo.vue +49 -49
- package/src/components/NS/Demo.vue +20 -20
- package/src/components/NS/cards/NSBackupCard.vue +41 -41
- package/src/components/NS/cards/NSSystemInfoCard.vue +37 -37
- package/src/components/NS/cards/NSSystemdServiceCard.vue +27 -27
- package/src/components/NS/checkbox/NSCheckbox.vue +4 -4
- package/src/components/NS/data-table/NSDataTable.vue +29 -29
- package/src/components/NS/empty-state/NSEmptyState.vue +3 -3
- package/src/components/NS/inline-notification/NSInlineNotification.vue +9 -9
- package/src/components/NS/lottie-animation/NSLottieAnimation.vue +5 -5
- package/src/components/NS/modal/NSModal.vue +10 -10
- package/src/components/NS/modal/NSModalTrigger.vue +1 -1
- package/src/components/NS/pagination/NSPagination.vue +10 -10
- package/src/components/NS/progress/NSProgress.vue +3 -3
- package/src/components/NS/progress/NSProgressBar.vue +4 -4
- package/src/components/NS/slider/NSByteSlider.vue +3 -3
- package/src/components/NS/slider/NSSlider.vue +2 -2
- package/src/components/NS/tag/NSTag.vue +5 -5
- package/src/components/NS/text-input/NSTextInput.vue +5 -5
- package/src/components/NS/toast-notification/NSToastNotification.vue +7 -7
- package/src/components/NS/toggle/NSToggle.vue +2 -2
- package/src/components/NS/wizard/NSWizard.vue +21 -21
- package/src/components/ui/accordion/AccordionContent.vue +2 -2
- package/src/components/ui/accordion/AccordionItem.vue +1 -1
- package/src/components/ui/accordion/AccordionTrigger.vue +3 -3
- package/src/components/ui/alert/AlertDescription.vue +1 -1
- package/src/components/ui/alert/AlertTitle.vue +1 -1
- package/src/components/ui/alert-dialog/AlertDialogCancel.vue +1 -1
- package/src/components/ui/alert-dialog/AlertDialogContent.vue +2 -2
- package/src/components/ui/alert-dialog/AlertDialogDescription.vue +1 -1
- package/src/components/ui/alert-dialog/AlertDialogFooter.vue +1 -1
- package/src/components/ui/alert-dialog/AlertDialogHeader.vue +1 -1
- package/src/components/ui/alert-dialog/AlertDialogTitle.vue +1 -1
- package/src/components/ui/avatar/Avatar.vue +1 -1
- package/src/components/ui/avatar/AvatarFallback.vue +1 -1
- package/src/components/ui/avatar/AvatarImage.vue +1 -1
- package/src/components/ui/breadcrumb/BreadcrumbEllipsis.vue +3 -3
- package/src/components/ui/breadcrumb/BreadcrumbItem.vue +1 -1
- package/src/components/ui/breadcrumb/BreadcrumbLink.vue +1 -1
- package/src/components/ui/breadcrumb/BreadcrumbList.vue +1 -1
- package/src/components/ui/breadcrumb/BreadcrumbPage.vue +1 -1
- package/src/components/ui/breadcrumb/BreadcrumbSeparator.vue +1 -1
- package/src/components/ui/button-group/ButtonGroupSeparator.vue +1 -1
- package/src/components/ui/button-group/ButtonGroupText.vue +1 -1
- package/src/components/ui/calendar/Calendar.vue +16 -16
- package/src/components/ui/calendar/CalendarCell.vue +1 -1
- package/src/components/ui/calendar/CalendarCellTrigger.vue +6 -6
- package/src/components/ui/calendar/CalendarGrid.vue +1 -1
- package/src/components/ui/calendar/CalendarGridRow.vue +1 -1
- package/src/components/ui/calendar/CalendarHeadCell.vue +1 -1
- package/src/components/ui/calendar/CalendarHeader.vue +1 -1
- package/src/components/ui/calendar/CalendarHeading.vue +1 -1
- package/src/components/ui/calendar/CalendarNextButton.vue +2 -2
- package/src/components/ui/calendar/CalendarPrevButton.vue +2 -2
- package/src/components/ui/card/Card.vue +1 -1
- package/src/components/ui/card/CardAction.vue +1 -1
- package/src/components/ui/card/CardContent.vue +1 -1
- package/src/components/ui/card/CardDescription.vue +1 -1
- package/src/components/ui/card/CardFooter.vue +1 -1
- package/src/components/ui/card/CardHeader.vue +1 -1
- package/src/components/ui/card/CardTitle.vue +1 -1
- package/src/components/ui/carousel/Carousel.vue +1 -1
- package/src/components/ui/carousel/CarouselContent.vue +3 -3
- package/src/components/ui/carousel/CarouselItem.vue +2 -2
- package/src/components/ui/carousel/CarouselNext.vue +4 -4
- package/src/components/ui/carousel/CarouselPrevious.vue +4 -4
- package/src/components/ui/checkbox/Checkbox.vue +3 -3
- package/src/components/ui/combobox/ComboboxAnchor.vue +1 -1
- package/src/components/ui/combobox/ComboboxEmpty.vue +1 -1
- package/src/components/ui/combobox/ComboboxGroup.vue +2 -2
- package/src/components/ui/combobox/ComboboxInput.vue +3 -3
- package/src/components/ui/combobox/ComboboxItem.vue +1 -1
- package/src/components/ui/combobox/ComboboxItemIndicator.vue +1 -1
- package/src/components/ui/combobox/ComboboxList.vue +1 -1
- package/src/components/ui/combobox/ComboboxSeparator.vue +1 -1
- package/src/components/ui/combobox/ComboboxTrigger.vue +1 -1
- package/src/components/ui/combobox/ComboboxViewport.vue +1 -1
- package/src/components/ui/command/Command.vue +1 -1
- package/src/components/ui/command/CommandDialog.vue +2 -2
- package/src/components/ui/command/CommandEmpty.vue +1 -1
- package/src/components/ui/command/CommandGroup.vue +2 -2
- package/src/components/ui/command/CommandInput.vue +3 -3
- package/src/components/ui/command/CommandItem.vue +1 -1
- package/src/components/ui/command/CommandList.vue +1 -1
- package/src/components/ui/command/CommandSeparator.vue +1 -1
- package/src/components/ui/command/CommandShortcut.vue +1 -1
- package/src/components/ui/context-menu/ContextMenuCheckboxItem.vue +3 -3
- package/src/components/ui/context-menu/ContextMenuContent.vue +1 -1
- package/src/components/ui/context-menu/ContextMenuItem.vue +1 -1
- package/src/components/ui/context-menu/ContextMenuLabel.vue +1 -1
- package/src/components/ui/context-menu/ContextMenuRadioItem.vue +3 -3
- package/src/components/ui/context-menu/ContextMenuSeparator.vue +1 -1
- package/src/components/ui/context-menu/ContextMenuShortcut.vue +1 -1
- package/src/components/ui/context-menu/ContextMenuSubContent.vue +1 -1
- package/src/components/ui/context-menu/ContextMenuSubTrigger.vue +2 -2
- package/src/components/ui/dialog/DialogContent.vue +18 -27
- package/src/components/ui/dialog/DialogDescription.vue +1 -1
- package/src/components/ui/dialog/DialogFooter.vue +1 -1
- package/src/components/ui/dialog/DialogHeader.vue +1 -1
- package/src/components/ui/dialog/DialogOverlay.vue +1 -1
- package/src/components/ui/dialog/DialogScrollContent.vue +5 -5
- package/src/components/ui/dialog/DialogTitle.vue +1 -1
- package/src/components/ui/drawer/DrawerContent.vue +6 -6
- package/src/components/ui/drawer/DrawerDescription.vue +1 -1
- package/src/components/ui/drawer/DrawerFooter.vue +1 -1
- package/src/components/ui/drawer/DrawerHeader.vue +1 -1
- package/src/components/ui/drawer/DrawerOverlay.vue +1 -1
- package/src/components/ui/drawer/DrawerTitle.vue +1 -1
- package/src/components/ui/dropdown-menu/DropdownMenuCheckboxItem.vue +3 -3
- package/src/components/ui/dropdown-menu/DropdownMenuContent.vue +1 -1
- package/src/components/ui/dropdown-menu/DropdownMenuItem.vue +1 -1
- package/src/components/ui/dropdown-menu/DropdownMenuLabel.vue +1 -1
- package/src/components/ui/dropdown-menu/DropdownMenuRadioItem.vue +3 -3
- package/src/components/ui/dropdown-menu/DropdownMenuSeparator.vue +1 -1
- package/src/components/ui/dropdown-menu/DropdownMenuShortcut.vue +1 -1
- package/src/components/ui/dropdown-menu/DropdownMenuSubContent.vue +1 -1
- package/src/components/ui/dropdown-menu/DropdownMenuSubTrigger.vue +2 -2
- package/src/components/ui/empty/Empty.vue +1 -1
- package/src/components/ui/empty/EmptyContent.vue +1 -1
- package/src/components/ui/empty/EmptyDescription.vue +2 -2
- package/src/components/ui/empty/EmptyHeader.vue +1 -1
- package/src/components/ui/empty/EmptyTitle.vue +1 -1
- package/src/components/ui/field/FieldContent.vue +1 -1
- package/src/components/ui/field/FieldDescription.vue +3 -3
- package/src/components/ui/field/FieldError.vue +2 -2
- package/src/components/ui/field/FieldGroup.vue +1 -1
- package/src/components/ui/field/FieldLabel.vue +3 -3
- package/src/components/ui/field/FieldLegend.vue +3 -3
- package/src/components/ui/field/FieldSeparator.vue +3 -3
- package/src/components/ui/field/FieldSet.vue +2 -2
- package/src/components/ui/field/FieldTitle.vue +1 -1
- package/src/components/ui/form/FormDescription.vue +1 -1
- package/src/components/ui/form/FormItem.vue +1 -1
- package/src/components/ui/form/FormLabel.vue +1 -1
- package/src/components/ui/form/FormMessage.vue +1 -1
- package/src/components/ui/hover-card/HoverCardContent.vue +1 -1
- package/src/components/ui/input/Input.vue +3 -3
- package/src/components/ui/input-group/InputGroup.vue +8 -8
- package/src/components/ui/input-group/InputGroupInput.vue +1 -1
- package/src/components/ui/input-group/InputGroupText.vue +1 -1
- package/src/components/ui/input-group/InputGroupTextarea.vue +1 -1
- package/src/components/ui/input-otp/InputOTP.vue +1 -1
- package/src/components/ui/input-otp/InputOTPGroup.vue +1 -1
- package/src/components/ui/input-otp/InputOTPSlot.vue +3 -3
- package/src/components/ui/item/ItemActions.vue +1 -1
- package/src/components/ui/item/ItemContent.vue +1 -1
- package/src/components/ui/item/ItemDescription.vue +2 -2
- package/src/components/ui/item/ItemFooter.vue +1 -1
- package/src/components/ui/item/ItemGroup.vue +1 -1
- package/src/components/ui/item/ItemHeader.vue +1 -1
- package/src/components/ui/item/ItemSeparator.vue +1 -1
- package/src/components/ui/item/ItemTitle.vue +1 -1
- package/src/components/ui/kbd/Kbd.vue +3 -3
- package/src/components/ui/kbd/KbdGroup.vue +1 -1
- package/src/components/ui/label/Label.vue +1 -1
- package/src/components/ui/menubar/Menubar.vue +1 -1
- package/src/components/ui/menubar/MenubarCheckboxItem.vue +3 -3
- package/src/components/ui/menubar/MenubarContent.vue +1 -1
- package/src/components/ui/menubar/MenubarItem.vue +1 -1
- package/src/components/ui/menubar/MenubarLabel.vue +1 -1
- package/src/components/ui/menubar/MenubarRadioItem.vue +3 -3
- package/src/components/ui/menubar/MenubarSeparator.vue +1 -1
- package/src/components/ui/menubar/MenubarShortcut.vue +1 -1
- package/src/components/ui/menubar/MenubarSubContent.vue +1 -1
- package/src/components/ui/menubar/MenubarSubTrigger.vue +2 -2
- package/src/components/ui/menubar/MenubarTrigger.vue +1 -1
- package/src/components/ui/native-select/NativeSelect.vue +5 -5
- package/src/components/ui/native-select/NativeSelectOptGroup.vue +1 -1
- package/src/components/ui/native-select/NativeSelectOption.vue +1 -1
- package/src/components/ui/navigation-menu/NavigationMenu.vue +1 -1
- package/src/components/ui/navigation-menu/NavigationMenuContent.vue +2 -2
- package/src/components/ui/navigation-menu/NavigationMenuIndicator.vue +2 -2
- package/src/components/ui/navigation-menu/NavigationMenuItem.vue +1 -1
- package/src/components/ui/navigation-menu/NavigationMenuLink.vue +1 -1
- package/src/components/ui/navigation-menu/NavigationMenuList.vue +1 -1
- package/src/components/ui/navigation-menu/NavigationMenuTrigger.vue +2 -2
- package/src/components/ui/navigation-menu/NavigationMenuViewport.vue +2 -2
- package/src/components/ui/number-field/NumberField.vue +1 -1
- package/src/components/ui/number-field/NumberFieldContent.vue +1 -1
- package/src/components/ui/number-field/NumberFieldDecrement.vue +2 -2
- package/src/components/ui/number-field/NumberFieldIncrement.vue +2 -2
- package/src/components/ui/number-field/NumberFieldInput.vue +1 -1
- package/src/components/ui/pagination/Pagination.vue +1 -1
- package/src/components/ui/pagination/PaginationContent.vue +1 -1
- package/src/components/ui/pagination/PaginationEllipsis.vue +3 -3
- package/src/components/ui/pagination/PaginationFirst.vue +2 -2
- package/src/components/ui/pagination/PaginationLast.vue +2 -2
- package/src/components/ui/pagination/PaginationNext.vue +2 -2
- package/src/components/ui/pagination/PaginationPrevious.vue +2 -2
- package/src/components/ui/pin-input/PinInput.vue +1 -1
- package/src/components/ui/pin-input/PinInputGroup.vue +1 -1
- package/src/components/ui/pin-input/PinInputSlot.vue +1 -1
- package/src/components/ui/popover/PopoverContent.vue +1 -1
- package/src/components/ui/progress/Progress.vue +12 -9
- package/src/components/ui/radio-group/RadioGroup.vue +1 -1
- package/src/components/ui/radio-group/RadioGroupItem.vue +16 -16
- package/src/components/ui/range-calendar/RangeCalendar.vue +4 -4
- package/src/components/ui/range-calendar/RangeCalendarCell.vue +1 -1
- package/src/components/ui/range-calendar/RangeCalendarCellTrigger.vue +7 -7
- package/src/components/ui/range-calendar/RangeCalendarGrid.vue +1 -1
- package/src/components/ui/range-calendar/RangeCalendarGridRow.vue +1 -1
- package/src/components/ui/range-calendar/RangeCalendarHeadCell.vue +1 -1
- package/src/components/ui/range-calendar/RangeCalendarHeader.vue +1 -1
- package/src/components/ui/range-calendar/RangeCalendarHeading.vue +1 -1
- package/src/components/ui/range-calendar/RangeCalendarNextButton.vue +3 -3
- package/src/components/ui/range-calendar/RangeCalendarPrevButton.vue +3 -3
- package/src/components/ui/resizable/ResizableHandle.vue +3 -3
- package/src/components/ui/resizable/ResizablePanelGroup.vue +1 -1
- package/src/components/ui/scroll-area/ScrollArea.vue +2 -2
- package/src/components/ui/scroll-area/ScrollBar.vue +16 -22
- package/src/components/ui/select/SelectContent.vue +18 -27
- package/src/components/ui/select/SelectItem.vue +3 -3
- package/src/components/ui/select/SelectLabel.vue +1 -1
- package/src/components/ui/select/SelectScrollDownButton.vue +2 -2
- package/src/components/ui/select/SelectScrollUpButton.vue +2 -2
- package/src/components/ui/select/SelectSeparator.vue +1 -1
- package/src/components/ui/select/SelectTrigger.vue +2 -2
- package/src/components/ui/separator/Separator.vue +1 -1
- package/src/components/ui/sheet/SheetContent.vue +28 -31
- package/src/components/ui/sheet/SheetDescription.vue +1 -1
- package/src/components/ui/sheet/SheetFooter.vue +1 -1
- package/src/components/ui/sheet/SheetHeader.vue +1 -1
- package/src/components/ui/sheet/SheetOverlay.vue +1 -1
- package/src/components/ui/sheet/SheetTitle.vue +1 -1
- package/src/components/ui/sidebar/Sidebar.vue +16 -16
- package/src/components/ui/sidebar/SidebarContent.vue +1 -1
- package/src/components/ui/sidebar/SidebarFooter.vue +1 -1
- package/src/components/ui/sidebar/SidebarGroup.vue +1 -1
- package/src/components/ui/sidebar/SidebarGroupAction.vue +3 -3
- package/src/components/ui/sidebar/SidebarGroupContent.vue +1 -1
- package/src/components/ui/sidebar/SidebarGroupLabel.vue +2 -2
- package/src/components/ui/sidebar/SidebarHeader.vue +1 -1
- package/src/components/ui/sidebar/SidebarInput.vue +1 -1
- package/src/components/ui/sidebar/SidebarInset.vue +2 -2
- package/src/components/ui/sidebar/SidebarMenu.vue +1 -1
- package/src/components/ui/sidebar/SidebarMenuAction.vue +7 -7
- package/src/components/ui/sidebar/SidebarMenuBadge.vue +6 -6
- package/src/components/ui/sidebar/SidebarMenuItem.vue +1 -1
- package/src/components/ui/sidebar/SidebarMenuSkeleton.vue +3 -3
- package/src/components/ui/sidebar/SidebarMenuSub.vue +2 -2
- package/src/components/ui/sidebar/SidebarMenuSubButton.vue +5 -5
- package/src/components/ui/sidebar/SidebarMenuSubItem.vue +1 -1
- package/src/components/ui/sidebar/SidebarProvider.vue +1 -1
- package/src/components/ui/sidebar/SidebarRail.vue +6 -6
- package/src/components/ui/sidebar/SidebarSeparator.vue +1 -1
- package/src/components/ui/sidebar/SidebarTrigger.vue +2 -2
- package/src/components/ui/skeleton/Skeleton.vue +1 -1
- package/src/components/ui/slider/Slider.vue +4 -4
- package/src/components/ui/sonner/Sonner.vue +7 -7
- package/src/components/ui/spinner/Spinner.vue +1 -1
- package/src/components/ui/stepper/Stepper.vue +1 -1
- package/src/components/ui/stepper/StepperDescription.vue +1 -1
- package/src/components/ui/stepper/StepperIndicator.vue +4 -4
- package/src/components/ui/stepper/StepperItem.vue +1 -1
- package/src/components/ui/stepper/StepperSeparator.vue +3 -3
- package/src/components/ui/stepper/StepperTitle.vue +1 -1
- package/src/components/ui/stepper/StepperTrigger.vue +1 -1
- package/src/components/ui/switch/Switch.vue +2 -2
- package/src/components/ui/table/Table.vue +6 -12
- package/src/components/ui/table/TableBody.vue +1 -1
- package/src/components/ui/table/TableCaption.vue +1 -1
- package/src/components/ui/table/TableCell.vue +1 -1
- package/src/components/ui/table/TableEmpty.vue +14 -17
- package/src/components/ui/table/TableFooter.vue +1 -1
- package/src/components/ui/table/TableHead.vue +1 -1
- package/src/components/ui/table/TableHeader.vue +1 -1
- package/src/components/ui/table/TableRow.vue +1 -1
- package/src/components/ui/tabs/Tabs.vue +1 -1
- package/src/components/ui/tabs/TabsContent.vue +1 -1
- package/src/components/ui/tabs/TabsList.vue +1 -1
- package/src/components/ui/tabs/TabsTrigger.vue +1 -1
- package/src/components/ui/tags-input/TagsInput.vue +3 -3
- package/src/components/ui/tags-input/TagsInputInput.vue +1 -1
- package/src/components/ui/tags-input/TagsInputItem.vue +1 -1
- package/src/components/ui/tags-input/TagsInputItemDelete.vue +2 -2
- package/src/components/ui/tags-input/TagsInputItemText.vue +1 -1
- package/src/components/ui/textarea/Textarea.vue +1 -1
- package/src/components/ui/toggle-group/ToggleGroup.vue +1 -1
- package/src/components/ui/toggle-group/ToggleGroupItem.vue +2 -2
- package/src/components/ui/tooltip/TooltipContent.vue +2 -2
- package/src/components/ui/checkbox/NsCheckbox.vue +0 -123
- package/src/components/ui/empty-state/NsEmptyState.vue +0 -149
- package/src/components/ui/inline-notification/NsInlineNotification.vue +0 -163
- package/src/components/ui/tag/NsTag.vue +0 -114
- package/src/components/ui/text-input/NsTextInput.vue +0 -269
- package/src/components/ui/toggle/NsToggle.vue +0 -126
|
@@ -136,11 +136,11 @@ const metricsGridClasses = computed(() => {
|
|
|
136
136
|
|
|
137
137
|
<template>
|
|
138
138
|
<Card :class="cardClasses">
|
|
139
|
-
<CardHeader class="
|
|
140
|
-
<div class="
|
|
139
|
+
<CardHeader class="pb-3">
|
|
140
|
+
<div class="flex items-center justify-between">
|
|
141
141
|
<div>
|
|
142
|
-
<CardTitle class="
|
|
143
|
-
<Activity class="
|
|
142
|
+
<CardTitle class="flex items-center gap-2">
|
|
143
|
+
<Activity class="h-5 w-5 text-primary" />
|
|
144
144
|
{{ title }}
|
|
145
145
|
</CardTitle>
|
|
146
146
|
<CardDescription>
|
|
@@ -155,56 +155,56 @@ const metricsGridClasses = computed(() => {
|
|
|
155
155
|
size="sm"
|
|
156
156
|
@click="emit('refresh')"
|
|
157
157
|
>
|
|
158
|
-
<Clock class="
|
|
158
|
+
<Clock class="h-4 w-4" />
|
|
159
159
|
</Button>
|
|
160
160
|
</div>
|
|
161
161
|
</CardHeader>
|
|
162
162
|
|
|
163
|
-
<CardContent class="
|
|
163
|
+
<CardContent class="space-y-4">
|
|
164
164
|
<!-- Loading state -->
|
|
165
|
-
<div v-if="loading" class="
|
|
166
|
-
<div class="
|
|
167
|
-
<div class="
|
|
168
|
-
<div class="
|
|
169
|
-
<div class="
|
|
165
|
+
<div v-if="loading" class="space-y-3">
|
|
166
|
+
<div class="space-y-2">
|
|
167
|
+
<div class="h-2 bg-secondary rounded-full" />
|
|
168
|
+
<div class="h-2 bg-secondary rounded-full" />
|
|
169
|
+
<div class="h-2 bg-secondary rounded-full" />
|
|
170
170
|
</div>
|
|
171
171
|
</div>
|
|
172
172
|
|
|
173
173
|
<!-- System metrics -->
|
|
174
174
|
<div v-else-if="hasMetrics" :class="metricsGridClasses">
|
|
175
175
|
<!-- Storage metrics -->
|
|
176
|
-
<div v-if="showStorage" class="
|
|
176
|
+
<div v-if="showStorage" class="space-y-2">
|
|
177
177
|
<div
|
|
178
|
-
class="
|
|
178
|
+
class="flex items-center gap-2 text-sm font-medium"
|
|
179
179
|
>
|
|
180
|
-
<HardDrive class="
|
|
180
|
+
<HardDrive class="h-4 w-4" />
|
|
181
181
|
Storage
|
|
182
182
|
</div>
|
|
183
183
|
<Progress
|
|
184
184
|
:value="metrics.usagePercentage"
|
|
185
185
|
:variant="storageVariant"
|
|
186
|
-
class="
|
|
186
|
+
class="mb-2"
|
|
187
187
|
/>
|
|
188
|
-
<div class="
|
|
188
|
+
<div class="text-xs text-muted-foreground space-y-1">
|
|
189
189
|
<div>Used: {{ metrics.usedSpace }} / {{ metrics.totalSpace }}</div>
|
|
190
190
|
<div>Free: {{ metrics.freeSpace }}</div>
|
|
191
191
|
</div>
|
|
192
192
|
</div>
|
|
193
193
|
|
|
194
194
|
<!-- Memory metrics -->
|
|
195
|
-
<div v-if="showMemory && metrics?.memory" class="
|
|
195
|
+
<div v-if="showMemory && metrics?.memory" class="space-y-2">
|
|
196
196
|
<div
|
|
197
|
-
class="
|
|
197
|
+
class="flex items-center gap-2 text-sm font-medium"
|
|
198
198
|
>
|
|
199
|
-
<Activity class="
|
|
199
|
+
<Activity class="h-4 w-4" />
|
|
200
200
|
Memory
|
|
201
201
|
</div>
|
|
202
202
|
<Progress
|
|
203
203
|
:value="metrics.memory.percentage"
|
|
204
204
|
:variant="memoryVariant"
|
|
205
|
-
class="
|
|
205
|
+
class="mb-2"
|
|
206
206
|
/>
|
|
207
|
-
<div class="
|
|
207
|
+
<div class="text-xs text-muted-foreground space-y-1">
|
|
208
208
|
<div>
|
|
209
209
|
Used: {{ metrics.memory.used }} / {{ metrics.memory.total }}
|
|
210
210
|
</div>
|
|
@@ -213,19 +213,19 @@ const metricsGridClasses = computed(() => {
|
|
|
213
213
|
</div>
|
|
214
214
|
|
|
215
215
|
<!-- CPU metrics -->
|
|
216
|
-
<div v-if="showCpu && metrics?.cpu" class="
|
|
216
|
+
<div v-if="showCpu && metrics?.cpu" class="space-y-2">
|
|
217
217
|
<div
|
|
218
|
-
class="
|
|
218
|
+
class="flex items-center gap-2 text-sm font-medium"
|
|
219
219
|
>
|
|
220
|
-
<Activity class="
|
|
220
|
+
<Activity class="h-4 w-4" />
|
|
221
221
|
CPU
|
|
222
222
|
</div>
|
|
223
223
|
<Progress
|
|
224
224
|
:value="metrics.cpu.usage"
|
|
225
225
|
:variant="cpuVariant"
|
|
226
|
-
class="
|
|
226
|
+
class="mb-2"
|
|
227
227
|
/>
|
|
228
|
-
<div class="
|
|
228
|
+
<div class="text-xs text-muted-foreground space-y-1">
|
|
229
229
|
<div>Usage: {{ metrics.cpu.usage }}%</div>
|
|
230
230
|
<div>Cores: {{ metrics.cpu.cores }}</div>
|
|
231
231
|
<div v-if="metrics.cpu.frequency">
|
|
@@ -238,41 +238,41 @@ const metricsGridClasses = computed(() => {
|
|
|
238
238
|
<!-- Additional system info -->
|
|
239
239
|
<div
|
|
240
240
|
v-if="hasMetrics"
|
|
241
|
-
class="
|
|
241
|
+
class="grid grid-cols-1 md:grid-cols-2 lg:grid-cols-4 gap-3 pt-4 border-t"
|
|
242
242
|
>
|
|
243
243
|
<!-- Temperature -->
|
|
244
244
|
<div v-if="showTemperature && metrics?.temperature">
|
|
245
|
-
<div class="
|
|
246
|
-
<div class="
|
|
245
|
+
<div class="text-xs text-muted-foreground">Temperature</div>
|
|
246
|
+
<div class="text-sm font-medium">{{ metrics.temperature }}</div>
|
|
247
247
|
</div>
|
|
248
248
|
|
|
249
249
|
<!-- Load average -->
|
|
250
250
|
<div v-if="showLoadAverage && metrics?.loadAverage">
|
|
251
|
-
<div class="
|
|
252
|
-
<div class="
|
|
251
|
+
<div class="text-xs text-muted-foreground">Load Average</div>
|
|
252
|
+
<div class="text-sm font-medium">
|
|
253
253
|
{{ metrics.loadAverage.join(", ") }}
|
|
254
254
|
</div>
|
|
255
255
|
</div>
|
|
256
256
|
|
|
257
257
|
<!-- Uptime -->
|
|
258
258
|
<div v-if="showUptime && metrics?.uptime">
|
|
259
|
-
<div class="
|
|
260
|
-
<div class="
|
|
259
|
+
<div class="text-xs text-muted-foreground">Uptime</div>
|
|
260
|
+
<div class="text-sm font-medium">{{ metrics.uptime }}</div>
|
|
261
261
|
</div>
|
|
262
262
|
|
|
263
263
|
<!-- Processes -->
|
|
264
264
|
<div v-if="showProcesses && metrics?.processes">
|
|
265
|
-
<div class="
|
|
266
|
-
<div class="
|
|
265
|
+
<div class="text-xs text-muted-foreground">Processes</div>
|
|
266
|
+
<div class="text-sm font-medium">{{ metrics.processes }}</div>
|
|
267
267
|
</div>
|
|
268
268
|
</div>
|
|
269
269
|
|
|
270
270
|
<!-- No data state -->
|
|
271
271
|
<div
|
|
272
272
|
v-if="!hasMetrics && !loading"
|
|
273
|
-
class="
|
|
273
|
+
class="flex items-center gap-3 text-muted-foreground"
|
|
274
274
|
>
|
|
275
|
-
<AlertCircle class="
|
|
275
|
+
<AlertCircle class="h-5 w-5" />
|
|
276
276
|
<span>No system metrics available</span>
|
|
277
277
|
</div>
|
|
278
278
|
</CardContent>
|
|
@@ -125,16 +125,16 @@ const iconClass = computed(() => {
|
|
|
125
125
|
|
|
126
126
|
<template>
|
|
127
127
|
<Card :class="cardClasses">
|
|
128
|
-
<CardHeader class="
|
|
129
|
-
<div class="
|
|
130
|
-
<CardTitle class="
|
|
128
|
+
<CardHeader class="pb-3">
|
|
129
|
+
<div class="flex items-center justify-between">
|
|
130
|
+
<CardTitle class="flex items-center gap-3">
|
|
131
131
|
<component
|
|
132
132
|
v-if="icon"
|
|
133
133
|
:is="icon"
|
|
134
134
|
:class="iconClass"
|
|
135
135
|
/>
|
|
136
136
|
<div>
|
|
137
|
-
<div class="
|
|
137
|
+
<div class="text-lg font-semibold">{{ title }}</div>
|
|
138
138
|
<CardDescription v-if="description">
|
|
139
139
|
{{ description }}
|
|
140
140
|
</CardDescription>
|
|
@@ -148,53 +148,53 @@ const iconClass = computed(() => {
|
|
|
148
148
|
</div>
|
|
149
149
|
</CardHeader>
|
|
150
150
|
|
|
151
|
-
<CardContent class="
|
|
151
|
+
<CardContent class="space-y-4">
|
|
152
152
|
<!-- Loading state -->
|
|
153
|
-
<div v-if="loading" class="
|
|
154
|
-
<Skeleton class="
|
|
155
|
-
<Skeleton class="
|
|
156
|
-
<Skeleton class="
|
|
153
|
+
<div v-if="loading" class="space-y-3">
|
|
154
|
+
<Skeleton class="h-4 w-3/4" />
|
|
155
|
+
<Skeleton class="h-4 w-1/2" />
|
|
156
|
+
<Skeleton class="h-4 w-2/3" />
|
|
157
157
|
</div>
|
|
158
158
|
|
|
159
159
|
<!-- Service details -->
|
|
160
|
-
<div v-else class="
|
|
160
|
+
<div v-else class="space-y-3">
|
|
161
161
|
<!-- Service name -->
|
|
162
|
-
<div v-if="serviceName" class="
|
|
163
|
-
<span class="
|
|
162
|
+
<div v-if="serviceName" class="text-sm text-muted-foreground">
|
|
163
|
+
<span class="font-medium">Service:</span> {{ serviceName }}
|
|
164
164
|
</div>
|
|
165
165
|
|
|
166
166
|
<!-- Uptime -->
|
|
167
|
-
<div v-if="showUptime && status?.uptime" class="
|
|
168
|
-
<Clock class="
|
|
169
|
-
<span class="
|
|
170
|
-
<span class="
|
|
167
|
+
<div v-if="showUptime && status?.uptime" class="flex items-center gap-2">
|
|
168
|
+
<Clock class="h-4 w-4 text-muted-foreground" />
|
|
169
|
+
<span class="text-sm">
|
|
170
|
+
<span class="font-medium">Uptime:</span> {{ status.uptime }}
|
|
171
171
|
</span>
|
|
172
172
|
</div>
|
|
173
173
|
|
|
174
174
|
<!-- Last restart -->
|
|
175
|
-
<div v-if="status?.lastRestart" class="
|
|
176
|
-
<span class="
|
|
175
|
+
<div v-if="status?.lastRestart" class="text-sm text-muted-foreground">
|
|
176
|
+
<span class="font-medium">Last restart:</span> {{ status.lastRestart }}
|
|
177
177
|
</div>
|
|
178
178
|
|
|
179
179
|
<!-- Metrics -->
|
|
180
|
-
<div v-if="showMetrics" class="
|
|
181
|
-
<div v-if="status?.memory" class="
|
|
182
|
-
<span class="
|
|
180
|
+
<div v-if="showMetrics" class="grid grid-cols-2 gap-3">
|
|
181
|
+
<div v-if="status?.memory" class="text-sm">
|
|
182
|
+
<span class="font-medium">Memory:</span> {{ status.memory }}
|
|
183
183
|
</div>
|
|
184
|
-
<div v-if="status?.cpu" class="
|
|
185
|
-
<span class="
|
|
184
|
+
<div v-if="status?.cpu" class="text-sm">
|
|
185
|
+
<span class="font-medium">CPU:</span> {{ status.cpu }}
|
|
186
186
|
</div>
|
|
187
187
|
</div>
|
|
188
188
|
|
|
189
189
|
<!-- Custom status message -->
|
|
190
|
-
<div v-if="status?.status && status?.status !== statusText" class="
|
|
190
|
+
<div v-if="status?.status && status?.status !== statusText" class="text-sm">
|
|
191
191
|
{{ status.status }}
|
|
192
192
|
</div>
|
|
193
193
|
</div>
|
|
194
194
|
|
|
195
195
|
<!-- Action buttons -->
|
|
196
|
-
<div class="
|
|
197
|
-
<div class="
|
|
196
|
+
<div class="flex items-center justify-between pt-4 border-t">
|
|
197
|
+
<div class="flex gap-2">
|
|
198
198
|
<Button
|
|
199
199
|
v-if="status?.enabled && !status?.running"
|
|
200
200
|
variant="default"
|
|
@@ -242,7 +242,7 @@ const iconClass = computed(() => {
|
|
|
242
242
|
size="sm"
|
|
243
243
|
@click="emit('view', serviceName)"
|
|
244
244
|
>
|
|
245
|
-
<MoreHorizontal class="
|
|
245
|
+
<MoreHorizontal class="h-4 w-4" />
|
|
246
246
|
</Button>
|
|
247
247
|
</div>
|
|
248
248
|
</CardContent>
|
|
@@ -60,12 +60,12 @@ const isChecked = computed({
|
|
|
60
60
|
'opacity-50': indeterminate
|
|
61
61
|
})"
|
|
62
62
|
>
|
|
63
|
-
<Check v-if="!indeterminate" class="
|
|
64
|
-
<div v-else class="
|
|
63
|
+
<Check v-if="!indeterminate" class="h-4 w-4" />
|
|
64
|
+
<div v-else class="h-1 w-2 bg-current rounded-sm" />
|
|
65
65
|
</CheckboxIndicator>
|
|
66
66
|
</CheckboxRoot>
|
|
67
67
|
|
|
68
|
-
<div class="
|
|
68
|
+
<div class="grid gap-1.5">
|
|
69
69
|
<label
|
|
70
70
|
v-if="label || $slots.label"
|
|
71
71
|
:for="checkboxId"
|
|
@@ -91,7 +91,7 @@ const isChecked = computed({
|
|
|
91
91
|
|
|
92
92
|
<p
|
|
93
93
|
v-if="errorMessage"
|
|
94
|
-
class="
|
|
94
|
+
class="text-sm text-destructive"
|
|
95
95
|
>
|
|
96
96
|
{{ errorMessage }}
|
|
97
97
|
</p>
|
|
@@ -237,52 +237,52 @@ watch(() => props.currentPage, () => {
|
|
|
237
237
|
<template>
|
|
238
238
|
<div :class="containerClasses">
|
|
239
239
|
<!-- Header with search and filters -->
|
|
240
|
-
<div class="
|
|
241
|
-
<div class="
|
|
240
|
+
<div class="flex items-center justify-between gap-4 mb-4">
|
|
241
|
+
<div class="flex items-center gap-2">
|
|
242
242
|
<!-- Search -->
|
|
243
|
-
<div v-if="searchable" class="
|
|
244
|
-
<Search class="
|
|
243
|
+
<div v-if="searchable" class="relative">
|
|
244
|
+
<Search class="absolute left-3 top-1/2 transform -translate-y-1/2 h-4 w-4 text-muted-foreground" />
|
|
245
245
|
<Input
|
|
246
246
|
:model-value="searchQuery"
|
|
247
247
|
@update:model-value="handleSearch"
|
|
248
248
|
placeholder="Search..."
|
|
249
|
-
class="
|
|
249
|
+
class="pl-9 w-64"
|
|
250
250
|
/>
|
|
251
251
|
</div>
|
|
252
252
|
|
|
253
253
|
<!-- Filters -->
|
|
254
|
-
<div v-if="filterable" class="
|
|
255
|
-
<Filter class="
|
|
254
|
+
<div v-if="filterable" class="flex items-center gap-2">
|
|
255
|
+
<Filter class="h-4 w-4 text-muted-foreground" />
|
|
256
256
|
<div v-for="column in columns.filter(c => c.filterable)" :key="column.key">
|
|
257
257
|
<Input
|
|
258
258
|
:model-value="filters[column.key]"
|
|
259
259
|
@update:model-value="(value) => handleFilterChange(column.key, value)"
|
|
260
260
|
:placeholder="`Filter ${column.label}...`"
|
|
261
|
-
class="
|
|
261
|
+
class="w-32"
|
|
262
262
|
/>
|
|
263
263
|
</div>
|
|
264
264
|
</div>
|
|
265
265
|
</div>
|
|
266
266
|
|
|
267
267
|
<!-- Total count -->
|
|
268
|
-
<div v-if="showTotal" class="
|
|
268
|
+
<div v-if="showTotal" class="text-sm text-muted-foreground">
|
|
269
269
|
{{ processedData.length }} items total
|
|
270
270
|
</div>
|
|
271
271
|
</div>
|
|
272
272
|
|
|
273
273
|
<!-- Table -->
|
|
274
|
-
<div class="
|
|
274
|
+
<div class="rounded-md border">
|
|
275
275
|
<Table :class="tableClasses">
|
|
276
276
|
<TableHeader :class="headerClasses">
|
|
277
277
|
<TableRow>
|
|
278
278
|
<!-- Select all checkbox -->
|
|
279
|
-
<TableHead v-if="selectable" class="
|
|
279
|
+
<TableHead v-if="selectable" class="w-12">
|
|
280
280
|
<input
|
|
281
281
|
type="checkbox"
|
|
282
282
|
:checked="isAllSelected"
|
|
283
283
|
:indeterminate="isIndeterminate"
|
|
284
284
|
@change="toggleAllSelection"
|
|
285
|
-
class="
|
|
285
|
+
class="rounded border-gray-300"
|
|
286
286
|
/>
|
|
287
287
|
</TableHead>
|
|
288
288
|
|
|
@@ -301,9 +301,9 @@ watch(() => props.currentPage, () => {
|
|
|
301
301
|
:style="{ width: column.width }"
|
|
302
302
|
@click="handleSort(column)"
|
|
303
303
|
>
|
|
304
|
-
<div class="
|
|
304
|
+
<div class="flex items-center gap-1">
|
|
305
305
|
{{ column.label }}
|
|
306
|
-
<div v-if="column.sortable" class="
|
|
306
|
+
<div v-if="column.sortable" class="flex flex-col">
|
|
307
307
|
<ChevronUp
|
|
308
308
|
:class="cn( 'h-3 w-3',
|
|
309
309
|
sortColumn === column.key && sortDirection === 'asc' ? 'text-primary' : 'text-muted-foreground'
|
|
@@ -319,8 +319,8 @@ watch(() => props.currentPage, () => {
|
|
|
319
319
|
</TableHead>
|
|
320
320
|
|
|
321
321
|
<!-- Actions column -->
|
|
322
|
-
<TableHead v-if="actions.length > 0" class="
|
|
323
|
-
<span class="
|
|
322
|
+
<TableHead v-if="actions.length > 0" class="w-16">
|
|
323
|
+
<span class="sr-only">Actions</span>
|
|
324
324
|
</TableHead>
|
|
325
325
|
</TableRow>
|
|
326
326
|
</TableHeader>
|
|
@@ -328,9 +328,9 @@ watch(() => props.currentPage, () => {
|
|
|
328
328
|
<TableBody :class="bodyClasses">
|
|
329
329
|
<!-- Loading state -->
|
|
330
330
|
<TableRow v-if="loading">
|
|
331
|
-
<TableCell :colspan="columns.length + (selectable ? 1 : 0) + (actions.length > 0 ? 1 : 0)" class="
|
|
332
|
-
<div class="
|
|
333
|
-
<div class="
|
|
331
|
+
<TableCell :colspan="columns.length + (selectable ? 1 : 0) + (actions.length > 0 ? 1 : 0)" class="text-center py-8">
|
|
332
|
+
<div class="flex items-center justify-center space-x-2">
|
|
333
|
+
<div class="animate-spin rounded-full h-4 w-4 border-b-2 border-primary"></div>
|
|
334
334
|
<span>{{ loadingMessage }}</span>
|
|
335
335
|
</div>
|
|
336
336
|
</TableCell>
|
|
@@ -338,7 +338,7 @@ watch(() => props.currentPage, () => {
|
|
|
338
338
|
|
|
339
339
|
<!-- Empty state -->
|
|
340
340
|
<TableRow v-else-if="currentPageData.length === 0">
|
|
341
|
-
<TableCell :colspan="columns.length + (selectable ? 1 : 0) + (actions.length > 0 ? 1 : 0)" class="
|
|
341
|
+
<TableCell :colspan="columns.length + (selectable ? 1 : 0) + (actions.length > 0 ? 1 : 0)" class="text-center py-8">
|
|
342
342
|
{{ emptyMessage }}
|
|
343
343
|
</TableCell>
|
|
344
344
|
</TableRow>
|
|
@@ -351,15 +351,15 @@ watch(() => props.currentPage, () => {
|
|
|
351
351
|
:class="{ 'selected': selectedRows.includes(row)
|
|
352
352
|
}"
|
|
353
353
|
@click="handleRowClick(row, index)"
|
|
354
|
-
class="
|
|
354
|
+
class="cursor-pointer"
|
|
355
355
|
>
|
|
356
356
|
<!-- Selection checkbox -->
|
|
357
|
-
<TableCell v-if="selectable" class="
|
|
357
|
+
<TableCell v-if="selectable" class="w-12">
|
|
358
358
|
<input
|
|
359
359
|
type="checkbox"
|
|
360
360
|
:checked="selectedRows.includes(row)"
|
|
361
361
|
@change="toggleSelection(row)"
|
|
362
|
-
class="
|
|
362
|
+
class="rounded border-gray-300"
|
|
363
363
|
/>
|
|
364
364
|
</TableCell>
|
|
365
365
|
|
|
@@ -391,7 +391,7 @@ watch(() => props.currentPage, () => {
|
|
|
391
391
|
|
|
392
392
|
<!-- Actions -->
|
|
393
393
|
<TableCell v-if="actions.length > 0">
|
|
394
|
-
<div class="
|
|
394
|
+
<div class="flex items-center justify-end space-x-1">
|
|
395
395
|
<Button
|
|
396
396
|
v-for="action in actions"
|
|
397
397
|
:key="action.key"
|
|
@@ -400,7 +400,7 @@ watch(() => props.currentPage, () => {
|
|
|
400
400
|
:disabled="action.disabled ? action.disabled(row) : false"
|
|
401
401
|
@click.stop="action.onClick(row, index)"
|
|
402
402
|
>
|
|
403
|
-
<component v-if="action.icon" :is="action.icon" class="
|
|
403
|
+
<component v-if="action.icon" :is="action.icon" class="h-4 w-4" />
|
|
404
404
|
{{ action.label }}
|
|
405
405
|
</Button>
|
|
406
406
|
</div>
|
|
@@ -411,14 +411,14 @@ watch(() => props.currentPage, () => {
|
|
|
411
411
|
</div>
|
|
412
412
|
|
|
413
413
|
<!-- Pagination -->
|
|
414
|
-
<div v-if="pagination" class="
|
|
414
|
+
<div v-if="pagination" class="mt-4">
|
|
415
415
|
<slot name="pagination" :current-page="currentPage" :total-items="processedData.length">
|
|
416
416
|
<!-- Built-in pagination placeholder -->
|
|
417
|
-
<div class="
|
|
418
|
-
<div class="
|
|
417
|
+
<div class="flex items-center justify-between">
|
|
418
|
+
<div class="text-sm text-muted-foreground">
|
|
419
419
|
Showing {{ (currentPage - 1) * itemsPerPage + 1 }} to {{ Math.min(currentPage * itemsPerPage, processedData.length) }} of {{ processedData.length }} items
|
|
420
420
|
</div>
|
|
421
|
-
<div class="
|
|
421
|
+
<div class="text-sm text-muted-foreground">
|
|
422
422
|
Page {{ currentPage }} of {{ Math.ceil(processedData.length / itemsPerPage) }}
|
|
423
423
|
</div>
|
|
424
424
|
</div>
|
|
@@ -148,7 +148,7 @@ const descriptionClasses = computed(() => {
|
|
|
148
148
|
<template>
|
|
149
149
|
<div :class="containerClasses">
|
|
150
150
|
<!-- Icon section -->
|
|
151
|
-
<div class="
|
|
151
|
+
<div class="mb-4">
|
|
152
152
|
<slot name="icon">
|
|
153
153
|
<!-- Lottie animation if provided -->
|
|
154
154
|
<NSLottieAnimation
|
|
@@ -185,12 +185,12 @@ const descriptionClasses = computed(() => {
|
|
|
185
185
|
</div>
|
|
186
186
|
|
|
187
187
|
<!-- Actions section -->
|
|
188
|
-
<div v-if="$slots.actions" class="
|
|
188
|
+
<div v-if="$slots.actions" class="mt-4">
|
|
189
189
|
<slot name="actions" />
|
|
190
190
|
</div>
|
|
191
191
|
|
|
192
192
|
<!-- Extra content section -->
|
|
193
|
-
<div v-if="$slots.extra" class="
|
|
193
|
+
<div v-if="$slots.extra" class="mt-6">
|
|
194
194
|
<slot name="extra" />
|
|
195
195
|
</div>
|
|
196
196
|
</div>
|
|
@@ -96,30 +96,30 @@ const showCloseButtonVisible = computed(() => props.showCloseButton && !hasLoadi
|
|
|
96
96
|
<!-- Icon -->
|
|
97
97
|
<component
|
|
98
98
|
:is="NotificationIcon"
|
|
99
|
-
class="
|
|
99
|
+
class="h-4 w-4"
|
|
100
100
|
/>
|
|
101
101
|
|
|
102
102
|
<!-- Loading spinner -->
|
|
103
103
|
<Loader2
|
|
104
104
|
v-if="loading"
|
|
105
|
-
class="
|
|
105
|
+
class="h-4 w-4 animate-spin absolute right-12 top-4"
|
|
106
106
|
/>
|
|
107
107
|
|
|
108
108
|
<!-- Timer circle -->
|
|
109
109
|
<div
|
|
110
110
|
v-if="timer"
|
|
111
|
-
class="
|
|
111
|
+
class="h-4 w-4 absolute right-12 top-4"
|
|
112
112
|
>
|
|
113
113
|
<!-- You can integrate NSCircleTimer component here -->
|
|
114
|
-
<div class="
|
|
114
|
+
<div class="h-4 w-4 rounded-full border-2 border-current animate-pulse" />
|
|
115
115
|
</div>
|
|
116
116
|
|
|
117
117
|
<!-- Content -->
|
|
118
|
-
<div class="
|
|
118
|
+
<div class="grid gap-1">
|
|
119
119
|
<!-- Title -->
|
|
120
120
|
<h4
|
|
121
121
|
v-if="hasTitle"
|
|
122
|
-
class="
|
|
122
|
+
class="text-sm font-medium leading-none"
|
|
123
123
|
>
|
|
124
124
|
<slot name="title">{{ title }}</slot>
|
|
125
125
|
</h4>
|
|
@@ -138,7 +138,7 @@ const showCloseButtonVisible = computed(() => props.showCloseButton && !hasLoadi
|
|
|
138
138
|
<button
|
|
139
139
|
v-if="hasAction"
|
|
140
140
|
type="button"
|
|
141
|
-
class="
|
|
141
|
+
class="inline-flex items-center text-sm font-medium underline underline-offset-2 hover:no-underline focus:outline-none focus:ring-2 focus:ring-ring focus:ring-offset-2 rounded-sm"
|
|
142
142
|
@click="emit('action')"
|
|
143
143
|
>
|
|
144
144
|
{{ actionLabel }}
|
|
@@ -150,10 +150,10 @@ const showCloseButtonVisible = computed(() => props.showCloseButton && !hasLoadi
|
|
|
150
150
|
v-if="showCloseButtonVisible"
|
|
151
151
|
type="button"
|
|
152
152
|
:aria-label="closeAriaLabel"
|
|
153
|
-
class="
|
|
153
|
+
class="absolute right-4 top-4 rounded-sm opacity-70 ring-offset-background transition-opacity hover:opacity-100 focus:outline-none focus:ring-2 focus:ring-ring focus:ring-offset-2 disabled:pointer-events-none"
|
|
154
154
|
@click="emit('close')"
|
|
155
155
|
>
|
|
156
|
-
<X class="
|
|
156
|
+
<X class="h-4 w-4" />
|
|
157
157
|
</button>
|
|
158
158
|
|
|
159
159
|
<!-- Extra content -->
|
|
@@ -242,12 +242,12 @@ defineExpose({
|
|
|
242
242
|
<!-- Loading placeholder -->
|
|
243
243
|
<div
|
|
244
244
|
v-if="isLoading && !isLoaded"
|
|
245
|
-
class="
|
|
245
|
+
class="flex items-center justify-center h-full"
|
|
246
246
|
>
|
|
247
247
|
<div
|
|
248
|
-
class="
|
|
248
|
+
class="animate-spin rounded-full h-8 w-8 border-b-2 border-primary"
|
|
249
249
|
></div>
|
|
250
|
-
<span v-if="placeholder" class="
|
|
250
|
+
<span v-if="placeholder" class="ml-2 text-sm text-muted-foreground">{{
|
|
251
251
|
placeholder
|
|
252
252
|
}}</span>
|
|
253
253
|
</div>
|
|
@@ -255,9 +255,9 @@ defineExpose({
|
|
|
255
255
|
<!-- Error state -->
|
|
256
256
|
<div
|
|
257
257
|
v-else-if="isError"
|
|
258
|
-
class="
|
|
258
|
+
class="flex items-center justify-center h-full text-destructive"
|
|
259
259
|
>
|
|
260
|
-
<div class="
|
|
260
|
+
<div class="text-sm">{{ error || "Failed to load animation" }}</div>
|
|
261
261
|
</div>
|
|
262
262
|
|
|
263
263
|
<!-- Lottie Animation -->
|
|
@@ -126,42 +126,42 @@ const handleClose = () => {
|
|
|
126
126
|
)"
|
|
127
127
|
>
|
|
128
128
|
<!-- Title and description -->
|
|
129
|
-
<div class="
|
|
129
|
+
<div class="space-y-1">
|
|
130
130
|
<DialogTitle
|
|
131
131
|
v-if="title || $slots.title"
|
|
132
|
-
class="
|
|
132
|
+
class="text-lg font-semibold leading-none tracking-tight"
|
|
133
133
|
>
|
|
134
134
|
<slot name="title">{{ title }}</slot>
|
|
135
135
|
</DialogTitle>
|
|
136
136
|
<DialogDescription
|
|
137
137
|
v-if="description || $slots.description"
|
|
138
|
-
class="
|
|
138
|
+
class="text-sm text-muted-foreground"
|
|
139
139
|
>
|
|
140
140
|
<slot name="description">{{ description }}</slot>
|
|
141
141
|
</DialogDescription>
|
|
142
142
|
</div>
|
|
143
143
|
|
|
144
144
|
<!-- Close button -->
|
|
145
|
-
<div class="
|
|
145
|
+
<div class="flex items-center gap-2">
|
|
146
146
|
<!-- Fullscreen toggle -->
|
|
147
147
|
<button
|
|
148
148
|
v-if="!fullscreen"
|
|
149
149
|
type="button"
|
|
150
|
-
class="
|
|
150
|
+
class="rounded-sm opacity-70 ring-offset-background transition-opacity hover:opacity-100 focus:outline-none focus:ring-2 focus:ring-ring focus:ring-offset-2 disabled:pointer-events-none"
|
|
151
151
|
:title="isFullscreen ? 'Exit fullscreen' : 'Enter fullscreen'"
|
|
152
152
|
@click="isFullscreen = !isFullscreen"
|
|
153
153
|
>
|
|
154
|
-
<Maximize2 v-if="!isFullscreen" class="
|
|
155
|
-
<Minimize2 v-else class="
|
|
154
|
+
<Maximize2 v-if="!isFullscreen" class="h-4 w-4" />
|
|
155
|
+
<Minimize2 v-else class="h-4 w-4" />
|
|
156
156
|
</button>
|
|
157
157
|
|
|
158
158
|
<!-- Close button -->
|
|
159
159
|
<DialogClose
|
|
160
160
|
v-if="showCloseButton && !persistent"
|
|
161
|
-
class="
|
|
161
|
+
class="rounded-sm opacity-70 ring-offset-background transition-opacity hover:opacity-100 focus:outline-none focus:ring-2 focus:ring-ring focus:ring-offset-2 disabled:pointer-events-none"
|
|
162
162
|
>
|
|
163
|
-
<X class="
|
|
164
|
-
<span class="
|
|
163
|
+
<X class="h-4 w-4" />
|
|
164
|
+
<span class="sr-only">Close</span>
|
|
165
165
|
</DialogClose>
|
|
166
166
|
</div>
|
|
167
167
|
</div>
|
|
@@ -59,7 +59,7 @@ const triggerRef = ref<HTMLElement>()
|
|
|
59
59
|
v-if="!$slots.trigger"
|
|
60
60
|
ref="triggerRef"
|
|
61
61
|
@click="isOpen = !isOpen"
|
|
62
|
-
class="
|
|
62
|
+
class="inline-flex items-center justify-center rounded-md text-sm font-medium transition-colors focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring focus-visible:ring-offset-2 disabled:pointer-events-none disabled:opacity-50 bg-primary text-primary-foreground hover:bg-primary/90"
|
|
63
63
|
>
|
|
64
64
|
Open Modal
|
|
65
65
|
</button>
|