Office Word 是如何根据字体的 OS/2 表等信息计算「单倍行距」的

2023-10-08 01:30

本文主要是介绍Office Word 是如何根据字体的 OS/2 表等信息计算「单倍行距」的,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

以 Office 2013 附带的 华文中宋 为例计算默认行高 [1]:
  • 按苹果最初为 TrueType 设计的 hhea 规则
    ( hhea.ascent + hhea.descent + hhea.lineGap ) / head.unitsPerEm 
    
    计算得 1.325(华文中宋在 Pages 中的效果符合此数值);
  • 按 OpenType 规范的 sTypo 规则
    ( OS/2.sTypoAscender + OS/2.sTypoDescender + OS/2.sTypoLineGap )/ head.unitsPerEm 
    
    计算得 1.144;
  • 按 Windows 里最主流但不符合规范的 usWin 规则
    ( OS/2.usWinAscent + OS/2.usWinDescent ) / head.unitsPerEm
    
    计算得 1.137。
以上三个结果都与  Word 2013  里的「单倍行距」效果(似乎是一个介于 1.47 与 1.48 之间的数值,且「如果定义了文档网格,则对齐到网格」已关闭)不一致。

那么,Word 是如何计算并实现「单倍行距」的呢?

另外, Word for Mac 2011  里的「单倍行距」似乎和 Windows 版 Word 里的数值并不一致,和 Pages 也不一样。它仿佛是这样计算的,完全忽略 hhea.lineGap 数值,又自己给乘上 1.3,不符合任何规范或事实标准:
( hhea.ascent + hhea.descent ) / head.unitsPerEm * 1.3
这是造成同一文件在 Windows 与 Mac 版 Word 及 Pages 中开启时版式不一致的原因之一吗?

[1] 下附用 ttx dump 出的华文中宋相关数据供参考(若代码未高亮请尝试展开补充说明):
<head><!-- Most of this table will be recalculated by the compiler --><tableVersion value="1.0"/><fontRevision value="1.0"/><checkSumAdjustment value="0xb611830c"/><magicNumber value="0x5f0f3cf5"/><flags value="00000000 00000011"/><unitsPerEm value="1000"/><created value="Fri Jul 17 10:51:22 1998"/><modified value="Wed Oct 30 08:28:00 2002"/><xMin value="-186"/><yMin value="-318"/><xMax value="1317"/><yMax value="1007"/><macStyle value="00000000 00000000"/><lowestRecPPEM value="14"/><fontDirectionHint value="1"/><indexToLocFormat value="1"/><glyphDataFormat value="0"/>
</head><hhea><tableVersion value="1.0"/><ascent value="1007"/><descent value="-318"/><lineGap value="0"/><advanceWidthMax value="1365"/><minLeftSideBearing value="-186"/><minRightSideBearing value="-186"/><xMaxExtent value="1317"/><caretSlopeRise value="1"/><caretSlopeRun value="0"/><caretOffset value="0"/><reserved0 value="0"/><reserved1 value="0"/><reserved2 value="0"/><reserved3 value="0"/><metricDataFormat value="0"/><numberOfHMetrics value="25185"/>
</hhea><OS_2><version value="1"/><xAvgCharWidth value="492"/><usWeightClass value="400"/><usWidthClass value="5"/><fsType value="00000000 00001000"/><ySubscriptXSize value="100"/><ySubscriptYSize value="100"/><ySubscriptXOffset value="0"/><ySubscriptYOffset value="150"/><ySuperscriptXSize value="100"/><ySuperscriptYSize value="100"/><ySuperscriptXOffset value="0"/><ySuperscriptYOffset value="650"/><yStrikeoutSize value="100"/><yStrikeoutPosition value="250"/><sFamilyClass value="0"/><panose><bFamilyType value="2"/><bSerifStyle value="1"/><bWeight value="6"/><bProportion value="0"/><bContrast value="4"/><bStrokeVariation value="1"/><bArmStyle value="1"/><bLetterForm value="1"/><bMidline value="1"/><bXHeight value="1"/></panose><ulUnicodeRange1 value="00000000 00000000 00000010 10000111"/><ulUnicodeRange2 value="00001000 00001111 00000000 00000000"/><ulUnicodeRange3 value="00000000 00000000 00000000 00000000"/><ulUnicodeRange4 value="00000000 00000000 00000000 00000000"/><achVendID value="SINO"/><fsSelection value="00000000 01000000"/><fsFirstCharIndex value="32"/><fsLastCharIndex value="65509"/><sTypoAscender value="800"/><sTypoDescender value="-200"/><sTypoLineGap value="144"/><usWinAscent value="912"/><usWinDescent value="225"/><ulCodePageRange1 value="00000000 00000100 00000000 10011111"/><ulCodePageRange2 value="11011111 11010111 00000000 00000000"/>
</OS_2>

