鸿蒙(HarmonyOS)提供了丰富的动画能力,涵盖属性动画、显式动画、转场动画、帧动画等多种类型,适用于不同场景的交互需求。以下是鸿蒙中各类动画的详细解析及使用示例:
1. 属性动画(Property Animation)
作用:通过改变组件的属性(如宽高、透明度、旋转角度等)实现平滑过渡效果。
核心接口 :animateTo
、animation
、keyframeAnimateTo
特点:系统自动插值计算中间帧,性能优化较好。
示例代码:
javascript
// 使用 animateTo 实现缩放动画
Button('点击放大')
.onClick(() => {
animateTo({ duration: 1000, curve: Curve.Ease }, () => {
this.scaleValue = this.scaleValue === 1 ? 1.5 : 1;
});
})
.scale({ x: this.scaleValue, y: this.scaleValue })
关键点:
- animateTo:显式触发动画闭包内的属性变化。
- animation****修饰符:自动响应状态变化(无需闭包)。
- 曲线类型 :如
Curve.Ease
(缓入缓出)、Curve.Spring
(弹性效果)。
2. 显式动画(Explicit Animation)
作用 :通过animateToImmediately
立即下发动画指令,减少延迟。
适用场景:需要优先渲染部分动画时(如高优先级交互反馈)。
示例代码:
javascript
animateToImmediately({ duration: 500 }, () => {
this.translateX = 100; // 立即执行位移动画
});
3. 转场动画(Transition Animation)
作用:处理组件出现/消失时的过渡效果,如页面跳转、弹窗弹出。
类型:
- 基础转场 :
TransitionEffect.opacity
(淡入淡出)、TransitionEffect.slide
(滑动)。 - 高级模板:导航转场、模态转场、共享元素转场(一镜到底)。

示例代码:
javascript
// 共享元素转场(一镜到底)
Image($r('app.media.thumbnail'))
.sharedTransition('imageTransition', { duration: 1000 })
// 页面转场
pageTransition() {
PageTransitionEnter({ duration: 300 }).slide(SlideEffect.Right);
PageTransitionExit({ duration: 300 }).opacity(0);
}
4. 帧动画(Frame Animation)
作用:逐帧控制属性变化,适合复杂自定义动画。
核心接口 :@ohos.animator
特点:灵活但性能开销较大,需手动管理帧回调。
示例代码:
javascript
const options = { duration: 2000, begin: 0, end: 100 };
const animator = this.getUIContext().createAnimator(options);
animator.onFrame = (value) => { this.progress = value; };
animator.play();
5. 粒子动画(Particle Animation)
作用:通过大量粒子运动营造氛围(如雪花、火焰)。
组件 :Particle
配置参数:粒子大小、颜色、速度、生命周期等。
示例代码:
javascript
Particle({
particles: [{
emitter: { particle: { type: ParticleType.POINT, radius: 5 } },
color: { range: ['#FF0000', '#FFFF00'] }
}]
}).width(200).height(200)
6. 路径动画(Motion Path)
作用:让组件沿指定路径运动。
接口 :motionPath
路径定义:支持 SVG 路径字符串或关键点坐标。
示例代码:
javascript
Image($r('app.media.rocket'))
.motionPath({ path: 'M 0 0 L 100 100', rotate: 'auto' })
7. 动画性能优化
- 减少布局属性动画 :优先使用
scale
/translate
替代width
/height
,避免触发重新布局。 - 合并动画闭包 :多个属性变化尽量合并到同一个
animateTo
中。 - 使用 renderGroup:对复杂动效组件启用缓存。
- 避免后台动画:应用切后台时暂停动画。
8. 常见问题
- 动画不生效 :检查属性是否支持动画(如
zIndex
不可动画)。 - 丢帧问题 :简化动画复杂度,或使用
expectedFrameRateRange
限制帧率范围。 - 手势与动画衔接 :通过
responsiveSpringMotion
继承手势速度,实现自然过渡。
综合示例
javascript
@Entry
@Component
struct ComplexAnimationDemo {
@State rotate: number = 0;
@State isVisible: boolean = false;
build() {
Column() {
// 属性动画 + 转场
if (this.isVisible) {
Text("Hello HarmonyOS")
.transition(TransitionEffect.rotate({ angle: 360 }).animation({ duration: 1000 }))
}
// 显式动画 + 路径
Button("触发动画")
.onClick(() => {
this.isVisible = !this.isVisible;
animateTo({ duration: 1500 }, () => {
this.rotate = 180;
});
})
.motionPath({ path: 'M 0 0 Q 50 100 100 0' })
}
}
}
总结
鸿蒙的动画体系覆盖了从简单属性变化到复杂场景动效的全场景需求,开发者应根据交互目标选择合适的动画类型,并遵循性能优化原则。具体场景可参考官方文档中的动画实践案例。