《深入理解Android》一2.1 浏览器工作原理概述

2.1 浏览器工作原理概述

众所周知,万维网(World Wide Web,WWW)以统一资源定位符(Uniform Resource Locator,URL)作为地址空间编码,以超文本传送协议(HyperText Transfer Protocol,HTTP)请求和应答,以超文本标记语言(HyperText Markup Language,HTML)记录并以超链接(hyperlink)互相关联起来的网页(web page)文档作为内容单元,构成了人类有史以来最为庞大的资料信息库。浏览器(browser application)即是专门用来访问和浏览万维网页面的客户端软件,也是现代计算机系统中应用最为广泛的软件之一,其重要性不言而喻。浏览器内部最主要也是最重要的模块是负责页面渲染的排版引擎(layout engine),也可称作浏览器的内核(kernel),其余的部分可统称为浏览器的外壳(browser shell)。
下面将从页面、排版引擎和浏览器外壳应用三个方面对万维网和浏览器技术的基本概念和原理逐一地做简单介绍。

2.1.1 页面

现代Web Page通常由三部分组成:描述页面结构和内容的HTML语言,控制页面动态逻辑的JavaScript脚本,设定页面风格样式的层叠样式表(Cascading Style Sheets,CSS)。
HTML是为创建和描述可在浏览器中展现的网页信息而设计的一种文本格式标记语言,最初于1982年由Tim Berners-Lee创建,后来成为国际标准,由万维网联盟(W3C)维护。HTML由SGML(Standard Generalized Markup Language)简化发展而来,能够结构化地表示文档的构成和内容(如标题、段落、文本、表格),以及一定的外观(如宽、高、颜色)和语义(如注释、链接)。HTML页面由多种尖括号<>包围起来的标签元素以树形结构组成,其顶级标签为,内容标签为

,标签中可内嵌JavaScript脚本和CSS。当前W3C推荐使用的HTML标准有XHTML 1.1、HTML 4.01和HTML 5。
JavaScript是一种内置于浏览器的动态、弱类型、基于原型的网页脚本语言。一般来说,完整的JavaScript应该包括以下几个部分:
ECMAScript:描述了该语言的语法和基本对象;
文档对象模型(DOM):描述处理网页内容的方法和接口;
浏览器对象模型(BOM):描述与浏览器进行交互的方法和接口。
JavaScript的出现使得网页由单纯的静态HTML变成动态可编程的DHTML,开发者可用JavaScript来完成读写DOM,向页面添加交互行为,对浏览器事件做出响应,创建和发起网络请求等许多工作。
层叠样式表(CSS)的发明是为了将网页的内容描述与显示风格的描述分隔出来,HTML中只包含结构和内容的描述信息,CSS则只包含样式的描述信息。单独把一些显示风格信息如字体颜色、背景、排版方式等统一放在CSS文本中,可以大大简化HTML文件,同时增强可读性和修改灵活性。
Web Page一般由前端(front end)开发设计人员直接编写或者由服务器端的脚本动态生成,通过Web服务器以HTTP协议发布,供浏览器访问,这种方式即是通常所说的B/S架构(Browser/Server Architecture)。

2.1.2 内核

浏览器的内核或称排版引擎,负责请求网络页面资源加以解析排版并呈现给用户。从资源的下载到最终的页面展现,可简单地理解成一个线性串联的变换过程的组合,原始输入为URL地址,最终输出为页面Bitmap,中间依次经过了Loader、Parser、Layout和Paint模块,如图2-1所示。

  1. Loader
    Loader模块(如图2-2所示)负责处理所有的HTTP请求以及网络资源的缓存,相当于是从URL输入到Page Resource输出的变换过程。HTML页面中通常有外链的JS/CSS/Image资源,为了不阻塞后续解析过程,一般会有两个IO管道同时存在,一个负责主页面下载,一个负责各种外链资源的下载。

 虽然大部分情况下不同资源可以并发下载异步解析(如图片资源可以在主页面解析显示完成后再被显示),但JS脚本可能会要求改变页面,因此有时保持执行顺序和下载管道后续处理的阻塞是不可避免的。

  1. Parser
    Parser模块主要负责解析HTML页面,完成从HTML文本到HTML语法树再到文档对象树(Document Object Model Tree,DOM Tree)的映射过程。

