Each frame is a different instance of 'emacs -Q -fn "DejaVu Sans Mono-9"'[4]. The left frame is configured --with-cairo, without my patch; the top-right one is without cairo, the bottom-right --with-cairo with my patch. On the third setup I could test[5], all three builds look the same AFAICT; no idea what this can be attributed to. Does this patch look like something that can be applied unconditionally? - CAIRO_HINT_STYLE_SLIGHT has been available from version 1.0, and we require 1.12, so AFAICT the setting can be used without checking for any CAIRO_… feature. - On the other hand, maybe this setting should be conditioned by a user option: as far as I could test, …_SLIGHT gives the "best" visual result[6], but maybe this is specific to my setups. I guess that a customizable option would need to specify a :set function tasked with making a few Cairo calls for the change to be effective without restarting; I have not spent much time looking at ftcrfont.c and its users yet, but I imagine that this hypothetical setter function should do something along the lines of: 1. retrieve all 'struct font_info' objects created with ftcrfont_open, 2. call cairo_scaled_font_get_font_options on their 'cr_scaled_font' field, 3. call …set_hint_style on the returned options. (… This is absolutely untested guesswork.) Caveat: I do not know the first thing about font rendering (or any kind of rendering for that matter), nor font hinting. This patch is the result of me googling around for "cairo smooth font" and trying out random snippets to tweak cairo_font_options_* knobs. Some snippets I have seen call …set_{antialias,subpixel_order} in conjunction with …set_hint_style; as far as I tested, the former two have no impact, so I left them out of the patch. Let me know if I should provide more information (font configuration, results after tweaking other settings… though I cannot access my desktops until Monday), and thank you for your time! [1] Objectively-speaking, the patch merely makes fonts "visually equivalent to the non-Cairo build"; whether it makes them "more readable" is a matter of taste I guess. [2] OS: Xubuntu 16.04 (libcairo2: 1.14.6) xrandr digest: DP-2 1920x1080 509mm x 286mm emacs-repository-version: … probably a commit on master from these past two weeks [3] OS: Debian stretch (libcairo2: 1.14.8) xrandr digest: LVDS1 1024x600 230mm x 140mm emacs-repository-version: e0ee41d155b210327eb9c9ad5334f80ed59439f4 [4] emacs -Q defaults to a bigger font size than what I use, and the "sharpness" difference is less visible then. [5] OS: openSUSE Tumbleweed (cairo: 1.16.0) xrandr digest: DVI-I-0 1680x1050 474mm x 296mm emacs-repository-version: … probably a commit on master from these past two weeks [6] Compiling with any other enum value looked equivalent to not setting this option at all IIRC. In GNU Emacs 27.0.50 (build 3, i686-pc-linux-gnu, GTK+ Version 3.22.11) of 2019-05-13 built on nc10-laptop Repository revision: d2d4916046e31e46598f0a0edbc65e75b8cb4cc3 Repository branch: master Windowing system distributor 'The X.Org Foundation', version 11.0.11902000 System Description: BunsenLabs GNU/Linux 9.8 (Helium) Recent messages: nnimap read 178k from imap.gmail.com (initial sync of 11 groups; please wait) nnimap read 222k from imap.gmail.com (initial sync of 11 groups; please wait) nnimap read 257k from imap.gmail.com (initial sync of 11 groups; please wait) Reading active file from archive via nnfolder...done Reading active file via nndraft...done Checking new news...done nnimap read 0k from imap.gmail.com No more unseen articles Mark set Quit [2 times] Configured using: 'configure --with-xwidgets' Configured features: XPM JPEG TIFF GIF PNG RSVG IMAGEMAGICK SOUND GPM DBUS GSETTINGS GLIB NOTIFY INOTIFY ACL LIBSELINUX GNUTLS LIBXML2 FREETYPE M17N_FLT LIBOTF XFT ZLIB TOOLKIT_SCROLL_BARS GTK3 X11 XDBE XIM THREADS XWIDGETS JSON PDUMPER LCMS2 GMP Important settings: value of $LANG: en_US.UTF-8 locale-coding-system: utf-8-unix Major mode: Summary Minor modes in effect: global-magit-file-mode: t magit-auto-revert-mode: t global-git-commit-mode: t async-bytecomp-package-mode: t shell-dirtrack-mode: t show-paren-mode: t minibuffer-depth-indicate-mode: t icomplete-mode: t global-page-break-lines-mode: t page-break-lines-mode: t electric-pair-mode: t diff-hl-flydiff-mode: t global-diff-hl-mode: t delete-selection-mode: t tooltip-mode: t global-eldoc-mode: t electric-indent-mode: t mouse-wheel-mode: t file-name-shadow-mode: t global-font-lock-mode: t font-lock-mode: t blink-cursor-mode: t auto-composition-mode: t auto-encryption-mode: t auto-compression-mode: t buffer-read-only: t column-number-mode: t line-number-mode: t transient-mark-mode: t Load-path shadows: None found. Features: (shadow emacsbug rect cl-print debug backtrace magit-extras magit-patch magit-subtree magit-ediff ediff-merg ediff-wind ediff-diff ediff-mult ediff-help ediff-init ediff-util ediff org-indent org-rmail org-mhe org-irc org-info org-gnus org-docview doc-view image-mode org-bibtex bibtex org-bbdb org-w3m org-element avl-tree org org-macro org-footnote org-pcomplete org-list org-faces org-entities org-version ob-emacs-lisp ob ob-tangle org-src ob-ref ob-lob ob-table ob-keys ob-exp ob-comint ob-core ob-eval org-compat org-macs org-loaddefs cal-menu calendar cal-loaddefs bug-reference magit-submodule magit-obsolete magit-blame magit-stash magit-reflog magit-bisect magit-push magit-pull magit-fetch magit-clone magit-remote magit-commit magit-sequence magit-notes magit-worktree magit-tag magit-merge magit-branch magit-reset magit-files magit-refs magit-status magit magit-repos magit-apply magit-wip magit-log which-func imenu magit-diff smerge-mode magit-core magit-autorevert autorevert filenotify magit-margin magit-transient magit-process magit-mode transient git-commit magit-git magit-section log-edit pcvs-util add-log with-editor async-bytecomp async server url-util sendmail nnir eieio-opt speedbar sb-image ezimage dframe gnus-fun shr-color color shr svg dom browse-url sort gnus-cite mm-archive mail-extr gnus-async gnus-bcklg qp gnus-ml nndraft nnmh nnfolder utf-7 epa-file gnutls network-stream nsm gnus-agent gnus-srvr gnus-score score-mode nnvirtual gnus-msg gnus-art mm-uu mml2015 mm-view mml-smime smime dig mailcap nntp gnus-cache gnus-sum gnus-group gnus-undo gnus-start gnus-cloud nnimap nnmail mail-source utf7 netrc nnoo parse-time gnus-spec gnus-int gnus-range gnus-win gnus nnheader find-func help-fns radix-tree conf-mode magit-utils crm dash jka-compr pulse find-dired ffap etags fileloop generator xref cus-edit wid-edit whitespace notifications dbus xml thingatpt noutline outline view message rmc puny dired dired-loaddefs format-spec rfc822 mml mml-sec epa derived epg gnus-util rmail rmail-loaddefs text-property-search time-date mm-decode mm-bodies mm-encode mail-parse rfc2231 rfc2047 rfc2045 mm-util ietf-drums mail-prsvr mailabbrev mail-utils gmm-utils mailheader flyspell ispell executable shell pcomplete misearch multi-isearch vc-mtn vc-hg cc-mode cc-fonts cc-guess cc-menus cc-cmds cc-styles cc-align cc-engine cc-vars cc-defs footnote rx vc-git vc-bzr vc-src vc-sccs vc-svn vc-cvs vc-rcs project delight advice eighters-theme quail cl-extra help-mode rg rg-ibuffer rg-result wgrep-rg wgrep s rg-history rg-header rg-compat ibuf-ext ibuffer ibuffer-loaddefs grep compile comint ansi-color ring edmacro kmacro disp-table paren mb-depth icomplete page-break-lines elec-pair diff-hl-flydiff diff diff-hl vc-dir ewoc vc vc-dispatcher diff-mode easy-mmode delsel cus-start cus-load mule-util tex-site info package easymenu epg-config url-handlers url-parse auth-source cl-seq eieio eieio-core cl-macs eieio-loaddefs password-cache json subr-x map url-vars seq byte-opt gv bytecomp byte-compile cconv cl-loaddefs cl-lib tooltip eldoc electric uniquify ediff-hook vc-hooks lisp-float-type mwheel term/x-win x-win term/common-win x-dnd tool-bar dnd fontset image regexp-opt fringe tabulated-list replace newcomment text-mode elisp-mode lisp-mode prog-mode register page menu-bar rfn-eshadow isearch timer select scroll-bar mouse jit-lock font-lock syntax facemenu font-core term/tty-colors frame cl-generic cham georgian utf-8-lang misc-lang vietnamese tibetan thai tai-viet lao korean japanese eucjp-ms cp51932 hebrew greek romanian slovak czech european ethiopic indian cyrillic chinese composite charscript charprop case-table epa-hook jka-cmpr-hook help simple abbrev obarray minibuffer cl-preloaded nadvice loaddefs button faces cus-face macroexp files text-properties overlay sha1 md5 base64 format env code-pages mule custom widget hashtable-print-readable backquote threads dbusbind inotify lcms2 dynamic-setting system-font-setting font-render-setting xwidget-internal move-toolbar gtk x-toolkit x multi-tty make-network-process emacs) Memory information: ((conses 8 510108 60620) (symbols 24 35458 1) (strings 16 125803 16010) (string-bytes 1 4146628) (vectors 8 59808) (vector-slots 4 1472134 107810) (floats 8 508 454) (intervals 28 32090 73) (buffers 564 69))