ai-design-system 0.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +307 -0
- package/components/ai-elements/actions.tsx +65 -0
- package/components/ai-elements/artifact.tsx +147 -0
- package/components/ai-elements/branch.tsx +212 -0
- package/components/ai-elements/canvas.tsx +24 -0
- package/components/ai-elements/chain-of-thought.tsx +228 -0
- package/components/ai-elements/code-block.tsx +179 -0
- package/components/ai-elements/confirmation.tsx +169 -0
- package/components/ai-elements/connection.tsx +28 -0
- package/components/ai-elements/context.tsx +408 -0
- package/components/ai-elements/controls.tsx +18 -0
- package/components/ai-elements/conversation.tsx +97 -0
- package/components/ai-elements/edge.tsx +140 -0
- package/components/ai-elements/image.tsx +24 -0
- package/components/ai-elements/inline-citation.tsx +287 -0
- package/components/ai-elements/loader.tsx +96 -0
- package/components/ai-elements/message.tsx +80 -0
- package/components/ai-elements/node.tsx +71 -0
- package/components/ai-elements/open-in-chat.tsx +363 -0
- package/components/ai-elements/panel.tsx +15 -0
- package/components/ai-elements/plan.tsx +142 -0
- package/components/ai-elements/prompt-input.tsx +1352 -0
- package/components/ai-elements/queue.tsx +274 -0
- package/components/ai-elements/reasoning.tsx +178 -0
- package/components/ai-elements/response.tsx +22 -0
- package/components/ai-elements/shimmer.tsx +64 -0
- package/components/ai-elements/sources.tsx +77 -0
- package/components/ai-elements/suggestion.tsx +56 -0
- package/components/ai-elements/task.tsx +87 -0
- package/components/ai-elements/tool.tsx +179 -0
- package/components/ai-elements/toolbar.tsx +16 -0
- package/components/ai-elements/web-preview.tsx +263 -0
- package/components/blocks/AIConversation/AIConversation.stories.tsx +164 -0
- package/components/blocks/AIConversation/AIConversation.tsx +186 -0
- package/components/blocks/AIConversation/index.ts +8 -0
- package/components/blocks/AppSidebar/AppSidebar.stories.tsx +63 -0
- package/components/blocks/AppSidebar/AppSidebar.tsx +87 -0
- package/components/blocks/AppSidebar/index.ts +2 -0
- package/components/blocks/DocumentEditorWithComments/DocumentEditorWithComments.stories.tsx +341 -0
- package/components/blocks/DocumentEditorWithComments/DocumentEditorWithComments.tsx +255 -0
- package/components/blocks/DocumentEditorWithComments/index.ts +9 -0
- package/components/blocks/FileChangeQueue/FileChangeQueue.stories.tsx +207 -0
- package/components/blocks/FileChangeQueue/FileChangeQueue.tsx +143 -0
- package/components/blocks/FileChangeQueue/index.ts +7 -0
- package/components/blocks/LayoutProvider/LayoutProvider.tsx +34 -0
- package/components/blocks/LayoutProvider/index.ts +1 -0
- package/components/blocks/index.ts +2 -0
- package/components/composites/AgentIndicator/AgentIndicator.stories.tsx +154 -0
- package/components/composites/AgentIndicator/AgentIndicator.tsx +102 -0
- package/components/composites/AgentIndicator/index.ts +8 -0
- package/components/composites/AppHeader/AppHeader.stories.tsx +46 -0
- package/components/composites/AppHeader/AppHeader.tsx +24 -0
- package/components/composites/AppHeader/index.ts +2 -0
- package/components/composites/CommentBox/CommentBox.stories.tsx +192 -0
- package/components/composites/CommentBox/CommentBox.tsx +364 -0
- package/components/composites/CommentBox/index.ts +8 -0
- package/components/composites/Confirmation/Confirmation.stories.tsx +151 -0
- package/components/composites/Confirmation/Confirmation.tsx +93 -0
- package/components/composites/Confirmation/index.ts +7 -0
- package/components/composites/DataTable/DataTable.stories.tsx +35 -0
- package/components/composites/DataTable/DataTable.tsx +95 -0
- package/components/composites/DataTable/index.ts +2 -0
- package/components/composites/DocumentEditor/DocumentEditor.css +106 -0
- package/components/composites/DocumentEditor/DocumentEditor.stories.tsx +927 -0
- package/components/composites/DocumentEditor/DocumentEditor.tsx +279 -0
- package/components/composites/DocumentEditor/index.ts +8 -0
- package/components/composites/FileQueue/FileQueue.stories.tsx +175 -0
- package/components/composites/FileQueue/FileQueue.tsx +161 -0
- package/components/composites/FileQueue/FileStatusBadge.tsx +74 -0
- package/components/composites/FileQueue/index.ts +24 -0
- package/components/composites/InteractiveChart/InteractiveChart.stories.tsx +49 -0
- package/components/composites/InteractiveChart/InteractiveChart.tsx +69 -0
- package/components/composites/InteractiveChart/index.ts +2 -0
- package/components/composites/ModeToggle/ModeToggle.stories.tsx +212 -0
- package/components/composites/ModeToggle/ModeToggle.tsx +100 -0
- package/components/composites/ModeToggle/index.ts +7 -0
- package/components/composites/NavUser/NavUser.stories.tsx +50 -0
- package/components/composites/NavUser/NavUser.tsx +60 -0
- package/components/composites/NavUser/index.ts +2 -0
- package/components/composites/NavigationList/NavigationList.stories.tsx +46 -0
- package/components/composites/NavigationList/NavigationList.tsx +46 -0
- package/components/composites/NavigationList/index.ts +2 -0
- package/components/composites/OrchestratorMessage/OrchestratorMessage.stories.tsx +188 -0
- package/components/composites/OrchestratorMessage/OrchestratorMessage.tsx +72 -0
- package/components/composites/OrchestratorMessage/index.ts +8 -0
- package/components/composites/PageContainer/PageContainer.stories.tsx +41 -0
- package/components/composites/PageContainer/PageContainer.tsx +24 -0
- package/components/composites/PageContainer/index.ts +2 -0
- package/components/composites/PromptInput/PromptInput.stories.tsx +200 -0
- package/components/composites/PromptInput/PromptInput.tsx +129 -0
- package/components/composites/PromptInput/index.ts +8 -0
- package/components/composites/SpecialistMessage/SpecialistMessage.stories.tsx +286 -0
- package/components/composites/SpecialistMessage/SpecialistMessage.tsx +107 -0
- package/components/composites/SpecialistMessage/index.ts +8 -0
- package/components/composites/StatsCard/StatsCard.stories.tsx +76 -0
- package/components/composites/StatsCard/StatsCard.tsx +81 -0
- package/components/composites/StatsCard/index.ts +2 -0
- package/components/composites/TablePagination/TablePagination.stories.tsx +38 -0
- package/components/composites/TablePagination/TablePagination.tsx +119 -0
- package/components/composites/TablePagination/index.ts +2 -0
- package/components/composites/TableToolbar/TableToolbar.stories.tsx +60 -0
- package/components/composites/TableToolbar/TableToolbar.tsx +66 -0
- package/components/composites/TableToolbar/index.ts +2 -0
- package/components/composites/ThemeSelector/ThemeSelector.stories.tsx +48 -0
- package/components/composites/ThemeSelector/ThemeSelector.tsx +79 -0
- package/components/composites/ThemeSelector/index.ts +2 -0
- package/components/composites/ToolCallDisplay/ToolCallDisplay.stories.tsx +49 -0
- package/components/composites/ToolCallDisplay/ToolCallDisplay.tsx +108 -0
- package/components/composites/ToolCallDisplay/index.ts +8 -0
- package/components/composites/UserMessage/UserMessage.stories.tsx +59 -0
- package/components/composites/UserMessage/UserMessage.tsx +52 -0
- package/components/composites/UserMessage/index.ts +8 -0
- package/components/composites/index.ts +90 -0
- package/components/features/AIDocEditor/AIDocEditor.behaviors.stories.tsx +451 -0
- package/components/features/AIDocEditor/AIDocEditor.mocks.ts +96 -0
- package/components/features/AIDocEditor/AIDocEditor.stories.tsx +140 -0
- package/components/features/AIDocEditor/AIDocEditor.tsx +130 -0
- package/components/features/AIDocEditor/index.ts +8 -0
- package/components/features/AIDocEditor/useAIDocEditor.d.ts +97 -0
- package/components/features/AIDocEditor/useAIDocEditor.mock.ts +83 -0
- package/components/features/PageLayout/PageLayout.behaviors.stories.tsx +119 -0
- package/components/features/PageLayout/PageLayout.mocks.ts +27 -0
- package/components/features/PageLayout/PageLayout.stories.tsx +142 -0
- package/components/features/PageLayout/PageLayout.tsx +94 -0
- package/components/features/PageLayout/index.ts +4 -0
- package/components/features/PageLayout/usePageLayout.d.ts +24 -0
- package/components/features/PageLayout/usePageLayout.mock.ts +19 -0
- package/components/features/RefinementPanel/README.md +189 -0
- package/components/features/RefinementPanel/RefinementPanel.behaviors.stories.tsx +475 -0
- package/components/features/RefinementPanel/RefinementPanel.mocks.ts +131 -0
- package/components/features/RefinementPanel/RefinementPanel.stories.tsx +141 -0
- package/components/features/RefinementPanel/RefinementPanel.tsx +160 -0
- package/components/features/RefinementPanel/index.ts +25 -0
- package/components/features/RefinementPanel/useRefinementPanel.d.ts +74 -0
- package/components/features/RefinementPanel/useRefinementPanel.mock.ts +121 -0
- package/components/features/SpecNavigator/SpecNavigator.behaviors.stories.tsx +379 -0
- package/components/features/SpecNavigator/SpecNavigator.mocks.ts +131 -0
- package/components/features/SpecNavigator/SpecNavigator.stories.tsx +122 -0
- package/components/features/SpecNavigator/SpecNavigator.tsx +43 -0
- package/components/features/SpecNavigator/index.ts +2 -0
- package/components/features/SpecNavigator/useSpecNavigator.d.ts +122 -0
- package/components/features/SpecNavigator/useSpecNavigator.mock.ts +93 -0
- package/components/features/index.ts +18 -0
- package/components/index.ts +14 -0
- package/components/primitives/Accordion/Accordion.stories.tsx +87 -0
- package/components/primitives/Accordion/Accordion.tsx +66 -0
- package/components/primitives/Accordion/index.ts +13 -0
- package/components/primitives/Alert/Alert.stories.tsx +422 -0
- package/components/primitives/Alert/Alert.tsx +61 -0
- package/components/primitives/Alert/index.ts +8 -0
- package/components/primitives/AlertDialog/AlertDialog.stories.tsx +367 -0
- package/components/primitives/AlertDialog/AlertDialog.tsx +182 -0
- package/components/primitives/AlertDialog/index.ts +25 -0
- package/components/primitives/Avatar/Avatar.stories.tsx +321 -0
- package/components/primitives/Avatar/Avatar.tsx +63 -0
- package/components/primitives/Avatar/index.ts +8 -0
- package/components/primitives/Badge/Badge.stories.tsx +74 -0
- package/components/primitives/Badge/Badge.tsx +49 -0
- package/components/primitives/Badge/index.ts +2 -0
- package/components/primitives/Button/Button.stories.tsx +445 -0
- package/components/primitives/Button/Button.tsx +89 -0
- package/components/primitives/Button/index.ts +7 -0
- package/components/primitives/Card/Card.stories.tsx +831 -0
- package/components/primitives/Card/Card.tsx +242 -0
- package/components/primitives/Card/index.ts +30 -0
- package/components/primitives/Carousel/Carousel.stories.tsx +32 -0
- package/components/primitives/Carousel/Carousel.tsx +63 -0
- package/components/primitives/Carousel/index.ts +13 -0
- package/components/primitives/Chart/Chart.stories.tsx +346 -0
- package/components/primitives/Chart/Chart.tsx +117 -0
- package/components/primitives/Chart/index.ts +20 -0
- package/components/primitives/Checkbox/Checkbox.stories.tsx +87 -0
- package/components/primitives/Checkbox/Checkbox.tsx +38 -0
- package/components/primitives/Checkbox/index.ts +2 -0
- package/components/primitives/Collapsible/Collapsible.stories.tsx +38 -0
- package/components/primitives/Collapsible/Collapsible.tsx +39 -0
- package/components/primitives/Collapsible/index.ts +8 -0
- package/components/primitives/Command/Command.stories.tsx +150 -0
- package/components/primitives/Command/Command.tsx +147 -0
- package/components/primitives/Command/index.ts +20 -0
- package/components/primitives/Dialog/Dialog.stories.tsx +390 -0
- package/components/primitives/Dialog/Dialog.tsx +140 -0
- package/components/primitives/Dialog/index.ts +22 -0
- package/components/primitives/Drawer/Drawer.stories.tsx +327 -0
- package/components/primitives/Drawer/Drawer.tsx +208 -0
- package/components/primitives/Drawer/index.ts +27 -0
- package/components/primitives/DropdownMenu/DropdownMenu.stories.tsx +150 -0
- package/components/primitives/DropdownMenu/DropdownMenu.tsx +73 -0
- package/components/primitives/DropdownMenu/index.ts +1 -0
- package/components/primitives/HoverCard/HoverCard.stories.tsx +26 -0
- package/components/primitives/HoverCard/HoverCard.tsx +39 -0
- package/components/primitives/HoverCard/index.ts +8 -0
- package/components/primitives/Icon/Icon.stories.tsx +281 -0
- package/components/primitives/Icon/Icon.tsx +87 -0
- package/components/primitives/Icon/index.ts +8 -0
- package/components/primitives/Input/Input.stories.tsx +370 -0
- package/components/primitives/Input/Input.tsx +88 -0
- package/components/primitives/Input/index.ts +7 -0
- package/components/primitives/InputGroup/InputGroup.stories.tsx +40 -0
- package/components/primitives/InputGroup/InputGroup.tsx +72 -0
- package/components/primitives/InputGroup/index.ts +14 -0
- package/components/primitives/Label/Label.stories.tsx +227 -0
- package/components/primitives/Label/Label.tsx +53 -0
- package/components/primitives/Label/index.ts +7 -0
- package/components/primitives/Popover/Popover.stories.tsx +42 -0
- package/components/primitives/Popover/Popover.tsx +107 -0
- package/components/primitives/Popover/index.ts +2 -0
- package/components/primitives/Progress/Progress.stories.tsx +340 -0
- package/components/primitives/Progress/Progress.tsx +31 -0
- package/components/primitives/Progress/index.ts +1 -0
- package/components/primitives/ScrollArea/ScrollArea.stories.tsx +26 -0
- package/components/primitives/ScrollArea/ScrollArea.tsx +28 -0
- package/components/primitives/ScrollArea/index.ts +6 -0
- package/components/primitives/Select/Select.stories.tsx +288 -0
- package/components/primitives/Select/Select.tsx +162 -0
- package/components/primitives/Select/index.ts +22 -0
- package/components/primitives/Separator/Separator.stories.tsx +264 -0
- package/components/primitives/Separator/Separator.tsx +48 -0
- package/components/primitives/Separator/index.ts +7 -0
- package/components/primitives/Sidebar/Sidebar.stories.tsx +358 -0
- package/components/primitives/Sidebar/Sidebar.tsx +317 -0
- package/components/primitives/Sidebar/index.ts +41 -0
- package/components/primitives/Table/Table.stories.tsx +389 -0
- package/components/primitives/Table/Table.tsx +191 -0
- package/components/primitives/Table/index.ts +26 -0
- package/components/primitives/Tabs/Tabs.stories.tsx +129 -0
- package/components/primitives/Tabs/Tabs.tsx +70 -0
- package/components/primitives/Tabs/index.ts +13 -0
- package/components/primitives/Textarea/Textarea.stories.tsx +358 -0
- package/components/primitives/Textarea/Textarea.tsx +91 -0
- package/components/primitives/Textarea/index.ts +7 -0
- package/components/primitives/ToggleGroup/ToggleGroup.stories.tsx +87 -0
- package/components/primitives/ToggleGroup/ToggleGroup.tsx +52 -0
- package/components/primitives/ToggleGroup/index.ts +6 -0
- package/components/primitives/Tooltip/Tooltip.stories.tsx +336 -0
- package/components/primitives/Tooltip/Tooltip.tsx +78 -0
- package/components/primitives/Tooltip/index.ts +10 -0
- package/components/primitives/index.ts +34 -0
- package/components/ui/accordion.tsx +66 -0
- package/components/ui/alert-dialog.tsx +157 -0
- package/components/ui/alert.tsx +66 -0
- package/components/ui/avatar.tsx +53 -0
- package/components/ui/badge.tsx +46 -0
- package/components/ui/button.tsx +60 -0
- package/components/ui/card.tsx +117 -0
- package/components/ui/carousel.tsx +241 -0
- package/components/ui/chart.tsx +334 -0
- package/components/ui/checkbox.tsx +32 -0
- package/components/ui/collapsible.tsx +33 -0
- package/components/ui/command.tsx +184 -0
- package/components/ui/dialog.tsx +143 -0
- package/components/ui/drawer.tsx +118 -0
- package/components/ui/dropdown-menu.tsx +257 -0
- package/components/ui/hover-card.tsx +44 -0
- package/components/ui/input-group.tsx +170 -0
- package/components/ui/input.tsx +48 -0
- package/components/ui/label.tsx +26 -0
- package/components/ui/popover.tsx +33 -0
- package/components/ui/progress.tsx +31 -0
- package/components/ui/scroll-area.tsx +58 -0
- package/components/ui/select.tsx +187 -0
- package/components/ui/separator.tsx +31 -0
- package/components/ui/sidebar.tsx +577 -0
- package/components/ui/table.tsx +120 -0
- package/components/ui/tabs.tsx +66 -0
- package/components/ui/textarea.tsx +46 -0
- package/components/ui/toggle-group.tsx +83 -0
- package/components/ui/toggle.tsx +47 -0
- package/components/ui/tooltip.tsx +61 -0
- package/dist/index.cjs +7389 -0
- package/dist/index.cjs.map +1 -0
- package/dist/index.css +75 -0
- package/dist/index.css.map +1 -0
- package/dist/index.js +7160 -0
- package/dist/index.js.map +1 -0
- package/hooks/useAIDocReviewer.d.ts +0 -0
- package/lib/utils.ts +6 -0
- package/package.json +140 -0
- package/tokens/color/base.json +14 -0
- package/tokens/color/dark.json +40 -0
- package/tokens/color/green.json +21 -0
- package/tokens/color/light.json +52 -0
- package/tokens/color/neutral.json +20 -0
- package/tokens/color/violet.json +21 -0
- package/tokens/spacing.json +22 -0
- package/utils/ai-editor/format-date.ts +41 -0
- package/utils/ai-editor/index.ts +22 -0
- package/utils/ai-editor/type-guards.ts +72 -0
- package/utils/ai-editor/validation.ts +130 -0
- package/utils/editor-annotations.ts +122 -0
|
@@ -0,0 +1,264 @@
|
|
|
1
|
+
import type { Meta, StoryObj } from '@storybook/react'
|
|
2
|
+
import { Separator } from './Separator'
|
|
3
|
+
|
|
4
|
+
/**
|
|
5
|
+
* Separator Primitive Stories
|
|
6
|
+
*
|
|
7
|
+
* The Separator component is a foundational primitive for visually dividing content.
|
|
8
|
+
* It extends shadcn/ui's Separator with design system-specific enhancements and maintains
|
|
9
|
+
* full accessibility compliance (WCAG 2.1 Level AA).
|
|
10
|
+
*
|
|
11
|
+
* ## Features
|
|
12
|
+
* - Horizontal and vertical orientations
|
|
13
|
+
* - Semantic HTML with proper ARIA attributes
|
|
14
|
+
* - Consistent styling across the application
|
|
15
|
+
* - Dark mode support
|
|
16
|
+
* - Decorative by default (not announced to screen readers)
|
|
17
|
+
*
|
|
18
|
+
* ## Accessibility
|
|
19
|
+
* - Uses semantic separator role
|
|
20
|
+
* - Decorative by default (aria-hidden)
|
|
21
|
+
* - Can be made non-decorative for semantic separators
|
|
22
|
+
* - Maintains proper color contrast ratios
|
|
23
|
+
*
|
|
24
|
+
* ## Usage Guidelines
|
|
25
|
+
*
|
|
26
|
+
* ### Do's
|
|
27
|
+
* - Use to visually separate content sections
|
|
28
|
+
* - Use horizontal separators for vertical content flow
|
|
29
|
+
* - Use vertical separators for horizontal content flow
|
|
30
|
+
* - Keep decorative for purely visual separators
|
|
31
|
+
*
|
|
32
|
+
* ### Don'ts
|
|
33
|
+
* - Don't use as a border replacement
|
|
34
|
+
* - Don't overuse - maintain visual hierarchy
|
|
35
|
+
* - Don't rely solely on separators to convey structure
|
|
36
|
+
*/
|
|
37
|
+
const meta = {
|
|
38
|
+
title: 'Primitives/Separator',
|
|
39
|
+
component: Separator,
|
|
40
|
+
tags: ['autodocs'],
|
|
41
|
+
argTypes: {
|
|
42
|
+
orientation: {
|
|
43
|
+
control: 'select',
|
|
44
|
+
options: ['horizontal', 'vertical'],
|
|
45
|
+
description: 'Orientation of the separator',
|
|
46
|
+
table: {
|
|
47
|
+
type: { summary: 'string' },
|
|
48
|
+
defaultValue: { summary: 'horizontal' },
|
|
49
|
+
},
|
|
50
|
+
},
|
|
51
|
+
decorative: {
|
|
52
|
+
control: 'boolean',
|
|
53
|
+
description: 'Whether the separator is purely decorative',
|
|
54
|
+
table: {
|
|
55
|
+
type: { summary: 'boolean' },
|
|
56
|
+
defaultValue: { summary: 'true' },
|
|
57
|
+
},
|
|
58
|
+
},
|
|
59
|
+
},
|
|
60
|
+
parameters: {
|
|
61
|
+
layout: 'centered',
|
|
62
|
+
docs: {
|
|
63
|
+
description: {
|
|
64
|
+
component: 'A visual separator component for dividing content, built on shadcn/ui foundation.',
|
|
65
|
+
},
|
|
66
|
+
},
|
|
67
|
+
},
|
|
68
|
+
} satisfies Meta<typeof Separator>
|
|
69
|
+
|
|
70
|
+
export default meta
|
|
71
|
+
type Story = StoryObj<typeof meta>
|
|
72
|
+
|
|
73
|
+
/**
|
|
74
|
+
* Default (Horizontal)
|
|
75
|
+
*
|
|
76
|
+
* Basic horizontal separator.
|
|
77
|
+
*/
|
|
78
|
+
export const Default: Story = {
|
|
79
|
+
render: () => (
|
|
80
|
+
<div style={{ width: '300px' }}>
|
|
81
|
+
<Separator />
|
|
82
|
+
</div>
|
|
83
|
+
),
|
|
84
|
+
}
|
|
85
|
+
|
|
86
|
+
/**
|
|
87
|
+
* Vertical
|
|
88
|
+
*
|
|
89
|
+
* Vertical separator for horizontal content layouts.
|
|
90
|
+
*/
|
|
91
|
+
export const Vertical: Story = {
|
|
92
|
+
render: () => (
|
|
93
|
+
<div style={{ display: 'flex', height: '100px', alignItems: 'center', gap: '16px' }}>
|
|
94
|
+
<div>Left Content</div>
|
|
95
|
+
<Separator orientation="vertical" />
|
|
96
|
+
<div>Right Content</div>
|
|
97
|
+
</div>
|
|
98
|
+
),
|
|
99
|
+
parameters: {
|
|
100
|
+
docs: {
|
|
101
|
+
description: {
|
|
102
|
+
story: 'Vertical separators are useful for dividing horizontally arranged content.',
|
|
103
|
+
},
|
|
104
|
+
},
|
|
105
|
+
},
|
|
106
|
+
}
|
|
107
|
+
|
|
108
|
+
/**
|
|
109
|
+
* In Content
|
|
110
|
+
*
|
|
111
|
+
* Separator used to divide text content sections.
|
|
112
|
+
*/
|
|
113
|
+
export const InContent: Story = {
|
|
114
|
+
render: () => (
|
|
115
|
+
<div style={{ maxWidth: '400px' }}>
|
|
116
|
+
<div style={{ marginBottom: '16px' }}>
|
|
117
|
+
<h3 style={{ fontSize: '16px', fontWeight: 600, marginBottom: '8px' }}>Section 1</h3>
|
|
118
|
+
<p style={{ fontSize: '14px', color: 'hsl(var(--muted-foreground))' }}>
|
|
119
|
+
This is the first section of content with some descriptive text.
|
|
120
|
+
</p>
|
|
121
|
+
</div>
|
|
122
|
+
<Separator />
|
|
123
|
+
<div style={{ marginTop: '16px' }}>
|
|
124
|
+
<h3 style={{ fontSize: '16px', fontWeight: 600, marginBottom: '8px' }}>Section 2</h3>
|
|
125
|
+
<p style={{ fontSize: '14px', color: 'hsl(var(--muted-foreground))' }}>
|
|
126
|
+
This is the second section of content with more descriptive text.
|
|
127
|
+
</p>
|
|
128
|
+
</div>
|
|
129
|
+
</div>
|
|
130
|
+
),
|
|
131
|
+
parameters: {
|
|
132
|
+
docs: {
|
|
133
|
+
description: {
|
|
134
|
+
story: 'Separators help create visual hierarchy between content sections.',
|
|
135
|
+
},
|
|
136
|
+
},
|
|
137
|
+
},
|
|
138
|
+
}
|
|
139
|
+
|
|
140
|
+
/**
|
|
141
|
+
* In Navigation
|
|
142
|
+
*
|
|
143
|
+
* Separator used in navigation menus.
|
|
144
|
+
*/
|
|
145
|
+
export const InNavigation: Story = {
|
|
146
|
+
render: () => (
|
|
147
|
+
<div style={{ width: '200px', padding: '8px', border: '1px solid hsl(var(--border))', borderRadius: '8px' }}>
|
|
148
|
+
<div style={{ padding: '8px', fontSize: '14px' }}>Profile</div>
|
|
149
|
+
<div style={{ padding: '8px', fontSize: '14px' }}>Settings</div>
|
|
150
|
+
<Separator style={{ margin: '8px 0' }} />
|
|
151
|
+
<div style={{ padding: '8px', fontSize: '14px', color: 'hsl(var(--destructive))' }}>Logout</div>
|
|
152
|
+
</div>
|
|
153
|
+
),
|
|
154
|
+
parameters: {
|
|
155
|
+
docs: {
|
|
156
|
+
description: {
|
|
157
|
+
story: 'Separators can group related navigation items and separate destructive actions.',
|
|
158
|
+
},
|
|
159
|
+
},
|
|
160
|
+
},
|
|
161
|
+
}
|
|
162
|
+
|
|
163
|
+
/**
|
|
164
|
+
* Multiple Sections
|
|
165
|
+
*
|
|
166
|
+
* Multiple separators dividing several content sections.
|
|
167
|
+
*/
|
|
168
|
+
export const MultipleSections: Story = {
|
|
169
|
+
render: () => (
|
|
170
|
+
<div style={{ maxWidth: '400px' }}>
|
|
171
|
+
<div style={{ padding: '16px 0' }}>
|
|
172
|
+
<h3 style={{ fontSize: '16px', fontWeight: 600 }}>Header</h3>
|
|
173
|
+
</div>
|
|
174
|
+
<Separator />
|
|
175
|
+
<div style={{ padding: '16px 0' }}>
|
|
176
|
+
<p style={{ fontSize: '14px' }}>Main content area with important information.</p>
|
|
177
|
+
</div>
|
|
178
|
+
<Separator />
|
|
179
|
+
<div style={{ padding: '16px 0' }}>
|
|
180
|
+
<p style={{ fontSize: '12px', color: 'hsl(var(--muted-foreground))' }}>Footer information</p>
|
|
181
|
+
</div>
|
|
182
|
+
</div>
|
|
183
|
+
),
|
|
184
|
+
parameters: {
|
|
185
|
+
docs: {
|
|
186
|
+
description: {
|
|
187
|
+
story: 'Multiple separators can create clear visual sections in a layout.',
|
|
188
|
+
},
|
|
189
|
+
},
|
|
190
|
+
},
|
|
191
|
+
}
|
|
192
|
+
|
|
193
|
+
/**
|
|
194
|
+
* With Flex Layout
|
|
195
|
+
*
|
|
196
|
+
* Separators in a flexbox layout with multiple items.
|
|
197
|
+
*/
|
|
198
|
+
export const WithFlexLayout: Story = {
|
|
199
|
+
render: () => (
|
|
200
|
+
<div style={{ display: 'flex', alignItems: 'center', gap: '16px' }}>
|
|
201
|
+
<div>Item 1</div>
|
|
202
|
+
<Separator orientation="vertical" style={{ height: '20px' }} />
|
|
203
|
+
<div>Item 2</div>
|
|
204
|
+
<Separator orientation="vertical" style={{ height: '20px' }} />
|
|
205
|
+
<div>Item 3</div>
|
|
206
|
+
<Separator orientation="vertical" style={{ height: '20px' }} />
|
|
207
|
+
<div>Item 4</div>
|
|
208
|
+
</div>
|
|
209
|
+
),
|
|
210
|
+
parameters: {
|
|
211
|
+
docs: {
|
|
212
|
+
description: {
|
|
213
|
+
story: 'Vertical separators work well in horizontal flex layouts.',
|
|
214
|
+
},
|
|
215
|
+
},
|
|
216
|
+
},
|
|
217
|
+
}
|
|
218
|
+
|
|
219
|
+
/**
|
|
220
|
+
* Dark Mode Preview
|
|
221
|
+
*
|
|
222
|
+
* Separators in dark mode to verify theming compatibility.
|
|
223
|
+
*/
|
|
224
|
+
export const DarkMode: Story = {
|
|
225
|
+
render: () => (
|
|
226
|
+
<div className="dark" style={{ padding: '24px', background: 'hsl(222.2 84% 4.9%)', borderRadius: '8px' }}>
|
|
227
|
+
<div style={{ maxWidth: '400px' }}>
|
|
228
|
+
<div style={{ marginBottom: '16px' }}>
|
|
229
|
+
<h3 style={{ fontSize: '16px', fontWeight: 600, marginBottom: '8px', color: 'hsl(var(--foreground))' }}>
|
|
230
|
+
Section 1
|
|
231
|
+
</h3>
|
|
232
|
+
<p style={{ fontSize: '14px', color: 'hsl(var(--muted-foreground))' }}>
|
|
233
|
+
This is the first section of content.
|
|
234
|
+
</p>
|
|
235
|
+
</div>
|
|
236
|
+
<Separator />
|
|
237
|
+
<div style={{ marginTop: '16px', marginBottom: '16px' }}>
|
|
238
|
+
<h3 style={{ fontSize: '16px', fontWeight: 600, marginBottom: '8px', color: 'hsl(var(--foreground))' }}>
|
|
239
|
+
Section 2
|
|
240
|
+
</h3>
|
|
241
|
+
<p style={{ fontSize: '14px', color: 'hsl(var(--muted-foreground))' }}>
|
|
242
|
+
This is the second section of content.
|
|
243
|
+
</p>
|
|
244
|
+
</div>
|
|
245
|
+
<Separator />
|
|
246
|
+
<div style={{ marginTop: '16px', display: 'flex', alignItems: 'center', gap: '16px' }}>
|
|
247
|
+
<div style={{ color: 'hsl(var(--foreground))' }}>Item 1</div>
|
|
248
|
+
<Separator orientation="vertical" style={{ height: '20px' }} />
|
|
249
|
+
<div style={{ color: 'hsl(var(--foreground))' }}>Item 2</div>
|
|
250
|
+
<Separator orientation="vertical" style={{ height: '20px' }} />
|
|
251
|
+
<div style={{ color: 'hsl(var(--foreground))' }}>Item 3</div>
|
|
252
|
+
</div>
|
|
253
|
+
</div>
|
|
254
|
+
</div>
|
|
255
|
+
),
|
|
256
|
+
parameters: {
|
|
257
|
+
docs: {
|
|
258
|
+
description: {
|
|
259
|
+
story: 'Separators automatically adapt to dark mode with appropriate contrast.',
|
|
260
|
+
},
|
|
261
|
+
},
|
|
262
|
+
backgrounds: { disable: true },
|
|
263
|
+
},
|
|
264
|
+
}
|
|
@@ -0,0 +1,48 @@
|
|
|
1
|
+
import * as React from "react"
|
|
2
|
+
import { Separator as ShadcnSeparator } from "../../ui/separator"
|
|
3
|
+
|
|
4
|
+
/**
|
|
5
|
+
* Separator Primitive
|
|
6
|
+
*
|
|
7
|
+
* A foundational separator component that wraps shadcn/ui Separator with design system
|
|
8
|
+
* enhancements. This primitive serves as the single source of truth for all visual
|
|
9
|
+
* separators across the application.
|
|
10
|
+
*
|
|
11
|
+
* @example
|
|
12
|
+
* ```tsx
|
|
13
|
+
* <Separator />
|
|
14
|
+
* <Separator orientation="vertical" />
|
|
15
|
+
* ```
|
|
16
|
+
*
|
|
17
|
+
* @see https://ui.shadcn.com/docs/components/separator - shadcn/ui Separator documentation
|
|
18
|
+
*/
|
|
19
|
+
|
|
20
|
+
/**
|
|
21
|
+
* Separator component props
|
|
22
|
+
* Extends the Radix UI Separator props
|
|
23
|
+
*/
|
|
24
|
+
export type SeparatorProps = React.ComponentPropsWithoutRef<typeof ShadcnSeparator>
|
|
25
|
+
|
|
26
|
+
/**
|
|
27
|
+
* Separator component
|
|
28
|
+
*
|
|
29
|
+
* A visual separator component for dividing content, built on shadcn/ui foundation.
|
|
30
|
+
* Optimized with React.memo for performance in high-frequency rendering scenarios.
|
|
31
|
+
*
|
|
32
|
+
* Features:
|
|
33
|
+
* - Horizontal and vertical orientations
|
|
34
|
+
* - Semantic HTML with proper ARIA attributes
|
|
35
|
+
* - Consistent styling across the application
|
|
36
|
+
* - Dark mode support
|
|
37
|
+
* - Decorative by default (not announced to screen readers)
|
|
38
|
+
*/
|
|
39
|
+
export const Separator = React.memo(
|
|
40
|
+
React.forwardRef<
|
|
41
|
+
React.ElementRef<typeof ShadcnSeparator>,
|
|
42
|
+
SeparatorProps
|
|
43
|
+
>((props, ref) => {
|
|
44
|
+
return <ShadcnSeparator ref={ref} {...props} />
|
|
45
|
+
})
|
|
46
|
+
)
|
|
47
|
+
|
|
48
|
+
Separator.displayName = "Separator"
|
|
@@ -0,0 +1,358 @@
|
|
|
1
|
+
import type { Meta, StoryObj } from '@storybook/react'
|
|
2
|
+
import {
|
|
3
|
+
Sidebar,
|
|
4
|
+
SidebarProvider,
|
|
5
|
+
SidebarInset,
|
|
6
|
+
SidebarHeader,
|
|
7
|
+
SidebarContent,
|
|
8
|
+
SidebarFooter,
|
|
9
|
+
SidebarMenu,
|
|
10
|
+
SidebarMenuItem,
|
|
11
|
+
SidebarMenuButton,
|
|
12
|
+
SidebarTrigger,
|
|
13
|
+
SidebarGroup,
|
|
14
|
+
SidebarGroupContent,
|
|
15
|
+
SidebarGroupLabel,
|
|
16
|
+
} from './Sidebar'
|
|
17
|
+
|
|
18
|
+
/**
|
|
19
|
+
* Sidebar Primitive Stories
|
|
20
|
+
*
|
|
21
|
+
* The Sidebar component is a foundational primitive for application navigation.
|
|
22
|
+
* It extends shadcn/ui's Sidebar with design system-specific enhancements and maintains
|
|
23
|
+
* full accessibility compliance (WCAG 2.1 Level AA).
|
|
24
|
+
*
|
|
25
|
+
* ## Features
|
|
26
|
+
* - Collapsible sidebar with smooth animations
|
|
27
|
+
* - Responsive behavior (mobile/desktop)
|
|
28
|
+
* - Keyboard navigation support
|
|
29
|
+
* - Multiple variants (sidebar, floating, inset)
|
|
30
|
+
* - Dark mode support
|
|
31
|
+
*
|
|
32
|
+
* ## Accessibility
|
|
33
|
+
* - Proper ARIA attributes for navigation
|
|
34
|
+
* - Keyboard shortcuts (Cmd/Ctrl + B to toggle)
|
|
35
|
+
* - Focus management
|
|
36
|
+
* - Screen reader announcements
|
|
37
|
+
*
|
|
38
|
+
* ## Usage Guidelines
|
|
39
|
+
*
|
|
40
|
+
* ### Do's
|
|
41
|
+
* - Use for primary application navigation
|
|
42
|
+
* - Group related navigation items
|
|
43
|
+
* - Provide clear labels and icons
|
|
44
|
+
* - Use SidebarProvider to wrap the layout
|
|
45
|
+
*
|
|
46
|
+
* ### Don'ts
|
|
47
|
+
* - Don't use for secondary navigation
|
|
48
|
+
* - Don't nest multiple sidebars
|
|
49
|
+
* - Don't omit navigation labels
|
|
50
|
+
* - Don't use for temporary content (use Drawer instead)
|
|
51
|
+
*/
|
|
52
|
+
const meta = {
|
|
53
|
+
title: 'Primitives/Sidebar',
|
|
54
|
+
component: Sidebar,
|
|
55
|
+
tags: ['autodocs'],
|
|
56
|
+
parameters: {
|
|
57
|
+
layout: 'fullscreen',
|
|
58
|
+
docs: {
|
|
59
|
+
description: {
|
|
60
|
+
component: 'A collapsible sidebar component for application navigation, built on shadcn/ui foundation.',
|
|
61
|
+
},
|
|
62
|
+
},
|
|
63
|
+
},
|
|
64
|
+
} satisfies Meta<typeof Sidebar>
|
|
65
|
+
|
|
66
|
+
export default meta
|
|
67
|
+
type Story = StoryObj<typeof meta>
|
|
68
|
+
|
|
69
|
+
/**
|
|
70
|
+
* Default sidebar
|
|
71
|
+
*
|
|
72
|
+
* Basic sidebar with navigation items.
|
|
73
|
+
*/
|
|
74
|
+
export const Default: Story = {
|
|
75
|
+
render: () => (
|
|
76
|
+
<SidebarProvider>
|
|
77
|
+
<div style={{ display: 'flex', minHeight: '400px', width: '100%' }}>
|
|
78
|
+
<Sidebar>
|
|
79
|
+
<SidebarHeader>
|
|
80
|
+
<div style={{ padding: '16px', fontWeight: 600 }}>My App</div>
|
|
81
|
+
</SidebarHeader>
|
|
82
|
+
<SidebarContent>
|
|
83
|
+
<SidebarMenu>
|
|
84
|
+
<SidebarMenuItem>
|
|
85
|
+
<SidebarMenuButton>Dashboard</SidebarMenuButton>
|
|
86
|
+
</SidebarMenuItem>
|
|
87
|
+
<SidebarMenuItem>
|
|
88
|
+
<SidebarMenuButton>Projects</SidebarMenuButton>
|
|
89
|
+
</SidebarMenuItem>
|
|
90
|
+
<SidebarMenuItem>
|
|
91
|
+
<SidebarMenuButton>Tasks</SidebarMenuButton>
|
|
92
|
+
</SidebarMenuItem>
|
|
93
|
+
<SidebarMenuItem>
|
|
94
|
+
<SidebarMenuButton>Settings</SidebarMenuButton>
|
|
95
|
+
</SidebarMenuItem>
|
|
96
|
+
</SidebarMenu>
|
|
97
|
+
</SidebarContent>
|
|
98
|
+
<SidebarFooter>
|
|
99
|
+
<div style={{ padding: '16px', fontSize: '12px', color: 'hsl(var(--muted-foreground))' }}>
|
|
100
|
+
© 2024 My App
|
|
101
|
+
</div>
|
|
102
|
+
</SidebarFooter>
|
|
103
|
+
</Sidebar>
|
|
104
|
+
<SidebarInset>
|
|
105
|
+
<header style={{ borderBottom: '1px solid hsl(var(--border))', padding: '16px', display: 'flex', alignItems: 'center', gap: '8px' }}>
|
|
106
|
+
<SidebarTrigger />
|
|
107
|
+
<h1 style={{ fontSize: '18px', fontWeight: 600 }}>Page Title</h1>
|
|
108
|
+
</header>
|
|
109
|
+
<main style={{ padding: '24px' }}>
|
|
110
|
+
<p>Main content area. Click the trigger button to toggle the sidebar.</p>
|
|
111
|
+
</main>
|
|
112
|
+
</SidebarInset>
|
|
113
|
+
</div>
|
|
114
|
+
</SidebarProvider>
|
|
115
|
+
),
|
|
116
|
+
}
|
|
117
|
+
|
|
118
|
+
/**
|
|
119
|
+
* With Groups
|
|
120
|
+
*
|
|
121
|
+
* Sidebar with grouped navigation items.
|
|
122
|
+
*/
|
|
123
|
+
export const WithGroups: Story = {
|
|
124
|
+
render: () => (
|
|
125
|
+
<SidebarProvider>
|
|
126
|
+
<div style={{ display: 'flex', minHeight: '400px', width: '100%' }}>
|
|
127
|
+
<Sidebar>
|
|
128
|
+
<SidebarHeader>
|
|
129
|
+
<div style={{ padding: '16px', fontWeight: 600 }}>My App</div>
|
|
130
|
+
</SidebarHeader>
|
|
131
|
+
<SidebarContent>
|
|
132
|
+
<SidebarGroup>
|
|
133
|
+
<SidebarGroupLabel>Main</SidebarGroupLabel>
|
|
134
|
+
<SidebarGroupContent>
|
|
135
|
+
<SidebarMenu>
|
|
136
|
+
<SidebarMenuItem>
|
|
137
|
+
<SidebarMenuButton>Dashboard</SidebarMenuButton>
|
|
138
|
+
</SidebarMenuItem>
|
|
139
|
+
<SidebarMenuItem>
|
|
140
|
+
<SidebarMenuButton>Analytics</SidebarMenuButton>
|
|
141
|
+
</SidebarMenuItem>
|
|
142
|
+
</SidebarMenu>
|
|
143
|
+
</SidebarGroupContent>
|
|
144
|
+
</SidebarGroup>
|
|
145
|
+
<SidebarGroup>
|
|
146
|
+
<SidebarGroupLabel>Projects</SidebarGroupLabel>
|
|
147
|
+
<SidebarGroupContent>
|
|
148
|
+
<SidebarMenu>
|
|
149
|
+
<SidebarMenuItem>
|
|
150
|
+
<SidebarMenuButton>All Projects</SidebarMenuButton>
|
|
151
|
+
</SidebarMenuItem>
|
|
152
|
+
<SidebarMenuItem>
|
|
153
|
+
<SidebarMenuButton>Favorites</SidebarMenuButton>
|
|
154
|
+
</SidebarMenuItem>
|
|
155
|
+
<SidebarMenuItem>
|
|
156
|
+
<SidebarMenuButton>Archived</SidebarMenuButton>
|
|
157
|
+
</SidebarMenuItem>
|
|
158
|
+
</SidebarMenu>
|
|
159
|
+
</SidebarGroupContent>
|
|
160
|
+
</SidebarGroup>
|
|
161
|
+
<SidebarGroup>
|
|
162
|
+
<SidebarGroupLabel>Settings</SidebarGroupLabel>
|
|
163
|
+
<SidebarGroupContent>
|
|
164
|
+
<SidebarMenu>
|
|
165
|
+
<SidebarMenuItem>
|
|
166
|
+
<SidebarMenuButton>Profile</SidebarMenuButton>
|
|
167
|
+
</SidebarMenuItem>
|
|
168
|
+
<SidebarMenuItem>
|
|
169
|
+
<SidebarMenuButton>Preferences</SidebarMenuButton>
|
|
170
|
+
</SidebarMenuItem>
|
|
171
|
+
</SidebarMenu>
|
|
172
|
+
</SidebarGroupContent>
|
|
173
|
+
</SidebarGroup>
|
|
174
|
+
</SidebarContent>
|
|
175
|
+
</Sidebar>
|
|
176
|
+
<SidebarInset>
|
|
177
|
+
<header style={{ borderBottom: '1px solid hsl(var(--border))', padding: '16px', display: 'flex', alignItems: 'center', gap: '8px' }}>
|
|
178
|
+
<SidebarTrigger />
|
|
179
|
+
<h1 style={{ fontSize: '18px', fontWeight: 600 }}>Grouped Navigation</h1>
|
|
180
|
+
</header>
|
|
181
|
+
<main style={{ padding: '24px' }}>
|
|
182
|
+
<p>Sidebar with grouped navigation items for better organization.</p>
|
|
183
|
+
</main>
|
|
184
|
+
</SidebarInset>
|
|
185
|
+
</div>
|
|
186
|
+
</SidebarProvider>
|
|
187
|
+
),
|
|
188
|
+
parameters: {
|
|
189
|
+
docs: {
|
|
190
|
+
description: {
|
|
191
|
+
story: 'Use SidebarGroup to organize related navigation items.',
|
|
192
|
+
},
|
|
193
|
+
},
|
|
194
|
+
},
|
|
195
|
+
}
|
|
196
|
+
|
|
197
|
+
/**
|
|
198
|
+
* With Active State
|
|
199
|
+
*
|
|
200
|
+
* Sidebar showing active navigation item.
|
|
201
|
+
*/
|
|
202
|
+
export const WithActiveState: Story = {
|
|
203
|
+
render: () => (
|
|
204
|
+
<SidebarProvider>
|
|
205
|
+
<div style={{ display: 'flex', minHeight: '400px', width: '100%' }}>
|
|
206
|
+
<Sidebar>
|
|
207
|
+
<SidebarHeader>
|
|
208
|
+
<div style={{ padding: '16px', fontWeight: 600 }}>My App</div>
|
|
209
|
+
</SidebarHeader>
|
|
210
|
+
<SidebarContent>
|
|
211
|
+
<SidebarMenu>
|
|
212
|
+
<SidebarMenuItem>
|
|
213
|
+
<SidebarMenuButton isActive>Dashboard</SidebarMenuButton>
|
|
214
|
+
</SidebarMenuItem>
|
|
215
|
+
<SidebarMenuItem>
|
|
216
|
+
<SidebarMenuButton>Projects</SidebarMenuButton>
|
|
217
|
+
</SidebarMenuItem>
|
|
218
|
+
<SidebarMenuItem>
|
|
219
|
+
<SidebarMenuButton>Tasks</SidebarMenuButton>
|
|
220
|
+
</SidebarMenuItem>
|
|
221
|
+
<SidebarMenuItem>
|
|
222
|
+
<SidebarMenuButton>Settings</SidebarMenuButton>
|
|
223
|
+
</SidebarMenuItem>
|
|
224
|
+
</SidebarMenu>
|
|
225
|
+
</SidebarContent>
|
|
226
|
+
</Sidebar>
|
|
227
|
+
<SidebarInset>
|
|
228
|
+
<header style={{ borderBottom: '1px solid hsl(var(--border))', padding: '16px', display: 'flex', alignItems: 'center', gap: '8px' }}>
|
|
229
|
+
<SidebarTrigger />
|
|
230
|
+
<h1 style={{ fontSize: '18px', fontWeight: 600 }}>Dashboard</h1>
|
|
231
|
+
</header>
|
|
232
|
+
<main style={{ padding: '24px' }}>
|
|
233
|
+
<p>The Dashboard item is marked as active in the sidebar.</p>
|
|
234
|
+
</main>
|
|
235
|
+
</SidebarInset>
|
|
236
|
+
</div>
|
|
237
|
+
</SidebarProvider>
|
|
238
|
+
),
|
|
239
|
+
parameters: {
|
|
240
|
+
docs: {
|
|
241
|
+
description: {
|
|
242
|
+
story: 'Use isActive prop to highlight the current page in navigation.',
|
|
243
|
+
},
|
|
244
|
+
},
|
|
245
|
+
},
|
|
246
|
+
}
|
|
247
|
+
|
|
248
|
+
/**
|
|
249
|
+
* Collapsed by Default
|
|
250
|
+
*
|
|
251
|
+
* Sidebar that starts in collapsed state.
|
|
252
|
+
*/
|
|
253
|
+
export const CollapsedByDefault: Story = {
|
|
254
|
+
render: () => (
|
|
255
|
+
<SidebarProvider defaultOpen={false}>
|
|
256
|
+
<div style={{ display: 'flex', minHeight: '400px', width: '100%' }}>
|
|
257
|
+
<Sidebar collapsible="icon">
|
|
258
|
+
<SidebarHeader>
|
|
259
|
+
<div style={{ padding: '16px', fontWeight: 600 }}>App</div>
|
|
260
|
+
</SidebarHeader>
|
|
261
|
+
<SidebarContent>
|
|
262
|
+
<SidebarMenu>
|
|
263
|
+
<SidebarMenuItem>
|
|
264
|
+
<SidebarMenuButton tooltip="Dashboard">Dashboard</SidebarMenuButton>
|
|
265
|
+
</SidebarMenuItem>
|
|
266
|
+
<SidebarMenuItem>
|
|
267
|
+
<SidebarMenuButton tooltip="Projects">Projects</SidebarMenuButton>
|
|
268
|
+
</SidebarMenuItem>
|
|
269
|
+
<SidebarMenuItem>
|
|
270
|
+
<SidebarMenuButton tooltip="Tasks">Tasks</SidebarMenuButton>
|
|
271
|
+
</SidebarMenuItem>
|
|
272
|
+
<SidebarMenuItem>
|
|
273
|
+
<SidebarMenuButton tooltip="Settings">Settings</SidebarMenuButton>
|
|
274
|
+
</SidebarMenuItem>
|
|
275
|
+
</SidebarMenu>
|
|
276
|
+
</SidebarContent>
|
|
277
|
+
</Sidebar>
|
|
278
|
+
<SidebarInset>
|
|
279
|
+
<header style={{ borderBottom: '1px solid hsl(var(--border))', padding: '16px', display: 'flex', alignItems: 'center', gap: '8px' }}>
|
|
280
|
+
<SidebarTrigger />
|
|
281
|
+
<h1 style={{ fontSize: '18px', fontWeight: 600 }}>Collapsed Sidebar</h1>
|
|
282
|
+
</header>
|
|
283
|
+
<main style={{ padding: '24px' }}>
|
|
284
|
+
<p>Sidebar starts collapsed. Hover over items to see tooltips.</p>
|
|
285
|
+
</main>
|
|
286
|
+
</SidebarInset>
|
|
287
|
+
</div>
|
|
288
|
+
</SidebarProvider>
|
|
289
|
+
),
|
|
290
|
+
parameters: {
|
|
291
|
+
docs: {
|
|
292
|
+
description: {
|
|
293
|
+
story: 'Set defaultOpen={false} to start with a collapsed sidebar.',
|
|
294
|
+
},
|
|
295
|
+
},
|
|
296
|
+
},
|
|
297
|
+
}
|
|
298
|
+
|
|
299
|
+
/**
|
|
300
|
+
* Dark Mode Preview
|
|
301
|
+
*
|
|
302
|
+
* Sidebar in dark mode to verify theming compatibility.
|
|
303
|
+
*/
|
|
304
|
+
export const DarkMode: Story = {
|
|
305
|
+
render: () => (
|
|
306
|
+
<div className="dark" style={{ background: 'hsl(222.2 84% 4.9%)' }}>
|
|
307
|
+
<SidebarProvider>
|
|
308
|
+
<div style={{ display: 'flex', minHeight: '400px', width: '100%' }}>
|
|
309
|
+
<Sidebar>
|
|
310
|
+
<SidebarHeader>
|
|
311
|
+
<div style={{ padding: '16px', fontWeight: 600 }}>My App</div>
|
|
312
|
+
</SidebarHeader>
|
|
313
|
+
<SidebarContent>
|
|
314
|
+
<SidebarGroup>
|
|
315
|
+
<SidebarGroupLabel>Navigation</SidebarGroupLabel>
|
|
316
|
+
<SidebarGroupContent>
|
|
317
|
+
<SidebarMenu>
|
|
318
|
+
<SidebarMenuItem>
|
|
319
|
+
<SidebarMenuButton isActive>Dashboard</SidebarMenuButton>
|
|
320
|
+
</SidebarMenuItem>
|
|
321
|
+
<SidebarMenuItem>
|
|
322
|
+
<SidebarMenuButton>Projects</SidebarMenuButton>
|
|
323
|
+
</SidebarMenuItem>
|
|
324
|
+
<SidebarMenuItem>
|
|
325
|
+
<SidebarMenuButton>Tasks</SidebarMenuButton>
|
|
326
|
+
</SidebarMenuItem>
|
|
327
|
+
</SidebarMenu>
|
|
328
|
+
</SidebarGroupContent>
|
|
329
|
+
</SidebarGroup>
|
|
330
|
+
</SidebarContent>
|
|
331
|
+
<SidebarFooter>
|
|
332
|
+
<div style={{ padding: '16px', fontSize: '12px', color: 'hsl(var(--muted-foreground))' }}>
|
|
333
|
+
© 2024 My App
|
|
334
|
+
</div>
|
|
335
|
+
</SidebarFooter>
|
|
336
|
+
</Sidebar>
|
|
337
|
+
<SidebarInset>
|
|
338
|
+
<header style={{ borderBottom: '1px solid hsl(var(--border))', padding: '16px', display: 'flex', alignItems: 'center', gap: '8px' }}>
|
|
339
|
+
<SidebarTrigger />
|
|
340
|
+
<h1 style={{ fontSize: '18px', fontWeight: 600, color: 'hsl(var(--foreground))' }}>Dark Mode</h1>
|
|
341
|
+
</header>
|
|
342
|
+
<main style={{ padding: '24px', color: 'hsl(var(--foreground))' }}>
|
|
343
|
+
<p>Sidebar automatically adapts to dark mode with appropriate contrast.</p>
|
|
344
|
+
</main>
|
|
345
|
+
</SidebarInset>
|
|
346
|
+
</div>
|
|
347
|
+
</SidebarProvider>
|
|
348
|
+
</div>
|
|
349
|
+
),
|
|
350
|
+
parameters: {
|
|
351
|
+
docs: {
|
|
352
|
+
description: {
|
|
353
|
+
story: 'Sidebar automatically adapts to dark mode with appropriate contrast and visibility.',
|
|
354
|
+
},
|
|
355
|
+
},
|
|
356
|
+
backgrounds: { disable: true },
|
|
357
|
+
},
|
|
358
|
+
}
|