Search documentation v0.5.0

Carousel

Browse through a series of content items

Source ↗️ Report Issue ↗️

Use the Carousel component to display images, text, or cards, that can be navigated by sliding or clicking through them one at a time. They are particularly useful for showcasing multiple pieces of content in a compact space. Use them for image galleries, featured content, testimonial slides, promotions or ads, onboarding steps, or for portfolio display.

Preview
How to use Carousels in Astro
---
import { Carousel } from 'webcoreui/astro'
---
<Carousel items={3}>
<li><Box>1</Box></li>
<li><Box>2</Box></li>
<li><Box>3</Box></li>
</Carousel>
How to use Carousels in Svelte
<script>
import { Carousel } from 'webcoreui/svelte'
</script>
<Carousel items={3} onScroll={page => console.log(`scrolled to ${page}`)}>
<li><Box>1</Box></li>
<li><Box>2</Box></li>
<li><Box>3</Box></li>
</Carousel>
How to use Carousels in React
import React from 'react'
import { Carousel } from 'webcoreui/react'
const Component = () => (
<Carousel items={3} onScroll={page => console.log(`scrolled to ${page}`)}>
<li><Box>1</Box></li>
<li><Box>2</Box></li>
<li><Box>3</Box></li>
</Carousel>
)
export default Component

To use the Carousel component, specify the number of slides using the items prop, and create the slides as children of the component. Each child must be wrapped inside an li element. Here you can pass any element to create image, card, or other types of carousels. To properly display each slide, make sure you set their width to 100% in your CSS.

ℹ️ Set your slide's width to 100%
.slide {
width: 100%;
}

Custom Pagination

The Carousel component uses the Pagination component to render the pagination under the slides. Using the pagination prop, you can customize the pagination in any way you can customize the Pagination component. For a full list of possible props, see the API of the Pagination component.

Dots
Arrows with labels
Pages
<Carousel items={3} pagination={{ type: 'dots' }}>
<li><Box>1</Box></li>
<li><Box>2</Box></li>
<li><Box>3</Box></li>
</Carousel>
<Carousel items={3} pagination={{ type: null, showChevrons: true }}>
<li><Box>1</Box></li>
<li><Box>2</Box></li>
<li><Box>3</Box></li>
</Carousel>
<Carousel items={2} pagination={{
type: null,
pages: [
{ label: 1, active: true },
{ label: 2 }
]
}}>
<li><Box>1</Box></li>
<li><Box>2</Box></li>
</Carousel>

Pagination with Label

Pagination can also be created with labels. Use the subText prop to display a text under the slides:

<Carousel items={3} subText="Slide {0} of {1}">
<li><Box>1</Box></li>
<li><Box>2</Box></li>
<li><Box>3</Box></li>
</Carousel>

You can use the special {0} and {1} placeholders to insert the current slide, and the total number of slides into your label.

Progress Bar

If you’d like to use a carousel as a list of steps, you might want to display a progress bar for the user to visually indicate their progress. This can be achieved by setting the progress prop to true:

<Carousel items={3} subText="Step {0} of {1}" progress={true}>
<li><Box>1</Box></li>
<li><Box>2</Box></li>
<li><Box>3</Box></li>
</Carousel>

The Carousel component listens to scroll events to update its state when slides are swiped on touch devices. By default, this event is debounced to reduce the number of function calls and improve its JavaScript performance.

As a result, this may cause a slight delay in state update when the carousel is navigated using a swipe motion. This functionality can be configured or turned off using the debounce prop:

<Carousel items={3} debounce={0}>
<li><Box>1</Box></li>
<li><Box>2</Box></li>
<li><Box>3</Box></li>
</Carousel>
Changing the debounce prop will effect mobile navigation performance.

Another way to customize mobile navigation, is using the scrollSnap prop. When slides are scrolled using a swipe motion, the carousel will snap to the next slide. This scroll snap behavior can also be turned off using the scrollSnap prop:

