JankStats 推出 alpha 版本
作者 / Chet Haase, Android 开发技术推广工程师
卡顿 (名词): 指应用性能糟糕,可能导致丢帧、界面动画不连贯和用户体验不佳等问题。请参阅 "不开心的用户" 词条。
性能问题很难调试。我们常常不清楚要从何下手、使用何种工具、用户遇到了什么问题,以及那些问题在现实的设备上有何表现。
过去几年间,Android 团队一直努力推出更多工具,用于调试各种问题,从分析启动性能到测试具体代码路径,再到测试和优化特定用例及 IDE 中的可视化分析器,各领域均有涉猎。所有这些工具均针对开发期间的测试设计,用于帮助您调试和修复在本地运行时发现的问题。
Jetpack 基准库 https://developer.android.google.cn/studio/profile/benchmark 用例: Macrobenchmark 简介 https://developer.android.google.cn/studio/profile/macrobenchmark-intro Android Profiler https://developer.android.google.cn/studio/profile/android-profiler
同时,Google Play 的 Android Vitals 和 Firebase 均提供信息中心,供开发者了解其应用在实际用户设备上的运行情况。
Android Vitals https://support.google.com/googleplay/android-developer/answer/9844486?visit_id=637793617854677762-3147968388&rd=1 Firebase https://firebase.google.cn/products/performance
每帧性能
FrameMetrics
https://developer.android.google.cn/reference/android/view/FrameMetrics
val jankFrameListener = JankStats.OnFrameListener { frameData ->
// real app would do something more interesting than log this...
Log.v("JankStatsSample", frameData.toString())
}
jankStats = JankStats.createAndTrack(
window,
Dispatchers.Default.asExecutor(),
jankFrameListener,
)
JankLoggingActivity https://github.com/android/performance-samples/blob/main/JankStatsSample/app/src/main/java/com/example/jankstats/JankLoggingActivity.kt
JankStats.OnFrameListener: FrameData(frameStartNanos=827233150542009, frameDurationUiNanos=27779985, frameDurationCpuNanos=31296985, isJank=false, states=[Activity: JankLoggingActivity])
JankStats.OnFrameListener: FrameData(frameStartNanos=827314067288736, frameDurationUiNanos=89903592, frameDurationCpuNanos=94582592, isJank=true, states=[RecyclerView: Dragging, Activity: JankLoggingActivity])
JankStats.OnFrameListener: FrameData(frameStartNanos=827314167288732, frameDurationUiNanos=88641926, frameDurationCpuNanos=91526926, isJank=true, states=[RecyclerView: Settling, RecyclerView: Dragging, Activity: JankLoggingActivity])
JankStats.OnFrameListener: FrameData(frameStartNanos=827314183945923, frameDurationUiNanos=4731405, frameDurationCpuNanos=8283405, isJank=false, states=[RecyclerView: Settling, Activity: JankLoggingActivity])
您可以在日志的 frameData 中看到一些有趣的内容:
其中有部分帧带有 isJank=true 标记。该日志取自运行的示例应用 JankLoggingActivity,您可查看完整示例了解更多。该应用会强制产生一些长帧 (没错,用了 Thread.sleep()!),从而让 JankStats 判定其为卡顿。 帧的时间信息中同时包含界面和 CPU 数据,但在 API 24 (FrameMetrics 被引入的版本) 之前的版本中,此信息仅包含界面持续时间。 该日志是从我在应用中开始滑动 RecyclerView 时获取的。当 RecyclerView 开始移动 (被 "拖动") 以及 RecyclerView 开始自由滚动 (被 "放置") 时,我们可在开始之前看到与界面状态相关的信息 (仅列出 Activity 状态)。有关这些界面状态的详细信息,请阅读下文。
JankStats 示例
https://github.com/android/performance-samples/tree/main/JankStatsSample
真实数据
应用状态
val scrollListener = object : RecyclerView.OnScrollListener() {
override fun onScrollStateChanged(recyclerView: RecyclerView,
newState: Int)
{
val metricsState = metricsStateHolder?.state ?: return
when (newState) {
RecyclerView.SCROLL_STATE_DRAGGING -> {
metricsState.addState("RecyclerView", "Dragging")
}
RecyclerView.SCROLL_STATE_SETTLING -> {
metricsState.addState("RecyclerView", "Settling")
}
else -> {
metricsState.removeState("RecyclerView")
}
}
}
}
资源
https://developer.android.google.cn/jetpack/androidx/releases/metrics#1.0.0-alpha01
https://developer.android.google.cn/studio/profile/jankstats
https://github.com/android/performance-samples/tree/main/JankStatsSample
https://issuetracker.google.com/issues/new?component=1109743&template=1621342
Alpha -> 1.0
获取 JankStats 1.0.0-alpha01
https://developer.android.google.cn/jetpack/androidx/releases/metrics#1.0.0-alpha01
提交反馈
https://issuetracker.google.com/issues/new?component=1109743&template=1621342
推荐阅读