关于 ios-animation-design
ios-animation-design 是用于规划 iOS 动效的设计技能,涵盖背景梳理、方案比较和可实施规格。它强调优先使用系统动效,并考虑无障碍与中断处理。
主要功能
- 01按顺序完成背景与设计关卡
- 02比较 2–3 种不同动效方案
- 03编写可实施的动效规格
- 04纳入减少动态效果与中断要求
- 05覆盖多类动画场景
适用场景
- 01规划新的 iOS 交互动效
- 02根据最低系统版本选择动画 API
- 03明确无障碍回退与触觉反馈
安装
复制下面的命令,在终端中运行。
npx skills add https:/ / github.com/ existential-birds/ beagle --skill ios-animation-design安装后在 Claude Code 中输入/ios-animation-design确认已加载。
附带文件references/animation-patterns.mdreferences/timing-guidelines.md
详细介绍
iOS 动画设计
规划恰到好处、而非徒有装饰性的动画。Apple 的 HIG 明确指出:“不要为了添加动效而添加动效。多余或过度的动画会分散人们的注意力,还可能让他们感到疏离或身体不适。”每个动画都必须有明确目的——引导注意力、传达状态变化、强化空间关系或提供反馈。
添加任何自定义动画之前,先问问:系统是否已经能处理?许多系统组件都自带动效——Liquid Glass(iOS 26)会对触控做出更明显的响应,而在触控板交互时则会呈现更含蓄的效果。标准控件、导航转场和工作表本身就会动效。自定义动效应填补系统未覆盖的空白,而不是取代系统已经处理得很好的部分。
设计流程
关卡(按顺序进行)
只有在工作产物(聊天或文档)满足每个关卡的通过条件后才能继续。没有证据时,不要为符合要求找理由。
- 关卡 — 已记录上下文 — 通过条件: 已书面回答以下问题:什么会触发动效、动效的目的、它在应用中的位置、运行频率、最低 iOS 版本,以及主要输入方式(或明确标注不适用的 N/A)。通过条件: 已说明系统提供的动效是否已覆盖此需求,或自定义动画要填补哪个空白。
- 关卡 — 方案有实质差异 — 通过条件: 提供了 2–3 种方案,且每种方案至少在以下方面中的两项有所不同:具名 API/技术、动效特征、复杂度等级或 iOS 最低版本要求;不能只是对同一想法进行细微的时间调整。
- 关卡 — 规格可直接用于实现 — 通过条件: 汇总后的规格包含以下各项的具体内容:触发条件、中断处理(取消/反向/排队)、减少动态效果时的替代方案、触觉反馈(或说明无触觉反馈并给出理由),以及推荐 API。
步骤 1:了解动画上下文
在提出方案之前,先了解需要为哪些内容添加动画,以及原因:
- 什么会触发动画? 用户操作(轻点、轻扫、拖动)、状态变化(数据已加载、发生错误),还是生命周期事件(出现、消失)?
- 动画的目的是什么? 提供反馈、辅助空间定位、过渡内容、增添趣味,还是传达状态?
- 动画位于应用的哪个位置? 导航流程、屏幕内状态变化、叠加层/模态视图,还是背景环境动效?
- 动画出现频率如何? 每个会话一次(引导流程)、每次交互时(切换标签页),还是持续运行(进度指示器)?Apple 的 HIG 提醒:“在应用中,通常应避免为频繁发生的 UI 交互添加动效。系统已经为标准界面元素的交互提供了细微的动画。”
- 部署目标是什么? 最低 iOS 版本决定了可用的 API。
- 输入方式有哪些? 触控、触控板、键盘、VoiceOver?iOS 26 的 Liquid Glass 会根据输入方式调整动效强度——直接触控的效果更明显,间接输入则更含蓄。自定义动画也应遵循相同原则。
步骤 2:提出 2–3 种动画方案
针对每项动画需求,提出 2–3 种各具特色的方案。每种方案都应有实质差异,而不是对同一想法稍作变通。每种方案按以下格式组织:
### Option [N]: [Name]
**Approach**: [1-2 sentences describing the motion design]
**Technique**: [Which Apple API — SwiftUI animation, KeyframeAnimator, matchedGeometryEffect, etc.]
**Character**: [How it feels — snappy, playful, elegant, subtle, dramatic]
**Complexity**: [Low / Medium / High — implementation and maintenance cost]
**iOS floor**: [Minimum iOS version required]
随后给出推荐方案,并结合已收集的上下文说明理由。推荐方案应考虑:
- API 是否适用于目标部署版本
- 复杂度预算——除非动画是标志性体验,否则越简单越好
- 系统是否已经能处理——优先使用系统提供的动效,而不是自定义实现
- 与应用现有动效风格的一致性
- 是否可以中断——用户能否中断或跳过动画?(Apple 的 HIG 指出:“不要让人们必须等待动画完成后才能进行其他操作。”)
- 无障碍性(在启用“减少动态效果”时能否平稳降级?)
- 多模态反馈——不应只靠动画传递信息。“除视觉反馈外,还应使用触觉反馈和音频等替代方式进行补充。”(Apple 的 HIG)
第 3 步:编写动画规范
用户选择一种方案(或确认推荐方案)后,编写一份结构化规范。这份规范是设计与实现之间的约定——其中应包含编写代码所需的一切信息,避免歧义。
动画规范格式
# Animation Spec: [Name]
## Overview
[1-2 sentences: what this animation does and why it exists]
## Trigger
- **Event**: [What initiates the animation — tap, state change, appear, gesture, etc.]
- **Direction**: [Forward / Reverse / Bidirectional]
## Motion Design
### Properties
| Property | From | To | Curve | Duration |
|----------|------|----|-------|----------|
| opacity | 0 | 1 | .easeOut | 0.25s |
| scale | 0.8 | 1.0 | .spring(duration: 0.5, bounce: 0.3) | — |
| offset.y | 20 | 0 | .spring(duration: 0.5, bounce: 0.3) | — |
### Timing
- **Total duration**: [end-to-end time]
- **Stagger**: [if multiple elements, delay between each]
- **Interruption**: [What happens if triggered again mid-animation — cancel, reverse, queue]
### Gesture Binding (if interactive)
- **Gesture type**: [drag, long press, rotation, magnification]
- **Progress mapping**: [How gesture progress maps to animation progress]
- **Threshold**: [When the animation commits vs. cancels]
- **Velocity handling**: [How release velocity affects completion]
## Accessibility & Multimodal Feedback
- **Reduce Motion**: [What happens — crossfade, instant, simplified version]
- **VoiceOver**: [Any announcement needed for the state change]
- **Haptics**: [Which sensoryFeedback type pairs with this animation — .impact, .selection, .success, etc.]
- **Audio**: [Optional sound cue if the state change is important enough]
- **Dynamic Type**: [Does layout shift affect the animation?]
## Implementation Notes
- **Recommended API**: [SwiftUI withAnimation, KeyframeAnimator, PhaseAnimator, matchedGeometryEffect, UIViewPropertyAnimator, etc.]
- **State model**: [What @State/@Binding drives this animation]
- **Extractable component**: [Yes/No — should this be a reusable ViewModifier or View?]
动画类别
设计时,请考虑以下类别。每种类别对时长、缓动和用途都有不同要求。
导航与场景转场
屏幕之间的切换。用户期望空间连贯——我从哪里来,要去哪里?这类动画应快速、利落。
- 使用主视觉元素的推入/弹出(
matchedGeometryEffect、navigationTransition(.zoom)) - 全屏覆盖层和工作表(自定义
Transition协议) - 标签页切换(交叉淡化、滑动或匹配几何效果)
- 引导流程(基于页面并逐步呈现)
时长:0.3–0.5s。缓动:基于弹簧(.snappy 或 .smooth)。中断处理:必须妥善处理返回手势。
微交互
针对用户操作提供即时的小幅反馈。Apple 的 HIG 强调简洁:“动画反馈简短而精确时,往往显得轻盈、不突兀,而且通常比醒目的动画更能有效传达信息。”这类反馈应几乎即时,且绝不能阻碍交互。对于频繁发生的交互,在添加自定义动效前,应认真考虑系统内置动画是否已足够。
- 按钮按下状态(缩放 + 触觉反馈)
- 开关动画
- 点赞/收藏/书签反馈
- 下拉刷新指示器
- 文本字段焦点转场
- 滑动操作显现
时长:0.1–0.3s。缓动:.snappy 或 .spring(duration: 0.2, bounce: 0.4)。始终搭配 sensoryFeedback——触觉反馈能强化视觉反馈,并向看不到动画的用户传达信息。
内容转场
视图中的数据发生变化时使用,例如数字更新、内容切换或列表重新排序。
- 数字文本转场(
.contentTransition(.numericText)) - 图像交叉淡化
- 列表项插入/移除
- 骨架屏过渡为内容
- 错误/空/已加载状态切换
时长:0.2–0.35s。缓动:.smooth 或 .easeInOut。使用与变化数据关联的 animation(_:value:)。
手势驱动的动画
用户直接控制动画进度的交互式动画。这类动画应让人感觉与手指紧密相连——不能有延迟或脱节感。
- 卡片关闭(滑动移除)
- 抽屉/工作表拖动
- 双指缩放
- 旋转交互
- 滚动联动视差(
scrollTransition)
基于弹簧的收尾至关重要。松开时追踪速度。UIKit 使用 UIViewPropertyAnimator,SwiftUI 使用 GestureState + spring。
加载与进度
传达等待状态和进度。动画应充满活力,但不能分散注意力。
- 骨架屏(使用渐变遮罩实现闪光效果)
- 不确定进度的旋转指示器(SF Symbol
.symbolEffect(.pulse)) - 确定进度的进度条/环形指示器(动画效果)
- 内容占位符脉冲(
PhaseAnimator)
循环动画应保持轻量——它们会持续运行,不得耗尽电量或造成卡顿。
环境与装饰效果
用于营造氛围的背景动效。请谨慎使用——这类效果最容易过度使用。
- 动态渐变(
MeshGradient配合计时器驱动的点位变化) - 浮动粒子效果
- 设备倾斜时的细微视差
- 背景模糊转场
启用“减少动态效果”时,务必禁用或简化动画。这类效果应最先为提升性能而删减。
原则
- 目的优先于润色 — 如果说不清某个动画的作用,它就不该存在。Apple 的 HIG 写道:“不要为了添加动效而添加动效。”
- 系统优先 — 许多系统组件已经包含动效(Liquid Glass、导航转场、表单、SF Symbol 效果)。设计自定义动效前,先检查系统是否已处理。自定义动画应填补空缺,而不是重复实现系统效果。
- 简洁胜于炫目 — “反馈动画应简洁精准”(Apple HIG)。简短的动画比醒目的动画更能有效传达信息。与操作相关的简洁响应,胜过复杂的动画序列。
- 优先使用弹簧,而非曲线 — 弹簧动画更有真实的物理感。使用
duration+bounce参数,而非贝塞尔曲线,除非有特定理由。 - 减少动态效果并非可选项 — 每份动画规范都必须包含减少动态效果的备用方案。Apple 的 HIG 写道:“让动效可以选择。并非所有人都能或愿意体验应用中的动效。”这也意味着,绝不能只用动画来传达重要信息。
- 多模态反馈 — 适当时,可通过触觉反馈(
.sensoryFeedback)和音频补充动画。不能只依靠动画传达关键状态变化。 - 用户有权取消 — “不要让人们必须等动画播放完才能进行其他操作,尤其是他们需要多次体验该动画时”(Apple HIG)。每个动画都必须可以中断。
- 符合现实的空间反馈 — 动效应遵循用户的手势和预期。如果用户将视图向下滑动,他们会期望通过向下滑动来关闭它,而不是向侧面滑动。违背空间逻辑的反馈会让人感到困惑。
- 速度赢得信任 — 时长低于 0.3s 的动画会让人感觉响应迅速。超过 0.5s 则会显得迟缓,除非是具有标志性的时刻。有疑问时,就选更快的速度。
- 一致性会不断积累 — 对相似交互使用相同的弹簧参数。一致的动效语言能让整个应用更协调。定义少量时长预设,并重复使用。