HTML语法树生成如图2-3所示是一个典型的语法解析过程,可以分成两个子过程:词法解析和语法解析。词法解析按照词法规则(如正则表达式)将HTML文本分割成大量的标记(token),并去除其中无关的字符如空格。语法解析按照语法规则(如上下文无关文法)匹配Token序列生成语法树,通常有自上而下和自下而上两种匹配方式。
浏览器内核中对HTML页面真正的内部表示并不是语法树,而是W3C组织规范的文档对象模型 (Document Object Model,DOM)。DOM也是树形结构,以Document对象为根。DOM节点基本和HTML语法树节点一一对应,因此在语法解析过程中,通常直接生成最终的DOM树。下面这个HTML文档对应的语法树如图2-4所示,而实际构建的DOM树如图2-5所示。

<html>
 <body>
    <p>Hello, World</p>
    <div><img src=”example.png”/><div/>
 </body>
</html>

 不同的页面标签对应不同类型的DOM树节点,如

标签会对应HTMLDiv-Element。DOM节点类型构成一个继承体系,详情可参见WebKit源码中WebCore/dom和WebCore/html两个目录。
页面中所有的CSS由样式表CSSStyleSheet集合构成,而CSSStyleSheet是一系列CSSRule的集合,每一条CSSRule则由选择器CSSStyleSelector部分和声明CSSStyleDeclaration部分构成,而CSSStyleDeclaration是CSS属性和值的Key-Value集合。图2-6显示了某一CSS样式表经过CSSParser解析后在浏览内核中的基本表示。
CSS解析完毕后会进行CSSRule的匹配过程,即寻找满足每条CSS规则Selector部分的HTML元素,然后将其Declaration部分应用于该元素。实际的规则匹配过程会考虑到默认和继承的CSS属性、匹配的效率及规则的优先级等因素。

JavaScript一般由单独的脚本引擎解析执行,它的作用通常是动态地改变DOM树(比如为DOM节点添加事件响应处理函数),即根据时间(timer)或事件(event)映射一棵DOM树到另一棵DOM树。
简单来说,经过了Parser模块的处理,内核把页面文本转换成了一棵节点带CSS Style、会响应自定义事件的Styled DOM树。

  1. Layout
    顾名思义,Layout过程就是排版,它包含两大过程。

步骤1:创建布局树。
布局树(或者叫做渲染树、Render Tree,如图2-7所示)和DOM树大体能一一对应,两者在内核中同时存在但作用不同。DOM树是HTML文档的对象表示,同时也作为JavaScript操纵HTML的对象接口。Render树是DOM树的排版表示,用以计算可视DOM节点的布局信息(如宽、高、坐标)和后续阶段的绘制显示。
 并非所有DOM节点都可视,也就是并非所有DOM树节点都会对应生成一个Render树节点。例如,

标签(HTMLHeadElement节点)不表示任何排版区域,因而没有对应的Render节点。同时,DOM树可视节点的CSS Style就是其对应Render树节点的Style。

步骤2:计算布局。
布局就是安排和计算页面中每个元素大小位置等几何信息的过程。HTML 采用流式布局模型,基本的原则是页面元素在顺序遍历过程中依次按从左至右、从上至下的排列方式确定各自的位置区域。一个HTML元素对应一个以CSS盒子模型(如图2-8所示)描述的方块区域,盒子模型决定了内容、边框和边框内外填充区(Padding、Margin)的大小。HTML元素分成两个基本类型,Inline和Block。Inline元素不会换行,按从左到右来布局。Block元素的出现意味着需要从上至下换到下一行来布局。除了这种基本的顺序按照元素的Inline和Block来进行流式布局之外,还有特殊指定的一些布局方式,如Absolute/Fixed/Relative三种定位布局以及Float浮动布局。简单情况下,布局可以顺序遍历一次Render树完成,但也有需要迭代的情况。当祖先元素的大小位置依赖于后代元素或者互相依赖时,一次遍历就无法完成布局,如Table元素的宽高未明确指定而其下某一子元素Tr指定其高度为父Table高度的30%的情况。

经过了Layout阶段的处理,我们把带Style的DOM树变换成包含布局信息和绘制信息的Render树,接下来的显示工作就交由Paint模块进行操作了。

  1. Paint
    Paint模块负责将Render树映射成可视的图形,它会遍历Render树调用每个Render节点的绘制方法将其内容显示在一块画布或者位图上,并最终呈现在浏览器应用窗口中成为用户看到的实际页面。每个节点对应的大小位置等信息都已经由Layout阶段计算好了,节点的内容取决于对应的HTML元素,或是文本,或是图片,或是UI控件。

