h5渲染性能一瞥


内容来源:2018 年 6 月 30 日,饿了么前端主管向勇在“饿了么技术沙龙・第27弹 【前端专场】”进行《h5渲染性能一瞥》演讲分享。IT 大咖说(微信id:itdakashuo)作为独家视频合作方,经主办方和讲者审阅授权发布。

阅读字数:2488 | 7分钟阅读

获取嘉宾演讲视频及PPT:http://suo.im/4SkvOx

摘要

前端性能按照类型来分主要分为加载性能和渲染性能。加载性能对于首屏的展示及其重要,而渲染性能对于页面加载完成后的交互体验极其重要。但目前绝大部分同学在提到前端性能的优化时都会默认等同于对加载性能的优化,而忽略了渲染性能。本次议题就从几个比较常见的角度聊聊开发中会无意识碰到的渲染性能问题。

H5 VS Native

在将H5和native进行对比的时候,我们通常能想到的一点就是“快”,H5相对于native开发和上线都会快一些,一般的活动页面和非关键页面更多的倾向于H5来开发。

当然H5也有相应的缺点,它的加载和操作会慢一些,抽象来看就是性能问题。加载慢对应的是加载性能,操作慢对应的是渲染性能。加载性能可被定义为页面首次加载时候的性能,这方面的优化方案主要有静态资源压缩、懒加载、雪碧图、CDN、server push等。

渲染性能可被定义为页面进行操作/交互时候的性能,对于这方面的优化可能并不太容易想到。我在面试的时候也经常会问面试者关于性能优化的问题,不过大部分提到的优化方案都是关于加载性能,少部分会提到GPU加速,相对来说这部分同学的CSS技能会高一些。

渲染

一般一次渲染都会经过JavaScript > style > layout > paint > compoasite这样的过程。在做动画的时候可以进行优化,将layout和paint省略掉,这其实是将做动画的元素提升为一个单独的层。

渲染性能的优化可以针对渲染过程中的每一步来做,下面列出了google开发者论坛中提到的具体优化措施

  • 优化JS执行(JS)

  • 缩小样式计算的范围并降低其复杂性(style)

  • 避免大型、复杂的布局和布局抖动(layout、paint)

  • 使用输入处理程序去除抖动(layout、paint)

  • 坚持仅合成器的属性和管理层技术(composite)

  • 简化绘制的复制度、减小绘制区域(paint、composite)

层的优化

上面加粗的两个优化手段可以总结为层的优化,也就是开启GPU加速。这里我们先假设一个场景,在一个页面中存在两个水平排列的元素1、2,他们分别位于左右两端,我们要做的是将1移动到2的位置。对此最简单的方案是设置position并改变right或left的值。第二种方式是使用transform:translateX,并加上 will-change: transform/transform: translate(0)将它提升为单独的层,这种方案的好处在于启用了GPU加速。

这样看来只要应用GPU加速就能很好的解决动画优化问题,但是实际应用中的页面往往要比上面所描述的场景复杂的多。就拿饿了么的H5页面来说,它除了有轮播外还涉及到页面滚动、点击展开,返回顶部等。当开启layer borders查看时会发现滑动的过程中如果轮播图正在播放整个页面就会创建很多不必要的层。另外开启Paint flashing查看重绘情况时也会发现每次轮播图播放都会导致整个页面重绘。这种问题在低端手机上可能会造成闪屏,需要额外注意。解决方案其实前面也提到过就是要将做动画的元素提升为一个单独的层(合成层)

之前说过动画的问题有两种解决方案,如果这两个方案结合在一起又会怎么样呢,也就是将position和will-change写在同一个元素上,这在实际写代码的过程中是很容易碰到的。由此引出了新的问题,浮动元素(渲染层)和合成层的关系。对此我个人做了下总结:若合成层的z-index值小于下方兄弟元素,且他们有重叠,则下方兄弟元素也会被提升为合成层。

上图是饿了么页面的简化场景,区域1是可滑动动画区,使用flex布局实现,区域2是店铺列表,区域3是店铺信息,这两个区域都添加了position:relative。

