aural-ui 2.0.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/LICENSE +21 -0
- package/README.md +456 -0
- package/dist/components/aspect-ratio/AspectRatio.stories.tsx +1327 -0
- package/dist/components/aspect-ratio/index.tsx +10 -0
- package/dist/components/aspect-ratio/meta.ts +8 -0
- package/dist/components/avatar/Avatar.stories.tsx +645 -0
- package/dist/components/avatar/index.tsx +50 -0
- package/dist/components/avatar/meta.ts +8 -0
- package/dist/components/badge/Badge.stories.tsx +169 -0
- package/dist/components/badge/index.tsx +28 -0
- package/dist/components/badge/meta.ts +6 -0
- package/dist/components/banner/Banner.stories.tsx +475 -0
- package/dist/components/banner/index.tsx +256 -0
- package/dist/components/banner/meta.ts +36 -0
- package/dist/components/button/Button.stories.tsx +74 -0
- package/dist/components/button/index.tsx +158 -0
- package/dist/components/button/meta.ts +33 -0
- package/dist/components/card/Card.stories.tsx +377 -0
- package/dist/components/card/index.tsx +85 -0
- package/dist/components/card/meta.ts +14 -0
- package/dist/components/char-count/CharCount.stories.tsx +334 -0
- package/dist/components/char-count/index.tsx +51 -0
- package/dist/components/char-count/meta.ts +13 -0
- package/dist/components/checkbox/Checkbox.stories.tsx +209 -0
- package/dist/components/checkbox/index.tsx +34 -0
- package/dist/components/checkbox/meta.ts +19 -0
- package/dist/components/chip/Chip.stories.tsx +207 -0
- package/dist/components/chip/index.tsx +92 -0
- package/dist/components/chip/meta.ts +17 -0
- package/dist/components/circular-loader/CircularLoader.stories.tsx +741 -0
- package/dist/components/circular-loader/index.tsx +138 -0
- package/dist/components/circular-loader/meta.ts +11 -0
- package/dist/components/collapsible/Collapsible.stories.tsx +319 -0
- package/dist/components/collapsible/index.tsx +158 -0
- package/dist/components/collapsible/meta.ts +22 -0
- package/dist/components/command/Command.stories.tsx +996 -0
- package/dist/components/command/index.tsx +324 -0
- package/dist/components/command/meta.ts +18 -0
- package/dist/components/dialog/Dialog.stories.tsx +963 -0
- package/dist/components/dialog/index.tsx +250 -0
- package/dist/components/dialog/meta.ts +28 -0
- package/dist/components/divider/Divider.stories.tsx +633 -0
- package/dist/components/divider/index.tsx +181 -0
- package/dist/components/divider/meta.ts +12 -0
- package/dist/components/dot-loader/DotLoader.stories.tsx +352 -0
- package/dist/components/dot-loader/index.tsx +78 -0
- package/dist/components/dot-loader/meta.ts +14 -0
- package/dist/components/dropdown/Dropdown.stories.tsx +1210 -0
- package/dist/components/dropdown/index.tsx +479 -0
- package/dist/components/dropdown/meta.ts +21 -0
- package/dist/components/form/Form.stories.tsx +320 -0
- package/dist/components/form/index.tsx +183 -0
- package/dist/components/form/meta.ts +11 -0
- package/dist/components/helper-text/HelperText.stories.tsx +254 -0
- package/dist/components/helper-text/index.tsx +102 -0
- package/dist/components/helper-text/meta.ts +18 -0
- package/dist/components/hover-card/HoverCard.stories.tsx +1328 -0
- package/dist/components/hover-card/index.tsx +42 -0
- package/dist/components/hover-card/meta.ts +12 -0
- package/dist/components/icon-button/IconButton.stories.tsx +252 -0
- package/dist/components/icon-button/index.tsx +130 -0
- package/dist/components/icon-button/meta.ts +20 -0
- package/dist/components/if-else/if-else.stories.tsx +100 -0
- package/dist/components/if-else/index.tsx +56 -0
- package/dist/components/if-else/meta.ts +6 -0
- package/dist/components/index.ts +70 -0
- package/dist/components/input/Input.stories.tsx +431 -0
- package/dist/components/input/index.tsx +487 -0
- package/dist/components/input/meta.ts +28 -0
- package/dist/components/label/Label.stories.tsx +200 -0
- package/dist/components/label/index.tsx +43 -0
- package/dist/components/label/meta.ts +14 -0
- package/dist/components/list/List.stories.tsx +963 -0
- package/dist/components/list/index.tsx +567 -0
- package/dist/components/list/meta.ts +24 -0
- package/dist/components/marquee/Marquee.stories.tsx +819 -0
- package/dist/components/marquee/index.tsx +107 -0
- package/dist/components/marquee/meta.ts +6 -0
- package/dist/components/overlay/Overlay.stories.tsx +954 -0
- package/dist/components/overlay/index.tsx +58 -0
- package/dist/components/overlay/meta.ts +10 -0
- package/dist/components/pagination/Pagination.stories.tsx +354 -0
- package/dist/components/pagination/index.tsx +455 -0
- package/dist/components/pagination/meta.ts +29 -0
- package/dist/components/popover/Popover.stories.tsx +1037 -0
- package/dist/components/popover/index.tsx +67 -0
- package/dist/components/popover/meta.ts +12 -0
- package/dist/components/radio/Radio.stories.tsx +146 -0
- package/dist/components/radio/index.tsx +41 -0
- package/dist/components/radio/meta.ts +19 -0
- package/dist/components/resizable/Resizable.stories.tsx +866 -0
- package/dist/components/resizable/index.tsx +55 -0
- package/dist/components/resizable/meta.ts +12 -0
- package/dist/components/scroll-area/ScrollArea.stories.tsx +1104 -0
- package/dist/components/scroll-area/index.tsx +55 -0
- package/dist/components/scroll-area/meta.ts +8 -0
- package/dist/components/search/Search.stories.tsx +678 -0
- package/dist/components/search/index.tsx +141 -0
- package/dist/components/search/meta.ts +6 -0
- package/dist/components/select/Select.stories.tsx +962 -0
- package/dist/components/select/index.tsx +512 -0
- package/dist/components/select/meta.ts +40 -0
- package/dist/components/sheet/Sheet.stories.tsx +1060 -0
- package/dist/components/sheet/index.tsx +440 -0
- package/dist/components/sheet/meta.ts +38 -0
- package/dist/components/skelton/Skelton.stories.tsx +859 -0
- package/dist/components/skelton/index.tsx +17 -0
- package/dist/components/skelton/meta.ts +6 -0
- package/dist/components/slider/Slider.stories.tsx +876 -0
- package/dist/components/slider/index.tsx +156 -0
- package/dist/components/slider/meta.ts +29 -0
- package/dist/components/stepper/Stepper.stories.tsx +639 -0
- package/dist/components/stepper/index.tsx +650 -0
- package/dist/components/stepper/meta.ts +19 -0
- package/dist/components/switch/Switch.stories.tsx +85 -0
- package/dist/components/switch/index.tsx +37 -0
- package/dist/components/switch/meta.ts +24 -0
- package/dist/components/switch-case/SwitchCase.stories.tsx +209 -0
- package/dist/components/switch-case/index.tsx +89 -0
- package/dist/components/switch-case/meta.ts +6 -0
- package/dist/components/table/Table.stories.tsx +1095 -0
- package/dist/components/table/index.tsx +113 -0
- package/dist/components/table/meta.ts +20 -0
- package/dist/components/tabs/Tabs.stories.tsx +1379 -0
- package/dist/components/tabs/index.tsx +186 -0
- package/dist/components/tabs/meta.ts +25 -0
- package/dist/components/tag/Tag.stories.tsx +625 -0
- package/dist/components/tag/index.tsx +320 -0
- package/dist/components/tag/meta.ts +52 -0
- package/dist/components/textarea/TextArea.stories.tsx +723 -0
- package/dist/components/textarea/index.tsx +480 -0
- package/dist/components/textarea/meta.ts +23 -0
- package/dist/components/toast/Toast.stories.tsx +1427 -0
- package/dist/components/toast/index.tsx +26 -0
- package/dist/components/toast/meta.ts +19 -0
- package/dist/components/toggle/Toggle.stories.tsx +1093 -0
- package/dist/components/toggle/index.tsx +44 -0
- package/dist/components/toggle/meta.ts +19 -0
- package/dist/components/tooltip/Tooltip.stories.tsx +1548 -0
- package/dist/components/tooltip/index.tsx +304 -0
- package/dist/components/tooltip/meta.ts +21 -0
- package/dist/components/typography/Typography.stories.tsx +197 -0
- package/dist/components/typography/index.tsx +184 -0
- package/dist/components/typography/meta.ts +38 -0
- package/dist/fonts/LabGrotesque-Regular.ttf +0 -0
- package/dist/fonts/LabGrotesqueTRIAL-Bold.otf +0 -0
- package/dist/fonts/LabGrotesqueTRIAL-Light.otf +0 -0
- package/dist/fonts/LabGrotesqueTRIAL-Medium.otf +0 -0
- package/dist/fonts/LabGrotesqueTRIAL-Regular.otf +0 -0
- package/dist/fonts/PPSupplySans-Regular (1).otf +0 -0
- package/dist/fonts/PPSupplySans-Regular.otf +0 -0
- package/dist/fonts/PPSupplySans-Ultralight.otf +0 -0
- package/dist/hooks/index.ts +3 -0
- package/dist/hooks/use-previous/UsePrevious.stories.tsx +997 -0
- package/dist/hooks/use-previous/index.ts +15 -0
- package/dist/hooks/use-previous/meta.ts +6 -0
- package/dist/hooks/use-standalone-pagination/UseStandalonePagination.stories.tsx +983 -0
- package/dist/hooks/use-standalone-pagination/index.ts +146 -0
- package/dist/hooks/use-standalone-pagination/meta.ts +6 -0
- package/dist/icons/Icons.stories.tsx +29 -0
- package/dist/icons/alert-icon/AlertIcon.stories.tsx +991 -0
- package/dist/icons/alert-icon/index.tsx +48 -0
- package/dist/icons/alert-icon/meta.ts +8 -0
- package/dist/icons/all-icons.tsx +738 -0
- package/dist/icons/angle-down-icon/AngleDownIcon.stories.tsx +1031 -0
- package/dist/icons/angle-down-icon/index.tsx +25 -0
- package/dist/icons/angle-down-icon/meta.ts +8 -0
- package/dist/icons/arrow-box-left-icon/ArrowBoxLeftIcon.stories.tsx +1080 -0
- package/dist/icons/arrow-box-left-icon/index.tsx +24 -0
- package/dist/icons/arrow-box-left-icon/meta.ts +8 -0
- package/dist/icons/arrow-right-icon/ArrowRightIcon.stories.tsx +1151 -0
- package/dist/icons/arrow-right-icon/index.tsx +26 -0
- package/dist/icons/arrow-right-icon/meta.ts +8 -0
- package/dist/icons/arrow-right-up-icon/ArrowRightUpIcon.stories.tsx +1273 -0
- package/dist/icons/arrow-right-up-icon/index.tsx +24 -0
- package/dist/icons/arrow-right-up-icon/meta.ts +8 -0
- package/dist/icons/art-board-icon/ArtBoardIcon.stories.tsx +670 -0
- package/dist/icons/art-board-icon/index.tsx +24 -0
- package/dist/icons/art-board-icon/meta.ts +7 -0
- package/dist/icons/audio-bar-icon/AudioBarIcon.stories.tsx +1244 -0
- package/dist/icons/audio-bar-icon/index.tsx +19 -0
- package/dist/icons/audio-bar-icon/meta.ts +8 -0
- package/dist/icons/bubble-check-icon/BubbleCheckIcon.stories.tsx +1239 -0
- package/dist/icons/bubble-check-icon/index.tsx +24 -0
- package/dist/icons/bubble-check-icon/meta.ts +8 -0
- package/dist/icons/bubble-crossed-icon/BubbleCrossedIcon.stories.tsx +1228 -0
- package/dist/icons/bubble-crossed-icon/index.tsx +24 -0
- package/dist/icons/bubble-crossed-icon/meta.ts +8 -0
- package/dist/icons/bubble-sparkle-icon/BubbleSparkleIcon.stories.tsx +912 -0
- package/dist/icons/bubble-sparkle-icon/index.tsx +26 -0
- package/dist/icons/bubble-sparkle-icon/meta.ts +8 -0
- package/dist/icons/chevron-double-left-icon/ChevronDoubleLeftIcon.stories.tsx +1021 -0
- package/dist/icons/chevron-double-left-icon/index.tsx +34 -0
- package/dist/icons/chevron-double-left-icon/meta.ts +8 -0
- package/dist/icons/chevron-double-right-icon/ChevronDoubleRightIcon.stories.tsx +1021 -0
- package/dist/icons/chevron-double-right-icon/index.tsx +34 -0
- package/dist/icons/chevron-double-right-icon/meta.ts +8 -0
- package/dist/icons/chevron-down-icon/ChevronDownIcon.stories.tsx +1001 -0
- package/dist/icons/chevron-down-icon/index.tsx +27 -0
- package/dist/icons/chevron-down-icon/meta.ts +8 -0
- package/dist/icons/chevron-left-icon/ChevronLeftIcon.stories.tsx +1029 -0
- package/dist/icons/chevron-left-icon/index.tsx +27 -0
- package/dist/icons/chevron-left-icon/meta.ts +8 -0
- package/dist/icons/chevron-right-icon/ChevronRightIcon.stories.tsx +1021 -0
- package/dist/icons/chevron-right-icon/index.tsx +27 -0
- package/dist/icons/chevron-right-icon/meta.ts +8 -0
- package/dist/icons/chevron-up-icon/ChevronUpIcon.stories.tsx +1036 -0
- package/dist/icons/chevron-up-icon/index.tsx +27 -0
- package/dist/icons/chevron-up-icon/meta.ts +8 -0
- package/dist/icons/command-icon/CommandIcon.stories.tsx +1098 -0
- package/dist/icons/command-icon/index.tsx +24 -0
- package/dist/icons/command-icon/meta.ts +8 -0
- package/dist/icons/cross-circle-icon/CrossCircleIcon.stories.tsx +1061 -0
- package/dist/icons/cross-circle-icon/index.tsx +23 -0
- package/dist/icons/cross-circle-icon/meta.ts +8 -0
- package/dist/icons/cross-icon/CrossIcon.stories.tsx +1027 -0
- package/dist/icons/cross-icon/index.tsx +24 -0
- package/dist/icons/cross-icon/meta.ts +8 -0
- package/dist/icons/edit-big-icon/EditBigIcon.stories.tsx +1092 -0
- package/dist/icons/edit-big-icon/index.tsx +22 -0
- package/dist/icons/edit-big-icon/meta.ts +8 -0
- package/dist/icons/eye-close-icon/EyeCloseIcon.stories.tsx +1090 -0
- package/dist/icons/eye-close-icon/index.tsx +26 -0
- package/dist/icons/eye-close-icon/meta.ts +8 -0
- package/dist/icons/eye-open-icon/EyeOpenIcon.stories.tsx +1098 -0
- package/dist/icons/eye-open-icon/index.tsx +24 -0
- package/dist/icons/eye-open-icon/meta.ts +8 -0
- package/dist/icons/feature-shine-icon/FeatureShineIcon.stories.tsx +1071 -0
- package/dist/icons/feature-shine-icon/index.tsx +29 -0
- package/dist/icons/feature-shine-icon/meta.ts +8 -0
- package/dist/icons/file-chart-icon/FileChartIcon.stories.tsx +1115 -0
- package/dist/icons/file-chart-icon/index.tsx +24 -0
- package/dist/icons/file-chart-icon/meta.ts +8 -0
- package/dist/icons/file-text-icon/FileTextIcon.stories.tsx +668 -0
- package/dist/icons/file-text-icon/index.tsx +24 -0
- package/dist/icons/file-text-icon/meta.ts +8 -0
- package/dist/icons/grip-vertical-icon/GripVerticalIcon.stories.tsx +1239 -0
- package/dist/icons/grip-vertical-icon/index.tsx +28 -0
- package/dist/icons/grip-vertical-icon/meta.ts +8 -0
- package/dist/icons/image-icon/ImageIcon.stories.tsx +1181 -0
- package/dist/icons/image-icon/index.tsx +24 -0
- package/dist/icons/image-icon/meta.ts +8 -0
- package/dist/icons/import-folder-icon/ImportFolderIcon.stories.tsx +1248 -0
- package/dist/icons/import-folder-icon/index.tsx +22 -0
- package/dist/icons/import-folder-icon/meta.ts +8 -0
- package/dist/icons/index.ts +46 -0
- package/dist/icons/light-bulb-simple-icon/LightBulbSimpleIcon.stories.tsx +1272 -0
- package/dist/icons/light-bulb-simple-icon/index.tsx +24 -0
- package/dist/icons/light-bulb-simple-icon/meta.ts +8 -0
- package/dist/icons/magic-book-icon/MagicBookIcon.stories.tsx +1245 -0
- package/dist/icons/magic-book-icon/index.tsx +32 -0
- package/dist/icons/magic-book-icon/meta.ts +8 -0
- package/dist/icons/maintenance-icon/MaintenanceIcon.stories.tsx +1251 -0
- package/dist/icons/maintenance-icon/index.tsx +23 -0
- package/dist/icons/maintenance-icon/meta.ts +8 -0
- package/dist/icons/message-icon/MessageIcon.stories.tsx +595 -0
- package/dist/icons/message-icon/index.tsx +30 -0
- package/dist/icons/message-icon/meta.ts +8 -0
- package/dist/icons/move-horizontal-icon/MoveHorizontalIcon.stories.tsx +1245 -0
- package/dist/icons/move-horizontal-icon/index.tsx +23 -0
- package/dist/icons/move-horizontal-icon/meta.ts +8 -0
- package/dist/icons/move-vertical-icon/MoveVerticalIcon.stories.tsx +1196 -0
- package/dist/icons/move-vertical-icon/index.tsx +23 -0
- package/dist/icons/move-vertical-icon/meta.ts +8 -0
- package/dist/icons/page-search-icon/PageSearchIcon.stories.tsx +1167 -0
- package/dist/icons/page-search-icon/index.tsx +21 -0
- package/dist/icons/page-search-icon/meta.ts +8 -0
- package/dist/icons/pencil-icon/PencilIcon.stories.tsx +1131 -0
- package/dist/icons/pencil-icon/index.tsx +21 -0
- package/dist/icons/pencil-icon/meta.ts +8 -0
- package/dist/icons/plus-icon/PlusIcon.stories.tsx +1151 -0
- package/dist/icons/plus-icon/index.tsx +24 -0
- package/dist/icons/plus-icon/meta.ts +8 -0
- package/dist/icons/search-icon/SearchIcon.stories.tsx +1181 -0
- package/dist/icons/search-icon/index.tsx +24 -0
- package/dist/icons/search-icon/meta.ts +8 -0
- package/dist/icons/site-logo-icon/SiteLogoIcon.stories.tsx +1167 -0
- package/dist/icons/site-logo-icon/index.tsx +79 -0
- package/dist/icons/site-logo-icon/meta.ts +8 -0
- package/dist/icons/spinner-gradient-icon/SpinnerGradientIcon.stories.tsx +637 -0
- package/dist/icons/spinner-gradient-icon/index.tsx +53 -0
- package/dist/icons/spinner-gradient-icon/meta.ts +8 -0
- package/dist/icons/spinner-solid-icon/SpinnerSolidIcon.stories.tsx +644 -0
- package/dist/icons/spinner-solid-icon/index.tsx +59 -0
- package/dist/icons/spinner-solid-icon/meta.ts +8 -0
- package/dist/icons/spinner-solid-neutral-icon/SpinnerSolidINeutralcon.stories.tsx +736 -0
- package/dist/icons/spinner-solid-neutral-icon/index.tsx +53 -0
- package/dist/icons/spinner-solid-neutral-icon/meta.ts +8 -0
- package/dist/icons/tick-circle-icon/TickCircleIcon.stories.tsx +1204 -0
- package/dist/icons/tick-circle-icon/index.tsx +23 -0
- package/dist/icons/tick-circle-icon/meta.ts +8 -0
- package/dist/icons/tick-icon/TickIcon.stories.tsx +1340 -0
- package/dist/icons/tick-icon/index.tsx +24 -0
- package/dist/icons/tick-icon/meta.ts +8 -0
- package/dist/icons/trash-icon/TrashIcon.stories.tsx +996 -0
- package/dist/icons/trash-icon/index.tsx +24 -0
- package/dist/icons/trash-icon/meta.ts +8 -0
- package/dist/icons/upload-icon/UploadIcon.stories.tsx +947 -0
- package/dist/icons/upload-icon/index.tsx +24 -0
- package/dist/icons/upload-icon/meta.ts +8 -0
- package/dist/icons/vertical-menu-icon/VerticalMenuIcon.stories.tsx +1045 -0
- package/dist/icons/vertical-menu-icon/index.tsx +27 -0
- package/dist/icons/vertical-menu-icon/meta.ts +8 -0
- package/dist/index.d.ts +6 -0
- package/dist/index.js +206 -0
- package/dist/lib/utils.ts +6 -0
- package/dist/styles/aural-theme.css +1008 -0
- package/package.json +142 -0
|
@@ -0,0 +1,1379 @@
|
|
|
1
|
+
import React from "react"
|
|
2
|
+
import {
|
|
3
|
+
AlertIcon,
|
|
4
|
+
CrossIcon,
|
|
5
|
+
EditBigIcon,
|
|
6
|
+
EyeOpenIcon,
|
|
7
|
+
FileChartIcon,
|
|
8
|
+
PlusIcon,
|
|
9
|
+
SearchIcon,
|
|
10
|
+
TickCircleIcon,
|
|
11
|
+
} from "@icons/index"
|
|
12
|
+
import type { Meta, StoryObj } from "@storybook/react"
|
|
13
|
+
|
|
14
|
+
import { Tabs, TabsContent, TabsList, TabsTrigger } from "."
|
|
15
|
+
|
|
16
|
+
const meta: Meta<typeof Tabs> = {
|
|
17
|
+
title: "Components/UI/Tabs",
|
|
18
|
+
component: Tabs,
|
|
19
|
+
parameters: {
|
|
20
|
+
layout: "centered",
|
|
21
|
+
backgrounds: {
|
|
22
|
+
default: "dark",
|
|
23
|
+
values: [
|
|
24
|
+
{ name: "dark", value: "#0a0a0a" },
|
|
25
|
+
{ name: "light", value: "#ffffff" },
|
|
26
|
+
],
|
|
27
|
+
},
|
|
28
|
+
docs: {
|
|
29
|
+
description: {
|
|
30
|
+
component: `
|
|
31
|
+
# Tabs Component
|
|
32
|
+
|
|
33
|
+
A beautiful and accessible tabs component built on top of Radix UI's Tabs primitive with custom styling and animations. Features smooth tab transitions, hover effects, and a stunning gradient glow for active tabs.
|
|
34
|
+
|
|
35
|
+
## Components
|
|
36
|
+
|
|
37
|
+
### Core Components
|
|
38
|
+
- **Tabs**: Root container for the entire tabs system with size context
|
|
39
|
+
- **TabsList**: Container for all tab triggers
|
|
40
|
+
- **TabsTrigger**: Individual tab buttons with custom glow effects
|
|
41
|
+
- **TabsContent**: Content panels that display when tabs are active
|
|
42
|
+
|
|
43
|
+
## Features
|
|
44
|
+
|
|
45
|
+
- **Gradient Glow Effects**: Beautiful radial gradient with blur effects on active tabs
|
|
46
|
+
- **Smooth Animations**: Fade in/out transitions between active and inactive states
|
|
47
|
+
- **Size Variants**: Small, medium, and large tab sizes via context
|
|
48
|
+
- **Keyboard Accessible**: Full keyboard navigation support
|
|
49
|
+
- **Screen Reader Support**: Proper ARIA attributes and announcements
|
|
50
|
+
- **Custom Styling**: Tailored design system integration
|
|
51
|
+
- **Responsive Design**: Adapts to different screen sizes
|
|
52
|
+
- **Icon Support**: Built-in support for icons in tab labels
|
|
53
|
+
|
|
54
|
+
## Size Variants
|
|
55
|
+
|
|
56
|
+
### Small (sm)
|
|
57
|
+
- Font size: var(--text-fm-md)
|
|
58
|
+
- Padding: 8px (p-2)
|
|
59
|
+
- Ideal for: Compact interfaces, sidebars
|
|
60
|
+
|
|
61
|
+
### Medium (md) - Default
|
|
62
|
+
- Font size: var(--text-fm-xl)
|
|
63
|
+
- Padding: 12px horizontal, 16px top, 12px bottom
|
|
64
|
+
- Ideal for: Main navigation, content sections
|
|
65
|
+
|
|
66
|
+
### Large (lg)
|
|
67
|
+
- Font size: var(--text-fm-2xl)
|
|
68
|
+
- Padding: 12px horizontal, 16px top, 12px bottom
|
|
69
|
+
- Ideal for: Primary navigation, hero sections
|
|
70
|
+
|
|
71
|
+
## Visual Effects
|
|
72
|
+
|
|
73
|
+
### Active Tab Glow
|
|
74
|
+
The active tab features a stunning dual-layer gradient effect:
|
|
75
|
+
- **Bottom Layer**: Curved gradient line at the tab base
|
|
76
|
+
- **Top Layer**: Blurred elliptical glow with screen blend mode
|
|
77
|
+
- **Colors**: Red to purple to black gradient (#FF3E4C → #5200A3 → #0A0A0A)
|
|
78
|
+
|
|
79
|
+
### Animations
|
|
80
|
+
- **Fade In**: Active tabs fade in with animate-fm-fadeIn
|
|
81
|
+
- **Fade Out**: Inactive tabs fade out with animate-fm-fadeOut
|
|
82
|
+
- **Smooth Transitions**: Color and glow transitions
|
|
83
|
+
|
|
84
|
+
## Usage Examples
|
|
85
|
+
|
|
86
|
+
### Basic Tabs with Size
|
|
87
|
+
\`\`\`tsx
|
|
88
|
+
<Tabs defaultValue="tab1" size="lg">
|
|
89
|
+
<TabsList>
|
|
90
|
+
<TabsTrigger value="tab1">Tab 1</TabsTrigger>
|
|
91
|
+
<TabsTrigger value="tab2">Tab 2</TabsTrigger>
|
|
92
|
+
</TabsList>
|
|
93
|
+
<TabsContent value="tab1">Content 1</TabsContent>
|
|
94
|
+
<TabsContent value="tab2">Content 2</TabsContent>
|
|
95
|
+
</Tabs>
|
|
96
|
+
\`\`\`
|
|
97
|
+
|
|
98
|
+
### With Icons
|
|
99
|
+
\`\`\`tsx
|
|
100
|
+
<Tabs defaultValue="dashboard" size="md">
|
|
101
|
+
<TabsList>
|
|
102
|
+
<TabsTrigger value="dashboard">
|
|
103
|
+
<BarChart className="w-4 h-4" />
|
|
104
|
+
Dashboard
|
|
105
|
+
</TabsTrigger>
|
|
106
|
+
<TabsTrigger value="settings">
|
|
107
|
+
<Settings className="w-4 h-4" />
|
|
108
|
+
Settings
|
|
109
|
+
</TabsTrigger>
|
|
110
|
+
</TabsList>
|
|
111
|
+
<TabsContent value="dashboard">Dashboard content</TabsContent>
|
|
112
|
+
<TabsContent value="settings">Settings content</TabsContent>
|
|
113
|
+
</Tabs>
|
|
114
|
+
\`\`\`
|
|
115
|
+
|
|
116
|
+
### Individual Size Override
|
|
117
|
+
\`\`\`tsx
|
|
118
|
+
<Tabs defaultValue="home" size="md">
|
|
119
|
+
<TabsList>
|
|
120
|
+
<TabsTrigger value="home">Home</TabsTrigger>
|
|
121
|
+
<TabsTrigger value="about" size="lg">About (Large)</TabsTrigger>
|
|
122
|
+
</TabsList>
|
|
123
|
+
<TabsContent value="home">Home content</TabsContent>
|
|
124
|
+
<TabsContent value="about">About content</TabsContent>
|
|
125
|
+
</Tabs>
|
|
126
|
+
\`\`\`
|
|
127
|
+
|
|
128
|
+
## Props
|
|
129
|
+
|
|
130
|
+
### Tabs Props
|
|
131
|
+
- **size**: "sm" | "md" | "lg" - Sets the size for all child TabsTrigger components
|
|
132
|
+
- **defaultValue**: string - The default active tab
|
|
133
|
+
- **value**: string - Controlled active tab value
|
|
134
|
+
- **onValueChange**: (value: string) => void - Callback when tab changes
|
|
135
|
+
|
|
136
|
+
### TabsTrigger Props
|
|
137
|
+
- **size**: "sm" | "md" | "lg" - Optional override for individual triggers
|
|
138
|
+
- **value**: string - Unique identifier for the tab
|
|
139
|
+
- **disabled**: boolean - Disable the tab trigger
|
|
140
|
+
|
|
141
|
+
## Accessibility
|
|
142
|
+
|
|
143
|
+
- **Keyboard Navigation**: Arrow keys to move between tabs, Space/Enter to activate
|
|
144
|
+
- **Screen Reader Support**: Proper ARIA labels and announcements
|
|
145
|
+
- **Focus Management**: Clear focus indicators and logical tab order
|
|
146
|
+
- **Role Attributes**: Correct tab, tablist, and tabpanel roles
|
|
147
|
+
- **State Announcements**: Active/inactive states announced to screen readers
|
|
148
|
+
|
|
149
|
+
## Design System Integration
|
|
150
|
+
|
|
151
|
+
- **Color Tokens**: Uses design system color tokens (fm-primary, fm-tertiary, etc.)
|
|
152
|
+
- **Typography**: Integrated with font size and leading variables
|
|
153
|
+
- **Focus States**: Consistent focus ring styling
|
|
154
|
+
- **Transitions**: Smooth color and effect transitions
|
|
155
|
+
- **Border Styles**: Consistent with design system borders
|
|
156
|
+
|
|
157
|
+
## Best Practices
|
|
158
|
+
|
|
159
|
+
- Keep tab labels concise and descriptive
|
|
160
|
+
- Use icons to improve visual hierarchy
|
|
161
|
+
- Don't use more than 7-8 tabs in a single group
|
|
162
|
+
- Ensure tab content is substantial enough to warrant separation
|
|
163
|
+
- Test keyboard navigation thoroughly
|
|
164
|
+
- Consider mobile responsive behavior
|
|
165
|
+
- Use consistent sizing throughout your application
|
|
166
|
+
- Set size on Tabs component instead of individual triggers
|
|
167
|
+
|
|
168
|
+
## Performance
|
|
169
|
+
|
|
170
|
+
- **Lazy Loading**: Content panels only render when active
|
|
171
|
+
- **Efficient Re-renders**: Optimized state management with context
|
|
172
|
+
- **CSS Animations**: Hardware-accelerated animations
|
|
173
|
+
- **Minimal DOM**: Clean, semantic HTML structure
|
|
174
|
+
`,
|
|
175
|
+
},
|
|
176
|
+
},
|
|
177
|
+
},
|
|
178
|
+
tags: ["autodocs"],
|
|
179
|
+
argTypes: {
|
|
180
|
+
size: {
|
|
181
|
+
control: "select",
|
|
182
|
+
options: ["sm", "md", "lg"],
|
|
183
|
+
description: "Size variant applied to all tab triggers",
|
|
184
|
+
},
|
|
185
|
+
defaultValue: {
|
|
186
|
+
control: "text",
|
|
187
|
+
description: "The default active tab value",
|
|
188
|
+
},
|
|
189
|
+
value: {
|
|
190
|
+
control: "text",
|
|
191
|
+
description: "The controlled active tab value",
|
|
192
|
+
},
|
|
193
|
+
onValueChange: {
|
|
194
|
+
action: "valueChanged",
|
|
195
|
+
description: "Callback when tab changes",
|
|
196
|
+
},
|
|
197
|
+
},
|
|
198
|
+
}
|
|
199
|
+
|
|
200
|
+
export default meta
|
|
201
|
+
type Story = StoryObj<typeof Tabs>
|
|
202
|
+
|
|
203
|
+
// 1. Basic Tabs
|
|
204
|
+
export const Basic: Story = {
|
|
205
|
+
render: () => (
|
|
206
|
+
<div className="w-full max-w-2xl">
|
|
207
|
+
<Tabs defaultValue="overview" className="w-full">
|
|
208
|
+
<TabsList className="grid w-full grid-cols-3">
|
|
209
|
+
<TabsTrigger value="overview">Overview</TabsTrigger>
|
|
210
|
+
<TabsTrigger value="analytics">Analytics</TabsTrigger>
|
|
211
|
+
<TabsTrigger value="reports">Reports</TabsTrigger>
|
|
212
|
+
</TabsList>
|
|
213
|
+
<TabsContent value="overview" className="mt-6">
|
|
214
|
+
<div className="rounded-lg border border-white/10 bg-white/5 p-6">
|
|
215
|
+
<h3 className="mb-4 text-lg font-semibold text-white">Overview</h3>
|
|
216
|
+
<p className="mb-4 text-white/70">
|
|
217
|
+
Get a comprehensive view of your project's key metrics and
|
|
218
|
+
performance indicators.
|
|
219
|
+
</p>
|
|
220
|
+
<div className="grid grid-cols-2 gap-4">
|
|
221
|
+
<div className="rounded-lg border border-blue-500/20 bg-blue-500/10 p-4">
|
|
222
|
+
<div className="text-2xl font-bold text-blue-400">1,234</div>
|
|
223
|
+
<div className="text-sm text-white/60">Total Users</div>
|
|
224
|
+
</div>
|
|
225
|
+
<div className="rounded-lg border border-green-500/20 bg-green-500/10 p-4">
|
|
226
|
+
<div className="text-2xl font-bold text-green-400">98.5%</div>
|
|
227
|
+
<div className="text-sm text-white/60">Uptime</div>
|
|
228
|
+
</div>
|
|
229
|
+
</div>
|
|
230
|
+
</div>
|
|
231
|
+
</TabsContent>
|
|
232
|
+
<TabsContent value="analytics" className="mt-6">
|
|
233
|
+
<div className="rounded-lg border border-white/10 bg-white/5 p-6">
|
|
234
|
+
<h3 className="mb-4 text-lg font-semibold text-white">Analytics</h3>
|
|
235
|
+
<p className="mb-4 text-white/70">
|
|
236
|
+
Deep dive into user behavior and engagement patterns across your
|
|
237
|
+
platform.
|
|
238
|
+
</p>
|
|
239
|
+
<div className="space-y-4">
|
|
240
|
+
<div className="flex items-center justify-between rounded-lg bg-white/5 p-3">
|
|
241
|
+
<span className="text-white">Page Views</span>
|
|
242
|
+
<span className="font-semibold text-green-400">+12.5%</span>
|
|
243
|
+
</div>
|
|
244
|
+
<div className="flex items-center justify-between rounded-lg bg-white/5 p-3">
|
|
245
|
+
<span className="text-white">Session Duration</span>
|
|
246
|
+
<span className="font-semibold text-blue-400">4:32 avg</span>
|
|
247
|
+
</div>
|
|
248
|
+
<div className="flex items-center justify-between rounded-lg bg-white/5 p-3">
|
|
249
|
+
<span className="text-white">Bounce Rate</span>
|
|
250
|
+
<span className="font-semibold text-orange-400">32.1%</span>
|
|
251
|
+
</div>
|
|
252
|
+
</div>
|
|
253
|
+
</div>
|
|
254
|
+
</TabsContent>
|
|
255
|
+
<TabsContent value="reports" className="mt-6">
|
|
256
|
+
<div className="rounded-lg border border-white/10 bg-white/5 p-6">
|
|
257
|
+
<h3 className="mb-4 text-lg font-semibold text-white">Reports</h3>
|
|
258
|
+
<p className="mb-4 text-white/70">
|
|
259
|
+
Generate and download detailed reports for stakeholders and
|
|
260
|
+
analysis.
|
|
261
|
+
</p>
|
|
262
|
+
<div className="space-y-3">
|
|
263
|
+
<button className="w-full rounded-lg bg-white/5 p-3 text-left transition-colors hover:bg-white/10">
|
|
264
|
+
<div className="font-medium text-white">
|
|
265
|
+
Monthly Performance Report
|
|
266
|
+
</div>
|
|
267
|
+
<div className="text-sm text-white/60">
|
|
268
|
+
Last generated: 2 days ago
|
|
269
|
+
</div>
|
|
270
|
+
</button>
|
|
271
|
+
<button className="w-full rounded-lg bg-white/5 p-3 text-left transition-colors hover:bg-white/10">
|
|
272
|
+
<div className="font-medium text-white">
|
|
273
|
+
User Engagement Analysis
|
|
274
|
+
</div>
|
|
275
|
+
<div className="text-sm text-white/60">
|
|
276
|
+
Last generated: 1 week ago
|
|
277
|
+
</div>
|
|
278
|
+
</button>
|
|
279
|
+
<button className="w-full rounded-lg bg-white/5 p-3 text-left transition-colors hover:bg-white/10">
|
|
280
|
+
<div className="font-medium text-white">Revenue Breakdown</div>
|
|
281
|
+
<div className="text-sm text-white/60">
|
|
282
|
+
Last generated: 3 days ago
|
|
283
|
+
</div>
|
|
284
|
+
</button>
|
|
285
|
+
</div>
|
|
286
|
+
</div>
|
|
287
|
+
</TabsContent>
|
|
288
|
+
</Tabs>
|
|
289
|
+
</div>
|
|
290
|
+
),
|
|
291
|
+
parameters: {
|
|
292
|
+
docs: {
|
|
293
|
+
description: {
|
|
294
|
+
story:
|
|
295
|
+
"Basic tabs implementation with three panels showing different types of content using default medium size.",
|
|
296
|
+
},
|
|
297
|
+
},
|
|
298
|
+
},
|
|
299
|
+
}
|
|
300
|
+
|
|
301
|
+
// 2. With Icons
|
|
302
|
+
export const WithIcons: Story = {
|
|
303
|
+
render: () => (
|
|
304
|
+
<div className="w-full max-w-3xl">
|
|
305
|
+
<Tabs defaultValue="dashboard" className="w-full">
|
|
306
|
+
<TabsList className="grid w-full grid-cols-4">
|
|
307
|
+
<TabsTrigger value="dashboard" className="gap-2">
|
|
308
|
+
<FileChartIcon className="h-4 w-4" />
|
|
309
|
+
Dashboard
|
|
310
|
+
</TabsTrigger>
|
|
311
|
+
<TabsTrigger value="users" className="gap-2">
|
|
312
|
+
<EyeOpenIcon className="h-4 w-4" />
|
|
313
|
+
Users
|
|
314
|
+
</TabsTrigger>
|
|
315
|
+
<TabsTrigger value="settings" className="gap-2">
|
|
316
|
+
<EditBigIcon className="h-4 w-4" />
|
|
317
|
+
Settings
|
|
318
|
+
</TabsTrigger>
|
|
319
|
+
<TabsTrigger value="alerts" className="gap-2">
|
|
320
|
+
<AlertIcon className="h-4 w-4" />
|
|
321
|
+
Alerts
|
|
322
|
+
</TabsTrigger>
|
|
323
|
+
</TabsList>
|
|
324
|
+
|
|
325
|
+
<TabsContent value="dashboard" className="mt-6">
|
|
326
|
+
<div className="rounded-lg border border-white/10 bg-white/5 p-6">
|
|
327
|
+
<div className="mb-4 flex items-center gap-3">
|
|
328
|
+
<FileChartIcon className="h-6 w-6 text-blue-400" />
|
|
329
|
+
<h3 className="text-lg font-semibold text-white">Dashboard</h3>
|
|
330
|
+
</div>
|
|
331
|
+
<div className="grid grid-cols-1 gap-4 md:grid-cols-3">
|
|
332
|
+
<div className="rounded-lg border border-blue-500/30 bg-gradient-to-br from-blue-500/20 to-purple-500/20 p-4">
|
|
333
|
+
<div className="text-2xl font-bold text-white">847</div>
|
|
334
|
+
<div className="text-sm text-white/70">Active Sessions</div>
|
|
335
|
+
<div className="mt-1 text-xs text-green-400">
|
|
336
|
+
↗ +15% from yesterday
|
|
337
|
+
</div>
|
|
338
|
+
</div>
|
|
339
|
+
<div className="rounded-lg border border-green-500/30 bg-gradient-to-br from-green-500/20 to-teal-500/20 p-4">
|
|
340
|
+
<div className="text-2xl font-bold text-white">$12,847</div>
|
|
341
|
+
<div className="text-sm text-white/70">Revenue Today</div>
|
|
342
|
+
<div className="mt-1 text-xs text-green-400">
|
|
343
|
+
↗ +8% from yesterday
|
|
344
|
+
</div>
|
|
345
|
+
</div>
|
|
346
|
+
<div className="rounded-lg border border-orange-500/30 bg-gradient-to-br from-orange-500/20 to-red-500/20 p-4">
|
|
347
|
+
<div className="text-2xl font-bold text-white">23</div>
|
|
348
|
+
<div className="text-sm text-white/70">Critical Issues</div>
|
|
349
|
+
<div className="mt-1 text-xs text-red-400">
|
|
350
|
+
↗ +3 new issues
|
|
351
|
+
</div>
|
|
352
|
+
</div>
|
|
353
|
+
</div>
|
|
354
|
+
</div>
|
|
355
|
+
</TabsContent>
|
|
356
|
+
|
|
357
|
+
<TabsContent value="users" className="mt-6">
|
|
358
|
+
<div className="rounded-lg border border-white/10 bg-white/5 p-6">
|
|
359
|
+
<div className="mb-4 flex items-center gap-3">
|
|
360
|
+
<EyeOpenIcon className="h-6 w-6 text-green-400" />
|
|
361
|
+
<h3 className="text-lg font-semibold text-white">
|
|
362
|
+
User Management
|
|
363
|
+
</h3>
|
|
364
|
+
</div>
|
|
365
|
+
<div className="space-y-3">
|
|
366
|
+
{[
|
|
367
|
+
{
|
|
368
|
+
name: "Alice Johnson",
|
|
369
|
+
role: "Admin",
|
|
370
|
+
status: "online",
|
|
371
|
+
avatar: "AJ",
|
|
372
|
+
},
|
|
373
|
+
{
|
|
374
|
+
name: "Bob Smith",
|
|
375
|
+
role: "Editor",
|
|
376
|
+
status: "away",
|
|
377
|
+
avatar: "BS",
|
|
378
|
+
},
|
|
379
|
+
{
|
|
380
|
+
name: "Carol Davis",
|
|
381
|
+
role: "Viewer",
|
|
382
|
+
status: "offline",
|
|
383
|
+
avatar: "CD",
|
|
384
|
+
},
|
|
385
|
+
{
|
|
386
|
+
name: "David Wilson",
|
|
387
|
+
role: "Admin",
|
|
388
|
+
status: "online",
|
|
389
|
+
avatar: "DW",
|
|
390
|
+
},
|
|
391
|
+
].map((user, index) => (
|
|
392
|
+
<div
|
|
393
|
+
key={index}
|
|
394
|
+
className="flex items-center justify-between rounded-lg bg-white/5 p-3 transition-colors hover:bg-white/10"
|
|
395
|
+
>
|
|
396
|
+
<div className="flex items-center gap-3">
|
|
397
|
+
<div className="flex h-10 w-10 items-center justify-center rounded-full bg-gradient-to-br from-purple-500 to-pink-500">
|
|
398
|
+
<span className="text-sm font-semibold text-white">
|
|
399
|
+
{user.avatar}
|
|
400
|
+
</span>
|
|
401
|
+
</div>
|
|
402
|
+
<div>
|
|
403
|
+
<div className="font-medium text-white">{user.name}</div>
|
|
404
|
+
<div className="text-sm text-white/60">{user.role}</div>
|
|
405
|
+
</div>
|
|
406
|
+
</div>
|
|
407
|
+
<div className="flex items-center gap-2">
|
|
408
|
+
<div
|
|
409
|
+
className={`h-2 w-2 rounded-full ${
|
|
410
|
+
user.status === "online"
|
|
411
|
+
? "bg-green-500"
|
|
412
|
+
: user.status === "away"
|
|
413
|
+
? "bg-yellow-500"
|
|
414
|
+
: "bg-gray-500"
|
|
415
|
+
}`}
|
|
416
|
+
/>
|
|
417
|
+
<span className="text-xs text-white/60 capitalize">
|
|
418
|
+
{user.status}
|
|
419
|
+
</span>
|
|
420
|
+
</div>
|
|
421
|
+
</div>
|
|
422
|
+
))}
|
|
423
|
+
</div>
|
|
424
|
+
</div>
|
|
425
|
+
</TabsContent>
|
|
426
|
+
|
|
427
|
+
<TabsContent value="settings" className="mt-6">
|
|
428
|
+
<div className="rounded-lg border border-white/10 bg-white/5 p-6">
|
|
429
|
+
<div className="mb-4 flex items-center gap-3">
|
|
430
|
+
<EditBigIcon className="h-6 w-6 text-purple-400" />
|
|
431
|
+
<h3 className="text-lg font-semibold text-white">Settings</h3>
|
|
432
|
+
</div>
|
|
433
|
+
<div className="space-y-4">
|
|
434
|
+
<div className="flex items-center justify-between rounded-lg bg-white/5 p-3">
|
|
435
|
+
<div>
|
|
436
|
+
<div className="font-medium text-white">
|
|
437
|
+
Email Notifications
|
|
438
|
+
</div>
|
|
439
|
+
<div className="text-sm text-white/60">
|
|
440
|
+
Receive updates via email
|
|
441
|
+
</div>
|
|
442
|
+
</div>
|
|
443
|
+
<button className="relative h-6 w-12 rounded-full bg-blue-500">
|
|
444
|
+
<div className="absolute top-0.5 right-0.5 h-5 w-5 rounded-full bg-white transition-transform"></div>
|
|
445
|
+
</button>
|
|
446
|
+
</div>
|
|
447
|
+
<div className="flex items-center justify-between rounded-lg bg-white/5 p-3">
|
|
448
|
+
<div>
|
|
449
|
+
<div className="font-medium text-white">Dark Mode</div>
|
|
450
|
+
<div className="text-sm text-white/60">Use dark theme</div>
|
|
451
|
+
</div>
|
|
452
|
+
<button className="relative h-6 w-12 rounded-full bg-blue-500">
|
|
453
|
+
<div className="absolute top-0.5 right-0.5 h-5 w-5 rounded-full bg-white transition-transform"></div>
|
|
454
|
+
</button>
|
|
455
|
+
</div>
|
|
456
|
+
<div className="flex items-center justify-between rounded-lg bg-white/5 p-3">
|
|
457
|
+
<div>
|
|
458
|
+
<div className="font-medium text-white">Auto-save</div>
|
|
459
|
+
<div className="text-sm text-white/60">
|
|
460
|
+
Automatically save changes
|
|
461
|
+
</div>
|
|
462
|
+
</div>
|
|
463
|
+
<button className="relative h-6 w-12 rounded-full bg-gray-600">
|
|
464
|
+
<div className="absolute top-0.5 left-0.5 h-5 w-5 rounded-full bg-white transition-transform"></div>
|
|
465
|
+
</button>
|
|
466
|
+
</div>
|
|
467
|
+
</div>
|
|
468
|
+
</div>
|
|
469
|
+
</TabsContent>
|
|
470
|
+
|
|
471
|
+
<TabsContent value="alerts" className="mt-6">
|
|
472
|
+
<div className="rounded-lg border border-white/10 bg-white/5 p-6">
|
|
473
|
+
<div className="mb-4 flex items-center gap-3">
|
|
474
|
+
<AlertIcon className="h-6 w-6 text-red-400" />
|
|
475
|
+
<h3 className="text-lg font-semibold text-white">
|
|
476
|
+
System Alerts
|
|
477
|
+
</h3>
|
|
478
|
+
</div>
|
|
479
|
+
<div className="space-y-3">
|
|
480
|
+
<div className="flex items-start gap-3 rounded-lg border border-red-500/20 bg-red-500/10 p-3">
|
|
481
|
+
<AlertIcon className="mt-0.5 h-5 w-5 flex-shrink-0 text-red-400" />
|
|
482
|
+
<div>
|
|
483
|
+
<div className="font-medium text-white">High CPU Usage</div>
|
|
484
|
+
<div className="text-sm text-white/70">
|
|
485
|
+
Server load is above 90% threshold
|
|
486
|
+
</div>
|
|
487
|
+
<div className="mt-1 text-xs text-white/50">
|
|
488
|
+
2 minutes ago
|
|
489
|
+
</div>
|
|
490
|
+
</div>
|
|
491
|
+
</div>
|
|
492
|
+
<div className="flex items-start gap-3 rounded-lg border border-yellow-500/20 bg-yellow-500/10 p-3">
|
|
493
|
+
<AlertIcon className="mt-0.5 h-5 w-5 flex-shrink-0 text-yellow-400" />
|
|
494
|
+
<div>
|
|
495
|
+
<div className="font-medium text-white">
|
|
496
|
+
Database Connection
|
|
497
|
+
</div>
|
|
498
|
+
<div className="text-sm text-white/70">
|
|
499
|
+
Intermittent connectivity issues detected
|
|
500
|
+
</div>
|
|
501
|
+
<div className="mt-1 text-xs text-white/50">
|
|
502
|
+
15 minutes ago
|
|
503
|
+
</div>
|
|
504
|
+
</div>
|
|
505
|
+
</div>
|
|
506
|
+
<div className="flex items-start gap-3 rounded-lg border border-green-500/20 bg-green-500/10 p-3">
|
|
507
|
+
<TickCircleIcon className="mt-0.5 h-5 w-5 flex-shrink-0 text-green-400" />
|
|
508
|
+
<div>
|
|
509
|
+
<div className="font-medium text-white">Backup Completed</div>
|
|
510
|
+
<div className="text-sm text-white/70">
|
|
511
|
+
Daily backup finished successfully
|
|
512
|
+
</div>
|
|
513
|
+
<div className="mt-1 text-xs text-white/50">1 hour ago</div>
|
|
514
|
+
</div>
|
|
515
|
+
</div>
|
|
516
|
+
</div>
|
|
517
|
+
</div>
|
|
518
|
+
</TabsContent>
|
|
519
|
+
</Tabs>
|
|
520
|
+
</div>
|
|
521
|
+
),
|
|
522
|
+
parameters: {
|
|
523
|
+
docs: {
|
|
524
|
+
description: {
|
|
525
|
+
story:
|
|
526
|
+
"Tabs with icons showing a complete admin dashboard interface with different functional areas using default medium size.",
|
|
527
|
+
},
|
|
528
|
+
},
|
|
529
|
+
},
|
|
530
|
+
}
|
|
531
|
+
|
|
532
|
+
// 3. Size Variations
|
|
533
|
+
export const SizeVariations: Story = {
|
|
534
|
+
render: () => (
|
|
535
|
+
<div className="w-full max-w-4xl space-y-8">
|
|
536
|
+
<div className="space-y-4">
|
|
537
|
+
<h3 className="text-lg font-medium text-white">Small Size</h3>
|
|
538
|
+
<Tabs defaultValue="tab1" size="sm" className="w-full">
|
|
539
|
+
<TabsList className="grid w-full grid-cols-3">
|
|
540
|
+
<TabsTrigger value="tab1">Compact</TabsTrigger>
|
|
541
|
+
<TabsTrigger value="tab2">Small</TabsTrigger>
|
|
542
|
+
<TabsTrigger value="tab3">Minimal</TabsTrigger>
|
|
543
|
+
</TabsList>
|
|
544
|
+
<TabsContent value="tab1" className="mt-4">
|
|
545
|
+
<div className="rounded-lg border border-white/10 bg-white/5 p-4">
|
|
546
|
+
<p className="text-white/70">
|
|
547
|
+
Small tabs are perfect for compact interfaces and secondary
|
|
548
|
+
navigation.
|
|
549
|
+
</p>
|
|
550
|
+
</div>
|
|
551
|
+
</TabsContent>
|
|
552
|
+
<TabsContent value="tab2" className="mt-4">
|
|
553
|
+
<div className="rounded-lg border border-white/10 bg-white/5 p-4">
|
|
554
|
+
<p className="text-white/70">
|
|
555
|
+
Ideal for sidebars, modal dialogs, and tight spaces.
|
|
556
|
+
</p>
|
|
557
|
+
</div>
|
|
558
|
+
</TabsContent>
|
|
559
|
+
<TabsContent value="tab3" className="mt-4">
|
|
560
|
+
<div className="rounded-lg border border-white/10 bg-white/5 p-4">
|
|
561
|
+
<p className="text-white/70">
|
|
562
|
+
Minimal design with efficient use of space.
|
|
563
|
+
</p>
|
|
564
|
+
</div>
|
|
565
|
+
</TabsContent>
|
|
566
|
+
</Tabs>
|
|
567
|
+
</div>
|
|
568
|
+
|
|
569
|
+
<div className="space-y-4">
|
|
570
|
+
<h3 className="text-lg font-medium text-white">
|
|
571
|
+
Medium Size (Default)
|
|
572
|
+
</h3>
|
|
573
|
+
<Tabs defaultValue="tab1" size="md" className="w-full">
|
|
574
|
+
<TabsList className="grid w-full grid-cols-3">
|
|
575
|
+
<TabsTrigger value="tab1">Standard</TabsTrigger>
|
|
576
|
+
<TabsTrigger value="tab2">Medium</TabsTrigger>
|
|
577
|
+
<TabsTrigger value="tab3">Default</TabsTrigger>
|
|
578
|
+
</TabsList>
|
|
579
|
+
<TabsContent value="tab1" className="mt-4">
|
|
580
|
+
<div className="rounded-lg border border-white/10 bg-white/5 p-6">
|
|
581
|
+
<p className="text-white/70">
|
|
582
|
+
Medium tabs provide the perfect balance between visibility and
|
|
583
|
+
space efficiency.
|
|
584
|
+
</p>
|
|
585
|
+
</div>
|
|
586
|
+
</TabsContent>
|
|
587
|
+
<TabsContent value="tab2" className="mt-4">
|
|
588
|
+
<div className="rounded-lg border border-white/10 bg-white/5 p-6">
|
|
589
|
+
<p className="text-white/70">
|
|
590
|
+
Great for main content areas and primary navigation.
|
|
591
|
+
</p>
|
|
592
|
+
</div>
|
|
593
|
+
</TabsContent>
|
|
594
|
+
<TabsContent value="tab3" className="mt-4">
|
|
595
|
+
<div className="rounded-lg border border-white/10 bg-white/5 p-6">
|
|
596
|
+
<p className="text-white/70">
|
|
597
|
+
The default choice for most tab implementations.
|
|
598
|
+
</p>
|
|
599
|
+
</div>
|
|
600
|
+
</TabsContent>
|
|
601
|
+
</Tabs>
|
|
602
|
+
</div>
|
|
603
|
+
|
|
604
|
+
<div className="space-y-4">
|
|
605
|
+
<h3 className="text-lg font-medium text-white">Large Size</h3>
|
|
606
|
+
<Tabs defaultValue="tab1" size="lg" className="w-full">
|
|
607
|
+
<TabsList className="grid w-full grid-cols-3">
|
|
608
|
+
<TabsTrigger value="tab1">Prominent</TabsTrigger>
|
|
609
|
+
<TabsTrigger value="tab2">Large</TabsTrigger>
|
|
610
|
+
<TabsTrigger value="tab3">Bold</TabsTrigger>
|
|
611
|
+
</TabsList>
|
|
612
|
+
<TabsContent value="tab1" className="mt-4">
|
|
613
|
+
<div className="rounded-lg border border-white/10 bg-white/5 p-8">
|
|
614
|
+
<p className="text-white/70">
|
|
615
|
+
Large tabs make a statement and are perfect for hero sections
|
|
616
|
+
and primary interfaces.
|
|
617
|
+
</p>
|
|
618
|
+
</div>
|
|
619
|
+
</TabsContent>
|
|
620
|
+
<TabsContent value="tab2" className="mt-4">
|
|
621
|
+
<div className="rounded-lg border border-white/10 bg-white/5 p-8">
|
|
622
|
+
<p className="text-white/70">
|
|
623
|
+
Enhanced visibility and improved touch targets for mobile
|
|
624
|
+
interfaces.
|
|
625
|
+
</p>
|
|
626
|
+
</div>
|
|
627
|
+
</TabsContent>
|
|
628
|
+
<TabsContent value="tab3" className="mt-4">
|
|
629
|
+
<div className="rounded-lg border border-white/10 bg-white/5 p-8">
|
|
630
|
+
<p className="text-white/70">
|
|
631
|
+
Bold design that commands attention and improves user
|
|
632
|
+
experience.
|
|
633
|
+
</p>
|
|
634
|
+
</div>
|
|
635
|
+
</TabsContent>
|
|
636
|
+
</Tabs>
|
|
637
|
+
</div>
|
|
638
|
+
</div>
|
|
639
|
+
),
|
|
640
|
+
parameters: {
|
|
641
|
+
docs: {
|
|
642
|
+
description: {
|
|
643
|
+
story:
|
|
644
|
+
"All three size variants (small, medium, large) showing different use cases and visual hierarchy. Notice how the size is set once on the Tabs component instead of each individual trigger.",
|
|
645
|
+
},
|
|
646
|
+
},
|
|
647
|
+
},
|
|
648
|
+
}
|
|
649
|
+
|
|
650
|
+
// 4. Individual Size Override
|
|
651
|
+
export const IndividualSizeOverride: Story = {
|
|
652
|
+
render: () => (
|
|
653
|
+
<div className="w-full max-w-3xl space-y-6">
|
|
654
|
+
<div className="text-center">
|
|
655
|
+
<h3 className="mb-2 text-lg font-medium text-white">
|
|
656
|
+
Individual Size Override
|
|
657
|
+
</h3>
|
|
658
|
+
<p className="text-sm text-white/70">
|
|
659
|
+
Tabs component has size="md" set, but individual triggers can override
|
|
660
|
+
with their own size prop
|
|
661
|
+
</p>
|
|
662
|
+
</div>
|
|
663
|
+
|
|
664
|
+
<Tabs defaultValue="normal" size="md" className="w-full">
|
|
665
|
+
<TabsList className="grid w-full grid-cols-4">
|
|
666
|
+
<TabsTrigger value="small" size="sm">
|
|
667
|
+
Small Override
|
|
668
|
+
</TabsTrigger>
|
|
669
|
+
<TabsTrigger value="normal">Normal (md)</TabsTrigger>
|
|
670
|
+
<TabsTrigger value="normal2">Normal (md)</TabsTrigger>
|
|
671
|
+
<TabsTrigger value="large" size="lg">
|
|
672
|
+
Large Override
|
|
673
|
+
</TabsTrigger>
|
|
674
|
+
</TabsList>
|
|
675
|
+
|
|
676
|
+
<TabsContent value="small" className="mt-6">
|
|
677
|
+
<div className="rounded-lg border border-white/10 bg-white/5 p-6">
|
|
678
|
+
<h3 className="mb-4 text-lg font-semibold text-white">
|
|
679
|
+
Small Override
|
|
680
|
+
</h3>
|
|
681
|
+
<p className="text-white/70">
|
|
682
|
+
This tab trigger has{" "}
|
|
683
|
+
<code className="rounded bg-white/10 px-2 py-1 text-sm">
|
|
684
|
+
size="sm"
|
|
685
|
+
</code>{" "}
|
|
686
|
+
which overrides the parent Tabs component's{" "}
|
|
687
|
+
<code className="rounded bg-white/10 px-2 py-1 text-sm">
|
|
688
|
+
size="md"
|
|
689
|
+
</code>{" "}
|
|
690
|
+
setting.
|
|
691
|
+
</p>
|
|
692
|
+
<div className="mt-4 rounded-lg border border-blue-500/20 bg-blue-500/10 p-3">
|
|
693
|
+
<div className="text-sm text-blue-200">
|
|
694
|
+
<strong>Use case:</strong> When you need most tabs to be medium
|
|
695
|
+
size but want to emphasize or de-emphasize specific tabs.
|
|
696
|
+
</div>
|
|
697
|
+
</div>
|
|
698
|
+
</div>
|
|
699
|
+
</TabsContent>
|
|
700
|
+
|
|
701
|
+
<TabsContent value="normal" className="mt-6">
|
|
702
|
+
<div className="rounded-lg border border-white/10 bg-white/5 p-6">
|
|
703
|
+
<h3 className="mb-4 text-lg font-semibold text-white">
|
|
704
|
+
Normal Size
|
|
705
|
+
</h3>
|
|
706
|
+
<p className="text-white/70">
|
|
707
|
+
This tab uses the default size inherited from the parent Tabs
|
|
708
|
+
component (
|
|
709
|
+
<code className="rounded bg-white/10 px-2 py-1 text-sm">
|
|
710
|
+
size="md"
|
|
711
|
+
</code>
|
|
712
|
+
).
|
|
713
|
+
</p>
|
|
714
|
+
<div className="mt-4 grid grid-cols-2 gap-4">
|
|
715
|
+
<div className="rounded-lg border border-green-500/20 bg-green-500/10 p-3">
|
|
716
|
+
<div className="text-sm text-green-200">
|
|
717
|
+
Consistent sizing across most tabs
|
|
718
|
+
</div>
|
|
719
|
+
</div>
|
|
720
|
+
<div className="rounded-lg border border-purple-500/20 bg-purple-500/10 p-3">
|
|
721
|
+
<div className="text-sm text-purple-200">
|
|
722
|
+
Clean, unified appearance
|
|
723
|
+
</div>
|
|
724
|
+
</div>
|
|
725
|
+
</div>
|
|
726
|
+
</div>
|
|
727
|
+
</TabsContent>
|
|
728
|
+
|
|
729
|
+
<TabsContent value="normal2" className="mt-6">
|
|
730
|
+
<div className="rounded-lg border border-white/10 bg-white/5 p-6">
|
|
731
|
+
<h3 className="mb-4 text-lg font-semibold text-white">
|
|
732
|
+
Another Normal Tab
|
|
733
|
+
</h3>
|
|
734
|
+
<p className="text-white/70">
|
|
735
|
+
Another tab using the inherited medium size from the parent
|
|
736
|
+
component.
|
|
737
|
+
</p>
|
|
738
|
+
<div className="mt-4 space-y-3">
|
|
739
|
+
<div className="flex items-center gap-3 rounded-lg bg-white/5 p-3">
|
|
740
|
+
<TickCircleIcon className="h-5 w-5 text-green-400" />
|
|
741
|
+
<span className="text-white/70">
|
|
742
|
+
Inherits parent size automatically
|
|
743
|
+
</span>
|
|
744
|
+
</div>
|
|
745
|
+
<div className="flex items-center gap-3 rounded-lg bg-white/5 p-3">
|
|
746
|
+
<TickCircleIcon className="h-5 w-5 text-green-400" />
|
|
747
|
+
<span className="text-white/70">
|
|
748
|
+
No need to specify size prop
|
|
749
|
+
</span>
|
|
750
|
+
</div>
|
|
751
|
+
<div className="flex items-center gap-3 rounded-lg bg-white/5 p-3">
|
|
752
|
+
<TickCircleIcon className="h-5 w-5 text-green-400" />
|
|
753
|
+
<span className="text-white/70">
|
|
754
|
+
Maintains consistent appearance
|
|
755
|
+
</span>
|
|
756
|
+
</div>
|
|
757
|
+
</div>
|
|
758
|
+
</div>
|
|
759
|
+
</TabsContent>
|
|
760
|
+
|
|
761
|
+
<TabsContent value="large" className="mt-6">
|
|
762
|
+
<div className="rounded-lg border border-white/10 bg-white/5 p-6">
|
|
763
|
+
<h3 className="mb-4 text-lg font-semibold text-white">
|
|
764
|
+
Large Override
|
|
765
|
+
</h3>
|
|
766
|
+
<p className="text-white/70">
|
|
767
|
+
This tab trigger has{" "}
|
|
768
|
+
<code className="rounded bg-white/10 px-2 py-1 text-sm">
|
|
769
|
+
size="lg"
|
|
770
|
+
</code>{" "}
|
|
771
|
+
which overrides the parent's medium size setting, making it more
|
|
772
|
+
prominent.
|
|
773
|
+
</p>
|
|
774
|
+
<div className="mt-4 rounded-lg border border-orange-500/20 bg-orange-500/10 p-3">
|
|
775
|
+
<div className="text-sm text-orange-200">
|
|
776
|
+
<strong>Use case:</strong> Call-to-action tabs, primary
|
|
777
|
+
navigation items, or tabs that need extra visual emphasis in
|
|
778
|
+
your interface.
|
|
779
|
+
</div>
|
|
780
|
+
</div>
|
|
781
|
+
<div className="mt-4 grid grid-cols-1 gap-4 md:grid-cols-2">
|
|
782
|
+
<div className="rounded-lg border border-blue-500/30 bg-gradient-to-br from-blue-500/20 to-purple-500/20 p-4">
|
|
783
|
+
<div className="text-lg font-semibold text-white">Enhanced</div>
|
|
784
|
+
<div className="text-sm text-white/70">Better visibility</div>
|
|
785
|
+
</div>
|
|
786
|
+
<div className="rounded-lg border border-green-500/30 bg-gradient-to-br from-green-500/20 to-teal-500/20 p-4">
|
|
787
|
+
<div className="text-lg font-semibold text-white">
|
|
788
|
+
Prominent
|
|
789
|
+
</div>
|
|
790
|
+
<div className="text-sm text-white/70">Draws attention</div>
|
|
791
|
+
</div>
|
|
792
|
+
</div>
|
|
793
|
+
</div>
|
|
794
|
+
</TabsContent>
|
|
795
|
+
</Tabs>
|
|
796
|
+
|
|
797
|
+
<div className="space-y-1 text-center text-xs text-white/60">
|
|
798
|
+
<p>
|
|
799
|
+
Parent Tabs component:{" "}
|
|
800
|
+
<code className="rounded bg-white/10 px-2 py-0.5 font-mono">
|
|
801
|
+
size="md"
|
|
802
|
+
</code>
|
|
803
|
+
</p>
|
|
804
|
+
<p>Individual overrides: Tab 1 (sm), Tab 4 (lg)</p>
|
|
805
|
+
</div>
|
|
806
|
+
</div>
|
|
807
|
+
),
|
|
808
|
+
parameters: {
|
|
809
|
+
docs: {
|
|
810
|
+
description: {
|
|
811
|
+
story:
|
|
812
|
+
"Demonstrates how individual TabsTrigger components can override the parent Tabs size setting. The parent has size='md' but individual triggers can specify their own size for special emphasis.",
|
|
813
|
+
},
|
|
814
|
+
},
|
|
815
|
+
},
|
|
816
|
+
}
|
|
817
|
+
|
|
818
|
+
// 5. Complex Content (Updated to use size prop)
|
|
819
|
+
export const ComplexContent: Story = {
|
|
820
|
+
render: () => (
|
|
821
|
+
<div className="w-full max-w-4xl">
|
|
822
|
+
<Tabs defaultValue="products" size="md" className="w-full">
|
|
823
|
+
<TabsList className="grid w-full grid-cols-4">
|
|
824
|
+
<TabsTrigger value="products" className="gap-2">
|
|
825
|
+
<SearchIcon className="h-4 w-4" />
|
|
826
|
+
Products
|
|
827
|
+
</TabsTrigger>
|
|
828
|
+
<TabsTrigger value="customers" className="gap-2">
|
|
829
|
+
<EyeOpenIcon className="h-4 w-4" />
|
|
830
|
+
Customers
|
|
831
|
+
</TabsTrigger>
|
|
832
|
+
<TabsTrigger value="orders" className="gap-2">
|
|
833
|
+
<FileChartIcon className="h-4 w-4" />
|
|
834
|
+
Orders
|
|
835
|
+
</TabsTrigger>
|
|
836
|
+
<TabsTrigger value="analytics" className="gap-2" size="lg">
|
|
837
|
+
<TickCircleIcon className="h-4 w-4" />
|
|
838
|
+
Analytics
|
|
839
|
+
</TabsTrigger>
|
|
840
|
+
</TabsList>
|
|
841
|
+
|
|
842
|
+
<TabsContent value="products" className="mt-6">
|
|
843
|
+
<div className="space-y-4">
|
|
844
|
+
<div className="flex items-center justify-between">
|
|
845
|
+
<h3 className="text-lg font-semibold text-white">
|
|
846
|
+
Product Catalog
|
|
847
|
+
</h3>
|
|
848
|
+
<button className="flex items-center gap-2 rounded-lg bg-blue-500 px-4 py-2 text-white transition-colors hover:bg-blue-600">
|
|
849
|
+
<PlusIcon className="h-4 w-4" />
|
|
850
|
+
Add Product
|
|
851
|
+
</button>
|
|
852
|
+
</div>
|
|
853
|
+
|
|
854
|
+
<div className="grid grid-cols-1 gap-4 md:grid-cols-2 lg:grid-cols-3">
|
|
855
|
+
{[
|
|
856
|
+
{
|
|
857
|
+
name: "Wireless Headphones",
|
|
858
|
+
price: "$199",
|
|
859
|
+
category: "Electronics",
|
|
860
|
+
stock: 45,
|
|
861
|
+
},
|
|
862
|
+
{
|
|
863
|
+
name: "Smart Watch",
|
|
864
|
+
price: "$299",
|
|
865
|
+
category: "Wearables",
|
|
866
|
+
stock: 23,
|
|
867
|
+
},
|
|
868
|
+
{
|
|
869
|
+
name: "Laptop Stand",
|
|
870
|
+
price: "$49",
|
|
871
|
+
category: "Accessories",
|
|
872
|
+
stock: 67,
|
|
873
|
+
},
|
|
874
|
+
{
|
|
875
|
+
name: "USB-C Cable",
|
|
876
|
+
price: "$29",
|
|
877
|
+
category: "Cables",
|
|
878
|
+
stock: 156,
|
|
879
|
+
},
|
|
880
|
+
{
|
|
881
|
+
name: "Wireless Mouse",
|
|
882
|
+
price: "$79",
|
|
883
|
+
category: "Electronics",
|
|
884
|
+
stock: 34,
|
|
885
|
+
},
|
|
886
|
+
{
|
|
887
|
+
name: "Keyboard",
|
|
888
|
+
price: "$149",
|
|
889
|
+
category: "Electronics",
|
|
890
|
+
stock: 28,
|
|
891
|
+
},
|
|
892
|
+
].map((product, index) => (
|
|
893
|
+
<div
|
|
894
|
+
key={index}
|
|
895
|
+
className="rounded-lg border border-white/10 bg-white/5 p-4 transition-colors hover:bg-white/10"
|
|
896
|
+
>
|
|
897
|
+
<div className="mb-3 flex aspect-square items-center justify-center rounded-lg bg-gradient-to-br from-purple-500/20 to-pink-500/20">
|
|
898
|
+
<SearchIcon className="h-8 w-8 text-white/50" />
|
|
899
|
+
</div>
|
|
900
|
+
<h4 className="mb-1 font-medium text-white">
|
|
901
|
+
{product.name}
|
|
902
|
+
</h4>
|
|
903
|
+
<p className="mb-2 text-sm text-white/60">
|
|
904
|
+
{product.category}
|
|
905
|
+
</p>
|
|
906
|
+
<div className="flex items-center justify-between">
|
|
907
|
+
<span className="font-semibold text-white">
|
|
908
|
+
{product.price}
|
|
909
|
+
</span>
|
|
910
|
+
<span className="text-xs text-white/60">
|
|
911
|
+
{product.stock} in stock
|
|
912
|
+
</span>
|
|
913
|
+
</div>
|
|
914
|
+
</div>
|
|
915
|
+
))}
|
|
916
|
+
</div>
|
|
917
|
+
</div>
|
|
918
|
+
</TabsContent>
|
|
919
|
+
|
|
920
|
+
<TabsContent value="customers" className="mt-6">
|
|
921
|
+
<div className="space-y-4">
|
|
922
|
+
<div className="flex items-center justify-between">
|
|
923
|
+
<h3 className="text-lg font-semibold text-white">
|
|
924
|
+
Customer Directory
|
|
925
|
+
</h3>
|
|
926
|
+
<div className="flex gap-2">
|
|
927
|
+
<button className="rounded bg-white/10 px-3 py-1 text-sm text-white transition-colors hover:bg-white/20">
|
|
928
|
+
Export
|
|
929
|
+
</button>
|
|
930
|
+
<button className="rounded bg-blue-500 px-3 py-1 text-sm text-white transition-colors hover:bg-blue-600">
|
|
931
|
+
Add Customer
|
|
932
|
+
</button>
|
|
933
|
+
</div>
|
|
934
|
+
</div>
|
|
935
|
+
|
|
936
|
+
<div className="space-y-2">
|
|
937
|
+
{[
|
|
938
|
+
{
|
|
939
|
+
name: "Alice Cooper",
|
|
940
|
+
email: "alice@example.com",
|
|
941
|
+
orders: 12,
|
|
942
|
+
value: "$2,847",
|
|
943
|
+
},
|
|
944
|
+
{
|
|
945
|
+
name: "Bob Martinez",
|
|
946
|
+
email: "bob@example.com",
|
|
947
|
+
orders: 8,
|
|
948
|
+
value: "$1,923",
|
|
949
|
+
},
|
|
950
|
+
{
|
|
951
|
+
name: "Carol Johnson",
|
|
952
|
+
email: "carol@example.com",
|
|
953
|
+
orders: 15,
|
|
954
|
+
value: "$3,456",
|
|
955
|
+
},
|
|
956
|
+
{
|
|
957
|
+
name: "David Kim",
|
|
958
|
+
email: "david@example.com",
|
|
959
|
+
orders: 6,
|
|
960
|
+
value: "$1,234",
|
|
961
|
+
},
|
|
962
|
+
{
|
|
963
|
+
name: "Eva Rodriguez",
|
|
964
|
+
email: "eva@example.com",
|
|
965
|
+
orders: 22,
|
|
966
|
+
value: "$4,567",
|
|
967
|
+
},
|
|
968
|
+
].map((customer, index) => (
|
|
969
|
+
<div
|
|
970
|
+
key={index}
|
|
971
|
+
className="flex items-center justify-between rounded-lg border border-white/10 bg-white/5 p-4 transition-colors hover:bg-white/10"
|
|
972
|
+
>
|
|
973
|
+
<div className="flex items-center gap-3">
|
|
974
|
+
<div className="flex h-10 w-10 items-center justify-center rounded-full bg-gradient-to-br from-blue-500 to-purple-500">
|
|
975
|
+
<span className="text-sm font-semibold text-white">
|
|
976
|
+
{customer.name
|
|
977
|
+
.split(" ")
|
|
978
|
+
.map((n) => n[0])
|
|
979
|
+
.join("")}
|
|
980
|
+
</span>
|
|
981
|
+
</div>
|
|
982
|
+
<div>
|
|
983
|
+
<div className="font-medium text-white">
|
|
984
|
+
{customer.name}
|
|
985
|
+
</div>
|
|
986
|
+
<div className="text-sm text-white/60">
|
|
987
|
+
{customer.email}
|
|
988
|
+
</div>
|
|
989
|
+
</div>
|
|
990
|
+
</div>
|
|
991
|
+
<div className="text-right">
|
|
992
|
+
<div className="font-medium text-white">
|
|
993
|
+
{customer.value}
|
|
994
|
+
</div>
|
|
995
|
+
<div className="text-sm text-white/60">
|
|
996
|
+
{customer.orders} orders
|
|
997
|
+
</div>
|
|
998
|
+
</div>
|
|
999
|
+
</div>
|
|
1000
|
+
))}
|
|
1001
|
+
</div>
|
|
1002
|
+
</div>
|
|
1003
|
+
</TabsContent>
|
|
1004
|
+
|
|
1005
|
+
<TabsContent value="orders" className="mt-6">
|
|
1006
|
+
<div className="space-y-4">
|
|
1007
|
+
<div className="flex items-center justify-between">
|
|
1008
|
+
<h3 className="text-lg font-semibold text-white">
|
|
1009
|
+
Recent Orders
|
|
1010
|
+
</h3>
|
|
1011
|
+
<div className="flex gap-2">
|
|
1012
|
+
<select className="rounded border border-white/20 bg-white/10 px-3 py-1 text-sm text-white">
|
|
1013
|
+
<option>All Status</option>
|
|
1014
|
+
<option>Pending</option>
|
|
1015
|
+
<option>Processing</option>
|
|
1016
|
+
<option>Shipped</option>
|
|
1017
|
+
<option>Delivered</option>
|
|
1018
|
+
</select>
|
|
1019
|
+
</div>
|
|
1020
|
+
</div>
|
|
1021
|
+
|
|
1022
|
+
<div className="space-y-3">
|
|
1023
|
+
{[
|
|
1024
|
+
{
|
|
1025
|
+
id: "#ORD-001",
|
|
1026
|
+
customer: "Alice Cooper",
|
|
1027
|
+
total: "$247.99",
|
|
1028
|
+
status: "delivered",
|
|
1029
|
+
date: "2 hours ago",
|
|
1030
|
+
},
|
|
1031
|
+
{
|
|
1032
|
+
id: "#ORD-002",
|
|
1033
|
+
customer: "Bob Martinez",
|
|
1034
|
+
total: "$89.50",
|
|
1035
|
+
status: "shipped",
|
|
1036
|
+
date: "4 hours ago",
|
|
1037
|
+
},
|
|
1038
|
+
{
|
|
1039
|
+
id: "#ORD-003",
|
|
1040
|
+
customer: "Carol Johnson",
|
|
1041
|
+
total: "$156.75",
|
|
1042
|
+
status: "processing",
|
|
1043
|
+
date: "6 hours ago",
|
|
1044
|
+
},
|
|
1045
|
+
{
|
|
1046
|
+
id: "#ORD-004",
|
|
1047
|
+
customer: "David Kim",
|
|
1048
|
+
total: "$324.00",
|
|
1049
|
+
status: "pending",
|
|
1050
|
+
date: "8 hours ago",
|
|
1051
|
+
},
|
|
1052
|
+
{
|
|
1053
|
+
id: "#ORD-005",
|
|
1054
|
+
customer: "Eva Rodriguez",
|
|
1055
|
+
total: "$78.25",
|
|
1056
|
+
status: "delivered",
|
|
1057
|
+
date: "1 day ago",
|
|
1058
|
+
},
|
|
1059
|
+
].map((order, index) => (
|
|
1060
|
+
<div
|
|
1061
|
+
key={index}
|
|
1062
|
+
className="flex items-center justify-between rounded-lg border border-white/10 bg-white/5 p-4 transition-colors hover:bg-white/10"
|
|
1063
|
+
>
|
|
1064
|
+
<div className="flex items-center gap-4">
|
|
1065
|
+
<div>
|
|
1066
|
+
<div className="font-medium text-white">{order.id}</div>
|
|
1067
|
+
<div className="text-sm text-white/60">
|
|
1068
|
+
{order.customer}
|
|
1069
|
+
</div>
|
|
1070
|
+
</div>
|
|
1071
|
+
</div>
|
|
1072
|
+
<div className="flex items-center gap-4">
|
|
1073
|
+
<div className="text-right">
|
|
1074
|
+
<div className="font-medium text-white">
|
|
1075
|
+
{order.total}
|
|
1076
|
+
</div>
|
|
1077
|
+
<div className="text-sm text-white/60">{order.date}</div>
|
|
1078
|
+
</div>
|
|
1079
|
+
<span
|
|
1080
|
+
className={`rounded-full px-2 py-1 text-xs ${
|
|
1081
|
+
order.status === "delivered"
|
|
1082
|
+
? "bg-green-500/20 text-green-400"
|
|
1083
|
+
: order.status === "shipped"
|
|
1084
|
+
? "bg-blue-500/20 text-blue-400"
|
|
1085
|
+
: order.status === "processing"
|
|
1086
|
+
? "bg-yellow-500/20 text-yellow-400"
|
|
1087
|
+
: "bg-gray-500/20 text-gray-400"
|
|
1088
|
+
}`}
|
|
1089
|
+
>
|
|
1090
|
+
{order.status}
|
|
1091
|
+
</span>
|
|
1092
|
+
</div>
|
|
1093
|
+
</div>
|
|
1094
|
+
))}
|
|
1095
|
+
</div>
|
|
1096
|
+
</div>
|
|
1097
|
+
</TabsContent>
|
|
1098
|
+
|
|
1099
|
+
<TabsContent value="analytics" className="mt-6">
|
|
1100
|
+
<div className="space-y-6">
|
|
1101
|
+
<div className="flex items-center gap-3">
|
|
1102
|
+
<TickCircleIcon className="h-6 w-6 text-green-400" />
|
|
1103
|
+
<h3 className="text-lg font-semibold text-white">
|
|
1104
|
+
Sales Analytics
|
|
1105
|
+
</h3>
|
|
1106
|
+
<span className="rounded-full bg-green-500/20 px-3 py-1 text-xs text-green-400">
|
|
1107
|
+
Large Tab
|
|
1108
|
+
</span>
|
|
1109
|
+
</div>
|
|
1110
|
+
|
|
1111
|
+
<div className="grid grid-cols-1 gap-4 md:grid-cols-2 lg:grid-cols-4">
|
|
1112
|
+
<div className="rounded-lg border border-blue-500/30 bg-gradient-to-br from-blue-500/20 to-cyan-500/20 p-4">
|
|
1113
|
+
<div className="text-2xl font-bold text-white">$45,231</div>
|
|
1114
|
+
<div className="text-sm text-white/70">Revenue This Month</div>
|
|
1115
|
+
<div className="mt-1 text-xs text-green-400">
|
|
1116
|
+
↗ +12% vs last month
|
|
1117
|
+
</div>
|
|
1118
|
+
</div>
|
|
1119
|
+
<div className="rounded-lg border border-green-500/30 bg-gradient-to-br from-green-500/20 to-emerald-500/20 p-4">
|
|
1120
|
+
<div className="text-2xl font-bold text-white">1,847</div>
|
|
1121
|
+
<div className="text-sm text-white/70">Orders This Month</div>
|
|
1122
|
+
<div className="mt-1 text-xs text-green-400">
|
|
1123
|
+
↗ +8% vs last month
|
|
1124
|
+
</div>
|
|
1125
|
+
</div>
|
|
1126
|
+
<div className="rounded-lg border border-purple-500/30 bg-gradient-to-br from-purple-500/20 to-pink-500/20 p-4">
|
|
1127
|
+
<div className="text-2xl font-bold text-white">324</div>
|
|
1128
|
+
<div className="text-sm text-white/70">New Customers</div>
|
|
1129
|
+
<div className="mt-1 text-xs text-green-400">
|
|
1130
|
+
↗ +15% vs last month
|
|
1131
|
+
</div>
|
|
1132
|
+
</div>
|
|
1133
|
+
<div className="rounded-lg border border-orange-500/30 bg-gradient-to-br from-orange-500/20 to-red-500/20 p-4">
|
|
1134
|
+
<div className="text-2xl font-bold text-white">$24.50</div>
|
|
1135
|
+
<div className="text-sm text-white/70">Avg Order Value</div>
|
|
1136
|
+
<div className="mt-1 text-xs text-red-400">
|
|
1137
|
+
↘ -3% vs last month
|
|
1138
|
+
</div>
|
|
1139
|
+
</div>
|
|
1140
|
+
</div>
|
|
1141
|
+
|
|
1142
|
+
<div className="rounded-lg border border-amber-500/20 bg-amber-500/10 p-4">
|
|
1143
|
+
<div className="text-sm text-amber-200">
|
|
1144
|
+
<strong>Note:</strong> The Analytics tab uses{" "}
|
|
1145
|
+
<code className="rounded bg-white/10 px-2 py-1">size="lg"</code>
|
|
1146
|
+
to emphasize its importance as the primary data view, while
|
|
1147
|
+
other tabs inherit the default medium size.
|
|
1148
|
+
</div>
|
|
1149
|
+
</div>
|
|
1150
|
+
</div>
|
|
1151
|
+
</TabsContent>
|
|
1152
|
+
</Tabs>
|
|
1153
|
+
</div>
|
|
1154
|
+
),
|
|
1155
|
+
parameters: {
|
|
1156
|
+
docs: {
|
|
1157
|
+
description: {
|
|
1158
|
+
story:
|
|
1159
|
+
"Complex e-commerce admin interface demonstrating the new size prop functionality. The parent Tabs has size='md' but the Analytics tab uses size='lg' to emphasize its importance.",
|
|
1160
|
+
},
|
|
1161
|
+
},
|
|
1162
|
+
},
|
|
1163
|
+
}
|
|
1164
|
+
|
|
1165
|
+
// 6. Interactive States (keeping the same as it demonstrates good functionality)
|
|
1166
|
+
export const InteractiveStates: Story = {
|
|
1167
|
+
render: () => {
|
|
1168
|
+
const [activeTab, setActiveTab] = React.useState("normal")
|
|
1169
|
+
const [isLoading, setIsLoading] = React.useState(false)
|
|
1170
|
+
|
|
1171
|
+
const handleTabChange = (value: string) => {
|
|
1172
|
+
setIsLoading(true)
|
|
1173
|
+
setActiveTab(value)
|
|
1174
|
+
|
|
1175
|
+
// Simulate loading
|
|
1176
|
+
setTimeout(() => {
|
|
1177
|
+
setIsLoading(false)
|
|
1178
|
+
}, 1000)
|
|
1179
|
+
}
|
|
1180
|
+
|
|
1181
|
+
return (
|
|
1182
|
+
<div className="w-full max-w-3xl space-y-6">
|
|
1183
|
+
<div className="text-center">
|
|
1184
|
+
<h3 className="mb-2 text-lg font-medium text-white">
|
|
1185
|
+
Interactive States Demo
|
|
1186
|
+
</h3>
|
|
1187
|
+
<p className="text-sm text-white/70">
|
|
1188
|
+
Click tabs to see loading states and transitions
|
|
1189
|
+
</p>
|
|
1190
|
+
</div>
|
|
1191
|
+
|
|
1192
|
+
<Tabs
|
|
1193
|
+
value={activeTab}
|
|
1194
|
+
onValueChange={handleTabChange}
|
|
1195
|
+
size="md"
|
|
1196
|
+
className="w-full"
|
|
1197
|
+
>
|
|
1198
|
+
<TabsList className="grid w-full grid-cols-4">
|
|
1199
|
+
<TabsTrigger value="normal" className="gap-2">
|
|
1200
|
+
<TickCircleIcon className="h-4 w-4" />
|
|
1201
|
+
Normal
|
|
1202
|
+
</TabsTrigger>
|
|
1203
|
+
<TabsTrigger value="loading" className="gap-2" disabled={isLoading}>
|
|
1204
|
+
{isLoading && activeTab === "loading" ? (
|
|
1205
|
+
<div className="h-4 w-4 animate-spin rounded-full border-2 border-white/30 border-t-white" />
|
|
1206
|
+
) : (
|
|
1207
|
+
<AlertIcon className="h-4 w-4" />
|
|
1208
|
+
)}
|
|
1209
|
+
Loading
|
|
1210
|
+
</TabsTrigger>
|
|
1211
|
+
<TabsTrigger value="error" className="gap-2">
|
|
1212
|
+
<CrossIcon className="h-4 w-4" />
|
|
1213
|
+
Error
|
|
1214
|
+
</TabsTrigger>
|
|
1215
|
+
<TabsTrigger value="success" className="gap-2">
|
|
1216
|
+
<TickCircleIcon className="h-4 w-4" />
|
|
1217
|
+
Success
|
|
1218
|
+
</TabsTrigger>
|
|
1219
|
+
</TabsList>
|
|
1220
|
+
|
|
1221
|
+
<TabsContent value="normal" className="mt-6">
|
|
1222
|
+
<div className="rounded-lg border border-white/10 bg-white/5 p-6">
|
|
1223
|
+
<h3 className="mb-4 text-lg font-semibold text-white">
|
|
1224
|
+
Normal State
|
|
1225
|
+
</h3>
|
|
1226
|
+
<p className="mb-4 text-white/70">
|
|
1227
|
+
This is the default state of the component with all
|
|
1228
|
+
functionality working normally.
|
|
1229
|
+
</p>
|
|
1230
|
+
<div className="grid grid-cols-2 gap-4">
|
|
1231
|
+
<div className="rounded-lg border border-blue-500/20 bg-blue-500/10 p-3">
|
|
1232
|
+
<div className="text-lg font-semibold text-white">98.5%</div>
|
|
1233
|
+
<div className="text-sm text-white/70">System Uptime</div>
|
|
1234
|
+
</div>
|
|
1235
|
+
<div className="rounded-lg border border-green-500/20 bg-green-500/10 p-3">
|
|
1236
|
+
<div className="text-lg font-semibold text-white">1,247</div>
|
|
1237
|
+
<div className="text-sm text-white/70">Active Users</div>
|
|
1238
|
+
</div>
|
|
1239
|
+
</div>
|
|
1240
|
+
</div>
|
|
1241
|
+
</TabsContent>
|
|
1242
|
+
|
|
1243
|
+
<TabsContent value="loading" className="mt-6">
|
|
1244
|
+
<div className="rounded-lg border border-white/10 bg-white/5 p-6">
|
|
1245
|
+
{isLoading ? (
|
|
1246
|
+
<div className="py-8 text-center">
|
|
1247
|
+
<div className="mx-auto mb-4 h-8 w-8 animate-spin rounded-full border-2 border-white/30 border-t-white" />
|
|
1248
|
+
<h3 className="mb-2 text-lg font-semibold text-white">
|
|
1249
|
+
Loading Content...
|
|
1250
|
+
</h3>
|
|
1251
|
+
<p className="text-white/70">
|
|
1252
|
+
Please wait while we fetch the latest data.
|
|
1253
|
+
</p>
|
|
1254
|
+
</div>
|
|
1255
|
+
) : (
|
|
1256
|
+
<>
|
|
1257
|
+
<h3 className="mb-4 text-lg font-semibold text-white">
|
|
1258
|
+
Loading State Demo
|
|
1259
|
+
</h3>
|
|
1260
|
+
<p className="mb-4 text-white/70">
|
|
1261
|
+
This tab demonstrates loading states and async content
|
|
1262
|
+
fetching.
|
|
1263
|
+
</p>
|
|
1264
|
+
<div className="space-y-3">
|
|
1265
|
+
<div className="flex items-center gap-3 rounded-lg bg-white/5 p-3">
|
|
1266
|
+
<div className="flex h-5 w-5 items-center justify-center rounded-full bg-green-500">
|
|
1267
|
+
<TickCircleIcon className="h-3 w-3 text-white" />
|
|
1268
|
+
</div>
|
|
1269
|
+
<span className="text-white/70">
|
|
1270
|
+
Content loaded successfully
|
|
1271
|
+
</span>
|
|
1272
|
+
</div>
|
|
1273
|
+
<div className="flex items-center gap-3 rounded-lg bg-white/5 p-3">
|
|
1274
|
+
<div className="flex h-5 w-5 items-center justify-center rounded-full bg-blue-500">
|
|
1275
|
+
<AlertIcon className="h-3 w-3 text-white" />
|
|
1276
|
+
</div>
|
|
1277
|
+
<span className="text-white/70">
|
|
1278
|
+
Data synchronized with server
|
|
1279
|
+
</span>
|
|
1280
|
+
</div>
|
|
1281
|
+
</div>
|
|
1282
|
+
</>
|
|
1283
|
+
)}
|
|
1284
|
+
</div>
|
|
1285
|
+
</TabsContent>
|
|
1286
|
+
|
|
1287
|
+
<TabsContent value="error" className="mt-6">
|
|
1288
|
+
<div className="rounded-lg border border-red-500/20 bg-red-500/5 p-6">
|
|
1289
|
+
<div className="mb-4 flex items-start gap-3">
|
|
1290
|
+
<CrossIcon className="mt-0.5 h-6 w-6 flex-shrink-0 text-red-400" />
|
|
1291
|
+
<div>
|
|
1292
|
+
<h3 className="text-lg font-semibold text-white">
|
|
1293
|
+
Error State
|
|
1294
|
+
</h3>
|
|
1295
|
+
<p className="text-white/70">
|
|
1296
|
+
Something went wrong while loading the content.
|
|
1297
|
+
</p>
|
|
1298
|
+
</div>
|
|
1299
|
+
</div>
|
|
1300
|
+
|
|
1301
|
+
<div className="mb-4 rounded-lg border border-red-500/20 bg-red-500/10 p-4">
|
|
1302
|
+
<div className="text-sm text-red-200">
|
|
1303
|
+
<strong>Error:</strong> Failed to fetch data from the server.
|
|
1304
|
+
Please check your connection and try again.
|
|
1305
|
+
</div>
|
|
1306
|
+
</div>
|
|
1307
|
+
|
|
1308
|
+
<div className="flex gap-2">
|
|
1309
|
+
<button className="rounded-lg bg-red-500 px-4 py-2 text-white transition-colors hover:bg-red-600">
|
|
1310
|
+
Retry
|
|
1311
|
+
</button>
|
|
1312
|
+
<button className="rounded-lg bg-white/10 px-4 py-2 text-white transition-colors hover:bg-white/20">
|
|
1313
|
+
Report Issue
|
|
1314
|
+
</button>
|
|
1315
|
+
</div>
|
|
1316
|
+
</div>
|
|
1317
|
+
</TabsContent>
|
|
1318
|
+
|
|
1319
|
+
<TabsContent value="success" className="mt-6">
|
|
1320
|
+
<div className="rounded-lg border border-green-500/20 bg-green-500/5 p-6">
|
|
1321
|
+
<div className="mb-4 flex items-start gap-3">
|
|
1322
|
+
<TickCircleIcon className="mt-0.5 h-6 w-6 flex-shrink-0 text-green-400" />
|
|
1323
|
+
<div>
|
|
1324
|
+
<h3 className="text-lg font-semibold text-white">
|
|
1325
|
+
Success State
|
|
1326
|
+
</h3>
|
|
1327
|
+
<p className="text-white/70">
|
|
1328
|
+
Operation completed successfully!
|
|
1329
|
+
</p>
|
|
1330
|
+
</div>
|
|
1331
|
+
</div>
|
|
1332
|
+
|
|
1333
|
+
<div className="space-y-3">
|
|
1334
|
+
<div className="rounded-lg border border-green-500/20 bg-green-500/10 p-4">
|
|
1335
|
+
<div className="text-sm text-green-200">
|
|
1336
|
+
✅ All systems are operational and running smoothly.
|
|
1337
|
+
</div>
|
|
1338
|
+
</div>
|
|
1339
|
+
|
|
1340
|
+
<div className="grid grid-cols-3 gap-3">
|
|
1341
|
+
<div className="rounded-lg bg-white/5 p-3 text-center">
|
|
1342
|
+
<div className="text-lg font-semibold text-white">100%</div>
|
|
1343
|
+
<div className="text-xs text-white/60">Success Rate</div>
|
|
1344
|
+
</div>
|
|
1345
|
+
<div className="rounded-lg bg-white/5 p-3 text-center">
|
|
1346
|
+
<div className="text-lg font-semibold text-white">0ms</div>
|
|
1347
|
+
<div className="text-xs text-white/60">Error Rate</div>
|
|
1348
|
+
</div>
|
|
1349
|
+
<div className="rounded-lg bg-white/5 p-3 text-center">
|
|
1350
|
+
<div className="text-lg font-semibold text-white">Fast</div>
|
|
1351
|
+
<div className="text-xs text-white/60">Performance</div>
|
|
1352
|
+
</div>
|
|
1353
|
+
</div>
|
|
1354
|
+
</div>
|
|
1355
|
+
</div>
|
|
1356
|
+
</TabsContent>
|
|
1357
|
+
</Tabs>
|
|
1358
|
+
|
|
1359
|
+
<div className="text-center text-xs text-white/60">
|
|
1360
|
+
<p>
|
|
1361
|
+
Current active tab:{" "}
|
|
1362
|
+
<span className="rounded bg-white/10 px-2 py-0.5 font-mono">
|
|
1363
|
+
{activeTab}
|
|
1364
|
+
</span>
|
|
1365
|
+
</p>
|
|
1366
|
+
{isLoading && <p className="mt-1">Loading state active...</p>}
|
|
1367
|
+
</div>
|
|
1368
|
+
</div>
|
|
1369
|
+
)
|
|
1370
|
+
},
|
|
1371
|
+
parameters: {
|
|
1372
|
+
docs: {
|
|
1373
|
+
description: {
|
|
1374
|
+
story:
|
|
1375
|
+
"Interactive states demonstration showing loading, error, and success states with real-time tab switching using the new size prop approach.",
|
|
1376
|
+
},
|
|
1377
|
+
},
|
|
1378
|
+
},
|
|
1379
|
+
}
|