dropdown-menu.jsx 7.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223
  1. "use client"
  2. import * as React from "react"
  3. import * as DropdownMenuPrimitive from "@radix-ui/react-dropdown-menu"
  4. import { CheckIcon, ChevronRightIcon, CircleIcon } from "lucide-react"
  5. import { cn } from "@/lib/utils"
  6. function DropdownMenu({
  7. ...props
  8. }) {
  9. return <DropdownMenuPrimitive.Root data-slot="dropdown-menu" {...props} />;
  10. }
  11. function DropdownMenuPortal({
  12. ...props
  13. }) {
  14. return (<DropdownMenuPrimitive.Portal data-slot="dropdown-menu-portal" {...props} />);
  15. }
  16. function DropdownMenuTrigger({
  17. ...props
  18. }) {
  19. return (<DropdownMenuPrimitive.Trigger data-slot="dropdown-menu-trigger" {...props} />);
  20. }
  21. function DropdownMenuContent({
  22. className,
  23. sideOffset = 4,
  24. ...props
  25. }) {
  26. return (
  27. <DropdownMenuPrimitive.Portal>
  28. <DropdownMenuPrimitive.Content
  29. data-slot="dropdown-menu-content"
  30. sideOffset={sideOffset}
  31. className={cn(
  32. "bg-popover text-popover-foreground 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 z-50 max-h-(--radix-dropdown-menu-content-available-height) min-w-[8rem] origin-(--radix-dropdown-menu-content-transform-origin) overflow-x-hidden overflow-y-auto rounded-md border p-1 shadow-md",
  33. className
  34. )}
  35. {...props} />
  36. </DropdownMenuPrimitive.Portal>
  37. );
  38. }
  39. function DropdownMenuGroup({
  40. ...props
  41. }) {
  42. return (<DropdownMenuPrimitive.Group data-slot="dropdown-menu-group" {...props} />);
  43. }
  44. function DropdownMenuItem({
  45. className,
  46. inset,
  47. variant = "default",
  48. ...props
  49. }) {
  50. return (
  51. <DropdownMenuPrimitive.Item
  52. data-slot="dropdown-menu-item"
  53. data-inset={inset}
  54. data-variant={variant}
  55. className={cn(
  56. "focus:bg-accent focus:text-accent-foreground data-[variant=destructive]:text-destructive data-[variant=destructive]:focus:bg-destructive/10 dark:data-[variant=destructive]:focus:bg-destructive/20 data-[variant=destructive]:focus:text-destructive data-[variant=destructive]:*:[svg]:!text-destructive [&_svg:not([class*='text-'])]:text-muted-foreground relative flex cursor-default items-center gap-2 rounded-sm px-2 py-1.5 text-sm outline-hidden select-none data-[disabled]:pointer-events-none data-[disabled]:opacity-50 data-[inset]:pl-8 [&_svg]:pointer-events-none [&_svg]:shrink-0 [&_svg:not([class*='size-'])]:size-4",
  57. className
  58. )}
  59. {...props} />
  60. );
  61. }
  62. function DropdownMenuCheckboxItem({
  63. className,
  64. children,
  65. checked,
  66. ...props
  67. }) {
  68. return (
  69. <DropdownMenuPrimitive.CheckboxItem
  70. data-slot="dropdown-menu-checkbox-item"
  71. className={cn(
  72. "focus:bg-accent focus:text-accent-foreground relative flex cursor-default items-center gap-2 rounded-sm py-1.5 pr-2 pl-8 text-sm outline-hidden select-none data-[disabled]:pointer-events-none data-[disabled]:opacity-50 [&_svg]:pointer-events-none [&_svg]:shrink-0 [&_svg:not([class*='size-'])]:size-4",
  73. className
  74. )}
  75. checked={checked}
  76. {...props}>
  77. <span
  78. className="pointer-events-none absolute left-2 flex size-3.5 items-center justify-center">
  79. <DropdownMenuPrimitive.ItemIndicator>
  80. <CheckIcon className="size-4" />
  81. </DropdownMenuPrimitive.ItemIndicator>
  82. </span>
  83. {children}
  84. </DropdownMenuPrimitive.CheckboxItem>
  85. );
  86. }
  87. function DropdownMenuRadioGroup({
  88. ...props
  89. }) {
  90. return (<DropdownMenuPrimitive.RadioGroup data-slot="dropdown-menu-radio-group" {...props} />);
  91. }
  92. function DropdownMenuRadioItem({
  93. className,
  94. children,
  95. ...props
  96. }) {
  97. return (
  98. <DropdownMenuPrimitive.RadioItem
  99. data-slot="dropdown-menu-radio-item"
  100. className={cn(
  101. "focus:bg-accent focus:text-accent-foreground relative flex cursor-default items-center gap-2 rounded-sm py-1.5 pr-2 pl-8 text-sm outline-hidden select-none data-[disabled]:pointer-events-none data-[disabled]:opacity-50 [&_svg]:pointer-events-none [&_svg]:shrink-0 [&_svg:not([class*='size-'])]:size-4",
  102. className
  103. )}
  104. {...props}>
  105. <span
  106. className="pointer-events-none absolute left-2 flex size-3.5 items-center justify-center">
  107. <DropdownMenuPrimitive.ItemIndicator>
  108. <CircleIcon className="size-2 fill-current" />
  109. </DropdownMenuPrimitive.ItemIndicator>
  110. </span>
  111. {children}
  112. </DropdownMenuPrimitive.RadioItem>
  113. );
  114. }
  115. function DropdownMenuLabel({
  116. className,
  117. inset,
  118. ...props
  119. }) {
  120. return (
  121. <DropdownMenuPrimitive.Label
  122. data-slot="dropdown-menu-label"
  123. data-inset={inset}
  124. className={cn("px-2 py-1.5 text-sm font-medium data-[inset]:pl-8", className)}
  125. {...props} />
  126. );
  127. }
  128. function DropdownMenuSeparator({
  129. className,
  130. ...props
  131. }) {
  132. return (
  133. <DropdownMenuPrimitive.Separator
  134. data-slot="dropdown-menu-separator"
  135. className={cn("bg-border -mx-1 my-1 h-px", className)}
  136. {...props} />
  137. );
  138. }
  139. function DropdownMenuShortcut({
  140. className,
  141. ...props
  142. }) {
  143. return (
  144. <span
  145. data-slot="dropdown-menu-shortcut"
  146. className={cn("text-muted-foreground ml-auto text-xs tracking-widest", className)}
  147. {...props} />
  148. );
  149. }
  150. function DropdownMenuSub({
  151. ...props
  152. }) {
  153. return <DropdownMenuPrimitive.Sub data-slot="dropdown-menu-sub" {...props} />;
  154. }
  155. function DropdownMenuSubTrigger({
  156. className,
  157. inset,
  158. children,
  159. ...props
  160. }) {
  161. return (
  162. <DropdownMenuPrimitive.SubTrigger
  163. data-slot="dropdown-menu-sub-trigger"
  164. data-inset={inset}
  165. className={cn(
  166. "focus:bg-accent focus:text-accent-foreground data-[state=open]:bg-accent data-[state=open]:text-accent-foreground [&_svg:not([class*='text-'])]:text-muted-foreground flex cursor-default items-center gap-2 rounded-sm px-2 py-1.5 text-sm outline-hidden select-none data-[inset]:pl-8 [&_svg]:pointer-events-none [&_svg]:shrink-0 [&_svg:not([class*='size-'])]:size-4",
  167. className
  168. )}
  169. {...props}>
  170. {children}
  171. <ChevronRightIcon className="ml-auto size-4" />
  172. </DropdownMenuPrimitive.SubTrigger>
  173. );
  174. }
  175. function DropdownMenuSubContent({
  176. className,
  177. ...props
  178. }) {
  179. return (
  180. <DropdownMenuPrimitive.SubContent
  181. data-slot="dropdown-menu-sub-content"
  182. className={cn(
  183. "bg-popover text-popover-foreground 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 z-50 min-w-[8rem] origin-(--radix-dropdown-menu-content-transform-origin) overflow-hidden rounded-md border p-1 shadow-lg",
  184. className
  185. )}
  186. {...props} />
  187. );
  188. }
  189. export {
  190. DropdownMenu,
  191. DropdownMenuPortal,
  192. DropdownMenuTrigger,
  193. DropdownMenuContent,
  194. DropdownMenuGroup,
  195. DropdownMenuLabel,
  196. DropdownMenuItem,
  197. DropdownMenuCheckboxItem,
  198. DropdownMenuRadioGroup,
  199. DropdownMenuRadioItem,
  200. DropdownMenuSeparator,
  201. DropdownMenuShortcut,
  202. DropdownMenuSub,
  203. DropdownMenuSubTrigger,
  204. DropdownMenuSubContent,
  205. }