这种实现方式没有指定浮动层的z-index值,因此在区域1进行滑动的时候,下方的每个店铺列表都会被提升为单独的层。在为区域1设置position:relative和z-index:1(高于下层)之后下方的层就不会再被提升了(此时下层z-index未设置)。

层爆炸

注意图中标记区域,当点击展开/收起活动的小三角的时候会有一个旋转180度的交互效果,相信大家对此都很熟悉。这种效果实现起来也很简单,设置transition过渡属性就能完成。

在实际操作的时候查看层级会发现,每个商店列表都被提升成单独的层且有很多嵌套。造成此问题的原因和前面的案例类似,主要还是没有给拥有过渡动画效果的小三角元素添加z-index值,解决方案同样是为动画元素设置z-inde。

这一系列的问题涉及到一个概念:层压缩,即如果多个渲染层同一个合成层重叠时候,这些渲染层会被压缩到一个GraphicsLayer中。

另外如果元素有动画/过渡效果,可未指定层级顺序高于下方浮动层,此时会假定下方的浮动层在动画期间会受影响,从而无法被压缩。

减少绘制区域

一般我们编写页面的时候都会为头部和底部设置固定浮动,这涉及到减少绘制区域的优化策略。在没有设置浮动的情况下,每次页面滚动头部和底部就会被重新渲染,解决方案是设置浮动后将这些浮动的头部和底部提升为单独的层。


本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/367144.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

爬虫系列之requests

爬取百度内容: 1 import requests2 url "https://www.baidu.com"3 4 if __name__ __main__:5 try:6 kv {user-agent: Mozilla/5.0}7 r requests.get(url, headerskv)8 r.raise_for_status() #返回状态值,如果…

如何使用JSON和Servlet创建JQuery DataTable

在本文中,我将介绍使用简单servlet传递的JSON创建JQuery DataTable所需的基本编码。 DataTable是基于JQuery的非常强大的网格,具有高级功能,可以使用自定义功能在短时间内构建。 安装 下载最新的JQuery DataTable下载 上面的下载将提供两个…

页面重绘 回流及其优化

在讨论页面重绘、回流之前。需要对页面的呈现流程有些了解,页面是怎么把html结合css等显示到浏览器上的, 下面的流程图显示了浏览器对页面的呈现的处理流程。可能不同的浏览器略微会有些不同。但基本上都是类似的。 1. 浏览器把获取到的HTML代码解析成1…

Servlet异常和错误处理示例教程

有时我写了一篇有关Java异常处理的文章,但是当涉及到Web应用程序时,我们需要的不仅仅是Java中的异常处理。 Servlet异常 如果您注意到,doGet()和doPost()方法将抛出ServletException和IOExcept…

python数据结构与算法13_python 数据结构与算法 (13)

python 数据结构与算法 (13)选择排序 (Selection sort) 是? 种简单直观的排序算法. 它的? 作原理如 下.? 先在未排序序列中找到最?(?)元素, 存放到排序序列的起始位 置, 然后, 再从剩余未排序元素中继续寻找最?(?)元素, 然后放到已排 序序列的末尾. 以此类推, 直到所有元…

小程序如何发红包

咳咳,直入主题。敲黑板,请看下面一段对话。 产品:我想要小程序发红包这个功能 程序员:目前不支持啊 产品:我不管! 程序员:做不到啊,这。。。 产品:我不管!我不…

如何实现REST资源的输入验证

如何实现REST资源的输入验证 我正在使用的SaaS平台具有一个RESTful接口,该接口可以接受XML有效负载。 实施REST资源 对于像我们这样的Java商店,使用JAX-B从XML Schema生成JavaBean类是有意义的。 在像Jersey的JAX-RS环境中,使用JAX-B处理X…

Linux系统下,MySQL以及禅道的安装/卸载

