# Carousel

> Swipeable cards for feature tours, stories and galleries, with five transitions, momentum dragging and an autoplay timer.

Swipeable cards with spring physics. Drag or flick the cards and they glide into place, scroll sideways with a trackpad, use the arrow keys, Home and End, or click a neighbouring card. Pick one of five transitions (tilt, slide, scale, fade, cube) and dots, timer bars or a counter underneath. Cards can show an icon, a title, a description or a full photo; pass a slot for anything else.

<demo-carousel>



</demo-carousel>

## Installation

```bash
npx shadcn-vue@latest add "https://nxui.geoql.in/r/carousel.json"
```

## Usage

```vue
<script setup lang="ts">
  import Carousel from '~/components/ui/carousel/Carousel.vue';
  import type { CarouselItem } from '~/components/ui/carousel/types';

  const photos: CarouselItem[] = [
    {
      id: 1,
      image: '/fields.jpg',
      title: 'Open fields',
      description: 'Golden light over the wheat at dusk.',
    },
    {
      id: 2,
      image: '/night.jpg',
      title: 'Night sky',
      description: 'Stars over the ridge.',
    },
  ];

  function onChange(index: number) {
    console.log('now showing', index);
  }
</script>

<template>
  <!-- Feature tour with the default cards -->
  <Carousel />

  <!-- Photo highlights -->
  <Carousel
    :items="photos"
    :base-width="640"
    :aspect-ratio="1.6"
    :peek="64"
    :radius="20"
    :frame="false"
    effect="scale"
    indicator="bars"
    arrows
    autoplay
    :autoplay-delay="4000"
    pause-on-hover
    loop
    @change="onChange"
  />

  <!-- Your own card content -->
  <Carousel :items="photos" effect="cube" :frame="false">
    <template #item="{ item, active }">
      <div class="grid size-full place-items-center">
        {{ typeof item === 'string' ? item : item.title }}
        {{ active ? '(active)' : '' }}
      </div>
    </template>
  </Carousel>
</template>
```

## Props

<table>
<thead>
  <tr>
    <th>
      Prop
    </th>
    
    <th>
      Type
    </th>
    
    <th>
      Default
    </th>
    
    <th>
      Description
    </th>
  </tr>
</thead>

