sdxc

Type to search, or start from one of these:

Carousel

A horizontally scrolling collection of slides riding native CSS scroll snap.

Shared inbox screenshot
Shared inboxEvery reply in one thread
Macros screenshot
MacrosAnswer the top twenty in a keystroke
SLA timers screenshot
SLA timersSee what is about to breach
Reports screenshot
ReportsVolume, first response, backlog
Handoff screenshot
HandoffMove a case without losing context
View code
<Carousel
	aria-label="Product tour"
	mix={[is("100%"), maxIs("32rem")]}
	style={{ "--ui-carousel-slide-size": "100%", "--ui-carousel-gap": "0px" }}
>
	<Carousel.Viewport id="preview-tour" mix={[carouselControls()]}>
		<Carousel.Track>
			{SLIDES.map((slide) => (
				<Carousel.Slide key={slide.id} data-carousel-slide aria-label={slide.title}>
					<figure mix={[vstack({ gap: 2, align: "stretch" }), m(0)]}>
						<img
							src={poster(slide.hue)}
							alt={`${slide.title} screenshot`}
							mix={[is("100%"), bs("9rem"), fit("cover"), rounded("lg")]}
						/>
						<figcaption mix={[vstack({ gap: 0, align: "start" })]}>
							<span mix={[text("sm"), weight("medium")]}>{slide.title}</span>
							<span mix={[text("xs"), fg("neutral")]}>{slide.caption}</span>
						</figcaption>
					</figure>
				</Carousel.Slide>
			))}
		</Carousel.Track>
	</Carousel.Viewport>

	<Carousel.Controls mix={[justify("between")]}>
		<Carousel.Previous commandfor="preview-tour" aria-label="Previous slide" />

		<div mix={[hstack({ gap: 2, align: "center" })]}>
			{SLIDES.map((slide, index) => (
				<button
					key={slide.id}
					type="button"
					commandfor="preview-tour"
					command="--ui-goto"
					data-slide={String(index)}
					aria-label={`Go to ${slide.title}`}
					mix={[
						is("0.5rem"),
						bs("0.5rem"),
						m(0),
						rounded("full"),
						border({ width: 0 }),
						cursor("pointer"),
						// carouselControls() marks the dot naming the slide in view.
						when("&:not([aria-current])", bg("neutral.border-hover")),
						when("&[aria-current]", bg("neutral.solid")),
					]}
				/>
			))}
		</div>

		<Carousel.Next commandfor="preview-tour" aria-label="Next slide" />
	</Carousel.Controls>
</Carousel>

Installation

An ordinary dependency: install it, import the theme once, and import the component where it is used.

npm add @sdxc/ui
import "@sdxc/ui/theme.css";

Usage

import { Carousel } from "@sdxc/ui";

The carousel root: a <section> stacking Carousel.Viewport and Carousel.Controls in a column, declaring the --ui-carousel-* custom properties its descendants read with per-instance defaults.

Composition

The parts the component publishes, each a static property of the host.

  • Carousel
  • Carousel.ViewportA <div> scrolling Carousel.Track along the inline axis via logical properties for correct writing direction, with mandatory scroll-snap stops; scroll padding reads --ui-carousel-padding to clear the track's own padding.
  • Carousel.TrackThe carousel's slide row: a <div> laying its Carousel.Slide children out in one inline row, gapped by --ui-carousel-gap and padded by --ui-carousel-padding so the first and last slide can still center.
  • Carousel.SlideA single slide: a <div> held at --ui-carousel-slide-size along the inline axis, snapping to its inline-start edge so the viewport settles on a slide boundary.
  • Carousel.ControlsThe carousel's control row: a <div> laying Carousel.Previous and Carousel.Next out as an end-aligned, vertically centered row.
  • Carousel.PreviousA static control scrolling Carousel.Viewport named by commandfor back one slide when a hydrated carouselControls() mixin handles "--ui-prev"; custom children replacing the chevron still need their own aria-label.
  • Carousel.NextA static control scrolling Carousel.Viewport named by commandfor forward one slide when a hydrated carouselControls() mixin handles "--ui-next"; custom children replacing the chevron still need their own aria-label.

Props

Read from the component's own types, so every prop, every default and every allowed value is listed.

Also accepts everything in TagProps<"section">.

Also accepts everything in TagProps<"div">.

Also accepts everything in TagProps<"div">.

Also accepts everything in TagProps<"div">.

Also accepts everything in TagProps<"div">.

PropTypeDescription
commandforstringid of the Carousel.Viewport this control scrolls back through.
command?"--ui-prev"Invoker Commands verb a carouselControls() mixin listens for. Defaults to "--ui-prev".

Also accepts everything in Omit<Button.Props, "commandfor" | "command">.

PropTypeDescription
commandforstringid of the Carousel.Viewport this control scrolls forward through.
command?"--ui-next"Invoker Commands verb a carouselControls() mixin listens for. Defaults to "--ui-next".

Also accepts everything in Omit<Button.Props, "commandfor" | "command">.