该教程已接近尾声,最后让我们再来讨论一下QML分析器。它是一种用于定位应用程序中性能问题的工具,如速度慢、不响应、界面不流畅等。典型的原因包括在较低的帧率中执行过多的JavaScript。在GUI线程继续之前,所有JavaScript必须返回,如果GUI线程没有准备好,则帧就会延迟或丢弃。
导致类似性能问题的另一个典型原因是创建、绘制或更新不可见项,这在GUI线程中也需要花费时间。
执行耗时的C++函数,如绘图方法和信号处理程序,在GUI线程中也会花费一些时间,但是QML 分析器很难捕获到它们,因为它不能解析C++代码。
若要检查JavaScript是否过度使用,可以查看动画和场景图事件中的帧率,刷新间隔,并检查应用程序的行为是否符合预期。JavaScript显示函数的运行时间,您应该尽量使其保持在每帧16毫秒以下。
若要查找因处理不可见项而导致的问题,请查找丢弃的帧,并检查您是否使用了太多的短绑定或更新每帧时的信号处理器。您还可以通过可视化场景透支图,以检查场景布局并查找不可见项目,因为这些项目位于屏幕之外或隐藏在其他可见元素之下。
如果在JavaScript未运行的情况下仍有帧丢失,并且时间线中存在无法解释的时间间隙,请检查您自定义的QQuickItem
实现。您可以使用Valgrind或其他通用分析器来分析C++代码。
1. 使用QML分析器
使用QML分析器需要为工程设置QML调试,并使用Qt 4.7.4或更高版本(无论如何,你应该在本课程中使用Qt 5,所以这应该不是一个问题)。
在Qt Creator的顶部菜单栏中选择“分析 > QML Profiler”。启动应用程序,并使用“开始”按钮启动数据收集,完成后单击“启用性能分析”(在退出应用程序之前执行此操作)。
2. 分析收集的数据
2.1 时间线
时间线是以图像化方式表示QML和JavaScript执行的视图,以及记录所有事件的压缩视图。
时间线(6)中的每一行描述了一种记录的QML事件类型。将光标移到行上的某个事件上,可以查看它花费了多长时间以及在源代码中调用它的位置。如果只是想在选定事件时显示信息,请禁用“在鼠标悬停时查看事件信息”按钮(4)。
(10)总结了收集数据的时间。拖动缩放范围(8)或单击轮廓以在轮廓上移动。你也可以通过选择“跳转到前一个事件”和“跳转到下一个事件”按钮(1)在事件之间移动。
选择显示缩放滑块按钮(2)打开一个滑块,您可以用它来设置缩放级别。也可以拖动缩放手柄(9)。要重置默认的缩放级别,只需右键单击时间线打开上下文菜单,然后选择重置缩放。
单击时间标尺,将垂直方向线(5)添加到时间线上。
2.2 统计
Statistics视图用于显示触发每个绑定、创建、编译、JavaScript或信号事件的次数和平均花费的时间。这允许您检查需要优化哪些事件。如果出现的事件数量很高,则可能表明不必要地触发了某个事件。要查看事件发生的中间时间、最长时间和最短时间,请在上下文菜单中选择Extended Event Statistics。
单击事件以移动到代码编辑器源代码中的事件。
2.3 火焰图
火焰图视图显示了QML和JavaScript执行的更简明的统计概述。在可视化总时间视图中,水平条显示了相对于所有JavaScript和QML事件的总运行时间,某个函数的所有调用总共花费的时间。嵌套显示了哪些函数被哪些函数调用。
要查看可视化内存视图中函数分配的内存总量,请在下拉菜单(1)中选择“Memory”。
要在可视化分配视图中查看功能执行的内存分配数量,请在下拉菜单(1)中选择“Allocations”。
双击视图中的项目以将其放大。双击视图中的空白区域以再次缩小。
与时间线视图不同,火焰图视图在根本没有运行QML或JavaScript时不会显示时间跨度。因此,它不适合分析每帧执行时间。但是,很容易看出各种QML和JavaScript事件的总体影响。
3. 延伸阅读
想了解更多QML分析器内容,请参见文档。
获取更多信息,请关注作者公众号:程序员练兵场