veza/apps/web/src/components/ui/EmptyState.stories.tsx
senke 8c0dd30685 feat(v0.13.2): consolidation design system — SUMI tokens, package, stories
TASK-DS-001: Migrated packages/design-system/ from legacy Kōdō to SUMI v2.0
  - New src/ structure with proper TypeScript exports
  - Component type registry documenting all 40+ UI components
  - cn() utility re-export
  - package.json with exports map for tokens subpaths

TASK-DS-002: Extracted design tokens as TypeScript objects
  - tokens/colors.ts: backgrounds, surfaces, text, pigments, semantic, glass, shadows, light theme
  - tokens/typography.ts: font families, sizes, weights, line heights, letter spacings
  - tokens/spacing.ts: spacing scale, radius, z-index, layout
  - tokens/motion.ts: durations and easing functions

TASK-DS-003: Added missing Storybook stories
  - EmptyState.stories.tsx (8 variants: default, icon, action, search, sizes, card, centered)
  - ButtonLoading.stories.tsx (6 variants: default, loading, text, destructive, outline, small)
  - ContentFadeIn.stories.tsx (2 variants: default, card)
  - DesignTokens.stories.tsx (visual token reference: pigments, backgrounds, text, typography, spacing, radius)
  - Total: 42 → 46 stories for UI components + design token showcase

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-13 09:45:09 +01:00

99 lines
2.3 KiB
TypeScript

import type { Meta, StoryObj } from '@storybook/react';
import { EmptyState } from './empty-state';
import { Inbox, Search, Music, Users } from 'lucide-react';
const meta: Meta<typeof EmptyState> = {
title: 'UI/EmptyState',
component: EmptyState,
tags: ['autodocs'],
argTypes: {
size: { control: 'select', options: ['sm', 'md', 'lg'] },
variant: { control: 'select', options: ['default', 'centered', 'card'] },
},
};
export default meta;
type Story = StoryObj<typeof EmptyState>;
export const Default: Story = {
args: {
title: 'No items found',
description: 'There are no items to display yet.',
},
};
export const WithIcon: Story = {
args: {
icon: <Inbox className="w-full h-full" />,
title: 'Your inbox is empty',
description: 'New messages will appear here when you receive them.',
},
};
export const WithAction: Story = {
args: {
icon: <Music className="w-full h-full" />,
title: 'No tracks uploaded',
description: 'Upload your first track to get started.',
action: {
label: 'Upload a track',
onClick: () => {},
},
},
};
export const SearchEmpty: Story = {
args: {
icon: <Search className="w-full h-full" />,
title: 'No results found',
description: 'Try adjusting your search criteria or browse by genre.',
action: {
label: 'Clear search',
onClick: () => {},
variant: 'outline',
},
},
};
export const Small: Story = {
args: {
size: 'sm',
title: 'No followers yet',
icon: <Users className="w-full h-full" />,
},
};
export const Large: Story = {
args: {
size: 'lg',
icon: <Music className="w-full h-full" />,
title: 'Your library is empty',
description: 'Discover music and add it to your library.',
action: { label: 'Explore', onClick: () => {} },
},
};
export const CardVariant: Story = {
args: {
variant: 'card',
icon: <Inbox className="w-full h-full" />,
title: 'Drop files here',
description: 'Drag and drop files to upload.',
},
};
export const CenteredVariant: Story = {
args: {
variant: 'centered',
icon: <Music className="w-full h-full" />,
title: 'Nothing playing',
description: 'Select a track to start listening.',
},
decorators: [
(Story) => (
<div className="h-96 flex items-stretch">
<Story />
</div>
),
],
};