通常情况下,布局和绘制是相当耗时的操作。如果DOM树每次略有改动都要重新布局和绘制一次,效率会相当低下。因此,一般浏览内核都会实现一种增量布局和增量绘制的方式。当一个DOM树节点(或者它的子节点)内容或者样式发生变化时,内核会确定其影响范围,在布局阶段会标记出受该节点布局影响的其他节点(比如可能是子节点),在绘制阶段则会标记出一个Dirty区域并通知系统重绘。
按照HTML相关规范,页面元素的CSS属性也规定了其绘制顺序,如根据不同Layer必须按顺序绘制,否则覆盖叠加效果会出现错误,如元素的边框轮廓和内容背景的绘制次序也有规定。
基本上浏览内核的工作原理即如上所述,不同浏览器的具体实现架构不尽相同,所采用的术语名称可能不一样,但都需要完成上述各个阶段的工作。例如,Mozilla Firefox浏览器使用的Gecko排版引擎主要流程如图2-9所示。

2.1.3 外壳

浏览器作为一个完整软件,除了对用户透明和不可见的渲染引擎作为内核外,还需要有供用户交互使用的外壳UI界面,图2-10给出了一个浏览器Shell的基本模块架构。目前的主流浏览器基本都会提供如下功能:
地址栏URI输入;
前进后退和刷新停止的控制按钮;
主页、网络导航和搜索;
历史、书签和下载管理;
多标签页浏览和会话管理;
查找、缩放和全屏;
数据持久化如Cookie、LocalStorage等;
选项设置;
插件和功能扩展。

由于Ajax、HTML 5等前端技术和浏览引擎的迅猛发展,今天的浏览器已经超出了展现某URL上网页内容这一基本功能的范畴,网页可作为绘图、办公、游戏、即时通信等应用的载体。Web App已经成为现实,浏览器也从单一的工具软件向Web OS的方向演进。每一个Web Page或Web App可看成对应于传统操作系统中的一个Native App,排版引擎作为Kernel执行Web App,浏览外壳作为GUI Shell供用户操作使用,多标签浏览器相当于多任务操作系统,Google的Chrome浏览器和由此演变而来的Chrome OS可看作这一想法的实施典型。图2-11描述了Chrome浏览器和WebKit排版引擎之间的层次结构和调用关系,图2-12则给出了Chrome多进程设计的核心架构。

时间: 2024-11-05 03:12:56

《深入理解Android》一2.1 浏览器工作原理概述的相关文章

《深入理解Android》一第2章 浏览器工作原理及WebKit概览

第2章 浏览器工作原理及WebKit概览本章主要内容简述浏览器的工作原理介绍浏览器内核发展史概述WebKit架构第1章为读者说明了Android源码的编译环境本书内容概要,在本章中将阐述万维网技术的基本概念和浏览器的主要工作原理,并简单介绍和对比主流的全功能浏览器内核以及WebKit项目的历史和现状,最后着重描述WebKit内核的架构流程和设计思想.

彻底理解引用在 Android 和 Java 中的工作原理

本文讲的是彻底理解引用在 Android 和 Java 中的工作原理, 几周前,我很荣幸地参加了在波兰举行的 Mobiconf ,移动开发者参加的最好的研讨会之一.我的朋友兼同事 Jorge Barroso 做了个名为"最好(良好)的做法"的演说 ,这让我在听后很有感触: 对于一个 Android 开发者,如果你不使用 WeakReferences,这是有问题的. 举个恰当的例子,几个月前,我发布了我的最后一本书 "Android High Performance"

【技术干货】浏览器工作原理和常见WEB攻击 (上)

本文作者:上海驻云开发总监 陈昂 浏览器工作原理 当你打开一个个设计漂亮.简洁大方的网页,有没有想过浏览器是如何展现这么一个网页的呢.当你在这些网页上输入你的淘宝账号登录购买东西的时候,有没有想过,你的账号密码.身份证号.手机号.真实姓名,这些信息会不会泄露,被黑客利用呢?在了解网络安全方面的知识之前我们先简单了解下浏览器的工作原理,以辅助我们更好的理解网络安全知识. 浏览器分类 现代浏览器从内核上来说,主要分为以下6大类: Trident内核,代表是IE EDGE内核,代表是微软的Edge浏览

