openSUSE Tumbleweed 中文字体配置记录

Linux 桌面系统发展了这么多年基本上已经解决了原先字体不好看的问题。而且开源字体大行其道也为我们提供了很多个性化的选择。但是对于系统默认的字体配置来说,还是有些需要自己调整的地方,特别是对于我这样同时使用西文和中文字符甚至在系统层面很多时侯使用西文字符更多些的人来说更是如此。

背景资料

openSUSE 现在使用 fontconfig 来配置字体。这个库虽然功能强大、配置方便,但是对于刚刚接触这些东西的人来说可并不容易。咱都是习惯了在 Windows 中享受一切被设定的人。

关于 openSUSE 甚至是随便什么发行版中的 fontconfig 的使用介绍可以参考下面的文档:

下面就是我自己的配置记录了。

下载安装字体

这里字体分为三大类:衬线字体(Serif)、无衬线字体(Sans Serif)和等宽字体(Monospace)。

反正衬线(Serif)字体也不怎么好看,在系统里就不打算用了。所以对我来说就需要两类字体:无衬线字体(Sans Serif)和等宽字体(Monospace)。

中文字体

Google 开源发布的 Noto 系列字体还是挺好看的,最大的优点就是提供的字符比较全。所以 Noto Sans 系列是我的主要字体。这个可以直接从 openSUSE 的源中安装。安装时候默认开启的 openSUSE-Tumbleweed-Oss 源中已经有了这些字体,同时包含了 noto-sans-monocjksc-fonts见下面的 2016.05.17 更新说明。)

zypper -n in noto-serif-fonts noto-sans-cjk-fonts

中文字体还有一个比较重要的就是文泉驿的等宽微米黑(WenQuanYi Micro Hei Mono),可以跟下面的 Roboto Mono、Droid Sans Mono g、Liberation Mono 比较好的进行搭配。文泉驿的等宽微米黑字体下载地址

西文字体

我自己用 Google 的 Tinos 和 Roboto 作为默认的 serif 和 sans serif 西文字体。然后用 Google Roboto Mono 作为 monospace 的西文字体。这几个都可以从 openSUSE 字体库中直接安装,

zypper -n in google-tinos-fonts google-roboto-fonts google-roboto-mono-fonts

强调西文字体主要是因为等宽字体(Monospace)的选用问题。

openSUSE 默认配置的西文字体跟中文字体配合起来不是太好。比如会造成 shell 终端中的中文字符下沉的问题,kate 中出现只显示中文字体的上边一半的问题等。

本来想反正 Noto Sans CJK 中是有西文字体的,干脆中英文都用这个好了。可是麻烦在于,文本编辑器 kate 中默认会给一些着重的词使用粗体,这时候使用 Noto Sans CJK 或者 Noto Sans Mono CJK 显示的西文字体就会渲染得特别的重,就感觉像是写在宣纸上的钢笔字(嗯,太能装逼了,或者说就像是钢笔字被水浸花了)。而我又不想挨个儿去修改 kate 的渲染设置。更何况也许还有别的软件也会有类似的问题呢。

Droid Sans Mono 跟 Noto Sans CJK 配合起来倒是挺好的,就是那个数字 0 跟大写的字母 O 看起来难以分辨是个很让人心痛的缺陷。然后,找了找果然有人编辑了 Droid Sans Mono 将其中的 0 用 Coonsolas 中的替换掉了。这个新的字体就是 Droid Sans Mono g,可以在 https://github.com/tupunco/Droid-Sans-Mono-g 这里下载到。感谢 tupunco 的分享。

如果要让自己下载的字体对整个系统可用,可以放到 /usr/share/fonts/truetype/usr/share/fonts 下也有许多不同用途的字体文件夹,除非是用于特殊应用程序比如 wps,否则请不要使用 /usr/share/fonts/kingsoft-office 这样的结构)。

如果只是当前用户可用,可以放到用户主文件夹:~/.fonts(该文件夹与系统文件夹不同,没有那么详细的按用途区分,而是按照字体名称的首字母来划分的,比如你下载的字体叫做「字幕黑体」,你就可以放到 ~/.fonts/字/ 文件夹下)。

然后刷新字体缓存,

fc-cache -fv

