美文网首页
iOS 离屏渲染

iOS 离屏渲染

作者: 阿木小丸子 | 来源:发表于2020-07-10 11:41 被阅读0次

1、什么是离屏渲染?

在正常情况下,经过CPU的计算以及GPU的渲染之后,会将结果存放到帧缓存区,随后视图控制器会读取帧缓存区的数据,经过数模转换,再逐行显示到屏幕上。
1.jpeg
并且在GPU渲染的过程中,一般情况下,会遵循‘画家算法’按次序由远及近的一层一层将结果放置到帧缓存区中,当前帧缓存区的数据显示到屏幕上之后,就会将该帧丢弃,周而复始。
@图片来自网络.jpeg
如果我们要对一个多图层的view设置圆角,当我们渲染完图层,要应用一些操作的时候,比如裁剪,之前放置在帧缓存区的数据早已经被丢弃,所以不能同时对多图层进行裁剪操作。
因此,我们需要开辟一些离屏缓存区来存放一些中间状态的数据,等待全部的图层都渲染到离屏缓存区之后,分别从各个离屏缓存区取出数据,分别做相应的操作(裁剪等)之后,组合存入帧缓存区,再等待屏幕控制器的读取和屏幕刷新。(参考HLinzl)
3.jpeg

2、如何检测项目中哪些图层发生了离屏渲染?

我们先看如下的代码:
// 有图片
    UIButton *btn1 = [[UIButton alloc]initWithFrame:CGRectMake(100, 40, 60, 60)];
    [btn1 setImage:[UIImage imageNamed:@"test_icon"] forState:UIControlStateNormal];
    btn1.layer.cornerRadius = 30;
    btn1.clipsToBounds = YES;
    [self.view addSubview:btn1];
    
    // 无图片
    UIButton *btn2 = [[UIButton alloc]initWithFrame:CGRectMake(100, 120, 60, 60)];
    btn2.backgroundColor = [UIColor orangeColor];
    btn2.layer.cornerRadius = 30;
    btn2.clipsToBounds = YES;
    [self.view addSubview:btn2];
    
    // 有背景色 + 图片
    UIImageView *imageV1 = [[UIImageView alloc]initWithFrame:CGRectMake(100, 200, 60, 60)];
    imageV1.backgroundColor = [UIColor blueColor];
    imageV1.image = [UIImage imageNamed:@"test_icon"];
    imageV1.layer.cornerRadius = 30;
    imageV1.layer.masksToBounds = YES;
    [self.view addSubview:imageV1];
    
    // 仅有图片
    UIImageView *imageV2 = [[UIImageView alloc]initWithFrame:CGRectMake(100, 200, 60, 60)];
    imageV2.image = [UIImage imageNamed:@"test_icon"];
    imageV2.layer.cornerRadius = 30;
    imageV2.layer.masksToBounds = YES;
    [self.view addSubview:imageV2];
这写代码是我们平时做项目时会经常用到的,但是这些圆角的设置就一定会发生离屏渲染吗?
接下来,我们在模拟器运行这些代码,打开模拟器的如下设置:
设置.png
看,神奇的现象就出现了!
运行结果.png
上图的第一个和第三个就发生了离屏渲染

3、离屏渲染的利弊:

弊:

(1)离屏渲染需要额外开辟离屏缓冲区的存储空间,加大了系统的负担,会造成性能上的损耗。而存储空间的大小的上限是2.5倍的屏幕像素大小,一旦超过,则无法使用离屏渲染。
(2)一旦因为离屏渲染导致最终存入帧缓存区的时候已经超过了16.67ms,则会出现掉帧的情况。

利:

(1)在我们项目中有一些特殊的效果(比如一些特殊动画效果),需要额外的缓冲区来保存中间状态,不得不使用离屏渲染。
(2)如果某一个效果会多次出现在屏幕上,那么可以提前渲染offscreen Buffer ,来达到复用的目的,这样CPU/GPU就不用做一些重复的计算。

3、离屏渲染的常见触发情况:

(1) 使用了 mask 的 layer (layer.mask)
(2) 需要进行裁剪的 layer (layer.masksToBounds /view.clipsToBounds)
(3) 设置了组透明度为 YES,并且透明度不为 1 的layer (layer.allowsGroupOpacity/ layer.opacity)
(4) 添加了投影的 layer (layer.shadow*)
(5) 采用了光栅化的 layer (layer.shouldRasterize)
(6) 绘制了文字的 layer (UILabel, CATextLayer, Core Text 等)

相关文章

  • iOS离屏渲染

    iOS-离屏渲染详解关于iOS离屏渲染的深入研究关于离屏渲染这两片文章分析的很详细。 渲染过程 根据渲染流水线示意...

  • iOS离屏渲染解析

    iOS离屏渲染解析

  • iOS圆角的离屏渲染,你真的弄明白了吗

    iOS圆角的离屏渲染,你真的弄明白了吗iOS圆角的离屏渲染,你真的弄明白了吗

  • iOS-离屏渲染探索

    iOS项目性能优化时,不得不提到离屏渲染,为了提升性能,我们要求尽量减少离屏渲染的发生。 那,什么是离屏渲染?离屏...

  • iOS离屏渲染的检测和优化

    在iOS离屏渲染介绍了离屏渲染的逻辑和原理,我们知道离屏渲染对于性能会有较大的消耗,那么开发中怎么避免产生离屏渲染...

  • iOS离屏渲染相关值得看的博客

    博客链接 iOS离屏渲染优化 绘制像素到屏幕上 关于iOS离屏渲染的深入研究 https://texturegro...

  • 三、iOS离屏渲染

    iOS离屏渲染 圆角不一定会造成离屏渲染 GPU屏幕渲染方式 On-Screen Rendering 当前屏幕渲染...

  • iOS性能优化之图片圆角

    在Apple官方文档中多次提出开发时,避免触发离屏渲染效果.离屏渲染触发的情况有很多种,具体可参考iOS离屏渲染相...

  • 离屏渲染

    离屏渲染是在iOS开发过程中脱离不了的话题,那么什么是离屏渲染以及哪些情况会导致离屏渲染呢?以及离谱渲染有哪些优势...

  • iOS中的离屏渲染相关

    开场白 本文简单介绍了iOS中离屏渲染的相关内容呢。 1.什么是离屏渲染: 要了解离屏渲染,我们先简单了解一下非离...

网友评论

      本文标题:iOS 离屏渲染

      本文链接:https://www.haomeiwen.com/subject/uzgpcktx.html