YoucefBnm Bnm

Story

Component 255

About

- story similar to IG and facebook, you can also use it as a autoplay carousel

Built with React and Tailwind. Copy the prompt and paste it into Claude Code, Cursor or Lovable: your agent adds Story to your project and fits it to your theme.

Code

How Story is used: the demo's code. The component's own source comes with a free account.

Usage.tsx

import { Avatar, AvatarFallback, AvatarImage } from '@/components/ui/avatar';

import { Story,
  StoryProgress,
  StoryControls,
  StorySlide,
  StoryOverlay, } from "@/components/ui/story";
import {
  Dialog,
  DialogContent,
  DialogHeader,
  DialogTitle,
  DialogTrigger,
} from '@/components/ui/dialog';
const FABRIZIO_STORIES = [
  {
    title: 'Champions league will begin soon',
    caption: 'whos you are running for ?',
    storyImage:
      'https://cdn.21st.dev/assets/mirror/a4/a43a1cdf92a7ded73a0071554501e3ff6e2c751e0437b9e42e623fe854f8d876.jpg',
  },
  {
    title: "who's your favourite player ?",
    caption: 'who you think will win the champions league ?',
    storyImage:
      'https://cdn.21st.dev/assets/mirror/e4/e4d02ca4e9b399dab06f39a4486f99c3ce544d443c43d0de7a8d5f0f1c4f21bf.jpg',
  },
];

const SHADCN_STORIES = [
  {
    title: 'Easy vibes',
    caption: 'In the System Prompts.',
    storyImage:
      'https://cdn.21st.dev/assets/mirror/09/09b10c0826185ea7133592eb84b99a13d4f421dca9089fd4c44492adfbe33174.jpg',
  },
  {
    title: 'The new calendar.tsx is here',
    caption: `
    → Latest react-daypicker
    → Tailwind v3 and v4
    → Date, range & time pickers
    → Persian, Hijri & timezone support
    → 30+ examples to copy, paste, and build.
    `,
    storyImage:
      'https://cdn.21st.dev/assets/mirror/20/2039c036ef48902a03be8610c023a135e9c9ce1442866d4eb14c4b5368626851.jpg',
  },
  {
    title: '🤣🤣🤣🤣🤣',
    caption: 'Me walking away after adding min-w-0 and it works.',
    storyImage:
      'https://cdn.21st.dev/assets/mirror/2b/2ba83238a941377289d8540dd3ecb92b72adf1eb0fddcc1aec21302207cb653b.jpg',
  },
];

const NBA_STORIES = [
  {
    title: 'Shai follows 38 in Game 1 with 34 tonight 🔥🔥🔥',
    caption:
      'MOST POINTS EVER by a player in his first 2 career Finals games 🚨🚨',
    storyImage:
      'https://cdn.21st.dev/assets/mirror/f1/f15899f6f96a11f576f4384b8ea8d5f07237bffcc507e8eb9508aa723b56ae88.jpg',
  },
];

