Font selection?
lobingera opened this issue · comments
No idea 🙂 Is the problem that a font can't be found?
' but the standard CSS2 generic family names, ("serif", "sans-serif", "cursive", "fantasy", "monospace"), are likely to work as expected.' in https://www.cairographics.org/manual/cairo-text.html.
What did you configure for fontconfig?
This is the builder for fontconfig: https://github.com/JuliaPackaging/Yggdrasil/blob/326831d236096ac147cece2dd2f53aee28d5b536/F/Fontconfig/build_tarballs.jl
Maybe you want to check the list of fonts found by fontconfig with
using Cairo
fc_list = joinpath(dirname(Cairo.Fontconfig_jll.libfontconfig_path), "..", "bin", "fc-list")
run(`$(fc_list)`)
The good news is Fontconfig_jll has reasonable defaults for paths and finds major part of my local fonts, so e.g. "DejaVu Sans" works. I'm still looking into the cairo build, how the defaults for 'sans' 'serif' etc. are build.
lobi@o4:~$ fc-match Sans
DejaVuSans.ttf: "DejaVu Sans" "Book"
vs.
julia> fc_list = joinpath(dirname(Cairo.Fontconfig_jll.libfontconfig_path), "..", "bin", "fc-match")
"/home/lobi/.julia/artifacts/225abdb6d736c3c743dbc9735950947bc064c0cd/lib/../bin/fc-match"
julia> run(`$(fc_list) Sans`)
FreeMono.ttf: "FreeMono" "Regular"
Process(`/home/lobi/.julia/artifacts/225abdb6d736c3c743dbc9735950947bc064c0cd/lib/../bin/fc-match Sans`, ProcessExited(0))
Where is DejaVuSans.ttf? Does running fc-cache help?
DejaVu Sans isn't the problem
julia> run(`$(fc_list) "DejaVu Sans"`)
/usr/share/fonts/truetype/dejavu/DejaVuSansCondensed-Oblique.ttf: DejaVu Sans,DejaVu Sans Condensed:style=Condensed Oblique,Oblique
/usr/share/fonts/truetype/dejavu/DejaVuSans-ExtraLight.ttf: DejaVu Sans,DejaVu Sans Light:style=ExtraLight
/usr/share/fonts/truetype/dejavu/DejaVuSans.ttf: DejaVu Sans:style=Book
/usr/share/fonts/truetype/ttf-dejavu/DejaVuSans.ttf: DejaVu Sans:style=Book
/usr/share/fonts/truetype/dejavu/DejaVuSans-Bold.ttf: DejaVu Sans:style=Bold
/usr/share/fonts/truetype/dejavu/DejaVuSansCondensed-BoldOblique.ttf: DejaVu Sans,DejaVu Sans Condensed:style=Condensed Bold Oblique,Bold Oblique
/usr/share/fonts/truetype/dejavu/DejaVuSansCondensed.ttf: DejaVu Sans,DejaVu Sans Condensed:style=Condensed,Book
/usr/share/fonts/truetype/dejavu/DejaVuSansCondensed-Bold.ttf: DejaVu Sans,DejaVu Sans Condensed:style=Condensed Bold,Bold
/usr/share/fonts/truetype/dejavu/DejaVuSans-Oblique.ttf: DejaVu Sans:style=Oblique
/usr/share/fonts/truetype/ttf-dejavu/DejaVuSans-Bold.ttf: DejaVu Sans:style=Bold
/usr/share/fonts/truetype/dejavu/DejaVuSans-BoldOblique.ttf: DejaVu Sans:style=Bold Oblique
Process(`/home/lobi/.julia/artifacts/225abdb6d736c3c743dbc9735950947bc064c0cd/lib/../bin/fc-list 'DejaVu Sans'`, ProcessExited(0))
julia> run(`$(fc_match) "DejaVu Sans"`)
DejaVuSans.ttf: "DejaVu Sans" "Book"
Process(`/home/lobi/.julia/artifacts/225abdb6d736c3c743dbc9735950947bc064c0cd/lib/../bin/fc-match 'DejaVu Sans'`, ProcessExited(0))
So fc-match Sans
is not matching it?
No (#312 (comment)) fc_list is misleading here, fc-match is called.
I know, in fact I said fc-match
.
Honestly, I'm a bit lost about what's the problem here 🙂
Cairo.jl should support the generic "Sans" "Serif" "Mono", but at least not providing a serif font for Sans.
So is this a Fontconfig problem that it's picking up a serif font when asking for a sans-serif one?
At least i see clearer now: The top-level font.conf is read from an artifact and hard coded.
Could you please elaborate? I still fail to understand where the problem is exactly.
With latest version of Fontconfig_jll
(v2.13.1+9), the fonts.conf
file is identical to my system fonts.conf
, that is a standard Linux configuration:
julia> using Fontconfig_jll
julia> run(`cmp $(Fontconfig_jll.fonts_conf) /etc/fonts/fonts.conf`)
Process(`cmp /home/mose/.julia/artifacts/b20d3b4e71d9209bc0d83410b048e97b4f8c7096/etc/fonts/fonts.conf /etc/fonts/fonts.conf`, ProcessExited(0))
We've now removed all references to paths in the build environment.
Note that calling fc-match
with the proper environment gives the expected result:
julia> fc_match() do fc_match_exe
run(`$fc_match_exe Sans`)
end
DejaVuSans.ttf: "DejaVu Sans" "Book"
Process(`/home/mose/.julia/artifacts/b20d3b4e71d9209bc0d83410b048e97b4f8c7096/bin/fc-match Sans`, ProcessExited(0))
while directly calling the executable doesn't:
julia> run(`/home/mose/.julia/artifacts/b20d3b4e71d9209bc0d83410b048e97b4f8c7096/bin/fc-match Sans`)
LinLibertine_R.otf: "Linux Libertine O" "Regular"
Process(`/home/mose/.julia/artifacts/b20d3b4e71d9209bc0d83410b048e97b4f8c7096/bin/fc-match Sans`, ProcessExited(0))
We probably need to set some more environment variables to get this working.
It turned out it's just LIBPATH
:
julia> withenv(Fontconfig_jll.LIBPATH_env => Fontconfig_jll.LIBPATH) do
run(`/home/mose/.julia/artifacts/b20d3b4e71d9209bc0d83410b048e97b4f8c7096/bin/fc-match Sans`)
end
DejaVuSans.ttf: "DejaVu Sans" "Book"
Process(`/home/mose/.julia/artifacts/b20d3b4e71d9209bc0d83410b048e97b4f8c7096/bin/fc-match Sans`, ProcessExited(0))
However setting this environment variable doesn't seem to help with sample_text.jl
.
I have similar issues.
Observations: Linux
Breaks going from Cairo v0.6.0 to v0.7.0 (Using Julia v1.3.1)
(Still broken for v0.8.0, 1.0.0, 1.0.2).
Does not appear to be caused by changes in Julia itself:
Also broken for Cairo v0.8.0 (Using Julia v1.1.1)
(Cannot go higher than Cairo v0.8.0 on Julia v1.1.1)
EDIT: Observations: Linux + Local Fonts
As mentioned by @lobingera, local fonts still appear to work:
Local fonts work well even with Cairo v1.0.2 on Julia v1.3.1.
Observations: Windows 10
"built-in" font aliases NOT broken, even for Cairo v0.8.0 (Using Julia v1.1.1)
So, it appears NOT to be an issue in Windows (no idea about mac).
EDIT: and is ONLY a problem with the "built-in" font aliases.
@lobingera what I would like to understand, and I hope you can help me on this, is what is choosing the font in Cairo.jl? Can you track down where the selection happens? That could tell us where to look further. As far as I can tell, the executable fc-match
isn't called in this package (not directly at least), so looking at it might not be relevant
afaiu, libcairo actually wants you to select a font and hand over some function handles via the renderer (or the outline conversion if the output isn't a bitmap). However there is a fallback/toy font solution that uses the means provided and configured at built time. If you build on linux this is mostliklely Fontconfig + FreeType. You can see a little bit of that in cairo-ft-font.c _cairo_ft_unscaled_font_create_for_pattern.
So.
I'd expect the provided fc-pattern and fc-match to resolve names like 'serif' and 'sans-serif' to resolve to a TTF that could be loaded.
I'd expect the provided fc-pattern and fc-match to resolve names like 'serif' and 'sans-serif' to resolve to a TTF that could be loaded.
They do:
julia> using Fontconfig_jll
julia> fc_match(cmd -> run(`$cmd Sans`));
DejaVuSans.ttf: "DejaVu Sans" "Book"
julia> fc_match(cmd -> run(`$cmd Serif`));
DejaVuSerif.ttf: "DejaVu Serif" "Book"
Well ...
l1@c5:~$ ./julia-1.4.1/bin/julia
_
_ _ _(_)_ | Documentation: https://docs.julialang.org
(_) | (_) (_) |
_ _ _| |_ __ _ | Type "?" for help, "]?" for Pkg help.
| | | | | | |/ _` | |
| | |_| | | | (_| | | Version 1.4.1 (2020-04-14)
_/ |\__'_|_|_|\__'_| | Official https://julialang.org/ release
|__/ |
shell> cd juliaenvironments/
/home/l1/juliaenvironments
shell> cd Emoji/
/home/l1/juliaenvironments/Emoji
(@v1.4) pkg> activate .
Activating environment at `~/juliaenvironments/Emoji/Project.toml`
(Emoji) pkg> st
Status `~/juliaenvironments/Emoji/Project.toml`
[159f3aea] Cairo v1.0.2
[186bb1d3] Fontconfig v0.4.0
[a3f928ae] Fontconfig_jll v2.13.1+11
(Emoji) pkg> up
Updating registry at `~/.julia/registries/General`
Updating git-repo `https://github.com/JuliaRegistries/General.git`
Installed Colors ─ v0.12.1
Updating `~/juliaenvironments/Emoji/Project.toml`
[159f3aea] ↑ Cairo v1.0.2 ⇒ v1.0.3
Updating `~/juliaenvironments/Emoji/Manifest.toml`
[159f3aea] ↑ Cairo v1.0.2 ⇒ v1.0.3
[3da002f7] ↑ ColorTypes v0.9.0 ⇒ v0.10.3
[5ae59095] ↑ Colors v0.11.2 ⇒ v0.12.1
[53c48c17] ↑ FixedPointNumbers v0.7.1 ⇒ v0.8.0
[a2bd30eb] ↑ Graphics v1.0.1 ⇒ v1.0.2
[546b0b6d] - X11_jll v1.6.8+5
[84d6cd60] - Xorg_inputproto_jll v2.3.2+1
[060dd47b] - Xorg_kbproto_jll v1.0.7+1
[4f6342f7] ↑ Xorg_libX11_jll v1.6.8+0 ⇒ v1.6.9+2
[21e99dc2] - Xorg_renderproto_jll v0.11.1+1
[7c09cfe3] - Xorg_util_macros_jll v1.19.2+1
[c2e9c405] - Xorg_xcb_proto_jll v1.13.0+1
[d13bc2ba] - Xorg_xextproto_jll v7.3.0+1
[46797783] - Xorg_xproto_jll v7.0.31+1
julia> using Fontconfig_jll
julia> fc_match(cmd -> run(`$cmd Sans`));
Fontconfig error: Cannot load default config file
FreeMono.ttf: "FreeMono" "Regular"
julia> fc_match(cmd -> run(`$cmd Serif`));
Fontconfig error: Cannot load default config file
FreeMono.ttf: "FreeMono" "Regular"
Try setting
ENV["FONTCONFIG_FILE"] = fonts_conf
julia> ENV["FONTCONFIG_FILE"] = fonts_conf
"/home/l1/.julia/artifacts/82f1062ef35feaa6d4cc426c15574338f12f5fd1/etc/fonts/fonts.conf"
julia> fc_match(cmd -> run(`$cmd Serif`));
FreeMono.ttf: "FreeMono" "Regular"
julia> fc_match(cmd -> run(`$cmd Sans`));
FreeMono.ttf: "FreeMono" "Regular"
For example what do you get with
julia> fc_list(cmd -> run(`$cmd "DejaVu Sans"`));
/usr/share/fonts/TTF/DejaVuSansCondensed.ttf: DejaVu Sans,DejaVu Sans Condensed:style=Condensed,Book
/usr/share/fonts/TTF/DejaVuSans-BoldOblique.ttf: DejaVu Sans:style=Bold Oblique
/usr/share/fonts/TTF/DejaVuSansCondensed-Oblique.ttf: DejaVu Sans,DejaVu Sans Condensed:style=Condensed Oblique,Oblique
/usr/share/fonts/TTF/DejaVuSansCondensed-BoldOblique.ttf: DejaVu Sans,DejaVu Sans Condensed:style=Condensed Bold Oblique,Bold Oblique
/usr/share/fonts/TTF/DejaVuSans-ExtraLight.ttf: DejaVu Sans,DejaVu Sans Light:style=ExtraLight
/usr/share/fonts/TTF/DejaVuSans-Oblique.ttf: DejaVu Sans:style=Oblique
/usr/share/fonts/TTF/DejaVuSansCondensed-Bold.ttf: DejaVu Sans,DejaVu Sans Condensed:style=Condensed Bold,Bold
/usr/share/fonts/TTF/DejaVuSans.ttf: DejaVu Sans:style=Book
/usr/share/fonts/TTF/DejaVuSans-Bold.ttf: DejaVu Sans:style=Bold
julia> fc_list(cmd -> run(`$cmd "DejaVu Serif"`));
/usr/share/fonts/TTF/DejaVuSerifCondensed.ttf: DejaVu Serif,DejaVu Serif Condensed:style=Condensed,Book
/usr/share/fonts/TTF/DejaVuSerifCondensed-Bold.ttf: DejaVu Serif,DejaVu Serif Condensed:style=Condensed Bold,Bold
/usr/share/fonts/TTF/DejaVuSerif-Bold.ttf: DejaVu Serif:style=Bold
/usr/share/fonts/TTF/DejaVuSerif.ttf: DejaVu Serif:style=Book
/usr/share/fonts/TTF/DejaVuSerifCondensed-Italic.ttf: DejaVu Serif,DejaVu Serif Condensed:style=Condensed Italic,Italic
/usr/share/fonts/TTF/DejaVuSerif-BoldItalic.ttf: DejaVu Serif:style=Bold Italic
/usr/share/fonts/TTF/DejaVuSerifCondensed-BoldItalic.ttf: DejaVu Serif,DejaVu Serif Condensed:style=Condensed Bold Italic,Bold Italic
/usr/share/fonts/TTF/DejaVuSerif-Italic.ttf: DejaVu Serif:style=Italic
?
julia> fc_list(cmd -> run(`$cmd "DejaVu Sans"`));
/usr/share/fonts/truetype/dejavu/DejaVuSans.ttf: DejaVu Sans:style=Book
/usr/share/fonts/truetype/dejavu/DejaVuSans-Bold.ttf: DejaVu Sans:style=Bold
julia> fc_list(cmd -> run(`$cmd "DejaVu Serif"`));
/usr/share/fonts/truetype/dejavu/DejaVuSerif-Bold.ttf: DejaVu Serif:style=Bold
/usr/share/fonts/truetype/dejavu/DejaVuSerif.ttf: DejaVu Serif:style=Book
Is this different from what you get with system fc-list
?
Hmm.
shell> fc-list | grep Deja
julia>
vs.
l1@c5:~$ fc-list | grep Deja
/usr/share/fonts/truetype/dejavu/DejaVuSerif-Bold.ttf: DejaVu Serif:style=Bold
/usr/share/fonts/truetype/dejavu/DejaVuSansMono.ttf: DejaVu Sans Mono:style=Book
/usr/share/fonts/truetype/dejavu/DejaVuSans.ttf: DejaVu Sans:style=Book
/usr/share/fonts/truetype/dejavu/DejaVuSans-Bold.ttf: DejaVu Sans:style=Bold
/usr/share/fonts/truetype/dejavu/DejaVuSansMono-Bold.ttf: DejaVu Sans Mono:style=Bold
/usr/share/fonts/truetype/dejavu/DejaVuSerif.ttf: DejaVu Serif:style=Book
I'm not sure
shell> fc-list | grep Deja
is doing what you expect. You can't pipe in that way in Julia's shell mode REPL
And i thought, there is a reason, why this is called shell mode ...
Doing a simple fc-list (in julia) i can see in the terminal some DejaVu in the above paths
And i thought, there is a reason, why this is called shell mode ...
There is a reason why it's called "Julia's shell mode" and not "your system's shell": it's Julia doing the parsing of the commands, not your shell.
I see.
With JuliaPackaging/Yggdrasil#1287 I finally get a sans serif font in the example, as expected. Could you please confirm that it works also for you after updating the packages in the registry? You should get Fontconfig_jll
v2.13.1+12. This is what I get now:
For comparison, the image in master
is
I might come up with some questions, but i put them then to the Yggdrasil issue...