后来发现 Liberation Mono 不管是跟文泉驿等宽微米黑还是 Noto Sans Mono CJK 配合都很好,所以就改用 Liberation Mono 或者 Roboto Mono 好了。见文后的 2016.05.17 更新说明

其它一些字体

可以从 Windows 系统中字体文件夹(%SYSTEMDRIVE%/Windows/Fonts)、其它软件安装源及网络上找到——需要注意一下版权问题。比如金步国介绍过的,“来自Adobe CS 6的”Adobe 宋体 Std”、”Adobe 仿宋 Std”、”Adobe 楷体 Std”,下载任意一个软件的试用版,即可从中提取如下文件:”AdobeSongStd-Light.otf”,”AdobeFangsongStd-Regular.otf”,”AdobeKaitiStd-Regular.otf””。

字体配置

除了次像素渲染外,后面的两项内容大概是选其一即可。折腾了太久,自己都忘记了。

次像素渲染

个人感觉这个没什么必要。见下面的 2016.05.17 的更新说明。

Subpixel Rendering(次像素渲染)因为版权问题没有集成到 openSUSE 系统中,需要自行安装支持包。点击这里下载安装。 Tumbleweed 选用那个 openSUSE Factory 就好。

或者命令行终端操作,

zypper ar -f -n subpixel http://download.opensuse.org/repositories/home:/namtrac:/subpixel/openSUSE_Factory/ subpixel
zypper -n in freetype2

字体配置文件

系统全局的字体配置文件存放在两个地方,/etc/fonts/ 和 /usr/share/fontconfig/ 两个文件夹下。实际上,前一文件夹中某些文件仅仅是链接到后一文件夹中的某个文件了。

用户自己的字体配置文件存放在 ~/.config/fontconfig/ 目录下(注意,原来的 ~/.fonts.conf 配置文件已经废弃,不再使用了)。所以如果有了这个,以后重装系统也不需要重新设置字体。反正这笔记本就自己一个人用,字体配置文件的修改只放在这里还是比较方便的。

我自己是给放在了用户目录下。在 ~/.config/fontconfig 目录下新建一个配置文件 fonts.conf,内容如下,(已更新,见文后的 2016.05.17 的更新说明。)

<?xml version='1.0' encoding='UTF-8' standalone='no'?>
<fontconfig>
  <dir>~/.fonts</dir>

<!-- https://wiki.archlinux.org/index.php/font_configuration#Replace_or_set_default_fonts -->
<!-- Default font (no fc-match pattern) -->
  <match>
    <edit mode="prepend" name="family">
      <string>Noto Sans</string>
    </edit>
  </match>

<!-- Default font for the zh_CN locale (no fc-match pattern) -->
  <match>
    <test compare="contains" name="lang">
      <string>zh</string>
    </test>
    <edit mode="prepend" name="family">
      <string>Noto Sans CJK SC</string>
    </edit>
  </match>

<!-- Default sans-serif font -->
  <match target="pattern">
    <test qual="any" name="family">
      <string>sans-serif</string>
    </test>
    <edit name="family" mode="prepend" binding="same">
      <string>Roboto</string>
    </edit>
    <edit name="family" mode="append" binding="same">
      <string>Noto Sans CJK SC</string>
    </edit>
  </match>
 
<!-- Default serif fonts -->
  <match target="pattern">
    <test qual="any" name="family">
      <string>serif</string>
    </test>
    <edit name="family" mode="prepend" binding="same">
      <string>Tinos</string>
    </edit>
    <edit name="family" mode="append" binding="same">
      <string>Noto Sans CJK SC</string><!-- 这里其实跟前面没有做区分,也可以根据喜好换成宋体或其它 -->
    </edit>
  </match>

<!-- Default monospace fonts -->
  <match target="pattern">
    <test qual="any" name="family">
      <string>monospace</string>
    </test>
    <!-- Considering the font height problem in terminal, -->
    <!-- it seems that Liberation Mono is the best. -->
    <edit name="family" mode="prepend" binding="same">
      <string>Liberation Mono</string>
    </edit>
    <edit name="family" mode="append" binding="same">
      <string>WenQuanYi Micro Hei Mono</string>
    </edit>
    <edit name="family" mode="append" binding="same">
      <string>Noto Sans Mono CJK SC</string>
    </edit>
  </match>

