A lightweight carousel library with fluid motion and great swipe precision
npx @tessl/cli install tessl/npm-embla-carousel-react@8.6.0Embla Carousel React is a lightweight React hook library that provides a declarative interface for creating fluid, performant carousels. It offers a single React hook that integrates seamlessly with the core Embla Carousel engine, providing developers with a React-idiomatic way to implement carousels with great swipe precision and smooth motion.
npm install embla-carousel-reactimport useEmblaCarousel from "embla-carousel-react";For named imports:
import useEmblaCarousel, { UseEmblaCarouselType, EmblaViewportRefType } from "embla-carousel-react";For CommonJS:
const useEmblaCarousel = require("embla-carousel-react").default;import React from "react";
import useEmblaCarousel from "embla-carousel-react";
const EmblaCarousel: React.FC = () => {
const [emblaRef, emblaApi] = useEmblaCarousel({ loop: false });
return (
<div className="embla" ref={emblaRef}>
<div className="embla__container">
<div className="embla__slide">Slide 1</div>
<div className="embla__slide">Slide 2</div>
<div className="embla__slide">Slide 3</div>
</div>
</div>
);
};The main React hook that creates and manages an Embla Carousel instance. Returns a viewport ref callback and carousel API instance.
/**
* React hook for creating and managing an Embla Carousel instance
* @param options - Optional configuration options for the carousel
* @param plugins - Optional array of carousel plugins
* @returns Tuple containing viewport ref callback and carousel API instance
*/
function useEmblaCarousel(
options?: EmblaOptionsType,
plugins?: EmblaPluginType[]
): UseEmblaCarouselType;Usage Examples:
import useEmblaCarousel from "embla-carousel-react";
import { EmblaOptionsType } from "embla-carousel";
// Basic usage
const [emblaRef, emblaApi] = useEmblaCarousel();
// With options
const [emblaRef, emblaApi] = useEmblaCarousel({
loop: true,
align: "start"
});
// With plugins
import Autoplay from "embla-carousel-autoplay";
const [emblaRef, emblaApi] = useEmblaCarousel(
{ loop: true },
[Autoplay()]
);
// Access carousel methods when API is ready
React.useEffect(() => {
if (emblaApi) {
console.log(emblaApi.scrollSnapList()); // Get all slide positions
emblaApi.on('select', () => {
console.log('Selected slide:', emblaApi.selectedScrollSnap());
});
}
}, [emblaApi]);Static property for setting default options that apply to all carousel instances.
/**
* Global options applied to all carousel instances
* Set this to provide default configuration for all carousels
*/
useEmblaCarousel.globalOptions: EmblaOptionsType | undefined;Usage Example:
import useEmblaCarousel from "embla-carousel-react";
// Set global options
useEmblaCarousel.globalOptions = {
align: "start",
containScroll: "trimSnaps"
};
// All subsequent useEmblaCarousel calls will inherit these options
const [emblaRef, emblaApi] = useEmblaCarousel();The return type of the useEmblaCarousel hook.
/**
* Return type of useEmblaCarousel hook
* Tuple containing viewport ref callback and carousel API instance
*/
type UseEmblaCarouselType = [
EmblaViewportRefType,
EmblaCarouselType | undefined
];Generic function type for the viewport element ref callback.
/**
* Ref callback function type for attaching to carousel viewport element
* Generic function that accepts any HTMLElement and returns void
*/
type EmblaViewportRefType = <ViewportElement extends HTMLElement>(
instance: ViewportElement | null
) => void;Main carousel API interface with all available methods and properties (re-exported from embla-carousel).
/**
* Complete carousel API interface providing all carousel functionality
* Available after carousel initialization (initially undefined)
*/
interface EmblaCarouselType {
/** Check if carousel can scroll to next slide */
canScrollNext(): boolean;
/** Check if carousel can scroll to previous slide */
canScrollPrev(): boolean;
/** Get the carousel container DOM element */
containerNode(): HTMLElement;
/** Get internal engine instance (advanced usage) */
internalEngine(): EngineType;
/** Destroy the carousel instance and clean up event listeners */
destroy(): void;
/** Remove event listener */
off(type: EmblaEventType, handler: (emblaApi: EmblaCarouselType, evt: EmblaEventType) => void): void;
/** Add event listener */
on(type: EmblaEventType, handler: (emblaApi: EmblaCarouselType, evt: EmblaEventType) => void): void;
/** Emit custom event */
emit(type: EmblaEventType): void;
/** Get all active plugins */
plugins(): EmblaPluginsType;
/** Get the previously selected slide index */
previousScrollSnap(): number;
/** Reinitialize carousel with new options or plugins */
reInit(options?: EmblaOptionsType, plugins?: EmblaPluginType[]): void;
/** Get the carousel root DOM element */
rootNode(): HTMLElement;
/** Scroll to next slide */
scrollNext(jump?: boolean): void;
/** Scroll to previous slide */
scrollPrev(jump?: boolean): void;
/** Get current scroll progress (0-1) */
scrollProgress(): number;
/** Get array of all slide positions */
scrollSnapList(): number[];
/** Scroll to specific slide by index */
scrollTo(index: number, jump?: boolean): void;
/** Get currently selected slide index */
selectedScrollSnap(): number;
/** Get array of all slide DOM elements */
slideNodes(): HTMLElement[];
/** Get indices of slides currently in view */
slidesInView(): number[];
/** Get indices of slides not currently in view */
slidesNotInView(): number[];
}Configuration options interface (re-exported from embla-carousel).
/**
* Configuration options for carousel behavior and appearance
* All options are optional with sensible defaults
*/
interface EmblaOptionsType {
/** Slide alignment within viewport */
align?: AlignmentOptionType;
/** Scroll direction axis */
axis?: AxisOptionType;
/** Container element selector or element */
container?: string | HTMLElement | null;
/** Slides selector, elements, or NodeList */
slides?: string | HTMLElement[] | NodeListOf<HTMLElement> | null;
/** How scrolling is contained within carousel bounds */
containScroll?: ScrollContainOptionType;
/** Text/layout direction for RTL/LTR support */
direction?: AxisDirectionOptionType;
/** Number of slides to scroll at once */
slidesToScroll?: SlidesToScrollOptionType;
/** Enable free scrolling without snap points */
dragFree?: boolean;
/** Minimum drag distance in pixels to trigger scroll */
dragThreshold?: number;
/** Intersection threshold for detecting slides in view (0-1) */
inViewThreshold?: SlidesInViewOptionsType;
/** Enable infinite loop scrolling */
loop?: boolean;
/** Skip slides that would create awkward snap points */
skipSnaps?: boolean;
/** Animation duration in milliseconds */
duration?: number;
/** Index of slide to start on */
startIndex?: number;
/** Enable/disable drag interaction or provide custom handler */
watchDrag?: DragHandlerOptionType;
/** Enable/disable resize handling or provide custom handler */
watchResize?: ResizeHandlerOptionType;
/** Enable/disable slides mutation observer or provide custom handler */
watchSlides?: SlidesHandlerOptionType;
/** Enable/disable focus handling or provide custom handler */
watchFocus?: FocusHandlerOptionType;
/** Enable/disable the entire carousel */
active?: boolean;
/** Responsive breakpoint options with media query keys */
breakpoints?: {
[mediaQuery: string]: Omit<Partial<EmblaOptionsType>, 'breakpoints'>;
};
}Event types available for carousel event handling (re-exported from embla-carousel).
/**
* Available event types for carousel event handling
* Used with on() and off() methods to listen for carousel events
*/
type EmblaEventType =
| 'init' // Carousel initialized
| 'pointerDown' // Pointer/mouse pressed on carousel
| 'pointerUp' // Pointer/mouse released from carousel
| 'slidesChanged' // Number or order of slides changed
| 'slidesInView' // Slides currently in view changed
| 'scroll' // Carousel scrolled
| 'select' // Slide selection changed
| 'settle' // Carousel settled after scroll
| 'destroy' // Carousel destroyed
| 'reInit' // Carousel reinitialized
| 'resize' // Carousel resized
| 'slideFocusStart' // Slide focus started
| 'slideFocus'; // Slide focusedPlugin interface for extending carousel functionality (re-exported from embla-carousel).
/**
* Interface for carousel plugins that extend functionality
* Plugins are initialized when carousel is created
*/
interface EmblaPluginType {
/** Unique plugin name */
name: string;
/** Plugin configuration options */
options: Partial<EmblaOptionsType>;
/** Initialize plugin with carousel instance */
init(embla: EmblaCarouselType, OptionsHandler: OptionsHandlerType): void;
/** Clean up plugin resources */
destroy(): void;
}Specific types for EmblaOptionsType properties (re-exported from embla-carousel).
/**
* Slide alignment options - determines how slides align within viewport
*/
type AlignmentOptionType =
| 'start' // Align slides to start of viewport
| 'center' // Center slides in viewport
| 'end' // Align slides to end of viewport
| ((viewSize: number, snapSize: number, index: number) => number); // Custom alignment function
/**
* Scroll axis options - defines scroll direction
*/
type AxisOptionType = 'x' | 'y';
/**
* Text direction options for RTL/LTR layouts
*/
type AxisDirectionOptionType = 'ltr' | 'rtl';
/**
* Scroll containment options - how scrolling is contained within bounds
*/
type ScrollContainOptionType =
| false // No scroll containment
| 'trimSnaps' // Remove awkward snap points at container edges
| 'keepSnaps'; // Keep all snap points
/**
* Number of slides to scroll at once
*/
type SlidesToScrollOptionType = 'auto' | number;
/**
* Intersection threshold for slides in view detection
*/
type SlidesInViewOptionsType = number | number[];
/**
* Drag handler configuration - boolean or custom handler function
*/
type DragHandlerOptionType =
| boolean
| ((emblaApi: EmblaCarouselType, evt: PointerEvent) => boolean | void);
/**
* Resize handler configuration - boolean or custom handler function
*/
type ResizeHandlerOptionType =
| boolean
| ((emblaApi: EmblaCarouselType, entries: ResizeObserverEntry[]) => boolean | void);
/**
* Slides handler configuration - boolean or custom handler function
*/
type SlidesHandlerOptionType =
| boolean
| ((emblaApi: EmblaCarouselType, mutations: MutationRecord[]) => boolean | void);
/**
* Focus handler configuration - boolean or custom handler function
*/
type FocusHandlerOptionType =
| boolean
| ((emblaApi: EmblaCarouselType, evt: FocusEvent) => boolean | void);