在 Lottie 动画中,Dynamic Property(动态属性)是一种特殊的属性,允许你在运行时修改动画的某些属性,例如颜色、位置、透明度等。它们提供了一种动态控制和交互的方式,使你能够根据应用程序的状态或用户输入来改变动画的外观和行为。
Dynamic Property 是通过 KeyPath(键路径)来标识和操作的。KeyPath 是一个由层级关系和属性名称组成的路径,用于指定要修改的动画属性所在的位置。
比如如下json 文件中的片段:
"layers": [
{
"ddd": 0,
"ind": 1,
"ty": 5,
"nm": "blue",
"parent": 2,
"sr": 1,
"ks" : {...},
"ao": 0,
"t": {...},
"ip": 0,
"op": 100,
"st": 0,
"bm": 0
}
]
其中这个blue就是该层级的key,使用动态属性时确保填入的 key 跟它一致,在代码层面就没有问题了,比如你有一个动态修改文本的需求,如果你AE里使用了自定义字体,它会出现在 json 结构的fonts数组里面,在代码中你应该先设置好字体,再动态修改文本。
// 定义一个函数加载Typeface
@Composable
fun rememberTypeface(path: String): Typeface? {
var typeface: Typeface? by remember {
mutableStateOf(null)
}
val context = LocalContext.current
LaunchedEffect(path) {
typeface = null
withContext(Dispatchers.IO) {
typeface = Typeface.createFromAsset(context.assets, path)
}
}
return typeface
}
// 加载自定义字体
val typeface = rememberTypeface("fonts/My-Font.otf")
// 定义动态属性
val dynamicProperties = rememberLottieDynamicProperties(
LottieDynamicProperty(
property = LottieProperty.TYPEFACE,
value = typeface,
keyPath = KeyPath("blue")
),
LottieDynamicProperty(
property = LottieProperty.TEXT,
value = "Narrow \njawline",
keyPath = KeyPath("blue")
),
)
val composition = rememberLottieComposition(
spec = LottieCompositionSpec.Asset("lottie/data.json"),
imageAssetsFolder = "lottie/images"
)
LottieAnimation(
composition = composition.value,
iterations = 1,
dynamicProperties = dynamicProperties,
modifier = Modifier
.matchParentSize()
)
代码这边就大功告成了,按理来说应该正常展示了,如果事实不然,出现了文本字符(字母)缺失的问题,再检查下你的 json 文件里是不是包含有一个chars数组,如果是,那么问题出在Bodymovin导出这一步,对应的github issue。
根据回答者提供的解决方案可以得知,UI导出lottie 的时候默认选中了Glyphs这个选项,会把文本转换成形状写入json里面,所以不用引入自定义的字体,缺点是只有动画中用到的字符才能被渲染。这显然不符合动态文本的需求,因此应该在Bodymovin的设置中取消勾选,这时只有文本会导出,插件也会让你上传自定义字体的文件,选择NONE跳过即可。
参考
1. Dynamic text in compose displays every third letter of the string