作者:VinnyXiong 链接:http://www.zhihu.com/question/23349103/answer/24328488 来源:知乎 著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。
下图为“华文中宋”字体“国”字,用的是FontCreater7.5,相应的字体参数已经标明。 通过在Word中手工测量(字体设置为200磅,放大到500%,测量像素然后转为twips,再计算),以及使用FontCreater修改字体参数,发现了一些规律:
  1. Word中的字体高度仅取决于 WinAscent WinDescent 两个值。
  2. 测量发现的高度总是大于 ( WinAscent + WinDescent ),说明Word在此基础上有扩展的高度 Extend
  3. 多次测试不同字体以及不同字号之后发现,实际高度 LineHeight (WinAscent + WinDescent) 之间存在一个可能是固定的比例关系,大约在 1.29 ~ 1.31 之间,即 LineHeight = ( WinAscent + WinDescent ) * 1.3
  4. 通过FontCreater修改 WinAscent 或 WinDescent 之后发现,扩展的Extend是平均分配到上面和下面的,Extend1 与 Extend2 相等,如上图所示。
    LineHeight = ( WinAscent + WinDescent ) * 1.3= ( WinAscent + WinDescent ) + ( WinAscent + WinDescent ) * 0.3= ( WinAscent + WinDescent ) + Extend1 + Extend2= ( WinAscent + WinDescent ) + Extend * 2Extend = ( WinAscent + WinDescent ) * 0.15
    
  5. 对于以上计算出的系数 0.15 目前没有确切的值,可能有偏差,还可能跟不同的字体有关。通过程序验证之后得到可能比较精确的值如下:
    第一种:0.14845,适用于 仿宋、宋体、幼圆、新宋体、方正姚体、方正舒体、楷体、隶书、黑体。
    第二种:0.15002,适用于 华文中宋、华文仿宋、华文宋体、华文新魏、华文楷体、华文琥珀、华文细黑、华文行楷、华文隶书、华文彩云、宋体-方正超大字符集、微软雅黑。

这篇关于Office Word 是如何根据字体的 OS/2 表等信息计算「单倍行距」的的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/161793

相关文章

Python自动化Office文档处理全攻略

《Python自动化Office文档处理全攻略》在日常办公中,处理Word、Excel和PDF等Office文档是再常见不过的任务,手动操作这些文档不仅耗时耗力,还容易出错,幸运的是,Python提供... 目录一、自动化处理Word文档1. 安装python-docx库2. 读取Word文档内容3. 修改

Python如何实现PDF隐私信息检测

《Python如何实现PDF隐私信息检测》随着越来越多的个人信息以电子形式存储和传输,确保这些信息的安全至关重要,本文将介绍如何使用Python检测PDF文件中的隐私信息,需要的可以参考下... 目录项目背景技术栈代码解析功能说明运行结php果在当今,数据隐私保护变得尤为重要。随着越来越多的个人信息以电子形

使用Python快速实现链接转word文档

《使用Python快速实现链接转word文档》这篇文章主要为大家详细介绍了如何使用Python快速实现链接转word文档功能,文中的示例代码讲解详细,感兴趣的小伙伴可以跟随小编一起学习一下... 演示代码展示from newspaper import Articlefrom docx import

Python如何计算两个不同类型列表的相似度

《Python如何计算两个不同类型列表的相似度》在编程中,经常需要比较两个列表的相似度,尤其是当这两个列表包含不同类型的元素时,下面小编就来讲讲如何使用Python计算两个不同类型列表的相似度吧... 目录摘要引言数字类型相似度欧几里得距离曼哈顿距离字符串类型相似度Levenshtein距离Jaccard相

Java使用POI-TL和JFreeChart动态生成Word报告

《Java使用POI-TL和JFreeChart动态生成Word报告》本文介绍了使用POI-TL和JFreeChart生成包含动态数据和图表的Word报告的方法,并分享了实际开发中的踩坑经验,通过代码... 目录前言一、需求背景二、方案分析三、 POI-TL + JFreeChart 实现3.1 Maven

电脑没有仿宋GB2312字体怎么办? 仿宋GB2312字体下载安装及调出来的教程

《电脑没有仿宋GB2312字体怎么办?仿宋GB2312字体下载安装及调出来的教程》仿宋字体gb2312作为一种经典且常用的字体,广泛应用于各种场合,如何在计算机中调出仿宋字体gb2312?本文将为您... 仿宋_GB2312是公文标准字体之一,仿China编程宋是字体名称,GB2312是字php符编码标准名称(简

C#实现系统信息监控与获取功能

《C#实现系统信息监控与获取功能》在C#开发的众多应用场景中,获取系统信息以及监控用户操作有着广泛的用途,比如在系统性能优化工具中,需要实时读取CPU、GPU资源信息,本文将详细介绍如何使用C#来实现... 目录前言一、C# 监控键盘1. 原理与实现思路2. 代码实现二、读取 CPU、GPU 资源信息1.

在C#中获取端口号与系统信息的高效实践

《在C#中获取端口号与系统信息的高效实践》在现代软件开发中,尤其是系统管理、运维、监控和性能优化等场景中,了解计算机硬件和网络的状态至关重要,C#作为一种广泛应用的编程语言,提供了丰富的API来帮助开... 目录引言1. 获取端口号信息1.1 获取活动的 TCP 和 UDP 连接说明:应用场景:2. 获取硬

使用Python实现在Word中添加或删除超链接

《使用Python实现在Word中添加或删除超链接》在Word文档中,超链接是一种将文本或图像连接到其他文档、网页或同一文档中不同部分的功能,本文将为大家介绍一下Python如何实现在Word中添加或... 在Word文档中,超链接是一种将文本或图像连接到其他文档、网页或同一文档中不同部分的功能。通过添加超

SpringBoot使用Apache Tika检测敏感信息

《SpringBoot使用ApacheTika检测敏感信息》ApacheTika是一个功能强大的内容分析工具,它能够从多种文件格式中提取文本、元数据以及其他结构化信息,下面我们来看看如何使用Ap... 目录Tika 主要特性1. 多格式支持2. 自动文件类型检测3. 文本和元数据提取4. 支持 OCR(光学