Svelte
Embla Carousel provides a wrapper for Svelte that ensures seamless integration of the carousel into your Svelte project and automatic cleanup on component unmount.
Start by installing the Embla Carousel npm package and add it to your dependencies.
npm install embla-carousel-svelte --savepnpm add embla-carousel-svelteyarn add embla-carousel-svelteThe component structure
A recommended setup uses an overflow wrapper and a scroll container, though the outer wrapper is optional. The element with the class name embla__viewport serves as both the root and the overflow wrapper. To avoid drag conflicts, place navigation buttons outside the viewport. Start by adding the following structure to your carousel:
<script> import useEmblaCarousel from 'embla-carousel-svelte'</script>
<div class="embla"> <div class="embla__viewport" use:useEmblaCarousel> <div class="embla__container"> <div class="embla__slide">Slide 1</div> <div class="embla__slide">Slide 2</div> <div class="embla__slide">Slide 3</div> </div> </div>
<button class="embla__prev">Scroll to prev</button> <button class="embla__next">Scroll to next</button></div>Styling the carousel
The element with the classname embla__viewport acts as an overflow wrapper, ensuring that any scroll overflow is hidden. The element with the classname embla__container is the scrollable area that holds and moves the slides. Add the following CSS to style these elements:
<style> .embla__viewport { overflow: hidden; }
.embla__container { display: flex; touch-action: pan-y pinch-zoom; }
.embla__slide { flex: 0 0 100%; min-width: 0; }</style>Accessing the carousel API
Use the useEmblaCarousel Svelte action and pass your options as the first argument. You can access the API by capturing the Embla API from the carousel's on:emblainit event, and use it to control the carousel or respond to user actions, as shown below:
<script> import useEmblaCarousel from 'embla-carousel-svelte'
let emblaApi let options = { loop: false }
const goToPrev = () => emblaApi?.goToPrev() const goToNext = () => emblaApi?.goToNext()
const onInit = (event) => { emblaApi = event.detail }</script>
<div class="embla"> <div class="embla__viewport" on:emblainit={onInit} use:useEmblaCarousel={{ options }} > <div class="embla__container"> <div class="embla__slide">Slide 1</div> <div class="embla__slide">Slide 2</div> <div class="embla__slide">Slide 3</div> </div> </div>
<button class="embla__prev" on:click={goToPrev}>Scroll to prev</button> <button class="embla__next" on:click={goToNext}>Scroll to next</button></div>Note: Starting with Svelte 5, the on: event handlers have been
deprecated. However, on:emblainit will remain for backward compatibility.
Adding plugins
Plugins let you extend your carousel with additional features beyond the built-in core functionality. To get started, install the plugin you want to use. In this example, we'll add the Autoplay plugin:
npm install embla-carousel-autoplay --savepnpm add embla-carousel-autoplayyarn add embla-carousel-autoplayYou can pass an optional plugin array as the second argument to the useEmblaCarousel Svelte action. Here's how to extend the carousel from the previous example with Autoplay:
<script> import useEmblaCarousel from 'embla-carousel-svelte' import Autoplay from 'embla-carousel-autoplay'
let options = { loop: false } let plugins = [Autoplay()]
const goToPrev = () => emblaApi?.goToPrev() const goToNext = () => emblaApi?.goToNext()
const onInit = (event) => { emblaApi = event.detail emblaApi.plugins().autoplay?.play() }</script>
<div class="embla"> <div class="embla__viewport" on:emblainit={onInit} use:useEmblaCarousel={{ options, plugins }} > <div class="embla__container"> <div class="embla__slide">Slide 1</div> <div class="embla__slide">Slide 2</div> <div class="embla__slide">Slide 3</div> </div> </div>
<button class="embla__prev" on:click={goToPrev}>Scroll to prev</button> <button class="embla__next" on:click={goToNext}>Scroll to next</button></div>Congratulations! You just created your first Embla Carousel component.