accordion.tsx raw

   1  import * as React from "react";
   2  import { ChevronDownIcon } from "lucide-react";
   3  import { Accordion as AccordionPrimitive } from "radix-ui";
   4  
   5  import { cn } from "src/lib/utils";
   6  
   7  function Accordion({
   8    ...props
   9  }: React.ComponentProps<typeof AccordionPrimitive.Root>) {
  10    return <AccordionPrimitive.Root data-slot="accordion" {...props} />;
  11  }
  12  
  13  function AccordionItem({
  14    className,
  15    ...props
  16  }: React.ComponentProps<typeof AccordionPrimitive.Item>) {
  17    return (
  18      <AccordionPrimitive.Item
  19        data-slot="accordion-item"
  20        className={cn("border-b last:border-b-0", className)}
  21        {...props}
  22      />
  23    );
  24  }
  25  
  26  function AccordionTrigger({
  27    className,
  28    children,
  29    ...props
  30  }: React.ComponentProps<typeof AccordionPrimitive.Trigger>) {
  31    return (
  32      <AccordionPrimitive.Header className="flex">
  33        <AccordionPrimitive.Trigger
  34          data-slot="accordion-trigger"
  35          className={cn(
  36            "flex flex-1 items-start justify-between gap-4 rounded-md py-4 text-left text-sm font-medium transition-all outline-none hover:underline focus-visible:border-ring focus-visible:ring-[3px] focus-visible:ring-ring/50 disabled:pointer-events-none disabled:opacity-50 [&[data-state=open]>svg]:rotate-180",
  37            className
  38          )}
  39          {...props}
  40        >
  41          {children}
  42          <ChevronDownIcon className="pointer-events-none size-4 shrink-0 translate-y-0.5 text-muted-foreground transition-transform duration-200" />
  43        </AccordionPrimitive.Trigger>
  44      </AccordionPrimitive.Header>
  45    );
  46  }
  47  
  48  function AccordionContent({
  49    className,
  50    children,
  51    ...props
  52  }: React.ComponentProps<typeof AccordionPrimitive.Content>) {
  53    return (
  54      <AccordionPrimitive.Content
  55        data-slot="accordion-content"
  56        className="overflow-hidden text-sm data-[state=closed]:animate-accordion-up data-[state=open]:animate-accordion-down"
  57        {...props}
  58      >
  59        <div className={cn("pt-0 pb-4", className)}>{children}</div>
  60      </AccordionPrimitive.Content>
  61    );
  62  }
  63  
  64  export { Accordion, AccordionItem, AccordionTrigger, AccordionContent };
  65