[__CAPGO_KEEP_9__]
[__CAPGO_KEEP_10__]
[__CAPGO_KEEP_11__]
- 为什么 Lottie 对 React Native 应用程序至关重要
- 设置您的 Lottie 开发环境
- 显示您的第一个 Lottie 动画
- 掌握 Lottie 动画控制
- 生产应用的性能调优
- 解决常见 Lottie 问题
为什么Lottie对于React Native应用程序至关重要
如果您曾经尝试在React Native中手动重建一个精致的产品动画,您就已经知道了痛苦。小动作细节变成了一个堆积的时间逻辑、插值和平台特性。动画可能看起来很接近,但“接近”通常不是设计师交付的内容。
Lottie改变了这一工作流程。Airbnb在2016年开源了Lottie,并且这一发布改变了移动动画,让设计师可以直接交付动画,而不用迫使工程师重建每个帧。 在某些企业环境中,这一转变降低了移动应用开发成本, 达到40%,根据 Airbnb的Lottie概述.
设计和工程停止为同一目标而战
Lottie React Native的关键益处不仅仅是“JSON中的漂亮动画”。它是关注点的分离。设计师在After Effects中工作,并使用Bodymovin导出。开发者使用原生支持的播放来渲染输出,而不是将运动转换为自定义code。
这很重要,因为动画工作有一个习惯性的倾向。一个单独的庆祝状态动画可以触及设计审查、产品审查、Android行为、iOS行为、可访问性和启动性能。Lottie缩小了这一表面面积。
实用规则: 在产品体验中使用Lottie时,动画是必要的,而不是仅仅需要一个简单的透明度或translate转换时。
还有一个用户体验方面。动画提供反馈,确认操作,并使加载状态感觉更不死气。 如果您的团队正在认真考虑界面上的细节、留存率或信任,动画就是该讨论的组成部分。更广泛的 应用用户体验讨论 通常会结束在同一个地方:快速反馈击败静态屏幕。
Lottie 在哪里最合适
Lottie React Native tends to work best for:
- 品牌微互动 例如喜欢、保存、勾选和成功购买状态
- 引导图 需要感觉自定义而不需要发送视频的
- 加载和空状态 静态 UI 感觉不完整
- 功能教育 当产品需要运动而不嵌入 GIFs 或 MP4s 时
它并不能解决所有动画问题。对于基本的屏幕过渡,React Native 的自身动画工具往往更简单。对于非常大的或高度交互的运动系统,JSON 格式可以成为一个权衡,而不是胜利。这种权衡在生产环境中变得更加重要,这也是大多数教程停得太早的地方。
设置您的 Lottie 开发环境
安装路径取决于一个决定: Expo 管理工作流或裸 React Native. 不要混淆两种思维模型。大多数设置问题发生在开发者在 Expo 中使用裸工作流程指南,或者假设 Expo 抽象了每个本机细节时。