<!--
Set fonts to be preferred when the standard aliases "serif", "sans-serif",
and "monospace" are used.
字体调用顺序设置
-->
<!-- Preferred fonts -->
<!-- Fallback fonts preference order -->
  <alias>
    <family>sans-serif</family>
    <prefer>
      <family>Roboto</family>
      <family>Noto Sans</family>
      <family>Noto Sans CJK SC</family>
      <family>Noto Sans CJK TC</family>
      <family>Noto Sans CJK JP</family>
      <family>Noto Sans CJK KR</family>
    </prefer>
  </alias>
  <alias>
    <family>serif</family>
    <prefer>
      <family>Tinos</family>
      <family>Noto Serif</family>
      <family>Roboto Slab</family>
      <family>Noto Sans CJK SC</family>
      <family>Noto Sans CJK TC</family>
      <family>Noto Sans CJK JP</family>
      <family>Noto Sans CJK KR</family>
    </prefer>
  </alias>
  <alias>
    <family>monospace</family>
    <prefer>
      <family>Roboto Mono</family>
      <family>Droid Sans Mono-g</family>
      <family>WenQuanYi Micro Hei Mono</family>
      <family>Noto Sans Mono CJK SC</family>
      <family>Noto Sans Mono CJK TC</family>
      <family>Noto Sans Mono CJK JP</family>
      <family>Noto Sans Mono CJK KR</family>
    </prefer>
  </alias>

<!-- 以下的部分也可以单独放在 ~/.config/fontconfig/rendering-options.conf 中 -->
<!-- cnzhx customised, 20160124 -->
<!-- 所有字体都不要小于 9 号,没办法,眼神儿不好 -->
<match target="font">
    <test name="size" compare="less" qual="any">
        <double>9.0</double>
    </test>
    <edit name="size" mode="assign">
        <double>9.0</double>
    </edit>
</match>

<!-- 
配置 CJK 字体的渲染。
来自: http://spin.atomicobject.com/2015/10/01/localization-font-selection-fontconfig/
-->
<!-- assign name to CJK group -->
<match target="font">
    <edit name="noto_cjk" mode="assign">
        <bool>true</bool>
    </edit>
</match>
<match target="font">
    <test name="family" compare="not_eq" qual="all">
        <string>Noto Sans CJK KR</string>
    </test>
    <test name="family" compare="not_eq" qual="all">
        <string>Noto Sans CJK SC</string>
    </test>
    <test name="family" compare="not_eq" qual="all">
        <string>Noto Sans CJK JP</string>
    </test>
    <test name="family" compare="not_eq" qual="all">
        <string>Noto Sans CJK TC</string>
    </test>
    <test name="family" compare="not_eq" qual="all">
        <string>Noto Sans Mono CJK KR</string>
    </test>
    <test name="family" compare="not_eq" qual="all">
        <string>Noto Sans Mono CJK SC</string>
    </test>
    <test name="family" compare="not_eq" qual="all">
        <string>Noto Sans Mono CJK JP</string>
    </test>
    <test name="family" compare="not_eq" qual="all">
        <string>Noto Sans Mono CJK TC</string>
    </test>
    <edit name="noto_cjk" mode="assign">
        <bool>false</bool>
    </edit>
</match>
<match target="font">
    <test name="noto_cjk">
        <bool>true</bool>
    </test>

<!-- Turn on the native CFF hint -->
<!-- Turn off sub-pixel anti-aliasing because Adobe's CFF
rasterizer is for gray-scale rendering. -->
    <edit name="hinting" mode="assign">
        <bool>true</bool>
    </edit>
    <edit name="autohint" mode="assign">
        <bool>false</bool>
    </edit>
    <edit name="hintstyle" mode="assign">
        <const>hintfull</const>
    </edit>
    <edit name="antialias" mode="assign">
        <bool>true</bool>
    </edit>
    <edit name="rgba" mode="assign">
        <const>none</const>
    </edit>
    <edit name="embolden" mode="assign">
        <bool>false</bool>
    </edit>
</match>

