移动性能测试 android app fps 计算

jack · 2016年02月19日 · 最后由 测试小书童 回复于 2016年10月26日 · 2692 次阅读

下面是个人在学习 FPS 时,求 FPS 的另一个计算方法,发出来是想验证下这个计算方法的合理性以及得到大伙的更多意见。

google说在开发者模式中开启adb shell dumpsys gfxinfo即可看到每一帧的渲染耗时,既然是每一帧,那么就可以用这些数据来计算fps.

1.使用如下命令得出帧数据的时间数组保存结果 times,每次取出的数据都是更新后的。

times = adb shell dumpsys gfxinfo com.tencent.android.qqdownloader

2.命令返回的每一行代表一帧,所以计算帧数量:

frames = len(times)

3.计算每一帧耗费的时间并生成新的数组,单位:s

frame_time = []
for i in times:
    time = i.split()
    sum_time = (float(time[0])+float(time[1])+float(time[2])+float(time[3]))/1000  # android 5.1.1中每一帧有四列数据:Draw  Prepare  Process  Execute
    frame_time.append(sum_time)

4.计算 frames 总共耗费的时间:s

seconds = 0.0
for i in frame_time:
    seconds += i

5.每隔 1s 取一次数据,fps = frames/seconds

6.另一种计算就是每 1s 取出的 frames = len(times) 其实就是这一秒的帧率,比如 1s 中取出 128 行帧,结果就是 128FPS,画面静止没有更新取出是 0 行帧就是 0FPS

上面的计算方法从结果来看觉得有些不对,大家有什么看法?

共收到 13 条回复 时间 点赞

额。计算方法中规中矩,都是从 gfx 里面去拿的,这种方式唯一可能不靠谱的地方在于,人工操作会影响结果的准确性。

2楼 已删除

#1 楼 @monkey 你是指人工操作会影响哪部分数据?另外,我是单位时间 1s 取出帧数量/帧绘制耗费的总时间计算出 fps 的,还是说 fps 就是这 1s 取出的帧数量

#3 楼 @x746560359 这个有官方的计算方法的,稍等,我找下。。。

#5 楼 @monkey 这个帖子我看过了,adb shell dumpsys SurfaceFlinger --latency com.tencent.assistantv2.activity.MainActivity 这种方法在我的真机 nexus5/三星 note4(系统都是 5.1.1)上都只返回一行 16666667 数据即系统刷新周期,没有返回一些帧相关数据。而且里面的算法不知道他为什么会那么去算,依据是什么?能否按你理解的说下呢?
对于 service call SurfaceFlinger 1013 这种计算方法已经理解了。但是只能 root 下用。
另外 gfxinfo 貌似不能 dump 出游戏的帧数据,只能是 APP

hmm
一个一个来,adb shell dumpsys surfaceflinger ,你直接这样运行后面跟你应用参数。我之前真机 nexus 是有数据的,就是很长一段 log 下面会有 fps 的数据,但是那个数据一直不变的,我不知道为啥。没有什么参考价值

另外你说 gfxinfo 貌似不能 dump 出游戏的数据,为啥?他应该区分不了这个 app 是不是游戏的。。。还是我木有理解你说的游戏的意思。。@。@。。。

另外 fps 我了下,每秒处理的 fps,应该是 1000/60,60fps 为平滑的标准嘛,然后得出的 16.6ms 的结论
所以我们反推 fps 的话,应该是 1000/消耗时间。

你看看?

#7 楼 @monkey 有段时间没上来了,1000/消耗时间是正解。

#7 楼 @monkey
1.如果按照 1000/消耗时间算,我单位时间 1s 内取出 28 帧,这 28 帧渲染总共耗费 299.89ms,得出结果为 1000/299.89=3fps???
2.基于 unity 游戏 dump 出来的是空的,你可以试试。

#9 楼 @x746560359 unity 的,我现在 build 个看下。。。

#9 楼 @x746560359

我觉得这是其中的一个错误的点。
因为 gfxinfo,其中有一个基线,是 16.6.官方文档如下的:

The green line represents 16 milliseconds. To achieve 60 frames per second, the vertical bar for each frame needs to stay below this 16 ms mark. Any time a bar pushes above this line, there may be pauses in the animations.

那么其实每一根线应该是`execute +process+draw 的,那么其实每根线应该是每秒钟为单位。
所以理论上你拿到的那个数据,一行就是一秒钟的一个数据。1s 28 帧是咋出来的呀。。= =

PS:如果是 M 的话,可以参考这里:http://developer.android.com/training/testing/performance.html

PSS:unity 的确是不行的。。。unity 本身也不是原生方式打包的了。。。。

#9 楼 @x746560359 如果是 1 秒 28 帧,不受干扰应该是 35.7ms
然后用 1000/35.7ms = 28fps
1000/消耗时间没错的

如果是 299.89ms 的话,那么 1000/299.89=3fps 也是对的。

你好,完整代码能借鉴一下吗

楼主,你怎么计算的?
times = adb shell dumpsys gfxinfo com.tencent.android.qqdownloader

2.命令返回的每一行代表一帧,所以计算帧数量:

frames = len(times)

这里能不能说下具体点?

需要 登录 后方可回复, 如果你还没有账号请点击这里 注册