1、MySQL卸载: (通过yum命令卸载之前安装的mysql, find命令找到mysql文件,再用rm –rf 强制删除/var/lib/mysql) 2、MySQL安装: (使用yum命令安装mysql,安装完成后启动数据库&#x…

winform 点击全选

代码如下: #region 全选//chkAll_Checked即全选控键的点击事件private void chkAll_CheckedChanged(object sender, EventArgs e){if (chkAll.Checked){chkSun.Checked true;chkMon.Checked true;chkThu.Checked true;chkTue.Checked true;chkWed.Checked true…

今天的考核题目: 你知道React和Vue的区别吗? skr,skr

React 和 Vue 的区别 博主面了几家公司,看简历上写着使用Vue.js框架,就会问,你能说一说 vue 和 react的区别吗 ?react 听过,没用过,所以就只能尴尬的说不怎么了解react。这不,最近刚学了react …

Play和Grails Java框架的优缺点

框架通过为程序员提供一些有用的功能来简化应用程序开发过程。 由于开发人员的普遍使用,Java框架经常被开发人员使用。 您可以在市场上找到各种Java开发框架。 新手开发人员经常在论坛上发布一个常见问题:“哪种Java框架是最好的?” 首先&am…

argb888与rgb888转换程序_一文了解各平台RGB565和RGB888区别

原标题:一文了解各平台RGB565和RGB888区别用过AM335x平台的小伙伴应该知道,OK335xS开发平台的LCD接口是RGB888模式的,而OK335xD开发平台的LCD接口是RGB565模式的。如果把xS的镜像烧写到xD平台上,那么LCD会显示颜色异常。这是为什么…

d4d#9 玩Docker只要浏览器就够了,PWD是个神奇的网站

本文是d4d系列的第9篇,在这一篇中给大家介绍一个学习Docker最为快捷高效的方式,你不需要自己搭建环境,也不用担心把自己的开发环境搞乱,你需要的只是一个浏览器,就可以立即开始学习Docker的常用命令;你甚至…

基于 Docker 打造前端持续集成开发环境

知乎: https://zhuanlan.zhihu.com/p/37961402本文将以一个标准的 Vue 项目为例,完全抛弃传统的前端项目开发部署方式,基于 Docker 容器技术打造一个精简的前端持续集成的开发环境。 前置知识:1. CI(持续集成)&#xf…

哪个内存更快?Heap或ByteBuffer或Direct?

Java正在成为新的C / C ,它被广泛用于开发高性能系统。 对像我这样的数百万Java开发人员来说非常好! 在这个博客中,我将分享我可以用Java完成的不同类型的内存分配实验以及您从中获得的好处。 Java中的内存分配 Java提供哪种类型的内存分配…

java没有打印mysql日志_0216 aop和打印数据库执行日志

需求maven依赖p6spyp6spy3.8.7com.google.guavaguava28.2-jreorg.springframework.bootspring-boot-starter-data-jpaorg.springframework.bootspring-boot-starter-webmysqlmysql-connector-javaruntimeorg.projectlomboklomboktrue打印sql配置要点:驱动配置 appli…

php数组基础

php中,数组的下标可以是整数,或字符串。 php中,数组的元素顺序不是由下标决定,而是由其“加入”的顺序决定。 定义: $arr1 array(元素1,元素2,。。。。。 ); array(1, 5, 1.1, “abc”, tr…

1.格式化输入输出

1.格式化输入input() input()函数,通常只能返回一个数据类型,那么怎么可以进行多个变量的复制呢?看下面这段代码。 1 str1, str2 eval(input("请输入两个字符串:")) 2 print(str1, str2) 3 4 num1, num2 eval(input(…

canvas像素点操作 —— 视频绿幕抠图

原文地址 主要内容 上篇文章学习了canvas像素点的获取 —— 传送门, 今天学一下canvas像素点操作。 一个方法:putImageData putImageData 用法: context.putImageData(imgData, x, y, dX, dY, dWidth, dHeight);参数描述imgData规定要放…

并发编程(一):基础概述

本篇博客主要讲述并发编程中的一些基础内容,并了解一下基本概念。 首先我们了解一下什么是并发? 同时拥有两个或者多个线程,如果程序在单核处理器上运行,多个线程将交替的换入或者换出内存,这些线程是同时“存在”的&a…