【技术干货】浏览器工作原理和常见WEB攻击 (下)

本文作者:上海驻云开发总监 陈昂 上篇给大家带来的是关于浏览器基本工作原理的总结和介绍,这篇文章重点给大家说明有哪些常见WEB攻击. 常见WEB攻击 互联网是个面向全世界的开放平台,越是开放的东西漏洞就越是多.有人曾维护了一个列表,上面有上百种的WEB攻击方式.我们常见的有:脚本注入.SQL注入.DDoS.DNS劫持.端口漏洞扫描.密码暴力破解.XSS.CSRF等.这里只挑一些常见的攻击做个介绍: SQL注入 现在的网站很多都不再是纯粹的静态网站,例如一些CMS网站.交易网站.p2p/p2c网站

深入理解Tomcat系列之六:Servlet工作原理

前言 Servlet是Web开发中的核心技术,作为一名合格的开发人员,就必须清楚Servlet的工作原理.本章没有对Servlet技术本身进行详细的说明,只是针对开发过程中一次Servlet的请求的处理过程进行分析的.Servlet实际上就是一个java类,只不过可以和浏览器进行一些数据的交换.有Servlet类就有管理Servlet的容器,种类有很多,这里主要针对Tomcat对Servlet的工作原理进行说明.为了说清楚Servlet工作原理,需要知道Servlet的工作过程大致可以分为以下几

iOS 和 Android 的后台推送工作原理各是如何?有什么区别?

iOS 的推送iOS 在系统级别有一个推送服务程序使用 5223 端口.使用这个端口的协议源于 Jabber 后来发展为 XMPP ,被用于 Gtalk 等 IM 软件中.所以, iOS 的推送,可以不严谨的理解为:苹果服务器朝手机后台挂的一个 IM 服务程序发送的消息.然后,系统根据该 IM 消息识别告诉哪个 Apps 具体发生了什么事.然后,系统分别通知这些 Apps . 这个消息的内容是这样的:应该说,苹果这种方式在技术上没有什么创新.但是,整个架构是很了不起的. 因为:1 使用久经考验的

《深入理解Android》一2.4 本章小结

2.4 本章小结 本章的目的是希望读者能获得对WebKit组成架构和浏览器工作原理的一个整体理解和认识,并概括出其中的一些关键点(主要对象)和线(核心流程),方便读者自主进行源码分析. 由于WebKit是一个相当庞大复杂的软件系统,代码行数在百万数量级,涉及语法解析.排版布局.图形绘制.硬件加速以及网络.多线程等多方面的算法和技术,期望在一章篇幅内能够完整叙述清楚是不太现实的. 在余下的章节中,我们将分别对WebKit各主要功能模块抽丝破茧,更加深入细致地介绍其算法原理和具体代码实现.

详细解析路由器工作原理

路由器工作原理概述在控制平面上, 路由协议可以有不同的类型.路由器工作原理通过路由协议交换网络的 拓扑结构信息,依照拓扑结构动态生成路由表.在数据通道上,转发引擎从输入线路接收IP包 后,分析与修改包头,使用转发表查找输出端口,把数据交换到输出线路上.转发表是根据路由表生成的,其表项和路由表项有直接对应关系,但转发表的格式和路 由表的格式不同,它更适合实现快速查找.转发的主要流程包括线路输入.包头分析.数据存储.包头修改和线路输出.路由协议根据网 络拓扑结构动态生成路由表.IP协议把整个网络划分

Android开发中通过源码彻底理解ListView工作原理【超详细】

ListView控件是Android应用开发中原生控件中最复杂,但是又相当的重要,当应用程序要处理很多内容而且屏幕无法公完全显示的时候,ListView就可以发挥其作用了,他可以滑动手指就能把超出屏幕的部分内容移动显示到屏幕中. ListView还有一个非常神奇的功能,即使在ListView中加载非常非常多的数据,比如达到成百上千条甚至更多,ListView都不会发生OOM或者崩溃,而且随着我们手指滑动来浏览更多数据时,程序所占用的内存竟然都不会跟着增长.那么ListView是怎么实现这么神奇的