diff --git a/lib/fmt/png.py b/lib/fmt/png.py index d1fbd17..be4d7be 100644 --- a/lib/fmt/png.py +++ b/lib/fmt/png.py @@ -1,5 +1,5 @@ #!/usr/bin/python -#vim: encoding=utf-8 +# vim: encoding=utf-8 # pylint: disable=wrong-import-position,wrong-import-order,redefined-builtin """ @@ -39,17 +39,17 @@ CHAR_WIDTH = 8 CHAR_HEIGHT = 14 FONT_SIZE = 13 FONT_CAT = { - 'default': "/usr/share/fonts/truetype/dejavu/DejaVuSansMono.ttf", - 'Cyrillic': "/usr/share/fonts/truetype/dejavu/DejaVuSansMono.ttf", - 'Greek': "/usr/share/fonts/truetype/dejavu/DejaVuSansMono.ttf", - 'Arabic': "/usr/share/fonts/truetype/dejavu/DejaVuSansMono.ttf", - 'Hebrew': "/usr/share/fonts/truetype/dejavu/DejaVuSansMono.ttf", - 'Han': "/usr/share/fonts/truetype/wqy/wqy-zenhei.ttc", - 'Hiragana': "/usr/share/fonts/truetype/motoya-l-cedar/MTLc3m.ttf", - 'Katakana': "/usr/share/fonts/truetype/motoya-l-cedar/MTLc3m.ttf", - 'Hangul': "/usr/share/fonts/truetype/lexi/LexiGulim.ttf", - 'Braille': "/usr/share/fonts/truetype/ancient-scripts/Symbola_hint.ttf", - 'Emoji': "/usr/share/fonts/truetype/ancient-scripts/Symbola_hint.ttf", + "default": "/usr/share/fonts/truetype/dejavu/DejaVuSansMono.ttf", + "Cyrillic": "/usr/share/fonts/truetype/dejavu/DejaVuSansMono.ttf", + "Greek": "/usr/share/fonts/truetype/dejavu/DejaVuSansMono.ttf", + "Arabic": "/usr/share/fonts/truetype/dejavu/DejaVuSansMono.ttf", + "Hebrew": "/usr/share/fonts/truetype/dejavu/DejaVuSansMono.ttf", + "Han": "/usr/share/fonts/truetype/wqy/wqy-zenhei.ttc", + "Hiragana": "/usr/share/fonts/truetype/motoya-l-cedar/MTLc3m.ttf", + "Katakana": "/usr/share/fonts/truetype/motoya-l-cedar/MTLc3m.ttf", + "Hangul": "/usr/share/fonts/truetype/lexi/LexiGulim.ttf", + "Braille": "/usr/share/fonts/truetype/ancient-scripts/Symbola_hint.ttf", + "Emoji": "/usr/share/fonts/truetype/ancient-scripts/Symbola_hint.ttf", } # @@ -66,6 +66,7 @@ FONT_CAT = { # * fonts-symbola (Braille/Emoji) # + def render_ansi(text, options=None): """Render `text` (terminal sequence) in a PNG file paying attention to passed command line `options`. @@ -85,24 +86,22 @@ def render_ansi(text, options=None): return _gen_term(buf, graphemes, options=options) + def _color_mapping(color, inverse=False): """Convert pyte color to PIL color Return: tuple of color values (R,G,B) """ - if color == 'default': + if color == "default": if inverse: - return 'black' - return 'lightgray' + return "black" + return "lightgray" - if color in ['green', 'black', 'cyan', 'blue', 'brown']: + if color in ["green", "black", "cyan", "blue", "brown"]: return color try: - return ( - int(color[0:2], 16), - int(color[2:4], 16), - int(color[4:6], 16)) + return (int(color[0:2], 16), int(color[2:4], 16), int(color[4:6], 16)) except (ValueError, IndexError): # if we do not know this color and it can not be decoded as RGB, # print it and return it as it is (will be displayed as black) @@ -110,6 +109,7 @@ def _color_mapping(color, inverse=False): return color return color + def _strip_buf(buf): """Strips empty spaces from behind and from the right side. (from the right side is not yet implemented) @@ -117,13 +117,13 @@ def _strip_buf(buf): def empty_line(line): "Returns True if the line consists from spaces" - return all(x.data == ' ' for x in line) + return all(x.data == " " for x in line) def line_len(line): "Returns len of the line excluding spaces from the right" last_pos = len(line) - while last_pos > 0 and line[last_pos-1].data == ' ': + while last_pos > 0 and line[last_pos - 1].data == " ": last_pos -= 1 return last_pos @@ -141,6 +141,7 @@ def _strip_buf(buf): return buf + def _script_category(char): """Returns category of a Unicode character @@ -152,12 +153,13 @@ def _script_category(char): return "Emoji" cat = unicodedata2.script_cat(char)[0] - if char == u':': - return 'Han' - if cat in ['Latin', 'Common']: - return 'default' + if char == ":": + return "Han" + if cat in ["Latin", "Common"]: + return "default" return cat + def _load_emojilib(): """Load known emojis from a directory, and return dictionary of PIL Image objects correspodent to the loaded emojis. @@ -167,10 +169,10 @@ def _load_emojilib(): emojilib = {} for filename in glob.glob("share/emoji/*.png"): character = os.path.basename(filename)[:-3] - emojilib[character] = \ - Image.open(filename).resize((CHAR_HEIGHT, CHAR_HEIGHT)) + emojilib[character] = Image.open(filename).resize((CHAR_HEIGHT, CHAR_HEIGHT)) return emojilib + # pylint: disable=too-many-locals,too-many-branches,too-many-statements def _gen_term(buf, graphemes, options=None): """Renders rendered pyte buffer `buf` and list of workaround `graphemes` @@ -190,7 +192,7 @@ def _gen_term(buf, graphemes, options=None): if "background" in options: bg_color = _color_mapping(options["background"], options.get("inverted_colors")) - image = Image.new('RGB', (cols * CHAR_WIDTH, rows * CHAR_HEIGHT), color=bg_color) + image = Image.new("RGB", (cols * CHAR_WIDTH, rows * CHAR_HEIGHT), color=bg_color) buf = buf[-ROWS:] @@ -207,11 +209,11 @@ def _gen_term(buf, graphemes, options=None): x_pos = 0 for char in line: current_color = _color_mapping(char.fg, options.get("inverted_colors")) - if char.bg != 'default': + if char.bg != "default": draw.rectangle( - ((x_pos, y_pos), - (x_pos+CHAR_WIDTH, y_pos+CHAR_HEIGHT)), - fill=_color_mapping(char.bg, options.get("inverted_colors"))) + ((x_pos, y_pos), (x_pos + CHAR_WIDTH, y_pos + CHAR_HEIGHT)), + fill=_color_mapping(char.bg, options.get("inverted_colors")), + ) if char.data == "!": try: @@ -226,20 +228,21 @@ def _gen_term(buf, graphemes, options=None): cat = _script_category(data[0]) if cat not in font: globals.log("Unknown font category: %s" % cat) - if cat == 'Emoji' and emojilib.get(data): + if cat == "Emoji" and emojilib.get(data): image.paste(emojilib.get(data), (x_pos, y_pos)) else: draw.text( (x_pos, y_pos), data, - font=font.get(cat, font.get('default')), - fill=current_color) + font=font.get(cat, font.get("default")), + fill=current_color, + ) x_pos += CHAR_WIDTH * constants.WEATHER_SYMBOL_WIDTH_VTE.get(data, 1) y_pos += CHAR_HEIGHT - if 'transparency' in options: - transparency = options.get('transparency', '255') + if "transparency" in options: + transparency = options.get("transparency", "255") try: transparency = int(transparency) except ValueError: @@ -265,6 +268,7 @@ def _gen_term(buf, graphemes, options=None): image.save(img_bytes, format="png") return img_bytes.getvalue() + def _fix_graphemes(text): """ Extract long graphemes sequences that can't be handled