You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

使用framer-motion的staggerChildren实现按钮逐个动画失败问题排查

问题解决:Framer-Motion Stagger效果不生效的修复

核心问题分析

你当前的代码里,每个按钮都被单独包裹在SectionTransition组件中,相当于每个按钮都是独立的动画容器,staggerChildren属性需要作用在包含多个子元素的父容器上,单个子元素自然无法触发 stagger 效果。此外还有动画状态名称不匹配、子元素未绑定motion动画的问题。

代码修复步骤

1. 重构transition.tsx

将容器和子元素的动画变体分开,确保父容器的staggerChildren能控制子元素的动画顺序:

import { motion } from "framer-motion";

// 父容器变体:控制整体透明度并启用子元素 stagger
const containerVariants = {
  hidden: { opacity: 0 },
  animate: {
    opacity: 1,
    transition: {
      staggerChildren: 0.2, // 子元素动画间隔0.2秒
      delayChildren: 0.1 // 可选:整体延迟0.1秒后开始动画
    }
  }
};

// 子元素变体:单个按钮的动画效果
export const itemVariants = {
  hidden: { scale: 0, opacity: 0, y: 20 },
  animate: { scale: 1, opacity: 1, y: 0 }
};

export const SectionTransition = ({ children }: { children: React.ReactNode }) => {
  return (
    <motion.div
      initial="hidden"
      animate="animate"
      variants={containerVariants}
      className="overflow-hidden"
    >
      {children}
    </motion.div>
  );
};

2. 修改page.tsx

将所有按钮放在同一个SectionTransition容器下,同时把按钮改为motion.a并绑定子元素变体:

import { motion } from "framer-motion";
import { SectionTransition, itemVariants } from "./components/transition";

interface ExternalLinkProps {
  href: string;
  icon: React.ReactNode;
  label: string;
}

const ExternalLink: React.FC<ExternalLinkProps> = ({ href, icon, label }) => {
  return (
    <motion.a
      href={href}
      variants={itemVariants}
      className="your-button-class" // 替换为你的按钮样式类
    >
      <span>{icon}</span>
      <span>{label}</span>
    </motion.a>
  );
};

const socialLinks = [
  { href: "spoiler", icon: <span>图标1</span>, label: "标签1" },
  { href: "spoiler2", icon: <span>图标2</span>, label: "标签2" },
];

export default function Home() {
  return (
    <SectionTransition>
      <div className="grid gap-y-3 mt-6">
        {socialLinks.map(({ href, icon, label }) => (
          <ExternalLink
            key={href}
            href={href}
            icon={icon}
            label={label}
          />
        ))}
      </div>
    </SectionTransition>
  )
}

关键修复点说明

  • 所有按钮共享同一个SectionTransition父容器,让staggerChildren能作用于多个子元素
  • 子元素使用motion.a并绑定itemVariants,确保能继承父容器的 stagger 调度
  • 修正了动画状态名称不匹配的问题(原代码用enter但变体定义是hidden/animate)
  • 移除了不必要的AnimatePresence,仅在处理组件挂载/卸载动画时才需要它

内容的提问来源于stack exchange,提问作者bnvmnvbm

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.27 15:45:11