LayoutNG

LayoutNG 是一款经过多年努力打造的全新布局引擎,计划在 Chrome 76 中发布。我们即将推出多项令人兴奋的改进,并将推出更多性能提升和高级布局功能。

最新资讯

  1. 改进了性能隔离。
  2. 更好地支持非拉丁字母。
  3. 修复了与浮动和边距相关的许多问题。
  4. 修复了大量网络兼容性问题。

请注意,LayoutNG 将分阶段发布。在 Chrome 76 中,LayoutNG 用于内嵌布局和块布局。其他布局基元(例如表格、Flexbox、网格和块碎片化)将在后续版本中替换。

对开发者可见的更改

虽然对用户可见的影响应该很小,但 LayoutNG 会以非常细微的方式更改某些行为、修复数百项测试,并改进与其他浏览器的兼容性。尽管我们已尽最大努力,但这可能会导致某些网站和应用的呈现或行为略有不同。

性能特性也完全不同;虽然整体性能与之前大致相同或略有提升,但某些用例可能会出现性能提升,而其他用例预计会出现一定程度的性能回归,至少在短期内如此。

浮点数

LayoutNG 重新实现了对浮动元素 (float: left;float: right;) 的支持,修复了与浮动元素相对于其他内容的放置相关的许多正确性问题。

存在内容叠加的问题

旧版浮动实现在将内容放置在浮动元素周围时未正确考虑边距,导致内容与浮动元素部分或完全重叠。当图像位于段落旁边时,此 bug 最常见的表现形式是,避让逻辑未考虑到行高。(请参阅 Chromium bug #861540。)

顶部文字行叠加显示在浮动图片上
图 1a,旧版布局引擎
文本与右侧的浮动图片重叠
左侧显示正确的文本,右侧显示浮动图片
图 1b,LayoutNG
文本位于右侧浮动图片旁边

同一行中也可能会出现同样的问题。以下示例展示了一个浮动元素后面紧跟着一个负边距的块元素 (#895962)。文本不应与浮动元素重叠。

文本行叠加在橙色框上
图 2a,旧版布局引擎
文本与悬浮的橙色元素重叠
橙色框右侧显示正确的文本
图 2b,LayoutNG
文本位于悬浮的橙色元素旁边

格式化上下文定位

当用于构成块格式设置上下文的元素在浮动元素旁边调整大小时,旧版布局引擎会尝试调整块的大小固定次数,然后才会放弃。这种方法会导致不可预测且不稳定的行为,并且与其他实现不一致。在 LayoutNG 中,在调整块大小时会考虑所有浮点值。(请参阅 Chromium bug #548033。)

绝对定位和固定定位现在更符合 W3C 规范,并且与其他浏览器中的行为更相符。这两种方法之间的差异最明显体现在以下两种情况下:

  • 多行内嵌包含块
    如果绝对定位的包含块跨越多行,旧版引擎可能会错误地仅使用部分行来计算包含块边界。
  • 纵向写入模式
    旧版引擎在将非流式元素放置在纵向写入模式的默认位置时会遇到许多问题。如需详细了解改进后的手写模式支持,请参阅下一部分。

从右到左 (RTL) 语言和纵向书写模式

LayoutNG 从一开始就设计为支持垂直书写模式和 RTL 语言,包括双向内容。

双向文本

LayoutNG 支持 Unicode 标准定义的最新双向算法。此更新不仅修复了各种渲染错误,还包含缺少的功能,例如对配对括号的支持(请参阅 Chromium bug #302469)。

正交流

LayoutNG 提高了垂直流布局的准确性,例如绝对定位对象的放置和正交流布局盒的大小(尤其是在使用百分比时)。在 W3C 测试套件中的 1,258 项测试中,103 项在旧版布局引擎中失败的测试在 LayoutNG 中通过了测试。

固有大小调整

现在,当某个块在正交写入模式下包含子项时,系统会正确计算固有尺寸。

文本布局和换行

旧版 Chromium 布局引擎会逐个元素、逐行布局文本。这种方法在大多数情况下都很有效,但需要额外增加很多复杂性才能支持脚本并实现良好的性能。它还容易出现测量不一致的情况,导致根据内容调整大小的容器及其内容的尺寸存在细微差异,或者出现不必要的行分隔符。

在 LayoutNG 中,文本会在段落级别进行排版,然后拆分为行。这样可以实现更好的性能、更高质量的文本渲染以及更一致的行断开。下面详细介绍了最显著的差异。

跨元素边界联接

在某些脚本中,相邻的某些字符在视觉上可以连接起来。请查看以下阿拉伯语示例:

在 LayoutNG 中,即使字符位于不同的元素中,联接现在也能正常运行。 即使应用了不同的样式,联接也会保留下来。(请参阅 Chromium bug #6122。)

字符是语言书写系统的最小单元。例如,在英语和其他使用拉丁字母的语言中,每个字母都是一个字符。

下图分别显示了以下 HTML 在旧版布局引擎和 LayoutNG 中的呈现效果:

<div>&#1606;&#1587;&#1602;</div>
<div>&#1606;&#1587;<span>&#1602;</span></div>
左侧为正确的字符,右侧为分离的错误呈现
图 3a,旧版布局引擎
请注意第二个字母的形式如何变化
显示了正确的组合字符图元
图 3b,LayoutNG
这两个版本现在完全相同

中文、日文和韩文 (CJK) 连字符

虽然 Chromium 已支持连字符并默认启用连字符,但存在一些限制:由于渲染优化,旧版布局引擎不支持涉及多个 CJK 代码点的连字符。LayoutNG 会移除这些限制,并且无论脚本如何,都支持连字符。

以下示例展示了使用 Adobe SourceHanSansJP 字体渲染三个任意连字符:

中间字符组合未形成连字符
图 4a,旧版布局引擎
MHz 正确地形成了连字符
但 マンション 和 10 点 没有形成连字符
显示了正确的连字符
图 4b,LayoutNG
所有三个组都按预期形成了连字符

按内容调整大小的元素

对于根据内容调整大小的元素(例如内嵌块),当前布局引擎会先计算块的大小,然后再对内容执行布局。在某些情况下(例如当字体强制调整间距时),这可能会导致内容大小与块大小不一致。在 LayoutNG 中,由于块的大小是根据实际内容确定的,因此已消除此失败模式。

以下示例展示了一个大小随内容而变化的黄色块。它使用 Lato 字体,该字体使用字形间距来调整 T 和 - 之间的间距。黄色方框的边界应与文本的边界一致。

文本容器末尾显示的尾随空格
图 5a,旧版布局引擎
请注意最后一个 T 后面的尾随空格
文本边界没有多余的空格
图 5b,LayoutNG
请注意框的左侧和右侧边缘如何与文本的边界相匹配

换行

与上述问题类似,如果按内容调整大小的块的内容大于(宽于)该块,内容有时可能会不必要地换行。这种情况很少见,但对于混合方向的内容,有时也会发生。

显示过早的行断开导致多余空格
图 6a,旧版布局引擎
请注意右侧不必要的行分隔符和额外的空格
不显示不必要的空格或换行
图 6b,LayoutNG
请注意框的左侧和右侧边缘如何与文本的边界相匹配

更多信息

如需详细了解 LayoutNG 修复的具体兼容性问题和 bug,请参阅上面链接的问题,或在 Chromium bug 数据库中搜索标记为 Fixed-In-LayoutNG 的 bug。

如果您怀疑 LayoutNG 可能导致了网站出现问题,请提交 bug 报告,我们会进行调查。