<!-- WenQuanYi Micro Hei Mono specific rendering options -->
<match target="font">
    <test name="family" qual="any">
        <string>WenQuanYi Zen Hei</string>
    </test>
    <edit name="globaladvance">
        <bool>false</bool>
    </edit>
    <edit name="spacing">
        <int>0</int>
    </edit>
    <edit name="antialias" mode="assign">
        <bool>true</bool>
    </edit>
    <edit name="hinting" mode="assign">
        <bool>true</bool>
    </edit>
    <edit name="hintstyle" mode="assign">
        <const>hintnone</const>
    </edit>
    <edit name="autohint" mode="assign">
        <bool>false</bool>
    </edit>
    <edit name="rh_prefer_bitmaps" mode="assign">
        <bool>false</bool>
    </edit>
    <edit name="rgba" mode="assign">
        <const>none</const>
    </edit>
    <edit name="embeddedbitmap">
        <bool>false</bool>
    </edit>
    <edit name="embolden" mode="assign">
        <bool>false</bool>
    </edit>
</match>

<!-- system auto rendering options -->
<match target="font">
    <edit name="hinting" mode="assign">
        <bool>true</bool>
    </edit>
</match>
<match target="font">
    <edit name="hintstyle" mode="assign">
        <const>hintslight</const>
    </edit>
</match>
<match target="font">
    <edit name="rgba" mode="assign">
        <const>rgb</const>
    </edit>
</match>
<match target="font">
    <edit name="antialias" mode="assign">
        <bool>true</bool>
    </edit>
</match>

</fontconfig>

通过 YaST 里的 Fonts 来配置

字体配置也可以通过 YaST 的 Fonts(字体)来进行。这里有 Antialiasing(抗锯齿)、Hinting(字体微调、平滑)和 Subpixel Rendering(次像素渲染),还可以配置系统级的字体优先选用次序,以及是否使用内嵌的点阵字体等等。开启 Antialiasing,并将 Hinting 设置为 hintslight 就可以了(这些当然跟个人喜好有关)。

YaST 中 Fonts 部件里进行的字体修改都存放在 /etc/sysconfig/font-config 文件里。然后 YaST 会自动调用,

sudo /usr/sbin/fonts-config

来使之生效。

字体配置查询

配置字体之后可以通过下面的指令查询某一字体类的默认选用字体名称,

fc-match serif --all -s | less
fc-match sans-serif --all -s | less
fc-match monospace --all -s | less

以方便确认是否配置正确。

要查询仅限于中文字体,则需要加上语言参数,例如,

fc-match -s sans-serif:lang=zh-cn | less

字体设置

其实这里配置和设置两个词真是不知道有什么区别。这里就是做个标记用的。配置指的是对字体这个系统功能的初始规划;设置是指的个人桌面系统的字体选用和字号大小等设置。

系统字体设置

系统字体设置有两个位置,

  • Application Menu(开始按钮) -> Settings(设置) -> System Settings(系统设置)
    • Font (系统及 KDE 原生 Qt 应用的字体)
    • Application Style -> GNOME Application Style(GTK) -> Font (GTK 应用的字体)

字体设置的时候都直接使用系统默认的字体类名而不是具体的字体名,除了等宽字体使用 Monospace 之外其它都使用 Sans Serif(个人感觉不太喜欢 Serif 字体)。然后直接修改默认字体类(Serif、Sans Serif、Monospace)的具体字体优先顺序来提供自己喜欢的字体(见前面的配置部分)。

默认的字体大小感觉有些小,换成了 10、10、9、10、10、10。

应用程序字体设置

Konsole

系统 Shell 终端用的是默认的 Konsole,能选择的字体很少,直接就选用 Monospace 了,让系统根据前面给的默认配置去匹配字体。这里就是 Liberation Mono 和 Noto Sans Mono CJK文泉驿等宽微米黑了。或者西文字体选择 Google Roboto Mono 也挺好的。

Kate

Linux 下虽然有很多大牌的文本编辑器如 VIM 和 emacs,可是实在不想去经历那么艰难的初始学习。所以就选用了还算不错的 KateNotepadqq 可能将会是首选,只是还需要进一步考察。Kate 中字体选用的是 Droid Sans Mono g(因为没有 “Monospace” 可以选)。(2016.05.13)后来使用 Kate 编代码的时候发现这个 Droid Sans Mono g 只有常规字形而没有加粗字形。于是 Kate 中的代码高亮的部分样式都无法显示出来。(2016.05.17)再考虑到 oO0 的区分问题,就直接选用了口碑还不错的 Liberation Mono。或者 Google Roboto Mono 也挺好的。

  • 能够区分 oO01liI;
  • 有两种字重与斜体;
  • 字重与汉字的文泉驿微米黑差不多;
  • 免费。

