cooterlabs 1.0.1 → 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.
@@ -1,17 +1,8 @@
1
1
  import * as React from "react"
2
-
3
- import { cn } from "./button" // Assuming they have cn utility somewhere accessible, or we'll rewrite it to inline
4
-
5
- export function cnFallback(...classes: (string | undefined | null | false)[]) {
6
- return classes.filter(Boolean).join(" ")
7
- }
8
-
9
- // In a real scenario you'd import 'cn' from a library or a utils file.
10
- // We'll provide an inline cn for fallback or rely on the user having ones installed:
11
2
  import { clsx, type ClassValue } from "clsx"
12
3
  import { twMerge } from "tailwind-merge"
13
4
 
14
- function localCn(...inputs: ClassValue[]) {
5
+ function cn(...inputs: ClassValue[]) {
15
6
  return twMerge(clsx(inputs))
16
7
  }
17
8
 
@@ -21,8 +12,8 @@ const Card = React.forwardRef<
21
12
  >(({ className, ...props }, ref) => (
22
13
  <div
23
14
  ref={ref}
24
- className={localCn(
25
- "rounded-xl border bg-card text-card-foreground shadow",
15
+ className={cn(
16
+ "overflow-hidden rounded-md border border-grey-100 bg-card text-foreground shadow-200",
26
17
  className
27
18
  )}
28
19
  {...props}
@@ -30,25 +21,38 @@ const Card = React.forwardRef<
30
21
  ))
31
22
  Card.displayName = "Card"
32
23
 
24
+ const CardImage = React.forwardRef<
25
+ HTMLImageElement,
26
+ React.ImgHTMLAttributes<HTMLImageElement>
27
+ >(({ className, alt = "", ...props }, ref) => (
28
+ <img
29
+ ref={ref}
30
+ alt={alt}
31
+ className={cn("h-50 w-full object-cover", className)}
32
+ {...props}
33
+ />
34
+ ))
35
+ CardImage.displayName = "CardImage"
36
+
33
37
  const CardHeader = React.forwardRef<
34
38
  HTMLDivElement,
35
39
  React.HTMLAttributes<HTMLDivElement>
36
40
  >(({ className, ...props }, ref) => (
37
41
  <div
38
42
  ref={ref}
39
- className={localCn("flex flex-col space-y-1.5 p-6", className)}
43
+ className={cn("flex flex-col space-y-1.5 p-6", className)}
40
44
  {...props}
41
45
  />
42
46
  ))
43
47
  CardHeader.displayName = "CardHeader"
44
48
 
45
49
  const CardTitle = React.forwardRef<
46
- HTMLParagraphElement,
50
+ HTMLHeadingElement,
47
51
  React.HTMLAttributes<HTMLHeadingElement>
48
52
  >(({ className, ...props }, ref) => (
49
53
  <h3
50
54
  ref={ref}
51
- className={localCn("font-semibold leading-none tracking-tight", className)}
55
+ className={cn("text-s2 text-foreground", className)}
52
56
  {...props}
53
57
  />
54
58
  ))
@@ -60,7 +64,7 @@ const CardDescription = React.forwardRef<
60
64
  >(({ className, ...props }, ref) => (
61
65
  <p
62
66
  ref={ref}
63
- className={localCn("text-sm text-muted-foreground", className)}
67
+ className={cn("text-b3 text-muted-foreground", className)}
64
68
  {...props}
65
69
  />
66
70
  ))
@@ -70,7 +74,7 @@ const CardContent = React.forwardRef<
70
74
  HTMLDivElement,
71
75
  React.HTMLAttributes<HTMLDivElement>
72
76
  >(({ className, ...props }, ref) => (
73
- <div ref={ref} className={localCn("p-6 pt-0", className)} {...props} />
77
+ <div ref={ref} className={cn("p-6 pt-0", className)} {...props} />
74
78
  ))
75
79
  CardContent.displayName = "CardContent"
76
80
 
@@ -80,10 +84,18 @@ const CardFooter = React.forwardRef<
80
84
  >(({ className, ...props }, ref) => (
81
85
  <div
82
86
  ref={ref}
83
- className={localCn("flex items-center p-6 pt-0", className)}
87
+ className={cn("flex items-center p-6 pt-0", className)}
84
88
  {...props}
85
89
  />
86
90
  ))
87
91
  CardFooter.displayName = "CardFooter"
88
92
 
89
- export { Card, CardHeader, CardFooter, CardTitle, CardDescription, CardContent }
93
+ export {
94
+ Card,
95
+ CardImage,
96
+ CardHeader,
97
+ CardFooter,
98
+ CardTitle,
99
+ CardDescription,
100
+ CardContent,
101
+ }
@@ -1,6 +1,6 @@
1
1
  import * as React from "react"
2
2
  import * as CheckboxPrimitive from "@radix-ui/react-checkbox"
3
- import { Check } from "lucide-react"
3
+ import { Check, Minus } from "lucide-react"
4
4
  import { clsx, type ClassValue } from "clsx"
5
5
  import { twMerge } from "tailwind-merge"
6
6
 
@@ -15,7 +15,7 @@ const Checkbox = React.forwardRef<
15
15
  <CheckboxPrimitive.Root
16
16
  ref={ref}
17
17
  className={cn(
18
- "peer h-4 w-4 shrink-0 rounded-sm border border-primary ring-offset-background focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring focus-visible:ring-offset-2 disabled:cursor-not-allowed disabled:opacity-50 data-[state=checked]:bg-primary data-[state=checked]:text-primary-foreground",
18
+ "group peer size-5 shrink-0 rounded-xxs border border-grey-300 bg-background ring-offset-background transition-colors hover:border-grey-400 focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring focus-visible:ring-offset-2 disabled:pointer-events-none disabled:border-grey-200 disabled:bg-muted data-[state=checked]:border-primary data-[state=checked]:bg-primary data-[state=checked]:text-primary-foreground data-[state=indeterminate]:border-primary data-[state=indeterminate]:bg-primary data-[state=indeterminate]:text-primary-foreground",
19
19
  className
20
20
  )}
21
21
  {...props}
@@ -23,7 +23,8 @@ const Checkbox = React.forwardRef<
23
23
  <CheckboxPrimitive.Indicator
24
24
  className={cn("flex items-center justify-center text-current")}
25
25
  >
26
- <Check className="h-4 w-4" />
26
+ <Check className="size-4 group-data-[state=indeterminate]:hidden" />
27
+ <Minus className="size-4 group-data-[state=checked]:hidden" />
27
28
  </CheckboxPrimitive.Indicator>
28
29
  </CheckboxPrimitive.Root>
29
30
  ))
@@ -0,0 +1,177 @@
1
+ import * as React from "react"
2
+ import * as ContextMenuPrimitive from "@radix-ui/react-context-menu"
3
+ import { Check, ChevronRight } from "lucide-react"
4
+ import { clsx, type ClassValue } from "clsx"
5
+ import { twMerge } from "tailwind-merge"
6
+
7
+ export function cn(...inputs: ClassValue[]) {
8
+ return twMerge(clsx(inputs))
9
+ }
10
+
11
+ const surfaceClasses =
12
+ "z-50 min-w-48 overflow-hidden bg-popover text-popover-foreground rounded-xs shadow-400 border border-grey-100 p-1"
13
+
14
+ const itemClasses =
15
+ "relative flex h-10 cursor-default select-none items-center gap-2 px-3 rounded-xxs text-b3 outline-none transition-colors data-[highlighted]:bg-accent data-[highlighted]:text-accent-foreground data-[disabled]:pointer-events-none data-[disabled]:opacity-50 [&_svg]:size-4 [&_svg]:shrink-0"
16
+
17
+ const ContextMenu = ContextMenuPrimitive.Root
18
+
19
+ const ContextMenuTrigger = ContextMenuPrimitive.Trigger
20
+
21
+ const ContextMenuGroup = ContextMenuPrimitive.Group
22
+
23
+ const ContextMenuPortal = ContextMenuPrimitive.Portal
24
+
25
+ const ContextMenuSub = ContextMenuPrimitive.Sub
26
+
27
+ const ContextMenuRadioGroup = ContextMenuPrimitive.RadioGroup
28
+
29
+ const ContextMenuContent = React.forwardRef<
30
+ React.ElementRef<typeof ContextMenuPrimitive.Content>,
31
+ React.ComponentPropsWithoutRef<typeof ContextMenuPrimitive.Content>
32
+ >(({ className, ...props }, ref) => (
33
+ <ContextMenuPrimitive.Portal>
34
+ <ContextMenuPrimitive.Content
35
+ ref={ref}
36
+ className={cn(surfaceClasses, className)}
37
+ {...props}
38
+ />
39
+ </ContextMenuPrimitive.Portal>
40
+ ))
41
+ ContextMenuContent.displayName = ContextMenuPrimitive.Content.displayName
42
+
43
+ export interface ContextMenuItemProps
44
+ extends React.ComponentPropsWithoutRef<typeof ContextMenuPrimitive.Item> {
45
+ variant?: "default" | "destructive"
46
+ }
47
+
48
+ const ContextMenuItem = React.forwardRef<
49
+ React.ElementRef<typeof ContextMenuPrimitive.Item>,
50
+ ContextMenuItemProps
51
+ >(({ className, variant = "default", ...props }, ref) => (
52
+ <ContextMenuPrimitive.Item
53
+ ref={ref}
54
+ className={cn(
55
+ itemClasses,
56
+ variant === "destructive" &&
57
+ "text-error data-[highlighted]:bg-error-50 data-[highlighted]:text-error",
58
+ className
59
+ )}
60
+ {...props}
61
+ />
62
+ ))
63
+ ContextMenuItem.displayName = ContextMenuPrimitive.Item.displayName
64
+
65
+ const ContextMenuCheckboxItem = React.forwardRef<
66
+ React.ElementRef<typeof ContextMenuPrimitive.CheckboxItem>,
67
+ React.ComponentPropsWithoutRef<typeof ContextMenuPrimitive.CheckboxItem>
68
+ >(({ className, children, checked, ...props }, ref) => (
69
+ <ContextMenuPrimitive.CheckboxItem
70
+ ref={ref}
71
+ className={cn(itemClasses, "pl-8", className)}
72
+ checked={checked}
73
+ {...props}
74
+ >
75
+ <span className="absolute left-2 flex size-4 items-center justify-center">
76
+ <ContextMenuPrimitive.ItemIndicator>
77
+ <Check className="size-4" />
78
+ </ContextMenuPrimitive.ItemIndicator>
79
+ </span>
80
+ {children}
81
+ </ContextMenuPrimitive.CheckboxItem>
82
+ ))
83
+ ContextMenuCheckboxItem.displayName =
84
+ ContextMenuPrimitive.CheckboxItem.displayName
85
+
86
+ const ContextMenuRadioItem = React.forwardRef<
87
+ React.ElementRef<typeof ContextMenuPrimitive.RadioItem>,
88
+ React.ComponentPropsWithoutRef<typeof ContextMenuPrimitive.RadioItem>
89
+ >(({ className, children, ...props }, ref) => (
90
+ <ContextMenuPrimitive.RadioItem
91
+ ref={ref}
92
+ className={cn(itemClasses, "pl-8", className)}
93
+ {...props}
94
+ >
95
+ <span className="absolute left-2 flex size-4 items-center justify-center">
96
+ <ContextMenuPrimitive.ItemIndicator>
97
+ <span className="block size-2 rounded-full bg-current" />
98
+ </ContextMenuPrimitive.ItemIndicator>
99
+ </span>
100
+ {children}
101
+ </ContextMenuPrimitive.RadioItem>
102
+ ))
103
+ ContextMenuRadioItem.displayName = ContextMenuPrimitive.RadioItem.displayName
104
+
105
+ const ContextMenuLabel = React.forwardRef<
106
+ React.ElementRef<typeof ContextMenuPrimitive.Label>,
107
+ React.ComponentPropsWithoutRef<typeof ContextMenuPrimitive.Label>
108
+ >(({ className, ...props }, ref) => (
109
+ <ContextMenuPrimitive.Label
110
+ ref={ref}
111
+ className={cn("px-3 py-2 text-label text-muted-foreground", className)}
112
+ {...props}
113
+ />
114
+ ))
115
+ ContextMenuLabel.displayName = ContextMenuPrimitive.Label.displayName
116
+
117
+ const ContextMenuSeparator = React.forwardRef<
118
+ React.ElementRef<typeof ContextMenuPrimitive.Separator>,
119
+ React.ComponentPropsWithoutRef<typeof ContextMenuPrimitive.Separator>
120
+ >(({ className, ...props }, ref) => (
121
+ <ContextMenuPrimitive.Separator
122
+ ref={ref}
123
+ className={cn("-mx-1 my-1 h-px bg-grey-100", className)}
124
+ {...props}
125
+ />
126
+ ))
127
+ ContextMenuSeparator.displayName = ContextMenuPrimitive.Separator.displayName
128
+
129
+ const ContextMenuSubTrigger = React.forwardRef<
130
+ React.ElementRef<typeof ContextMenuPrimitive.SubTrigger>,
131
+ React.ComponentPropsWithoutRef<typeof ContextMenuPrimitive.SubTrigger>
132
+ >(({ className, children, ...props }, ref) => (
133
+ <ContextMenuPrimitive.SubTrigger
134
+ ref={ref}
135
+ className={cn(
136
+ itemClasses,
137
+ "data-[state=open]:bg-accent data-[state=open]:text-accent-foreground",
138
+ className
139
+ )}
140
+ {...props}
141
+ >
142
+ {children}
143
+ <ChevronRight className="ml-auto size-4" />
144
+ </ContextMenuPrimitive.SubTrigger>
145
+ ))
146
+ ContextMenuSubTrigger.displayName = ContextMenuPrimitive.SubTrigger.displayName
147
+
148
+ const ContextMenuSubContent = React.forwardRef<
149
+ React.ElementRef<typeof ContextMenuPrimitive.SubContent>,
150
+ React.ComponentPropsWithoutRef<typeof ContextMenuPrimitive.SubContent>
151
+ >(({ className, ...props }, ref) => (
152
+ <ContextMenuPrimitive.Portal>
153
+ <ContextMenuPrimitive.SubContent
154
+ ref={ref}
155
+ className={cn(surfaceClasses, className)}
156
+ {...props}
157
+ />
158
+ </ContextMenuPrimitive.Portal>
159
+ ))
160
+ ContextMenuSubContent.displayName = ContextMenuPrimitive.SubContent.displayName
161
+
162
+ export {
163
+ ContextMenu,
164
+ ContextMenuTrigger,
165
+ ContextMenuContent,
166
+ ContextMenuItem,
167
+ ContextMenuCheckboxItem,
168
+ ContextMenuRadioGroup,
169
+ ContextMenuRadioItem,
170
+ ContextMenuLabel,
171
+ ContextMenuSeparator,
172
+ ContextMenuGroup,
173
+ ContextMenuPortal,
174
+ ContextMenuSub,
175
+ ContextMenuSubTrigger,
176
+ ContextMenuSubContent,
177
+ }
@@ -0,0 +1,127 @@
1
+ import * as React from "react"
2
+ import * as DialogPrimitive from "@radix-ui/react-dialog"
3
+ import { X } from "lucide-react"
4
+ import { clsx, type ClassValue } from "clsx"
5
+ import { twMerge } from "tailwind-merge"
6
+
7
+ export function cn(...inputs: ClassValue[]) {
8
+ return twMerge(clsx(inputs))
9
+ }
10
+
11
+ const Dialog = DialogPrimitive.Root
12
+
13
+ const DialogTrigger = DialogPrimitive.Trigger
14
+
15
+ const DialogPortal = DialogPrimitive.Portal
16
+
17
+ const DialogClose = DialogPrimitive.Close
18
+
19
+ const DialogOverlay = React.forwardRef<
20
+ React.ElementRef<typeof DialogPrimitive.Overlay>,
21
+ React.ComponentPropsWithoutRef<typeof DialogPrimitive.Overlay>
22
+ >(({ className, ...props }, ref) => (
23
+ <DialogPrimitive.Overlay
24
+ ref={ref}
25
+ className={cn(
26
+ "fixed inset-0 z-50 bg-black/50 transition-opacity data-[state=closed]:opacity-0",
27
+ className
28
+ )}
29
+ {...props}
30
+ />
31
+ ))
32
+ DialogOverlay.displayName = DialogPrimitive.Overlay.displayName
33
+
34
+ const DialogContent = React.forwardRef<
35
+ React.ElementRef<typeof DialogPrimitive.Content>,
36
+ React.ComponentPropsWithoutRef<typeof DialogPrimitive.Content>
37
+ >(({ className, children, ...props }, ref) => (
38
+ <DialogPortal>
39
+ <DialogOverlay />
40
+ <DialogPrimitive.Content
41
+ ref={ref}
42
+ className={cn(
43
+ "fixed left-1/2 top-1/2 z-50 grid w-full max-w-md -translate-x-1/2 -translate-y-1/2 gap-4 bg-background p-6 rounded-md shadow-600 transition-opacity data-[state=closed]:opacity-0",
44
+ className
45
+ )}
46
+ {...props}
47
+ >
48
+ {children}
49
+ <DialogPrimitive.Close className="absolute right-4 top-4 rounded-xxs text-muted-foreground transition-colors hover:text-foreground focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring focus-visible:ring-offset-2 disabled:pointer-events-none">
50
+ <X className="size-5" />
51
+ <span className="sr-only">Close</span>
52
+ </DialogPrimitive.Close>
53
+ </DialogPrimitive.Content>
54
+ </DialogPortal>
55
+ ))
56
+ DialogContent.displayName = DialogPrimitive.Content.displayName
57
+
58
+ const DialogHeader = ({
59
+ className,
60
+ ...props
61
+ }: React.HTMLAttributes<HTMLDivElement>) => (
62
+ <div
63
+ className={cn("flex flex-col gap-2 text-center sm:text-left", className)}
64
+ {...props}
65
+ />
66
+ )
67
+ DialogHeader.displayName = "DialogHeader"
68
+
69
+ export interface DialogFooterProps
70
+ extends React.HTMLAttributes<HTMLDivElement> {
71
+ orientation?: "horizontal" | "vertical"
72
+ }
73
+
74
+ const DialogFooter = ({
75
+ className,
76
+ orientation = "horizontal",
77
+ ...props
78
+ }: DialogFooterProps) => (
79
+ <div
80
+ className={cn(
81
+ "flex gap-2",
82
+ orientation === "vertical"
83
+ ? "flex-col"
84
+ : "flex-row justify-end [&>*]:flex-1 sm:[&>*]:flex-none",
85
+ className
86
+ )}
87
+ {...props}
88
+ />
89
+ )
90
+ DialogFooter.displayName = "DialogFooter"
91
+
92
+ const DialogTitle = React.forwardRef<
93
+ React.ElementRef<typeof DialogPrimitive.Title>,
94
+ React.ComponentPropsWithoutRef<typeof DialogPrimitive.Title>
95
+ >(({ className, ...props }, ref) => (
96
+ <DialogPrimitive.Title
97
+ ref={ref}
98
+ className={cn("text-s1 text-foreground", className)}
99
+ {...props}
100
+ />
101
+ ))
102
+ DialogTitle.displayName = DialogPrimitive.Title.displayName
103
+
104
+ const DialogDescription = React.forwardRef<
105
+ React.ElementRef<typeof DialogPrimitive.Description>,
106
+ React.ComponentPropsWithoutRef<typeof DialogPrimitive.Description>
107
+ >(({ className, ...props }, ref) => (
108
+ <DialogPrimitive.Description
109
+ ref={ref}
110
+ className={cn("text-b3 text-muted-foreground", className)}
111
+ {...props}
112
+ />
113
+ ))
114
+ DialogDescription.displayName = DialogPrimitive.Description.displayName
115
+
116
+ export {
117
+ Dialog,
118
+ DialogTrigger,
119
+ DialogPortal,
120
+ DialogOverlay,
121
+ DialogContent,
122
+ DialogHeader,
123
+ DialogFooter,
124
+ DialogTitle,
125
+ DialogDescription,
126
+ DialogClose,
127
+ }
@@ -0,0 +1,180 @@
1
+ import * as React from "react"
2
+ import * as DropdownMenuPrimitive from "@radix-ui/react-dropdown-menu"
3
+ import { Check, ChevronRight } from "lucide-react"
4
+ import { clsx, type ClassValue } from "clsx"
5
+ import { twMerge } from "tailwind-merge"
6
+
7
+ export function cn(...inputs: ClassValue[]) {
8
+ return twMerge(clsx(inputs))
9
+ }
10
+
11
+ const surfaceClasses =
12
+ "z-50 min-w-48 overflow-hidden bg-popover text-popover-foreground rounded-xs shadow-400 border border-grey-100 p-1"
13
+
14
+ const itemClasses =
15
+ "relative flex h-10 cursor-default select-none items-center gap-2 px-3 rounded-xxs text-b3 outline-none transition-colors data-[highlighted]:bg-accent data-[highlighted]:text-accent-foreground data-[disabled]:pointer-events-none data-[disabled]:opacity-50 [&_svg]:size-4 [&_svg]:shrink-0"
16
+
17
+ const DropdownMenu = DropdownMenuPrimitive.Root
18
+
19
+ const DropdownMenuTrigger = DropdownMenuPrimitive.Trigger
20
+
21
+ const DropdownMenuGroup = DropdownMenuPrimitive.Group
22
+
23
+ const DropdownMenuPortal = DropdownMenuPrimitive.Portal
24
+
25
+ const DropdownMenuSub = DropdownMenuPrimitive.Sub
26
+
27
+ const DropdownMenuRadioGroup = DropdownMenuPrimitive.RadioGroup
28
+
29
+ const DropdownMenuContent = React.forwardRef<
30
+ React.ElementRef<typeof DropdownMenuPrimitive.Content>,
31
+ React.ComponentPropsWithoutRef<typeof DropdownMenuPrimitive.Content>
32
+ >(({ className, sideOffset = 4, ...props }, ref) => (
33
+ <DropdownMenuPrimitive.Portal>
34
+ <DropdownMenuPrimitive.Content
35
+ ref={ref}
36
+ sideOffset={sideOffset}
37
+ className={cn(surfaceClasses, className)}
38
+ {...props}
39
+ />
40
+ </DropdownMenuPrimitive.Portal>
41
+ ))
42
+ DropdownMenuContent.displayName = DropdownMenuPrimitive.Content.displayName
43
+
44
+ export interface DropdownMenuItemProps
45
+ extends React.ComponentPropsWithoutRef<typeof DropdownMenuPrimitive.Item> {
46
+ variant?: "default" | "destructive"
47
+ }
48
+
49
+ const DropdownMenuItem = React.forwardRef<
50
+ React.ElementRef<typeof DropdownMenuPrimitive.Item>,
51
+ DropdownMenuItemProps
52
+ >(({ className, variant = "default", ...props }, ref) => (
53
+ <DropdownMenuPrimitive.Item
54
+ ref={ref}
55
+ className={cn(
56
+ itemClasses,
57
+ variant === "destructive" &&
58
+ "text-error data-[highlighted]:bg-error-50 data-[highlighted]:text-error",
59
+ className
60
+ )}
61
+ {...props}
62
+ />
63
+ ))
64
+ DropdownMenuItem.displayName = DropdownMenuPrimitive.Item.displayName
65
+
66
+ const DropdownMenuCheckboxItem = React.forwardRef<
67
+ React.ElementRef<typeof DropdownMenuPrimitive.CheckboxItem>,
68
+ React.ComponentPropsWithoutRef<typeof DropdownMenuPrimitive.CheckboxItem>
69
+ >(({ className, children, checked, ...props }, ref) => (
70
+ <DropdownMenuPrimitive.CheckboxItem
71
+ ref={ref}
72
+ className={cn(itemClasses, "pl-8", className)}
73
+ checked={checked}
74
+ {...props}
75
+ >
76
+ <span className="absolute left-2 flex size-4 items-center justify-center">
77
+ <DropdownMenuPrimitive.ItemIndicator>
78
+ <Check className="size-4" />
79
+ </DropdownMenuPrimitive.ItemIndicator>
80
+ </span>
81
+ {children}
82
+ </DropdownMenuPrimitive.CheckboxItem>
83
+ ))
84
+ DropdownMenuCheckboxItem.displayName =
85
+ DropdownMenuPrimitive.CheckboxItem.displayName
86
+
87
+ const DropdownMenuRadioItem = React.forwardRef<
88
+ React.ElementRef<typeof DropdownMenuPrimitive.RadioItem>,
89
+ React.ComponentPropsWithoutRef<typeof DropdownMenuPrimitive.RadioItem>
90
+ >(({ className, children, ...props }, ref) => (
91
+ <DropdownMenuPrimitive.RadioItem
92
+ ref={ref}
93
+ className={cn(itemClasses, "pl-8", className)}
94
+ {...props}
95
+ >
96
+ <span className="absolute left-2 flex size-4 items-center justify-center">
97
+ <DropdownMenuPrimitive.ItemIndicator>
98
+ <span className="block size-2 rounded-full bg-current" />
99
+ </DropdownMenuPrimitive.ItemIndicator>
100
+ </span>
101
+ {children}
102
+ </DropdownMenuPrimitive.RadioItem>
103
+ ))
104
+ DropdownMenuRadioItem.displayName = DropdownMenuPrimitive.RadioItem.displayName
105
+
106
+ const DropdownMenuLabel = React.forwardRef<
107
+ React.ElementRef<typeof DropdownMenuPrimitive.Label>,
108
+ React.ComponentPropsWithoutRef<typeof DropdownMenuPrimitive.Label>
109
+ >(({ className, ...props }, ref) => (
110
+ <DropdownMenuPrimitive.Label
111
+ ref={ref}
112
+ className={cn("px-3 py-2 text-label text-muted-foreground", className)}
113
+ {...props}
114
+ />
115
+ ))
116
+ DropdownMenuLabel.displayName = DropdownMenuPrimitive.Label.displayName
117
+
118
+ const DropdownMenuSeparator = React.forwardRef<
119
+ React.ElementRef<typeof DropdownMenuPrimitive.Separator>,
120
+ React.ComponentPropsWithoutRef<typeof DropdownMenuPrimitive.Separator>
121
+ >(({ className, ...props }, ref) => (
122
+ <DropdownMenuPrimitive.Separator
123
+ ref={ref}
124
+ className={cn("-mx-1 my-1 h-px bg-grey-100", className)}
125
+ {...props}
126
+ />
127
+ ))
128
+ DropdownMenuSeparator.displayName = DropdownMenuPrimitive.Separator.displayName
129
+
130
+ const DropdownMenuSubTrigger = React.forwardRef<
131
+ React.ElementRef<typeof DropdownMenuPrimitive.SubTrigger>,
132
+ React.ComponentPropsWithoutRef<typeof DropdownMenuPrimitive.SubTrigger>
133
+ >(({ className, children, ...props }, ref) => (
134
+ <DropdownMenuPrimitive.SubTrigger
135
+ ref={ref}
136
+ className={cn(
137
+ itemClasses,
138
+ "data-[state=open]:bg-accent data-[state=open]:text-accent-foreground",
139
+ className
140
+ )}
141
+ {...props}
142
+ >
143
+ {children}
144
+ <ChevronRight className="ml-auto size-4" />
145
+ </DropdownMenuPrimitive.SubTrigger>
146
+ ))
147
+ DropdownMenuSubTrigger.displayName =
148
+ DropdownMenuPrimitive.SubTrigger.displayName
149
+
150
+ const DropdownMenuSubContent = React.forwardRef<
151
+ React.ElementRef<typeof DropdownMenuPrimitive.SubContent>,
152
+ React.ComponentPropsWithoutRef<typeof DropdownMenuPrimitive.SubContent>
153
+ >(({ className, ...props }, ref) => (
154
+ <DropdownMenuPrimitive.Portal>
155
+ <DropdownMenuPrimitive.SubContent
156
+ ref={ref}
157
+ className={cn(surfaceClasses, className)}
158
+ {...props}
159
+ />
160
+ </DropdownMenuPrimitive.Portal>
161
+ ))
162
+ DropdownMenuSubContent.displayName =
163
+ DropdownMenuPrimitive.SubContent.displayName
164
+
165
+ export {
166
+ DropdownMenu,
167
+ DropdownMenuTrigger,
168
+ DropdownMenuContent,
169
+ DropdownMenuItem,
170
+ DropdownMenuCheckboxItem,
171
+ DropdownMenuRadioGroup,
172
+ DropdownMenuRadioItem,
173
+ DropdownMenuLabel,
174
+ DropdownMenuSeparator,
175
+ DropdownMenuGroup,
176
+ DropdownMenuPortal,
177
+ DropdownMenuSub,
178
+ DropdownMenuSubTrigger,
179
+ DropdownMenuSubContent,
180
+ }
@@ -6,16 +6,43 @@ export function cn(...inputs: ClassValue[]) {
6
6
  return twMerge(clsx(inputs))
7
7
  }
8
8
 
9
+ const inputVariants = {
10
+ outline: "border-input bg-background hover:border-grey-300",
11
+ filled: "border-transparent bg-secondary hover:bg-muted",
12
+ }
13
+
14
+ const inputSizes = {
15
+ large: "h-12 px-4 text-b1",
16
+ medium: "h-10 px-3 text-b3",
17
+ }
18
+
19
+ const inputStatuses = {
20
+ success: "border-success",
21
+ info: "border-info",
22
+ warning: "border-warning",
23
+ error: "border-error",
24
+ }
25
+
9
26
  export interface InputProps
10
- extends React.InputHTMLAttributes<HTMLInputElement> { }
27
+ extends Omit<React.InputHTMLAttributes<HTMLInputElement>, "size"> {
28
+ variant?: keyof typeof inputVariants
29
+ size?: keyof typeof inputSizes
30
+ status?: keyof typeof inputStatuses
31
+ }
11
32
 
12
33
  const Input = React.forwardRef<HTMLInputElement, InputProps>(
13
- ({ className, type, ...props }, ref) => {
34
+ (
35
+ { className, type, variant = "outline", size = "large", status, ...props },
36
+ ref
37
+ ) => {
14
38
  return (
15
39
  <input
16
40
  type={type}
17
41
  className={cn(
18
- "flex h-10 w-full rounded-md border border-input bg-background px-3 py-2 text-sm ring-offset-background file:border-0 file:bg-transparent file:text-sm file:font-medium placeholder:text-muted-foreground focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring focus-visible:ring-offset-2 disabled:cursor-not-allowed disabled:opacity-50",
42
+ "flex w-full rounded-xs border text-foreground ring-offset-background transition-colors file:border-0 file:bg-transparent file:font-medium placeholder:text-muted-foreground focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring focus-visible:ring-offset-2 aria-invalid:border-error disabled:pointer-events-none disabled:border-grey-200 disabled:bg-secondary disabled:text-grey-400",
43
+ inputVariants[variant],
44
+ inputSizes[size],
45
+ status && inputStatuses[status],
19
46
  className
20
47
  )}
21
48
  ref={ref}
@@ -3,7 +3,7 @@ import * as LabelPrimitive from "@radix-ui/react-label"
3
3
  import { clsx, type ClassValue } from "clsx"
4
4
  import { twMerge } from "tailwind-merge"
5
5
 
6
- function cn(...inputs: ClassValue[]) {
6
+ export function cn(...inputs: ClassValue[]) {
7
7
  return twMerge(clsx(inputs))
8
8
  }
9
9
 
@@ -14,7 +14,7 @@ const Label = React.forwardRef<
14
14
  <LabelPrimitive.Root
15
15
  ref={ref}
16
16
  className={cn(
17
- "text-sm font-medium leading-none peer-disabled:cursor-not-allowed peer-disabled:opacity-70",
17
+ "text-label text-foreground peer-disabled:pointer-events-none peer-disabled:text-grey-400",
18
18
  className
19
19
  )}
20
20
  {...props}