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

Flutter中如何实现音频与Lottie/Rive动画的同步?

Lottie/Rive 与音频并行播放的同步解决方案

这个需求属于动效落地的常见场景,目前已经有成熟的落地方案可以完全解决10-15分钟时长的音画同步问题,具体实现逻辑如下:

  • 核心原则:以音频进度为单一基准对齐动画,不要让音频和动画使用独立的时钟控制,二者的时钟漂移累积是音画不同步的核心原因。
  • 前置准备:制作阶段在动画和音频的关键节点(比如角色台词开头、转场节点)预埋统一的同步标记,Lottie可以通过属性关键帧埋点,Rive可以直接在编辑器内添加自定义事件,后续作为校准的参考点。
  • 播放端实现步骤:
    1. 资源预加载:等音频资源缓冲完成、动画首帧渲染完成后,再同时调用二者的播放接口,避免加载速度差异导致的初始偏移
    2. 定时校准:每300ms比对一次音频当前进度和动画当前进度,偏移超过100ms时直接把动画进度seek到对应位置,人耳对音频跳变的敏感度远高于画面小幅度跳帧,所以优先保证音频连续
    3. 关键节点强校验:到预埋的同步标记点时,强制校验一次二者进度,有偏移立即校准,避免误差累积
  • 代码参考示例(Lottie + 原生Audio):
// 音频实例、Lottie动画实例
const audio = document.getElementById('audio')
const anim = lottie.loadAnimation({
  container: document.getElementById('anim'),
  path: 'xxx.json'
})
let isPlaying = false

// 等待资源全部加载完成
Promise.all([
  new Promise(res => audio.addEventListener('canplaythrough', res)),
  new Promise(res => anim.addEventListener('DOMLoaded', res))
]).then(() => {
  // 同时启动播放
  audio.play()
  anim.play()
  isPlaying = true
})

// 定时校准
setInterval(() => {
  if (!isPlaying) return
  // 动画帧率假设为30,按实际帧率换算即可
  const currentAnimTime = (anim.currentFrame / 30) * 1000
  const currentAudioTime = audio.currentTime * 1000
  const diff = currentAudioTime - currentAnimTime
  // 偏移超过100ms执行校准
  if (Math.abs(diff) > 100) {
    anim.goToAndPlay(audio.currentTime * 30, true)
  }
}, 300)

Rive场景下实现逻辑完全一致,仅需将动画的进度查询、seek、加载完成监听的API替换为Rive官方提供的对应接口即可。按照上述方案实现,15分钟时长的动画播放偏移可以稳定控制在50ms以内,人眼和人耳都感知不到差异,已经在大量商用H5、短视频生成工具中落地验证。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.10.03 01:36:05