本文档旨在指导 iOS 和 Android 开发人员如何在原生应用中复刻 Liquid Face ID / Touch ID 的流体动效。该动效已更新为最新的 小型化 (Micro-Interaction) 规范。
为了在移动端的小尺寸图标中保持清晰的流体质感,请严格遵循以下参数:
| 参数 | 数值 (Web/CSS) | iOS (pt) | Android (dp) | 说明 |
|---|---|---|---|---|
| 容器尺寸 | 25px x 25px |
25 x 25 | 25 x 25 | 标准图标大小 |
| 模糊半径 (Blur) | 5px |
~5 | ~5 | 关键: 小尺寸下必须降低模糊值,否则会糊成一团。 |
| 不透明度 (Opacity) | 0.9 |
0.9 | 0.90f | 保持较高的不透明度以增强色彩实感。 |
| 色块尺寸 | 150% |
37.5 (1.5x) | 37.5 (1.5x) | 色块需要比容器大,以覆盖整个视野。 |
以下是所有 8 套主题的官方配色方案。动效由三个不同颜色的模糊圆形(Blob)混合而成。
适配 25x25 尺寸的微调代码。
import SwiftUI
struct LiquidIcon25px: View {
@State private var animate = false
// 示例颜色:Neon Theme
let colors: [Color] = [
Color(hex: "6366f1"),
Color(hex: "06b6d4"),
Color(hex: "a855f7")
]
var body: some View {
ZStack {
// 背景层(可选,增加层次)
// Color.black.opacity(0.05)
// 液体层
GeometryReader { geometry in
ZStack {
// Blob 1
Circle().fill(colors[0]).opacity(0.9)
.frame(width: 35, height: 35) // 1.5倍左右
.blur(radius: 5) // 模糊半径降低至 5
.offset(x: animate ? 15 : -15, y: -5)
// Blob 2
Circle().fill(colors[1]).opacity(0.9)
.frame(width: 30, height: 30)
.blur(radius: 5)
.offset(x: animate ? -10 : 10, y: 10)
// Blob 3
Circle().fill(colors[2]).opacity(0.9)
.frame(width: 32, height: 32)
.blur(radius: 5)
.offset(x: animate ? 8 : -8, y: 0)
}
.frame(width: 25, height: 25, alignment: .center) // 容器限制
.onAppear {
withAnimation(.linear(duration: 1.5).repeatForever(autoreverses: true)) {
animate.toggle()
}
}
}
}
.frame(width: 25, height: 25)
// 使用 Face/Touch ID 形状进行遮罩
.mask(Image("icon_face_25pt").resizable())
}
}
@Composable
fun LiquidIcon25dp() {
val infiniteTransition = rememberInfiniteTransition()
// 动画状态定义...
Box(
modifier = Modifier
.size(25.dp) // 尺寸 25dp
.clip(FaceIdShape) // SVG Path 遮罩
) {
// Blob 1
Box(
modifier = Modifier
.size(35.dp)
.offset(x = 10.dp)
.graphicsLayer {
alpha = 0.9f
renderEffect = BlurEffect(5f, 5f) // API 31+ 模糊半径 5dp
}
.background(Color(0xFF6366f1), CircleShape)
)
// ... 其他 Blob
}
}