Accordion
Organizes content into collapsible sections, allowing users to focus on one section at a time.
	<script lang="ts">
  import { Accordion } from "bits-ui";
  import { CaretDown } from "$icons/index.js";
 
  const items = [
    {
      title: "What is the meaning of life?",
      content:
        "To become a better person, to help others, and to leave the world a better place than you found it."
    },
    {
      title: "How do I become a better person?",
      content:
        "Read books, listen to podcasts, and surround yourself with people who inspire you."
    },
    {
      title: "What is the best way to help others?",
      content: "Give them your time, attention, and love."
    }
  ];
 
  let value = $state<string[]>([]);
</script>
 
<Accordion.Root class="w-full sm:max-w-[70%]" type="multiple" bind:value>
  {#each items as item, i}
    <Accordion.Item value={`${i}`} class="group border-b border-dark-10 px-1.5">
      <Accordion.Header>
        <Accordion.Trigger
          class="flex w-full flex-1 items-center justify-between py-5 text-[15px] font-medium transition-all [&[data-state=open]>span>svg]:rotate-180"
        >
          {item.title}
          <span
            class="inline-flex size-8 items-center justify-center rounded-[7px] bg-transparent transition-all hover:bg-dark-10"
          >
            <CaretDown class="size-[18px] transition-all duration-200" />
          </span>
        </Accordion.Trigger>
      </Accordion.Header>
      <Accordion.Content
        class="overflow-hidden text-sm tracking-[-0.01em] data-[state=closed]:animate-accordion-up data-[state=open]:animate-accordion-down"
      >
        <div class="pb-[25px]">
          {item.content}
        </div>
      </Accordion.Content>
    </Accordion.Item>
  {/each}
</Accordion.Root>
	
Structure
	<script lang="ts">
	import { Accordion } from "bits-ui";
</script>
 
<Accordion.Root>
	<Accordion.Item>
		<Accordion.Header>
			<Accordion.Trigger />
		</Accordion.Header>
		<Accordion.Content />
	</Accordion.Item>
</Accordion.Root>
	
Usage
Single
Set the type prop to "single" to allow only one accordion item to be open at a time.
	<Accordion.Root type="single">
	<!-- ... -->
</Accordion.Root>
	
Multiple
Set the type prop to "multiple" to allow multiple accordion items to be open at the same time.
	<Accordion.Root type="multiple">
	<!-- ... -->
</Accordion.Root>
	
Disable Items
To disable an individual accordion item, set the disabled prop to true. This will prevent users from interacting with the item.
	<Accordion.Root type="single">
	<Accordion.Item value="item-1" disabled>
		<!-- ... -->
	</Accordion.Item>
</Accordion.Root>
	
Controlled Value
You can programmatically control the active of the accordion item(s) using the value prop.
	<script lang="ts">
	let value = $state("item-1");
</script>
 
<button onclick={() => (value = "item-2")}>Change value</button>
 
<Accordion.Root bind:value>
	<!-- ... -->
</Accordion.Root>
	
Value Change Side Effects
You can use the onValueChange prop to handle side effects when the value of the accordion changes.
	<Accordion.Root
	onValueChange={(value) => {
		doSomething(value);
	}}
>
	<!-- ... -->
</Accordion.Root>
	
Alternatively, you can use bind:value with an $effect block to handle side effects when the value of the accordion changes.
	<script lang="ts">
	import { Accordion } from "bits-ui";
 
	let value = $state("item-1")
 
	$effect(() => {
		doSomething(value);
	})
</script>
 
<Accordion.Root bind:value>
	<!-- ... -->
</Accordion.Item>
	
Reusable Wrappers
Entire Component
If you're going to be using the same accordion component multiple places throughout your app, you can create a reusable wrapper to reduce the amount of code you need to write each time.
	<script lang="ts">
	import { Accordion, type WithoutChildren } from "bits-ui";
 
	type Props = WithoutChildren<Accordion.RootProps> & {
		items: Array<{
			value: string;
			disabled?: boolean;
			title: string;
			content: string;
		}>;
	};
 
	let { items, value = $bindable(""), ...restProps }: Props = $props();
</script>
 
<Accordion.Root bind:value {...restProps}>
	{#each items as item}
		<Accordion.Item value={item.value} disabled={item.disabled}>
			<Accordion.Header>
				<Accordion.Trigger>{item.title}</Accordion.Trigger>
			</Accordion.Header>
			<Accordion.Content>{item.content}</Accordion.Content>
		</Accordion.Item>
	{/each}
</Accordion.Root>
	
Individual Item
For each invidual item, you need an Accordion.Item, Accordion.Header, Accordion.Trigger and Accordion.Content component. You can make a reusable wrapper to reduce the amount of code you need to write each time.
	<script lang="ts">
	import { Accordion, type WithoutChildren } from "bits-ui";
 
	type Props = WithoutChildren<Accordion.ItemProps> & {
		title: string;
		content: string;
	};
 
	let { title, content, ...restProps }: Props = $props();
</script>
 
<Accordion.Item {...restProps}>
	<Accordion.Header>
		<Accordion.Trigger>
			{title}
		</Accordion.Trigger>
	</Accordion.Header>
	<Accordion.Content>
		{content}
	</Accordion.Content>
</Accordion.Item>
	
	<script lang="ts">
	import { Accordion } from "bits-ui";
	import CustomAccordionItem from "$lib/components/CustomAccordionItem.svelte";
</script>
 
<Accordion.Root type="single">
	<CustomAccordionItem title="Item 1" content="Content 1" />
	<CustomAccordionItem title="Item 2" content="Content 2" />
	<CustomAccordionItem title="Item 3" content="Content 3" />
</Accordion.Root>
	
API Reference
The root accordion component used to set and manage the state of the accordion.
| Property | Type | Description | 
|---|---|---|
| multiple | boolean | Whether or not multiple accordion items can be active at the same time. Default:  false | 
| disabled | boolean | Whether or not the accordion is disabled. Default:  false | 
| value | union | The active accordion item value. Default:  undefined | 
| onValueChange | function | A callback function called when the active accordion item value changes. Default:  undefined | 
| asChild | boolean | Whether to use render delegation with this component or not. Default:  false | 
| el | HTMLDivElement | The underlying DOM element being rendered. You can bind to this to programatically interact with the element. Default:  undefined | 
| Slot Property | Type | Description | 
|---|---|---|
| builder | object | The builder attributes and actions to apply to the element if using the  | 
| Data Attribute | Value | Description | 
|---|---|---|
| data-orientation | enum | The orientation of the accordion. | 
| data-accordion-root |  | Present on the root element. | 
An accordion item.
| Property | Type | Description | 
|---|---|---|
| value*Required | string | The value of the accordion item. Default:  undefined | 
| disabled | boolean | Whether or not the accordion item is disabled. Default:  false | 
| asChild | boolean | Whether to use render delegation with this component or not. Default:  false | 
| el | HTMLDivElement | The underlying DOM element being rendered. You can bind to this to programatically interact with the element. Default:  undefined | 
| Slot Property | Type | Description | 
|---|---|---|
| builder | object | The builder attributes and actions to apply to the element if using the  | 
| Data Attribute | Value | Description | 
|---|---|---|
| data-state | enum | The state of the accordion item. | 
| data-disabled |  | Present when the accordion item is disabled. | 
| data-accordion-item | —— | Present on the item element. | 
The accordion item header, which wraps the trigger and makes it more accessible.
| Property | Type | Description | 
|---|---|---|
| level | enum | The heading level to use for the header. This will be set as the  Default:  undefined | 
| asChild | boolean | Whether to use render delegation with this component or not. Default:  false | 
| el | HTMLDivElement | The underlying DOM element being rendered. You can bind to this to programatically interact with the element. Default:  undefined | 
| Slot Property | Type | Description | 
|---|---|---|
| builder | object | The builder attributes and actions to apply to the element if using the  | 
| Data Attribute | Value | Description | 
|---|---|---|
| data-heading-level | enum | The heading level of the header. | 
| data-accordion-header | —— | Present on the header element. | 
The accordion item trigger, which opens and closes the accordion item.
| Property | Type | Description | 
|---|---|---|
| asChild | boolean | Whether to use render delegation with this component or not. Default:  false | 
| el | HTMLButtonElement | The underlying DOM element being rendered. You can bind to this to programatically interact with the element. Default:  undefined | 
| Slot Property | Type | Description | 
|---|---|---|
| builder | object | The builder attributes and actions to apply to the element if using the  | 
| Data Attribute | Value | Description | 
|---|---|---|
| data-state | enum | The state of the accordion item. | 
| data-disabled | —— | Present when the accordion item is disabled. | 
| data-value | —— | The value of the accordion item. | 
| data-accordion-trigger | —— | Present on the trigger element. | 
The accordion item content, which is displayed when the item is open.
| Property | Type | Description | 
|---|---|---|
| transition | function | A Svelte transition function to use when transitioning the content in and out. Default:  undefined | 
| transitionConfig | TransitionConfig | The configuration to apply to the transition. Default:  undefined | 
| inTransition | function | A Svelte transition function to use when transitioning the content in and out. Default:  undefined | 
| inTransitionConfig | TransitionConfig | The configuration to apply to the transition. Default:  undefined | 
| outTransition | function | A Svelte transition function to use when transitioning the content in and out. Default:  undefined | 
| outTransitionConfig | TransitionConfig | The configuration to apply to the transition. Default:  undefined | 
| asChild | boolean | Whether to use render delegation with this component or not. Default:  false | 
| el | HTMLDivElement | The underlying DOM element being rendered. You can bind to this to programatically interact with the element. Default:  undefined | 
| Slot Property | Type | Description | 
|---|---|---|
| builder | object | The builder attributes and actions to apply to the element if using the  | 
| Data Attribute | Value | Description | 
|---|---|---|
| data-state | enum | The state of the accordion item. | 
| data-disabled | —— | Present when the accordion item is disabled. | 
| data-value | —— | The value of the accordion item. | 
| data-accordion-content | —— | Present on the content element. |