当然微软的 Consolas 可能更好,虽然收费但是能从网上下载到。可是 Liberation Mono 本身就是免费的,也不想去占 M$ 的便宜了。不过目前只是在 Kate 中选用了 Liberation Mono,系统默认的字体设置还是选用了 Droid Sans Mono g。现在又在全系统范围内改用 Roboto Mono 了。

这么一折腾,现在 openSUSE 中的字体已经让我非常满意了。

更新

TL;DR

2016.11.26

最近 openSUSE Tumbleweed 社区已经将 CJK 字体的配置问题修复了,使用 Google Noto Sans CJK 默认情况下就没什么问题,而且显示质量也挺好的,所以几乎不用再自己修改配置了。

不过可能还需要根据自己的喜好修改默认的系统字体。比如水景一页已经精简了用户层面的字体配置文件,从前面给出的那个长长的用户字体配置改成了下面这个。

<?xml version="1.0"?><!DOCTYPE fontconfig SYSTEM 'fonts.dtd'>
<fontconfig>
    <dir>~/.fonts</dir>
    
    <!-- Default font (no fc-match pattern) -->
    <!-- 这个在默认系统字体配置文件
         /etc/fonts/conf.d/60-family-prefer.conf
         下面只是根据个人喜好的重新设定。
    -->
    <!-- Default serif fonts -->
    <alias>
        <family>Droid Serif</family>
        <default>
            <family>serif</family>
        </default>
    </alias>
    <alias>
        <family>serif</family>
        <prefer>
            <family>Droid Serif</family>
            <family>Noto Serif</family>
            <family>HanaMinA</family>
            <family>Noto Sans CJK SC</family>
        </prefer>
    </alias>
    
    <!-- Default sans-serif font -->
    <alias>
        <family>Roboto</family>
        <default>
            <family>sans-serif</family>
        </default>
    </alias>
    <alias>
        <family>sans-serif</family>
        <prefer>
            <family>Roboto</family>
            <family>Noto Sans</family>
            <family>Noto Sans CJK SC</family>
        </prefer>
    </alias>
    
    <!-- Default monospace fonts -->
    <alias>
        <family>Roboto Mono</family>
        <default>
            <family>monospace</family>
        </default>
    </alias>
    <alias>
        <family>monospace</family>
        <prefer>
            <family>Roboto Mono</family>
            <family>Liberation Mono</family>
            <family>WenQuanYi Micro Hei Mono</family>
            <family>Noto Sans Mono CJK SC</family>
        </prefer>
    </alias>
    
    <!-- To disable embedded bitmap for all fonts -->
    <match target="font">
        <edit name="embeddedbitmap" mode="assign">
            <bool>false</bool>
        </edit>
    </match>
</fontconfig>

说明如下。

  1. 参考系统默认字体配置文件(根据 openSUSE Tumbleweed snapshot 20161122 给出),
    /etc/fonts/conf.d/56-user.conf
    /etc/fonts/conf.d/58-family-prefer-local.conf
    /etc/fonts/conf.d/59-family-prefer-lang-specific.conf
    /etc/fonts/conf.d/60-family-prefer.conf
    

    所有这些文件中已经有的配置都从最前面的配置文件中移除了。具体如下,留在这里做个参考。

  2. 针对 zh_CN 的配置都已经在 /etc/fonts/conf.d/59-family-prefer-lang-specific.conf 中了。
  3. 字体渲染,系统默认也都挺好了。可以看 YaST -> Fonts 中的设置。
  4. 针对 Liberation Sans 的特别设置,
        <!-- Choose sans-serif alias depending on antialias. -->
        <!-- Prefer Liberation Sans -->

    已经在 /etc/fonts/conf.d/60-family-prefer.conf 中了。

  5. 文泉驿字体的优化渲染,已经在 /etc/fonts/conf.d/57-wqy-zenhei.conf/etc/fonts/conf.d/57-wqy-microhei.conf 中了。
  6. Chrome / Chromium 中的字体渲染问题已经修复了。

