@@ -1240,58 +1240,115 @@ def get_underline_thickness(self, font, fontsize, dpi):
12401240# The number of different sizes of chars to use, beyond which they will not
12411241# get any smaller
12421242NUM_SIZE_LEVELS = 6
1243- # Percentage of x-height of additional horiz. space after sub/superscripts
1244- SCRIPT_SPACE = {'cm' : 0.075 ,
1245- 'stix' : 0.10 ,
1246- 'stixsans' : 0.05 ,
1247- 'dejavuserif' : 0.05 ,
1248- 'dejavusans' : 0.05 }
1249- ## Percentage of x-height that sub/superscripts drop below the baseline
1250- SUBDROP = {'cm' : 0.2 ,
1251- 'stix' : 0.4 ,
1252- 'stixsans' : 0.4 ,
1253- 'dejavuserif' : 0.4 ,
1254- 'dejavusans' : 0.4 }
1255- # Percentage of x-height that superscripts are raised from the baseline
1256- SUP1 = {'cm' : 0.45 ,
1257- 'stix' : 0.8 ,
1258- 'stixsans' : 0.8 ,
1259- 'dejavuserif' : 0.7 ,
1260- 'dejavusans' : 0.7 }
1261- # Percentage of x-height that subscripts drop below the baseline
1262- SUB1 = {'cm' : 0.2 ,
1263- 'stix' : 0.3 ,
1264- 'stixsans' : 0.3 ,
1265- 'dejavuserif' : 0.3 ,
1266- 'dejavusans' : 0.3 }
1267- # Percentage of x-height that subscripts drop below the baseline when a
1268- # superscript is present
1269- SUB2 = {'cm' : 0.3 ,
1270- 'stix' : 0.6 ,
1271- 'stixsans' : 0.5 ,
1272- 'dejavuserif' : 0.5 ,
1273- 'dejavusans' : 0.5 }
1274- # Percentage of x-height that sub/supercripts are offset relative to the
1275- # nucleus edge for non-slanted nuclei
1276- DELTA = {'cm' : 0.075 ,
1277- 'stix' : 0.05 ,
1278- 'stixsans' : 0.025 ,
1279- 'dejavuserif' : 0.025 ,
1280- 'dejavusans' : 0.025 }
1281- # Additional percentage of last character height above 2/3 of the x-height that
1282- # supercripts are offset relative to the subscript for slanted nuclei
1283- DELTASLANTED = {'cm' : 0.3 ,
1284- 'stix' : 0.3 ,
1285- 'stixsans' : 0.6 ,
1286- 'dejavuserif' : 0.2 ,
1287- 'dejavusans' : 0.2 }
1288- # Percentage of x-height that supercripts and subscripts are offset for
1289- # integrals
1290- DELTAINTEGRAL = {'cm' : 0.3 ,
1291- 'stix' : 0.3 ,
1292- 'stixsans' : 0.3 ,
1293- 'dejavuserif' : 0.1 ,
1294- 'dejavusans' : 0.1 }
1243+
1244+
1245+ class FontConstantsBase (object ):
1246+ """
1247+ A set of constants that controls how certain things, such as sub-
1248+ and superscripts are laid out. These are all metrics that can't
1249+ be reliably retrieved from the font metrics in the font itself.
1250+ """
1251+ # Percentage of x-height of additional horiz. space after sub/superscripts
1252+ script_space = 0.05
1253+
1254+ # Percentage of x-height that sub/superscripts drop below the baseline
1255+ subdrop = 0.4
1256+
1257+ # Percentage of x-height that superscripts are raised from the baseline
1258+ sup1 = 0.7
1259+
1260+ # Percentage of x-height that subscripts drop below the baseline
1261+ sub1 = 0.3
1262+
1263+ # Percentage of x-height that subscripts drop below the baseline when a
1264+ # superscript is present
1265+ sub2 = 0.5
1266+
1267+ # Percentage of x-height that sub/supercripts are offset relative to the
1268+ # nucleus edge for non-slanted nuclei
1269+ delta = 0.025
1270+
1271+ # Additional percentage of last character height above 2/3 of the
1272+ # x-height that supercripts are offset relative to the subscript
1273+ # for slanted nuclei
1274+ delta_slanted = 0.2
1275+
1276+ # Percentage of x-height that supercripts and subscripts are offset for
1277+ # integrals
1278+ delta_integral = 0.1
1279+
1280+
1281+ class ComputerModernFontConstants (FontConstantsBase ):
1282+ script_space = 0.075
1283+ subdrop = 0.2
1284+ sup1 = 0.45
1285+ sub1 = 0.2
1286+ sub2 = 0.3
1287+ delta = 0.075
1288+ delta_slanted = 0.3
1289+ delta_integral = 0.3
1290+
1291+
1292+ class STIXFontConstants (FontConstantsBase ):
1293+ script_space = 0.1
1294+ sup1 = 0.8
1295+ sub2 = 0.6
1296+ delta = 0.05
1297+ delta_slanted = 0.3
1298+ delta_integral = 0.3
1299+
1300+
1301+ class STIXSansFontConstants (FontConstantsBase ):
1302+ script_space = 0.05
1303+ sup1 = 0.8
1304+ delta_slanted = 0.6
1305+ delta_integral = 0.3
1306+
1307+
1308+ class DejaVuSerifFontConstants (FontConstantsBase ):
1309+ pass
1310+
1311+
1312+ class DejaVuSansFontConstants (FontConstantsBase ):
1313+ pass
1314+
1315+
1316+ # Maps font family names to the FontConstantBase subclass to use
1317+ _font_constant_mapping = {
1318+ 'DejaVu Sans' : DejaVuSansFontConstants ,
1319+ 'DejaVu Sans Mono' : DejaVuSansFontConstants ,
1320+ 'DejaVu Serif' : DejaVuSerifFontConstants ,
1321+ 'cmb10' : ComputerModernFontConstants ,
1322+ 'cmex10' : ComputerModernFontConstants ,
1323+ 'cmmi10' : ComputerModernFontConstants ,
1324+ 'cmr10' : ComputerModernFontConstants ,
1325+ 'cmss10' : ComputerModernFontConstants ,
1326+ 'cmsy10' : ComputerModernFontConstants ,
1327+ 'cmtt10' : ComputerModernFontConstants ,
1328+ 'STIXGeneral' : STIXFontConstants ,
1329+ 'STIXNonUnicode' : STIXFontConstants ,
1330+ 'STIXSizeFiveSym' : STIXFontConstants ,
1331+ 'STIXSizeFourSym' : STIXFontConstants ,
1332+ 'STIXSizeThreeSym' : STIXFontConstants ,
1333+ 'STIXSizeTwoSym' : STIXFontConstants ,
1334+ 'STIXSizeOneSym' : STIXFontConstants ,
1335+ # Map the fonts we used to ship, just for good measure
1336+ 'Bitstream Vera Sans' : DejaVuSansFontConstants ,
1337+ 'Bitstream Vera' : DejaVuSansFontConstants ,
1338+ }
1339+
1340+
1341+ def _get_font_constant_set (state ):
1342+ constants = _font_constant_mapping .get (
1343+ state .font_output ._get_font (state .font ).family_name ,
1344+ FontConstantsBase )
1345+ # STIX sans isn't really its own fonts, just different code points
1346+ # in the STIX fonts, so we have to detect this one separately.
1347+ if (constants is STIXFontConstants and
1348+ isinstance (state .font_output , StixSansFonts )):
1349+ return STIXSansFontConstants
1350+ return constants
1351+
12951352
12961353class MathTextWarning (Warning ):
12971354 pass
@@ -2873,25 +2930,24 @@ def subsuper(self, s, loc, toks):
28732930 nucleus = Hlist ([nucleus ])
28742931
28752932 # Handle regular sub/superscripts
2876-
2877- fs = rcParams ['mathtext.fontset' ]
2878- if fs == 'custom' :
2879- fs = 'dejavusans'
2880-
2933+ constants = _get_font_constant_set (state )
28812934 lc_height = last_char .height
28822935 lc_baseline = 0
28832936 if self .is_dropsub (last_char ):
28842937 lc_baseline = last_char .depth
28852938
28862939 # Compute kerning for sub and super
2887- superkern = DELTA [ fs ] * xHeight
2888- subkern = DELTA [ fs ] * xHeight
2940+ superkern = constants . delta * xHeight
2941+ subkern = constants . delta * xHeight
28892942 if self .is_slanted (last_char ):
2890- superkern += DELTA [fs ] * xHeight
2891- superkern += DELTASLANTED [fs ] * (lc_height - xHeight * 2. / 3. )
2943+ superkern += constants .delta * xHeight
2944+ superkern += (constants .delta_slanted *
2945+ (lc_height - xHeight * 2. / 3. ))
28922946 if self .is_dropsub (last_char ):
2893- subkern = (3 * DELTA [fs ] - DELTAINTEGRAL [fs ]) * lc_height
2894- superkern = (3 * DELTA [fs ] + DELTAINTEGRAL [fs ]) * lc_height
2947+ subkern = (3 * constants .delta -
2948+ constants .delta_integral ) * lc_height
2949+ superkern = (3 * constants .delta +
2950+ constants .delta_integral ) * lc_height
28952951 else :
28962952 subkern = 0
28972953
@@ -2900,26 +2956,26 @@ def subsuper(self, s, loc, toks):
29002956 x = Hlist ([Kern (subkern ), sub ])
29012957 x .shrink ()
29022958 if self .is_dropsub (last_char ):
2903- shift_down = lc_baseline + SUBDROP [ fs ] * xHeight
2959+ shift_down = lc_baseline + constants . subdrop * xHeight
29042960 else :
2905- shift_down = SUB1 [ fs ] * xHeight
2961+ shift_down = constants . sub1 * xHeight
29062962 x .shift_amount = shift_down
29072963 else :
29082964 x = Hlist ([Kern (superkern ), super ])
29092965 x .shrink ()
29102966 if self .is_dropsub (last_char ):
2911- shift_up = lc_height - SUBDROP [ fs ] * xHeight
2967+ shift_up = lc_height - constants . subdrop * xHeight
29122968 else :
2913- shift_up = SUP1 [ fs ] * xHeight
2969+ shift_up = constants . sup1 * xHeight
29142970 if sub is None :
29152971 x .shift_amount = - shift_up
29162972 else : # Both sub and superscript
29172973 y = Hlist ([Kern (subkern ),sub ])
29182974 y .shrink ()
29192975 if self .is_dropsub (last_char ):
2920- shift_down = lc_baseline + SUBDROP [ fs ] * xHeight
2976+ shift_down = lc_baseline + constants . subdrop * xHeight
29212977 else :
2922- shift_down = SUB2 [ fs ] * xHeight
2978+ shift_down = constants . sub2 * xHeight
29232979 # If sub and superscript collide, move super up
29242980 clr = (2.0 * rule_thickness -
29252981 ((shift_up - x .depth ) - (y .height - shift_down )))
@@ -2931,8 +2987,9 @@ def subsuper(self, s, loc, toks):
29312987 x .shift_amount = shift_down
29322988
29332989 if not self .is_dropsub (last_char ):
2934- x .width += SCRIPT_SPACE [ fs ] * xHeight
2990+ x .width += constants . script_space * xHeight
29352991 result = Hlist ([nucleus , x ])
2992+
29362993 return [result ]
29372994
29382995 def _genfrac (self , ldelim , rdelim , rule , style , num , den ):
0 commit comments