【问题标题】:Make Anaconda's tkinter aware of system fonts or install new fonts for Anaconda让 Anaconda 的 tkinter 了解系统字体或为 Anaconda 安装新字体
【发布时间】:2018-05-25 22:27:42
【问题描述】:

我的 Debian Sid 笔记本上有两个 Python 安装,⑴ 系统的 Python (v.2.7) 和一些实用程序包(包括Tkinter)和⑵ Anaconda 的 Python 3。

很容易看出两种 Python 发行版有哪些(嗯,这里有多少...)字体。

Python 2

>>> from Tkinter import Tk
>>> from tkFont import families
>>> Tk(); available = families()   ### Tk() is needed to have a running tcl interpreter
<Tkinter.Tk instance at 0x7f977bcbfb90>
>>> len(available)
3011

Python 3

>>> from tkinter import Tk
>>> from tkinter.font import families
>>> Tk() ; available = families()
<tkinter.Tk object .>
>>> len(available)
68

在我看来,Anaconda 的 tkinter 只查看基本的 X 字体随发行版提供请参阅下面的编辑

你知道一个程序,或者

  • 让 Anaconda 的 tkinter 知道系统字体(首选替代方案)或
  • 在 Anaconda 的树中安装一些字体以便tkinter 可以使用它们?

tia


编辑 Anaconda 可用的字体确实是系统字体,但只有xfontsel 知道的字体,即可以使用xset 操作的字体路径中的字体。

我尝试了以下

$ cd ~/.fonts ; mkfontscale ; mkfontdir ; xset fp+ `pwd`

xfontsel 显示了大约 30 多个字体系列。通过 Python 3 检查,我确认只有两个 字体系列被添加到可用字体列表中(即 'go''gomono' — 没有 'consolas' 等)并生成标签

...
r = Tk() ; Label(r, text="Go Mono", font=('gomono', 24)).pack()

使用 Python 2 和 Python 3 在这两种情况下都成功了,但是 Debian 的 Python 显示了很好的抗锯齿文本,而另一个是(粗略的)位图再现。

所以,从某种意义上说,我已经部分回答了我的问题,但是

  1. 并非xfontsel 所示的每个字体系列都被tkinter 采用
  2. 即使对于少数被认可的人来说,演绎也有太多不足之处...

我想阅读一个更好、更有用的答案。

【问题讨论】:

  • 我怀疑您的问题类似于以下问题中描述的内容:Path to Linux Fonts in Python3 and tkinter
  • @PicoutputCls 我明白了,这些问题至少可以说是相似的......但是我要留下我的问题,因为我觉得问题标题更切题并且可以吸引更多答案,你怎么看?
  • 同意。我只是引用了这篇文章,因为我认为它可能会帮助您或其他人找到问题的解决方案。
  • FONTCONFIG_PATH/FONTCONFIG_FILE 环境变量吗?你能检查一下'FONTCONFIG_PATH' in os.environ之类的东西吗?
  • @CommonSense 我已经检查过了,没有合适的(显然是fontconfig 相关的)环境变量。

标签: python tkinter fonts anaconda fontconfig


【解决方案1】:

{tT}kinter 链接到 Tk/Tcl 解释器,松散地说,它包含在几个 DLL 中,特别是图形库是 libtk6.0.so

tkinter 看不到的大部分额外字体由 Freetype 库管理,Anaconda 的 libtk6.0.so 不是针对 Freetype 构建的...

$ ldd /usr/lib/x86_64-linux-gnu/libtk8.6.so | grep freetype
        libfreetype.so.6 => /usr/lib/x86_64-linux-gnu/libfreetype.so.6 (0x00007f0a24597000)
$ ldd miniconda3/lib/libtk8.6.so | grep freetype
$

我尝试了以下,可怕的事情

$ mv lib/miniconda3/lib/libtk8.6.so lib/miniconda3/lib/libtk8.6.sav
$ ln -s /usr/lib/x86_64-linux-gnu/libtk8.6.so lib/miniconda3/lib/libtk8.6.so
$ ipython
Python 3.6.3 |Anaconda, Inc.| (default, Nov 20 2017, 20:41:42) 
Type 'copyright', 'credits' or 'license' for more information
IPython 6.2.1 -- An enhanced Interactive Python. Type '?' for help.
In [1]: from tkinter import Tk, Label ; from tkinter.font import families
In [2]: r = Tk() ; a = families() ; len(a)
Out[2]: 328
In [3]: r=Tk() ;  Label(r, text="Constantia", font=("Constantia", 60)).pack()
In [4]: r.mainloop()

