From 772770971780b29bed36c11658bf5607bd1e50d3 Mon Sep 17 00:00:00 2001 From: miiton <468745+miiton@users.noreply.github.com> Date: Thu, 27 Jun 2019 23:09:11 +0900 Subject: [PATCH 01/31] =?UTF-8?q?=F0=9F=92=B0=20class=E6=96=87=E3=81=AB?= =?UTF-8?q?=E3=81=A1=E3=82=87=E3=81=A3=E3=81=A8=E6=95=B4=E7=90=86?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- cica.py | 1612 ++++++++++++++++++++++++++++--------------------------- 1 file changed, 820 insertions(+), 792 deletions(-) diff --git a/cica.py b/cica.py index 73284c31..777bbcf6 100644 --- a/cica.py +++ b/cica.py @@ -18,127 +18,17 @@ VERSION = '5.0.1' FAMILY = 'Cica' -fonts = [ - { - 'family': FAMILY, - 'name': FAMILY + '-Regular', - 'filename': FAMILY + '-Regular.ttf', - 'weight': 400, - 'weight_name': 'Regular', - 'style_name': 'Regular', - 'hack': 'Hack-Regular.ttf', - 'mgen_plus': 'rounded-mgenplus-1m-regular.ttf', - 'hack_weight_reduce': 0, - 'mgen_weight_add': 0, - 'italic': False, - }, { - 'family': FAMILY, - 'name': FAMILY + '-RegularItalic', - 'filename': FAMILY + '-RegularItalic.ttf', - 'weight': 400, - 'weight_name': 'Regular', - 'style_name': 'Italic', - 'hack': 'Hack-Regular.ttf', - 'mgen_plus': 'rounded-mgenplus-1m-regular.ttf', - 'hack_weight_reduce': 0, - 'mgen_weight_add': 0, - 'italic': True, - }, { - 'family': FAMILY, - 'name': FAMILY + '-Bold', - 'filename': FAMILY + '-Bold.ttf', - 'weight': 700, - 'weight_name': 'Bold', - 'style_name': 'Bold', - 'hack': 'Hack-Bold.ttf', - 'mgen_plus': 'rounded-mgenplus-1m-bold.ttf', - 'hack_weight_reduce': 0, - 'mgen_weight_add': 0, - 'italic': False, - }, { - 'family': FAMILY, - 'name': FAMILY + '-BoldItalic', - 'filename': FAMILY + '-BoldItalic.ttf', - 'weight': 700, - 'weight_name': 'Bold', - 'style_name': 'Bold Italic', - 'hack': 'Hack-Bold.ttf', - 'mgen_plus': 'rounded-mgenplus-1m-bold.ttf', - 'hack_weight_reduce': 0, - 'mgen_weight_add': 0, - 'italic': True, - } -] def log(_str): + """ログ出力 + fontforgeにquietオプションが無いので悲しい + """ now = datetime.now().strftime('%Y-%m-%d %H:%M:%S') print(now + " " + _str) -def remove_glyph_from_hack(_font): - """Rounded Mgen+を採用したいグリフをHackから削除 - """ - glyphs = [ - 0x2026, # … - ] - - for g in glyphs: - _font.selection.select(g) - _font.clear() - - return _font - - -def check_files(): - err = 0 - for f in fonts: - if not os.path.isfile('./sourceFonts/%s' % f.get('hack')): - logger.error('%s not exists.' % f) - err = 1 - - if not os.path.isfile('./sourceFonts/%s' % f.get('mgen_plus')): - logger.error('%s not exists.' % f) - err = 1 - - - if err > 0: - sys.exit(err) - -def set_os2_values(_font, _info): - weight = _info.get('weight') - style_name = _info.get('style_name') - _font.os2_weight = weight - _font.os2_width = 5 - _font.os2_fstype = 0 - if style_name == 'Regular': - _font.os2_stylemap = 64 - elif style_name == 'Bold': - _font.os2_stylemap = 32 - elif style_name == 'Italic': - _font.os2_stylemap = 1 - elif style_name == 'Bold Italic': - _font.os2_stylemap = 33 - _font.os2_vendor = 'TMNM' - _font.os2_version = 1 - _font.os2_winascent = ASCENT - _font.os2_winascent_add = False - _font.os2_windescent = DESCENT - _font.os2_windescent_add = False - - _font.os2_typoascent = -150 - _font.os2_typoascent_add = True - _font.os2_typodescent = 100 - _font.os2_typodescent_add = True - _font.os2_typolinegap = 0 - - _font.hhea_ascent = -150 - _font.hhea_ascent_add = True - _font.hhea_descent = 100 - _font.hhea_descent_add = True - _font.hhea_linegap = 0 - _font.os2_panose = (2, 11, int(weight / 100), 9, 2, 2, 3, 2, 2, 7) - return _font - def align_to_center(_g): + """グリフを中央寄せにする + """ width = 0 if _g.width > 700: @@ -153,147 +43,47 @@ def align_to_center(_g): return _g def align_to_left(_g): + """グリフを左寄せにする + """ width = _g.width _g.left_side_bearing = 0 _g.width = width def align_to_right(_g): + """グリフを右寄せにする + """ width = _g.width bb = _g.boundingBox() left = width - (bb[2] - bb[0]) _g.left_side_bearing = left _g.width = width -def add_dejavu(_f, conf): - dejavu = None - weight_name = conf.get('weight_name') - if weight_name == "Regular": - dejavu = fontforge.open('./sourceFonts/DejaVuSansMono.ttf') - elif weight_name == "Bold": - dejavu = fontforge.open('./sourceFonts/DejaVuSansMono-Bold.ttf') - - for g in dejavu.glyphs(): - g.transform(psMat.compose(psMat.scale(0.45, 0.45), psMat.translate(-21, 0))) - g.width = 512 - - _f.importLookups(dejavu, dejavu.gpos_lookups) - - # 0x0300 - 0x036f - Combining Diacritical Marks - for g in dejavu.glyphs(): - if g.encoding < 0x0300 or g.encoding > 0x036f or g.encoding == 0x0398: - continue - else: - if len(g.references) > 0: - anchorPoints = g.anchorPoints - g.anchorPoints = () - g.transform(psMat.scale(2.22, 2.22)) - g.transform(psMat.translate(50, 0)) - g.width = 512 - g.anchorPoints = anchorPoints - - if g.encoding <= 0x0304: - anchorPoints = g.anchorPoints - g.anchorPoints = () - g.transform(psMat.scale(1.2, 1.2)) - g.transform(psMat.translate(-100, -60)) - g.width = 512 - g.anchorPoints = anchorPoints - elif g.encoding == 0x0305: - g.transform(psMat.translate(0, -60)) - elif g.encoding <= 0x0315: - g.transform(psMat.translate(0, 0)) - elif g.encoding <= 0x0317: - g.transform(psMat.translate(0, 302)) - elif g.encoding <= 0x0319: - g.transform(psMat.translate(0, 200)) - elif g.encoding <= 0x031b: - g.transform(psMat.translate(0, -60)) - elif g.encoding <= 0x031c: - g.transform(psMat.translate(0, 22)) - elif g.encoding <= 0x031f: - g.transform(psMat.translate(0, 141)) - elif g.encoding <= 0x0332: - g.transform(psMat.translate(0, 90)) - elif g.encoding == 0x0333: - g.transform(psMat.compose(psMat.scale(0.9, 0.9), psMat.translate(-415, 29))) - g.width = 512 - elif g.encoding <= 0x0338: - g.transform(psMat.translate(0, 0)) - elif g.encoding <= 0x033c: - g.transform(psMat.translate(0, 138)) - else: - g.transform(psMat.translate(0, 0)) - dejavu.selection.select(g.encoding) - dejavu.copy() - _f.selection.select(g.encoding) - _f.paste() - # 0x0370 - 0x03ff - GREEK - for g in dejavu.glyphs(): - if g.encoding < 0x0370 or g.encoding > 0x03ff or g.encoding == 0x0398: - continue - else: - if len(g.references) == 0: - bb = g.boundingBox() - g.anchorPoints = (('Anchor-7', 'mark', 256, bb[3] + 20),) - dejavu.selection.select(g.encoding) - dejavu.copy() - _f.selection.select(g.encoding) - _f.paste() - # 0x2100 - 0x214f Letterlike Symbols - for g in dejavu.glyphs(): - if g.encoding < 0x2100 or g.encoding > 0x214f or g.encoding == 0x2122: - continue - else: - if len(g.references) == 0: - dejavu.selection.select(g.encoding) - dejavu.copy() - _f.selection.select(g.encoding) - _f.paste() - # 0x2150 - 0x218f Number Forms - for g in dejavu.glyphs(): - if g.encoding < 0x2150 or g.encoding > 0x218f: - continue - else: - if len(g.references) == 0: - dejavu.selection.select(g.encoding) - dejavu.copy() - _f.selection.select(g.encoding) - _f.paste() - # 0x2190 - 0x21ff Arrows - # TODO: 矢印を全角のままにしたパターンも生成したい - for g in dejavu.glyphs(): - if g.encoding < 0x2190 or g.encoding > 0x21ff: - continue - else: - if len(g.references) == 0: - dejavu.selection.select(g.encoding) - dejavu.copy() - _f.selection.select(g.encoding) - _f.paste() - # 0x2200 - 0x22ff Mathematical Operators - for g in dejavu.glyphs(): - if g.encoding < 0x2200 or g.encoding > 0x22ff: - continue - else: - if len(g.references) == 0: - dejavu.selection.select(g.encoding) - dejavu.copy() - _f.selection.select(g.encoding) - _f.paste() - # 0x2300 - 0x23ff Miscellaneous Technical - for g in dejavu.glyphs(): - if g.encoding < 0x2300 or g.encoding > 0x23ff: - continue - else: - if len(g.references) == 0: - dejavu.selection.select(g.encoding) - dejavu.copy() - _f.selection.select(g.encoding) - _f.paste() - dejavu.close() - return _f +def fix_overflow(glyph): + """上が820を超えている、または下が-204を超えているグリフを + 1024x1024の枠にはまるように修正する + ※全角のグリフのみに実施する + """ + if glyph.width < 1024: + return glyph + if glyph.isWorthOutputting: + bb = glyph.boundingBox() + height = bb[3] - bb[1] + if height > 1024: + # resize + scale = 1024 / height + glyph.transform(psMat.scale(scale, scale)) + bb = glyph.boundingBox() + bottom = bb[1] + top = bb[3] + if bottom < -204: + glyph.transform(psMat.translate(0, -204 - bottom)) + elif top > 820: + glyph.transform(psMat.translate(0, 820 - top)) + return glyph def modify_nerd(_g): + """nerdfontの大きさと位置をCica用に調整 + """ align_left = [ 0xe0b0, 0xe0b1, 0xe0b4, 0xe0b5, 0xe0b8, 0xe0b9, 0xe0bc, 0xe0bd, 0xe0c0, 0xe0c1, 0xe0c4, 0xe0c6, 0xe0c8, 0xe0cc, 0xe0cd, @@ -395,597 +185,835 @@ def modify_nerd(_g): return _g - def modify_iconsfordevs(_g): + """iconsfordevsの大きさと位置をCica用に調整 + """ _g.transform(psMat.compose(psMat.scale(2), psMat.translate(0, -126))) _g.width = 1024 _g = align_to_center(_g) return _g -def vertical_line_to_broken_bar(_f): - _f.selection.select(0x00a6) - _f.copy() - _f.selection.select(0x007c) - _f.paste() - return _f - -def emdash_to_broken_dash(_f): - _f.selection.select(0x006c) - _f.copy() - _f.selection.select(0x2014) - _f.pasteInto() - _f.intersect() - return _f - -def mathglyph_to_double(_f): - pass - -def zenkaku_space(_f): - _f.selection.select(0x2610) - _f.copy() - _f.selection.select(0x3000) - _f.paste() - _f.selection.select(0x271a) - _f.copy() - _f.selection.select(0x3000) - _f.pasteInto() - _f.intersect() - for g in _f.selection.byGlyphs: - g = align_to_center(g) - return _f - -def zero(_f): - _f.selection.select(0x4f) - _f.copy() - _f.selection.select(0x30) - _f.paste() - _f.selection.select(0xb7) - _f.copy() - _f.selection.select(0x30) - _f.pasteInto() - for g in _f.selection.byGlyphs: - g = align_to_center(g) - return _f - -def modify_WM(_f): - _f.selection.select(0x57) - _f.transform(psMat.scale(0.95, 1.0)) - _f.copy() - _f.selection.select(0x4d) - _f.paste() - _f.transform(psMat.compose(psMat.rotate(math.radians(180)), psMat.translate(0, 627))) - for g in _f.selection.byGlyphs: - g = align_to_center(g) - return _f - -def modify_m(_f, _weight): - m = fontforge.open('./sourceFonts/m-Regular.sfd') - if _weight == 'Bold': - m.close() - m = fontforge.open('./sourceFonts/m-Bold.sfd') - m.selection.select(0x6d) - m.copy() - _f.selection.select(0x6d) - _f.paste() - for g in m.glyphs(): - if g.encoding == 0x6d: - anchorPoints = g.anchorPoints - for g in _f.glyphs(): - if g.encoding == 0x6d: - g.anchorPoints = anchorPoints - - return _f - - -def add_smalltriangle(_f): - _f.selection.select(0x25bc) - _f.copy() - _f.selection.select(0x25be) - _f.paste() - _f.transform(psMat.compose(psMat.scale(0.64), psMat.translate(0, 68))) - _f.copy() - _f.selection.select(0x25b8) - _f.paste() - _f.transform(psMat.rotate(math.radians(90))) - _f.transform(psMat.translate(0, 212)) - - for g in _f.glyphs(): - if g.encoding == 0x25be or g.encoding == 0x25b8: + +class Cica: + def __init__(self, family, name, output_name, weight, weight_name, style_name, src_font_en, src_font_jp): + self.family = family + self.name = name + self.output_name = output_name + self.weight = weight + self.weight_name = weight_name + self.style_name = style_name + self.src_font_en = src_font_en + self.src_font_jp = src_font_jp + self.check_files() + + def check_files(self): + """ファイルがあるかチェック + 無ければ1を返してコマンドを終了させる + """ + err = 0 + if not os.path.isfile('./sourceFonts/%s' % self.src_font_en): + log('%s not exists.' % self.src_font_en) + err = 1 + if not os.path.isfile('./sourceFonts/%s' % self.src_font_jp): + log('%s not exists.' % self.src_font_jp) + err = 1 + + if err > 0: + sys.exit(err) + + def remove_glyph_from_en(self, _font): + """jpフォント側を採用したいグリフをenフォントから削除 + """ + glyphs = [ + 0x2026, # … + ] + + for g in glyphs: + _font.selection.select(g) + _font.clear() + + return _font + + def set_os2_values(self, _font, _info): + """フォントメタ情報の設定 + """ + weight = _info.get('weight') + style_name = _info.get('style_name') + _font.os2_weight = weight + _font.os2_width = 5 + _font.os2_fstype = 0 + if style_name == 'Regular': + _font.os2_stylemap = 64 + elif style_name == 'Bold': + _font.os2_stylemap = 32 + elif style_name == 'Italic': + _font.os2_stylemap = 1 + elif style_name == 'Bold Italic': + _font.os2_stylemap = 33 + _font.os2_vendor = 'TMNM' + _font.os2_version = 1 + _font.os2_winascent = ASCENT + _font.os2_winascent_add = False + _font.os2_windescent = DESCENT + _font.os2_windescent_add = False + + _font.os2_typoascent = -150 + _font.os2_typoascent_add = True + _font.os2_typodescent = 100 + _font.os2_typodescent_add = True + _font.os2_typolinegap = 0 + + _font.hhea_ascent = -150 + _font.hhea_ascent_add = True + _font.hhea_descent = 100 + _font.hhea_descent_add = True + _font.hhea_linegap = 0 + _font.os2_panose = (2, 11, int(weight / 100), 9, 2, 2, 3, 2, 2, 7) + return _font + + + def add_dejavu(self, _f, conf): + dejavu = None + weight_name = conf.get('weight_name') + if weight_name == "Regular": + dejavu = fontforge.open('./sourceFonts/DejaVuSansMono.ttf') + elif weight_name == "Bold": + dejavu = fontforge.open('./sourceFonts/DejaVuSansMono-Bold.ttf') + + for g in dejavu.glyphs(): + g.transform(psMat.compose(psMat.scale(0.45, 0.45), psMat.translate(-21, 0))) g.width = 512 - g = align_to_center(g) - return _f + _f.importLookups(dejavu, dejavu.gpos_lookups) -def fix_box_drawings(_f): - left = [ - 0x2510, 0x2518, 0x2524, 0x2555, 0x2556, 0x2557, 0x255b, 0x255c, 0x255d, - 0x2561, 0x2562, 0x2563, 0x256e, 0x256f, 0x2574, 0x2578, - 0xf2510, 0xf2518, 0xf2524, 0xf2555, 0xf2556, 0xf2557, 0xf255b, 0xf255c, 0xf255d, - 0xff2561, 0xf2562, 0xf2563, 0xf256e, 0xf256f, 0xf2574, 0xf2578 - ] - right = [ - 0x250c, 0x2514, 0x251c, 0x2552, 0x2553, 0x2554, 0x2558, 0x2559, 0x255a, - 0x255e, 0x255f, 0x2560, 0x256d, 0x2570, 0x2576, 0x257a, - 0xf250c, 0xf2514, 0xf251c, 0xf2552, 0xf2553, 0xf2554, 0xf2558, 0xf2559, 0xf255a, - 0xf255e, 0xf255f, 0xf2560, 0xf256d, 0xf2570, 0xf2576, 0xf257a - ] + # 0x0300 - 0x036f - Combining Diacritical Marks + for g in dejavu.glyphs(): + if g.encoding < 0x0300 or g.encoding > 0x036f or g.encoding == 0x0398: + continue + else: + if len(g.references) > 0: + anchorPoints = g.anchorPoints + g.anchorPoints = () + g.transform(psMat.scale(2.22, 2.22)) + g.transform(psMat.translate(50, 0)) + g.width = 512 + g.anchorPoints = anchorPoints + + if g.encoding <= 0x0304: + anchorPoints = g.anchorPoints + g.anchorPoints = () + g.transform(psMat.scale(1.2, 1.2)) + g.transform(psMat.translate(-100, -60)) + g.width = 512 + g.anchorPoints = anchorPoints + elif g.encoding == 0x0305: + g.transform(psMat.translate(0, -60)) + elif g.encoding <= 0x0315: + g.transform(psMat.translate(0, 0)) + elif g.encoding <= 0x0317: + g.transform(psMat.translate(0, 302)) + elif g.encoding <= 0x0319: + g.transform(psMat.translate(0, 200)) + elif g.encoding <= 0x031b: + g.transform(psMat.translate(0, -60)) + elif g.encoding <= 0x031c: + g.transform(psMat.translate(0, 22)) + elif g.encoding <= 0x031f: + g.transform(psMat.translate(0, 141)) + elif g.encoding <= 0x0332: + g.transform(psMat.translate(0, 90)) + elif g.encoding == 0x0333: + g.transform(psMat.compose(psMat.scale(0.9, 0.9), psMat.translate(-415, 29))) + g.width = 512 + elif g.encoding <= 0x0338: + g.transform(psMat.translate(0, 0)) + elif g.encoding <= 0x033c: + g.transform(psMat.translate(0, 138)) + else: + g.transform(psMat.translate(0, 0)) + dejavu.selection.select(g.encoding) + dejavu.copy() + _f.selection.select(g.encoding) + _f.paste() + # 0x0370 - 0x03ff - GREEK + for g in dejavu.glyphs(): + if g.encoding < 0x0370 or g.encoding > 0x03ff or g.encoding == 0x0398: + continue + else: + if len(g.references) == 0: + bb = g.boundingBox() + g.anchorPoints = (('Anchor-7', 'mark', 256, bb[3] + 20),) + dejavu.selection.select(g.encoding) + dejavu.copy() + _f.selection.select(g.encoding) + _f.paste() + # 0x2100 - 0x214f Letterlike Symbols + for g in dejavu.glyphs(): + if g.encoding < 0x2100 or g.encoding > 0x214f or g.encoding == 0x2122: + continue + else: + if len(g.references) == 0: + dejavu.selection.select(g.encoding) + dejavu.copy() + _f.selection.select(g.encoding) + _f.paste() + # 0x2150 - 0x218f Number Forms + for g in dejavu.glyphs(): + if g.encoding < 0x2150 or g.encoding > 0x218f: + continue + else: + if len(g.references) == 0: + dejavu.selection.select(g.encoding) + dejavu.copy() + _f.selection.select(g.encoding) + _f.paste() + # 0x2190 - 0x21ff Arrows + # TODO: 矢印を全角のままにしたパターンも生成したい + for g in dejavu.glyphs(): + if g.encoding < 0x2190 or g.encoding > 0x21ff: + continue + else: + if len(g.references) == 0: + dejavu.selection.select(g.encoding) + dejavu.copy() + _f.selection.select(g.encoding) + _f.paste() + # 0x2200 - 0x22ff Mathematical Operators + for g in dejavu.glyphs(): + if g.encoding < 0x2200 or g.encoding > 0x22ff: + continue + else: + if len(g.references) == 0: + dejavu.selection.select(g.encoding) + dejavu.copy() + _f.selection.select(g.encoding) + _f.paste() + # 0x2300 - 0x23ff Miscellaneous Technical + for g in dejavu.glyphs(): + if g.encoding < 0x2300 or g.encoding > 0x23ff: + continue + else: + if len(g.references) == 0: + dejavu.selection.select(g.encoding) + dejavu.copy() + _f.selection.select(g.encoding) + _f.paste() + dejavu.close() + return _f + + + def vertical_line_to_broken_bar(self, _f): + """縦線を破線にする + """ + _f.selection.select(0x00a6) + _f.copy() + _f.selection.select(0x007c) + _f.paste() + return _f - for g in _f.glyphs(): - if g.encoding < 0x2500: - continue - if g.encoding > 0x256c and g.encoding < 0xf2500: - continue - if g.encoding in left: - align_to_left(g) - elif g.encoding in right: - align_to_right(g) - - return _f - -def reiwa(_f, _weight): - reiwa = fontforge.open('./sourceFonts/reiwa.sfd') - if _weight == 'Bold': - reiwa.close() - reiwa = fontforge.open('./sourceFonts/reiwa-Bold.sfd') - for g in reiwa.glyphs(): - if g.isWorthOutputting: - reiwa.selection.select(0x00) - reiwa.copy() - _f.selection.select(0x32ff) - _f.paste() - reiwa.close() - return _f + def emdash_to_broken_dash(self, _f): + """ダッシュ記号を破線にする + """ + _f.selection.select(0x006c) + _f.copy() + _f.selection.select(0x2014) + _f.pasteInto() + _f.intersect() + return _f + + def zenkaku_space(self, _f): + """全角スペースに枠をつけて可視化する + """ + _f.selection.select(0x2610) + _f.copy() + _f.selection.select(0x3000) + _f.paste() + _f.selection.select(0x271a) + _f.copy() + _f.selection.select(0x3000) + _f.pasteInto() + _f.intersect() + for g in _f.selection.byGlyphs: + g = align_to_center(g) + return _f -def fix_overflow(glyph): - """上が820を超えている、または下が-204を超えているグリフを - 1024x1024の枠にはまるように修正する - ※全角のグリフのみに実施する - """ - if glyph.width < 1024: - return glyph - if glyph.isWorthOutputting: - bb = glyph.boundingBox() - height = bb[3] - bb[1] - if height > 1024: - # resize - scale = 1024 / height - glyph.transform(psMat.scale(scale, scale)) - bb = glyph.boundingBox() - bottom = bb[1] - top = bb[3] - if bottom < -204: - glyph.transform(psMat.translate(0, -204 - bottom)) - elif top > 820: - glyph.transform(psMat.translate(0, 820 - top)) - return glyph + def zero(self, _f): + """半角数字の0をドットゼロにする + """ + _f.selection.select(0x4f) + _f.copy() + _f.selection.select(0x30) + _f.paste() + _f.selection.select(0xb7) + _f.copy() + _f.selection.select(0x30) + _f.pasteInto() + for g in _f.selection.byGlyphs: + g = align_to_center(g) + return _f -def import_svg(font): - """オリジナルのsvgグリフをインポートする - """ - files = glob.glob('sourceFonts/svg/*.svg') - for f in files: - filename, _ = os.path.splitext(os.path.basename(f)) - g = font.createChar(int(filename, 16)) - g.width = 1024 - g.vwidth = 1024 - g.clear() - g.importOutlines(f) - g.transform(psMat.translate(0, -61)) - # g = fix_overflow(g) - return font - - -def build_font(_f, emoji): - hack = fontforge.open('./sourceFonts/%s' % _f.get('hack')) - log('remove_glyph_from_hack()') - hack = remove_glyph_from_hack(hack) - cica = fontforge.open('./sourceFonts/%s' % _f.get('mgen_plus')) - nerd = fontforge.open('./sourceFonts/nerd.sfd') - icons_for_devs = fontforge.open('./sourceFonts/iconsfordevs.ttf') - - - log('transform Hack') - for g in hack.glyphs(): - g.transform((0.42,0,0,0.42,0,0)) - if _f.get('hack_weight_reduce') != 0: - # g.changeWeight(_f.get('hack_weight_reduce'), 'auto', 0, 0, 'auto') - g.stroke("circular", _f.get('hack_weight_reduce'), 'butt', 'round', 'removeexternal') - g = align_to_center(g) - hack = modify_m(hack, _f.get('weight_name')) - - - alternate_expands = [ - 0x306e, - ] + def modify_WM(self, _f): + """WとMの字体を調整 + """ + _f.selection.select(0x57) + _f.transform(psMat.scale(0.95, 1.0)) + _f.copy() + _f.selection.select(0x4d) + _f.paste() + _f.transform(psMat.compose(psMat.rotate(math.radians(180)), psMat.translate(0, 627))) + for g in _f.selection.byGlyphs: + g = align_to_center(g) + return _f + + def modify_m(self, _f, _weight): + """mの中央の棒を少し短くする + """ + m = fontforge.open('./sourceFonts/m-Regular.sfd') + if _weight == 'Bold': + m.close() + m = fontforge.open('./sourceFonts/m-Bold.sfd') + m.selection.select(0x6d) + m.copy() + _f.selection.select(0x6d) + _f.paste() + for g in m.glyphs(): + if g.encoding == 0x6d: + anchorPoints = g.anchorPoints + for g in _f.glyphs(): + if g.encoding == 0x6d: + g.anchorPoints = anchorPoints - if _f.get('mgen_weight_add') != 0: - for g in cica.glyphs(): - # g.changeWeight(_f.get('mgen_weight_add'), 'auto', 0, 0, 'auto') - g.stroke("caligraphic", _f.get('mgen_weight_add'), _f.get('mgen_weight_add'), 45, 'removeinternal') - # g.stroke("circular", _f.get('mgen_weight_add'), 'butt', 'round', 'removeinternal') + return _f - ignoring_center = [ - 0x3001, 0x3002, 0x3008, 0x3009, 0x300a, 0x300b, 0x300c, 0x300d, - 0x300e, 0x300f, 0x3010, 0x3011, 0x3014, 0x3015, 0x3016, 0x3017, - 0x3018, 0x3019, 0x301a, 0x301b, 0x301d, 0x301e, 0x3099, 0x309a, - 0x309b, 0x309c, - ] - log('transform Mgen+') - for g in cica.glyphs(): - g.transform((0.91,0,0,0.91,0,0)) - full_half_threshold = 700 - if _f.get('italic'): - g.transform(psMat.skew(0.25)) - skew_amount = g.font.ascent * 0.91 * 0.25 - g.width = g.width + skew_amount - full_half_threshold += skew_amount - if g.width > full_half_threshold: - width = 1024 - else: - width = 512 - g.transform(psMat.translate((width - g.width)/2, 0)) - g.width = width - if g.encoding in ignoring_center: - pass - else: + def add_smalltriangle(self, _f): + """小さいサンカクを追加 + NerdTree用 + """ + _f.selection.select(0x25bc) + _f.copy() + _f.selection.select(0x25be) + _f.paste() + _f.transform(psMat.compose(psMat.scale(0.64), psMat.translate(0, 68))) + _f.copy() + _f.selection.select(0x25b8) + _f.paste() + _f.transform(psMat.rotate(math.radians(90))) + _f.transform(psMat.translate(0, 212)) + + for g in _f.glyphs(): + if g.encoding == 0x25be or g.encoding == 0x25b8: + g.width = 512 + g = align_to_center(g) + + return _f + + def fix_box_drawings(self, _f): + """罫線を調整 + """ + left = [ + 0x2510, 0x2518, 0x2524, 0x2555, 0x2556, 0x2557, 0x255b, 0x255c, 0x255d, + 0x2561, 0x2562, 0x2563, 0x256e, 0x256f, 0x2574, 0x2578, + 0xf2510, 0xf2518, 0xf2524, 0xf2555, 0xf2556, 0xf2557, 0xf255b, 0xf255c, 0xf255d, + 0xff2561, 0xf2562, 0xf2563, 0xf256e, 0xf256f, 0xf2574, 0xf2578 + ] + right = [ + 0x250c, 0x2514, 0x251c, 0x2552, 0x2553, 0x2554, 0x2558, 0x2559, 0x255a, + 0x255e, 0x255f, 0x2560, 0x256d, 0x2570, 0x2576, 0x257a, + 0xf250c, 0xf2514, 0xf251c, 0xf2552, 0xf2553, 0xf2554, 0xf2558, 0xf2559, 0xf255a, + 0xf255e, 0xf255f, 0xf2560, 0xf256d, 0xf2570, 0xf2576, 0xf257a + ] + + for g in _f.glyphs(): + if g.encoding < 0x2500: + continue + if g.encoding > 0x256c and g.encoding < 0xf2500: + continue + if g.encoding in left: + align_to_left(g) + elif g.encoding in right: + align_to_right(g) + + return _f + + def reiwa(self, _f, _weight): + """令和グリフを追加 + """ + reiwa = fontforge.open('./sourceFonts/reiwa.sfd') + if _weight == 'Bold': + reiwa.close() + reiwa = fontforge.open('./sourceFonts/reiwa-Bold.sfd') + for g in reiwa.glyphs(): + if g.isWorthOutputting: + reiwa.selection.select(0x00) + reiwa.copy() + _f.selection.select(0x32ff) + _f.paste() + reiwa.close() + return _f + + def import_svg(self, font): + """オリジナルのsvgグリフをインポートする + """ + files = glob.glob('sourceFonts/svg/*.svg') + for f in files: + filename, _ = os.path.splitext(os.path.basename(f)) + g = font.createChar(int(filename, 16)) + g.width = 1024 + g.vwidth = 1024 + g.clear() + g.importOutlines(f) + g.transform(psMat.translate(0, -61)) + # g = fix_overflow(g) + return font + + + def build_font(self, _f, emoji): + hack = fontforge.open('./sourceFonts/%s' % _f.get('hack')) + log('remove_glyph_from_hack()') + hack = self.remove_glyph_from_en(hack) + cica = fontforge.open('./sourceFonts/%s' % _f.get('mgen_plus')) + nerd = fontforge.open('./sourceFonts/nerd.sfd') + icons_for_devs = fontforge.open('./sourceFonts/iconsfordevs.ttf') + + + log('transform Hack') + for g in hack.glyphs(): + g.transform((0.42,0,0,0.42,0,0)) + if _f.get('hack_weight_reduce') != 0: + # g.changeWeight(_f.get('hack_weight_reduce'), 'auto', 0, 0, 'auto') + g.stroke("circular", _f.get('hack_weight_reduce'), 'butt', 'round', 'removeexternal') g = align_to_center(g) + hack = self.modify_m(hack, _f.get('weight_name')) + + + alternate_expands = [ + 0x306e, + ] - log('modify border glyphs') - for g in hack.glyphs(): - if g.isWorthOutputting: + if _f.get('mgen_weight_add') != 0: + for g in cica.glyphs(): + # g.changeWeight(_f.get('mgen_weight_add'), 'auto', 0, 0, 'auto') + g.stroke("caligraphic", _f.get('mgen_weight_add'), _f.get('mgen_weight_add'), 45, 'removeinternal') + # g.stroke("circular", _f.get('mgen_weight_add'), 'butt', 'round', 'removeinternal') + + + ignoring_center = [ + 0x3001, 0x3002, 0x3008, 0x3009, 0x300a, 0x300b, 0x300c, 0x300d, + 0x300e, 0x300f, 0x3010, 0x3011, 0x3014, 0x3015, 0x3016, 0x3017, + 0x3018, 0x3019, 0x301a, 0x301b, 0x301d, 0x301e, 0x3099, 0x309a, + 0x309b, 0x309c, + ] + log('transform Mgen+') + for g in cica.glyphs(): + g.transform((0.91,0,0,0.91,0,0)) + full_half_threshold = 700 if _f.get('italic'): g.transform(psMat.skew(0.25)) - if g.encoding >= 0x2500 and g.encoding <= 0x257f: - # 全角の罫線を0xf0000以降に退避 + skew_amount = g.font.ascent * 0.91 * 0.25 + g.width = g.width + skew_amount + full_half_threshold += skew_amount + if g.width > full_half_threshold: + width = 1024 + else: + width = 512 + g.transform(psMat.translate((width - g.width)/2, 0)) + g.width = width + if g.encoding in ignoring_center: + pass + else: + g = align_to_center(g) + + log('modify border glyphs') + for g in hack.glyphs(): + if g.isWorthOutputting: + if _f.get('italic'): + g.transform(psMat.skew(0.25)) + if g.encoding >= 0x2500 and g.encoding <= 0x257f: + # 全角の罫線を0xf0000以降に退避 + cica.selection.select(g.encoding) + cica.copy() + cica.selection.select(g.encoding + 0xf0000) + cica.paste() + if g.encoding >= 0x2500 and g.encoding <= 0x25af: + g.transform(psMat.compose(psMat.scale(1.024, 1.024), psMat.translate(0, -30))) + g = align_to_center(g) + hack.selection.select(g.encoding) + hack.copy() cica.selection.select(g.encoding) - cica.copy() + cica.paste() + + log('modify nerd glyphs') + for g in nerd.glyphs(): + if g.encoding < 0xe0a0 or g.encoding > 0xfd46: + continue + g = modify_nerd(g) + nerd.selection.select(g.encoding) + nerd.copy() + if g.encoding >= 0xf500: + # Material Design IconsはNerd Fontsに従うとアラビア文字等を壊して + # しまうので、0xf0000〜に配置する cica.selection.select(g.encoding + 0xf0000) cica.paste() - if g.encoding >= 0x2500 and g.encoding <= 0x25af: - g.transform(psMat.compose(psMat.scale(1.024, 1.024), psMat.translate(0, -30))) - g = align_to_center(g) - hack.selection.select(g.encoding) - hack.copy() - cica.selection.select(g.encoding) - cica.paste() + else: + cica.selection.select(g.encoding) + cica.paste() - log('modify nerd glyphs') - for g in nerd.glyphs(): - if g.encoding < 0xe0a0 or g.encoding > 0xfd46: - continue - g = modify_nerd(g) - nerd.selection.select(g.encoding) - nerd.copy() - if g.encoding >= 0xf500: - # Material Design IconsはNerd Fontsに従うとアラビア文字等を壊して - # しまうので、0xf0000〜に配置する - cica.selection.select(g.encoding + 0xf0000) - cica.paste() - else: + log('modify icons_for_devs glyphs') + for g in icons_for_devs.glyphs(): + if g.encoding < 0xe900 or g.encoding > 0xe950: + continue + g = modify_iconsfordevs(g) + icons_for_devs.selection.select(g.encoding) + icons_for_devs.copy() cica.selection.select(g.encoding) cica.paste() - log('modify icons_for_devs glyphs') - for g in icons_for_devs.glyphs(): - if g.encoding < 0xe900 or g.encoding > 0xe950: - continue - g = modify_iconsfordevs(g) - icons_for_devs.selection.select(g.encoding) - icons_for_devs.copy() - cica.selection.select(g.encoding) - cica.paste() - - cica = fix_box_drawings(cica) - cica = zenkaku_space(cica) - cica = zero(cica) - cica = modify_WM(cica) - cica = vertical_line_to_broken_bar(cica) - cica = emdash_to_broken_dash(cica) - cica = reiwa(cica, _f.get('weight_name')) - cica = add_gopher(cica) - cica = modify_ellipsis(cica) - if emoji: - cica = add_notoemoji(cica) - cica = add_smalltriangle(cica) - cica = add_dejavu(cica, _f) - cica = resize_supersub(cica) - - log("fix_overflow()") - for g in cica.glyphs(): - g = fix_overflow(g) - log("import_svg()") - cica = import_svg(cica) - cica.ascent = ASCENT - cica.descent = DESCENT - cica.upos = 45 - cica.fontname = _f.get('family') - cica.familyname = _f.get('family') - cica.fullname = _f.get('name') - cica.weight = _f.get('weight_name') - cica = set_os2_values(cica, _f) - cica.appendSFNTName(0x411,0, COPYRIGHT) - cica.appendSFNTName(0x411,1, _f.get('family')) - cica.appendSFNTName(0x411,2, _f.get('style_name')) - # cica.appendSFNTName(0x411,3, "") - cica.appendSFNTName(0x411,4, _f.get('name')) - cica.appendSFNTName(0x411,5, "Version " + VERSION) - cica.appendSFNTName(0x411,6, _f.get('family') + "-" + _f.get('weight_name')) - # cica.appendSFNTName(0x411,7, "") - # cica.appendSFNTName(0x411,8, "") - # cica.appendSFNTName(0x411,9, "") - # cica.appendSFNTName(0x411,10, "") - # cica.appendSFNTName(0x411,11, "") - # cica.appendSFNTName(0x411,12, "") - cica.appendSFNTName(0x411,13, LICENSE) - # cica.appendSFNTName(0x411,14, "") - # cica.appendSFNTName(0x411,15, "") - cica.appendSFNTName(0x411,16, _f.get('family')) - cica.appendSFNTName(0x411,17, _f.get('style_name')) - cica.appendSFNTName(0x409,0, COPYRIGHT) - cica.appendSFNTName(0x409,1, _f.get('family')) - cica.appendSFNTName(0x409,2, _f.get('style_name')) - cica.appendSFNTName(0x409,3, VERSION + ";" + _f.get('family') + "-" + _f.get('style_name')) - cica.appendSFNTName(0x409,4, _f.get('name')) - cica.appendSFNTName(0x409,5, "Version " + VERSION) - cica.appendSFNTName(0x409,6, _f.get('name')) - # cica.appendSFNTName(0x409,7, "") - # cica.appendSFNTName(0x409,8, "") - # cica.appendSFNTName(0x409,9, "") - # cica.appendSFNTName(0x409,10, "") - # cica.appendSFNTName(0x409,11, "") - # cica.appendSFNTName(0x409,12, "") - cica.appendSFNTName(0x409,13, LICENSE) - # cica.appendSFNTName(0x409,14, "") - # cica.appendSFNTName(0x409,15, "") - cica.appendSFNTName(0x409,16, _f.get('family')) - cica.appendSFNTName(0x409,17, _f.get('style_name')) - if emoji: - fontpath = './dist/%s' % _f.get('filename') - else: - fontpath = './dist/noemoji/%s' % _f.get('filename') + cica = self.fix_box_drawings(cica) + cica = self.zenkaku_space(cica) + cica = self.zero(cica) + cica = self.modify_WM(cica) + cica = self.vertical_line_to_broken_bar(cica) + cica = self.emdash_to_broken_dash(cica) + cica = self.reiwa(cica, _f.get('weight_name')) + cica = self.add_gopher(cica) + cica = self.modify_ellipsis(cica) + if emoji: + cica = self.add_notoemoji(cica) + cica = self.add_smalltriangle(cica) + cica = self.add_dejavu(cica, _f) + cica = self.resize_supersub(cica) + + log("fix_overflow()") + for g in cica.glyphs(): + g = fix_overflow(g) + log("import_svg()") + cica = self.import_svg(cica) + cica.ascent = ASCENT + cica.descent = DESCENT + cica.upos = 45 + cica.fontname = _f.get('family') + cica.familyname = _f.get('family') + cica.fullname = _f.get('name') + cica.weight = _f.get('weight_name') + cica = self.set_os2_values(cica, _f) + cica.appendSFNTName(0x411,0, COPYRIGHT) + cica.appendSFNTName(0x411,1, _f.get('family')) + cica.appendSFNTName(0x411,2, _f.get('style_name')) + cica.appendSFNTName(0x411,4, _f.get('name')) + cica.appendSFNTName(0x411,5, "Version " + VERSION) + cica.appendSFNTName(0x411,6, _f.get('family') + "-" + _f.get('weight_name')) + cica.appendSFNTName(0x411,13, LICENSE) + cica.appendSFNTName(0x411,16, _f.get('family')) + cica.appendSFNTName(0x411,17, _f.get('style_name')) + cica.appendSFNTName(0x409,0, COPYRIGHT) + cica.appendSFNTName(0x409,1, _f.get('family')) + cica.appendSFNTName(0x409,2, _f.get('style_name')) + cica.appendSFNTName(0x409,3, VERSION + ";" + _f.get('family') + "-" + _f.get('style_name')) + cica.appendSFNTName(0x409,4, _f.get('name')) + cica.appendSFNTName(0x409,5, "Version " + VERSION) + cica.appendSFNTName(0x409,6, _f.get('name')) + cica.appendSFNTName(0x409,13, LICENSE) + cica.appendSFNTName(0x409,16, _f.get('family')) + cica.appendSFNTName(0x409,17, _f.get('style_name')) + if emoji: + fontpath = './dist/%s' % _f.get('filename') + else: + fontpath = './dist/noemoji/%s' % _f.get('filename') - cica.generate(fontpath) + cica.generate(fontpath) - cica.close() - hack.close() - nerd.close() - icons_for_devs.close() + cica.close() + hack.close() + nerd.close() + icons_for_devs.close() -def add_notoemoji(_f): - notoemoji = fontforge.open('./sourceFonts/NotoEmoji-Regular.ttf') - for g in notoemoji.glyphs(): - if g.isWorthOutputting and g.encoding > 0x04f9: - g.transform((0.42,0,0,0.42,0,0)) - g = align_to_center(g) - notoemoji.selection.select(g.encoding) - notoemoji.copy() - _f.selection.select(g.encoding) - _f.paste() - notoemoji.close() - return _f - -def add_gopher(_f): - gopher = fontforge.open('./sourceFonts/gopher.sfd') - for g in gopher.glyphs(): - if g.isWorthOutputting: - gopher.selection.select(0x40) - gopher.copy() - _f.selection.select(0xE160) + def add_notoemoji(self, _f): + notoemoji = fontforge.open('./sourceFonts/NotoEmoji-Regular.ttf') + for g in notoemoji.glyphs(): + if g.isWorthOutputting and g.encoding > 0x04f9: + g.transform((0.42,0,0,0.42,0,0)) + g = align_to_center(g) + notoemoji.selection.select(g.encoding) + notoemoji.copy() + _f.selection.select(g.encoding) + _f.paste() + notoemoji.close() + return _f + + def add_gopher(self, _f): + gopher = fontforge.open('./sourceFonts/gopher.sfd') + for g in gopher.glyphs(): + if g.isWorthOutputting: + gopher.selection.select(0x40) + gopher.copy() + _f.selection.select(0xE160) + _f.paste() + g.transform(psMat.compose(psMat.scale(-1, 1), psMat.translate(g.width, 0))) + gopher.copy() + _f.selection.select(0xE161) + _f.paste() + gopher.close() + return _f + + def resize_supersub(self, _f): + superscripts = [ + {"src": 0x0031, "dest": 0x00b9}, {"src": 0x0032, "dest": 0x00b2}, + {"src": 0x0033, "dest": 0x00b3}, {"src": 0x0030, "dest": 0x2070}, + {"src": 0x0069, "dest": 0x2071}, {"src": 0x0034, "dest": 0x2074}, + {"src": 0x0037, "dest": 0x2077}, {"src": 0x0038, "dest": 0x2078}, + {"src": 0x0039, "dest": 0x2079}, {"src": 0x002b, "dest": 0x207a}, + {"src": 0x002d, "dest": 0x207b}, {"src": 0x003d, "dest": 0x207c}, + {"src": 0x0028, "dest": 0x207d}, {"src": 0x0029, "dest": 0x207e}, + {"src": 0x006e, "dest": 0x207f}, + # ↓上付きの大文字 + {"src": 0x0041, "dest": 0x1d2c}, {"src": 0x00c6, "dest": 0x1d2d}, + {"src": 0x0042, "dest": 0x1d2e}, {"src": 0x0044, "dest": 0x1d30}, + {"src": 0x0045, "dest": 0x1d31}, {"src": 0x018e, "dest": 0x1d32}, + {"src": 0x0047, "dest": 0x1d33}, {"src": 0x0048, "dest": 0x1d34}, + {"src": 0x0049, "dest": 0x1d35}, {"src": 0x004a, "dest": 0x1d36}, + {"src": 0x004b, "dest": 0x1d37}, {"src": 0x004c, "dest": 0x1d38}, + {"src": 0x004d, "dest": 0x1d39}, {"src": 0x004e, "dest": 0x1d3a}, + ## ↓REVERSED N なのでNを左右反転させる必要あり + {"src": 0x004e, "dest": 0x1d3b, "reversed": True}, + {"src": 0x004f, "dest": 0x1d3c}, {"src": 0x0222, "dest": 0x1d3d}, + {"src": 0x0050, "dest": 0x1d3e}, {"src": 0x0052, "dest": 0x1d3f}, + {"src": 0x0054, "dest": 0x1d40}, {"src": 0x0055, "dest": 0x1d41}, + {"src": 0x0057, "dest": 0x1d42}, + # ↓上付きの小文字 + {"src": 0x0061, "dest": 0x1d43}, {"src": 0x0250, "dest": 0x1d44}, + {"src": 0x0251, "dest": 0x1d45}, {"src": 0x1d02, "dest": 0x1d46}, + {"src": 0x0062, "dest": 0x1d47}, {"src": 0x0064, "dest": 0x1d48}, + {"src": 0x0065, "dest": 0x1d49}, {"src": 0x0259, "dest": 0x1d4a}, + {"src": 0x025b, "dest": 0x1d4b}, {"src": 0x025c, "dest": 0x1d4c}, + {"src": 0x0067, "dest": 0x1d4d}, + ## ↓TURNED i なので 180度回す必要あり + {"src": 0x0069, "dest": 0x1d4e, "turned": True}, + {"src": 0x006b, "dest": 0x1d4f}, {"src": 0x006d, "dest": 0x1d50}, + {"src": 0x014b, "dest": 0x1d51}, {"src": 0x006f, "dest": 0x1d52}, + {"src": 0x0254, "dest": 0x1d53}, {"src": 0x1d16, "dest": 0x1d54}, + {"src": 0x1d17, "dest": 0x1d55}, {"src": 0x0070, "dest": 0x1d56}, + {"src": 0x0074, "dest": 0x1d57}, {"src": 0x0075, "dest": 0x1d58}, + {"src": 0x1d1d, "dest": 0x1d59}, {"src": 0x026f, "dest": 0x1d5a}, + {"src": 0x0076, "dest": 0x1d5b}, {"src": 0x1d25, "dest": 0x1d5c}, + {"src": 0x03b2, "dest": 0x1d5d}, {"src": 0x03b3, "dest": 0x1d5e}, + {"src": 0x03b4, "dest": 0x1d5f}, {"src": 0x03c6, "dest": 0x1d60}, + {"src": 0x03c7, "dest": 0x1d61}, + {"src": 0x0056, "dest": 0x2c7d}, {"src": 0x0068, "dest": 0x02b0}, + {"src": 0x0266, "dest": 0x02b1}, {"src": 0x006a, "dest": 0x02b2}, + {"src": 0x006c, "dest": 0x02e1}, {"src": 0x0073, "dest": 0x02e2}, + {"src": 0x0078, "dest": 0x02e3}, {"src": 0x0072, "dest": 0x02b3}, + {"src": 0x0077, "dest": 0x02b7}, {"src": 0x0079, "dest": 0x02b8}, + {"src": 0x0063, "dest": 0x1d9c}, {"src": 0x0066, "dest": 0x1da0}, + {"src": 0x007a, "dest": 0x1dbb}, {"src": 0x0061, "dest": 0x00aa}, + {"src": 0x0252, "dest": 0x1d9b}, {"src": 0x0255, "dest": 0x1d9d}, + {"src": 0x00f0, "dest": 0x1d9e}, {"src": 0x025c, "dest": 0x1d9f}, + {"src": 0x025f, "dest": 0x1da1}, {"src": 0x0261, "dest": 0x1da2}, + {"src": 0x0265, "dest": 0x1da3}, {"src": 0x0268, "dest": 0x1da4}, + {"src": 0x0269, "dest": 0x1da5}, {"src": 0x026a, "dest": 0x1da6}, + {"src": 0x1d7b, "dest": 0x1da7}, {"src": 0x029d, "dest": 0x1da8}, + {"src": 0x026d, "dest": 0x1da9}, {"src": 0x1d85, "dest": 0x1daa}, + {"src": 0x029f, "dest": 0x1dab}, {"src": 0x0271, "dest": 0x1dac}, + {"src": 0x0270, "dest": 0x1dad}, {"src": 0x0272, "dest": 0x1dae}, + {"src": 0x0273, "dest": 0x1daf}, {"src": 0x0274, "dest": 0x1db0}, + {"src": 0x0275, "dest": 0x1db1}, {"src": 0x0278, "dest": 0x1db2}, + {"src": 0x0282, "dest": 0x1db3}, {"src": 0x0283, "dest": 0x1db4}, + {"src": 0x01ab, "dest": 0x1db5}, {"src": 0x0289, "dest": 0x1db6}, + {"src": 0x028a, "dest": 0x1db7}, {"src": 0x1d1c, "dest": 0x1db8}, + {"src": 0x028b, "dest": 0x1db9}, {"src": 0x028c, "dest": 0x1dba}, + {"src": 0x0290, "dest": 0x1dbc}, {"src": 0x0291, "dest": 0x1dbd}, + {"src": 0x0292, "dest": 0x1dbe}, {"src": 0x03b8, "dest": 0x1dbf}, + + ] + subscripts = [ + {"src": 0x0069, "dest": 0x1d62}, {"src": 0x0072, "dest": 0x1d63}, + {"src": 0x0075, "dest": 0x1d64}, {"src": 0x0076, "dest": 0x1d65}, + {"src": 0x03b2, "dest": 0x1d66}, {"src": 0x03b3, "dest": 0x1d67}, + {"src": 0x03c1, "dest": 0x1d68}, {"src": 0x03c6, "dest": 0x1d69}, + {"src": 0x03c7, "dest": 0x1d6a}, {"src": 0x006a, "dest": 0x2c7c}, + {"src": 0x0030, "dest": 0x2080}, {"src": 0x0031, "dest": 0x2081}, + {"src": 0x0032, "dest": 0x2082}, {"src": 0x0033, "dest": 0x2083}, + {"src": 0x0034, "dest": 0x2084}, {"src": 0x0035, "dest": 0x2085}, + {"src": 0x0036, "dest": 0x2086}, {"src": 0x0037, "dest": 0x2087}, + {"src": 0x0038, "dest": 0x2088}, {"src": 0x0039, "dest": 0x2089}, + {"src": 0x002b, "dest": 0x208a}, {"src": 0x002d, "dest": 0x208b}, + {"src": 0x003d, "dest": 0x208c}, {"src": 0x0028, "dest": 0x208d}, + {"src": 0x0029, "dest": 0x208e}, {"src": 0x0061, "dest": 0x2090}, + {"src": 0x0065, "dest": 0x2091}, {"src": 0x006f, "dest": 0x2092}, + {"src": 0x0078, "dest": 0x2093}, {"src": 0x0259, "dest": 0x2094}, + {"src": 0x0068, "dest": 0x2095}, {"src": 0x006b, "dest": 0x2096}, + {"src": 0x006c, "dest": 0x2097}, {"src": 0x006d, "dest": 0x2098}, + {"src": 0x006e, "dest": 0x2099}, {"src": 0x0070, "dest": 0x209a}, + {"src": 0x0073, "dest": 0x209b}, {"src": 0x0074, "dest": 0x209c} + ] + + for g in superscripts: + _f.selection.select(g["src"]) + _f.copy() + _f.selection.select(g["dest"]) _f.paste() - g.transform(psMat.compose(psMat.scale(-1, 1), psMat.translate(g.width, 0))) - gopher.copy() - _f.selection.select(0xE161) + for g in subscripts: + _f.selection.select(g["src"]) + _f.copy() + _f.selection.select(g["dest"]) _f.paste() - gopher.close() - return _f - -def resize_supersub(_f): - superscripts = [ - {"src": 0x0031, "dest": 0x00b9}, {"src": 0x0032, "dest": 0x00b2}, - {"src": 0x0033, "dest": 0x00b3}, {"src": 0x0030, "dest": 0x2070}, - {"src": 0x0069, "dest": 0x2071}, {"src": 0x0034, "dest": 0x2074}, - {"src": 0x0037, "dest": 0x2077}, {"src": 0x0038, "dest": 0x2078}, - {"src": 0x0039, "dest": 0x2079}, {"src": 0x002b, "dest": 0x207a}, - {"src": 0x002d, "dest": 0x207b}, {"src": 0x003d, "dest": 0x207c}, - {"src": 0x0028, "dest": 0x207d}, {"src": 0x0029, "dest": 0x207e}, - {"src": 0x006e, "dest": 0x207f}, - # ↓上付きの大文字 - {"src": 0x0041, "dest": 0x1d2c}, {"src": 0x00c6, "dest": 0x1d2d}, - {"src": 0x0042, "dest": 0x1d2e}, {"src": 0x0044, "dest": 0x1d30}, - {"src": 0x0045, "dest": 0x1d31}, {"src": 0x018e, "dest": 0x1d32}, - {"src": 0x0047, "dest": 0x1d33}, {"src": 0x0048, "dest": 0x1d34}, - {"src": 0x0049, "dest": 0x1d35}, {"src": 0x004a, "dest": 0x1d36}, - {"src": 0x004b, "dest": 0x1d37}, {"src": 0x004c, "dest": 0x1d38}, - {"src": 0x004d, "dest": 0x1d39}, {"src": 0x004e, "dest": 0x1d3a}, - ## ↓REVERSED N なのでNを左右反転させる必要あり - {"src": 0x004e, "dest": 0x1d3b, "reversed": True}, - {"src": 0x004f, "dest": 0x1d3c}, {"src": 0x0222, "dest": 0x1d3d}, - {"src": 0x0050, "dest": 0x1d3e}, {"src": 0x0052, "dest": 0x1d3f}, - {"src": 0x0054, "dest": 0x1d40}, {"src": 0x0055, "dest": 0x1d41}, - {"src": 0x0057, "dest": 0x1d42}, - # ↓上付きの小文字 - {"src": 0x0061, "dest": 0x1d43}, {"src": 0x0250, "dest": 0x1d44}, - {"src": 0x0251, "dest": 0x1d45}, {"src": 0x1d02, "dest": 0x1d46}, - {"src": 0x0062, "dest": 0x1d47}, {"src": 0x0064, "dest": 0x1d48}, - {"src": 0x0065, "dest": 0x1d49}, {"src": 0x0259, "dest": 0x1d4a}, - {"src": 0x025b, "dest": 0x1d4b}, {"src": 0x025c, "dest": 0x1d4c}, - {"src": 0x0067, "dest": 0x1d4d}, - ## ↓TURNED i なので 180度回す必要あり - {"src": 0x0069, "dest": 0x1d4e, "turned": True}, - {"src": 0x006b, "dest": 0x1d4f}, {"src": 0x006d, "dest": 0x1d50}, - {"src": 0x014b, "dest": 0x1d51}, {"src": 0x006f, "dest": 0x1d52}, - {"src": 0x0254, "dest": 0x1d53}, {"src": 0x1d16, "dest": 0x1d54}, - {"src": 0x1d17, "dest": 0x1d55}, {"src": 0x0070, "dest": 0x1d56}, - {"src": 0x0074, "dest": 0x1d57}, {"src": 0x0075, "dest": 0x1d58}, - {"src": 0x1d1d, "dest": 0x1d59}, {"src": 0x026f, "dest": 0x1d5a}, - {"src": 0x0076, "dest": 0x1d5b}, {"src": 0x1d25, "dest": 0x1d5c}, - {"src": 0x03b2, "dest": 0x1d5d}, {"src": 0x03b3, "dest": 0x1d5e}, - {"src": 0x03b4, "dest": 0x1d5f}, {"src": 0x03c6, "dest": 0x1d60}, - {"src": 0x03c7, "dest": 0x1d61}, - {"src": 0x0056, "dest": 0x2c7d}, {"src": 0x0068, "dest": 0x02b0}, - {"src": 0x0266, "dest": 0x02b1}, {"src": 0x006a, "dest": 0x02b2}, - {"src": 0x006c, "dest": 0x02e1}, {"src": 0x0073, "dest": 0x02e2}, - {"src": 0x0078, "dest": 0x02e3}, {"src": 0x0072, "dest": 0x02b3}, - {"src": 0x0077, "dest": 0x02b7}, {"src": 0x0079, "dest": 0x02b8}, - {"src": 0x0063, "dest": 0x1d9c}, {"src": 0x0066, "dest": 0x1da0}, - {"src": 0x007a, "dest": 0x1dbb}, {"src": 0x0061, "dest": 0x00aa}, - {"src": 0x0252, "dest": 0x1d9b}, {"src": 0x0255, "dest": 0x1d9d}, - {"src": 0x00f0, "dest": 0x1d9e}, {"src": 0x025c, "dest": 0x1d9f}, - {"src": 0x025f, "dest": 0x1da1}, {"src": 0x0261, "dest": 0x1da2}, - {"src": 0x0265, "dest": 0x1da3}, {"src": 0x0268, "dest": 0x1da4}, - {"src": 0x0269, "dest": 0x1da5}, {"src": 0x026a, "dest": 0x1da6}, - {"src": 0x1d7b, "dest": 0x1da7}, {"src": 0x029d, "dest": 0x1da8}, - {"src": 0x026d, "dest": 0x1da9}, {"src": 0x1d85, "dest": 0x1daa}, - {"src": 0x029f, "dest": 0x1dab}, {"src": 0x0271, "dest": 0x1dac}, - {"src": 0x0270, "dest": 0x1dad}, {"src": 0x0272, "dest": 0x1dae}, - {"src": 0x0273, "dest": 0x1daf}, {"src": 0x0274, "dest": 0x1db0}, - {"src": 0x0275, "dest": 0x1db1}, {"src": 0x0278, "dest": 0x1db2}, - {"src": 0x0282, "dest": 0x1db3}, {"src": 0x0283, "dest": 0x1db4}, - {"src": 0x01ab, "dest": 0x1db5}, {"src": 0x0289, "dest": 0x1db6}, - {"src": 0x028a, "dest": 0x1db7}, {"src": 0x1d1c, "dest": 0x1db8}, - {"src": 0x028b, "dest": 0x1db9}, {"src": 0x028c, "dest": 0x1dba}, - {"src": 0x0290, "dest": 0x1dbc}, {"src": 0x0291, "dest": 0x1dbd}, - {"src": 0x0292, "dest": 0x1dbe}, {"src": 0x03b8, "dest": 0x1dbf}, - ] - subscripts = [ - {"src": 0x0069, "dest": 0x1d62}, {"src": 0x0072, "dest": 0x1d63}, - {"src": 0x0075, "dest": 0x1d64}, {"src": 0x0076, "dest": 0x1d65}, - {"src": 0x03b2, "dest": 0x1d66}, {"src": 0x03b3, "dest": 0x1d67}, - {"src": 0x03c1, "dest": 0x1d68}, {"src": 0x03c6, "dest": 0x1d69}, - {"src": 0x03c7, "dest": 0x1d6a}, {"src": 0x006a, "dest": 0x2c7c}, - {"src": 0x0030, "dest": 0x2080}, {"src": 0x0031, "dest": 0x2081}, - {"src": 0x0032, "dest": 0x2082}, {"src": 0x0033, "dest": 0x2083}, - {"src": 0x0034, "dest": 0x2084}, {"src": 0x0035, "dest": 0x2085}, - {"src": 0x0036, "dest": 0x2086}, {"src": 0x0037, "dest": 0x2087}, - {"src": 0x0038, "dest": 0x2088}, {"src": 0x0039, "dest": 0x2089}, - {"src": 0x002b, "dest": 0x208a}, {"src": 0x002d, "dest": 0x208b}, - {"src": 0x003d, "dest": 0x208c}, {"src": 0x0028, "dest": 0x208d}, - {"src": 0x0029, "dest": 0x208e}, {"src": 0x0061, "dest": 0x2090}, - {"src": 0x0065, "dest": 0x2091}, {"src": 0x006f, "dest": 0x2092}, - {"src": 0x0078, "dest": 0x2093}, {"src": 0x0259, "dest": 0x2094}, - {"src": 0x0068, "dest": 0x2095}, {"src": 0x006b, "dest": 0x2096}, - {"src": 0x006c, "dest": 0x2097}, {"src": 0x006d, "dest": 0x2098}, - {"src": 0x006e, "dest": 0x2099}, {"src": 0x0070, "dest": 0x209a}, - {"src": 0x0073, "dest": 0x209b}, {"src": 0x0074, "dest": 0x209c} - ] - - for g in superscripts: - _f.selection.select(g["src"]) + for g in _f.glyphs("encoding"): + if g.encoding > 0x2c7d: + continue + elif self.in_scripts(g.encoding, superscripts): + if g.encoding == 0x1d5d or g.encoding == 0x1d61: + g.transform(psMat.scale(0.70, 0.70)) + elif g.encoding == 0x1d3b: + g.transform(psMat.scale(0.75, 0.75)) + g.transform(psMat.compose(psMat.scale(-1, 1), psMat.translate(g.width, 0))) + elif g.encoding == 0x1d4e: + g.transform(psMat.scale(0.75, 0.75)) + g.transform(psMat.rotate(3.14159)) + g.transform(psMat.translate(0, 512)) + else: + g.transform(psMat.scale(0.75, 0.75)) + bb = g.boundingBox() + g.transform(psMat.translate(0, 244)) + align_to_center(g) + elif self.in_scripts(g.encoding, subscripts): + if g.encoding == 0x1d66 or g.encoding == 0x1d6a: + g.transform(psMat.scale(0.70, 0.70)) + else: + g.transform(psMat.scale(0.75, 0.75)) + bb = g.boundingBox() + y = -144 + if bb[1] < -60: # DESCENT - 144 + y = -60 + g.transform(psMat.translate(0, y)) + align_to_center(g) + return _f + + def in_scripts(self, encoding, scripts): + for s in scripts: + if encoding == s["dest"]: + return True + return False + + + def scripts_from(self, encoding, scripts): + for s in scripts: + if encoding == s["dest"]: + return s["src"] + raise ValueError + + def modify_ellipsis(self, _f): + """3点リーダーを半角にする + DejaVuSansMono の U+22EF(⋯) をU+2026(…)、U+22EE(⋮)、U+22F0(⋰)、U+22F1(⋱) + にコピーした上で回転させて生成 + + 三点リーダの文字幅について · Issue #41 · miiton/Cica https://github.com/miiton/Cica/issues/41 + """ + _f.selection.select(0x22ef) _f.copy() - _f.selection.select(g["dest"]) + _f.selection.select(0x2026) _f.paste() - for g in subscripts: - _f.selection.select(g["src"]) - _f.copy() - _f.selection.select(g["dest"]) + _f.selection.select(0x22ee) + _f.paste() + _f.selection.select(0x22f0) + _f.paste() + _f.selection.select(0x22f1) _f.paste() + for g in _f.glyphs("encoding"): + if g.encoding < 0x22ee: + continue + elif g.encoding > 0x22f1: + break + elif g.encoding == 0x22ee: + bb = g.boundingBox() + cx = (bb[2] + bb[0]) / 2 + cy = (bb[3] + bb[1]) / 2 + trcen = psMat.translate(-cx, -cy) + rotcen = psMat.compose(trcen, psMat.compose(psMat.rotate(math.radians(90)), psMat.inverse(trcen))) + g.transform(rotcen) + elif g.encoding == 0x22f0: + bb = g.boundingBox() + cx = (bb[2] + bb[0]) / 2 + cy = (bb[3] + bb[1]) / 2 + trcen = psMat.translate(-cx, -cy) + rotcen = psMat.compose(trcen, psMat.compose(psMat.rotate(math.radians(45)), psMat.inverse(trcen))) + g.transform(rotcen) + elif g.encoding == 0x22f1: + bb = g.boundingBox() + cx = (bb[2] + bb[0]) / 2 + cy = (bb[3] + bb[1]) / 2 + trcen = psMat.translate(-cx, -cy) + rotcen = psMat.compose(trcen, psMat.compose(psMat.rotate(math.radians(-45)), psMat.inverse(trcen))) + g.transform(rotcen) + return _f - for g in _f.glyphs("encoding"): - if g.encoding > 0x2c7d: - continue - elif in_scripts(g.encoding, superscripts): - if g.encoding == 0x1d5d or g.encoding == 0x1d61: - g.transform(psMat.scale(0.70, 0.70)) - elif g.encoding == 0x1d3b: - g.transform(psMat.scale(0.75, 0.75)) - g.transform(psMat.compose(psMat.scale(-1, 1), psMat.translate(g.width, 0))) - elif g.encoding == 0x1d4e: - g.transform(psMat.scale(0.75, 0.75)) - g.transform(psMat.rotate(3.14159)) - g.transform(psMat.translate(0, 512)) - else: - g.transform(psMat.scale(0.75, 0.75)) - bb = g.boundingBox() - g.transform(psMat.translate(0, 244)) - align_to_center(g) - elif in_scripts(g.encoding, subscripts): - if g.encoding == 0x1d66 or g.encoding == 0x1d6a: - g.transform(psMat.scale(0.70, 0.70)) - else: - g.transform(psMat.scale(0.75, 0.75)) - bb = g.boundingBox() - y = -144 - if bb[1] < -60: # DESCENT - 144 - y = -60 - g.transform(psMat.translate(0, y)) - align_to_center(g) - return _f - -def in_scripts(encoding, scripts): - for s in scripts: - if encoding == s["dest"]: - return True - return False - - -def scripts_from(encoding, scripts): - for s in scripts: - if encoding == s["dest"]: - return s["src"] - raise ValueError - -def modify_ellipsis(_f): - """3点リーダーを半角にする - DejaVuSansMono の U+22EF(⋯) をU+2026(…)、U+22EE(⋮)、U+22F0(⋰)、U+22F1(⋱) - にコピーした上で回転させて生成 - - 三点リーダの文字幅について · Issue #41 · miiton/Cica https://github.com/miiton/Cica/issues/41 - """ - _f.selection.select(0x22ef) - _f.copy() - _f.selection.select(0x2026) - _f.paste() - _f.selection.select(0x22ee) - _f.paste() - _f.selection.select(0x22f0) - _f.paste() - _f.selection.select(0x22f1) - _f.paste() - for g in _f.glyphs("encoding"): - if g.encoding < 0x22ee: - continue - elif g.encoding > 0x22f1: - break - elif g.encoding == 0x22ee: - bb = g.boundingBox() - cx = (bb[2] + bb[0]) / 2 - cy = (bb[3] + bb[1]) / 2 - trcen = psMat.translate(-cx, -cy) - rotcen = psMat.compose(trcen, psMat.compose(psMat.rotate(math.radians(90)), psMat.inverse(trcen))) - g.transform(rotcen) - elif g.encoding == 0x22f0: - bb = g.boundingBox() - cx = (bb[2] + bb[0]) / 2 - cy = (bb[3] + bb[1]) / 2 - trcen = psMat.translate(-cx, -cy) - rotcen = psMat.compose(trcen, psMat.compose(psMat.rotate(math.radians(45)), psMat.inverse(trcen))) - g.transform(rotcen) - elif g.encoding == 0x22f1: - bb = g.boundingBox() - cx = (bb[2] + bb[0]) / 2 - cy = (bb[3] + bb[1]) / 2 - trcen = psMat.translate(-cx, -cy) - rotcen = psMat.compose(trcen, psMat.compose(psMat.rotate(math.radians(-45)), psMat.inverse(trcen))) - g.transform(rotcen) - return _f +fonts = [ + { + 'family': FAMILY, + 'name': FAMILY + '-Regular', + 'filename': FAMILY + '-Regular.ttf', + 'weight': 400, + 'weight_name': 'Regular', + 'style_name': 'Regular', + 'hack': 'Hack-Regular.ttf', + 'mgen_plus': 'rounded-mgenplus-1m-regular.ttf', + 'hack_weight_reduce': 0, + 'mgen_weight_add': 0, + 'italic': False, + }, { + 'family': FAMILY, + 'name': FAMILY + '-RegularItalic', + 'filename': FAMILY + '-RegularItalic.ttf', + 'weight': 400, + 'weight_name': 'Regular', + 'style_name': 'Italic', + 'hack': 'Hack-Regular.ttf', + 'mgen_plus': 'rounded-mgenplus-1m-regular.ttf', + 'hack_weight_reduce': 0, + 'mgen_weight_add': 0, + 'italic': True, + }, { + 'family': FAMILY, + 'name': FAMILY + '-Bold', + 'filename': FAMILY + '-Bold.ttf', + 'weight': 700, + 'weight_name': 'Bold', + 'style_name': 'Bold', + 'hack': 'Hack-Bold.ttf', + 'mgen_plus': 'rounded-mgenplus-1m-bold.ttf', + 'hack_weight_reduce': 0, + 'mgen_weight_add': 0, + 'italic': False, + }, { + 'family': FAMILY, + 'name': FAMILY + '-BoldItalic', + 'filename': FAMILY + '-BoldItalic.ttf', + 'weight': 700, + 'weight_name': 'Bold', + 'style_name': 'Bold Italic', + 'hack': 'Hack-Bold.ttf', + 'mgen_plus': 'rounded-mgenplus-1m-bold.ttf', + 'hack_weight_reduce': 0, + 'mgen_weight_add': 0, + 'italic': True, + } +] def main(): - check_files() for _f in fonts: - log("Started: dist/" + _f["filename"]) - build_font(_f, True) - log("Finished: dist/" + _f["filename"]) - log("") - log("Started: dist/noemoji/" + _f["filename"]) - build_font(_f, False) - log("Finished: dist/noemoji/" + _f["filename"]) - log("") - + cica = Cica(_f["family"], + _f["name"], + _f["filename"], + _f["weight"], + _f["weight_name"], + _f["style_name"], + _f["hack"], + _f["mgen_plus"] + ) + cica.build_font(_f["name"], True) if __name__ == '__main__': main() From e83f3ce1b869a59ece19a5f1e0a3773049da4957 Mon Sep 17 00:00:00 2001 From: miiton <468745+miiton@users.noreply.github.com> Date: Sat, 29 Jun 2019 16:18:55 +0900 Subject: [PATCH 02/31] =?UTF-8?q?=F0=9F=92=B0=20=E3=83=AA=E3=83=95?= =?UTF-8?q?=E3=82=A1=E3=82=AF=E3=82=BF=E3=83=AA=E3=83=B3=E3=82=B0=E5=BE=8C?= =?UTF-8?q?=E3=83=93=E3=83=AB=E3=83=89=E3=81=8C=E4=B8=80=E9=80=9A=E3=82=8A?= =?UTF-8?q?=E5=8B=95=E3=81=8F=E3=82=88=E3=81=86=E3=81=AB?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- cica.py | 701 ++++++++++++++++++++++++++------------------------------ 1 file changed, 322 insertions(+), 379 deletions(-) diff --git a/cica.py b/cica.py index 777bbcf6..0d452785 100644 --- a/cica.py +++ b/cica.py @@ -195,33 +195,20 @@ def modify_iconsfordevs(_g): class Cica: - def __init__(self, family, name, output_name, weight, weight_name, style_name, src_font_en, src_font_jp): + def __init__(self, family, name, output_name, weight, weight_name, style_name, font_en, font_jp, italic): self.family = family self.name = name self.output_name = output_name self.weight = weight self.weight_name = weight_name self.style_name = style_name - self.src_font_en = src_font_en - self.src_font_jp = src_font_jp - self.check_files() + self.font_en = fontforge.open('./sourceFonts/%s' % font_en) + self.font_jp = fontforge.open('./sourceFonts/%s' % font_jp) + self.italic = italic + self.nerd = fontforge.open('./sourceFonts/nerd.sfd') + self.icons_for_devs = fontforge.open('./sourceFonts/iconsfordevs.ttf') - def check_files(self): - """ファイルがあるかチェック - 無ければ1を返してコマンドを終了させる - """ - err = 0 - if not os.path.isfile('./sourceFonts/%s' % self.src_font_en): - log('%s not exists.' % self.src_font_en) - err = 1 - if not os.path.isfile('./sourceFonts/%s' % self.src_font_jp): - log('%s not exists.' % self.src_font_jp) - err = 1 - - if err > 0: - sys.exit(err) - - def remove_glyph_from_en(self, _font): + def remove_glyph_from_en(self): """jpフォント側を採用したいグリフをenフォントから削除 """ glyphs = [ @@ -229,52 +216,49 @@ def remove_glyph_from_en(self, _font): ] for g in glyphs: - _font.selection.select(g) - _font.clear() - - return _font + self.font_en.selection.select(g) + self.font_en.clear() - def set_os2_values(self, _font, _info): + def set_os2_values(self): """フォントメタ情報の設定 """ - weight = _info.get('weight') - style_name = _info.get('style_name') - _font.os2_weight = weight - _font.os2_width = 5 - _font.os2_fstype = 0 + weight = self.weight + style_name = self.style_name + self.font_jp.os2_weight = weight + self.font_jp.os2_width = 5 + self.font_jp.os2_fstype = 0 if style_name == 'Regular': - _font.os2_stylemap = 64 + self.font_jp.os2_stylemap = 64 elif style_name == 'Bold': - _font.os2_stylemap = 32 + self.font_jp.os2_stylemap = 32 elif style_name == 'Italic': - _font.os2_stylemap = 1 + self.font_jp.os2_stylemap = 1 elif style_name == 'Bold Italic': - _font.os2_stylemap = 33 - _font.os2_vendor = 'TMNM' - _font.os2_version = 1 - _font.os2_winascent = ASCENT - _font.os2_winascent_add = False - _font.os2_windescent = DESCENT - _font.os2_windescent_add = False - - _font.os2_typoascent = -150 - _font.os2_typoascent_add = True - _font.os2_typodescent = 100 - _font.os2_typodescent_add = True - _font.os2_typolinegap = 0 - - _font.hhea_ascent = -150 - _font.hhea_ascent_add = True - _font.hhea_descent = 100 - _font.hhea_descent_add = True - _font.hhea_linegap = 0 - _font.os2_panose = (2, 11, int(weight / 100), 9, 2, 2, 3, 2, 2, 7) - return _font - - - def add_dejavu(self, _f, conf): + self.font_jp.os2_stylemap = 33 + self.font_jp.os2_vendor = 'TMNM' + self.font_jp.os2_version = 1 + self.font_jp.os2_winascent = ASCENT + self.font_jp.os2_winascent_add = False + self.font_jp.os2_windescent = DESCENT + self.font_jp.os2_windescent_add = False + + self.font_jp.os2_typoascent = -150 + self.font_jp.os2_typoascent_add = True + self.font_jp.os2_typodescent = 100 + self.font_jp.os2_typodescent_add = True + self.font_jp.os2_typolinegap = 0 + + self.font_jp.hhea_ascent = -150 + self.font_jp.hhea_ascent_add = True + self.font_jp.hhea_descent = 100 + self.font_jp.hhea_descent_add = True + self.font_jp.hhea_linegap = 0 + self.font_jp.os2_panose = (2, 11, int(weight / 100), 9, 2, 2, 3, 2, 2, 7) + + + def add_dejavu(self): dejavu = None - weight_name = conf.get('weight_name') + weight_name = self.weight_name if weight_name == "Regular": dejavu = fontforge.open('./sourceFonts/DejaVuSansMono.ttf') elif weight_name == "Bold": @@ -284,7 +268,7 @@ def add_dejavu(self, _f, conf): g.transform(psMat.compose(psMat.scale(0.45, 0.45), psMat.translate(-21, 0))) g.width = 512 - _f.importLookups(dejavu, dejavu.gpos_lookups) + self.font_jp.importLookups(dejavu, dejavu.gpos_lookups) # 0x0300 - 0x036f - Combining Diacritical Marks for g in dejavu.glyphs(): @@ -333,8 +317,8 @@ def add_dejavu(self, _f, conf): g.transform(psMat.translate(0, 0)) dejavu.selection.select(g.encoding) dejavu.copy() - _f.selection.select(g.encoding) - _f.paste() + self.font_jp.selection.select(g.encoding) + self.font_jp.paste() # 0x0370 - 0x03ff - GREEK for g in dejavu.glyphs(): if g.encoding < 0x0370 or g.encoding > 0x03ff or g.encoding == 0x0398: @@ -345,8 +329,8 @@ def add_dejavu(self, _f, conf): g.anchorPoints = (('Anchor-7', 'mark', 256, bb[3] + 20),) dejavu.selection.select(g.encoding) dejavu.copy() - _f.selection.select(g.encoding) - _f.paste() + self.font_jp.selection.select(g.encoding) + self.font_jp.paste() # 0x2100 - 0x214f Letterlike Symbols for g in dejavu.glyphs(): if g.encoding < 0x2100 or g.encoding > 0x214f or g.encoding == 0x2122: @@ -355,8 +339,8 @@ def add_dejavu(self, _f, conf): if len(g.references) == 0: dejavu.selection.select(g.encoding) dejavu.copy() - _f.selection.select(g.encoding) - _f.paste() + self.font_jp.selection.select(g.encoding) + self.font_jp.paste() # 0x2150 - 0x218f Number Forms for g in dejavu.glyphs(): if g.encoding < 0x2150 or g.encoding > 0x218f: @@ -365,8 +349,8 @@ def add_dejavu(self, _f, conf): if len(g.references) == 0: dejavu.selection.select(g.encoding) dejavu.copy() - _f.selection.select(g.encoding) - _f.paste() + self.font_jp.selection.select(g.encoding) + self.font_jp.paste() # 0x2190 - 0x21ff Arrows # TODO: 矢印を全角のままにしたパターンも生成したい for g in dejavu.glyphs(): @@ -376,8 +360,8 @@ def add_dejavu(self, _f, conf): if len(g.references) == 0: dejavu.selection.select(g.encoding) dejavu.copy() - _f.selection.select(g.encoding) - _f.paste() + self.font_jp.selection.select(g.encoding) + self.font_jp.paste() # 0x2200 - 0x22ff Mathematical Operators for g in dejavu.glyphs(): if g.encoding < 0x2200 or g.encoding > 0x22ff: @@ -386,8 +370,8 @@ def add_dejavu(self, _f, conf): if len(g.references) == 0: dejavu.selection.select(g.encoding) dejavu.copy() - _f.selection.select(g.encoding) - _f.paste() + self.font_jp.selection.select(g.encoding) + self.font_jp.paste() # 0x2300 - 0x23ff Miscellaneous Technical for g in dejavu.glyphs(): if g.encoding < 0x2300 or g.encoding > 0x23ff: @@ -396,76 +380,71 @@ def add_dejavu(self, _f, conf): if len(g.references) == 0: dejavu.selection.select(g.encoding) dejavu.copy() - _f.selection.select(g.encoding) - _f.paste() + self.font_jp.selection.select(g.encoding) + self.font_jp.paste() dejavu.close() - return _f - def vertical_line_to_broken_bar(self, _f): + def vertical_line_to_broken_bar(self): """縦線を破線にする """ - _f.selection.select(0x00a6) - _f.copy() - _f.selection.select(0x007c) - _f.paste() - return _f + self.font_jp.selection.select(0x00a6) + self.font_jp.copy() + self.font_jp.selection.select(0x007c) + self.font_jp.paste() + return self.font_jp - def emdash_to_broken_dash(self, _f): + def emdash_to_broken_dash(self): """ダッシュ記号を破線にする """ - _f.selection.select(0x006c) - _f.copy() - _f.selection.select(0x2014) - _f.pasteInto() - _f.intersect() - return _f - - def zenkaku_space(self, _f): + self.font_jp.selection.select(0x006c) + self.font_jp.copy() + self.font_jp.selection.select(0x2014) + self.font_jp.pasteInto() + self.font_jp.intersect() + + def zenkaku_space(self): """全角スペースに枠をつけて可視化する """ - _f.selection.select(0x2610) - _f.copy() - _f.selection.select(0x3000) - _f.paste() - _f.selection.select(0x271a) - _f.copy() - _f.selection.select(0x3000) - _f.pasteInto() - _f.intersect() - for g in _f.selection.byGlyphs: + self.font_jp.selection.select(0x2610) + self.font_jp.copy() + self.font_jp.selection.select(0x3000) + self.font_jp.paste() + self.font_jp.selection.select(0x271a) + self.font_jp.copy() + self.font_jp.selection.select(0x3000) + self.font_jp.pasteInto() + self.font_jp.intersect() + for g in self.font_jp.selection.byGlyphs: g = align_to_center(g) - return _f - def zero(self, _f): + def zero(self): """半角数字の0をドットゼロにする """ - _f.selection.select(0x4f) - _f.copy() - _f.selection.select(0x30) - _f.paste() - _f.selection.select(0xb7) - _f.copy() - _f.selection.select(0x30) - _f.pasteInto() - for g in _f.selection.byGlyphs: + self.font_jp.selection.select(0x4f) + self.font_jp.copy() + self.font_jp.selection.select(0x30) + self.font_jp.paste() + self.font_jp.selection.select(0xb7) + self.font_jp.copy() + self.font_jp.selection.select(0x30) + self.font_jp.pasteInto() + for g in self.font_jp.selection.byGlyphs: g = align_to_center(g) - return _f - def modify_WM(self, _f): + def modify_WM(self): """WとMの字体を調整 """ - _f.selection.select(0x57) - _f.transform(psMat.scale(0.95, 1.0)) - _f.copy() - _f.selection.select(0x4d) - _f.paste() - _f.transform(psMat.compose(psMat.rotate(math.radians(180)), psMat.translate(0, 627))) - for g in _f.selection.byGlyphs: + self.font_jp.selection.select(0x57) + self.font_jp.transform(psMat.scale(0.95, 1.0)) + self.font_jp.copy() + self.font_jp.selection.select(0x4d) + self.font_jp.paste() + self.font_jp.transform(psMat.compose(psMat.rotate(math.radians(180)), psMat.translate(0, 627))) + for g in self.font_jp.selection.byGlyphs: g = align_to_center(g) - return _f - def modify_m(self, _f, _weight): + def modify_m(self, _weight): """mの中央の棒を少し短くする """ m = fontforge.open('./sourceFonts/m-Regular.sfd') @@ -474,41 +453,37 @@ def modify_m(self, _f, _weight): m = fontforge.open('./sourceFonts/m-Bold.sfd') m.selection.select(0x6d) m.copy() - _f.selection.select(0x6d) - _f.paste() + self.font_en.selection.select(0x6d) + self.font_en.paste() for g in m.glyphs(): if g.encoding == 0x6d: anchorPoints = g.anchorPoints - for g in _f.glyphs(): + for g in self.font_en.glyphs(): if g.encoding == 0x6d: g.anchorPoints = anchorPoints - return _f - - def add_smalltriangle(self, _f): + def add_smalltriangle(self): """小さいサンカクを追加 NerdTree用 """ - _f.selection.select(0x25bc) - _f.copy() - _f.selection.select(0x25be) - _f.paste() - _f.transform(psMat.compose(psMat.scale(0.64), psMat.translate(0, 68))) - _f.copy() - _f.selection.select(0x25b8) - _f.paste() - _f.transform(psMat.rotate(math.radians(90))) - _f.transform(psMat.translate(0, 212)) - - for g in _f.glyphs(): + self.font_jp.selection.select(0x25bc) + self.font_jp.copy() + self.font_jp.selection.select(0x25be) + self.font_jp.paste() + self.font_jp.transform(psMat.compose(psMat.scale(0.64), psMat.translate(0, 68))) + self.font_jp.copy() + self.font_jp.selection.select(0x25b8) + self.font_jp.paste() + self.font_jp.transform(psMat.rotate(math.radians(90))) + self.font_jp.transform(psMat.translate(0, 212)) + + for g in self.font_jp.glyphs(): if g.encoding == 0x25be or g.encoding == 0x25b8: g.width = 512 g = align_to_center(g) - return _f - - def fix_box_drawings(self, _f): + def fix_box_drawings(self): """罫線を調整 """ left = [ @@ -524,7 +499,7 @@ def fix_box_drawings(self, _f): 0xf255e, 0xf255f, 0xf2560, 0xf256d, 0xf2570, 0xf2576, 0xf257a ] - for g in _f.glyphs(): + for g in self.font_jp.glyphs(): if g.encoding < 0x2500: continue if g.encoding > 0x256c and g.encoding < 0xf2500: @@ -534,9 +509,7 @@ def fix_box_drawings(self, _f): elif g.encoding in right: align_to_right(g) - return _f - - def reiwa(self, _f, _weight): + def reiwa(self, _weight): """令和グリフを追加 """ reiwa = fontforge.open('./sourceFonts/reiwa.sfd') @@ -547,189 +520,24 @@ def reiwa(self, _f, _weight): if g.isWorthOutputting: reiwa.selection.select(0x00) reiwa.copy() - _f.selection.select(0x32ff) - _f.paste() + self.font_jp.selection.select(0x32ff) + self.font_jp.paste() reiwa.close() - return _f - def import_svg(self, font): + def import_svg(self): """オリジナルのsvgグリフをインポートする """ files = glob.glob('sourceFonts/svg/*.svg') for f in files: filename, _ = os.path.splitext(os.path.basename(f)) - g = font.createChar(int(filename, 16)) + g = self.font_jp.createChar(int(filename, 16)) g.width = 1024 g.vwidth = 1024 g.clear() g.importOutlines(f) g.transform(psMat.translate(0, -61)) - # g = fix_overflow(g) - return font - - - def build_font(self, _f, emoji): - hack = fontforge.open('./sourceFonts/%s' % _f.get('hack')) - log('remove_glyph_from_hack()') - hack = self.remove_glyph_from_en(hack) - cica = fontforge.open('./sourceFonts/%s' % _f.get('mgen_plus')) - nerd = fontforge.open('./sourceFonts/nerd.sfd') - icons_for_devs = fontforge.open('./sourceFonts/iconsfordevs.ttf') - - - log('transform Hack') - for g in hack.glyphs(): - g.transform((0.42,0,0,0.42,0,0)) - if _f.get('hack_weight_reduce') != 0: - # g.changeWeight(_f.get('hack_weight_reduce'), 'auto', 0, 0, 'auto') - g.stroke("circular", _f.get('hack_weight_reduce'), 'butt', 'round', 'removeexternal') - g = align_to_center(g) - hack = self.modify_m(hack, _f.get('weight_name')) - - - alternate_expands = [ - 0x306e, - ] - - if _f.get('mgen_weight_add') != 0: - for g in cica.glyphs(): - # g.changeWeight(_f.get('mgen_weight_add'), 'auto', 0, 0, 'auto') - g.stroke("caligraphic", _f.get('mgen_weight_add'), _f.get('mgen_weight_add'), 45, 'removeinternal') - # g.stroke("circular", _f.get('mgen_weight_add'), 'butt', 'round', 'removeinternal') - - - ignoring_center = [ - 0x3001, 0x3002, 0x3008, 0x3009, 0x300a, 0x300b, 0x300c, 0x300d, - 0x300e, 0x300f, 0x3010, 0x3011, 0x3014, 0x3015, 0x3016, 0x3017, - 0x3018, 0x3019, 0x301a, 0x301b, 0x301d, 0x301e, 0x3099, 0x309a, - 0x309b, 0x309c, - ] - log('transform Mgen+') - for g in cica.glyphs(): - g.transform((0.91,0,0,0.91,0,0)) - full_half_threshold = 700 - if _f.get('italic'): - g.transform(psMat.skew(0.25)) - skew_amount = g.font.ascent * 0.91 * 0.25 - g.width = g.width + skew_amount - full_half_threshold += skew_amount - if g.width > full_half_threshold: - width = 1024 - else: - width = 512 - g.transform(psMat.translate((width - g.width)/2, 0)) - g.width = width - if g.encoding in ignoring_center: - pass - else: - g = align_to_center(g) - - log('modify border glyphs') - for g in hack.glyphs(): - if g.isWorthOutputting: - if _f.get('italic'): - g.transform(psMat.skew(0.25)) - if g.encoding >= 0x2500 and g.encoding <= 0x257f: - # 全角の罫線を0xf0000以降に退避 - cica.selection.select(g.encoding) - cica.copy() - cica.selection.select(g.encoding + 0xf0000) - cica.paste() - if g.encoding >= 0x2500 and g.encoding <= 0x25af: - g.transform(psMat.compose(psMat.scale(1.024, 1.024), psMat.translate(0, -30))) - g = align_to_center(g) - hack.selection.select(g.encoding) - hack.copy() - cica.selection.select(g.encoding) - cica.paste() - - log('modify nerd glyphs') - for g in nerd.glyphs(): - if g.encoding < 0xe0a0 or g.encoding > 0xfd46: - continue - g = modify_nerd(g) - nerd.selection.select(g.encoding) - nerd.copy() - if g.encoding >= 0xf500: - # Material Design IconsはNerd Fontsに従うとアラビア文字等を壊して - # しまうので、0xf0000〜に配置する - cica.selection.select(g.encoding + 0xf0000) - cica.paste() - else: - cica.selection.select(g.encoding) - cica.paste() - - log('modify icons_for_devs glyphs') - for g in icons_for_devs.glyphs(): - if g.encoding < 0xe900 or g.encoding > 0xe950: - continue - g = modify_iconsfordevs(g) - icons_for_devs.selection.select(g.encoding) - icons_for_devs.copy() - cica.selection.select(g.encoding) - cica.paste() - - cica = self.fix_box_drawings(cica) - cica = self.zenkaku_space(cica) - cica = self.zero(cica) - cica = self.modify_WM(cica) - cica = self.vertical_line_to_broken_bar(cica) - cica = self.emdash_to_broken_dash(cica) - cica = self.reiwa(cica, _f.get('weight_name')) - cica = self.add_gopher(cica) - cica = self.modify_ellipsis(cica) - if emoji: - cica = self.add_notoemoji(cica) - cica = self.add_smalltriangle(cica) - cica = self.add_dejavu(cica, _f) - cica = self.resize_supersub(cica) - - log("fix_overflow()") - for g in cica.glyphs(): - g = fix_overflow(g) - log("import_svg()") - cica = self.import_svg(cica) - cica.ascent = ASCENT - cica.descent = DESCENT - cica.upos = 45 - cica.fontname = _f.get('family') - cica.familyname = _f.get('family') - cica.fullname = _f.get('name') - cica.weight = _f.get('weight_name') - cica = self.set_os2_values(cica, _f) - cica.appendSFNTName(0x411,0, COPYRIGHT) - cica.appendSFNTName(0x411,1, _f.get('family')) - cica.appendSFNTName(0x411,2, _f.get('style_name')) - cica.appendSFNTName(0x411,4, _f.get('name')) - cica.appendSFNTName(0x411,5, "Version " + VERSION) - cica.appendSFNTName(0x411,6, _f.get('family') + "-" + _f.get('weight_name')) - cica.appendSFNTName(0x411,13, LICENSE) - cica.appendSFNTName(0x411,16, _f.get('family')) - cica.appendSFNTName(0x411,17, _f.get('style_name')) - cica.appendSFNTName(0x409,0, COPYRIGHT) - cica.appendSFNTName(0x409,1, _f.get('family')) - cica.appendSFNTName(0x409,2, _f.get('style_name')) - cica.appendSFNTName(0x409,3, VERSION + ";" + _f.get('family') + "-" + _f.get('style_name')) - cica.appendSFNTName(0x409,4, _f.get('name')) - cica.appendSFNTName(0x409,5, "Version " + VERSION) - cica.appendSFNTName(0x409,6, _f.get('name')) - cica.appendSFNTName(0x409,13, LICENSE) - cica.appendSFNTName(0x409,16, _f.get('family')) - cica.appendSFNTName(0x409,17, _f.get('style_name')) - if emoji: - fontpath = './dist/%s' % _f.get('filename') - else: - fontpath = './dist/noemoji/%s' % _f.get('filename') - - cica.generate(fontpath) - cica.close() - hack.close() - nerd.close() - icons_for_devs.close() - - - def add_notoemoji(self, _f): + def add_notoemoji(self): notoemoji = fontforge.open('./sourceFonts/NotoEmoji-Regular.ttf') for g in notoemoji.glyphs(): if g.isWorthOutputting and g.encoding > 0x04f9: @@ -737,27 +545,29 @@ def add_notoemoji(self, _f): g = align_to_center(g) notoemoji.selection.select(g.encoding) notoemoji.copy() - _f.selection.select(g.encoding) - _f.paste() + self.font_jp.selection.select(g.encoding) + self.font_jp.paste() notoemoji.close() - return _f - def add_gopher(self, _f): + def add_gopher(self): + """半身Gopherくんを追加 + """ gopher = fontforge.open('./sourceFonts/gopher.sfd') for g in gopher.glyphs(): if g.isWorthOutputting: gopher.selection.select(0x40) gopher.copy() - _f.selection.select(0xE160) - _f.paste() + self.font_jp.selection.select(0xE160) + self.font_jp.paste() g.transform(psMat.compose(psMat.scale(-1, 1), psMat.translate(g.width, 0))) gopher.copy() - _f.selection.select(0xE161) - _f.paste() + self.font_jp.selection.select(0xE161) + self.font_jp.paste() gopher.close() - return _f - def resize_supersub(self, _f): + def resize_supersub(self): + """上付文字、下付文字を調整して可読性を上げる + """ superscripts = [ {"src": 0x0031, "dest": 0x00b9}, {"src": 0x0032, "dest": 0x00b2}, {"src": 0x0033, "dest": 0x00b3}, {"src": 0x0030, "dest": 0x2070}, @@ -849,17 +659,17 @@ def resize_supersub(self, _f): ] for g in superscripts: - _f.selection.select(g["src"]) - _f.copy() - _f.selection.select(g["dest"]) - _f.paste() + self.font_jp.selection.select(g["src"]) + self.font_jp.copy() + self.font_jp.selection.select(g["dest"]) + self.font_jp.paste() for g in subscripts: - _f.selection.select(g["src"]) - _f.copy() - _f.selection.select(g["dest"]) - _f.paste() + self.font_jp.selection.select(g["src"]) + self.font_jp.copy() + self.font_jp.selection.select(g["dest"]) + self.font_jp.paste() - for g in _f.glyphs("encoding"): + for g in self.font_jp.glyphs("encoding"): if g.encoding > 0x2c7d: continue elif self.in_scripts(g.encoding, superscripts): @@ -888,7 +698,6 @@ def resize_supersub(self, _f): y = -60 g.transform(psMat.translate(0, y)) align_to_center(g) - return _f def in_scripts(self, encoding, scripts): for s in scripts: @@ -903,24 +712,24 @@ def scripts_from(self, encoding, scripts): return s["src"] raise ValueError - def modify_ellipsis(self, _f): + def modify_ellipsis(self): """3点リーダーを半角にする DejaVuSansMono の U+22EF(⋯) をU+2026(…)、U+22EE(⋮)、U+22F0(⋰)、U+22F1(⋱) にコピーした上で回転させて生成 三点リーダの文字幅について · Issue #41 · miiton/Cica https://github.com/miiton/Cica/issues/41 """ - _f.selection.select(0x22ef) - _f.copy() - _f.selection.select(0x2026) - _f.paste() - _f.selection.select(0x22ee) - _f.paste() - _f.selection.select(0x22f0) - _f.paste() - _f.selection.select(0x22f1) - _f.paste() - for g in _f.glyphs("encoding"): + self.font_jp.selection.select(0x22ef) + self.font_jp.copy() + self.font_jp.selection.select(0x2026) + self.font_jp.paste() + self.font_jp.selection.select(0x22ee) + self.font_jp.paste() + self.font_jp.selection.select(0x22f0) + self.font_jp.paste() + self.font_jp.selection.select(0x22f1) + self.font_jp.paste() + for g in self.font_jp.glyphs("encoding"): if g.encoding < 0x22ee: continue elif g.encoding > 0x22f1: @@ -946,45 +755,180 @@ def modify_ellipsis(self, _f): trcen = psMat.translate(-cx, -cy) rotcen = psMat.compose(trcen, psMat.compose(psMat.rotate(math.radians(-45)), psMat.inverse(trcen))) g.transform(rotcen) - return _f + + def build_font(self, emoji): + + log('remove_glyph_from_en()') + self.remove_glyph_from_en() + + log('transform font_en') + for g in self.font_en.glyphs(): + g.transform((0.42,0,0,0.42,0,0)) + g = align_to_center(g) + self.modify_m(self.weight_name) + + ignoring_center = [ + 0x3001, 0x3002, 0x3008, 0x3009, 0x300a, 0x300b, 0x300c, 0x300d, + 0x300e, 0x300f, 0x3010, 0x3011, 0x3014, 0x3015, 0x3016, 0x3017, + 0x3018, 0x3019, 0x301a, 0x301b, 0x301d, 0x301e, 0x3099, 0x309a, + 0x309b, 0x309c, + ] + log('transform font_jp') + for g in self.font_jp.glyphs(): + g.transform((0.91,0,0,0.91,0,0)) + full_half_threshold = 700 + if self.italic: + g.transform(psMat.skew(0.25)) + skew_amount = g.font.ascent * 0.91 * 0.25 + g.width = g.width + skew_amount + full_half_threshold += skew_amount + if g.width > full_half_threshold: + width = 1024 + else: + width = 512 + g.transform(psMat.translate((width - g.width)/2, 0)) + g.width = width + if g.encoding in ignoring_center: + pass + else: + g = align_to_center(g) + + log('modify border glyphs') + for g in self.font_en.glyphs(): + if g.isWorthOutputting: + if self.italic: + g.transform(psMat.skew(0.25)) + if g.encoding >= 0x2500 and g.encoding <= 0x257f: + # 全角の罫線を0xf0000以降に退避 + self.font_jp.selection.select(g.encoding) + self.font_jp.copy() + self.font_jp.selection.select(g.encoding + 0xf0000) + self.font_jp.paste() + if g.encoding >= 0x2500 and g.encoding <= 0x25af: + g.transform(psMat.compose(psMat.scale(1.024, 1.024), psMat.translate(0, -30))) + g = align_to_center(g) + self.font_en.selection.select(g.encoding) + self.font_en.copy() + self.font_jp.selection.select(g.encoding) + self.font_jp.paste() + + log('modify nerd glyphs') + for g in self.nerd.glyphs(): + if g.encoding < 0xe0a0 or g.encoding > 0xfd46: + continue + g = modify_nerd(g) + self.nerd.selection.select(g.encoding) + self.nerd.copy() + if g.encoding >= 0xf500: + # Material Design IconsはNerd Fontsに従うとアラビア文字等を壊して + # しまうので、0xf0000〜に配置する + self.font_jp.selection.select(g.encoding + 0xf0000) + self.font_jp.paste() + else: + self.font_jp.selection.select(g.encoding) + self.font_jp.paste() + + log('modify icons_for_devs glyphs') + for g in self.icons_for_devs.glyphs(): + if g.encoding < 0xe900 or g.encoding > 0xe950: + continue + g = modify_iconsfordevs(g) + self.icons_for_devs.selection.select(g.encoding) + self.icons_for_devs.copy() + self.font_jp.selection.select(g.encoding) + self.font_jp.paste() + + self.fix_box_drawings() + self.zenkaku_space() + self.zero() + self.modify_WM() + self.vertical_line_to_broken_bar() + self.emdash_to_broken_dash() + self.reiwa(self.weight_name) + self.add_gopher() + self.modify_ellipsis() + if emoji: + self.add_notoemoji() + self.add_smalltriangle() + self.add_dejavu() + self.resize_supersub() + + log("fix_overflow()") + for g in self.font_jp.glyphs(): + g = fix_overflow(g) + log("import_svg()") + self.import_svg() + self.font_jp.ascent = ASCENT + self.font_jp.descent = DESCENT + self.font_jp.upos = 45 + self.font_jp.fontname = self.family + self.font_jp.familyname = self.family + self.font_jp.fullname = self.name + self.font_jp.weight = self.weight_name + self.set_os2_values() + self.font_jp.appendSFNTName(0x411,0, COPYRIGHT) + self.font_jp.appendSFNTName(0x411,1, self.family) + self.font_jp.appendSFNTName(0x411,2, self.style_name) + self.font_jp.appendSFNTName(0x411,4, self.name) + self.font_jp.appendSFNTName(0x411,5, "Version " + VERSION) + self.font_jp.appendSFNTName(0x411,6, self.family + "-" + self.weight_name) + self.font_jp.appendSFNTName(0x411,13, LICENSE) + self.font_jp.appendSFNTName(0x411,16, self.family) + self.font_jp.appendSFNTName(0x411,17, self.style_name) + self.font_jp.appendSFNTName(0x409,0, COPYRIGHT) + self.font_jp.appendSFNTName(0x409,1, self.family) + self.font_jp.appendSFNTName(0x409,2, self.style_name) + self.font_jp.appendSFNTName(0x409,3, VERSION + ";" + self.family + "-" + self.style_name) + self.font_jp.appendSFNTName(0x409,4, self.name) + self.font_jp.appendSFNTName(0x409,5, "Version " + VERSION) + self.font_jp.appendSFNTName(0x409,6, self.name) + self.font_jp.appendSFNTName(0x409,13, LICENSE) + self.font_jp.appendSFNTName(0x409,16, self.family) + self.font_jp.appendSFNTName(0x409,17, self.style_name) + if emoji: + fontpath = './dist/%s' % self.output_name + else: + fontpath = './dist/noemoji/%s' % self.output_name + + self.font_jp.generate(fontpath) + + self.font_jp.close() + self.font_en.close() + self.nerd.close() + self.icons_for_devs.close() + fonts = [ { - 'family': FAMILY, - 'name': FAMILY + '-Regular', - 'filename': FAMILY + '-Regular.ttf', - 'weight': 400, - 'weight_name': 'Regular', - 'style_name': 'Regular', - 'hack': 'Hack-Regular.ttf', - 'mgen_plus': 'rounded-mgenplus-1m-regular.ttf', - 'hack_weight_reduce': 0, - 'mgen_weight_add': 0, - 'italic': False, - }, { - 'family': FAMILY, - 'name': FAMILY + '-RegularItalic', - 'filename': FAMILY + '-RegularItalic.ttf', - 'weight': 400, - 'weight_name': 'Regular', - 'style_name': 'Italic', - 'hack': 'Hack-Regular.ttf', - 'mgen_plus': 'rounded-mgenplus-1m-regular.ttf', - 'hack_weight_reduce': 0, - 'mgen_weight_add': 0, - 'italic': True, + 'family': FAMILY, + 'name': FAMILY + '-Regular', + 'filename': FAMILY + '-Regular.ttf', + 'weight': 400, + 'weight_name': 'Regular', + 'style_name': 'Regular', + 'hack': 'Hack-Regular.ttf', + 'mgen_plus': 'rounded-mgenplus-1m-regular.ttf', + 'italic': False, + }, { + 'family': FAMILY, + 'name': FAMILY + '-RegularItalic', + 'filename': FAMILY + '-RegularItalic.ttf', + 'weight': 400, + 'weight_name': 'Regular', + 'style_name': 'Italic', + 'hack': 'Hack-Regular.ttf', + 'mgen_plus': 'rounded-mgenplus-1m-regular.ttf', + 'italic': True, }, { 'family': FAMILY, 'name': FAMILY + '-Bold', 'filename': FAMILY + '-Bold.ttf', 'weight': 700, 'weight_name': 'Bold', - 'style_name': 'Bold', + 'style_name': 'Bold', 'hack': 'Hack-Bold.ttf', 'mgen_plus': 'rounded-mgenplus-1m-bold.ttf', - 'hack_weight_reduce': 0, - 'mgen_weight_add': 0, 'italic': False, }, { 'family': FAMILY, @@ -995,8 +939,6 @@ def modify_ellipsis(self, _f): 'style_name': 'Bold Italic', 'hack': 'Hack-Bold.ttf', 'mgen_plus': 'rounded-mgenplus-1m-bold.ttf', - 'hack_weight_reduce': 0, - 'mgen_weight_add': 0, 'italic': True, } ] @@ -1011,9 +953,10 @@ def main(): _f["weight_name"], _f["style_name"], _f["hack"], - _f["mgen_plus"] + _f["mgen_plus"], + _f["italic"] ) - cica.build_font(_f["name"], True) + cica.build_font(True) if __name__ == '__main__': main() From 046b4d38bce9fa7eda782836efc439634e8ca45f Mon Sep 17 00:00:00 2001 From: miiton <468745+miiton@users.noreply.github.com> Date: Sun, 30 Jun 2019 00:04:56 +0900 Subject: [PATCH 03/31] =?UTF-8?q?=F0=9F=92=B0=20sourceFonts=20->=20source?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- cica.py | 41 +++++++++++--------------- {sourceFonts => source}/gopher.sfd | 0 {sourceFonts => source}/m-Bold.sfd | 0 {sourceFonts => source}/m-Regular.sfd | 0 {sourceFonts => source}/nerd.sfd | 0 {sourceFonts => source}/reiwa-Bold.sfd | 0 {sourceFonts => source}/reiwa.sfd | 0 {sourceFonts => source}/svg/f3000.svg | 0 {sourceFonts => source}/svg/f3001.svg | 0 {sourceFonts => source}/svg/f3002.svg | 0 {sourceFonts => source}/svg/f3100.svg | 0 {sourceFonts => source}/svg/f3101.svg | 0 {sourceFonts => source}/svg/f3102.svg | 0 {sourceFonts => source}/svg/fe0b0.svg | 0 {sourceFonts => source}/svg/fe0b1.svg | 0 {sourceFonts => source}/svg/fe0b2.svg | 0 {sourceFonts => source}/svg/fe0b3.svg | 0 {sourceFonts => source}/svg/fe0b4.svg | 0 {sourceFonts => source}/svg/fe0b5.svg | 0 {sourceFonts => source}/svg/fe566.svg | 0 {sourceFonts => source}/svg/fe567.svg | 0 {sourceFonts => source}/svg/fe568.svg | 0 22 files changed, 17 insertions(+), 24 deletions(-) rename {sourceFonts => source}/gopher.sfd (100%) rename {sourceFonts => source}/m-Bold.sfd (100%) rename {sourceFonts => source}/m-Regular.sfd (100%) rename {sourceFonts => source}/nerd.sfd (100%) rename {sourceFonts => source}/reiwa-Bold.sfd (100%) rename {sourceFonts => source}/reiwa.sfd (100%) rename {sourceFonts => source}/svg/f3000.svg (100%) rename {sourceFonts => source}/svg/f3001.svg (100%) rename {sourceFonts => source}/svg/f3002.svg (100%) rename {sourceFonts => source}/svg/f3100.svg (100%) rename {sourceFonts => source}/svg/f3101.svg (100%) rename {sourceFonts => source}/svg/f3102.svg (100%) rename {sourceFonts => source}/svg/fe0b0.svg (100%) rename {sourceFonts => source}/svg/fe0b1.svg (100%) rename {sourceFonts => source}/svg/fe0b2.svg (100%) rename {sourceFonts => source}/svg/fe0b3.svg (100%) rename {sourceFonts => source}/svg/fe0b4.svg (100%) rename {sourceFonts => source}/svg/fe0b5.svg (100%) rename {sourceFonts => source}/svg/fe566.svg (100%) rename {sourceFonts => source}/svg/fe567.svg (100%) rename {sourceFonts => source}/svg/fe568.svg (100%) diff --git a/cica.py b/cica.py index 0d452785..73ca21d7 100644 --- a/cica.py +++ b/cica.py @@ -6,13 +6,14 @@ import sys import math import glob +import width_parser from datetime import datetime # ASCENT = 850 # DESCENT = 174 ASCENT = 820 DESCENT = 204 -SOURCE = './sourceFonts' +SOURCE = './source' LICENSE = open('./LICENSE.txt').read() COPYRIGHT = open('./COPYRIGHT.txt').read() VERSION = '5.0.1' @@ -202,11 +203,11 @@ def __init__(self, family, name, output_name, weight, weight_name, style_name, f self.weight = weight self.weight_name = weight_name self.style_name = style_name - self.font_en = fontforge.open('./sourceFonts/%s' % font_en) - self.font_jp = fontforge.open('./sourceFonts/%s' % font_jp) + self.font_en = fontforge.open('./source/%s' % font_en) + self.font_jp = fontforge.open('./source/%s' % font_jp) self.italic = italic - self.nerd = fontforge.open('./sourceFonts/nerd.sfd') - self.icons_for_devs = fontforge.open('./sourceFonts/iconsfordevs.ttf') + self.nerd = fontforge.open('./source/nerd.sfd') + self.icons_for_devs = fontforge.open('./source/iconsfordevs.ttf') def remove_glyph_from_en(self): """jpフォント側を採用したいグリフをenフォントから削除 @@ -260,9 +261,9 @@ def add_dejavu(self): dejavu = None weight_name = self.weight_name if weight_name == "Regular": - dejavu = fontforge.open('./sourceFonts/DejaVuSansMono.ttf') + dejavu = fontforge.open('./source/DejaVuSansMono.ttf') elif weight_name == "Bold": - dejavu = fontforge.open('./sourceFonts/DejaVuSansMono-Bold.ttf') + dejavu = fontforge.open('./source/DejaVuSansMono-Bold.ttf') for g in dejavu.glyphs(): g.transform(psMat.compose(psMat.scale(0.45, 0.45), psMat.translate(-21, 0))) @@ -447,10 +448,10 @@ def modify_WM(self): def modify_m(self, _weight): """mの中央の棒を少し短くする """ - m = fontforge.open('./sourceFonts/m-Regular.sfd') + m = fontforge.open('./source/m-Regular.sfd') if _weight == 'Bold': m.close() - m = fontforge.open('./sourceFonts/m-Bold.sfd') + m = fontforge.open('./source/m-Bold.sfd') m.selection.select(0x6d) m.copy() self.font_en.selection.select(0x6d) @@ -512,10 +513,10 @@ def fix_box_drawings(self): def reiwa(self, _weight): """令和グリフを追加 """ - reiwa = fontforge.open('./sourceFonts/reiwa.sfd') + reiwa = fontforge.open('./source/reiwa.sfd') if _weight == 'Bold': reiwa.close() - reiwa = fontforge.open('./sourceFonts/reiwa-Bold.sfd') + reiwa = fontforge.open('./source/reiwa-Bold.sfd') for g in reiwa.glyphs(): if g.isWorthOutputting: reiwa.selection.select(0x00) @@ -527,7 +528,7 @@ def reiwa(self, _weight): def import_svg(self): """オリジナルのsvgグリフをインポートする """ - files = glob.glob('sourceFonts/svg/*.svg') + files = glob.glob('source/svg/*.svg') for f in files: filename, _ = os.path.splitext(os.path.basename(f)) g = self.font_jp.createChar(int(filename, 16)) @@ -538,7 +539,7 @@ def import_svg(self): g.transform(psMat.translate(0, -61)) def add_notoemoji(self): - notoemoji = fontforge.open('./sourceFonts/NotoEmoji-Regular.ttf') + notoemoji = fontforge.open('./source/NotoEmoji-Regular.ttf') for g in notoemoji.glyphs(): if g.isWorthOutputting and g.encoding > 0x04f9: g.transform((0.42,0,0,0.42,0,0)) @@ -552,7 +553,7 @@ def add_notoemoji(self): def add_gopher(self): """半身Gopherくんを追加 """ - gopher = fontforge.open('./sourceFonts/gopher.sfd') + gopher = fontforge.open('./source/gopher.sfd') for g in gopher.glyphs(): if g.isWorthOutputting: gopher.selection.select(0x40) @@ -700,18 +701,13 @@ def resize_supersub(self): align_to_center(g) def in_scripts(self, encoding, scripts): + """scriptsの中にencodingが含まれるかをチェックする + """ for s in scripts: if encoding == s["dest"]: return True return False - - def scripts_from(self, encoding, scripts): - for s in scripts: - if encoding == s["dest"]: - return s["src"] - raise ValueError - def modify_ellipsis(self): """3点リーダーを半角にする DejaVuSansMono の U+22EF(⋯) をU+2026(…)、U+22EE(⋮)、U+22F0(⋰)、U+22F1(⋱) @@ -897,8 +893,6 @@ def build_font(self, emoji): self.nerd.close() self.icons_for_devs.close() - - fonts = [ { 'family': FAMILY, @@ -943,7 +937,6 @@ def build_font(self, emoji): } ] - def main(): for _f in fonts: cica = Cica(_f["family"], diff --git a/sourceFonts/gopher.sfd b/source/gopher.sfd similarity index 100% rename from sourceFonts/gopher.sfd rename to source/gopher.sfd diff --git a/sourceFonts/m-Bold.sfd b/source/m-Bold.sfd similarity index 100% rename from sourceFonts/m-Bold.sfd rename to source/m-Bold.sfd diff --git a/sourceFonts/m-Regular.sfd b/source/m-Regular.sfd similarity index 100% rename from sourceFonts/m-Regular.sfd rename to source/m-Regular.sfd diff --git a/sourceFonts/nerd.sfd b/source/nerd.sfd similarity index 100% rename from sourceFonts/nerd.sfd rename to source/nerd.sfd diff --git a/sourceFonts/reiwa-Bold.sfd b/source/reiwa-Bold.sfd similarity index 100% rename from sourceFonts/reiwa-Bold.sfd rename to source/reiwa-Bold.sfd diff --git a/sourceFonts/reiwa.sfd b/source/reiwa.sfd similarity index 100% rename from sourceFonts/reiwa.sfd rename to source/reiwa.sfd diff --git a/sourceFonts/svg/f3000.svg b/source/svg/f3000.svg similarity index 100% rename from sourceFonts/svg/f3000.svg rename to source/svg/f3000.svg diff --git a/sourceFonts/svg/f3001.svg b/source/svg/f3001.svg similarity index 100% rename from sourceFonts/svg/f3001.svg rename to source/svg/f3001.svg diff --git a/sourceFonts/svg/f3002.svg b/source/svg/f3002.svg similarity index 100% rename from sourceFonts/svg/f3002.svg rename to source/svg/f3002.svg diff --git a/sourceFonts/svg/f3100.svg b/source/svg/f3100.svg similarity index 100% rename from sourceFonts/svg/f3100.svg rename to source/svg/f3100.svg diff --git a/sourceFonts/svg/f3101.svg b/source/svg/f3101.svg similarity index 100% rename from sourceFonts/svg/f3101.svg rename to source/svg/f3101.svg diff --git a/sourceFonts/svg/f3102.svg b/source/svg/f3102.svg similarity index 100% rename from sourceFonts/svg/f3102.svg rename to source/svg/f3102.svg diff --git a/sourceFonts/svg/fe0b0.svg b/source/svg/fe0b0.svg similarity index 100% rename from sourceFonts/svg/fe0b0.svg rename to source/svg/fe0b0.svg diff --git a/sourceFonts/svg/fe0b1.svg b/source/svg/fe0b1.svg similarity index 100% rename from sourceFonts/svg/fe0b1.svg rename to source/svg/fe0b1.svg diff --git a/sourceFonts/svg/fe0b2.svg b/source/svg/fe0b2.svg similarity index 100% rename from sourceFonts/svg/fe0b2.svg rename to source/svg/fe0b2.svg diff --git a/sourceFonts/svg/fe0b3.svg b/source/svg/fe0b3.svg similarity index 100% rename from sourceFonts/svg/fe0b3.svg rename to source/svg/fe0b3.svg diff --git a/sourceFonts/svg/fe0b4.svg b/source/svg/fe0b4.svg similarity index 100% rename from sourceFonts/svg/fe0b4.svg rename to source/svg/fe0b4.svg diff --git a/sourceFonts/svg/fe0b5.svg b/source/svg/fe0b5.svg similarity index 100% rename from sourceFonts/svg/fe0b5.svg rename to source/svg/fe0b5.svg diff --git a/sourceFonts/svg/fe566.svg b/source/svg/fe566.svg similarity index 100% rename from sourceFonts/svg/fe566.svg rename to source/svg/fe566.svg diff --git a/sourceFonts/svg/fe567.svg b/source/svg/fe567.svg similarity index 100% rename from sourceFonts/svg/fe567.svg rename to source/svg/fe567.svg diff --git a/sourceFonts/svg/fe568.svg b/source/svg/fe568.svg similarity index 100% rename from sourceFonts/svg/fe568.svg rename to source/svg/fe568.svg From d6a8d03e941aa3f02114c9eeb68605b41d37cb85 Mon Sep 17 00:00:00 2001 From: miiton <468745+miiton@users.noreply.github.com> Date: Sun, 30 Jun 2019 00:06:08 +0900 Subject: [PATCH 04/31] =?UTF-8?q?=F0=9F=92=B0=20add=20make=20collect-sourc?= =?UTF-8?q?e?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- Makefile | 17 +++++++++++++++++ 1 file changed, 17 insertions(+) diff --git a/Makefile b/Makefile index 917c25c2..7b526226 100644 --- a/Makefile +++ b/Makefile @@ -1,2 +1,19 @@ +collect-source: + curl -L https://github.com/source-foundry/Hack/releases/download/v3.003/Hack-v3.003-ttf.zip -o hack.zip + unar hack.zip + cp ttf/* source/ + rm hack.zip + rm -r ttf + curl -LO https://osdn.jp/downloads/users/8/8598/rounded-mgenplus-20150602.7z + unar rounded-mgenplus-20150602.7z + cp rounded-mgenplus-20150602/rounded-mgenplus-1m-regular.ttf ./source + cp rounded-mgenplus-20150602/rounded-mgenplus-1m-bold.ttf ./source + curl -L https://github.com/googlei18n/noto-emoji/raw/master/fonts/NotoEmoji-Regular.ttf -o source/NotoEmoji-Regular.ttf + curl -LO http://sourceforge.net/projects/dejavu/files/dejavu/2.37/dejavu-fonts-ttf-2.37.zip + unar dejavu-fonts-ttf-2.37.zip + mv dejavu-fonts-ttf-2.37/ttf/DejaVuSansMono.ttf ./source/ + mv dejavu-fonts-ttf-2.37/ttf/DejaVuSansMono-Bold.ttf ./source/ + curl -L https://github.com/mirmat/iconsfordevs/raw/master/fonts/iconsfordevs.ttf -o source/iconsfordevs.ttf + curl -L http://www.unicode.org/Public/12.0.0/ucd/EastAsianWidth.txt -o source/EastAsianWidth.txt build: @fontforge -lang=py -script cica.py 2> /dev/null From 82e64f735f7ad470d0ac1d6f6d15835a567db82f Mon Sep 17 00:00:00 2001 From: miiton <468745+miiton@users.noreply.github.com> Date: Sun, 30 Jun 2019 00:06:42 +0900 Subject: [PATCH 05/31] =?UTF-8?q?=F0=9F=92=B0=20update=20.gitignore?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .gitignore | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.gitignore b/.gitignore index daab4e67..bb0ab095 100644 --- a/.gitignore +++ b/.gitignore @@ -1,5 +1,5 @@ tmp/* -sourceFonts/* +source/* Cica/* .DS_Store *.orig From 24858b2a3e666bb3ae5d89e3047b1a266a5fcee7 Mon Sep 17 00:00:00 2001 From: miiton <468745+miiton@users.noreply.github.com> Date: Sun, 30 Jun 2019 00:07:26 +0900 Subject: [PATCH 06/31] =?UTF-8?q?=E2=9C=A8=20=E6=96=87=E5=AD=97=E5=B9=85?= =?UTF-8?q?=E3=82=92=E8=BF=94=E3=81=99=E3=81=9F=E3=82=81=E3=81=AEclass?= =?UTF-8?q?=E8=BF=BD=E5=8A=A0?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- width_parser.py | 70 +++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 70 insertions(+) create mode 100644 width_parser.py diff --git a/width_parser.py b/width_parser.py new file mode 100644 index 00000000..32905d89 --- /dev/null +++ b/width_parser.py @@ -0,0 +1,70 @@ +#!/usr/bin/env python +# -*- coding: utf-8 -*- + +import os +import re + +# 0: ambi, 1: half, 2: wide +# glyphs = [ +# {0xe0b3: 0}, +# {0xe0b3: 0}, +# {0xe0b3: 0}, +# {0xe0b3: 0}, +# ] + +class WidthParser: + """グリフの幅をunicode.orgのデータから判定する + + Examples + -------- + >>> wp = WidthParser() + >>> wp.width(0x3000) + 2 + """ + def __init__(self): + self.width_type = { + 'A': 0, + 'H': 1, 'N': 1, 'Na': 1, + 'F': 2, 'W': 2, + } + self.dictionary = {} + self.execute() + + + def parse_line(self, line): + a = line.split(";") + u = a[0].split("..") + width = self.width_type[a[1]] + start = int(u[0], 16) + if len(u) == 2: + finish = int(u[1], 16) + for i in range(start, finish): + self.dictionary[i] = width + else: + self.dictionary[start] = width + + + def execute(self): + """EastAsianWidth.txtをパースする + """ + pattern = '^([^ ]+) *#.*$' + regex = re.compile(pattern) + data = open("source/EastAsianWidth.txt", "r") + + # 一行ずつ読み込んでは表示する + for line in data: + match = regex.match(line) + if match: + self.parse_line(match.group(1)) + + # ファイルをクローズする + data.close() + + def width(self, uni): + return self.dictionary[uni] + + + +if __name__ == '__main__': + wp = WidthParser() + print(wp.width(0x3000)) From 1a92dea6c6b1c6df299bf527d466e49ece422568 Mon Sep 17 00:00:00 2001 From: miiton <468745+miiton@users.noreply.github.com> Date: Sun, 30 Jun 2019 00:36:04 +0900 Subject: [PATCH 07/31] =?UTF-8?q?=E2=9C=A8=20=E3=82=B9=E3=83=A9=E3=83=83?= =?UTF-8?q?=E3=82=B7=E3=83=A5=E3=82=BC=E3=83=AD=E4=BD=9C=E6=88=90=E5=87=A6?= =?UTF-8?q?=E7=90=86=E8=BF=BD=E5=8A=A0?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- cica.py | 22 ++++++++++++++++++++-- 1 file changed, 20 insertions(+), 2 deletions(-) diff --git a/cica.py b/cica.py index 73ca21d7..3a30782a 100644 --- a/cica.py +++ b/cica.py @@ -419,7 +419,7 @@ def zenkaku_space(self): for g in self.font_jp.selection.byGlyphs: g = align_to_center(g) - def zero(self): + def dotted_zero(self): """半角数字の0をドットゼロにする """ self.font_jp.selection.select(0x4f) @@ -433,6 +433,23 @@ def zero(self): for g in self.font_jp.selection.byGlyphs: g = align_to_center(g) + def slashed_zero(self): + """半角数字の0をスラッシュゼロにする + """ + self.font_jp.selection.select(0x4f) + self.font_jp.copy() + self.font_jp.selection.select(0x30) + self.font_jp.paste() + self.font_jp.selection.select(0x2f) + self.font_jp.copy() + self.font_jp.selection.select(0x1) + self.font_jp.paste() + self.font_jp.transform(psMat.compose(psMat.scale(0.7, 0.75), psMat.translate(70, 115))) + self.font_jp.copy() + self.font_jp.selection.select(0x30) + self.font_jp.pasteInto() + self.font_jp.removeOverlap() + def modify_WM(self): """WとMの字体を調整 """ @@ -836,7 +853,8 @@ def build_font(self, emoji): self.fix_box_drawings() self.zenkaku_space() - self.zero() + self.dotted_zero() + self.slashed_zero() self.modify_WM() self.vertical_line_to_broken_bar() self.emdash_to_broken_dash() From aea46880a24a43ba237fdce8f32543758220d5b1 Mon Sep 17 00:00:00 2001 From: miiton <468745+miiton@users.noreply.github.com> Date: Sun, 30 Jun 2019 08:18:26 +0900 Subject: [PATCH 08/31] =?UTF-8?q?=E2=9C=A8=20D=E3=82=92=C3=90=E3=81=AB?= =?UTF-8?q?=E5=A4=89=E6=8F=9B=E3=81=99=E3=82=8B=E5=87=A6=E7=90=86=E3=82=92?= =?UTF-8?q?=E8=BF=BD=E5=8A=A0=20#47?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- cica.py | 36 ++++++++++++++++++++++++------------ 1 file changed, 24 insertions(+), 12 deletions(-) diff --git a/cica.py b/cica.py index 3a30782a..519210d6 100644 --- a/cica.py +++ b/cica.py @@ -19,7 +19,6 @@ VERSION = '5.0.1' FAMILY = 'Cica' - def log(_str): """ログ出力 fontforgeにquietオプションが無いので悲しい @@ -27,9 +26,20 @@ def log(_str): now = datetime.now().strftime('%Y-%m-%d %H:%M:%S') print(now + " " + _str) +ignoring_center = [i for i in range(0x20, 0x6ff)] +ignoring_center.extend([ + 0x3001, 0x3002, 0x3008, 0x3009, 0x300a, 0x300b, 0x300c, 0x300d, + 0x300e, 0x300f, 0x3010, 0x3011, 0x3014, 0x3015, 0x3016, 0x3017, + 0x3018, 0x3019, 0x301a, 0x301b, 0x301d, 0x301e, 0x3099, 0x309a, + 0x309b, 0x309c, +]) + def align_to_center(_g): """グリフを中央寄せにする """ + if _g.encoding in ignoring_center: + return _g + width = 0 if _g.width > 700: @@ -393,7 +403,6 @@ def vertical_line_to_broken_bar(self): self.font_jp.copy() self.font_jp.selection.select(0x007c) self.font_jp.paste() - return self.font_jp def emdash_to_broken_dash(self): """ダッシュ記号を破線にする @@ -769,6 +778,15 @@ def modify_ellipsis(self): rotcen = psMat.compose(trcen, psMat.compose(psMat.rotate(math.radians(-45)), psMat.inverse(trcen))) g.transform(rotcen) + def stroked_d(self): + """DをĐにする + """ + self.font_jp.selection.select(0x110) + self.font_jp.copy() + self.font_jp.selection.select(0x44) + self.font_jp.paste() + + def build_font(self, emoji): log('remove_glyph_from_en()') @@ -778,14 +796,9 @@ def build_font(self, emoji): for g in self.font_en.glyphs(): g.transform((0.42,0,0,0.42,0,0)) g = align_to_center(g) + self.modify_m(self.weight_name) - ignoring_center = [ - 0x3001, 0x3002, 0x3008, 0x3009, 0x300a, 0x300b, 0x300c, 0x300d, - 0x300e, 0x300f, 0x3010, 0x3011, 0x3014, 0x3015, 0x3016, 0x3017, - 0x3018, 0x3019, 0x301a, 0x301b, 0x301d, 0x301e, 0x3099, 0x309a, - 0x309b, 0x309c, - ] log('transform font_jp') for g in self.font_jp.glyphs(): g.transform((0.91,0,0,0.91,0,0)) @@ -801,10 +814,7 @@ def build_font(self, emoji): width = 512 g.transform(psMat.translate((width - g.width)/2, 0)) g.width = width - if g.encoding in ignoring_center: - pass - else: - g = align_to_center(g) + g = align_to_center(g) log('modify border glyphs') for g in self.font_en.glyphs(): @@ -855,6 +865,7 @@ def build_font(self, emoji): self.zenkaku_space() self.dotted_zero() self.slashed_zero() + self.stroked_d() self.modify_WM() self.vertical_line_to_broken_bar() self.emdash_to_broken_dash() @@ -955,6 +966,7 @@ def build_font(self, emoji): } ] + def main(): for _f in fonts: cica = Cica(_f["family"], From f393bda8bf2927be3b8a50fb318981074e12e3b9 Mon Sep 17 00:00:00 2001 From: miiton <468745+miiton@users.noreply.github.com> Date: Sun, 30 Jun 2019 16:27:29 +0900 Subject: [PATCH 09/31] =?UTF-8?q?=F0=9F=90=9E=20=E5=B9=85=E3=81=8C512?= =?UTF-8?q?=E3=81=A7=E3=81=AF=E3=81=AA=E3=81=8F=E3=81=AA=E3=81=A3=E3=81=A6?= =?UTF-8?q?=E3=81=84=E3=81=9F=E3=81=AE=E3=82=92=E4=BF=AE=E6=AD=A3?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- cica.py | 42 ++++++++++++++++++++++-------------------- 1 file changed, 22 insertions(+), 20 deletions(-) diff --git a/cica.py b/cica.py index 519210d6..4e279dbc 100644 --- a/cica.py +++ b/cica.py @@ -37,9 +37,6 @@ def log(_str): def align_to_center(_g): """グリフを中央寄せにする """ - if _g.encoding in ignoring_center: - return _g - width = 0 if _g.width > 700: @@ -48,10 +45,13 @@ def align_to_center(_g): width = 512 _g.width = width + if _g.encoding in ignoring_center: + return + _g.left_side_bearing = _g.right_side_bearing = (_g.left_side_bearing + _g.right_side_bearing)/2 _g.width = width - return _g + return def align_to_left(_g): """グリフを左寄せにする @@ -168,9 +168,9 @@ def modify_nerd(_g): _g.width = 1024 if _g.encoding == 0xe0cf: _g.transform(psMat.scale(0.9, 1.0)) - _g = align_to_center(_g) + align_to_center(_g) if _g.encoding == 0xe0d0: - _g = align_to_center(_g) + align_to_center(_g) if _g.encoding == 0xe0d1: _g.transform(psMat.compose(psMat.scale(1.0, 0.982), psMat.translate(0, -1))) _g.left_side_bearing = 0 @@ -188,11 +188,11 @@ def modify_nerd(_g): elif _g.encoding >= 0xf000 and _g.encoding <= 0xf2e0: _g.transform(psMat.compose(psMat.scale(0.75, 0.75), psMat.translate(0, 55))) _g.width = 1024 - _g = align_to_center(_g) + align_to_center(_g) else: _g.transform(psMat.translate(0, -55)) _g.width = 1024 - _g = align_to_center(_g) + align_to_center(_g) return _g @@ -201,7 +201,7 @@ def modify_iconsfordevs(_g): """ _g.transform(psMat.compose(psMat.scale(2), psMat.translate(0, -126))) _g.width = 1024 - _g = align_to_center(_g) + align_to_center(_g) return _g @@ -426,7 +426,7 @@ def zenkaku_space(self): self.font_jp.pasteInto() self.font_jp.intersect() for g in self.font_jp.selection.byGlyphs: - g = align_to_center(g) + align_to_center(g) def dotted_zero(self): """半角数字の0をドットゼロにする @@ -440,7 +440,7 @@ def dotted_zero(self): self.font_jp.selection.select(0x30) self.font_jp.pasteInto() for g in self.font_jp.selection.byGlyphs: - g = align_to_center(g) + align_to_center(g) def slashed_zero(self): """半角数字の0をスラッシュゼロにする @@ -453,7 +453,7 @@ def slashed_zero(self): self.font_jp.copy() self.font_jp.selection.select(0x1) self.font_jp.paste() - self.font_jp.transform(psMat.compose(psMat.scale(0.7, 0.75), psMat.translate(70, 115))) + self.font_jp.transform(psMat.compose(psMat.scale(0.7, 0.75), psMat.translate(80, 115))) self.font_jp.copy() self.font_jp.selection.select(0x30) self.font_jp.pasteInto() @@ -463,13 +463,15 @@ def modify_WM(self): """WとMの字体を調整 """ self.font_jp.selection.select(0x57) - self.font_jp.transform(psMat.scale(0.95, 1.0)) + self.font_jp.transform(psMat.compose(psMat.scale(0.95, 1.0), psMat.translate(10, 0))) + for g in self.font_jp.selection.byGlyphs: + align_to_center(g) self.font_jp.copy() self.font_jp.selection.select(0x4d) self.font_jp.paste() - self.font_jp.transform(psMat.compose(psMat.rotate(math.radians(180)), psMat.translate(0, 627))) + self.font_jp.transform(psMat.compose(psMat.rotate(math.radians(180)), psMat.translate(512, 627))) for g in self.font_jp.selection.byGlyphs: - g = align_to_center(g) + align_to_center(g) def modify_m(self, _weight): """mの中央の棒を少し短くする @@ -508,7 +510,7 @@ def add_smalltriangle(self): for g in self.font_jp.glyphs(): if g.encoding == 0x25be or g.encoding == 0x25b8: g.width = 512 - g = align_to_center(g) + align_to_center(g) def fix_box_drawings(self): """罫線を調整 @@ -569,7 +571,7 @@ def add_notoemoji(self): for g in notoemoji.glyphs(): if g.isWorthOutputting and g.encoding > 0x04f9: g.transform((0.42,0,0,0.42,0,0)) - g = align_to_center(g) + align_to_center(g) notoemoji.selection.select(g.encoding) notoemoji.copy() self.font_jp.selection.select(g.encoding) @@ -795,7 +797,7 @@ def build_font(self, emoji): log('transform font_en') for g in self.font_en.glyphs(): g.transform((0.42,0,0,0.42,0,0)) - g = align_to_center(g) + align_to_center(g) self.modify_m(self.weight_name) @@ -814,7 +816,7 @@ def build_font(self, emoji): width = 512 g.transform(psMat.translate((width - g.width)/2, 0)) g.width = width - g = align_to_center(g) + align_to_center(g) log('modify border glyphs') for g in self.font_en.glyphs(): @@ -829,7 +831,7 @@ def build_font(self, emoji): self.font_jp.paste() if g.encoding >= 0x2500 and g.encoding <= 0x25af: g.transform(psMat.compose(psMat.scale(1.024, 1.024), psMat.translate(0, -30))) - g = align_to_center(g) + align_to_center(g) self.font_en.selection.select(g.encoding) self.font_en.copy() self.font_jp.selection.select(g.encoding) From e3b70b620044274fd1be510e3c99da94927809cf Mon Sep 17 00:00:00 2001 From: miiton <468745+miiton@users.noreply.github.com> Date: Sun, 30 Jun 2019 20:41:42 +0900 Subject: [PATCH 10/31] =?UTF-8?q?=F0=9F=90=9E=20=E8=BE=9E=E6=9B=B8?= =?UTF-8?q?=E5=9E=8B=E3=81=AE=E7=94=9F=E6=88=90=E3=81=AErange=E6=8C=87?= =?UTF-8?q?=E5=AE=9A=E8=AA=A4=E3=82=8A=E3=82=92=E4=BF=AE=E6=AD=A3?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- width_parser.py | 10 +++++++--- 1 file changed, 7 insertions(+), 3 deletions(-) diff --git a/width_parser.py b/width_parser.py index 32905d89..310664c2 100644 --- a/width_parser.py +++ b/width_parser.py @@ -38,7 +38,7 @@ def parse_line(self, line): start = int(u[0], 16) if len(u) == 2: finish = int(u[1], 16) - for i in range(start, finish): + for i in range(start, finish + 1): self.dictionary[i] = width else: self.dictionary[start] = width @@ -61,10 +61,14 @@ def execute(self): data.close() def width(self, uni): - return self.dictionary[uni] + try: + return self.dictionary[uni] + except: + pass + if __name__ == '__main__': wp = WidthParser() - print(wp.width(0x3000)) + print(wp.width(0x25a1)) From 797b3bf005ab5a3b479c47042892b87b639b9074 Mon Sep 17 00:00:00 2001 From: miiton <468745+miiton@users.noreply.github.com> Date: Tue, 2 Jul 2019 19:42:12 +0900 Subject: [PATCH 11/31] =?UTF-8?q?=F0=9F=91=8D=20ambiwidth=E5=AF=BE?= =?UTF-8?q?=E5=BF=9C?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- cica.py | 72 ++++++++++++++++++++++++++++++++++++------------- width_parser.py | 2 +- 2 files changed, 54 insertions(+), 20 deletions(-) diff --git a/cica.py b/cica.py index 4e279dbc..ee9f1969 100644 --- a/cica.py +++ b/cica.py @@ -17,7 +17,10 @@ LICENSE = open('./LICENSE.txt').read() COPYRIGHT = open('./COPYRIGHT.txt').read() VERSION = '5.0.1' -FAMILY = 'Cica' +FAMILY = 'CicaTest' +AMBI = 0 +SINGLE = 1 +DOUBLE = 2 def log(_str): """ログ出力 @@ -218,17 +221,7 @@ def __init__(self, family, name, output_name, weight, weight_name, style_name, f self.italic = italic self.nerd = fontforge.open('./source/nerd.sfd') self.icons_for_devs = fontforge.open('./source/iconsfordevs.ttf') - - def remove_glyph_from_en(self): - """jpフォント側を採用したいグリフをenフォントから削除 - """ - glyphs = [ - 0x2026, # … - ] - - for g in glyphs: - self.font_en.selection.select(g) - self.font_en.clear() + self.wp = width_parser.WidthParser() def set_os2_values(self): """フォントメタ情報の設定 @@ -276,6 +269,8 @@ def add_dejavu(self): dejavu = fontforge.open('./source/DejaVuSansMono-Bold.ttf') for g in dejavu.glyphs(): + if self.wp.width(g.encoding) == AMBI: + continue g.transform(psMat.compose(psMat.scale(0.45, 0.45), psMat.translate(-21, 0))) g.width = 512 @@ -283,6 +278,8 @@ def add_dejavu(self): # 0x0300 - 0x036f - Combining Diacritical Marks for g in dejavu.glyphs(): + if self.wp.width(g.encoding) == AMBI: + continue if g.encoding < 0x0300 or g.encoding > 0x036f or g.encoding == 0x0398: continue else: @@ -332,6 +329,8 @@ def add_dejavu(self): self.font_jp.paste() # 0x0370 - 0x03ff - GREEK for g in dejavu.glyphs(): + if self.wp.width(g.encoding) == AMBI: + continue if g.encoding < 0x0370 or g.encoding > 0x03ff or g.encoding == 0x0398: continue else: @@ -344,6 +343,8 @@ def add_dejavu(self): self.font_jp.paste() # 0x2100 - 0x214f Letterlike Symbols for g in dejavu.glyphs(): + if self.wp.width(g.encoding) == AMBI: + continue if g.encoding < 0x2100 or g.encoding > 0x214f or g.encoding == 0x2122: continue else: @@ -354,6 +355,8 @@ def add_dejavu(self): self.font_jp.paste() # 0x2150 - 0x218f Number Forms for g in dejavu.glyphs(): + if self.wp.width(g.encoding) == AMBI: + continue if g.encoding < 0x2150 or g.encoding > 0x218f: continue else: @@ -363,8 +366,9 @@ def add_dejavu(self): self.font_jp.selection.select(g.encoding) self.font_jp.paste() # 0x2190 - 0x21ff Arrows - # TODO: 矢印を全角のままにしたパターンも生成したい for g in dejavu.glyphs(): + if self.wp.width(g.encoding) == AMBI: + continue if g.encoding < 0x2190 or g.encoding > 0x21ff: continue else: @@ -375,6 +379,8 @@ def add_dejavu(self): self.font_jp.paste() # 0x2200 - 0x22ff Mathematical Operators for g in dejavu.glyphs(): + if self.wp.width(g.encoding) == AMBI: + continue if g.encoding < 0x2200 or g.encoding > 0x22ff: continue else: @@ -385,6 +391,8 @@ def add_dejavu(self): self.font_jp.paste() # 0x2300 - 0x23ff Miscellaneous Technical for g in dejavu.glyphs(): + if self.wp.width(g.encoding) == AMBI: + continue if g.encoding < 0x2300 or g.encoding > 0x23ff: continue else: @@ -567,6 +575,8 @@ def import_svg(self): g.transform(psMat.translate(0, -61)) def add_notoemoji(self): + """Noto Emojiを足す + """ notoemoji = fontforge.open('./source/NotoEmoji-Regular.ttf') for g in notoemoji.glyphs(): if g.isWorthOutputting and g.encoding > 0x04f9: @@ -789,10 +799,7 @@ def stroked_d(self): self.font_jp.paste() - def build_font(self, emoji): - - log('remove_glyph_from_en()') - self.remove_glyph_from_en() + def build(self, emoji): log('transform font_en') for g in self.font_en.glyphs(): @@ -818,9 +825,36 @@ def build_font(self, emoji): g.width = width align_to_center(g) + # TODO: 0x2715 -> 0xd7 : 乗算記号 + self.font_jp.selection.select(0x2715) + self.font_jp.copy() + self.font_jp.selection.select(0xd7) + self.font_jp.paste() + # TODO: 0xff1a + 0xff0d -> 0xf7 : 除算記号 + self.font_jp.selection.select(0xff1a) + self.font_jp.copy() + self.font_jp.selection.select(0xf7) + self.font_jp.paste() + self.font_jp.selection.select(0xff0d) + self.font_jp.copy() + self.font_jp.selection.select(0xf7) + self.font_jp.pasteInto() + # TODO: 0xff0b + 0xff3f -> 0xb1 : プラスマイナス記号 + self.font_jp.selection.select(0xff0b) + self.font_jp.copy() + self.font_jp.selection.select(0xb1) + self.font_jp.paste() + self.font_jp.selection.select(0xff3f) + self.font_jp.copy() + self.font_jp.selection.select(0xb1) + self.font_jp.pasteInto() + + log('modify border glyphs') for g in self.font_en.glyphs(): - if g.isWorthOutputting: + if self.wp.width(g.encoding) == AMBI: + continue + if g.isWorthOutputting: if self.italic: g.transform(psMat.skew(0.25)) if g.encoding >= 0x2500 and g.encoding <= 0x257f: @@ -981,7 +1015,7 @@ def main(): _f["mgen_plus"], _f["italic"] ) - cica.build_font(True) + cica.build(True) if __name__ == '__main__': main() diff --git a/width_parser.py b/width_parser.py index 310664c2..54922d76 100644 --- a/width_parser.py +++ b/width_parser.py @@ -71,4 +71,4 @@ def width(self, uni): if __name__ == '__main__': wp = WidthParser() - print(wp.width(0x25a1)) + print(wp.width(0xb1)) From 6a59eef7c76ec1af774f4e0e83a6e15255dfb127 Mon Sep 17 00:00:00 2001 From: miiton <468745+miiton@users.noreply.github.com> Date: Tue, 2 Jul 2019 21:46:52 +0900 Subject: [PATCH 12/31] =?UTF-8?q?=E2=9C=A8=20=E6=94=BE=E5=B0=84=E7=8A=B6?= =?UTF-8?q?=E3=82=A2=E3=82=B9=E3=82=BF=E3=83=AA=E3=82=B9=E3=82=AF=20close?= =?UTF-8?q?=20#49?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- cica.py | 13 ++++++++++++- 1 file changed, 12 insertions(+), 1 deletion(-) diff --git a/cica.py b/cica.py index ee9f1969..babcc8f5 100644 --- a/cica.py +++ b/cica.py @@ -466,6 +466,8 @@ def slashed_zero(self): self.font_jp.selection.select(0x30) self.font_jp.pasteInto() self.font_jp.removeOverlap() + self.font_jp.selection.select(0x1) + self.font_jp.clear() def modify_WM(self): """WとMの字体を調整 @@ -791,13 +793,21 @@ def modify_ellipsis(self): g.transform(rotcen) def stroked_d(self): - """DをĐにする + """Dを横線入りのĐにする """ self.font_jp.selection.select(0x110) self.font_jp.copy() self.font_jp.selection.select(0x44) self.font_jp.paste() + def asterisk(self, up = 200): + """アスタリスクを放射状にする + """ + self.font_jp.selection.select(0xffbc2) + self.font_jp.copy() + self.font_jp.selection.select(0x2a) + self.font_jp.paste() + self.font_jp.transform(psMat.compose(psMat.scale(0.5, 0.5), psMat.translate(0, up))) def build(self, emoji): @@ -908,6 +918,7 @@ def build(self, emoji): self.reiwa(self.weight_name) self.add_gopher() self.modify_ellipsis() + self.asterisk(300) # 200 or 300 ## if emoji: self.add_notoemoji() self.add_smalltriangle() From a9640c485f1d26c58ff237fcef9f84061decf3b4 Mon Sep 17 00:00:00 2001 From: miiton <468745+miiton@users.noreply.github.com> Date: Tue, 2 Jul 2019 21:51:56 +0900 Subject: [PATCH 13/31] =?UTF-8?q?=F0=9F=92=9A=20modified=20circle=20ci?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- Dockerfile | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/Dockerfile b/Dockerfile index 52e66c51..188ab366 100644 --- a/Dockerfile +++ b/Dockerfile @@ -12,19 +12,19 @@ RUN apt-get update && \ software-properties-common fontforge unar git curl && \ mkdir /work WORKDIR /work -COPY sourceFonts sourceFonts +COPY source source RUN curl -L https://github.com/source-foundry/Hack/releases/download/$HACK_VERSION/Hack-$HACK_VERSION-ttf.zip -o /tmp/hack.zip && \ - unar /tmp/hack.zip -o /tmp/hack && cp /tmp/hack/ttf/* sourceFonts/ && \ + unar /tmp/hack.zip -o /tmp/hack && cp /tmp/hack/ttf/* source/ && \ curl -L https://osdn.jp/downloads/users/8/8598/rounded-mgenplus-$MGENPLUS_VERSION.7z -o /tmp/rounded-mgenplus.7z && \ unar /tmp/rounded-mgenplus.7z -o /tmp && \ - cp /tmp/rounded-mgenplus/rounded-mgenplus-1m-regular.ttf sourceFonts/ && \ - cp /tmp/rounded-mgenplus/rounded-mgenplus-1m-bold.ttf sourceFonts/ && \ - curl -L https://github.com/googlei18n/noto-emoji/raw/$NOTO_EMOJI_VERSION/fonts/NotoEmoji-Regular.ttf -o sourceFonts/NotoEmoji-Regular.ttf && \ + cp /tmp/rounded-mgenplus/rounded-mgenplus-1m-regular.ttf source/ && \ + cp /tmp/rounded-mgenplus/rounded-mgenplus-1m-bold.ttf source/ && \ + curl -L https://github.com/googlei18n/noto-emoji/raw/$NOTO_EMOJI_VERSION/fonts/NotoEmoji-Regular.ttf -o source/NotoEmoji-Regular.ttf && \ curl -L http://sourceforge.net/projects/dejavu/files/dejavu/$DEJAVU_VERSION/dejavu-fonts-ttf-$DEJAVU_VERSION.zip -o /tmp/dejavu.zip && \ unar /tmp/dejavu.zip -o /tmp && \ - cp /tmp/dejavu-fonts-ttf-$DEJAVU_VERSION/ttf/DejaVuSansMono.ttf sourceFonts/ && \ - cp /tmp/dejavu-fonts-ttf-$DEJAVU_VERSION/ttf/DejaVuSansMono-Bold.ttf sourceFonts/ && \ - curl -L https://github.com/mirmat/iconsfordevs/raw/$ICONSFORDEVS_VERSION/fonts/iconsfordevs.ttf -o sourceFonts/iconsfordevs.ttf + cp /tmp/dejavu-fonts-ttf-$DEJAVU_VERSION/ttf/DejaVuSansMono.ttf source/ && \ + cp /tmp/dejavu-fonts-ttf-$DEJAVU_VERSION/ttf/DejaVuSansMono-Bold.ttf source/ && \ + curl -L https://github.com/mirmat/iconsfordevs/raw/$ICONSFORDEVS_VERSION/fonts/iconsfordevs.ttf -o source/iconsfordevs.ttf COPY cica.py cica.py COPY LICENSE.txt LICENSE.txt From d17518c3fc2d3287bc39e183ff212ef7f297f1df Mon Sep 17 00:00:00 2001 From: miiton <468745+miiton@users.noreply.github.com> Date: Tue, 2 Jul 2019 21:56:27 +0900 Subject: [PATCH 14/31] =?UTF-8?q?=F0=9F=92=9A=20modified=20circleci?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- Dockerfile | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/Dockerfile b/Dockerfile index 188ab366..7aa24074 100644 --- a/Dockerfile +++ b/Dockerfile @@ -24,9 +24,11 @@ RUN curl -L https://github.com/source-foundry/Hack/releases/download/$HACK_VERSI unar /tmp/dejavu.zip -o /tmp && \ cp /tmp/dejavu-fonts-ttf-$DEJAVU_VERSION/ttf/DejaVuSansMono.ttf source/ && \ cp /tmp/dejavu-fonts-ttf-$DEJAVU_VERSION/ttf/DejaVuSansMono-Bold.ttf source/ && \ - curl -L https://github.com/mirmat/iconsfordevs/raw/$ICONSFORDEVS_VERSION/fonts/iconsfordevs.ttf -o source/iconsfordevs.ttf + curl -L https://github.com/mirmat/iconsfordevs/raw/$ICONSFORDEVS_VERSION/fonts/iconsfordevs.ttf -o source/iconsfordevs.ttf && \ + curl -L http://www.unicode.org/Public/12.0.0/ucd/EastAsianWidth.txt -o source/EastAsianWidth.txt COPY cica.py cica.py +COPY width_parser.py width_parser.py COPY LICENSE.txt LICENSE.txt COPY COPYRIGHT.txt COPYRIGHT.txt From 4cbec2ee7596be6ab065935e795cbb151b3cc2af Mon Sep 17 00:00:00 2001 From: miiton <468745+miiton@users.noreply.github.com> Date: Tue, 2 Jul 2019 22:26:00 +0900 Subject: [PATCH 15/31] =?UTF-8?q?=F0=9F=91=8D=20=E3=82=A2=E3=82=B9?= =?UTF-8?q?=E3=82=BF=E3=83=AA=E3=82=B9=E3=82=AF=E3=81=AEBold=E5=AF=BE?= =?UTF-8?q?=E5=BF=9C?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- cica.py | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-) diff --git a/cica.py b/cica.py index babcc8f5..d56d5e9d 100644 --- a/cica.py +++ b/cica.py @@ -808,9 +808,11 @@ def asterisk(self, up = 200): self.font_jp.selection.select(0x2a) self.font_jp.paste() self.font_jp.transform(psMat.compose(psMat.scale(0.5, 0.5), psMat.translate(0, up))) + if self.weight_name == 'Bold': + self.font_jp.stroke("circular", 20, 'butt', 'round', 'removeinternal') - def build(self, emoji): + def build(self, emoji): log('transform font_en') for g in self.font_en.glyphs(): g.transform((0.42,0,0,0.42,0,0)) @@ -835,12 +837,12 @@ def build(self, emoji): g.width = width align_to_center(g) - # TODO: 0x2715 -> 0xd7 : 乗算記号 + # 0x2715 -> 0xd7 : 乗算記号 self.font_jp.selection.select(0x2715) self.font_jp.copy() self.font_jp.selection.select(0xd7) self.font_jp.paste() - # TODO: 0xff1a + 0xff0d -> 0xf7 : 除算記号 + # 0xff1a + 0xff0d -> 0xf7 : 除算記号 self.font_jp.selection.select(0xff1a) self.font_jp.copy() self.font_jp.selection.select(0xf7) @@ -849,7 +851,7 @@ def build(self, emoji): self.font_jp.copy() self.font_jp.selection.select(0xf7) self.font_jp.pasteInto() - # TODO: 0xff0b + 0xff3f -> 0xb1 : プラスマイナス記号 + # 0xff0b + 0xff3f -> 0xb1 : プラスマイナス記号 self.font_jp.selection.select(0xff0b) self.font_jp.copy() self.font_jp.selection.select(0xb1) From 6c929057ef52785ab8bab616931de7fefbaed153 Mon Sep 17 00:00:00 2001 From: miiton <468745+miiton@users.noreply.github.com> Date: Thu, 4 Jul 2019 22:16:26 +0900 Subject: [PATCH 16/31] =?UTF-8?q?=F0=9F=91=8D=20argparser=E8=BF=BD?= =?UTF-8?q?=E5=8A=A0?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- cica.py | 12 ++++++++++++ 1 file changed, 12 insertions(+) diff --git a/cica.py b/cica.py index d56d5e9d..da37a236 100644 --- a/cica.py +++ b/cica.py @@ -8,6 +8,7 @@ import glob import width_parser from datetime import datetime +import argparse # ASCENT = 850 # DESCENT = 174 @@ -208,6 +209,17 @@ def modify_iconsfordevs(_g): return _g +parser = argparse.ArgumentParser() +parser.add_argument("-s", "--space", type=int, help="全角スペースに枠をつける (0) かつけない (1) か選べます") +parser.add_argument("-z", "--zero", type=int, help="ゼロを dotted(0)、slashed(1)、Hack(2)、blanked(3) から選べます") +parser.add_argument("-a", "--asterisk", type=int, help="アスタリスクのタイプを radial(0) か star(1) か選べます") +parser.add_argument("-d", "--stroked-d", type=int, help="Dを stroked(0) か normal(1) か選べます") +parser.add_argument("-v", "--vertical-line", type=int, help="縦線を broken(0) か solid(1) か選べます") +parser.add_argument("-w", "--ambiguous-width", type=int, help="曖昧幅文字幅を single(0) か wide(1) か選べます") +parser.add_argument("-e", "--ellipsis", type=int, help="三点リーダー類を single(0) か wide(1) か選べます") +parser.add_argument("-i", "--emoji", type=int, help="絵文字類を noto emoji(0) か system(1) か選べます") +args = parser.parse_args() + class Cica: def __init__(self, family, name, output_name, weight, weight_name, style_name, font_en, font_jp, italic): self.family = family From e1f9d3d68ee95af4c35f9f293d7f6f6cf1f96d10 Mon Sep 17 00:00:00 2001 From: miiton <468745+miiton@users.noreply.github.com> Date: Thu, 4 Jul 2019 22:22:24 +0900 Subject: [PATCH 17/31] =?UTF-8?q?=F0=9F=91=8D=20=E5=85=A8=E8=A7=92?= =?UTF-8?q?=E3=82=B9=E3=83=9A=E3=83=BC=E3=82=B9=E3=81=AE=E6=9E=A0=E9=81=B8?= =?UTF-8?q?=E6=8A=9E=E3=82=92=E5=AE=9F=E8=A3=85?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- cica.py | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/cica.py b/cica.py index da37a236..c39d5317 100644 --- a/cica.py +++ b/cica.py @@ -922,7 +922,9 @@ def build(self, emoji): self.font_jp.paste() self.fix_box_drawings() - self.zenkaku_space() + if args.space == 0: + self.zenkaku_space() + self.dotted_zero() self.slashed_zero() self.stroked_d() From e2a92747d4e459a99e1e37594df7deceed610b51 Mon Sep 17 00:00:00 2001 From: miiton <468745+miiton@users.noreply.github.com> Date: Thu, 4 Jul 2019 22:24:07 +0900 Subject: [PATCH 18/31] =?UTF-8?q?=F0=9F=91=8D=200=E3=81=AE=E9=81=B8?= =?UTF-8?q?=E6=8A=9E=E3=82=92=E5=AE=9F=E8=A3=85?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- cica.py | 9 +++++++-- 1 file changed, 7 insertions(+), 2 deletions(-) diff --git a/cica.py b/cica.py index c39d5317..6cd53b1b 100644 --- a/cica.py +++ b/cica.py @@ -925,8 +925,13 @@ def build(self, emoji): if args.space == 0: self.zenkaku_space() - self.dotted_zero() - self.slashed_zero() + if args.zero == 0: + self.dotted_zero() + elif args.zero == 1: + self.slashed_zero() + elif args.zero == 2: + pass + self.stroked_d() self.modify_WM() self.vertical_line_to_broken_bar() From f7f0e7b4cfde742c233aabe5d39dd89f8f9e1575 Mon Sep 17 00:00:00 2001 From: miiton <468745+miiton@users.noreply.github.com> Date: Thu, 4 Jul 2019 22:25:02 +0900 Subject: [PATCH 19/31] =?UTF-8?q?=F0=9F=91=8D=20stroked=5Fd=20=E3=81=AE?= =?UTF-8?q?=E9=81=B8=E6=8A=9E=E3=82=92=E5=AE=9F=E8=A3=85?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- cica.py | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/cica.py b/cica.py index 6cd53b1b..2c7a3f41 100644 --- a/cica.py +++ b/cica.py @@ -932,7 +932,9 @@ def build(self, emoji): elif args.zero == 2: pass - self.stroked_d() + if args.stroked_d == 0: + self.stroked_d() + self.modify_WM() self.vertical_line_to_broken_bar() self.emdash_to_broken_dash() From 289b110676b998c2bfb9ed4c0651915ec14d5560 Mon Sep 17 00:00:00 2001 From: miiton <468745+miiton@users.noreply.github.com> Date: Thu, 4 Jul 2019 22:32:50 +0900 Subject: [PATCH 20/31] =?UTF-8?q?=F0=9F=91=8D=20=E7=B8=A6=E7=B7=9A?= =?UTF-8?q?=E3=81=AE=E9=81=B8=E6=8A=9E=E3=82=92=E5=AE=9F=E8=A3=85?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- cica.py | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/cica.py b/cica.py index 2c7a3f41..4fce934c 100644 --- a/cica.py +++ b/cica.py @@ -936,7 +936,12 @@ def build(self, emoji): self.stroked_d() self.modify_WM() - self.vertical_line_to_broken_bar() + + if args.vertical_line == 0: + self.vertical_line_to_broken_bar() + elif args.vertical_line == 1: + pass + self.emdash_to_broken_dash() self.reiwa(self.weight_name) self.add_gopher() From 3892a12036d7f33f171f636960fc2a7ce3278b41 Mon Sep 17 00:00:00 2001 From: miiton <468745+miiton@users.noreply.github.com> Date: Thu, 4 Jul 2019 22:33:53 +0900 Subject: [PATCH 21/31] =?UTF-8?q?=F0=9F=91=8D=20=E4=B8=89=E7=82=B9?= =?UTF-8?q?=E3=83=AA=E3=83=BC=E3=83=80=E3=83=BC=E3=81=AE=E9=81=B8=E6=8A=9E?= =?UTF-8?q?=E3=82=92=E5=AE=9F=E8=A3=85?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- cica.py | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/cica.py b/cica.py index 4fce934c..139f485a 100644 --- a/cica.py +++ b/cica.py @@ -945,7 +945,11 @@ def build(self, emoji): self.emdash_to_broken_dash() self.reiwa(self.weight_name) self.add_gopher() - self.modify_ellipsis() + if args.ellipsis == 0: + self.modify_ellipsis() + elif args.ellipsis == 1: + pass + self.asterisk(300) # 200 or 300 ## if emoji: self.add_notoemoji() From 256b3bf564250ca1204f32750774e2a2197b9e47 Mon Sep 17 00:00:00 2001 From: miiton <468745+miiton@users.noreply.github.com> Date: Thu, 4 Jul 2019 22:34:22 +0900 Subject: [PATCH 22/31] =?UTF-8?q?=F0=9F=91=8D=20=E3=82=A2=E3=82=B9?= =?UTF-8?q?=E3=82=BF=E3=83=AA=E3=82=B9=E3=82=AF=E3=81=AE=E9=81=B8=E6=8A=9E?= =?UTF-8?q?=E3=82=92=E5=AE=9F=E8=A3=85?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- cica.py | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/cica.py b/cica.py index 139f485a..4ba254cb 100644 --- a/cica.py +++ b/cica.py @@ -950,7 +950,11 @@ def build(self, emoji): elif args.ellipsis == 1: pass - self.asterisk(300) # 200 or 300 ## + if args.asterisk == 0: + self.asterisk(200) # 200 or 300 ## + elif args.asterisk == 1: + pass + if emoji: self.add_notoemoji() self.add_smalltriangle() From 356c1bfe38a7d4ad6a854ed43736fd32adc1490b Mon Sep 17 00:00:00 2001 From: miiton <468745+miiton@users.noreply.github.com> Date: Thu, 4 Jul 2019 22:36:22 +0900 Subject: [PATCH 23/31] =?UTF-8?q?=F0=9F=91=8D=20=E7=B5=B5=E6=96=87?= =?UTF-8?q?=E5=AD=97=E3=81=AE=E9=81=B8=E6=8A=9E=E3=82=92=E5=AE=9F=E8=A3=85?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- cica.py | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/cica.py b/cica.py index 4ba254cb..1ec5fb4e 100644 --- a/cica.py +++ b/cica.py @@ -955,8 +955,11 @@ def build(self, emoji): elif args.asterisk == 1: pass - if emoji: + if args.emoji == 0: self.add_notoemoji() + elif args.emoji == 1: + pass + self.add_smalltriangle() self.add_dejavu() self.resize_supersub() From e2b669a5feeee6e351dc24c47aea3b14cb881666 Mon Sep 17 00:00:00 2001 From: Kyoichiro Yamada Date: Wed, 21 Aug 2019 23:57:32 +0900 Subject: [PATCH 24/31] =?UTF-8?q?=E3=83=93=E3=83=AB=E3=83=89=E6=99=82?= =?UTF-8?q?=E3=81=AE=E3=83=90=E3=83=AA=E3=82=A8=E3=83=BC=E3=82=B7=E3=83=A7?= =?UTF-8?q?=E3=83=B3=E3=82=92=E7=92=B0=E5=A2=83=E5=A4=89=E6=95=B0=E3=81=A7?= =?UTF-8?q?=E6=8C=87=E5=AE=9A=E3=81=A7=E3=81=8D=E3=82=8B=E3=82=88=E3=81=86?= =?UTF-8?q?=E3=81=AB?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- cica.py | 66 ++++++++++++++++++++++++++++++++++++++++++++++++++------- 1 file changed, 58 insertions(+), 8 deletions(-) diff --git a/cica.py b/cica.py index 1ec5fb4e..c8487411 100644 --- a/cica.py +++ b/cica.py @@ -210,16 +210,66 @@ def modify_iconsfordevs(_g): parser = argparse.ArgumentParser() -parser.add_argument("-s", "--space", type=int, help="全角スペースに枠をつける (0) かつけない (1) か選べます") -parser.add_argument("-z", "--zero", type=int, help="ゼロを dotted(0)、slashed(1)、Hack(2)、blanked(3) から選べます") -parser.add_argument("-a", "--asterisk", type=int, help="アスタリスクのタイプを radial(0) か star(1) か選べます") -parser.add_argument("-d", "--stroked-d", type=int, help="Dを stroked(0) か normal(1) か選べます") -parser.add_argument("-v", "--vertical-line", type=int, help="縦線を broken(0) か solid(1) か選べます") -parser.add_argument("-w", "--ambiguous-width", type=int, help="曖昧幅文字幅を single(0) か wide(1) か選べます") -parser.add_argument("-e", "--ellipsis", type=int, help="三点リーダー類を single(0) か wide(1) か選べます") -parser.add_argument("-i", "--emoji", type=int, help="絵文字類を noto emoji(0) か system(1) か選べます") +parser.add_argument( + "-s", + "--space", + type=int, + default=int(os.environ.get("CICA_SPACE", "0")), + help="全角スペースに枠をつける (0) かつけない (1) か選べます", +) +parser.add_argument( + "-z", + "--zero", + type=int, + default=int(os.environ.get("CICA_ZERO", "0")), + help="ゼロを dotted(0)、slashed(1)、Hack(2)、blanked(3) から選べます", +) +parser.add_argument( + "-a", + "--asterisk", + type=int, + default=int(os.environ.get("CICA_ASTERISK", "0")), + help="アスタリスクのタイプを radial(0) か star(1) か選べます", +) +parser.add_argument( + "-d", + "--stroked-d", + type=int, + default=int(os.environ.get("CICA_STROKED_D", "0")), + help="Dを stroked(0) か normal(1) か選べます", +) +parser.add_argument( + "-v", + "--vertical-line", + type=int, + default=int(os.environ.get("CICA_VERTICAL_LINE", "0")), + help="縦線を broken(0) か solid(1) か選べます", +) +parser.add_argument( + "-w", + "--ambiguous-width", + type=int, + default=int(os.environ.get("CICA_AMBIGUOUS_WIDTH", "0")), + help="曖昧幅文字幅を single(0) か wide(1) か選べます", +) +parser.add_argument( + "-e", + "--ellipsis", + type=int, + default=int(os.environ.get("CICA_ELLIPSIS", "0")), + help="三点リーダー類を single(0) か wide(1) か選べます", +) +parser.add_argument( + "-i", + "--emoji", + type=int, + default=int(os.environ.get("CICA_EMOJI", "0")), + help="絵文字類を noto emoji(0) か system(1) か選べます", +) args = parser.parse_args() +print(args) + class Cica: def __init__(self, family, name, output_name, weight, weight_name, style_name, font_en, font_jp, italic): self.family = family From 5e42418aa633aa6424b4e2eb1ee1acbe8609199b Mon Sep 17 00:00:00 2001 From: Kyoichiro Yamada Date: Wed, 21 Aug 2019 23:57:46 +0900 Subject: [PATCH 25/31] =?UTF-8?q?=E3=83=93=E3=83=AB=E3=83=89=E6=99=82?= =?UTF-8?q?=E3=81=AE=E3=83=90=E3=83=AA=E3=82=A8=E3=83=BC=E3=82=B7=E3=83=A7?= =?UTF-8?q?=E3=83=B3=E3=81=AE=E6=8C=87=E5=AE=9A=E6=96=B9=E6=B3=95=E3=82=92?= =?UTF-8?q?README=E3=81=AB=E8=BF=BD=E8=A8=98?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- README.md | 29 +++++++++++++++++++++++++++++ 1 file changed, 29 insertions(+) diff --git a/README.md b/README.md index b682e42c..5f8ee702 100644 --- a/README.md +++ b/README.md @@ -138,6 +138,35 @@ fontforge 20120731 libfontforge 20120731-ML ``` +### ビルドオプション + +ビルド時にオプションまたは環境変数で、一部の文字の設定を変更できます。 + +Dockerを使う場合の例: + +```sh +docker-compose build; docker-compose run --rm -e CICA_SPACE=1 cica +``` + +手動でやる場合の例: + +```sh +fontforge -lang=py -script cica.py --space 1 +``` + +各オプションは以下のとおりです。 + +| オプション | 環境変数 | 意味 | +| --- | --- | --- | +| --space | CICA_SPACE | 全角スペースに枠をつける (0) かつけない (1) か選べます | +| --zero | CICA_ZERO | ゼロを dotted(0)、slashed(1)、Hack(2)、blanked(3) から選べます | +| --asterisk | CICA_ASTERISK | アスタリスクのタイプを radial(0) か star(1) か選べます | +| --stroked-d | CICA_STROKED_D | Dを stroked(0) か normal(1) か選べます | +| --vertical-line | CICA_VERTICAL_LINE | 縦線を broken(0) か solid(1) か選べます | +| --ambiguous-width | CICA_AMBIGUOUS_WIDTH | 曖昧幅文字幅を single(0) か wide(1) か選べます | +| --ellipsis | CICA_ELLIPSIS | 三点リーダー類を single(0) か wide(1) か選べます | +| --emoji | CICA_EMOJI | 絵文字類を noto emoji(0) か system(1) か選べます | + ## ライセンス * [LICENSE.txt](LICENSE.txt) From 698a91a2a3fca5ade014b87740d53151d9f0e63d Mon Sep 17 00:00:00 2001 From: SSW-SCIENTIFIC Date: Sun, 15 Sep 2019 02:46:44 +0900 Subject: [PATCH 26/31] =?UTF-8?q?=E3=83=95=E3=82=A9=E3=83=B3=E3=83=88?= =?UTF-8?q?=E3=82=92=E3=83=93=E3=83=AB=E3=83=89=E3=81=99=E3=82=8B=E9=9A=9B?= =?UTF-8?q?=E3=81=AE=E3=82=AA=E3=83=97=E3=82=B7=E3=83=A7=E3=83=B3=E3=82=92?= =?UTF-8?q?=E8=BF=BD=E5=8A=A0?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit * `--modified-m`, `CICA_MODIFIED_LOWERCASE_M`: 小文字の`m`を中心線の短いスタイルに修正するか否か * `--modified-WM`, `CICA_MODIFIED_WM`: 大文字の`W`と`M`を修正するか否か * `--broken-emdash`, `CICA_BROKEN_EMDASH`: emdash `—` をbroken-emdashにするか否か 上記に加えてオプションのデフォルト値についてドキュメントに追記 --- README.md | 19 +++++++++++-------- cica.py | 46 +++++++++++++++++++++++++++++++++++----------- 2 files changed, 46 insertions(+), 19 deletions(-) diff --git a/README.md b/README.md index 5f8ee702..45020a80 100644 --- a/README.md +++ b/README.md @@ -158,14 +158,17 @@ fontforge -lang=py -script cica.py --space 1 | オプション | 環境変数 | 意味 | | --- | --- | --- | -| --space | CICA_SPACE | 全角スペースに枠をつける (0) かつけない (1) か選べます | -| --zero | CICA_ZERO | ゼロを dotted(0)、slashed(1)、Hack(2)、blanked(3) から選べます | -| --asterisk | CICA_ASTERISK | アスタリスクのタイプを radial(0) か star(1) か選べます | -| --stroked-d | CICA_STROKED_D | Dを stroked(0) か normal(1) か選べます | -| --vertical-line | CICA_VERTICAL_LINE | 縦線を broken(0) か solid(1) か選べます | -| --ambiguous-width | CICA_AMBIGUOUS_WIDTH | 曖昧幅文字幅を single(0) か wide(1) か選べます | -| --ellipsis | CICA_ELLIPSIS | 三点リーダー類を single(0) か wide(1) か選べます | -| --emoji | CICA_EMOJI | 絵文字類を noto emoji(0) か system(1) か選べます | +| --space | CICA_SPACE | 全角スペースに枠をつける (0) かつけない (1) か選べます (デフォルト: 0) | +| --zero | CICA_ZERO | ゼロを dotted(0)、slashed(1)、Hack(2)、blanked(3) から選べます (デフォルト: 0) | +| --asterisk | CICA_ASTERISK | アスタリスクのタイプを radial(0) か star(1) か選べます (デフォルト: 0) | +| --stroked-d | CICA_STROKED_D | Dを stroked(0) か normal(1) か選べます (デフォルト: 0) | +| --vertical-line | CICA_VERTICAL_LINE | 縦線を broken(0) か solid(1) か選べます (デフォルト: 0) | +| --ambiguous-width | CICA_AMBIGUOUS_WIDTH | 曖昧幅文字幅を single(0) か wide(1) か選べます (デフォルト: 0) | +| --ellipsis | CICA_ELLIPSIS | 三点リーダー類を single(0) か wide(1) か選べます (デフォルト: 0) | +| --emoji | CICA_EMOJI | 絵文字類を noto emoji(0) か system(1) か選べます (デフォルト: 0) | +| --m | CICA_MODIFIED_LOWERCASE_M | mの中心の線が short(0) か Hack(1) か選べます (デフォルト: 0) | +| --WM | CICA_MODIFIED_WM | MとWが modified(0) か Hack(1) か選べます (デフォルト: 0) | +| --broken-emdash | CICA_BROKEN_EMDASH | emdashを broken(0) にするか Hack(1) か選べます (デフォルト: 0) | ## ライセンス diff --git a/cica.py b/cica.py index c8487411..6269c486 100644 --- a/cica.py +++ b/cica.py @@ -215,56 +215,77 @@ def modify_iconsfordevs(_g): "--space", type=int, default=int(os.environ.get("CICA_SPACE", "0")), - help="全角スペースに枠をつける (0) かつけない (1) か選べます", + help="全角スペースに枠をつける (0) かつけない (1) か選べます (デフォルト: 0)", ) parser.add_argument( "-z", "--zero", type=int, default=int(os.environ.get("CICA_ZERO", "0")), - help="ゼロを dotted(0)、slashed(1)、Hack(2)、blanked(3) から選べます", + help="ゼロを dotted(0)、slashed(1)、Hack(2)、blanked(3) から選べます (デフォルト: 0)", ) parser.add_argument( "-a", "--asterisk", type=int, default=int(os.environ.get("CICA_ASTERISK", "0")), - help="アスタリスクのタイプを radial(0) か star(1) か選べます", + help="アスタリスクのタイプを radial(0) か star(1) か選べます (デフォルト: 0)", ) parser.add_argument( "-d", "--stroked-d", type=int, default=int(os.environ.get("CICA_STROKED_D", "0")), - help="Dを stroked(0) か normal(1) か選べます", + help="Dを stroked(0) か normal(1) か選べます (デフォルト: 0)", ) parser.add_argument( "-v", "--vertical-line", type=int, default=int(os.environ.get("CICA_VERTICAL_LINE", "0")), - help="縦線を broken(0) か solid(1) か選べます", + help="縦線を broken(0) か solid(1) か選べます (デフォルト: 0)", ) parser.add_argument( "-w", "--ambiguous-width", type=int, default=int(os.environ.get("CICA_AMBIGUOUS_WIDTH", "0")), - help="曖昧幅文字幅を single(0) か wide(1) か選べます", + help="曖昧幅文字幅を single(0) か wide(1) か選べます (デフォルト: 0)", ) parser.add_argument( "-e", "--ellipsis", type=int, default=int(os.environ.get("CICA_ELLIPSIS", "0")), - help="三点リーダー類を single(0) か wide(1) か選べます", + help="三点リーダー類を single(0) か wide(1) か選べます (デフォルト: 0)", ) parser.add_argument( "-i", "--emoji", type=int, default=int(os.environ.get("CICA_EMOJI", "0")), - help="絵文字類を noto emoji(0) か system(1) か選べます", + help="絵文字類を noto emoji(0) か system(1) か選べます (デフォルト: 0)", +) +parser.add_argument( + "-m", + "--modified-m", + type=int, + default=int(os.environ.get("CICA_MODIFIED_LOWERCASE_M", "0")), + help="mの中心の線が short(0) か Hack(1) か選べます (デフォルト: 0)", +) +parser.add_argument( + "-W", + "--modified-WM", + type=int, + default=int(os.environ.get("CICA_MODIFIED_WM", "0")), + help="WとMが modified(0) か Hack(1) か選べます (デフォルト: 0)", +) +parser.add_argument( + "-b", + "--broken-emdash", + type=int, + default=int(os.environ.get("CICA_BROKEN_EMDASH", "0")), + help="emdashを broken(0) にするか Hack(1) か選べます (デフォルト: 0)", ) args = parser.parse_args() @@ -880,7 +901,8 @@ def build(self, emoji): g.transform((0.42,0,0,0.42,0,0)) align_to_center(g) - self.modify_m(self.weight_name) + if args.modified_m == 0: + self.modify_m(self.weight_name) log('transform font_jp') for g in self.font_jp.glyphs(): @@ -985,14 +1007,16 @@ def build(self, emoji): if args.stroked_d == 0: self.stroked_d() - self.modify_WM() + if args.modified_WM == 0: + self.modify_WM() if args.vertical_line == 0: self.vertical_line_to_broken_bar() elif args.vertical_line == 1: pass - self.emdash_to_broken_dash() + if args.broken_emdash == 0: + self.emdash_to_broken_dash() self.reiwa(self.weight_name) self.add_gopher() if args.ellipsis == 0: From e409afe0e6f5c55f538fe77018ebc53ae60bf27f Mon Sep 17 00:00:00 2001 From: miiton <468745+miiton@users.noreply.github.com> Date: Tue, 17 Mar 2020 23:20:25 +0900 Subject: [PATCH 27/31] =?UTF-8?q?=F0=9F=91=8D=20=E8=A1=8C=E9=96=93?= =?UTF-8?q?=E3=81=AE=E8=AA=BF=E6=95=B4?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- cica.py | 39 +++++++++++++++++++++++---------------- 1 file changed, 23 insertions(+), 16 deletions(-) diff --git a/cica.py b/cica.py index 7a7f960e..d3080b09 100644 --- a/cica.py +++ b/cica.py @@ -14,6 +14,13 @@ # DESCENT = 174 ASCENT = 820 DESCENT = 204 +WIN_ASCENT = 820 +WIN_DESCENT = 204 +TYPO_ASCENT = 670 +TYPO_DESCENT = -104 +TYPO_LINEGAP = 80 +HHEA_ASCENT = 855 +HHEA_DESCENT = -169 SOURCE = './source' LICENSE = open('./LICENSE.txt').read() COPYRIGHT = open('./COPYRIGHT.txt').read() @@ -74,7 +81,7 @@ def align_to_right(_g): _g.width = width def fix_overflow(glyph): - """上が820を超えている、または下が-204を超えているグリフを + """上がASCENTを超えている、または下が-DESCENTを超えているグリフを 1024x1024の枠にはまるように修正する ※全角のグリフのみに実施する """ @@ -90,10 +97,10 @@ def fix_overflow(glyph): bb = glyph.boundingBox() bottom = bb[1] top = bb[3] - if bottom < -204: - glyph.transform(psMat.translate(0, -204 - bottom)) - elif top > 820: - glyph.transform(psMat.translate(0, 820 - top)) + if bottom < -DESCENT: + glyph.transform(psMat.translate(0, -DESCENT - bottom)) + elif top > ASCENT: + glyph.transform(psMat.translate(0, ASCENT - top)) return glyph def modify_nerd(_g): @@ -324,21 +331,21 @@ def set_os2_values(self): self.font_jp.os2_stylemap = 33 self.font_jp.os2_vendor = 'TMNM' self.font_jp.os2_version = 1 - self.font_jp.os2_winascent = ASCENT + self.font_jp.os2_winascent = WIN_ASCENT self.font_jp.os2_winascent_add = False - self.font_jp.os2_windescent = DESCENT + self.font_jp.os2_windescent = WIN_DESCENT self.font_jp.os2_windescent_add = False - self.font_jp.os2_typoascent = -150 - self.font_jp.os2_typoascent_add = True - self.font_jp.os2_typodescent = 100 - self.font_jp.os2_typodescent_add = True - self.font_jp.os2_typolinegap = 0 + self.font_jp.os2_typoascent = TYPO_ASCENT + self.font_jp.os2_typoascent_add = False + self.font_jp.os2_typodescent = TYPO_DESCENT + self.font_jp.os2_typodescent_add = False + self.font_jp.os2_typolinegap = TYPO_LINEGAP - self.font_jp.hhea_ascent = -150 - self.font_jp.hhea_ascent_add = True - self.font_jp.hhea_descent = 100 - self.font_jp.hhea_descent_add = True + self.font_jp.hhea_ascent = HHEA_ASCENT + self.font_jp.hhea_ascent_add = False + self.font_jp.hhea_descent = HHEA_DESCENT + self.font_jp.hhea_descent_add = False self.font_jp.hhea_linegap = 0 self.font_jp.os2_panose = (2, 11, int(weight / 100), 9, 2, 2, 3, 2, 2, 7) From 579554dd8687a815a70529a18e2184cc6e2a4b99 Mon Sep 17 00:00:00 2001 From: miiton <468745+miiton@users.noreply.github.com> Date: Wed, 18 Mar 2020 09:23:33 +0900 Subject: [PATCH 28/31] =?UTF-8?q?=E4=B8=80=E9=83=A8=E6=84=8F=E5=9B=B3?= =?UTF-8?q?=E3=81=9B=E3=81=9A=E3=82=B0=E3=83=AA=E3=83=95=E3=81=8CMgen+?= =?UTF-8?q?=E3=81=AB=E3=81=AA=E3=81=A3=E3=81=A6=E3=81=97=E3=81=BE=E3=81=86?= =?UTF-8?q?=E3=81=AE=E3=81=A7=E3=80=81=E8=87=AA=E5=8B=95=E7=9A=84=E3=81=AB?= =?UTF-8?q?ambiguous=E3=82=B0=E3=83=AA=E3=83=95=E3=82=92=E5=88=A4=E5=AE=9A?= =?UTF-8?q?=E3=81=97=E3=81=A6=E3=82=92=E5=87=A6=E7=90=86=E3=81=97=E3=81=AA?= =?UTF-8?q?=E3=81=84=E3=81=A8=E3=81=84=E3=81=86=E6=9D=A1=E4=BB=B6=E5=88=86?= =?UTF-8?q?=E5=B2=90=E3=82=92=E5=89=8A=E9=99=A4?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- cica.py | 48 +++++++++++++++++++++++++----------------------- 1 file changed, 25 insertions(+), 23 deletions(-) diff --git a/cica.py b/cica.py index d3080b09..c6fdb1ac 100644 --- a/cica.py +++ b/cica.py @@ -18,14 +18,14 @@ WIN_DESCENT = 204 TYPO_ASCENT = 670 TYPO_DESCENT = -104 -TYPO_LINEGAP = 80 +TYPO_LINEGAP = 0 HHEA_ASCENT = 855 HHEA_DESCENT = -169 SOURCE = './source' LICENSE = open('./LICENSE.txt').read() COPYRIGHT = open('./COPYRIGHT.txt').read() -VERSION = '5.0.2' -FAMILY = 'CicaTest' +VERSION = '6.0.0-beta' +FAMILY = 'Cica' AMBI = 0 SINGLE = 1 DOUBLE = 2 @@ -257,14 +257,14 @@ def modify_iconsfordevs(_g): "--ambiguous-width", type=int, default=int(os.environ.get("CICA_AMBIGUOUS_WIDTH", "0")), - help="曖昧幅文字幅を single(0) か wide(1) か選べます (デフォルト: 0)", + help="曖昧幅文字幅を single(0) か double(1) か選べます (デフォルト: 0)", ) parser.add_argument( "-e", "--ellipsis", type=int, default=int(os.environ.get("CICA_ELLIPSIS", "0")), - help="三点リーダー類を single(0) か wide(1) か選べます (デフォルト: 0)", + help="三点リーダー類の幅を single(0) か double(1) か選べます (デフォルト: 0)", ) parser.add_argument( "-i", @@ -359,8 +359,6 @@ def add_dejavu(self): dejavu = fontforge.open('./source/DejaVuSansMono-Bold.ttf') for g in dejavu.glyphs(): - if self.wp.width(g.encoding) == AMBI: - continue g.transform(psMat.compose(psMat.scale(0.45, 0.45), psMat.translate(-21, 0))) g.width = 512 @@ -368,8 +366,6 @@ def add_dejavu(self): # 0x0300 - 0x036f - Combining Diacritical Marks for g in dejavu.glyphs(): - if self.wp.width(g.encoding) == AMBI: - continue if g.encoding < 0x0300 or g.encoding > 0x036f or g.encoding == 0x0398: continue else: @@ -419,8 +415,6 @@ def add_dejavu(self): self.font_jp.paste() # 0x0370 - 0x03ff - GREEK for g in dejavu.glyphs(): - if self.wp.width(g.encoding) == AMBI: - continue if g.encoding < 0x0370 or g.encoding > 0x03ff or g.encoding == 0x0398: continue else: @@ -433,8 +427,6 @@ def add_dejavu(self): self.font_jp.paste() # 0x2100 - 0x214f Letterlike Symbols for g in dejavu.glyphs(): - if self.wp.width(g.encoding) == AMBI: - continue if g.encoding < 0x2100 or g.encoding > 0x214f or g.encoding == 0x2122: continue else: @@ -445,8 +437,6 @@ def add_dejavu(self): self.font_jp.paste() # 0x2150 - 0x218f Number Forms for g in dejavu.glyphs(): - if self.wp.width(g.encoding) == AMBI: - continue if g.encoding < 0x2150 or g.encoding > 0x218f: continue else: @@ -457,8 +447,6 @@ def add_dejavu(self): self.font_jp.paste() # 0x2190 - 0x21ff Arrows for g in dejavu.glyphs(): - if self.wp.width(g.encoding) == AMBI: - continue if g.encoding < 0x2190 or g.encoding > 0x21ff: continue else: @@ -469,8 +457,6 @@ def add_dejavu(self): self.font_jp.paste() # 0x2200 - 0x22ff Mathematical Operators for g in dejavu.glyphs(): - if self.wp.width(g.encoding) == AMBI: - continue if g.encoding < 0x2200 or g.encoding > 0x22ff: continue else: @@ -481,8 +467,6 @@ def add_dejavu(self): self.font_jp.paste() # 0x2300 - 0x23ff Miscellaneous Technical for g in dejavu.glyphs(): - if self.wp.width(g.encoding) == AMBI: - continue if g.encoding < 0x2300 or g.encoding > 0x23ff: continue else: @@ -928,6 +912,26 @@ def build(self, emoji): if args.modified_m == 0: self.modify_m(self.weight_name) + log('transform font_jp') + for g in self.font_jp.glyphs(): + g.transform((0.91,0,0,0.91,0,0)) + full_half_threshold = 700 + if self.italic: + g.transform(psMat.skew(0.25)) + skew_amount = g.font.ascent * 0.91 * 0.25 + g.width = g.width + skew_amount + full_half_threshold += skew_amount + if g.width > full_half_threshold: + width = 1024 + else: + width = 512 + g.transform(psMat.translate((width - g.width)/2, 0)) + g.width = width + if g.encoding in ignoring_center: + pass + else: + align_to_center(g) + # 0x2715 -> 0xd7 : 乗算記号 self.font_jp.selection.select(0x2715) self.font_jp.copy() @@ -954,8 +958,6 @@ def build(self, emoji): log('modify border glyphs') for g in self.font_en.glyphs(): - if self.wp.width(g.encoding) == AMBI: - continue if g.isWorthOutputting: if self.italic: g.transform(psMat.skew(0.25)) From 886ef05002ab52054562abb55401690c5eba5d68 Mon Sep 17 00:00:00 2001 From: miiton <468745+miiton@users.noreply.github.com> Date: Tue, 27 Jul 2021 08:04:44 +0900 Subject: [PATCH 29/31] =?UTF-8?q?GitHub=20Actions=E3=81=AB=E7=A7=BB?= =?UTF-8?q?=E8=A1=8C=E3=81=99=E3=82=8B=E3=81=AE=E3=81=A7Circle=20CI?= =?UTF-8?q?=E3=81=AE=E8=A8=AD=E5=AE=9A=E3=82=92=E5=89=8A=E9=99=A4?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .circleci/config.yml | 37 ------------------------------------- 1 file changed, 37 deletions(-) delete mode 100644 .circleci/config.yml diff --git a/.circleci/config.yml b/.circleci/config.yml deleted file mode 100644 index 15c2da2c..00000000 --- a/.circleci/config.yml +++ /dev/null @@ -1,37 +0,0 @@ -version: 2 -jobs: - build: - docker: - - image: docker:17.05.0-ce-git - steps: - - checkout - - setup_remote_docker - - run: - name: Install dependencies - command: | - apk add --no-cache \ - py-pip=9.0.0-r1 - pip install \ - docker-compose==1.12.0 \ - awscli==1.11.76 - - run: - name: Build - command: | - docker-compose build && docker-compose run --rm cica - publish-github-release: - required: - - build - filters: - tags: - only: /^v\d+\.\d+\.\d+$/ - docker: - - image: circleci/golang:1.8 - steps: - - attach_workspace: - at: ./dist - - run: - name: Publish Release on GitHub - command: | - go get github.com/tcnksm/ghr - VERSION=$(my-binary --version) - ghr -t ${GITHUB_TOKEN} -u ${CIRCLE_PROJECT_USERNAME} -r ${CIRCLE_PROJECT_REPONAME} -c ${CIRCLE_SHA1} -delete ${VERSION} ./dist/ From 79d59257d1009db254825ecebf933af315dd594c Mon Sep 17 00:00:00 2001 From: miiton <468745+miiton@users.noreply.github.com> Date: Fri, 11 Feb 2022 15:32:09 +0900 Subject: [PATCH 30/31] Merge pull request #73 from YuseiUeno/patch-1 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit docker-compose build で unar が失敗しないように修正 (cherry picked from commit 9b89b8dbc5ab23ff97f0979af181e9cee7301f9c) --- Dockerfile | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/Dockerfile b/Dockerfile index 105a6cd2..5c892b52 100644 --- a/Dockerfile +++ b/Dockerfile @@ -24,8 +24,8 @@ RUN curl --fail -L https://github.com/source-foundry/Hack/releases/download/$HAC unar /tmp/dejavu.zip -o /tmp && \ cp /tmp/dejavu-fonts-ttf-$DEJAVU_VERSION/ttf/DejaVuSansMono.ttf sourceFonts/ && \ cp /tmp/dejavu-fonts-ttf-$DEJAVU_VERSION/ttf/DejaVuSansMono-Bold.ttf sourceFonts/ && \ - curl -L https://github.com/mirmat/iconsfordevs/raw/$ICONSFORDEVS_VERSION/fonts/iconsfordevs.ttf -o sourceFonts/iconsfordevs.ttf && \ - curl -L http://www.unicode.org/Public/12.0.0/ucd/EastAsianWidth.txt -o sourceFonts/EastAsianWidth.txt + curl --fail -L https://github.com/mirmat/iconsfordevs/raw/$ICONSFORDEVS_VERSION/fonts/iconsfordevs.ttf -o sourceFonts/iconsfordevs.ttf + curl --fail -L http://www.unicode.org/Public/12.0.0/ucd/EastAsianWidth.txt -o sourceFonts/EastAsianWidth.txt COPY cica.py cica.py COPY width_parser.py width_parser.py From 750e7dcbbb19298a21cd422480e7154a465a829a Mon Sep 17 00:00:00 2001 From: miiton <468745+miiton@users.noreply.github.com> Date: Fri, 11 Feb 2022 15:38:09 +0900 Subject: [PATCH 31/31] Merge pull request #72 from kusanaginoturugi/main MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit NotoEmoji-Regular.ttf のダウンロード元を変更 (cherry picked from commit 1d0e1915acb3071d05589b988f386bc8b609508e) --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index b7f1d14f..3d547b72 100644 --- a/README.md +++ b/README.md @@ -115,7 +115,7 @@ curl -LO https://osdn.jp/downloads/users/8/8598/rounded-mgenplus-20150602.7z unar rounded-mgenplus-20150602.7z cp rounded-mgenplus-20150602/rounded-mgenplus-1m-regular.ttf ./sourceFonts cp rounded-mgenplus-20150602/rounded-mgenplus-1m-bold.ttf ./sourceFonts -curl -L https://github.com/googlei18n/noto-emoji/raw/master/fonts/NotoEmoji-Regular.ttf -o sourceFonts/NotoEmoji-Regular.ttf +curl -L https://github.com/googlefonts/noto-emoji/raw/main/fonts/NotoEmoji-Regular.ttf -o sourceFonts/NotoEmoji-Regular.ttf curl -LO http://sourceforge.net/projects/dejavu/files/dejavu/2.37/dejavu-fonts-ttf-2.37.zip unar dejavu-fonts-ttf-2.37.zip mv dejavu-fonts-ttf-2.37/ttf/DejaVuSansMono.ttf ./sourceFonts/