关于 auto-animate
面向使用 @formkit/auto-animate 的开发者,提供动画集成与排错指南,涵盖 SSR、框架配置和常见布局问题。
主要功能
- 01SSR 安全集成建议
- 02React、Vue 等框架示例
- 0315 类问题排查建议
- 04可访问性与动效注意事项
- 05附带模板和参考资料
适用场景
- 01排查 Next.js 的导入错误
- 02修复列表动画闪烁或错位
- 03处理 Vue 或 Nuxt 注册问题
安装
复制下面的命令,在终端中运行。
npx skills add https:/ / github.com/ jezweb/ claude-skills --skill auto-animate安装后在 Claude Code 中输入/auto-animate确认已加载。
包含的文件
除 SKILL.md 外,安装时一起下载的参考资料和脚本。
README.md.claude-plugin/plugin.jsonassets/example-template.txtreferences/auto-animate-vs-motion.mdcss-conflicts.mdexample-reference.mdssr-patterns.mdscripts/example-script.shinit-auto-animate.shtemplates/accordion.tsxfilter-sort-list.tsxform-validation.tsxreact-basic.tsxreact-typescript.tsxtoast-notifications.tsxvite-ssr-safe.tsx详细介绍
AutoAnimate - 错误预防指南
软件包:@formkit/[email protected](当前版本) 框架:React、Vue、Solid、Svelte、Preact 最后更新:2026-01-21
SSR 安全模式(对 Cloudflare Workers/Next.js 至关重要)
// Use client-only import to prevent SSR errors
import { useState, useEffect } from "react";
export function useAutoAnimateSafe<T extends HTMLElement>() {
const [parent, setParent] = useState<T | null>(null);
useEffect(() => {
if (typeof window !== "undefined" && parent) {
import("@formkit/auto-animate").then(({ default: autoAnimate }) => {
autoAnimate(parent);
});
}
}, [parent]);
return [parent, setParent] as const;
}
为何重要:可避免问题 #1(SSR/Next.js 导入错误)。AutoAnimate 使用了服务器上不可用的 DOM API。
已知问题预防(15 个已记录错误)
此技能可预防 15 个已记录的问题:
问题 #1:SSR/Next.js 导入错误
错误:“无法从非 EcmaScript 模块导入命名导出 ‘useEffect’”
来源:https://github.com/formkit/auto-animate/issues/55
原因:AutoAnimate 使用了服务器上不可用的 DOM API
预防措施:使用动态导入(参见 templates/vite-ssr-safe.tsx)
问题 #2:条件渲染父元素
错误:父元素为条件渲染时,动画无法运行 来源:https://github.com/formkit/auto-animate/issues/8 原因:Ref 无法附加到不存在的元素 预防措施:
React 模式:
// ❌ Wrong
{showList && <ul ref={parent}>...</ul>}
// ✅ Correct
<ul ref={parent}>{showList && items.map(...)}</ul>
Vue.js 模式:
<ul v-if="showList" ref="parent">
<li v-for="item in items" :key="item.id">{{ item.text }}</li>
</ul>
<ul ref="parent">
<li v-if="showList" v-for="item in items" :key="item.id">
{{ item.text }}
</li>
</ul>
问题 #3:缺少唯一键
错误:项目动画异常或闪烁
来源:官方文档
原因:React 无法跟踪哪些项目发生了变化
预防措施:始终使用唯一且稳定的键(key={item.id})
问题 #4:Flexbox 宽度和抖动问题
错误:元素直接跳到目标宽度,而不是平滑地播放动画;或者移除元素时容器抖动
来源:官方文档,问题 #212
原因:flex-grow: 1 会等待周围内容,导致时序问题
预防措施:对带动画的元素使用明确的宽度,而不是 flex-grow
// ❌ Wrong - causes shaking
<ul ref={parent} style={{ display: 'flex' }}>
{items.map(item => (
<li key={item.id} style={{ flex: '1 1 auto' }}>{item.text}</li>
))}
</ul>
// ✅ Correct - fixed sizes
<ul ref={parent} style={{ display: 'flex', gap: '1rem' }}>
{items.map(item => (
<li
key={item.id}
style={{ minWidth: '200px', maxWidth: '200px' }}
>
{item.text}
</li>
))}
</ul>
维护者说明:justin-schroeder 已确认,Flex 容器需要固定尺寸
问题 #5:表格行显示问题
错误:移除行时表格结构会损坏
来源:https://github.com/formkit/auto-animate/issues/7
原因:Display: table-row 与动画冲突
预防措施:将其应用于 <tbody>,而不是单独的行;或者使用基于 div 的布局
问题 #6:Jest 测试错误
错误:“找不到模块 ‘@formkit/auto-animate/react’”
来源:https://github.com/formkit/auto-animate/issues/29
原因:Jest 无法正确解析 ESM 导出
预防措施:在 jest.config.js 中配置 moduleNameMapper
问题 #7:esbuild 兼容性
错误:“软件包未导出路径 ‘.’” 来源:https://github.com/formkit/auto-animate/issues/36 原因:ESM/CommonJS 条件不匹配 预防措施:配置 esbuild,以正确处理 ESM 模块
问题 #8:CSS 定位的副作用
错误:添加 AutoAnimate 后布局损坏
来源:官方文档
原因:父元素会自动获得 position: relative
预防措施:在 CSS 中考虑定位变化,或显式设置定位
问题 #9:Vue/Nuxt 注册错误
错误:“无法解析指令:auto-animate” 来源:https://github.com/formkit/auto-animate/issues/43 原因:插件未正确注册 预防措施:在 Vue/Nuxt 配置中正确设置插件(参见 references/)
Nuxt 3 说明:需要 v0.8.2+(2024 年 4 月)。较早版本存在 ESM 导入问题,已由 Daniel Roe 修复。参见问题 #199
问题 #10:Angular ESM 问题
错误:构建失败,并提示“仅支持 ESM 的软件包” 来源:https://github.com/formkit/auto-animate/issues/72 原因:CommonJS 构建环境 预防措施:为 Angular Package Format 配置 ng-packagr
问题 #11:React 19 StrictMode 双重调用 Bug
错误:React 19 StrictMode 下子元素动画无法运行 来源:https://github.com/formkit/auto-animate/issues/232 原因:StrictMode 会调用两次 useEffect,导致 autoAnimate 初始化两次 预防措施:使用 ref 跟踪初始化状态
// ❌ Wrong - breaks in StrictMode
const [parent] = useAutoAnimate();
// ✅ Correct - prevents double initialization
const [parent] = useAutoAnimate();
const initialized = useRef(false);
useEffect(() => {
if (initialized.current) return;
initialized.current = true;
}, []);
注意:React 19 在开发环境中默认启用 StrictMode。这会影响所有 React 19+ 项目。
问题 #12:视口外动画失效
错误:列表位于视口外时,动画失效 来源:https://github.com/formkit/auto-animate/issues/222 原因:Chrome 可能不会为屏幕外的元素运行 Animation API 预防措施:应用 autoAnimate 前,确保父元素可见
const isInViewport = (element) => {
const rect = element.getBoundingClientRect();
return rect.top >= 0 && rect.bottom <= window.innerHeight;
};
useEffect(() => {
if (parent.current && isInViewport(parent.current)) {
autoAnimate(parent.current);
}
}, [parent]);
问题 #13:已删除的元素覆盖现有内容
错误:移除的项目在淡出期间覆盖其他项目 来源:https://github.com/formkit/auto-animate/issues/231 原因:退出动画会保留 z-index,遮挡活动内容 预防措施:显式处理 z-index
// CSS workaround
<style>{`
[data-auto-animate-target] {
z-index: -1 !important;
}
`}</style>
问题 #14:拖放期间无法禁用
错误:调用 enable(false) 无法阻止拖动期间的动画 来源:https://github.com/formkit/auto-animate/issues/215 原因:拖动过程中禁用功能不可靠 预防措施:拖动期间有条件地移除 ref
const [isDragging, setIsDragging] = useState(false);
const [parent] = useAutoAnimate();
return (
<ul ref={isDragging ? null : parent}>
{/* items */}
</ul>
);
问题 #15:CSS Transform 父元素位置 Bug
错误:父元素执行 transform 后,项目从错误的位置开始动画 来源:https://github.com/formkit/auto-animate/issues/227 原因:项目会记住 transform 前的原始位置 预防措施:等 transform 完成后再调用 autoAnimate
useEffect(() => {
if (showList && parent.current) {
setTimeout(() => {
autoAnimate(parent.current);
}, 300); // Match CSS transition duration
}
}, [showList]);
关键规则(避免错误)
始终做到
✅ 使用唯一且稳定的键 - 使用 key={item.id},而不是 key={index}
✅ 让父元素保留在 DOM 中 - 父元素的 ref 始终保持渲染
✅ SSR 时仅在客户端使用 - 在服务器环境中使用动态导入
✅ 遵循无障碍要求 - 保持 disrespectUserMotionPreference: false
✅ 在禁用动画时测试 - 验证界面在没有动画时仍能正常运行
✅ 使用显式宽度 - 避免在动画元素上使用 flex-grow
✅ 对表格应用于 tbody - 不要应用于单独的行
切勿这样做
❌ 有条件地渲染父元素 - {show && <ul ref={parent}>}
❌ 将索引用作键 - key={index} 会导致动画失效
❌ 忽略 SSR - 会在 Cloudflare Workers/Next.js 中出错
❌ 强制播放动画 - disrespectUserMotionPreference: true 会影响无障碍体验
❌ 直接对表格添加动画 - 使用 tbody 或基于 div 的布局
❌ 省略唯一键 - 正确播放动画的必要条件
❌ 使用复杂动画 - 改用 Motion
注意:AutoAnimate 会自动遵循 prefers-reduced-motion(切勿禁用此行为)。
社区技巧(来自社区)
注意:这些技巧来自社区讨论。请根据你使用的版本进行验证。
技巧:使用模拟的包避免测试卡顿
来源:问题 #230 | 可信度:中 适用版本:v0.8.2+
模拟包时,测试可能会卡顿约 10 秒。请添加 ResizeObserver 模拟:
// jest.setup.js
global.ResizeObserver = jest.fn().mockImplementation(() => ({
observe: jest.fn(),
unobserve: jest.fn(),
disconnect: jest.fn(),
}));
// __mocks__/@formkit/auto-animate.js
const autoAnimate = jest.fn(() => () => {});
const useAutoAnimate = jest.fn(() => [null, jest.fn(), jest.fn()]);
module.exports = { default: autoAnimate, useAutoAnimate };
技巧:防止内存泄漏
来源:问题 #180 | 可信度:低 适用版本:所有版本
对于长期运行的 SPA,请确保正确清理:
useEffect(() => {
const cleanup = autoAnimate(parent.current);
return () => cleanup && cleanup();
}, []);
// useAutoAnimate hook handles cleanup automatically
const [parent] = useAutoAnimate(); // Preferred
包版本
最新版本:@formkit/[email protected](2025 年 9 月 5 日)
近期发布:
- v0.9.0(2025 年 9 月 5 日)- 当前稳定版
- v0.8.2(2024 年 4 月 10 日)- 修复 Nuxt 3 ESM 导入问题,并添加 ResizeObserver 防护
{
"dependencies": {
"@formkit/auto-animate": "^0.9.0"
}
}
框架兼容性:React 18+、Vue 3+、Solid、Svelte、Preact
重要:Nuxt 3 用户必须使用 v0.8.2+。早期版本存在 ESM 导入问题
官方文档
- 官方网站:https://auto-animate.formkit.com
- GitHub:https://github.com/formkit/auto-animate
- npm:https://www.npmjs.com/package/@formkit/auto-animate
- React 文档:https://auto-animate.formkit.com/react
模板与参考资料
请参阅随附资源:
templates/- 可直接复制粘贴的示例(兼容 SSR、手风琴、提示消息、表单)references/- CSS 冲突、SSR 模式、库比较