#1 - 2021-7-31 20:49
NekoNull
最近遇到了一个和 Emoji 相关的奇妙问题,在此分享一下自己的探索过程,以及期望能得到一些指点。
起源是发现 ©️ 这个 Emoji 在不同浏览器中的显示不一样。在 Chrome 系下就是一个单纯的文本字符,但是在 Firefox 中就会显示为一个 Emoji (圆圈内有白色底色)。进一步探索,发现 Emoji 实际上有两种 presentation:text 和 emoji (也称作 pictographic)(Link)。Unicode 中规定了 VS15 和 VS16 (VS=Variation Selector),实际上是两个特殊的 Unicode 码点( U+FE0E 和 U+FE0F),追加在 Emoji 后可以强制指定要显示哪种 presentaion。如果不在 Emoji 字符后追加 VS,那么默认的 presentation 是系统/环境特定的。比较新的 emoji 基本上只有 emoji presentation,但是老的 emoji(包括部分从 wingding 继承过来的),就同时有 text 和 emoji presentation。
(所有 emoji 的 Presentation 展示,网页较大,请用 Firefox 打开,可能导致 Chrome 崩溃。)
然而追加 VS16(即要求使用 emoji presentation),只能解决部分 Emoji 在 Chrome 下调用 text presentation 的问题,有的 Emoji 依然不会调用 emoji presentation。
(前者没有加 VS16,后者加了 VS16)
可以要求调用 emoji: ⛰ ⛰️
不能要求调用 emoji:© ©️
预期:在任何浏览器上,第二个 emoji 都应该以 emoji 图像的形式显示
实际:Firefox 正常,Chrome 系 Copyright 加了 VS16 也不会显示为 emoji。
(工具:Unicode Inspector)
进一步调查,发现可能和浏览器的字体回退机制有关。(Reddit 讨论)具体而言,在 Chrome 上,如果 CSS 里写的是 SYSTEM-UI 的话,Windows 10 下会被解析到 Segoe UI,但这个字体对 Emoji 的支持是不完整的,即便追加了 VS16 也无法解析到 Copyright 这个 emoji 的 emoji presentation,最后回落到了 text presentation。但是在 Firefox 上,对 emoji 有特定处理,emoji 会被解析到 Segoe UI Emoji,从而能正常显示。
(豆知识:如果在网页里用了 Emoji,为了确保 Windows 10 + Chrome 用户能正常显示,请在 CSS 中把 Segoe UI Emoji 放在 SYSTEM-UI 或类似的字体家族之前。 不要这样做,不然文字显示也会受到影响。Segoe UI Emoji 里不仅有 Emoji,也有正常字符。)
到这里逻辑链条似乎都很正常,但是似乎继续深究下去就出现了奇怪的问题。以阴阳(☯,☯️,U+262F)这个 emoji 为例子,如果在 notepad 中直接复制,显示的 glyph (字形) 是一个带黑框,阴阳两点在纵轴的 text presentation。用 FontForge 打开各个字体文件检查,可以发现这个glyph 来自于 Segoe UI Emoji。notepad 默认字体是微软雅黑,但是检查 NT 系统的字体回退机制(Link),可以发现 Microsoft YaHei 这个字体的回退项并不包括 Segoe UI Emoji。所以这个字形到底是怎么被选中的?
希望各位能提供一些思路。
起源是发现 ©️ 这个 Emoji 在不同浏览器中的显示不一样。在 Chrome 系下就是一个单纯的文本字符,但是在 Firefox 中就会显示为一个 Emoji (圆圈内有白色底色)。进一步探索,发现 Emoji 实际上有两种 presentation:text 和 emoji (也称作 pictographic)(Link)。Unicode 中规定了 VS15 和 VS16 (VS=Variation Selector),实际上是两个特殊的 Unicode 码点( U+FE0E 和 U+FE0F),追加在 Emoji 后可以强制指定要显示哪种 presentaion。如果不在 Emoji 字符后追加 VS,那么默认的 presentation 是系统/环境特定的。比较新的 emoji 基本上只有 emoji presentation,但是老的 emoji(包括部分从 wingding 继承过来的),就同时有 text 和 emoji presentation。
(所有 emoji 的 Presentation 展示,网页较大,请用 Firefox 打开,可能导致 Chrome 崩溃。)
然而追加 VS16(即要求使用 emoji presentation),只能解决部分 Emoji 在 Chrome 下调用 text presentation 的问题,有的 Emoji 依然不会调用 emoji presentation。
(前者没有加 VS16,后者加了 VS16)
可以要求调用 emoji: ⛰ ⛰️
不能要求调用 emoji:© ©️
预期:在任何浏览器上,第二个 emoji 都应该以 emoji 图像的形式显示
实际:Firefox 正常,Chrome 系 Copyright 加了 VS16 也不会显示为 emoji。
(工具:Unicode Inspector)
进一步调查,发现可能和浏览器的字体回退机制有关。(Reddit 讨论)具体而言,在 Chrome 上,如果 CSS 里写的是 SYSTEM-UI 的话,Windows 10 下会被解析到 Segoe UI,但这个字体对 Emoji 的支持是不完整的,即便追加了 VS16 也无法解析到 Copyright 这个 emoji 的 emoji presentation,最后回落到了 text presentation。但是在 Firefox 上,对 emoji 有特定处理,emoji 会被解析到 Segoe UI Emoji,从而能正常显示。
(豆知识:如果在网页里用了 Emoji,为了确保 Windows 10 + Chrome 用户能正常显示,请在 CSS 中把 Segoe UI Emoji 放在 SYSTEM-UI 或类似的字体家族之前。 不要这样做,不然文字显示也会受到影响。Segoe UI Emoji 里不仅有 Emoji,也有正常字符。)
到这里逻辑链条似乎都很正常,但是似乎继续深究下去就出现了奇怪的问题。以阴阳(☯,☯️,U+262F)这个 emoji 为例子,如果在 notepad 中直接复制,显示的 glyph (字形) 是一个带黑框,阴阳两点在纵轴的 text presentation。用 FontForge 打开各个字体文件检查,可以发现这个glyph 来自于 Segoe UI Emoji。notepad 默认字体是微软雅黑,但是检查 NT 系统的字体回退机制(Link),可以发现 Microsoft YaHei 这个字体的回退项并不包括 Segoe UI Emoji。所以这个字形到底是怎么被选中的?
希望各位能提供一些思路。
或者说,font link 是否可以理解为生成了一个 virtual font,其中的 glyph 相当于 base font 并上(putIfAbsent)所有存在于 link 列表里的 font?
Font link 列表里好像没有一对多的情况吧,把对应的字体理解为相同字体就可以了。至于字形自然以 link 到的字体为准。
sai 老板对帖子正文(class="topic_content")原始的 font-family 设定是
'SF Pro SC','SF Pro Display','PingFang SC','Lucida Grande','Helvetica Neue',Helvetica,Arial,Verdana,sans-serif,"Hiragino Sans GB";
如果在 Helvetica 前面手动加上 "Segoe UI Emoji",那么就能让 Copyright 正常以 Emoji 形式显示。但是如果在 Helvetica 和 Arial 中间加,就不行。但是我的系统内是没有安装 Helvetica 的,所以不太确定为什么会有这样的行为。
如果需要看完整 emoji 列表,可以用这个连接:https://unicode.org/emoji/charts/full-emoji-list.html
关于 presentation,我之前在 emojipedia 上读到的是所有的 emoji 都有 emoji presentation,部分 emoji 有 text presentation。
(他这里举的例子我这里只有闪电使用了Emoji(Symbol有这个字符吗?),其他都是Symbol,所以我怀疑这个“issue”已经不再存在了?不知道为啥还是Open)。
显示效果如下: Fx 93.0 (64-bit)
审查元素前4个都是用了Symbol,只有最后一个用了Emoji
(Chrome也是一样,只不过Chrome里的Emoji如下所述是黑白的。)
另外火狐应该也针对其他 emoji 字体做了处理,EmojiOne 的显示效果与 Segoe 的不同。但是在酷容下都是同样的图形。(我还拿 IE 做了实验,虽然也是黑白的,但 EmojiOne 的显示效果也与 Segoe 的不同,这样看来貌似是酷容写死了用于显示 emoji 的字体)。