我认为没有规定写在任何地方,但希望这可以帮助解决问题:
首先,让我们澄清一些定义。我认为屏幕外渲染与屏幕内渲染并不是大多数情况下最重要的问题,因为屏幕外渲染可以和屏幕内渲染一样快。主要问题是渲染是否在硬件或软件中完成。
使用图层和视图之间的实际区别也很小。视图只是CALayer的一个薄包装器,并且大部分时间它们不会引入显着的性能损失。如果想要拥有由CAShapeLayer或CATileLayer等支持的视图,则可以使用+layerClass方法覆盖所使用的层类型。
通常,在iOS上,像素效果和Quartz / Core Graphics绘图都没有硬件加速,而其他大多数事物都有。
以下内容没有硬件加速,这意味着它们需要通过软件(屏幕外)完成:
在drawRect方法中完成的任何操作。如果您的视图有drawRect方法,即使是空的,绘制也不是在硬件中完成,会产生性能损失。
任何shouldRasterize属性设置为YES的图层。
具有蒙版或投影的任何图层。
文本(任何类型,包括UILabels、CATextLayers、Core Text等)。
您自己完成的任何绘图(无论是在屏幕上还是屏幕外)都使用CGContext。
其他大多数事物都有硬件加速,因此它们更快。但这可能并不是您想象的那样。
与硬件加速绘图相比,上述任何一种绘图都很慢,但它们不一定会减慢您的应用程序,因为它们不需要每帧都发生。例如,在视图上绘制投影首次很慢,但绘制完后会被缓存,并且仅在视图更改大小或形状时重新绘制。
同样的,对于栅格化视图或带有自定义drawRect的视图,该视图通常不会在每一帧中重新绘制,而是绘制一次并缓存起来,因此在视图首次设置后性能不会变差,除非边界发生更改或者调用了setNeedsDisplay。
为了获得良好的性能,关键是避免在每一帧都需要更改的视图中使用软件绘图。例如,如果您需要一个动态矢量形状,则使用CAShapeLayer或OpenGL比使用drawRect和Core Graphics获得更好的性能。但是,如果您只需绘制一次形状,并且不需要更改它,那么这并不会产生太大的影响。
同样地,不要将投影放在动画视图上,因为它会降低帧率。但是,对于从一帧到另一帧不会更改的视图上的阴影效果,影响不会太大。
另一个要注意的问题是不要减慢视图设置时间。例如,假设您有一个文本页面,所有文本都带有投影;由于文本和阴影都需要在软件中渲染,因此初始绘制会花费很长时间,但一旦绘制完成,它就会变得很快。因此,您需要在应用程序加载时提前设置这个视图,并在内存中保留一份副本,以便用户不必等待太久才能看到视图首次出现在屏幕上。
这可能是WWDC视频中表面上矛盾的原因。对于大型、复杂的视图,如果它们不会每一帧都进行更改,则在软件中绘制它们一次(之后将缓存它们,无需重新绘制)将比每一帧都让硬件重新合成它们具有更好的性能,尽管第一次绘制会更慢。
但是对于必须经常重绘的视图,例如表格单元格(单元格会被回收,因此每次一个单元格从屏幕滚动到另一边并作为不同行再次滚回来时都必须重绘),使用软件绘图可能会大大降低性能。