但是这个东西是完全看用户的个人喜好的,仅供参考,以便挑选使用前面给出的长配置文件。

2016.10.20

Chrome 中网页字体的问题早就解决了,忘记更新这里了。

2016.05.17

现在可以直接从 openSUSE-Tumbleweed-Oss 源里面直接安装 Noto Sans CJK 四语言一体语言包了。上次更新的时候提到官方源 M17N 里面把 noto-sans-cjk-{ja, ko, sc, tc} 以及 noto-sans-mono-cjk-{ja, ko, sc, tc} 这个等宽字体包的几个分离的语言包给整合成一个独立的 super OTC 格式的 noto-sans-cjk 语言包,并合并进入了 openSUSE-Tumbleweed-Oss 源。这样可以节省很大的安装占用的磁盘空间。当时的情况下 openSUSE 的 fontconfig 还没有针对这一情况进行处理,因而造成系统在使用 Noto Sans CJK 匹配中文语言的时候总是直接选用按字母顺序排在前面的 ja,也就是日语字体。现在这个问题已经经由 Marguerite Su 报告并提供补丁进行了修复。

关于字体渲染的问题。 根据体验以及这里的说明,似乎并不需要在 openSUSE Tumbleweed 中启用次像素渲染(subpixel)。而且 Infinality 似乎是更好的解决方案(虽然看起来似乎也没必要特意去安装配置,openSUSE Tumbleweed 的源在这里,也许不久以后就会整合到 Tumbleweed 中)。

另外,根据 reddit 上的讨论,openSUSE 的 Chairman rbrownsuse 表示通常 fetchmsttfonts 这个包会让 openSUSE 的字体渲染变得不好。所以移除它是比较推荐的做法,

sudo zypper rm fetchmsttfonts

当然如果没有安装过那就不用管它了。

然后,前面贴的自定义 fonts.conf 的代码就被更新了一下,依照的是 ArchLinux 上的这个模板。与之前相比,除了有用户 prefer 字体的声明外,还增加了默认系统字体的声明。具体见上面“字体配置文件”那一节的代码。

最后,可能是因为 Chrome / Chromium 浏览器本身的问题,也可能是 fontconfig 的问题,需要针对 Chrome / Chromium 浏览器做个具体的字体调整才完美。因为同时也解决了之前的配置中存在的一个网页中的韩语会挤成一团的问题。具体见上面“应用字体设置”那一节中关于 Chrome 的特别说明。

不管是 Google Chrome 还是 Chromium 目前都存在一个问题,默认情况下会选用 Noto Sans CJK Demilight 来渲染 Normal 字重的中文字体,因而显得太浅。需要特别设置一下,

Google Chrome -> 高级 -> 网页内容 -> 自定义字体 -> 标准字体 -> Noto Sans CJK SC,

这样就解决了上述问题。不知道这个问题是否与 fontconfig 的这个 bug 有关(已经被修复,但是还没有更新稳定版本,所以没有被下游发行版采用)。

2016.04.20

似乎官方源 M17N 里面把 noto-sans-cjk 的几个分离的语言包给去掉了,也就是说无法通过官方源直接安装 noto-sans-cjksc 了。

我采用的解决方案是,直接从 Google Noto 字体网站下载简体中文的字体包。下载地址:https://www.google.com/get/noto/#sans-hans。下载后解压,并将 7 种样式的字体文件复制到 ~/.fonts/ 文件夹(仅供当前用户使用)或者 /usr/share/fonts/notocjksc 文件夹(需要 root 权限;没有该文件夹可以自己创建;这样安装相当于整个系统都可以使用该字体)。

注意*不要*安装系统自动提供的 noto-sans-cjk 合体包(一下子包含全部四种 CJK 字体)。

这是水景一页迁移到 openSUSE 系统之后的一系列配置记录之一。©

本文发表于水景一页。永久链接:<https://cnzhx.net/blog/opensuse-tw-zh_cn-font-config/>。转载请保留此信息及相应链接。

雁过留声,人过留名

电子邮件地址不会被公开。 必填项已用*标注

特别提示:与当前文章主题无关的讨论相关但需要较多讨论求助信息请发布到水景一页讨论区的相应版块,谢谢您的理解与合作!请参考本站互助指南