mocodraw 0.1.0__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
mocodraw/__init__.py ADDED
@@ -0,0 +1,57 @@
1
+ """Draw entity-relationship diagrams from a text description.
2
+
3
+ The input language is the one Mocodo uses::
4
+
5
+ CLIENT: Réf. client, Nom, Prénom, Adresse
6
+ PASSER, 0N CLIENT, 11 COMMANDE
7
+ COMMANDE: Num commande, Date, Montant
8
+
9
+ Each line is an entity (``NAME: attributes``) or an association
10
+ (``NAME, cardinality ENTITY, cardinality ENTITY``). A blank line starts a new row of
11
+ the grid, and indentation puts boxes on successive pages.
12
+
13
+ Getting started::
14
+
15
+ import mocodraw
16
+
17
+ mocodraw.preview(source) # ASCII, for the terminal
18
+ svg = mocodraw.render(source) # SVG string
19
+ mocodraw.render_to_file(source, "model.svg") # SVG on disk
20
+ mocodraw.render_to_file(source, "model.svg", png=True) # needs cairosvg
21
+
22
+ Everything except the optional PNG step uses the standard library only.
23
+ """
24
+
25
+ from ._version import __version__
26
+ from .api import Diagram, parse, preview, render, render_to_file
27
+ from .document import Model
28
+ from .errors import MocodrawError, ModelError, ParseError, SchemaError, StyleError
29
+ from .layout import Geometry, detect_overlaps
30
+ from .preview import render_preview
31
+ from .schema import Association, Entity, Leg, Schema
32
+ from .style import Style, available_palettes, available_shapes
33
+
34
+ __all__ = [
35
+ "Association",
36
+ "Diagram",
37
+ "Entity",
38
+ "Geometry",
39
+ "Model",
40
+ "Leg",
41
+ "MocodrawError",
42
+ "ModelError",
43
+ "ParseError",
44
+ "Schema",
45
+ "SchemaError",
46
+ "Style",
47
+ "StyleError",
48
+ "__version__",
49
+ "available_palettes",
50
+ "available_shapes",
51
+ "detect_overlaps",
52
+ "parse",
53
+ "preview",
54
+ "render_preview",
55
+ "render",
56
+ "render_to_file",
57
+ ]
mocodraw/__main__.py ADDED
@@ -0,0 +1,8 @@
1
+ """``python -m mocodraw`` — same entry point as the ``mocodraw`` script."""
2
+
3
+ import sys
4
+
5
+ from .cli import main
6
+
7
+ if __name__ == "__main__":
8
+ sys.exit(main())
mocodraw/_font_data.py ADDED
@@ -0,0 +1,137 @@
1
+ """Generated by ``tools/gen_font_metrics.py``. Do not edit by hand.
2
+
3
+ Each entry maps a font family to ``(widths, height, default)`` where
4
+ ``widths`` is a string whose *n*-th character encodes the advance width of the
5
+ *n*-th character of ``ALPHABET`` in 1/256 em units, ``height`` is the line
6
+ height and ``default`` the fallback width, both in the same unit.
7
+ """
8
+
9
+ EM = 256
10
+
11
+ ALPHABET = (
12
+ ' !"#$%&\'()*+,-./0123456789:;<=>?@ABCDEFGHIJKLMNOPQRSTUVWXYZ[\\]^_`abcdefghijk'
13
+ 'lmnopqrstuvwxyz{|}~¡¢£¤¥¦§©«¬®°±²³µ¶·º»¿ÀÁÂÃÄÅÆÇÈÉÊËÌÍÎÏÐÑÒÓÔÕÖŒ×ØÙÚÛÜÝÞßàáâ'
14
+ 'ãäåæçèéêëìíîïðñòóôõöœ÷øùúûüýþÿ—‘’•…′″‵‶'
15
+ )
16
+
17
+ #: ``family -> (widths, height, default)``
18
+ FONTS = {
19
+ 'Arial': (
20
+ 'GG[\x8e\x8eä«1UUd\x96GUGG\x8e\x8e\x8e\x8e\x8e\x8e\x8e\x8e\x8e\x8eGG\x96\x96\x96\x8eĄ««¹¹«\x9cǹG\x80«\x8eչǫǹ«\x9c¹«ò««\x9cGGGx\x8eU\x8e\x8e\x80\x8e\x8eG\x8e\x8e99\x80'
21
+ '9Õ\x8e\x8e\x8e\x8eU\x80G\x8e\x80¹\x80\x80\x80VCV\x96U\x8e\x8e\x8e\x8eC\x8e½\x8e\x96½f\x8dUU\x94\x8aU^\x8e\x9c««««««Ā¹««««GGGG¹¹ÇÇÇÇÇĀ\x96ǹ¹¹¹««\x9c\x8e\x8e\x8e'
22
+ '\x8e\x8e\x8eä\x80\x8e\x8e\x8e\x8eGGGG\x8e\x8e\x8e\x8e\x8e\x8e\x8eò\x8d\x9c\x8e\x8e\x8e\x8e\x80\x8e\x80Ā99ZĀ0[\x18\x18'
23
+ , 294, 192),
24
+ 'Arial Black': (
25
+ 'UU\x80©«ĀäGdd\x8e©UUUG««««««««««UU©©©\x9c¾ÇÇÇǹ«ÕÕd«Õ«òÕÕ¹Õǹ¹ÕÇĀÇǹdGd©\x80U«««««d««UU«'
26
+ 'UĀ««««r\x9cr«\x9cò«\x9c\x8edGd©U««©«G«Í«©Íf©ff«ÚUf«\x9cÇÇÇÇÇÇĀǹ¹¹¹ddddÇÕÕÕÕÕÕĀ©ÕÕÕÕÕǹ««««'
27
+ '«««Ā«««««UUUU«««««««Ā©«««««\x9c«\x9cĀGG\x80ĀN\x86\x18\x18'
28
+ , 361, 192),
29
+ 'Comic Sans MS': (
30
+ 'M=mزҨc^^\x88{Gk@\x83\x9cs\x9c\x9c\x9c\x9c\x9c\x9c\x9c\x9cMMb\x83b\x86\x9a¹\xa0\x9b®Å\x8cª\x9c\x8dâÌÌ\x85ࡲ®½¦Ċ¹£²`\x8d`\x95¡\x8e\x83\x98\x84\x96\x8c\x82\x88\x94Hg\x8a'
31
+ 'FÇ\x86\x87\x89\x85{}y\x85}¯\x97\x85\x8a^l^\x99=\xa0Ë\x9d£h£Ì\x94{Ìi{§§\x85²@s\x94\x86»»»»»»Ė\x9a\xa0\xa0\xa0\xa0\x8c\x8c\x8c\x8c¹ÌÌÌÌÌÌIJ{̽½½½£\x85r\x83\x83\x83'
32
+ '\x83\x83\x83é\x84\x8c\x8c\x8c\x8cHHHH\x82\x86\x87\x87\x87\x87\x87æ{\x87\x85\x85\x85\x85\x85\x89nâ..c\xad.U\x0f\x0f'
33
+ , 357, 122),
34
+ 'Copperplate': (
35
+ 'NUU\x9c\x9cä¹9dd\x80\x9aNUNG\x9c\x9c\x9c\x9c\x9c\x9c\x9c\x9c\x9c\x9cNN\x9a\x9a\x9ar\x9a«¹¹¹«\x9c¹ÇU\x80«\x9cÕÇǫǹ«\x9c¹«ò«\x9c\x9cdGd\x9a\x80U\x8e\x9c\x8e\x9c\x8e\x8e\x9c«Ur\x8e'
36
+ '\x8e¹«\x9c\x8e\x9c\x9c\x8e\x80«\x8eÇ\x8e\x8e\x8ed9d\x9aU\x9c\x9c\x9c\x9c9\x80\x9a\x80\x9a\x9af\x9a^^«\x9aN^\x80r««««««Ā¹««««UUUU¹ÇÇÇÇÇÇĀ\x9aǹ¹¹¹\x9c«ĝ\x8e\x8e\x8e'
37
+ '\x8e\x8e\x8eä\x8e\x8e\x8e\x8e\x8eUUUU\x9c«\x9c\x9c\x9c\x9c\x9cò\x9a\x9c««««\x8e\x8e\x8eĀGG\x80Ā!!!!'
38
+ , 264, 128),
39
+ 'Courier New': (
40
+ '\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a'
41
+ '\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a'
42
+ '\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x13\x13'
43
+ , 290, 154),
44
+ 'Futura': (
45
+ 'OUi\x9e\x9eë»;^^\x9e\x9eO8O\x85\x9e\x9e\x9e\x9e\x9e\x9e\x9e\x9e\x9e\x9eOO\x9e\x9e\x9e}á¾\x97³º\x91\x82ؼLiªröØå\x8aå\x9a\x95|½\xadĐ\x9e\x9a\xa0\\\x85\\\x91\x91\x91\x9a\x9az\x9a\x8eL\x99\x8c@@\x80'
46
+ '@Ë\x8c\x9a\x9a\x9a`hF\x8c\x81Æ\x8f\x8b\x8b\\\x91\\ÁU\x9e\x9e\x9e\x9e\x91\x9eÜ\x93\x91ܤ\x9epp\x8c\x9eOi\x93}¾¾¾¾¾¾Č³\x91\x91\x91\x91LLLLºØåååååį\x9eå½½½½\x9a\x8a\x9f\x9a\x9a\x9a'
47
+ '\x9a\x9a\x9aÜz\x8e\x8e\x8e\x8e@@@@\x9a\x8c\x9a\x9a\x9a\x9a\x9aô\x9e\x9a\x8c\x8c\x8c\x8c\x8b\x9a\x8b§TTÁò\x10\x10\x10\x10'
48
+ , 340, 128),
49
+ 'Geneva': (
50
+ 'UN\x80««èºNrr\x82«NaN\x8a««««««««««NN«««\x92ߺ£§³\x93\x8e\xad±>~ª\x95ʵ¼\x95¼\x9b\x9b¤«ºò\x9c\x9c\x93r\x8ar««\x97\x8e\x9c\x8c\x9a\x93d\x9c\x95<G\x8a'
51
+ '<å\x95\x9b\x9a\x9ac\x82r\x95\x91È\x88\x92\x8es?s«N««««?«á\x89«áW«gg\x97««_\x89\x92ººººººþ§\x93\x93\x93\x93>>>>³µ¼¼¼¼¼ė«¼««««\x9c\x95\x97\x8e\x8e\x8e'
52
+ '\x8e\x8e\x8eî\x8c\x93\x93\x93\x93<<<<\x98\x95\x9b\x9b\x9b\x9b\x9bÿ«\x9b\x95\x95\x95\x95\x92\x9a\x92ĈNN«Ĉ\x85¨\x85¨'
53
+ , 341, 128),
54
+ 'Georgia': (
55
+ '>Ui¥\x9cѶ7``y¥E`Ex\x9dn\x8f\x8d\x91\x87\x91\x81\x99\x91PP¥¥¥{¤À§\x99ºÑd\x85²\x9bíÄ¿\x9c¿´\x90\x9e«ú¶\x9e\x9a`x`¥¥\x80\x81\x8ft\x93|S\x82\x95KK\x89'
56
+ 'Iâ\x97\x8a\x92\x8fioX\x93\x7f½\x81~rn`n¥U\x8e\x9f\x92\x9d`\x80ñ\x95¥ñk¥\x80\x80\x94\x80H\x80\x95{¬¬¬¬¬¬ù¤§§§§ddddÀÄ¿¿¿¿¿Ā¥¿ÂÂÂÂ\x9e\x9d\x8c\x81\x81\x81'
57
+ '\x81\x81\x81½t||||KKKK\x88\x97\x8a\x8a\x8a\x8a\x8aÑ¥\x8a\x93\x93\x93\x93~\x8f~Û::eÏR\x84 '
58
+ , 291, 256),
59
+ 'Gill Sans': (
60
+ 'GE[\x96\x8b\xad\xa00SSk\x968S8H\x80\x80\x80\x80\x80\x80\x80\x80\x80\x808;\x96\x96\x96Uă«\x90µÀ\x80x¾»@@¨~ÈÈÓ\x83Ó\x9bu\x9bµ\x9bċµ\x9b¥UHUx\x8dUm\x80p\x83{@m\x8088{'
61
+ '8Å\x80\x8d\x80\x80ecU\x80p¸\x80pkUCU\x95Ep\x88\x8d\x8dCh¾~\x96¾e\x96SS\x8d\x8bU^~U««««««åµ\x80\x80\x80\x80@@@@ÀÈÓÓÓÓÓë\x96Óµµµµ\x9b\x83\x80mmm'
62
+ 'mmm«p{{{{8888\x90\x80\x8d\x8d\x8d\x8d\x8dÕ\x96\x8d\x80\x80\x80\x80p\x80pĀ88[Ā '
63
+ , 294, 256),
64
+ 'Helvetica': (
65
+ 'GG[\x8e\x8eä«1UUd\x96GUGG\x8e\x8e\x8e\x8e\x8e\x8e\x8e\x8e\x8e\x8eGG\x96\x96\x96\x8eĄ««¹¹«\x9cǹG\x80«\x8eչǫǹ«\x9c¹«ò««\x9cGGGx\x8eU\x8e\x8e\x80\x8e\x8eG\x8e\x8e99\x80'
66
+ '9Õ\x8e\x8e\x8e\x8eU\x80G\x8e\x80¹\x80\x80\x80VCV\x96U\x8e\x8e\x8e\x8eC\x8e½\x8e\x96½f\x8dUU\x94\x8aG^\x8e\x9c««««««Ā¹««««GGGG¹¹ÇÇÇÇÇĀ\x96ǹ¹¹¹««\x9c\x8e\x8e\x8e'
67
+ '\x8e\x8e\x8eä\x80\x8e\x8e\x8e\x8eGGGG\x8e\x8e\x8e\x8e\x8e\x8e\x8eò\x8d\x9c\x8e\x8e\x8e\x8e\x80\x8e\x80Ā99ZĀU\x86U\x86'
68
+ , 256, 162),
69
+ 'Liberation Sans': (
70
+ 'GG[\x8e\x8eä«1UUd\x96GUGG\x8e\x8e\x8e\x8e\x8e\x8e\x8e\x8e\x8e\x8eGG\x96\x96\x96\x8eĄ««¹¹«\x9cǹG\x80«\x8eչǫǹ«\x9c¹«ò««\x9cGGGx\x8eU\x8e\x8e\x80\x8e\x8eG\x8e\x8e99\x80'
71
+ '9Õ\x8e\x8e\x8e\x8eU\x80G\x8e\x80¹\x80\x80\x80VCV\x96U\x8e\x8e\x8e\x8eC\x8e½\x8e\x96½f\x8dUU\x94\x8aU^\x8e\x9c««««««Ā¹««««GGGG¹¹ÇÇÇÇÇĀ\x96ǹ¹¹¹««\x9c\x8e\x8e\x8e'
72
+ '\x8e\x8e\x8eä\x80\x8e\x8e\x8e\x8eGGGG\x8e\x8e\x8e\x8e\x8e\x8e\x8eò\x8d\x9c\x8e\x8e\x8e\x8e\x80\x8e\x80Ā99ZĀ0[\x18\x18'
73
+ , 294, 192),
74
+ 'Liberation Serif': (
75
+ '@Ui\x80\x80ÕÇ.UU\x80\x90@U@G\x80\x80\x80\x80\x80\x80\x80\x80\x80\x80GG\x90\x90\x90r칫«¹\x9c\x8e¹¹Ud¹\x9cä¹¹\x8e¹«\x8e\x9c¹¹ò¹¹\x9cUGUx\x80Ur\x80r\x80rU\x80\x80GG\x80'
76
+ 'GÇ\x80\x80\x80\x80UdG\x80\x80¹\x80\x80r{3{\x8bU\x80\x80\x80\x803\x80Ã\x80\x90Ãf\x8dMM\x94tUO\x80r¹¹¹¹¹¹ä«\x9c\x9c\x9c\x9cUUUU¹¹¹¹¹¹¹ä\x90¹¹¹¹¹¹\x8e\x80rrr'
77
+ 'rrr«rrrrrGGGG\x80\x80\x80\x80\x80\x80\x80¹\x8d\x80\x80\x80\x80\x80\x80\x80\x80ĀUUZĀ8k\x19\x19'
78
+ , 294, 199),
79
+ 'Monaco': (
80
+ '\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a'
81
+ '\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a'
82
+ '\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a\x9a'
83
+ , 341, 154),
84
+ 'Skia': (
85
+ '@w_±lý»6jj]±CWCU\x9fb\x83v\x96{\x93|\x94\x93RR±±±\x8f檤\x94»\x9b\x92°ÈO`¢\x8aòÊÂ\x91¢\x81\x92ÁªČ\x9d\x94\x99jUj±\x80d\x84\x8et\x8e\x83^\x8d\x95DE\x86'
86
+ 'Dà\x95\x92\x8e\x8echd\x95\x88Î\x81\x89zjKj±wu|\x96\x94Ktñ\x83±ñi±ii\x9c\x8eCi\x83\x8fªªªªªªé\x94\x9b\x9b\x9b\x9bOOOO»ÊÂÂÂÂÂþáÂÁÁÁÁ\x94\x91\x9a\x84\x84\x84'
87
+ '\x84\x84\x84Ït\x83\x83\x83\x83DDDD\x8d\x95\x92\x92\x92\x92\x92ç±\x92\x95\x95\x95\x95\x89\x8e\x89Ā66\x8eĀ\x17\x17\x17\x17'
88
+ , 256, 186),
89
+ 'Times New Roman': (
90
+ '@Ui\x80\x80ÕÇ.UU\x80\x90@U@G\x80\x80\x80\x80\x80\x80\x80\x80\x80\x80GG\x90\x90\x90r칫«¹\x9c\x8e¹¹Ud¹\x9cä¹¹\x8e¹«\x8e\x9c¹¹ò¹¹\x9cUGUx\x80Ur\x80r\x80rU\x80\x80GG\x80'
91
+ 'GÇ\x80\x80\x80\x80UdG\x80\x80¹\x80\x80r{3{\x8bU\x80\x80\x80\x803\x80Ã\x80\x90Ãf\x8dMM\x94tUO\x80r¹¹¹¹¹¹ä«\x9c\x9c\x9c\x9cUUUU¹¹¹¹¹¹¹ä\x90¹¹¹¹¹¹\x8e\x80rrr'
92
+ 'rrr«rrrrrGGGG\x80\x80\x80\x80\x80\x80\x80¹\x8d\x80\x80\x80\x80\x80\x80\x80\x80ĀUUZĀ8k\x19\x19'
93
+ , 294, 199),
94
+ 'Trebuchet MS': (
95
+ 'M^S\x86\x86\x9aµ)^^^\x86^^^\x86\x86\x86\x86\x86\x86\x86\x86\x86\x86\x86^^\x86\x86\x86^Å\x97\x91\x99\x9d\x89\x86\xad¨Gz\x93\x82¶£\xad\x8f\xad\x95{\x95¦\x96Ú\x8f\x92\x8d^[^\x86\x86\x86\x87\x8f\x7f\x8f\x8c_\x81\x8cI^\x81'
96
+ 'LÕ\x8c\x89\x8f\x8fdhf\x8c}¿\x80~z^\x86^\x86^\x86\x86\x86\x92\x86t·\x86\x86·\x86\x86tt\x8c\x86^^\x86^\x97\x97\x97\x97\x97\x97Þ\x99\x89\x89\x89\x89GGGG\x9d£\xad\xad\xad\xad\xadþ\x86¨¦¦¦¦\x92\x8e\x8c\x87\x87\x87'
97
+ '\x87\x87\x87à\x7f\x8c\x8c\x8c\x8cIIII\x8d\x8c\x89\x89\x89\x89\x89í\x86\x8c\x8c\x8c\x8c\x8c~\x8e~¼^^\x86¼)W\x0c\x0c'
98
+ , 297, 94),
99
+ 'Verdana': (
100
+ 'ZevÒ£ĔºEtt£Ò]t]t££££££££££ttÒÒÒ\x8c°³Å¢\x93ÇÀlt±\x8fØÀÊ\x9aʲ¯\x9e»¯ý¯\x9e¯tttÒ££\x9a\xa0\x85\xa0\x99Z\xa0¢FX\x98'
101
+ 'Fù¢\x9b\xa0\xa0m\x85e¢\x98Ò\x98\x98\x87£t£Òe££££t£Ā¥ÒĀ\x8bÒ\x8b\x8b¤£]\x8c¥\x8c¯¯¯¯¯¯ü³¢¢¢¢llllÇÀÊÊÊÊÊĒÒÊ»»»»\x9e\x9b\x9f\x9a\x9a\x9a'
102
+ '\x9a\x9a\x9aõ\x85\x99\x99\x99\x99FFFF\x9d¢\x9b\x9b\x9b\x9b\x9bûÒ\x9b¢¢¢¢\x98\xa0\x98ĀEE\x8cÒ]\x8f '
103
+ , 311, 256),
104
+ }
105
+
106
+
107
+ #: Codepoints the measured fonts do not contain, and which therefore fall
108
+ #: back to the default width. Recorded so that a comparison against
109
+ #: another font table can tell a real discrepancy from a missing glyph.
110
+ ABSENT = {
111
+ 'Arial': '‵‶',
112
+ 'Arial Black': '‵‶',
113
+ 'Comic Sans MS': '‵‶',
114
+ 'Copperplate': '′″‵‶',
115
+ 'Courier New': '‵‶',
116
+ 'Futura': '′″‵‶',
117
+ 'Georgia': '‵‶',
118
+ 'Gill Sans': '′″‵‶',
119
+ 'Liberation Sans': '‵‶',
120
+ 'Liberation Serif': '‵‶',
121
+ 'Skia': '′″‵‶',
122
+ 'Times New Roman': '‵‶',
123
+ 'Trebuchet MS': '‵‶',
124
+ 'Verdana': '‵‶',
125
+ }
126
+
127
+ #: Extra width factor applied on top of the raw advances.
128
+ CORRECTIONS = {
129
+ 'Arial': 1.05,
130
+ 'Times New Roman': 1.04,
131
+ 'Trebuchet MS': 1.025,
132
+ }
133
+
134
+ #: Per-character nudges, in 1/256 em, applied when encoding.
135
+ NUDGE = {
136
+ }
137
+