措施
1、避免图层混合
- 确保控件的
opaque
属性设置为true
,确保backgroundColor
和父视图颜色一致且不透明 - 如无特殊需要,不要设置低于1的
alpha
值 - 确保
UIImage
没有alpha通道
2、避免临时转换
- 确保图片大小和
frame
一致,不要在滑动时缩放图片 - 确保图片颜色格式被GPU支持,避免劳烦CPU转换
3、慎用离屏渲染
- 绝大多数时候离屏渲染会影响性能
- 重写
drawRect
方法,设置圆角、阴影、模糊效果,光栅化都会导致离屏渲染 - 设置阴影效果是加上阴影路径
- 滑动时若需要圆角效果,开启光栅化
UIView与CALayer
在iOS系统中所有显示的视图都是从基类UIView继承而来的,同时UIView负责接收用户交互。但是实际上你所看到的视图内容,包括图形等,都是由UIView的一个实例图层属性来绘制和渲染的,那就是CALayer。
CALayer类的概念与UIView非常类似,它也具有树形的层级关系,并且可以包含图片文本、背景色等。它与UIView最大的不同在于它不能响应用户交互,可以说它根本就不知道响应链的存在,它的API虽然提供了“某点是否在图层范围内的方法”,但是它并不具有响应的能力。
在每一个UIView实例当中,都有一个默认的支持图层,UIView负责创建并且管理这个图层。实际上这个CALayer图层才是真正用来在屏幕上显示的,UIView仅仅是对它的一层封装,实现了CALayer的delegate,提供了处理事件交互的具体功能,还有动画底层方法的高级API。
可以说CALayer是UIView的内部实现细节。
圆角与离屏渲染
总结
- 如果能够只用 cornerRadius 解决问题,就不用优化。
- 如果必须设置 masksToBounds,可以参考圆角视图的数量,如果数量较少(一页只有几个)也可以考虑不用优化。
- UIImageView 的圆角通过直接截取图片实现,其它视图的圆角可以通过 Core Graphics 画出圆角矩形实现。
设置圆角很简单,它不会带来任何性能损耗
view.layer.cornerRadius = 5
这行代码不会产生额外的性能损耗。在默认情况下,这个属性只会影响视图的背景颜色和 border。对于 UILabel 这样内部还有子视图的控件就无能为力了。所以很多情况下我们会看到这样的代码:
label.layer.cornerRadius = 5
label.layer.masksToBounds = true
正确的做法是对于UIView,自己画一个带圆角的背景图,创建一个imageView插入到视图底层。对于UIImageView来说是直接截取图片,然后圆角路径直接用贝塞尔曲线绘制,这样来生成一个复合图片。
1.内存恶鬼drawRect
2.iOS 高效添加圆角效果实战讲解
3.性能调优实战
4.iOS 保持界面流畅的技巧
5.iOS Core Animation: Advanced Techniques中文译本
6.使用 ASDK 性能调优 - 提升 iOS 界面的渲染性能