flutter项目优化--渲染优化

基于当前的flutter项目功能基本实现,项目框架结构不清晰,代码耦合严重,重复渲染耗费资源过大等问题影响项目接下去的迭代开发,所以对当前项目先进行重构变得尤为重要。
虽然 Flutter 技术构建的应用程序在默认情况下已经非常高性能,但一开始急于完成项目,并没有就渲染上的性能问题做过多的思考。参考flutter官网,对页面的渲染性能问题需要做如下几点的考虑。

1. 减少build()的耗时

1) 避免在build()方法中执行重复且耗时的工作,因为当父widget重建时,子widget的build()方法会被重复调用
2)避免在build()方法中返回一个超大widget,将widget拆分成多个小widget,各自控制UI的渲染,避免重复渲染一个大的widget。


实践

1) 采用Provider库,分离数据及视图代码,隔绝widget。
2) 将原先在build()方法中的的一些逻辑代码提取到provider model中处理,减少build()后多次执行。
3)将大组件拆分成多个widget小组件。与业务代码耦合的组件采用provider进行数据管理,进而驱动页面UI渲染,独立小组件采用statefullwidget进行各自数据的状态管理。
4)采用Provider库中的shouldRebuild来减少不必要的渲染

Selector>(
                shouldRebuild: (previous, next) {
                  if (previous.item1 != next.item1 && next.item1 != null) {
                    ...
                  }
                  return false;
                },
                selector: ((_, data) => Tuple2(
                    data.frontIdentity,
                    data.backIdentity)),
                builder: (context, data, _) { return ...})

2. 在必要的时候才使用一些效果

类似web开发中css3实现一些3D效果会开启GPU加速渲染,占用过多的资源,flutter中也有相同的问题。
在flutter中实现某些效果会调用性能代价很大的saveLayer()方法。因为调用 saveLayer() 会开辟一片离屏缓冲区。将内容绘制到离屏缓冲区可能会触发渲染目标切换,这些切换在较早期的 GPU 中特别慢。
避免使用一些会触发saveLayer()的widget:

  • 尽量不使用Opacitywidget
  • 使用Clipping时避免使用Clip.antiAliasWithSaveLayer
  • ShaderMask
  • ColorFilter
  • 使用Chip且disabledColorAlpha != oxff 时
  • 使用Text且存在overfloShader时

避免调用 saveLayer() 的方式:

  • 要在图像中实现淡入淡出,请考虑使用 FadeInImage widget,该 widget 使用 GPU 的片段着色器应用渐变不透明度。
  • 要创建带圆角的矩形,而不是应用剪切矩形,考虑使用很多 widget 都提供的 borderRadius属性。

3. 对列表或者网格列表采用懒加载

在构建大型网格或列表时,使用带有回调的惰性方法。这样,只有屏幕的可见部分是在开始时构建的。

ScrollController doneScrollController = ScrollController();
doneScrollController.addListener(() {
      if (doneScrollController.position.pixels ==
              doneScrollController.position.maxScrollExtent &&
          !Provider.of(context, listen: false).isLastPage) {
        Provider.of(context, listen: false).nextPageListData();
      }
    });
ListView.separated(
  itemBuilder: (BuildContext context, int idx) {
    return ...
  },
  separatorBuilder: (BuildContext context, int index) {
    return ...
  },
  itemCount: 50,
  controller: scrollController,
)

你可能感兴趣的:(flutter项目优化--渲染优化)