在安装之前选择工作流程
如果您的应用程序生活在 Expo 中,并且您想要最快的设置,请在 Expo 路径上保持,除非您知道您需要自定义本机工作。 如果您在裸应用中,或者您已经依赖本机模块,需要直接控制,安装它作为一个正常的本机依赖项,并立即验证 iOS 和 Android 构建。
许多团队低估了当您将设置与项目类型保持一致时,调试变得多么容易。这也是为什么许多团队在构建自定义本机集成时,早早转向 Expo 开发客户端工作流 而不是等待应用程序变得更难改变。
Expo管理设置
对于Expo管理的应用程序,保持简单。
-
安装包
npx expo install lottie-react-native -
重启Metro
npx expo start -c -
在设备或模拟器上验证 从本地JSON文件开始,并首先渲染一个非常小的动画。不要同时调试一个大资产和一个新安装。
在Expo中,以下几点实用注意事项很重要:
- 优先使用本地文件: 远程动画调试会在您只想证明库正常工作时添加网络噪音。
- 尽早测试发布行为: 开发模式可能会隐藏与时间和性能相关的问题。
- 监控资产路径: 不正确的 JSON 文件是最常见的“渲染 nothing”原因之一。
Expo 是快速实现“它工作”的捷径,但这并不意味着它是快速实现“它可扩展”的捷径。
裸露的 React Native 设置
在裸露的项目中,立即安装并验证原生依赖项。
-
安装包
npm install lottie-react-native -
安装 iOS pods
cd ios && pod install && cd .. -
重建应用
npx react-native run-ios或
npx react-native run-android
许多快速启动指南都忽略了这一点:安装后,进行一次完整的原生重建,然后才能确定某些东西是有问题的。热重载无法修复一个没有正确编译到应用中的原生依赖项。
裸露工作流程的检查项,节省时间
在继续之前,请使用以下简短的检查清单:
| 检查 | 为什么它很重要 |
|---|---|
| __CAPGO_KEEP_0__ | 安装后重新构建 |
原生模块需要重新编译 pod install |
运行 |
| 没有它,iOS就不靠谱 | 首先使用一个简单的本地 JSON |
| 隔离安装问题和资产问题 | 尽早测试两种平台 |
Android 和 iOS 可能因为不同的原因失败
如果包安装正常,但您的第一帧动画没有显示出来,那通常不是安装问题。通常是资产路径、组件大小或播放配置的问题。
显示您的第一个 Lottie 动画

添加一个本地动画文件
如果你还没有一个资产文件夹,创建一个:
assets/
animations/
success.json
保持名称简单。避免使用空格、奇怪的标点符号和多层次的文件夹结构。您希望 require() 路径保持明显。
如果您正在使用 Lottie 为首次启动的品牌加载屏幕或启动后进行手动操作,想想在启动路径中放置一个大动画之前。尤其是当您还在调整您的 React Native 启动屏幕行为.
使用 LottieView 渲染它
创建一个专门的组件而不是直接将其放入一个大屏幕文件中:
import React from 'react';
import { View, StyleSheet } from 'react-native';
import LottieView from 'lottie-react-native';
export function SuccessAnimation() {
return (
<View style={styles.container}>
<LottieView
source={require('../assets/animations/success.json')}
autoPlay
loop={false}
style={styles.animation}
/>
</View>
);
}
const styles = StyleSheet.create({
container: {
alignItems: 'center',
justifyContent: 'center',
},
animation: {
width: 220,
height: 220,
},
});
这三点非常有用:
- 它证明了库正确渲染
- 它证明了资产路径正确解析
- 它给你一个单独的地方来调整播放和大小
如果你跳过基础知识,立即会出现几个问题:
- 没有宽度或高度: 动画可以存在但不可见
- 错误
require()路径: Metro找不到文件 - 无效的导出: 有些JSON文件是技术上有效的,但包含的特性在移动设备上不按预期工作
保持第一次渲染本地和确定性的。你是在测试集成,而不是架构
更好的首屏测试
将组件放置在一个简单的屏幕上,背景为中性
import React from 'react';
import { SafeAreaView, StyleSheet } from 'react-native';
import { SuccessAnimation } from './src/SuccessAnimation';
export default function App() {
return (
<SafeAreaView style={styles.screen}>
<SuccessAnimation />
</SafeAreaView>
);
}
const styles = StyleSheet.create({
screen: {
flex: 1,
justifyContent: 'center',
alignItems: 'center',
backgroundColor: '#fff',
},
});
如果在 iOS 和 Android 模拟器中都能正常工作,你已经克服了第一个真正的障碍。从那里,下一步不是添加更多的动画。它是学习何时使用声明性属性和何时使用 refs 直接控制。
掌握 Lottie 动画控制
大多数 Lottie React Native 错误出现在动画需要响应状态时。自动播放很容易。"当用户喜欢一个项目时播放这个段落,反转时不反转,当组件重新渲染时不要卡顿"是这里变得混乱的地方。

