@postxl/generators 1.1.1 → 1.2.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.
Files changed (161) hide show
  1. package/dist/frontend-core/frontend.generator.d.ts +0 -58
  2. package/dist/frontend-core/frontend.generator.js +6 -172
  3. package/dist/frontend-core/frontend.generator.js.map +1 -1
  4. package/dist/frontend-core/template/README.md +1 -1
  5. package/dist/frontend-core/template/src/components/admin/table-filter.tsx +1 -5
  6. package/dist/frontend-core/template/src/components/ui/color-mode-toggle/color-mode-toggle.tsx +10 -4
  7. package/dist/frontend-core/template/src/pages/dashboard/dashboard.page.tsx +2 -3
  8. package/dist/frontend-core/template/src/pages/error/default-error.page.tsx +1 -1
  9. package/dist/frontend-core/template/src/pages/error/not-found-error.page.tsx +1 -1
  10. package/dist/frontend-core/template/src/styles/styles.css +13 -1
  11. package/dist/frontend-core/template/tsconfig.json +2 -0
  12. package/dist/frontend-core/types/component.d.ts +1 -1
  13. package/dist/frontend-forms/generators/discriminated-union/fields.generator.js +4 -6
  14. package/dist/frontend-forms/generators/discriminated-union/fields.generator.js.map +1 -1
  15. package/dist/frontend-forms/generators/discriminated-union/inputs.generator.js +1 -1
  16. package/dist/frontend-forms/generators/discriminated-union/inputs.generator.js.map +1 -1
  17. package/dist/frontend-forms/generators/enum/inputs.generator.js +1 -1
  18. package/dist/frontend-forms/generators/enum/inputs.generator.js.map +1 -1
  19. package/dist/frontend-forms/generators/model/forms.generator.js +8 -12
  20. package/dist/frontend-forms/generators/model/forms.generator.js.map +1 -1
  21. package/dist/frontend-forms/generators/model/inputs.generator.js +2 -6
  22. package/dist/frontend-forms/generators/model/inputs.generator.js.map +1 -1
  23. package/dist/frontend-forms/template/src/components/ui/field/field.tsx +1 -4
  24. package/dist/frontend-tables/generators/model-table.generator.js +1 -5
  25. package/dist/frontend-tables/generators/model-table.generator.js.map +1 -1
  26. package/package.json +3 -2
  27. package/dist/frontend-core/template/src/components/ui/accordion/accordion.stories.tsx +0 -47
  28. package/dist/frontend-core/template/src/components/ui/accordion/accordion.tsx +0 -52
  29. package/dist/frontend-core/template/src/components/ui/admin-sidebar/admin-sidebar.tsx +0 -195
  30. package/dist/frontend-core/template/src/components/ui/alert/alert.stories.tsx +0 -61
  31. package/dist/frontend-core/template/src/components/ui/alert/alert.tsx +0 -45
  32. package/dist/frontend-core/template/src/components/ui/alert-dialog/alert-dialog.stories.tsx +0 -52
  33. package/dist/frontend-core/template/src/components/ui/alert-dialog/alert-dialog.tsx +0 -105
  34. package/dist/frontend-core/template/src/components/ui/avatar/avatar.stories.tsx +0 -30
  35. package/dist/frontend-core/template/src/components/ui/avatar/avatar.tsx +0 -39
  36. package/dist/frontend-core/template/src/components/ui/badge/badge.stories.tsx +0 -78
  37. package/dist/frontend-core/template/src/components/ui/badge/badge.tsx +0 -48
  38. package/dist/frontend-core/template/src/components/ui/breadcrumb/breadcrumb.stories.tsx +0 -67
  39. package/dist/frontend-core/template/src/components/ui/breadcrumb/breadcrumb.tsx +0 -85
  40. package/dist/frontend-core/template/src/components/ui/button/button.stories.tsx +0 -150
  41. package/dist/frontend-core/template/src/components/ui/button/button.tsx +0 -68
  42. package/dist/frontend-core/template/src/components/ui/calendar/calendar.stories.tsx +0 -160
  43. package/dist/frontend-core/template/src/components/ui/calendar/calendar.tsx +0 -293
  44. package/dist/frontend-core/template/src/components/ui/card/card.stories.tsx +0 -77
  45. package/dist/frontend-core/template/src/components/ui/card/card.tsx +0 -45
  46. package/dist/frontend-core/template/src/components/ui/card-hover/card-hover.stories.tsx +0 -29
  47. package/dist/frontend-core/template/src/components/ui/card-hover/card-hover.tsx +0 -28
  48. package/dist/frontend-core/template/src/components/ui/carousel/carousel.stories.tsx +0 -154
  49. package/dist/frontend-core/template/src/components/ui/carousel/carousel.tsx +0 -227
  50. package/dist/frontend-core/template/src/components/ui/checkbox/checkbox.stories.tsx +0 -106
  51. package/dist/frontend-core/template/src/components/ui/checkbox/checkbox.tsx +0 -88
  52. package/dist/frontend-core/template/src/components/ui/checkbox/shadcn-checkbox.stories.tsx +0 -90
  53. package/dist/frontend-core/template/src/components/ui/checkbox/shadcn-checkbox.tsx +0 -54
  54. package/dist/frontend-core/template/src/components/ui/collapse/collapse.stories.tsx +0 -52
  55. package/dist/frontend-core/template/src/components/ui/collapse/collapse.tsx +0 -9
  56. package/dist/frontend-core/template/src/components/ui/combobox/combobox.stories.tsx +0 -207
  57. package/dist/frontend-core/template/src/components/ui/combobox/combobox.tsx +0 -79
  58. package/dist/frontend-core/template/src/components/ui/command/command.stories.tsx +0 -186
  59. package/dist/frontend-core/template/src/components/ui/command/command.tsx +0 -165
  60. package/dist/frontend-core/template/src/components/ui/command-palette/command-palette.stories.tsx +0 -160
  61. package/dist/frontend-core/template/src/components/ui/command-palette/command-palette.tsx +0 -134
  62. package/dist/frontend-core/template/src/components/ui/content-frame/content-frame.stories.tsx +0 -198
  63. package/dist/frontend-core/template/src/components/ui/content-frame/content-frame.tsx +0 -100
  64. package/dist/frontend-core/template/src/components/ui/context-menu/context-menu.stories.tsx +0 -78
  65. package/dist/frontend-core/template/src/components/ui/context-menu/context-menu.tsx +0 -179
  66. package/dist/frontend-core/template/src/components/ui/data-grid/cell-variants/cell-variant-types.ts +0 -11
  67. package/dist/frontend-core/template/src/components/ui/data-grid/cell-variants/checkbox-cell.tsx +0 -116
  68. package/dist/frontend-core/template/src/components/ui/data-grid/cell-variants/date-cell.tsx +0 -157
  69. package/dist/frontend-core/template/src/components/ui/data-grid/cell-variants/gantt-cell.tsx +0 -82
  70. package/dist/frontend-core/template/src/components/ui/data-grid/cell-variants/long-text-cell.tsx +0 -180
  71. package/dist/frontend-core/template/src/components/ui/data-grid/cell-variants/multi-select-cell.tsx +0 -280
  72. package/dist/frontend-core/template/src/components/ui/data-grid/cell-variants/number-cell.tsx +0 -169
  73. package/dist/frontend-core/template/src/components/ui/data-grid/cell-variants/react-node-cell.tsx +0 -33
  74. package/dist/frontend-core/template/src/components/ui/data-grid/cell-variants/select-cell.tsx +0 -175
  75. package/dist/frontend-core/template/src/components/ui/data-grid/cell-variants/short-text-cell.tsx +0 -138
  76. package/dist/frontend-core/template/src/components/ui/data-grid/cell-variants/utils/gantt-timeline.tsx +0 -92
  77. package/dist/frontend-core/template/src/components/ui/data-grid/cell-variants/utils/gantt-timerange-picker.tsx +0 -330
  78. package/dist/frontend-core/template/src/components/ui/data-grid/data-grid-cell-wrapper.tsx +0 -212
  79. package/dist/frontend-core/template/src/components/ui/data-grid/data-grid-cell.tsx +0 -157
  80. package/dist/frontend-core/template/src/components/ui/data-grid/data-grid-column-header.tsx +0 -340
  81. package/dist/frontend-core/template/src/components/ui/data-grid/data-grid-context-menu.tsx +0 -271
  82. package/dist/frontend-core/template/src/components/ui/data-grid/data-grid-row.tsx +0 -123
  83. package/dist/frontend-core/template/src/components/ui/data-grid/data-grid-search.tsx +0 -211
  84. package/dist/frontend-core/template/src/components/ui/data-grid/data-grid-types.ts +0 -159
  85. package/dist/frontend-core/template/src/components/ui/data-grid/data-grid-utils.ts +0 -67
  86. package/dist/frontend-core/template/src/components/ui/data-grid/data-grid-view-menu.tsx +0 -360
  87. package/dist/frontend-core/template/src/components/ui/data-grid/data-grid.stories.tsx +0 -780
  88. package/dist/frontend-core/template/src/components/ui/data-grid/data-grid.tsx +0 -217
  89. package/dist/frontend-core/template/src/components/ui/data-grid/hooks/use-callback-ref.ts +0 -22
  90. package/dist/frontend-core/template/src/components/ui/data-grid/hooks/use-data-grid.tsx +0 -1892
  91. package/dist/frontend-core/template/src/components/ui/data-grid/hooks/use-debounced-callback.ts +0 -19
  92. package/dist/frontend-core/template/src/components/ui/data-grid/styles.css +0 -3
  93. package/dist/frontend-core/template/src/components/ui/data-table/context-menu-simple.tsx +0 -141
  94. package/dist/frontend-core/template/src/components/ui/data-table/data-table.stories.tsx +0 -146
  95. package/dist/frontend-core/template/src/components/ui/data-table/data-table.tsx +0 -447
  96. package/dist/frontend-core/template/src/components/ui/data-table/renderers/country-array-cell-renderer.tsx +0 -77
  97. package/dist/frontend-core/template/src/components/ui/data-table/renderers/country-cell-renderer.tsx +0 -56
  98. package/dist/frontend-core/template/src/components/ui/data-table/renderers/favorite-cell-renderer.tsx +0 -68
  99. package/dist/frontend-core/template/src/components/ui/data-table/renderers/links-cell-renderer.tsx +0 -205
  100. package/dist/frontend-core/template/src/components/ui/data-table/utils/columns.ts +0 -351
  101. package/dist/frontend-core/template/src/components/ui/data-table/utils/data-table.utils.ts +0 -49
  102. package/dist/frontend-core/template/src/components/ui/date-picker/date-picker.stories.tsx +0 -149
  103. package/dist/frontend-core/template/src/components/ui/date-picker/date-picker.tsx +0 -30
  104. package/dist/frontend-core/template/src/components/ui/dialog/dialog.stories.tsx +0 -80
  105. package/dist/frontend-core/template/src/components/ui/dialog/dialog.tsx +0 -134
  106. package/dist/frontend-core/template/src/components/ui/drawer/drawer.stories.tsx +0 -104
  107. package/dist/frontend-core/template/src/components/ui/drawer/drawer.tsx +0 -87
  108. package/dist/frontend-core/template/src/components/ui/dropdown-menu/dropdown-menu.stories.tsx +0 -168
  109. package/dist/frontend-core/template/src/components/ui/dropdown-menu/dropdown-menu.tsx +0 -225
  110. package/dist/frontend-core/template/src/components/ui/input/input.stories.tsx +0 -141
  111. package/dist/frontend-core/template/src/components/ui/input/input.tsx +0 -47
  112. package/dist/frontend-core/template/src/components/ui/label/label.stories.tsx +0 -41
  113. package/dist/frontend-core/template/src/components/ui/label/label.tsx +0 -20
  114. package/dist/frontend-core/template/src/components/ui/loader/loader.stories.tsx +0 -45
  115. package/dist/frontend-core/template/src/components/ui/loader/loader.tsx +0 -17
  116. package/dist/frontend-core/template/src/components/ui/mark-value-renderer/mark-value-renderer.stories.tsx +0 -114
  117. package/dist/frontend-core/template/src/components/ui/mark-value-renderer/mark-value-renderer.tsx +0 -48
  118. package/dist/frontend-core/template/src/components/ui/menubar/menu.stories.tsx +0 -134
  119. package/dist/frontend-core/template/src/components/ui/menubar/menubar.tsx +0 -208
  120. package/dist/frontend-core/template/src/components/ui/modal/modal.stories.tsx +0 -297
  121. package/dist/frontend-core/template/src/components/ui/modal/modal.tsx +0 -80
  122. package/dist/frontend-core/template/src/components/ui/navigation-menu/navigation-menu.stories.tsx +0 -213
  123. package/dist/frontend-core/template/src/components/ui/navigation-menu/navigation-menu.tsx +0 -142
  124. package/dist/frontend-core/template/src/components/ui/pagination/pagination.stories.tsx +0 -49
  125. package/dist/frontend-core/template/src/components/ui/pagination/pagination.tsx +0 -84
  126. package/dist/frontend-core/template/src/components/ui/popover/popover.stories.tsx +0 -82
  127. package/dist/frontend-core/template/src/components/ui/popover/popover.tsx +0 -55
  128. package/dist/frontend-core/template/src/components/ui/progress/progress.stories.tsx +0 -80
  129. package/dist/frontend-core/template/src/components/ui/progress/progress.tsx +0 -17
  130. package/dist/frontend-core/template/src/components/ui/radio-group/radio-group.stories.tsx +0 -154
  131. package/dist/frontend-core/template/src/components/ui/radio-group/radio-group.tsx +0 -68
  132. package/dist/frontend-core/template/src/components/ui/resizable/resizable.stories.tsx +0 -73
  133. package/dist/frontend-core/template/src/components/ui/resizable/resizeable.tsx +0 -38
  134. package/dist/frontend-core/template/src/components/ui/scroll-area/scroll-area.stories.tsx +0 -55
  135. package/dist/frontend-core/template/src/components/ui/scroll-area/scroll-area.tsx +0 -39
  136. package/dist/frontend-core/template/src/components/ui/select/select.stories.tsx +0 -297
  137. package/dist/frontend-core/template/src/components/ui/select/select.tsx +0 -227
  138. package/dist/frontend-core/template/src/components/ui/separator/separator.tsx +0 -21
  139. package/dist/frontend-core/template/src/components/ui/separator/seperator.stories.tsx +0 -25
  140. package/dist/frontend-core/template/src/components/ui/sheet/sheet.stories.tsx +0 -45
  141. package/dist/frontend-core/template/src/components/ui/sheet/sheet.tsx +0 -107
  142. package/dist/frontend-core/template/src/components/ui/skeleton/skeleton.stories.tsx +0 -26
  143. package/dist/frontend-core/template/src/components/ui/skeleton/skeleton.tsx +0 -7
  144. package/dist/frontend-core/template/src/components/ui/slider/slider.stories.tsx +0 -101
  145. package/dist/frontend-core/template/src/components/ui/slider/slider.tsx +0 -98
  146. package/dist/frontend-core/template/src/components/ui/spinner/spinner.stories.tsx +0 -19
  147. package/dist/frontend-core/template/src/components/ui/spinner/spinner.tsx +0 -21
  148. package/dist/frontend-core/template/src/components/ui/switch/switch.stories.tsx +0 -33
  149. package/dist/frontend-core/template/src/components/ui/switch/switch.tsx +0 -28
  150. package/dist/frontend-core/template/src/components/ui/tabs/tabs.stories.tsx +0 -215
  151. package/dist/frontend-core/template/src/components/ui/tabs/tabs.tsx +0 -70
  152. package/dist/frontend-core/template/src/components/ui/textarea/textarea.stories.tsx +0 -138
  153. package/dist/frontend-core/template/src/components/ui/textarea/textarea.tsx +0 -40
  154. package/dist/frontend-core/template/src/components/ui/toast/toast.mdx +0 -31
  155. package/dist/frontend-core/template/src/components/ui/toast/toast.stories.tsx +0 -89
  156. package/dist/frontend-core/template/src/components/ui/toggle/toggle.stories.tsx +0 -65
  157. package/dist/frontend-core/template/src/components/ui/toggle/toggle.tsx +0 -38
  158. package/dist/frontend-core/template/src/components/ui/toggle-group/toggle-group.stories.tsx +0 -85
  159. package/dist/frontend-core/template/src/components/ui/toggle-group/toggle-group.tsx +0 -54
  160. package/dist/frontend-core/template/src/components/ui/tooltip/tooltip.stories.tsx +0 -29
  161. package/dist/frontend-core/template/src/components/ui/tooltip/tooltip.tsx +0 -29