<tbody>
  <tr>
    <td>
      <code>
        items
      </code>
    </td>
    
    <td>
      <code>
        Array<CarouselItem | string>
      </code>
    </td>
    
    <td>
      5 feature cards
    </td>
    
    <td>
      Objects with <code>
        image
      </code>
      
      , <code>
        icon
      </code>
      
       (Iconify name), <code>
        title
      </code>
      
      , <code>
        description
      </code>
      
       and <code>
        alt
      </code>
      
       get the built-in card; strings are used as image URLs.
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        base-width
      </code>
    </td>
    
    <td>
      <code>
        number | string
      </code>
    </td>
    
    <td>
      <code>
        300
      </code>
    </td>
    
    <td>
      Width in px, or any CSS width. It never grows past its container.
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        aspect-ratio
      </code>
    </td>
    
    <td>
      <code>
        number
      </code>
    </td>
    
    <td>
      <code>
        1.25
      </code>
    </td>
    
    <td>
      Width of a card divided by its height.
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        peek
      </code>
    </td>
    
    <td>
      <code>
        number
      </code>
    </td>
    
    <td>
      <code>
        0
      </code>
    </td>
    
    <td>
      Space on each side of the active card where the neighbours show, in px. Works with slide and scale.
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        gap
      </code>
    </td>
    
    <td>
      <code>
        number
      </code>
    </td>
    
    <td>
      <code>
        16
      </code>
    </td>
    
    <td>
      Space between the cards in px.
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        radius
      </code>
    </td>
    
    <td>
      <code>
        number
      </code>
    </td>
    
    <td>
      <code>
        12
      </code>
    </td>
    
    <td>
      Corner radius of the cards in px.
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        frame
      </code>
    </td>
    
    <td>
      <code>
        boolean
      </code>
    </td>
    
    <td>
      <code>
        true
      </code>
    </td>
    
    <td>
      Holds the cards and controls in a glass panel. Without it the cards fade out at the edges.
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        effect
      </code>
    </td>
    
    <td>
      <code>
        'tilt' | 'slide' | 'scale' | 'fade' | 'cube'
      </code>
    </td>
    
    <td>
      <code>
        'tilt'
      </code>
    </td>
    
    <td>
      How the cards move from one to the next.
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        indicator
      </code>
    </td>
    
    <td>
      <code>
        'dots' | 'bars' | 'counter' | 'none'
      </code>
    </td>
    
    <td>
      <code>
        'dots'
      </code>
    </td>
    
    <td>
      Navigation under the cards. Bars fill up with the autoplay timer.
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        arrows
      </code>
    </td>
    
    <td>
      <code>
        boolean
      </code>
    </td>
    
    <td>
      <code>
        false
      </code>
    </td>
    
    <td>
      Shows previous and next buttons.
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        autoplay
      </code>
    </td>
    
    <td>
      <code>
        boolean
      </code>
    </td>
    
    <td>
      <code>
        false
      </code>
    </td>
    
    <td>
      Moves to the next card on a timer.
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        autoplay-delay
      </code>
    </td>
    
    <td>
      <code>
        number
      </code>
    </td>
    
    <td>
      <code>
        3000
      </code>
    </td>
    
    <td>
      Time on each card in ms while autoplay is on (minimum 600).
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        pause-on-hover
      </code>
    </td>
    
    <td>
      <code>
        boolean
      </code>
    </td>
    
    <td>
      <code>
        false
      </code>
    </td>
    
    <td>
      Pauses autoplay while the pointer is over the carousel.
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        loop
      </code>
    </td>
    
    <td>
      <code>
        boolean
      </code>
    </td>
    
    <td>
      <code>
        false
      </code>
    </td>
    
    <td>
      Wraps around from the last card to the first and back.
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        draggable
      </code>
    </td>
    
    <td>
      <code>
        boolean
      </code>
    </td>
    
    <td>
      <code>
        true
      </code>
    </td>
    
    <td>
      Lets people drag, swipe or scroll sideways through the cards.
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        round
      </code>
    </td>
    
    <td>
      <code>
        boolean
      </code>
    </td>
    
    <td>
      <code>
        false
      </code>
    </td>
    
    <td>
      Turns the cards into circles.
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        initial-index
      </code>
    </td>
    
    <td>
      <code>
        number
      </code>
    </td>
    
    <td>
      <code>
        0
      </code>
    </td>
    
    <td>
      Card shown first.
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        theme
      </code>
    </td>
    
    <td>
      <code>
        'dark' | 'light'
      </code>
    </td>
    
    <td>
      <code>
        'dark'
      </code>
    </td>
    
    <td>
      Color scheme of the cards, frame and controls.
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        class
      </code>
    </td>
    
    <td>
      <code>
        string
      </code>
    </td>
    
    <td>
      <code>
        ''
      </code>
    </td>
    
    <td>
      Extra classes on the root.
    </td>
  </tr>
</tbody>
</table>

## Events

<table>
<thead>
  <tr>
    <th>
      Event
    </th>
    
    <th>
      Payload
    </th>
    
    <th>
      Description
    </th>
  </tr>
</thead>

<tbody>
  <tr>
    <td>
      <code>
        change
      </code>
    </td>
    
    <td>
      <code>
        index: number
      </code>
    </td>
    
    <td>
      Fired with the index of the new active card.
    </td>
  </tr>
</tbody>
</table>

## Slots

<table>
<thead>
  <tr>
    <th>
      Slot
    </th>
    
    <th>
      Props
    </th>
    
    <th>
      Description
    </th>
  </tr>
</thead>

<tbody>
  <tr>
    <td>
      <code>
        item
      </code>
    </td>
    
    <td>
      <code>
        { item: CarouselItem | string, index: number, active: boolean }
      </code>
    </td>
    
    <td>
      Replaces the built-in card content for every slide.
    </td>
  </tr>
</tbody>
</table>

## Accessibility

- The root is a focusable `region` with `aria-roledescription="carousel"`; each slide is a `group` labelled “N of M”.
- Arrow Left/Right step, Home/End jump to the first and last card. Keyboard focus pauses autoplay.
- Dots and bars are buttons with `aria-current` on the active one; arrows are disabled at the ends unless `loop` is on.
- Announcements are polite when autoplay is off and silenced while it runs. With `prefers-reduced-motion`, cards jump without the spring.
- Ported from [React Bits](https://reactbits.dev/components/carousel) by David Haz.