使用属性时播放
对于非交互式播放,属性就足够了。
<LottieView
source={require('../assets/animations/loading.json')}
autoPlay
loop
speed={1}
/>
适合此风格的场景是:
- 加载指示器
- 被动引导图示
- 装饰性空白状态
它是声明性的和可读的。组件挂载,播放开始,React 保持控制。如果动画逻辑可以完全由属性描述,保持在那里。
一个更复杂的声明性案例是 progress在动画帧中绑定到另一个值时,效果很好,当动画反映某些外部进度源时,但对于一次性触发事件来说,这种方式不太方便。
快速对比动画前进到 refs 之前:
当状态驱动动画时,使用 refs
当用户点击、切换或完成某个动作时,refs 通常是一个更安全的工具。现实世界的数据显示 使用混合框架的开发者中,68% 的人报告由于在 hooks 中处理 refs 不当而导致动画触发失败在 useEffect hooks,这就是为什么围绕 animation.current.play() 的可靠模式很重要,正如本 Capacitor-关注的讨论中提到的失败触发器.
这个问题不仅限于混合应用。它也出现在普通的 React Native 中,尤其是当开发者重建 refs、在 mount 之前触发播放或将动画调用与不稳定的效果绑定时。
import React, { useRef, useState } from 'react';
import { Pressable } from 'react-native';
import LottieView from 'lottie-react-native';
export function LikeButton() {
const animationRef = useRef<LottieView>(null);
const [liked, setLiked] = useState(false);
const onPress = () => {
if (!animationRef.current) return;
if (liked) {
animationRef.current.play(60, 0);
} else {
animationRef.current.play(0, 60);
}
setLiked(!liked);
};
return (
<Pressable onPress={onPress}>
<LottieView
ref={animationRef}
source={require('../assets/animations/like.json')}
loop={false}
autoPlay={false}
style={{ width: 96, height: 96 }}
/>
</Pressable>
);
}
可靠的喜欢和不喜欢模式
这个模式在生产环境中比直接调用更可靠 play() 内部 useEffect 每次状态改变时都会发生。
为什么会这样:
- 事件拥有动画触发器: 按键事件是稳定的开始播放的时机。
- 引用保持本地和持久:
useRef避免不必要的重新渲染。 - 组件避免自动播放冲突: 你不希望挂载行为与用户触发行为冲突。
值得避免的常见错误:
-
在引用不存在时触发
如果animationRef.current如果为空,播放将不会发生。保护它。 -
使用
autoPlay与命令式控件
选择一个默认的播放器拥有者。 -
驱动一切
useEffect
效果很有用,但在UI操作中,它们经常会引入时间问题而不是去除它们。
如果一个动画响应一个点击,首先在点击处理器内部触发它。只有当真实数据源位于该交互作用之外时才使用
useEffect生产应用程序的性能优化
Lottie React Native 是一种看起来很轻量级的库,直到团队开始将大型 JSON 文件塞入应用程序包并Wondering 为什么启动时间回归。动画本身并不是问题。交付策略才是。
详细介绍了 Lottie 性能优化的三个关键优势:减小包大小、提高帧率和降低内存使用率的 infographic。

