diff --git a/packages/react/src/components/DTStaggerContainer.tsx b/packages/react/src/components/DTStaggerContainer.tsx index 7c3f224..8f07332 100644 --- a/packages/react/src/components/DTStaggerContainer.tsx +++ b/packages/react/src/components/DTStaggerContainer.tsx @@ -2,18 +2,22 @@ * DTStaggerContainer — Staggered scale-in animation for children. * * CSS reference: animations.css .dt-stagger-container - * CSS handles all stagger timing via nth-child — no JS animation needed. + * Each child is wrapped in a div that carries the animationDelay. + * Wrapper divs inherit display:contents would break animation, so + * the CSS rule targets .dt-stagger-container > * directly. */ -import type { ReactNode, CSSProperties } from 'react'; +import { Children, type ReactNode, type CSSProperties } from 'react'; import { cx } from '../utils/cx'; interface DTStaggerContainerProps { children: ReactNode; /** Duration per child animation @default '0.33s' */ duration?: string; - /** Delay between each child @default '75ms' */ - interval?: string; + /** Delay between each child in ms @default 150 */ + interval?: number; + /** Base delay before the first child animates in ms @default 0 */ + delay?: number; className?: string; style?: CSSProperties; } @@ -21,19 +25,23 @@ interface DTStaggerContainerProps { export function DTStaggerContainer({ children, duration, - interval, + interval = 150, + delay = 0, className, style, }: DTStaggerContainerProps) { const cssVars: Record = {}; if (duration) cssVars['--dt-stagger-duration'] = duration; - if (interval) cssVars['--dt-stagger-interval'] = interval; return (
- {children} + {Children.map(children, (child, i) => ( +
+ {child} +
+ ))}
); } diff --git a/packages/react/src/index.ts b/packages/react/src/index.ts index cece900..f0b1fb6 100644 --- a/packages/react/src/index.ts +++ b/packages/react/src/index.ts @@ -44,7 +44,6 @@ export { DTSearchInput } from './components/DTSearchInput'; export { DTProgressBar } from './components/DTProgressBar'; export { DTAccordion } from './components/DTAccordion'; export type { DTAccordionSection } from './components/DTAccordion'; -export { DTStaggerContainer } from './components/DTStaggerContainer'; export { DTBadgeOverlay } from './components/DTBadgeOverlay'; // Components — filter & feature @@ -58,3 +57,6 @@ export { DTMobileFilterOverlay } from './components/DTMobileFilterOverlay'; export { DTGallery } from './components/DTGallery'; export type { DTGalleryItem } from './components/DTGallery'; export { DTHexagon } from './components/DTHexagon'; + +// Components — animation +export { DTStaggerContainer } from './components/DTStaggerContainer'; diff --git a/packages/web/src/components/animations.css b/packages/web/src/components/animations.css index 4f4de43..a6caf52 100644 --- a/packages/web/src/components/animations.css +++ b/packages/web/src/components/animations.css @@ -82,49 +82,16 @@ /* ============================================================================ Stagger Container - Source: storefront framer-motion staggered card entrance - Usage:
...
- Customize: --dt-stagger-duration, --dt-stagger-interval ============================================================================ */ .dt-stagger-container { --dt-stagger-duration: 0.33s; - --dt-stagger-interval: 75ms; } .dt-stagger-container > * { animation: dt-scale-in var(--dt-stagger-duration) ease-in-out both; } -.dt-stagger-container > :nth-child(1) { animation-delay: calc(0 * var(--dt-stagger-interval)); } -.dt-stagger-container > :nth-child(2) { animation-delay: calc(1 * var(--dt-stagger-interval)); } -.dt-stagger-container > :nth-child(3) { animation-delay: calc(2 * var(--dt-stagger-interval)); } -.dt-stagger-container > :nth-child(4) { animation-delay: calc(3 * var(--dt-stagger-interval)); } -.dt-stagger-container > :nth-child(5) { animation-delay: calc(4 * var(--dt-stagger-interval)); } -.dt-stagger-container > :nth-child(6) { animation-delay: calc(5 * var(--dt-stagger-interval)); } -.dt-stagger-container > :nth-child(7) { animation-delay: calc(6 * var(--dt-stagger-interval)); } -.dt-stagger-container > :nth-child(8) { animation-delay: calc(7 * var(--dt-stagger-interval)); } -.dt-stagger-container > :nth-child(9) { animation-delay: calc(8 * var(--dt-stagger-interval)); } -.dt-stagger-container > :nth-child(10) { animation-delay: calc(9 * var(--dt-stagger-interval)); } -.dt-stagger-container > :nth-child(11) { animation-delay: calc(10 * var(--dt-stagger-interval)); } -.dt-stagger-container > :nth-child(12) { animation-delay: calc(11 * var(--dt-stagger-interval)); } -.dt-stagger-container > :nth-child(13) { animation-delay: calc(12 * var(--dt-stagger-interval)); } -.dt-stagger-container > :nth-child(14) { animation-delay: calc(13 * var(--dt-stagger-interval)); } -.dt-stagger-container > :nth-child(15) { animation-delay: calc(14 * var(--dt-stagger-interval)); } -.dt-stagger-container > :nth-child(16) { animation-delay: calc(15 * var(--dt-stagger-interval)); } -.dt-stagger-container > :nth-child(17) { animation-delay: calc(16 * var(--dt-stagger-interval)); } -.dt-stagger-container > :nth-child(18) { animation-delay: calc(17 * var(--dt-stagger-interval)); } -.dt-stagger-container > :nth-child(19) { animation-delay: calc(18 * var(--dt-stagger-interval)); } -.dt-stagger-container > :nth-child(20) { animation-delay: calc(19 * var(--dt-stagger-interval)); } -.dt-stagger-container > :nth-child(21) { animation-delay: calc(20 * var(--dt-stagger-interval)); } -.dt-stagger-container > :nth-child(22) { animation-delay: calc(21 * var(--dt-stagger-interval)); } -.dt-stagger-container > :nth-child(23) { animation-delay: calc(22 * var(--dt-stagger-interval)); } -.dt-stagger-container > :nth-child(24) { animation-delay: calc(23 * var(--dt-stagger-interval)); } - -.dt-stagger-container > :nth-child(n+25) { - animation-delay: calc(24 * var(--dt-stagger-interval)); -} - /* ============================================================================ Transition Utilities ============================================================================ */