From d22634e518078a9a51c9a30b44a72e0c9e7c96cd Mon Sep 17 00:00:00 2001 From: YAMAMOTO Mitsuharu Date: Wed, 30 Sep 2015 18:56:30 +0900 Subject: [PATCH] Work around crash when displaying etc/HELLO on OS X 10.11 * src/macfont.m (mac_font_get_weight) (mac_font_descriptor_get_adjusted_weight): New functions. (macfont_store_descriptor_attributes): Adjust weight. --- src/macfont.m | 58 ++++++++++++++++++++++++++++++++++++++++++++++++--- 1 file changed, 55 insertions(+), 3 deletions(-) diff --git a/src/macfont.m b/src/macfont.m index 69640766d4e..cfe0e0a2b92 100644 --- a/src/macfont.m +++ b/src/macfont.m @@ -190,6 +190,14 @@ cfstring_create_with_string_noencode (Lisp_Object s) return string; } +static CFIndex +mac_font_get_weight (CTFontRef font) +{ + NSFont *nsFont = (NSFont *) font; + + return [[NSFontManager sharedFontManager] weightOfFont:nsFont]; +} + static CGFloat mac_screen_font_get_advance_width_for_glyph (ScreenFontRef font, CGGlyph glyph) { @@ -758,6 +766,46 @@ cfnumber_get_font_symbolic_traits_value (CFNumberRef number, return false; } +static CGFloat +mac_font_descriptor_get_adjusted_weight (CTFontDescriptorRef desc, CGFloat val) +{ + long percent_val = lround (val * 100); + + if (percent_val == -40 || percent_val == 56) + { + CTFontRef font = NULL; + CFStringRef name = + CTFontDescriptorCopyAttribute (desc, kCTFontNameAttribute); + + if (name) + { + font = CTFontCreateWithName (name, 0, NULL); + CFRelease (name); + } + if (font) + { + CFIndex weight = mac_font_get_weight (font); + + if (percent_val == -40) + { + /* Workaround for crash when displaying Oriya characters + with Arial Unicode MS on OS X 10.11. */ + if (weight == 5) + val = 0; + } + else /* percent_val == 56 */ + { + if (weight == 9) + /* Adjustment for HiraginoSans-W7 on OS X 10.11. */ + val = 0.4; + } + CFRelease (font); + } + } + + return val; +} + static void macfont_store_descriptor_attributes (CTFontDescriptorRef desc, Lisp_Object spec_or_entity) @@ -781,6 +829,7 @@ macfont_store_descriptor_attributes (CTFontDescriptorRef desc, enum font_property_index index; CFStringRef trait; CGPoint points[6]; + CGFloat (*adjust_func) (CTFontDescriptorRef, CGFloat); } numeric_traits[] = {{FONT_WEIGHT_INDEX, kCTFontWeightTrait, {{-0.4, 50}, /* light */ @@ -788,11 +837,12 @@ macfont_store_descriptor_attributes (CTFontDescriptorRef desc, {0, 100}, /* normal */ {0.24, 140}, /* (semi-bold + normal) / 2 */ {0.4, 200}, /* bold */ - {CGFLOAT_MAX, CGFLOAT_MAX}}}, + {CGFLOAT_MAX, CGFLOAT_MAX}}, + mac_font_descriptor_get_adjusted_weight}, {FONT_SLANT_INDEX, kCTFontSlantTrait, - {{0, 100}, {0.1, 200}, {CGFLOAT_MAX, CGFLOAT_MAX}}}, + {{0, 100}, {0.1, 200}, {CGFLOAT_MAX, CGFLOAT_MAX}}, NULL}, {FONT_WIDTH_INDEX, kCTFontWidthTrait, - {{0, 100}, {1, 200}, {CGFLOAT_MAX, CGFLOAT_MAX}}}}; + {{0, 100}, {1, 200}, {CGFLOAT_MAX, CGFLOAT_MAX}}, NULL}}; int i; for (i = 0; i < ARRAYELTS (numeric_traits); i++) @@ -802,6 +852,8 @@ macfont_store_descriptor_attributes (CTFontDescriptorRef desc, { CGPoint *point = numeric_traits[i].points; + if (numeric_traits[i].adjust_func) + floatval = (*numeric_traits[i].adjust_func) (desc, floatval); while (point->x < floatval) point++; if (point == numeric_traits[i].points) -- 2.39.2