__CAPGO_KEEP_0__
直接将每个动画打包到 JavaScript 中并在启动时全部加载是最容易犯的错误,根据 关于错误地将 Lottie JSON 发送的指南,将类似 Lottie JSON 的资产加载到 JS 包中会在中档设备上 使应用启动时间增加 40% 或更多将它们移动到原生资产中进行按需加载是关键优化
这与许多团队在实践中看到的结果一致
- 问题不是单个小型成功动画
- 而是积累:
- 引导动画
- 加载状态
- 电子商务反应
品牌空白屏幕
优化的第一步是什么
首先优化导出本身。导出动画时的糟糕复杂性会在解析、内存和渲染稳定性上带来后果。不要接受设计师导出的所有内容不加修改。
使用此生产检查清单:
- 在交付前压缩 JSON: 较小的文件更容易加载,且启动时不会导致膨胀。
- 将非关键动画从 JS 包中移除: 保持启动 code 聚焦于应用当前需要的内容。
- 按需加载动画: 在屏幕或动作需要时渲染。
- 审计旧设备行为: 现代模拟器可以隐藏昂贵的播放。
- 避免使用大型 Lottie 文件作为启动装饰: 如果它对首次交互不是至关重要的,那么它就不应该与应用启动竞争。
对于严肃地进行移动性能工作的团队来说, AppLighter的移动性能指南 是一个有用的参考读物,因为它将动画决策置于应用启动、渲染和框架权衡的更大背景中。
一个残酷的真相: 延迟首次交互的美丽动画通常是一个产品bug,而不是一个设计胜利。
您还应考虑超出React Native的孤立。混合堆栈的团队会遇到类似的资产加载问题,而更广泛的 Capacitor应用的动画性能指南 与Lottie决策也很相符。
本地文件与远程交付
本地文件是可预测的。它们可以在离线状态下工作,消除了网络变异性,并且更容易测试。它们也很容易过度打包。
远程交付使二进制文件更轻,但现在您的动画有可用性、缓存和fallback问题。这种权衡对于非关键动作是可接受的,但对于主要的UX状态,如购买确认或身份验证成功,则风险较大。
一个实用的分离方案很好:
| 资产类型 | 更好的默认值 |
|---|---|
| 核心交互动画 | 本地、优化、不超载 |
| 偶尔的促销动画 | 远程fallback |
| 启动路径动画 | 仅当绝对必要时本地 |
| 罕见的功能说明 | 按需加载 |
如果您只应用本节中的一个规则,请使用此规则: 对 Lottie JSON 文件视为性能敏感的资产,而不是无害的装饰.
常见 Lottie 问题的故障排除
当 Lottie 出现问题时,通常是因为普通的原因:错误的路径、缺失的尺寸、错误的引用时间、过重的 JSON。快速调试的方法是减少变量。
在 Android 上,动画无法渲染
首先确认 JSON 文件可以解析,然后为组件指定明确的尺寸。
<LottieView
source={require('../assets/animations/success.json')}
autoPlay
style={{ width: 200, height: 200 }}
/>
如果仍然无法解决问题,请切换到一个已知的良好动画。这可以告诉你问题是否出在文件上还是设置上。
在旧设备上,播放动画时出现卡顿
这通常指向资产本身,而不是组件 API。
尝试以下修复方法:
- 减少动画复杂度: 如果源文件很重,请要求导出一个更轻的版本。
- 延迟加载: 不要与初始屏幕工作竞争。
- 测试压缩版本: 如果压缩文件表现得更好,那么你找到了瓶颈。
- 移除多个同时显示的Lottie视图: 屏幕上有多个动画可能太多了。
ref为null或播放无效
通常null refs意味着触发器在mount之前触发,或者组件被条件删除。
if (animationRef.current) {
animationRef.current.play();
}
保持ref稳定,使用和不必要地重建动画组件。如果你在本地构建中反复出现奇怪的bug,清除过时的缓存可以有所帮助。一个简单的 useRefYarn缓存清理程序 有时足以移除开发期间的误导性资产行为。 动画在屏幕大小上看起来不正确
如果你在本地构建中反复出现奇怪的bug,清除过时的缓存可以有所帮助。一个简单的Yarn缓存清理程序有时足以移除开发期间的误导性资产行为。
不要让动画定义布局。将其放入一个容器中并有意地设置其大小。
- 使用固定边界的图标和反应
- 使用更大的插图的比例感知包装器
- 在没有检查导出意图的组合的情况下不检查拉伸到全宽
大多数“Lottie 是破损”的报告最终都是布局问题、资产问题或时间问题。该库经常做的是您要求它做的事情
如果您需要一个最终的调试快捷方式,请移除每个高级属性,渲染一个本地动画在一个居中的视图中,然后从那里逐步构建。这种方法比凝视一个繁忙的生产屏幕更快地隔离问题
Capgo 帮助团队将 JavaScript、资产和配置修复推送到 Capacitor 应用程序,而无需等待商店审查。如果您维护一个混合应用并需要更安全的方式来推送更新、处理阶段性发布和快速恢复前端问题, Capgo 值得一看