diff --git a/font-patcher b/font-patcher index 5e7b8e3ce..9187858d0 100755 --- a/font-patcher +++ b/font-patcher @@ -969,17 +969,33 @@ class font_patcher: # print("FINAL", self.font_dim) - def get_scale_factor(self, sym_dim): - scale_ratio = 1 + def get_scale_factors(self, sym_dim, stretch): + """ Get scale in x and y as tuple """ + # It is possible to have empty glyphs, so we need to skip those. + if not sym_dim['width'] or not sym_dim['height']: + return (1.0, 1.0) - # We want to preserve x/y aspect ratio, so find biggest scale factor that allows symbol to fit - scale_ratio_x = self.font_dim['width'] / sym_dim['width'] - scale_ratio_y = self.font_dim['height'] / sym_dim['height'] - if scale_ratio_x > scale_ratio_y: - scale_ratio = scale_ratio_y + # For monospaced fonts all chars need to be maximum 'one' space wide + target_width = self.font_dim['width'] + scale_ratio_x = target_width / sym_dim['width'] + + # font_dim['height'] represents total line height, keep our symbols sized based upon font's em + # Use the font_dim['height'] only for explicit 'y' scaling (not 'pa') + target_height = self.font_dim['height'] + scale_ratio_y = target_height / sym_dim['height'] + + if stretch == 'pa': + # We want to preserve x/y aspect ratio, so find biggest scale factor that allows symbol to fit + scale_ratio_x = min(scale_ratio_x, scale_ratio_y) + scale_ratio_y = scale_ratio_x else: - scale_ratio = scale_ratio_x - return scale_ratio + # Keep the not-stretched direction + if not 'x' in stretch: + scale_ratio_x = 1.0 + if not 'y' in stretch: + scale_ratio_y = 1.0 + + return (scale_ratio_x, scale_ratio_y) def copy_glyphs(self, sourceFontStart, symbolFont, symbolFontStart, symbolFontEnd, exactEncoding, scaleRules, setName, attributes): @@ -1039,6 +1055,10 @@ class font_patcher: currentSourceFontGlyph = sourceFontStart + sourceFontCounter sourceFontCounter += 1 + # For debugging process only limited glyphs + # if currentSourceFontGlyph != 0xe7bd: + # continue + if not self.args.quiet: if self.args.progressbars: update_progress(round(float(index + 1) / glyphSetLength, 2)) @@ -1077,48 +1097,20 @@ class font_patcher: # Prepare symbol glyph dimensions sym_dim = get_glyph_dimensions(self.sourceFont[currentSourceFontGlyph]) - scale_ratio_x = 1 - scale_ratio_y = 1 + if glyph_scale_data is not None: + # This is roughly alike get_scale_factors(glyph_scale_data[1], 'pa') + # Except we do not have glyph_scale_data[1] always... + (scale_ratio_x, scale_ratio_y) = (glyph_scale_data[0], glyph_scale_data[0]) + else: + (scale_ratio_x, scale_ratio_y) = self.get_scale_factors(sym_dim, sym_attr['stretch']) - # Now that we have copy/pasted the glyph, if we are creating a monospace - # font we need to scale and move the glyphs. It is possible to have - # empty glyphs, so we need to skip those. - if self.args.single and sym_dim['width'] and sym_dim['height']: - # If we want to preserve that aspect ratio of the glyphs we need to - # find the largest possible scaling factor that will allow the glyph - # to fit in both the x and y directions - if sym_attr['stretch'] == 'pa': - scale_ratio_x = None - if glyph_scale_data: - # We want to preserve the relative size of each glyph in a glyph group - scale_ratio_x = glyph_scale_data[0] - if scale_ratio_x is None: - # In the remaining cases, each glyph is sized independently to each other - scale_ratio_x = self.get_scale_factor(sym_dim) - scale_ratio_y = scale_ratio_x - else: - if 'x' in sym_attr['stretch']: - # Stretch the glyph horizontally to fit the entire available width - scale_ratio_x = None - if glyph_scale_data is not None and glyph_scale_data[1] is not None: - scale_ratio_x = self.font_dim['width'] / glyph_scale_data[1]['width'] - if scale_ratio_x is None: - scale_ratio_x = self.font_dim['width'] / sym_dim['width'] - # end if single width - - # non-monospace (double width glyphs) - # elif sym_dim['width'] and sym_dim['height']: - # any special logic we want to apply for double-width variation - # would go here - - if 'y' in sym_attr['stretch']: - # Stretch the glyph vertically to total line height (good for powerline separators) - # Currently stretching vertically for both monospace and double-width - scale_ratio_y = None - if glyph_scale_data is not None and glyph_scale_data[1] is not None: - scale_ratio_y = self.font_dim['height'] / glyph_scale_data[1]['height'] - if scale_ratio_y is None: - scale_ratio_y = self.font_dim['height'] / sym_dim['height'] + if not self.args.single: + # any special logic we want to apply for double-width variation + # would go here: + # non monospaced fonts just scale y, on 'y' scale request (not 'pa') + scale_ratio_x = 1.0 + if not 'y' in sym_attr['stretch']: + scale_ratio_y = 1.0 overlap = sym_attr['params'].get('overlap') @@ -1286,7 +1278,7 @@ class font_patcher: # 'bbdims': [ dim_dict1, dim_dict2, ] } # # Each item in 'ScaleGroups' (a range or an explicit list) forms a group of glyphs that shall be - # as rescaled all with the same and maximum possible (for the included glyphs) factor. + # as rescaled all with the same and maximum possible (for the included glyphs) 'pa' factor. # If the 'bbdims' is present they all shall be shifted in the same way. # # Previously this structure has been used: @@ -1307,7 +1299,7 @@ class font_patcher: scaleRules['ScaleGroups'] = [] for group in scaleRules['ScaleGroups']: sym_dim = get_multiglyph_boundingBox([ symbolFont[g] if g in symbolFont else None for g in group ], destGlyph) - scale = self.get_scale_factor(sym_dim) + scale = self.get_scale_factors(sym_dim, 'pa')[0] scaleRules['scales'].append(scale) scaleRules['bbdims'].append(sym_dim) @@ -1320,7 +1312,7 @@ class font_patcher: else: group_list.append(i) sym_dim = get_glyph_dimensions(symbolFont[scaleRules['ScaleGlyph']]) - scale = self.get_scale_factor(sym_dim) + scale = self.get_scale_factors(sym_dim, 'pa')[0] scaleRules['ScaleGroups'].append(group_list) scaleRules['scales'].append(scale) scaleRules['bbdims'].append(None) # The 'old' style keeps just the scale, not the positioning