Add a command to list fonts
This commit is contained in:
parent
1d7b650fd0
commit
43bf056f09
@ -6,6 +6,9 @@ kitty is a feature full, cross-platform, *fast*, GPU based terminal emulator.
|
|||||||
version 0.5.0 [future]
|
version 0.5.0 [future]
|
||||||
---------------------------
|
---------------------------
|
||||||
|
|
||||||
|
- Make it easy to select fonts by allowing listing of monospace fonts using:
|
||||||
|
kitty list-fonts
|
||||||
|
|
||||||
- macOS: Enable subpixel rendering of text for improved appearance
|
- macOS: Enable subpixel rendering of text for improved appearance
|
||||||
|
|
||||||
- Linux: Support rendering of non-normalizable unicode combining characters by using harfbuzz
|
- Linux: Support rendering of non-normalizable unicode combining characters by using harfbuzz
|
||||||
|
|||||||
@ -7,6 +7,9 @@ import sys
|
|||||||
if len(sys.argv) > 1 and sys.argv[1] == 'icat':
|
if len(sys.argv) > 1 and sys.argv[1] == 'icat':
|
||||||
from kitty.icat import main
|
from kitty.icat import main
|
||||||
main(sys.argv[1:])
|
main(sys.argv[1:])
|
||||||
|
elif len(sys.argv) > 1 and sys.argv[1] == 'list-fonts':
|
||||||
|
from kitty.fonts.list import main
|
||||||
|
main(sys.argv[1:])
|
||||||
else:
|
else:
|
||||||
from kitty.main import main
|
from kitty.main import main
|
||||||
main()
|
main()
|
||||||
|
|||||||
@ -34,6 +34,15 @@ def all_fonts_map():
|
|||||||
return ans
|
return ans
|
||||||
|
|
||||||
|
|
||||||
|
def list_fonts():
|
||||||
|
for fd in coretext_all_fonts():
|
||||||
|
f = fd['family']
|
||||||
|
if f:
|
||||||
|
fn = (f + ' ' + (fd['style'] or '')).strip()
|
||||||
|
is_mono = bool(fd['monospace'])
|
||||||
|
yield {'family': f, 'full_name': fn, 'is_monospace': is_mono}
|
||||||
|
|
||||||
|
|
||||||
def find_best_match(family, bold, italic):
|
def find_best_match(family, bold, italic):
|
||||||
q = re.sub(r'\s+', ' ', family.lower())
|
q = re.sub(r'\s+', ' ', family.lower())
|
||||||
font_map = all_fonts_map()
|
font_map = all_fonts_map()
|
||||||
|
|||||||
@ -19,6 +19,8 @@ attr_map = {(False, False): 'font_family',
|
|||||||
def create_font_map(all_fonts):
|
def create_font_map(all_fonts):
|
||||||
ans = {'family_map': {}, 'ps_map': {}, 'full_map': {}}
|
ans = {'family_map': {}, 'ps_map': {}, 'full_map': {}}
|
||||||
for x in all_fonts:
|
for x in all_fonts:
|
||||||
|
if 'path' not in x:
|
||||||
|
continue
|
||||||
f = (x.get('family') or '').lower()
|
f = (x.get('family') or '').lower()
|
||||||
full = (x.get('full_name') or '').lower()
|
full = (x.get('full_name') or '').lower()
|
||||||
ps = (x.get('postscript_name') or '').lower()
|
ps = (x.get('postscript_name') or '').lower()
|
||||||
@ -33,14 +35,23 @@ def all_fonts_map(monospaced=True):
|
|||||||
return create_font_map(fc_list(monospaced))
|
return create_font_map(fc_list(monospaced))
|
||||||
|
|
||||||
|
|
||||||
|
def list_fonts():
|
||||||
|
for fd in fc_list(False):
|
||||||
|
f = fd.get('family')
|
||||||
|
if f:
|
||||||
|
fn = fd.get('full_name') or (f + ' ' + fd.get('style', '')).strip()
|
||||||
|
is_mono = fd.get('spacing') == 'MONO'
|
||||||
|
yield {'family': f, 'full_name': fn, 'is_monospace': is_mono}
|
||||||
|
|
||||||
|
|
||||||
def find_best_match(family, bold=False, italic=False, monospaced=True):
|
def find_best_match(family, bold=False, italic=False, monospaced=True):
|
||||||
q = re.sub(r'\s+', ' ', family.lower())
|
q = re.sub(r'\s+', ' ', family.lower())
|
||||||
font_map = all_fonts_map(monospaced)
|
font_map = all_fonts_map(monospaced)
|
||||||
|
|
||||||
def score(candidate):
|
def score(candidate):
|
||||||
bold_score = abs((FC_WEIGHT_BOLD if bold else FC_WEIGHT_REGULAR) - candidate['weight'])
|
bold_score = abs((FC_WEIGHT_BOLD if bold else FC_WEIGHT_REGULAR) - candidate.get('weight', 0))
|
||||||
italic_score = abs((FC_SLANT_ITALIC if italic else FC_SLANT_ROMAN) - candidate['slant'])
|
italic_score = abs((FC_SLANT_ITALIC if italic else FC_SLANT_ROMAN) - candidate.get('slant', 0))
|
||||||
monospace_match = 0 if candidate['spacing'] == 'MONO' else 1
|
monospace_match = 0 if candidate.get('spacing') == 'MONO' else 1
|
||||||
return bold_score + italic_score, monospace_match
|
return bold_score + italic_score, monospace_match
|
||||||
|
|
||||||
# First look for an exact match
|
# First look for an exact match
|
||||||
@ -56,8 +67,8 @@ def find_best_match(family, bold=False, italic=False, monospaced=True):
|
|||||||
|
|
||||||
|
|
||||||
def face_from_font(font, pt_sz=11.0, xdpi=96.0, ydpi=96.0):
|
def face_from_font(font, pt_sz=11.0, xdpi=96.0, ydpi=96.0):
|
||||||
font = fc_font(pt_sz, (xdpi + ydpi) / 2.0, font['path'], font['index'])
|
font = fc_font(pt_sz, (xdpi + ydpi) / 2.0, font['path'], font.get('index', 0))
|
||||||
return Face(font['path'], font['index'], font['hinting'], font['hint_style'], pt_sz, xdpi, ydpi)
|
return Face(font['path'], font.get('index', 0), font.get('hinting', False), font.get('hint_style', 0), pt_sz, xdpi, ydpi)
|
||||||
|
|
||||||
|
|
||||||
def resolve_family(f, main_family, bold, italic):
|
def resolve_family(f, main_family, bold, italic):
|
||||||
@ -86,8 +97,8 @@ def get_font_files(opts):
|
|||||||
|
|
||||||
|
|
||||||
def font_for_family(family):
|
def font_for_family(family):
|
||||||
ans = find_best_match(family)
|
ans = find_best_match(family, monospaced=False)
|
||||||
return ans, ans['weight'] >= FC_WEIGHT_BOLD, ans['slant'] != FC_SLANT_ROMAN
|
return ans, ans.get('weight', 0) >= FC_WEIGHT_BOLD, ans.get('slant', FC_SLANT_ROMAN) != FC_SLANT_ROMAN
|
||||||
|
|
||||||
|
|
||||||
def font_for_text(text, current_font_family='monospace', pt_sz=11.0, xdpi=96.0, ydpi=96.0, bold=False, italic=False):
|
def font_for_text(text, current_font_family='monospace', pt_sz=11.0, xdpi=96.0, ydpi=96.0, bold=False, italic=False):
|
||||||
|
|||||||
35
kitty/fonts/list.py
Normal file
35
kitty/fonts/list.py
Normal file
@ -0,0 +1,35 @@
|
|||||||
|
#!/usr/bin/env python
|
||||||
|
# vim:fileencoding=utf-8
|
||||||
|
# License: GPL v3 Copyright: 2017, Kovid Goyal <kovid at kovidgoyal.net>
|
||||||
|
|
||||||
|
import sys
|
||||||
|
from kitty.constants import isosx
|
||||||
|
|
||||||
|
if isosx:
|
||||||
|
from .core_text import list_fonts
|
||||||
|
else:
|
||||||
|
from .fontconfig import list_fonts
|
||||||
|
|
||||||
|
|
||||||
|
def create_family_groups(monospaced=True):
|
||||||
|
g = {}
|
||||||
|
for f in list_fonts():
|
||||||
|
if not monospaced or f['is_monospace']:
|
||||||
|
g.setdefault(f['family'], []).append(f)
|
||||||
|
return g
|
||||||
|
|
||||||
|
|
||||||
|
def main(argv):
|
||||||
|
isatty = sys.stdout.isatty()
|
||||||
|
groups = create_family_groups()
|
||||||
|
for k in sorted(groups, key=lambda x: x.lower()):
|
||||||
|
if isatty:
|
||||||
|
print('\033[1;32m' + k + '\033[m')
|
||||||
|
else:
|
||||||
|
print(k)
|
||||||
|
for f in sorted(groups[k], key=lambda x: x['full_name'].lower()):
|
||||||
|
p = f['full_name']
|
||||||
|
if isatty:
|
||||||
|
p = '\033[3m' + p + '\033[m'
|
||||||
|
print(' ', p)
|
||||||
|
print()
|
||||||
@ -5,14 +5,12 @@
|
|||||||
# by the OSes font system. Setting them manually is useful for font families
|
# by the OSes font system. Setting them manually is useful for font families
|
||||||
# that have many weight variants like Book, Medium, Thick, etc. For example:
|
# that have many weight variants like Book, Medium, Thick, etc. For example:
|
||||||
# font_family Operator Mono Book
|
# font_family Operator Mono Book
|
||||||
# bold_font Operator Mono Thick
|
# bold_font Operator Mono Medium
|
||||||
# bold_italic_font Operator Mono Medium
|
# italic_font Operator Mono Book Italic
|
||||||
# or
|
# bold_italic_font Operator Mono Medium Italic
|
||||||
# font_family SF Mono Medium
|
#
|
||||||
# bold_font SF Mono Semibold
|
# You can get a list of full family names available on your computer by running
|
||||||
# bold_italic_font SF Mono Semibold
|
# kitty list-fonts
|
||||||
# Note that you should use the full family name but do not add Bold or Italic qualifiers
|
|
||||||
# to the name.
|
|
||||||
font_family monospace
|
font_family monospace
|
||||||
italic_font auto
|
italic_font auto
|
||||||
bold_font auto
|
bold_font auto
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user