<Carousel items={3} scrollSnap={false}>
<li><Box>1</Box></li>
<li><Box>2</Box></li>
<li><Box>3</Box></li>
</Carousel>

Transition Effects

The Carousel component also comes with two transition effect out of the box:

The effect can be configured using the effect prop:

Opacity
Saturate
<Carousel items={3} effect="opacity">
<li data-active="true">
<img src="/img/placeholder1.png" />
</li>
<li>
<img src="/img/placeholder2.png" />
</li>
<li>
<img src="/img/placeholder3.png" />
</li>
</Carousel>
<Carousel items={3} effect="saturate">
<li data-active="true">
<img src="/img/placeholder1.png" />
</li>
<li>
<img src="/img/placeholder2.png" />
</li>
<li>
<img src="/img/placeholder3.png" />
</li>
</Carousel>

The correct style is applied based on the state of the slide (active/inactive). To mark the first slide as the active element, you must set the data-active attribute to true on the li element. If no data-active attribute is present during the initial render, all slides will have the effect of the inactive state.

Opacity without data-active
Saturate without data-active

Image and Component Carousels

You can combine the Carousel component with images or other component to create image carousels, onboarding steps, promotional sliders or other types of carousels.

<Carousel
items={3}
subText="Slide {0} of {1}"
effect="saturate"
debounce={0}
pagination={{ type: 'dots' }}
>
<li data-active="true">
<img src="/img/slide1.png" />
<span>Astro</span>
</li>
<li>
<img src="/img/slide2.png" />
<span>Svelte</span>
</li>
<li>
<img src="/img/slide3.png" />
<span>React</span>
</li>
</Carousel>
li {
position: relative;
overflow: hidden;
&[data-active] span {
transform: translateY(0);
}
img {
width: 100%;
height: 150px;
object-fit: cover;
}
span {
transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
position: absolute;
bottom: 0;
left: 0;
width: 100%;
padding: 2px 10px;
transform: translateY(100%);
background: rgba(0, 0, 0, 0.75);
}
}
<Carousel
items={3}
subText="Step {0} of {1}"
progress={true}
>
<li>
<Alert theme="success" title="Note">...</Alert>
</li>
<li>
<Alert theme="info" title="Info">....</Alert>
</li>
<li>
<Alert>
<div>...</div>
<Button className="go-back">Go back</Button>
</Alert>
</li>
</Carousel>
<script>
const button = document.querySelector('.go-back')
// Implementation may differ for Svelte/React components
button?.addEventListener('click', () => {
const firstSlide = event.target
?.closest('li')
?.previousElementSibling
?.previousElementSibling
// Using `.scrollIntoView` will automatically trigger state update for the carousel
firstSlide?.scrollIntoView({ behavior: 'smooth', block: 'nearest' })
})
</script>

API

type CarouselProps = {
items: number
subText?: string
scrollSnap?: boolean
progress?: boolean
pagination?: PaginationProps
effect?: 'opacity' | 'saturate'
debounce?: number
className?: string
wrapperClassName?: string
paginationClassName?: string
}
type SvelteCarouselProps = {
onScroll?: (page: number) => void
} & CarouselProps
type ReactCarouselProps = {
onScroll?: (page: number) => void
} & CarouselProps
See the documentation of the Pagination component for the PaginationProps type.
PropPurpose
items Set the number of slides.
subText Sets a label under the slides.
scrollSnap Sets scroll snap for swipe motion. Enabled by default.
progress Displays a progress bar under the slides. Defaults to false.
pagination Customize the pagination of the carousel. It can accept the props of the Pagination component.
effect Sets a transition effect for the slides. Can be one of opacity, saturate.
debounce Sets the debounce amount for the scroll event listener.
className Pass additional CSS classes for the carousel.
wrapperClassName Pass additional CSS classes for slides container.
paginationClassName Pass additional CSS classes for the pagination of the carousel.
Svelte & React PropPurpose
onScroll Attach event listeners that are triggered when the carousel is scrolled. The page parameter will return the current page as a number.

Request improvement for this page