From 47b4f09786f1edff0a65a9c52eb4f62612f3f5e3 Mon Sep 17 00:00:00 2001 From: Gregory Heytings Date: Wed, 7 Dec 2022 23:15:06 +0000 Subject: [PATCH] Unset the weight/slant/width in the spec when realizing a font Between commits bf0d3f76dc (2014) and 6b1ed2f2c9 (2022), realize_gui_face called font_load_for_lface with an empty or partly emptied font spec, i.e. it ignored a part of its attrs argument. The rationale given in bug#17973, which led to bf0d3f76dc, is not clear. However, 6b1ed2f2c9, which passes the full font spec to font_load_for_lface and font_find_for_lface, leads to suboptimal font choices, for example when the font chosen for the default face has a weight, slant or width that is not supported by other available fonts on the system, such as 'medium' or 'heavy'. If these attributes are not unset here, the call to font_list_entities in font_find_for_lface arbitrarily limits the candidate font list to those that are perfect matches for these attributes, which means that the scoring mechanism is bypassed. Note that the size attribute in spec is also unset, in font_find_for_lface. * src/xfaces.c (realize_gui_face): Unset the weight, slant and width of the font spec. Fixes bug#57555 and bug#59347. --- src/xfaces.c | 20 ++++++++++++++++++-- 1 file changed, 18 insertions(+), 2 deletions(-) diff --git a/src/xfaces.c b/src/xfaces.c index df078227c8..71042a3126 100644 --- a/src/xfaces.c +++ b/src/xfaces.c @@ -6071,8 +6071,24 @@ realize_gui_face (struct face_cache *cache, Lisp_Object attrs[LFACE_VECTOR_SIZE] emacs_abort (); } if (! FONT_OBJECT_P (attrs[LFACE_FONT_INDEX])) - attrs[LFACE_FONT_INDEX] - = font_load_for_lface (f, attrs, attrs[LFACE_FONT_INDEX]); + { + Lisp_Object spec = copy_font_spec (attrs[LFACE_FONT_INDEX]); + /* Unset the weight, slant and width in spec. The best + possible values for these attributes is determined in + font_find_for_lface, called by font_load_for_lface, when + the candidate list returned by font_list_entities is + sorted by font_select_entity (which calls + font_sort_entities, which calls font_score). If these + attributes are not unset here, the candidate font list + returned by font_list_entities only contains fonts that + are exact matches for these weight, slant and width + attributes, which leads to suboptimal or wrong font + choices. See bug#59347. */ + ASET (spec, FONT_WEIGHT_INDEX, Qnil); + ASET (spec, FONT_SLANT_INDEX, Qnil); + ASET (spec, FONT_WIDTH_INDEX, Qnil); + attrs[LFACE_FONT_INDEX] = font_load_for_lface (f, attrs, spec); + } if (FONT_OBJECT_P (attrs[LFACE_FONT_INDEX])) { face->font = XFONT_OBJECT (attrs[LFACE_FONT_INDEX]); -- 2.35.1