@@ -1,77 +0,0 @@
1
- import { Meta, StoryObj } from '@storybook/react-vite'
2
-
3
- import { Card, CardContent, CardDescription, CardFooter, CardHeader, CardTitle } from './card'
4
- import { BellIcon, CheckIcon } from '@radix-ui/react-icons'
5
- import { cn } from '@lib/utils'
6
- import { Button } from '@components/ui/button/button'
7
-
8
- const meta = {
9
- title: 'Card',
10
- component: Card,
11
- tags: ['autodocs'],
12
- } satisfies Meta<typeof Card>
13
-
14
- export default meta
15
-
16
- export const Default: StoryObj<typeof meta> = {
17
- parameters: {
18
- docs: {
19
- description: {
20
- story:
21
- 'The Card component is used to group related information in a single container.This means any other component can be placed inside the Card component.',
22
- },
23
- },
24
- },
25
- render: () => (
26
- <div className="flex items-center justify-center border rounded p-4">
27
- <Card className={cn('w-[380px]')}>
28
- <CardHeader>
29
- <CardTitle>Card Title</CardTitle>
30
- <CardDescription>You have 3 unread messages.</CardDescription>
31
- </CardHeader>
32
- <CardContent className="grid gap-4">
33
- <div className=" flex items-center space-x-4 rounded-md border p-4">
34
- <BellIcon />
35
- <div className="flex-1 space-y-1">
36
- <p className="text-sm font-medium leading-none">Push Notifications</p>
37
- <p className="text-sm text-muted-foreground">Send notifications to device.</p>
38
- </div>
39
- </div>
40
- <div>
41
- {notifications.map((notification, index) => (
42
- <div key={index} className="mb-4 grid grid-cols-[25px_1fr] items-start pb-4 last:mb-0 last:pb-0">
43
- <span className="flex h-2 w-2 translate-y-1 rounded-full bg-sky-500" />
44
- <div className="space-y-1">
45
- <p className="text-sm font-medium leading-none">{notification.title}</p>
46
- <p className="text-sm text-muted-foreground">{notification.description}</p>
47
- </div>
48
- </div>
49
- ))}
50
- </div>
51
- </CardContent>
52
- <CardFooter>
53
- <Button className="w-full">
54
- <CheckIcon className="mr-2 h-4 w-4" /> Mark all as read
55
- </Button>
56
- </CardFooter>
57
- </Card>
58
- </div>
59
- ),
60
- }
61
-
62
- // DATA ------------------------------------------------------------------------
63
-
64
- const notifications = [
65
- {
66
- title: 'Your call has been confirmed.',
67
- description: '1 hour ago',
68
- },
69
- {
70
- title: 'You have a new message!',
71
- description: '1 hour ago',
72
- },
73
- {
74
- title: 'Your subscription is expiring soon!',
75
- description: '2 hours ago',
76
- },
77
- ]
@@ -1,45 +0,0 @@
1
- import * as React from 'react'
2
-
3
- import { cn } from '@lib/utils'
4
-
5
- const Card = React.forwardRef<HTMLDivElement, React.HTMLAttributes<HTMLDivElement>>(({ className, ...props }, ref) => (
6
- <div ref={ref} className={cn('rounded-xl border bg-card text-card-foreground shadow', className)} {...props} />
7
- ))
8
- Card.displayName = 'Card'
9
-
10
- const CardHeader = React.forwardRef<HTMLDivElement, React.HTMLAttributes<HTMLDivElement>>(
11
- ({ className, ...props }, ref) => (
12
- <div ref={ref} className={cn('flex flex-col space-y-1.5 p-6', className)} {...props} />
13
- ),
14
- )
15
- CardHeader.displayName = 'CardHeader'
16
-
17
- const CardTitle = React.forwardRef<HTMLParagraphElement, React.HTMLAttributes<HTMLHeadingElement>>(
18
- ({ className, children, ...props }, ref) => (
19
- <h3 ref={ref} className={cn('font-semibold leading-none tracking-tight', className)} {...props}>
20
- {children}
21
- </h3>
22
- ),
23
- )
24
- CardTitle.displayName = 'CardTitle'
25
-
26
- const CardDescription = React.forwardRef<HTMLParagraphElement, React.HTMLAttributes<HTMLParagraphElement>>(
27
- ({ className, ...props }, ref) => (
28
- <p ref={ref} className={cn('text-sm text-muted-foreground', className)} {...props} />
29
- ),
30
- )
31
- CardDescription.displayName = 'CardDescription'
32
-
33
- const CardContent = React.forwardRef<HTMLDivElement, React.HTMLAttributes<HTMLDivElement>>(
34
- ({ className, ...props }, ref) => <div ref={ref} className={cn('p-6 pt-0', className)} {...props} />,
35
- )
36
- CardContent.displayName = 'CardContent'
37
-
38
- const CardFooter = React.forwardRef<HTMLDivElement, React.HTMLAttributes<HTMLDivElement>>(
39
- ({ className, ...props }, ref) => (
40
- <div ref={ref} className={cn('flex items-center p-6 pt-0', className)} {...props} />
41
- ),
42
- )
43
- CardFooter.displayName = 'CardFooter'
44
-
45
- export { Card, CardHeader, CardFooter, CardTitle, CardDescription, CardContent }
@@ -1,29 +0,0 @@
1
- import { Meta, StoryObj } from '@storybook/react-vite'
2
-
3
- import { HoverCard, HoverCardContent, HoverCardTrigger } from './card-hover'
4
-
5
- const meta = {
6
- title: 'Hover Card',
7
- component: HoverCard,
8
- tags: ['autodocs'],
9
- } satisfies Meta<typeof HoverCard>
10
-
11
- export default meta
12
-
13
- export const Default: StoryObj<typeof meta> = {
14
- parameters: {
15
- docs: {
16
- description: {
17
- story: 'The Hover Card component displays additional information when hovering over an element.',
18
- },
19
- },
20
- },
21
- render: () => (
22
- <div className="flex items-center justify-center">
23
- <HoverCard>
24
- <HoverCardTrigger>Hover</HoverCardTrigger>
25
- <HoverCardContent>The React Framework – created and maintained by @vercel.</HoverCardContent>
26
- </HoverCard>
27
- </div>
28
- ),
29
- }
@@ -1,28 +0,0 @@
1
- import * as HoverCardPrimitive from '@radix-ui/react-hover-card'
2
-
3
- import * as React from 'react'
4
-
5
- import { cn } from '@lib/utils'
6
-
7
- const HoverCard = HoverCardPrimitive.Root
8
-
9
- const HoverCardTrigger = HoverCardPrimitive.Trigger
10
-
11
- const HoverCardContent = React.forwardRef<
12
- React.ElementRef<typeof HoverCardPrimitive.Content>,
13
- React.ComponentPropsWithoutRef<typeof HoverCardPrimitive.Content>
14
- >(({ className, align = 'center', sideOffset = 4, ...props }, ref) => (
15
- <HoverCardPrimitive.Content
16
- ref={ref}
17
- align={align}
18
- sideOffset={sideOffset}
19
- className={cn(
20
- 'z-50 w-64 rounded-md border bg-popover p-4 text-popover-foreground shadow-md outline-none data-[state=open]:animate-in data-[state=closed]:animate-out data-[state=closed]:fade-out-0 data-[state=open]:fade-in-0 data-[state=closed]:zoom-out-95 data-[state=open]:zoom-in-95 data-[side=bottom]:slide-in-from-top-2 data-[side=left]:slide-in-from-right-2 data-[side=right]:slide-in-from-left-2 data-[side=top]:slide-in-from-bottom-2',
21
- className,
22
- )}
23
- {...props}
24
- />
25
- ))
26
- HoverCardContent.displayName = HoverCardPrimitive.Content.displayName
27
-
28
- export { HoverCard, HoverCardTrigger, HoverCardContent }
@@ -1,154 +0,0 @@
1
- import { Meta, StoryObj } from '@storybook/react-vite'
2
-
3
- import {
4
- Carousel,
5
- CarouselApi,
6
- CarouselContent,
7
- CarouselItem,
8
- CarouselNext,
9
- CarouselPrevious,
10
- CarouselProps,
11
- } from './carousel'
12
- import { Card, CardContent } from '@components/ui/card/card'
13
- import { useEffect, useState } from 'react'
14
-
15
- const meta = {
16
- title: 'Carousel',
17
- component: Carousel,
18
- tags: ['autodocs'],
19
- argTypes: {
20
- orientation: {
21
- control: 'select',
22
- options: ['horizontal', 'vertical'],
23
- },
24
- },
25
- } satisfies Meta<typeof Carousel>
26
-
27
- export default meta
28
-
29
- export const Default: StoryObj<typeof meta> = {
30
- parameters: {
31
- docs: {
32
- description: {
33
- story: 'The Carousel component displays a list of items that can be scrolled through.',
34
- },
35
- },
36
- },
37
- args: {
38
- orientation: 'horizontal',
39
- },
40
- render: (args) => (
41
- <div className="flex items-center justify-center border rounded p-4">
42
- <Carousel {...args} className="w-full max-w-xs">
43
- <CarouselContent>
44
- {Array.from({ length: 5 }).map((_, index) => (
45
- <CarouselItem key={index} className="basis-1/3">
46
- <div className="p-1">
47
- <Card>
48
- <CardContent className="flex aspect-square items-center justify-center p-6">
49
- <span className="text-4xl font-semibold">{index + 1}</span>
50
- </CardContent>
51
- </Card>
52
- </div>
53
- </CarouselItem>
54
- ))}
55
- </CarouselContent>
56
- <CarouselPrevious />
57
- <CarouselNext />
58
- </Carousel>
59
- </div>
60
- ),
61
- }
62
-
63
- function CarouselWithApi() {
64
- const [api, setApi] = useState<CarouselApi>()
65
- const [current, setCurrent] = useState(0)
66
- const [count, setCount] = useState(0)
67
-
68
- useEffect(() => {
69
- if (!api) {
70
- return
71
- }
72
-
73
- setCount(api.scrollSnapList().length)
74
- setCurrent(api.selectedScrollSnap() + 1)
75
-
76
- api.on('select', () => {
77
- setCurrent(api.selectedScrollSnap() + 1)
78
- })
79
- }, [api])
80
-
81
- return (
82
- <div className="mx-auto max-w-xs">
83
- <Carousel setApi={setApi} className="w-full max-w-xs">
84
- <CarouselContent>
85
- {Array.from({ length: 5 }).map((_, index) => (
86
- <CarouselItem key={index}>
87
- <Card>
88
- <CardContent className="flex aspect-square items-center justify-center p-6">
89
- <span className="text-4xl font-semibold">{index + 1}</span>
90
- </CardContent>
91
- </Card>
92
- </CarouselItem>
93
- ))}
94
- </CarouselContent>
95
- <CarouselPrevious />
96
- <CarouselNext />
97
- </Carousel>
98
- <div className="py-2 text-center text-sm text-muted-foreground">
99
- Slide {current} of {count}
100
- </div>
101
- </div>
102
- )
103
- }
104
-
105
- export const WithApi: StoryObj<typeof meta> = {
106
- parameters: {
107
- docs: {
108
- description: {
109
- story:
110
- 'Carousel with API integration showing current slide counter. The setApi prop allows you to access carousel methods and state for custom controls and indicators.',
111
- },
112
- },
113
- },
114
- render: () => (
115
- <div className="flex items-center justify-center border rounded p-4">
116
- <CarouselWithApi />
117
- </div>
118
- ),
119
- }
120
-
121
- export const Vertical: StoryObj<typeof meta> = {
122
- parameters: {
123
- docs: {
124
- description: {
125
- story:
126
- 'Vertical orientation carousel that scrolls up and down instead of left and right. Perfect for vertical content layouts or space-constrained horizontal designs.',
127
- },
128
- },
129
- },
130
- args: {
131
- orientation: 'vertical',
132
- },
133
- render: (args) => (
134
- <div className="flex items-center justify-center border rounded p-4">
135
- <Carousel {...args} className="w-full max-w-xs">
136
- <CarouselContent className="h-[200px]">
137
- {Array.from({ length: 5 }).map((_, index) => (
138
- <CarouselItem key={index}>
139
- <div className="p-1">
140
- <Card>
141
- <CardContent className="flex aspect-square items-center justify-center p-6">
142
- <span className="text-4xl font-semibold">{index + 1}</span>
143
- </CardContent>
144
- </Card>
145
- </div>
146
- </CarouselItem>
147
- ))}
148
- </CarouselContent>
149
- <CarouselPrevious />
150
- <CarouselNext />
151
- </Carousel>
152
- </div>
153
- ),
154
- }
@@ -1,227 +0,0 @@
1
- import { ArrowLeftIcon, ArrowRightIcon } from '@radix-ui/react-icons'
2
-
3
- import useEmblaCarousel, { type UseEmblaCarouselType } from 'embla-carousel-react'
4
- import * as React from 'react'
5
- import { useMemo } from 'react'
6
-
7
- import { Button } from '@components/ui/button/button'
8
- import { cn } from '@lib/utils'
9
-
10
- type CarouselApi = UseEmblaCarouselType[1]
11
- type UseCarouselParameters = Parameters<typeof useEmblaCarousel>
12
- type CarouselOptions = UseCarouselParameters[0]
13
- type CarouselPlugin = UseCarouselParameters[1]
14
-
15
- type CarouselProps = {
16
- opts?: CarouselOptions
17
- plugins?: CarouselPlugin
18
- orientation?: 'horizontal' | 'vertical'
19
- setApi?: (api: CarouselApi) => void
20
- }
21
-
22
- type CarouselContextProps = {
23
- carouselRef: ReturnType<typeof useEmblaCarousel>[0]
24
- api: ReturnType<typeof useEmblaCarousel>[1]
25
- scrollPrev: () => void
26
- scrollNext: () => void
27
- canScrollPrev: boolean
28
- canScrollNext: boolean
29
- } & CarouselProps
30
-
31
- const CarouselContext = React.createContext<CarouselContextProps | null>(null)
32
-
33
- function useCarousel() {
34
- const context = React.useContext(CarouselContext)
35
-
36
- if (!context) {
37
- throw new Error('useCarousel must be used within a <Carousel />')
38
- }
39
-
40
- return context
41
- }
42
-
43
- const Carousel = React.forwardRef<HTMLDivElement, React.HTMLAttributes<HTMLDivElement> & CarouselProps>(
44
- ({ orientation = 'horizontal', opts, setApi, plugins, className, children, ...props }, ref) => {
45
- const [carouselRef, api] = useEmblaCarousel(
46
- {
47
- ...opts,
48
- axis: orientation === 'horizontal' ? 'x' : 'y',
49
- },
50
- plugins,
51
- )
52
- const [canScrollPrev, setCanScrollPrev] = React.useState(false)
53
- const [canScrollNext, setCanScrollNext] = React.useState(false)
54
-
55
- const onSelect = React.useCallback(() => {
56
- if (!api) {
57
- return
58
- }
59
-
60
- setCanScrollPrev(api.canScrollPrev())
61
- setCanScrollNext(api.canScrollNext())
62
- }, [api])
63
-
64
- const scrollPrev = React.useCallback(() => {
65
- api?.scrollPrev()
66
- }, [api])
67
-
68
- const scrollNext = React.useCallback(() => {
69
- api?.scrollNext()
70
- }, [api])
71
-
72
- const handleKeyDown = React.useCallback(
73
- (event: React.KeyboardEvent<HTMLDivElement>) => {
74
- if (event.key === 'ArrowLeft') {
75
- event.preventDefault()
76
- scrollPrev()
77
- } else if (event.key === 'ArrowRight') {
78
- event.preventDefault()
79
- scrollNext()
80
- }
81
- },
82
- [scrollPrev, scrollNext],
83
- )
84
-
85
- React.useEffect(() => {
86
- if (!api || !setApi) {
87
- return
88
- }
89
-
90
- setApi(api)
91
- }, [api, setApi])
92
-
93
- React.useEffect(() => {
94
- if (!api) {
95
- return
96
- }
97
-
98
- onSelect()
99
- api.on('reInit', onSelect)
100
- api.on('select', onSelect)
101
-
102
- return () => {
103
- api?.off('select', onSelect)
104
- }
105
- }, [api, onSelect])
106
-
107
- const memoizedValue = useMemo(
108
- () => ({
109
- carouselRef,
110
- api: api,
111
- opts,
112
- orientation: orientation || (opts?.axis === 'y' ? 'vertical' : 'horizontal'),
113
- scrollPrev,
114
- scrollNext,
115
- canScrollPrev,
116
- canScrollNext,
117
- }),
118
- [api, canScrollNext, canScrollPrev, carouselRef, opts, orientation, scrollNext, scrollPrev],
119
- )
120
-
121
- return (
122
- <CarouselContext.Provider value={memoizedValue}>
123
- <div
124
- ref={ref}
125
- onKeyDownCapture={handleKeyDown}
126
- className={cn('relative', className)}
127
- aria-roledescription="carousel"
128
- {...props}
129
- >
130
- {children}
131
- </div>
132
- </CarouselContext.Provider>
133
- )
134
- },
135
- )
136
- Carousel.displayName = 'Carousel'
137
-
138
- const CarouselContent = React.forwardRef<HTMLDivElement, React.HTMLAttributes<HTMLDivElement>>(
139
- ({ className, ...props }, ref) => {
140
- const { carouselRef, orientation } = useCarousel()
141
-
142
- return (
143
- <div ref={carouselRef} className="overflow-hidden">
144
- <div
145
- ref={ref}
146
- className={cn('flex', orientation === 'horizontal' ? '-ml-4' : '-mt-4 flex-col', className)}
147
- {...props}
148
- />
149
- </div>
150
- )
151
- },
152
- )
153
- CarouselContent.displayName = 'CarouselContent'
154
-
155
- const CarouselItem = React.forwardRef<HTMLDivElement, React.HTMLAttributes<HTMLDivElement>>(
156
- ({ className, ...props }, ref) => {
157
- const { orientation } = useCarousel()
158
-
159
- return (
160
- <div
161
- ref={ref}
162
- aria-roledescription="slide"
163
- className={cn('min-w-0 shrink-0 grow-0 basis-full', orientation === 'horizontal' ? 'pl-4' : 'pt-4', className)}
164
- {...props}
165
- />
166
- )
167
- },
168
- )
169
- CarouselItem.displayName = 'CarouselItem'
170
-
171
- const CarouselPrevious = React.forwardRef<HTMLButtonElement, React.ComponentProps<typeof Button>>(
172
- ({ className, variant = 'outline', size = 'icon', ...props }, ref) => {
173
- const { orientation, scrollPrev, canScrollPrev } = useCarousel()
174
-
175
- return (
176
- <Button
177
- ref={ref}
178
- variant={variant}
179
- size={size}
180
- className={cn(
181
- 'absolute h-8 w-8 rounded-full',
182
- orientation === 'horizontal'
183
- ? '-left-12 top-1/2 -translate-y-1/2'
184
- : '-top-12 left-1/2 -translate-x-1/2 rotate-90',
185
- className,
186
- )}
187
- disabled={!canScrollPrev}
188
- onClick={scrollPrev}
189
- {...props}
190
- >
191
- <ArrowLeftIcon className="h-4 w-4" />
192
- <span className="sr-only">Previous slide</span>
193
- </Button>
194
- )
195
- },
196
- )
197
- CarouselPrevious.displayName = 'CarouselPrevious'
198
-
199
- const CarouselNext = React.forwardRef<HTMLButtonElement, React.ComponentProps<typeof Button>>(
200
- ({ className, variant = 'outline', size = 'icon', ...props }, ref) => {
201
- const { orientation, scrollNext, canScrollNext } = useCarousel()
202
-
203
- return (
204
- <Button
205
- ref={ref}
206
- variant={variant}
207
- size={size}
208
- className={cn(
209
- 'absolute h-8 w-8 rounded-full',
210
- orientation === 'horizontal'
211
- ? '-right-12 top-1/2 -translate-y-1/2'
212
- : '-bottom-12 left-1/2 -translate-x-1/2 rotate-90',
213
- className,
214
- )}
215
- disabled={!canScrollNext}
216
- onClick={scrollNext}
217
- {...props}
218
- >
219
- <ArrowRightIcon className="h-4 w-4" />
220
- <span className="sr-only">Next slide</span>
221
- </Button>
222
- )
223
- },
224
- )
225
- CarouselNext.displayName = 'CarouselNext'
226
-
227
- export { type CarouselApi, type CarouselProps, Carousel, CarouselContent, CarouselItem, CarouselPrevious, CarouselNext }
@@ -1,106 +0,0 @@
1
- import type { Meta, StoryObj } from '@storybook/react-vite'
2
-
3
- import { Checkbox } from './checkbox'
4
- import { expect, userEvent, screen } from 'storybook/test'
5
-
6
- const meta = {
7
- title: 'Checkbox',
8
- component: Checkbox,
9
- tags: ['autodocs'],
10
- parameters: {
11
- layout: 'centered',
12
- },
13
- argTypes: {
14
- variant: {
15
- control: 'select',
16
- options: ['default', 'simple', 'iconSolo'],
17
- },
18
- checkboxSize: {
19
- control: 'select',
20
- options: ['default', 'sm', 'lg'],
21
- },
22
- checkIcon: {
23
- control: 'select',
24
- options: ['default', 'check', 'square'],
25
- },
26
- iconStyle: {
27
- control: 'select',
28
- options: ['default', 'simple', 'solo'],
29
- },
30
- },
31
- } satisfies Meta<typeof Checkbox>
32
- export default meta
33
-
34
- type Story = StoryObj<typeof meta>
35
-
36
- export const Default: Story = {
37
- args: { variant: 'default', checkboxSize: 'default', checkIcon: 'default', iconStyle: 'default' },
38
- render: (args) => <Checkbox {...args} defaultChecked={true} label="Default" id="default-cb" />,
39
- }
40
-
41
- export const Variants: Story = {
42
- render: () => (
43
- <div className="flex flex-wrap gap-2">
44
- <Checkbox defaultChecked={true} label="Default" variant="default" id="default-variant" />
45
- <Checkbox
46
- defaultChecked={true}
47
- label="Simple (combined with iconStyle=simple)"
48
- variant="simple"
49
- iconStyle="simple"
50
- id="simple-variant"
51
- />
52
- <Checkbox
53
- defaultChecked={true}
54
- label="IconSolo (combined with iconStyle=solo)"
55
- variant="iconSolo"
56
- iconStyle="solo"
57
- id="icon-solo-variant"
58
- />
59
- </div>
60
- ),
61
- }
62
-
63
- export const IconStyles: Story = {
64
- render: () => (
65
- <div className="flex flex-wrap gap-2">
66
- <Checkbox defaultChecked={true} label="Default" iconStyle="default" id="default-icon-style" />
67
- <Checkbox defaultChecked={true} label="Simple" iconStyle="simple" id="simple-icon-style" />
68
- <Checkbox defaultChecked={true} label="Solo" iconStyle="solo" />
69
- </div>
70
- ),
71
- }
72
-
73
- export const Sizes: Story = {
74
- render: () => (
75
- <div className="flex flex-wrap gap-2">
76
- <Checkbox defaultChecked={true} label="Small" checkboxSize="sm" />
77
- <Checkbox defaultChecked={true} label="Default" checkboxSize="default" id="default-size" />
78
- <Checkbox defaultChecked={true} label="Large" checkboxSize="lg" />
79
- </div>
80
- ),
81
- }
82
-
83
- export const CheckIcons: Story = {
84
- render: () => (
85
- <div className="flex flex-wrap gap-2">
86
- <Checkbox defaultChecked={true} label="Default" checkIcon="default" id="default-icon" />
87
- <Checkbox defaultChecked={true} label="Check" checkIcon="check" />
88
- <Checkbox defaultChecked={true} label="Square" checkIcon="square" />
89
- </div>
90
- ),
91
- }
92
-
93
- export const Disabled: Story = {
94
- args: {
95
- label: 'Disabled',
96
- disabled: true,
97
- },
98
- render: (args) => <Checkbox {...args} data-testid="disabled-checkbox" />,
99
- play: async () => {
100
- const disabledCheckbox = screen.getByTestId('disabled-checkbox')
101
-
102
- await expect(disabledCheckbox).toHaveAttribute('disabled')
103
-
104
- await userEvent.click(disabledCheckbox, { pointerEventsCheck: 0 })
105
- },
106
- }