最后的想法。

  1. 替换 DLL 不是一个干净的解决方案。
  2. 字体不完全相同。 Anaconda 肯定有自己的 Fontconfig 子系统,可能扫描的目录不同,但我对字体数量的差异没有正确理解。
  3. 正确的做法是说服 Anaconda, Inc. 针对 Freetype 构建 libtk,但我不知道如何向他们报告,例如,如果我转到 https://www.anaconda.com/search/issues,我看到的是一个列表关于分发的信息文章。

更新

关于第 3 点,我通过 a github issue Anaconda Inc. 联系并被告知

不,我们不能这样做。在构建我们的软件时,我们需要很早地构建 python,远在构建任何图形之前。添加 Freetype 作为 tkinter 的 dep 会导致构建图中出现循环,我们无法再构建发行版。

为什么不使用比 tkinter 更现代的东西呢?

                                                  --- Ray Donnelly(又名 mingwandroid)

【讨论】:

  • 我找到了合适的渠道,我已经在以下问题tkinter fonts #6833 中发布了我的发现
  • 我也在package tk appears to be built without truetype support #776 上发帖,这似乎更相关,并且(曾经?)被分发的开发者跟踪。
  • 哇。你得到的答复同时是有益的和侮辱性的。天哪。
  • @erekalper 很有帮助,因为他们明确表示他们不会解决问题。另一方面,我怀疑答案的优点是 b.s.但我不想和一个立场如此大胆的人讨论。
【解决方案2】:

编辑:正如@gboffi 指出的那样,这个解决方案似乎 像它一样有效,因为sudo python 不使用Anaconda 的安装,而是使用系统默认设置。使用带有 sudo 的完整 Anaconda Python 路径仍然会产生有限的字体选项。我将继续探索这一点,但目前的答案显然是不正确的。


我遇到了几乎完全相同的问题,对我来说“修复”是使用 sudo 运行 Anaconda 的 Python。这样做显然可以访问其他字体,无论出于何种原因,它本身没有。 (在人烟稀少的Google Groups discussion 中找到此信息。)

作为参考,我的系统运行的是 Ubuntu 16.04,Anaconda 4.4.8 和 Python 3.6.4。

python my_script.py 产生:

sudo python my_script.py 产生:

奇怪的是它们没有重叠,但我对 Anaconda 感到非常沮丧,我现在已经完成了调查。希望这(也许)有帮助!这是一个糟糕的解决方案,足以进行测试。

【讨论】:

  • sudo python script 运行系统的 Python,它是针对 fontconfig 和 truetype 正确构建的。恐怕我不能赞成你的回答......
  • 你说的很对;这完全是我的疏忽(而且启动起来相当愚蠢)。我将继续探索这一点,但会更新我的答案。
【解决方案3】:

我正在通过在无 conda 的环境中启动 gitk 来解决这个问题。我对 conda 很陌生,所以我不知道这样做是否存在微妙/隐藏的问题。

# Fix gitk fonts in conda environments
# The Tcl/Tk environment in conda has font linking issues, so hard-to-read fonts get chosen
# Start a subshell ( ), any changes within will die with the subshell
# Detect if conda is active, if so deactivate until it isn't
# Run gitk in a conda-free environment
alias gitk='( [ -n "${CONDA_SHLVL}" ] && while [ $CONDA_SHLVL -gt 0 ]; do conda deactivate; done; gitk --all & )'

【讨论】:

  • 我没有投反对票,但你的解决方案大致相当于锯掉你坐在的树枝。反对者可能是愿意使用 Anaconda 的 Tkinter 和漂亮字体的人。
  • (或向客户销售基于 Anaconda+Tkinter 的解决方案,并且厌倦了听到他们对锯齿状字体的抱怨的人)
  • @gboffi 谢谢。不过,它并没有真正锯掉我的树枝,而是将 gitk 放在树枝上,锯掉那根树枝,然后注意到 gitk 是一只依靠翅膀的鸟,并不关心树枝是否存在。据我所知,gitk 需要 git,而 Anaconda 环境中什么也没有。而且它在一个子shell中,所以它不会影响其他任何东西。
猜你喜欢
  • 2015-10-17
  • 1970-01-01
  • 2016-04-26
  • 2013-04-08
  • 1970-01-01
  • 2020-05-13
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多