美文网首页
iOS 离屏渲染

iOS 离屏渲染

作者: fred风飘 | 来源:发表于2020-07-08 00:20 被阅读0次

一、什么是离屏渲染?

首先我们看下正常的图像显示流程:
GPU进⾏渲染->帧缓存区⾥ ->视频控制器->读取帧缓存区信息(位图) -> 数模转化(数字信号处->模 拟型号) ->(逐⾏扫描)显示;

但是,在上诉流程中还存在一种特殊情况,当需要显示的数据不能被视频控制器直接显示的时候,会在帧缓冲区外新开辟一个离屏缓冲区,后续GPU会复用离屏缓冲区的数据,计算完毕后再放入到帧缓冲区等待读取显示

一、那什么情况我们的代码会触发离屏渲染?

我们常会听说,设置圆角会触发离屏渲染。

但此种说法其实是不准确的。

我们先来看看苹果官方文档对于cornerRadius的描述:

Setting the radius to a value greater than 0.0 causes the layer to begin drawing rounded corners on its background. By default, the corner radius does not apply to the image in the layer’s contents property; it applies only to the background color and border of the layer. However, setting the masksToBounds property to true causes the content to be clipped to the rounded corners.

意思:设置cornerRadius仅作用于background和border,不作用于layer’s contents ,除非设置masksToBounds

但设置了masksToBounds就会导致离屏渲染吗?
当然不是!!!

下面我们来看一些测试代码:

 //1.按钮存在背景图片
    UIButton *btn1 = [UIButton buttonWithType:UIButtonTypeCustom];
    btn1.frame = CGRectMake(100, 30, 100, 100);
    btn1.layer.cornerRadius = 50;
    [self.view addSubview:btn1];
    
    [btn1 setImage:[UIImage imageNamed:@"btn.png"] forState:UIControlStateNormal];
    btn1.clipsToBounds = YES;
    
    //2.按钮不存在背景图片
    UIButton *btn2 = [UIButton buttonWithType:UIButtonTypeCustom];
    btn2.frame = CGRectMake(100, 180, 100, 100);
    btn2.layer.cornerRadius = 50;
    btn2.backgroundColor = [UIColor blueColor];
    [self.view addSubview:btn2];
    btn2.clipsToBounds = YES;
    
    //3.UIImageView 设置了图片+背景色;
    UIImageView *img1 = [[UIImageView alloc]init];
    img1.frame = CGRectMake(100, 320, 100, 100);
    img1.backgroundColor = [UIColor blueColor];
    [self.view addSubview:img1];
    img1.layer.cornerRadius = 50;
    img1.layer.masksToBounds = YES;
    img1.image = [UIImage imageNamed:@"btn.png"];
    
    //4.UIImageView 只设置了图片,无背景色;
    UIImageView *img2 = [[UIImageView alloc]init];
    img2.frame = CGRectMake(100, 480, 100, 100);
    [self.view addSubview:img2];
    img2.layer.cornerRadius = 50;
    img2.layer.masksToBounds = YES;
    img2.image = [UIImage imageNamed:@"btn.png"];

打开模拟器的离屏渲染检测工具:


image.png

通过demo我们可以看到,并不是所有的例子都发生了离屏渲染。


image.png

通过案例我们发现,当视图存在内容和背景时发生圆角裁剪,那么此时必定会产生离屏渲染。

image.png

三、解决办法

(1)后台绘制圆角图片,前台进行设置

image image

(2)对于 contents 无内容或者内容的背景透明(无涉及到圆角以外的区域)的layer,直接设置layer的 backgroundColor 和 cornerRadius 属性来绘制圆角。

(3)使用混合图层,在layer上方叠加相应mask形状的半透明layer

sublayer.contents=(id)[UIImage imageNamed:@"xxx"].CGImage;

[view.layer addSublayer:sublayer];

(4)- (UIImage *)yy_imageByRoundCornerRadius:(CGFloat)radius corners:(UIRectCorner)corners borderWidth:(CGFloat)borderWidth borderColor:(UIColor *)borderColor borderLineJoin:(CGLineJoin)borderLineJoin此方法为YY_image处理圆角的方法,你可以去下载YY_image查看源码

其他情况触发离屏渲染以及解决办法:

  1. mask(遮罩)------>使用混合图层,在layer上方叠加相应mask形状的半透明layer

2.edge antialiasing(抗锯齿)----->不设置 allowsEdgeAntialiasing 属性为YES(默认为NO)

  1. allowsGroupOpacity(组不透明,开启CALayer的allowsGroupOpacity属性后,子 layer 在视觉上的透明度的上限是其父 layer 的opacity(对应UIView的alpha),并且从 iOS 7 以后默认全局开启了这个功能,这样做是为了让子视图与其容器视图保持同样的透明度。)------->关闭 allowsGroupOpacity 属性,按产品需求自己控制layer透明度

4.shadows(阴影)------>设置阴影后,设置CALayer的 shadowPath,view.layer.shadowPath=[UIBezierPath pathWithCGRect:view.bounds].CGPath;

CALayer离屏渲染终极解决方案:当视图内容是静态不变时,设置 shouldRasterize(光栅化)为YES(缓存离屏渲染的数据,当下次用到的时候直接拿,不需要开辟新的离屏缓冲区),此方案最为实用方便。view.layer.shouldRasterize = true;view.layer.rasterizationScale = view.layer.contentsScale;

shouldRasterize (光栅华使用建议):

1.如果layer不需要服用,则没有必要打开

2.如果layer不是静态的,需要被频繁修改,比如出于动画之中,则开启光栅华反而影响性能

3.离屏渲染缓存有时间限制,当超过100ms,内容没有被使用就会被丢弃,无法复用

4.离屏渲染缓存有空间限制,超过屏幕像素的2.5倍则失效,并无法使用

特别说明:当内容属于不常被复用的,不建议使用光栅化,开启了后反而会损耗性能

相关文章

  • 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/qevtcktx.html