const StoryDemo = () => {
  return  <section className="min-h-dvh p-12 w-full place-content-center">
      <div className="flex gap-4 justify-center">
        <Dialog>
          <DialogTrigger>
            <Avatar className="size-12">
              <AvatarImage
                src="https://scontent.forn3-5.fna.fbcdn.net/v/t39.30808-1/347110386_993663875383747_583934797072922306_n.jpg?stp=c0.124.1179.1179a_cp0_dst-jpg_s80x80_tt6&_nc_cat=1&ccb=1-7&_nc_sid=2d3e12&_nc_ohc=sznTMSftQGgQ7kNvwFnYrhK&_nc_oc=Adl88GWERQJFnS-FhRo3kmyRvwQeqel4uE97CRcHAX2hgEouXRhN98vLowFYZewYbKE&_nc_zt=24&_nc_ht=scontent.forn3-5.fna&_nc_gid=zgCgewXONoFNXl_Ycl7B9Q&oh=00_AfP29XsY8aMHX1lZasw43qaYzda8eY9esKHCjO-ZARUk5A&oe=684D1280"
                alt="@fabrizioRomano"
              />
              <AvatarFallback>FR</AvatarFallback>
            </Avatar>
          </DialogTrigger>
          <DialogContent className="aspect-[12/16] w-auto h-[90vh] overflow-hidden p-0">
            <DialogTitle className="sr-only">Story</DialogTitle>

            <Story
              className="relative size-full "
              duration={5000}
              mediaLength={FABRIZIO_STORIES.length}
            >
              <DialogHeader className="px-4 py-6">
                <div className="relative z-10 flex items-center gap-2">
                  <Avatar className="size-10">
                    <AvatarImage
                      src="https://scontent.forn3-5.fna.fbcdn.net/v/t39.30808-1/347110386_993663875383747_583934797072922306_n.jpg?stp=c0.124.1179.1179a_cp0_dst-jpg_s80x80_tt6&_nc_cat=1&ccb=1-7&_nc_sid=2d3e12&_nc_ohc=sznTMSftQGgQ7kNvwFnYrhK&_nc_oc=Adl88GWERQJFnS-FhRo3kmyRvwQeqel4uE97CRcHAX2hgEouXRhN98vLowFYZewYbKE&_nc_zt=24&_nc_ht=scontent.forn3-5.fna&_nc_gid=zgCgewXONoFNXl_Ycl7B9Q&oh=00_AfP29XsY8aMHX1lZasw43qaYzda8eY9esKHCjO-ZARUk5A&oe=684D1280"
                      alt="@fabrizioRomano"
                    />
                    <AvatarFallback>FR</AvatarFallback>
                  </Avatar>

                  <StoryProgress
                    className="flex-1"
                    progressWrapClass="h-1.5"
                    progressActiveClass="bg-blue-500"
                  />
                  <StoryControls
                    variant="ghost"
                    className="text-white rounded-full"
                  />
                </div>
              </DialogHeader>
              {FABRIZIO_STORIES.map((story, idx) => (
                <StorySlide
                  key={idx}
                  index={idx}
                  className="absolute inset-0 size-full"
                >
                  {/* Example with image */}
                  <img
                    src={story.storyImage}
                    className="w-full h-auto max-h-auto"
                    alt={story.title}
                  />

                  <div className="absolute bottom-4 left-4  z-10 space-y-1 text-white p-4">
                    <a
                      className="text-secondary"
                      href="https://x.com/FabrizioRomano"
                    >
                      @FabrizioRomano
                    </a>
                    <h3 className="text-medium tracking-tight text-foreground-muted">
                      {story.title}
                    </h3>
                    <p className="text-sm text-slate-200">{story.caption}</p>
                  </div>
                </StorySlide>
              ))}
              <StoryOverlay />
            </Story>
          </DialogContent>
        </Dialog>

        <Dialog>
          <DialogTrigger>
            <Avatar className="size-12">
              <AvatarImage
                src="https://cdn.21st.dev/assets/mirror/e9/e941f86e0ca2b1c9eefd47618a92040443f85598470bad47399cee7f259c0756.jpg"
                alt="@shadcn"
              />
              <AvatarFallback>SC</AvatarFallback>
            </Avatar>
          </DialogTrigger>
          <DialogContent className="aspect-[12/16] w-auto h-[90vh] overflow-hidden p-0 rounded-md">
            <DialogTitle className="sr-only">Story</DialogTitle>

            <Story
              className="relative size-full "
              duration={5000}
              mediaLength={SHADCN_STORIES.length}
            >
              <DialogHeader className="px-4 py-6">
                <div className="relative z-10 flex items-center gap-2">
                  <Avatar className="size-10">
                    <AvatarImage
                      src="https://cdn.21st.dev/assets/mirror/e9/e941f86e0ca2b1c9eefd47618a92040443f85598470bad47399cee7f259c0756.jpg"
                      alt="@shadcn"
                    />
                    <AvatarFallback>SC</AvatarFallback>
                  </Avatar>

                  <StoryProgress
                    className="flex-1"
                    progressWrapClass="h-1.5"
                    progressActiveClass="bg-pink-500"
                  />
                  <StoryControls
                    variant="ghost"
                    className="text-white rounded-full"
                  />
                </div>
              </DialogHeader>
              {SHADCN_STORIES.map((story, idx) => (
                <StorySlide
                  key={idx}
                  index={idx}
                  className="absolute inset-0 size-full"
                >
                  <img
                    src={story.storyImage}
                    className="w-full h-auto max-h-auto"
                    alt={story.title}
                  />

                  <div className="absolute bottom-4 left-4  z-10 space-y-1 text-white p-4">
                    <a
                      className="text-secondary"
                      href="https://x.com/FabrizioRomano"
                    >
                      @Shadcn
                    </a>
                    <h3 className="text-medium tracking-tight text-foreground-muted">
                      {story.title}
                    </h3>
                    <p className="text-sm text-slate-200">{story.caption}</p>
                  </div>
                </StorySlide>
              ))}
              <StoryOverlay />
            </Story>
          </DialogContent>
        </Dialog>

        <Dialog>
          <DialogTrigger>
            <Avatar className="size-12">
              <AvatarImage
                src="https://cdn.21st.dev/assets/mirror/14/142642fb731b152d2c4903291404c61859cc41ac9595180975ad57b193dce007.jpg"
                alt="@nba"
              />
              <AvatarFallback>SC</AvatarFallback>
            </Avatar>
          </DialogTrigger>
          <DialogContent className="aspect-[12/16] w-auto h-[90vh] overflow-hidden p-0 rounded-md">
            <DialogTitle className="sr-only">Story</DialogTitle>

            <Story
              className="relative size-full "
              duration={8000}
              mediaLength={NBA_STORIES.length}
            >
              <DialogHeader className="px-4 py-6">
                <div className="relative z-10 flex items-center gap-2">
                  <Avatar className="size-10">
                    <AvatarImage
                      src="https://cdn.21st.dev/assets/mirror/14/142642fb731b152d2c4903291404c61859cc41ac9595180975ad57b193dce007.jpg"
                      alt="@nba"
                    />
                    <AvatarFallback>SC</AvatarFallback>
                  </Avatar>

                  <StoryProgress
                    className="flex-1"
                    progressWrapClass="h-1.5"
                    progressActiveClass="bg-red-500"
                  />
                  <StoryControls
                    variant="ghost"
                    className="text-white rounded-full"
                  />
                </div>
              </DialogHeader>
              {NBA_STORIES.map((story, idx) => (
                <StorySlide
                  key={idx}
                  index={idx}
                  className="absolute inset-0 size-full"
                >
                  <img
                    src={story.storyImage}
                    className="w-full h-auto max-h-auto"
                    alt={story.title}
                  />

                  <div className="absolute bottom-4 left-4  z-10 space-y-1 text-white p-4">
                    <a
                      className="text-secondary"
                      href="https://x.com/FabrizioRomano"
                    >
                      @nba
                    </a>
                    <h3 className="text-medium tracking-tight text-foreground-muted">
                      {story.title}
                    </h3>
                    <p className="text-sm text-slate-200">{story.caption}</p>
                  </div>
                </StorySlide>
              ))}
              <StoryOverlay />
            </Story>
          </DialogContent>
        </Dialog>
      </div>
    </section>;
};

export { StoryDemo };

Dependencies

More by YoucefBnm Bnm

View all
  • Animated Slideshow

    Animated Slideshow

    2.2K
  • Hero Gallery Scroll Animation

    Hero Gallery Scroll Animation

    1.5K
  • Animated Gallery

    Animated Gallery

    1.4K
  • Animated Video on Scroll

    Animated Video on Scroll

    1.4K
  • Animated Cards Stack

    Animated Cards Stack

    1.3K
  • Cards Stack

    Cards Stack

    1.1K
  • cta section with gallery

    cta section with gallery

    672
  • Hero Video

    Hero Video

    538