예제 #1
0
def printRange(rangeName, toFile=None):
    out = [
        "{0:<50s}{1:<30}{2:<30}{3}{4:<5}{5}".format("Generated Name", "AGD", "Glyphs", "uni    ", " ", "uni name"),
        ""

    ]
    for u in range(*_rangeNameToRange(rangeName)):
        g = GlyphName(uniNumber=u)
        name = g.getName()
        if name is None:
            continue
        AGDName = unicode2name_AGD.get(g.uniNumber)
        if AGDName is None:
            AGDName = "-"
        elif AGDName == name:
            AGDName = u"�"
        GLYPHSName = unicode2name_GLYPHS.get(g.uniNumber)
        if GLYPHSName is None:
            GLYPHSName = "-"
        elif GLYPHSName == name:
            GLYPHSName = ""
        txt = name.ljust(50)
        txt += AGDName.ljust(30)
        txt += GLYPHSName.ljust(30)
        txt += "%04X   " % g.uniNumber
        txt += g.uniLetter.ljust(5)
        txt += g.uniName
        out.append(txt)
    out = "\n".join(out)
    if toFile:
        toFile.write(out)
    else:
        print(out)
    testDoubles(rangeName, toFile)
    testGLIFFileName(rangeName, toFile)
예제 #2
0
def printRange(rangeName, toFile=None):
    out = []
    for u in range(*_rangeNameToRange(rangeName)):
        g = GlyphName(uniNumber=u)
        name = g.getName()
        if name is None:
            continue
        AGDName = unicode2name_AGD.get(g.uniNumber)
        if AGDName is None:
            AGDName = "-"
        elif AGDName == name:
            AGDName = u"👍"
        txt = name.ljust(50)
        txt += AGDName.ljust(30)
        txt += "%04X   " % g.uniNumber
        txt += g.uniLetter.ljust(5)
        txt += g.uniName
        out.append(txt)
    out = "\n".join(out)
    out = out.encode("utf-8")
    if toFile:
        toFile.write(out)
    else:
        print(out)
    testDoubles(rangeName, toFile)
    testGLIFFileName(rangeName, toFile)
def generateFlat(path,
                 onlySupported=True,
                 scriptSeparator=None,
                 scriptAsPrefix=None,
                 status=0,
                 includeUnicodeCategory=False):
    data = [
        "# Glyph Name Formatted Unicode List - GNFUL",
        "# GlyphNameFormatter version %s" % _versionNumber,
        "# Unicode version: %s" % unicodeVersion,
        "# Source code: %s" % _githubLink,
        "# Generated on %s" % time.strftime("%Y %m %d %H:%M:%S"),
    ]
    if includeUnicodeCategory:
        data.append("# <glyphName> <hex unicode> <unicodeCategory>")
    else:
        data.append("# <glyphName> <hex unicode>")
    if scriptSeparator is not None:
        data.append("# Separator \"%s\"" % scriptSeparator)
    if scriptAsPrefix is not None:
        data.append("# Prefixed \"%s\"" % scriptAsPrefix)
    data.append("#")
    for rangeName in getAllRangeNames():
        if onlySupported:
            moduleName = rangeNameToModuleName(rangeName)
            try:
                module = importlib.import_module(
                    'glyphNameFormatter.rangeProcessors.%s' % moduleName)
            except:
                continue
        data.append("# %s" % rangeName)
        start, end = getRangeByName(rangeName)
        for u in range(start, end + 1):
            g = GlyphName(uniNumber=u,
                          scriptSeparator=scriptSeparator,
                          scriptAsPrefix=scriptAsPrefix)
            g.compress()  # should auto compress
            if status is not None:
                if g.status < status:
                    # if the glyph has a status that is less than what we're looking for
                    # then do not include it in the list.
                    continue
            name = g.getName(extension=True)
            if name is None:
                continue
            if includeUnicodeCategory:
                data.append("%s %04X %s" %
                            (name, u, unicodeCategories.get(u, "-")))
            else:
                data.append("%s %04X" % (name, u))

    f = open(path, "w")
    f.write("\n".join(data))
    f.close()
def generateFlat(path, onlySupported=True, scriptSeparator=None, scriptAsPrefix=None, status=0, includeUnicodeCategory=False):
    data = [
        "# Glyph Name Formatted Unicode List - GNFUL",
        "# GlyphNameFormatter version %s" % _versionNumber,
        "# Unicode version: %s" % unicodeVersion,
        "# Source code: %s" % _githubLink,
        "# Generated on %s" % time.strftime("%Y %m %d %H:%M:%S"),
    ]
    if includeUnicodeCategory:
        data.append("# <glyphName> <hex unicode> <unicodeCategory>")
    else:
        data.append("# <glyphName> <hex unicode>")
    if scriptSeparator is not None:
        data.append("# Separator \"%s\"" % scriptSeparator)
    if scriptAsPrefix is not None:
        data.append("# Prefixed \"%s\"" % scriptAsPrefix)
    data.append("#")
    for rangeName in getAllRangeNames():
        if onlySupported:
            moduleName = rangeNameToModuleName(rangeName)
            try:
                module = importlib.import_module('glyphNameFormatter.rangeProcessors.%s' % moduleName)
            except:
                continue
        data.append("# %s" % rangeName)
        start, end = getRangeByName(rangeName)
        for u in range(start, end+1):
            g = GlyphName(uniNumber=u, scriptSeparator=scriptSeparator, scriptAsPrefix=scriptAsPrefix)
            g.compress()  # should auto compress
            if status is not None:
                if g.status < status:
                    # if the glyph has a status that is less than what we're looking for
                    # then do not include it in the list.
                    continue
            name = g.getName(extension=True)
            if name is None:
                continue
            if includeUnicodeCategory:
                data.append("%s %04X %s" % (name, u, unicodeCategories.get(u, "-")))
            else:
                data.append("%s %04X" % (name, u))


    f = open(path, "w")
    f.write("\n".join(data))
    f.close()
예제 #5
0
def testGLIFFileName(rangeName, toFile=None):
    """
    test on glif file name
    """
    # support both UFO2 as UFO3
    try:
        # UFO3 ufoLib
        from fontTools.ufoLib.filenames import userNameToFileName

        def nameToFileName(name):
            return userNameToFileName(name)
    except:
        # UFO2 robofab
        from robofab.tools.glyphNameSchemes import glyphNameToShortFileName

        def nameToFileName(name):
            return glyphNameToShortFileName(name, None)
    existing = set()
    doubles = set()
    r = _rangeNameToRange(rangeName)
    for u in range(*r):
        g = GlyphName(uniNumber=u)
        name = g.getName()
        if name is None:
            # ignore
            continue
        glifFileName = nameToFileName(name)
        if glifFileName in existing:
            doubles.add(glifFileName)
        else:
            existing.add(glifFileName)
    if doubles:
        rangeText = "%04X - %04X" % (r[0], r[1])
        txt = "\n\ndouble glif file names for range %s:\n\t%s" % (rangeText, "\n\t".join(sorted(doubles)))

        if toFile:
            toFile.write(txt)
        else:
            print(txt)
예제 #6
0
def testGLIFFileName(rangeName, toFile=None):
    """
    test on glif file name
    """
    # support both UFO2 as UFO3
    try:
        # UFO3 ufoLib
        from ufoLib.filenames import userNameToFileName

        def nameToFileName(name):
            return userNameToFileName(unicode(name))
    except:
        # UFO2 robofab
        from robofab.tools.glyphNameSchemes import glyphNameToShortFileName

        def nameToFileName(name):
            return glyphNameToShortFileName(name, None)
    existing = set()
    doubles = set()
    r = _rangeNameToRange(rangeName)
    for u in range(*r):
        g = GlyphName(uniNumber=u)
        name = g.getName()
        if name is None:
            # ignore
            continue
        glifFileName = nameToFileName(name)
        if glifFileName in existing:
            doubles.add(glifFileName)
        else:
            existing.add(glifFileName)
    if doubles:
        rangeText = "%04X - %04X" % (r[0], r[1])
        txt = "\n\ndouble glif file names for range %s:\n\t%s" % (rangeText, "\n\t".join(sorted(doubles)))

        if toFile:
            toFile.write(txt)
        else:
            print(txt)
예제 #7
0
def generateFlat(path, onlySupported=True):
    data = [
        "# format",
        "# <glyphName> <hex unicode>"
    ]
    for rangeName in getAllRangeNames():
        if onlySupported:
            moduleName = rangeNameToModuleName(rangeName)
            try:
                module = importlib.import_module('glyphNameFormatter.rangeProcessors.%s' % moduleName)
            except:
                continue
        data.append("# %s" % rangeName)
        for u in range(*getRangeByName(rangeName)):
            g = GlyphName(uniNumber=u)
            name = g.getName(extension=True)
            if name is None:
                continue
            data.append("%s %04X" % (name, u))

    f = open(path, "w")
    f.write("\n".join(data))
    f.close()
예제 #8
0
def printRange(rangeName, toFile=None):
    out = [
        "{0:<50s}{1:<30}{2:<30}{3}{4:<5}{5}".format("Generated Name", "AGD", "Glyphs", "uni    ", " ", "uni name"),
        ""

    ]
    for u in range(*_rangeNameToRange(rangeName)):
        g = GlyphName(uniNumber=u)
        name = g.getName()
        if name is None:
            continue
        AGDName = unicode2name_AGD.get(g.uniNumber)
        if AGDName is None:
            AGDName = "-"
        elif AGDName == name:
            AGDName = u"�"
        GLYPHSName = unicode2name_GLYPHS.get(g.uniNumber)
        if GLYPHSName is None:
            GLYPHSName = "-"
        elif GLYPHSName == name:
            GLYPHSName = ""
        txt = name.ljust(50)
        txt += AGDName.ljust(30)
        txt += GLYPHSName.ljust(30)
        txt += "%04X   " % g.uniNumber
        txt += g.uniLetter.ljust(5)
        txt += g.uniName
        out.append(txt)
    out = "\n".join(out)
    if PY2:
        out = out.encode("utf-8")
    if toFile:
        toFile.write(out)
    else:
        print(out)
    testDoubles(rangeName, toFile)
    testGLIFFileName(rangeName, toFile)
예제 #9
0
def testDoubles(rangeName, toFile=None):
    """
    test if there are doubles
    """
    names = set()
    doubles = set()
    r = _rangeNameToRange(rangeName)
    for u in range(*r):
        g = GlyphName(uniNumber=u)
        name = g.getName()
        if name is None:
            # ignore
            continue
        if name in names:
            doubles.add(name)
        else:
            names.add(name)
    if doubles:
        rangeText = "%04X - %04X" % (r[0], r[1])
        txt = "\n\ndouble names for range %s:\n\t%s" % (rangeText, "\n\t".join(sorted(doubles)))
        if toFile:
            toFile.write(txt)
        else:
            print(txt)
예제 #10
0
def testDoubles(rangeName, toFile=None):
    """
    test if there are doubles
    """
    names = set()
    doubles = set()
    r = _rangeNameToRange(rangeName)
    for u in range(*r):
        g = GlyphName(uniNumber=u)
        name = g.getName()
        if name is None:
            # ignore
            continue
        if name in names:
            doubles.add(name)
        else:
            names.add(name)
    if doubles:
        rangeText = "%04X - %04X" % (r[0], r[1])
        txt = "\n\ndouble names for range %s:\n\t%s" % (rangeText, "\n\t".join(sorted(doubles)))
        if toFile:
            toFile.write(txt)
        else:
            print(txt)
from glyphNameFormatter import GlyphName
from glyphNameFormatter.unicodeRangeNames import *

greekSymbols = []
pi = []
theta = []
for name in getAllRangeNames():
    if name in [
            'Ancient Greek Musical Notation',
            'Mathematical Alphanumeric Symbols'
    ]:
        continue
    a, b = getRangeByName(name)
    for uniNumber in range(a, b):
        g = GlyphName(uniNumber)
        if g.uniName is None: continue
        if "GREEK" in g.uniName and g.isMath:
            greekSymbols.append(g)

        if "GREEK" in g.uniName and ("LETTER PI" in g.uniName
                                     or "PI SYMBOL" in g.uniName):
            pi.append(g)

        if "GREEK" in g.uniName and ("LETTER THETA" in g.uniName
                                     or "THETA SYMBOL" in g.uniName):
            theta.append(g)

print("\n\ngreek and math")
for g in greekSymbols:
    print(g, g.uniRangeName, g.isMath)
예제 #12
0
def testCoverage():
    uncountables = ['Hangul Syllables', 'CJK Unified Ideographs', 'Private']
    uncounted = []
    text = []
    text.append("\n\n# Coverage")
    wantRanges = {}
    glyphCount = {}
    for thisRange in getAllRangeNames():
        a, b = getRangeByName(thisRange)
        countThis = True
        for uc in uncountables:
            if thisRange.find(uc) != -1:
                uncounted.append(" * %s" % thisRange)
                print(thisRange, "uncountable")
                countThis = False

        moduleName = rangeNameToModuleName(thisRange)
        if thisRange not in glyphCount:
            glyphCount[thisRange] = {
                'nameable': 0,
                'uniNames': 0,
                'total': b - a,
                'rangeProcessor': None
            }
        try:
            module = importlib.import_module(
                'glyphNameFormatter.rangeProcessors.%s' % moduleName)
            glyphCount[thisRange]['rangeProcessor'] = True
        except ImportError:
            pass
        for uniNumber in range(a, b):
            g = GlyphName(uniNumber)
            if g.uniName is not None:
                glyphCount[thisRange]['uniNames'] += 1
                if countThis:
                    glyphCount[thisRange]['nameable'] += 1

    totalGlyphs = 0  # the total of all glyph counts in all ranges
    totalCovered = 0  # the total of all glyphs that this package has rangeprocessors for
    totalPoints = 0  # the total of all ranges
    totalNameable = 0  # the total of all glyphs that can be named

    for key, items in glyphCount.items():
        #print(key, items)
        totalGlyphs += items['uniNames']
        totalPoints += items['total']
        if items['rangeProcessor'] is not None:
            totalCovered += items['uniNames']
            totalNameable += items['nameable']

    text = []
    text.append("")
    text.append("## Version %s" % unicodeVersion)
    text.append("\n\n\n")
    text.append("### Note:\n")
    text.append("This coverage page is has some issues.\n")
    text.append(
        " * Most of the Unicode data is downloaded from Unicode.org. Only the bidirectional data still depends on the Python unicodedata module.."
    )
    text.append(
        " * Narrow build Python might also leave some names inaccessible.")
    text.append(
        " * Not all ranges need to count. Private Use ranges are ignored, perhaps others need to as well."
    )
    text.append("\n\n\n")

    # if uncounted:
    #     text.append("The following ranges are skipped:")
    #     for line in uncounted:
    #         text.append(line)

    # text.append("\n\n\n")
    # text.append("| Stats                                      | :)        |")
    # text.append("| ------------------------------------------ | --------: |")
    # text.append('| Total code points in the available ranges  |   `%d`    |'%totalPoints)
    # text.append('| Total glyphs in the available ranges       |   `%d`    |'%totalGlyphs)
    # text.append('| Total glyphs that can be named             |   `%d`    |'%totalNameable)
    # text.append('| Total names covered in GlyphNameFormatter  | `%d`      |'%totalCovered)
    # text.append('| Progress                                   | `%3.3f%%` |'%(100.0*totalCovered/totalGlyphs))

    text.append("\n\n\n")
    text.append("| Range name | # | has processor | Start | End |")
    text.append("| ----- | ----- |----- | ----- | ----- |")

    for thisRange in getAllRangeNames():
        if not thisRange in glyphCount: continue
        a, b = getRangeByName(thisRange)
        items = glyphCount[thisRange]
        if items['rangeProcessor'] != None:
            has = "**Yes**"
            n = "**%s**" % items['uniNames']
        else:
            has = "No"
            n = items['uniNames']
        text.append("| %s | %s | %s | `%04X` | `%04X` |" %
                    (thisRange, n, has, a, b))

    text.append("\n\n")
    path = "../../../coverage.md"
    f = open(path, 'w')
    f.write("\n".join(text))
    f.close()
예제 #13
0
        if name is None:
            # ignore
            continue
        glifFileName = nameToFileName(name)
        if glifFileName in existing:
            doubles.add(glifFileName)
        else:
            existing.add(glifFileName)
    if doubles:
        rangeText = "%04X - %04X" % (r[0], r[1])
        txt = "\n\ndouble glif file names for range %s:\n\t%s" % (rangeText, "\n\t".join(sorted(doubles)))

        if toFile:
            toFile.write(txt)
        else:
            print(txt)


if __name__ == "__main__":
    from glyphNameFormatter.unicodeRangeNames import getAllRangeNames

    # time test
    import time
    t = time.time()
    for rangeName in getAllRangeNames():
        r = _rangeNameToRange(rangeName)
        for u in range(*r):
            g = GlyphName(uniNumber=u)
            name = g.getName()
    print(time.time() - t)
예제 #14
0
            print("ERROR: unknown ligature structure")
            print("\n", self.uniName)
            print("\t", len(ligatureParts), ligatureParts[0])
            print("\t", ligatureType)
            return
        # assembly
        self.uniNameProcessed = ""
        ligaName = []
        for p in ligatureParts:
            ligaName.append("".join(p).lower())
        self.uniNameProcessed = "_".join(ligaName)


if __name__ == "__main__":
    from glyphNameFormatter import GlyphName
    assert GlyphName(uniNumber=0xFDFA).getName() == "SallallahouAlayheWasallam"
    assert GlyphName(
        uniNumber=0xFDC4).getName() == "ain.init_jeem.medi_meem.medi"
    assert GlyphName(
        uniNumber=0xFC5D).getName() == "alefmaksura.init_superscriptalef.fina"
    assert GlyphName(uniNumber=0xFC40).getName() == "lam.init_hah.fina"
    assert GlyphName(uniNumber=0xFBFC).getName() == "yehfarsi.isol"

    print("\ndoNotProcessAsLigatureRanges", doNotProcessAsLigatureRanges)
    odd = 0xfe76
    for a, b in doNotProcessAsLigatureRanges:
        print('\nrange:', hex(a), hex(odd), hex(b))
        print(a <= odd <= b, )
        for u in range(a, b + 1):
            try:
                g = GlyphName(uniNumber=u)
예제 #15
0
# Make a new font
nf = NewFont("NES")

# convert the hex value to decimal
start = int(HEX, 16)

amount = len(glyphOrder) * 2  # x2 because of the empty sprites inbetween

for i in range(amount):
    if i % 2 != 0: continue  # skip those empty inbetweens

    # we draw pixels upwards on a rows and than decrement the row.
    y = pixelSize * 7

    name = GlyphName(ord(glyphOrder[floor(i / 2)])).getName()
    if name == "at": continue

    # ng = new glyph
    ng = nf.newGlyph(name)
    ng.autoUnicodes()  # add unicode
    ng.width = pixelSize * 8

    for b in fnt[start + (i * 8):start + ((i + 1) * 8)]:  # fetch a byte
        c = ("{0:b}".format(b).zfill(8))  # int to binary
        for x, bit in enumerate(c):  # loop the bits
            if bit == "1":  # <-- make it "0" to make a cameo font
                path = BezierPath()
                path.rect(x * pixelSize, y, pixelSize, pixelSize)

                # draw the path in the glyph
예제 #16
0
        if name is None:
            # ignore
            continue
        glifFileName = nameToFileName(name)
        if glifFileName in existing:
            doubles.add(glifFileName)
        else:
            existing.add(glifFileName)
    if doubles:
        rangeText = "%04X - %04X" % (r[0], r[1])
        txt = "\n\ndouble glif file names for range %s:\n\t%s" % (rangeText, "\n\t".join(sorted(doubles)))

        if toFile:
            toFile.write(txt)
        else:
            print(txt)


if __name__ == "__main__":
    from glyphNameFormatter.unicodeRangeNames import getAllRangeNames

    # time test
    import time
    t = time.time()
    for rangeName in getAllRangeNames():
        r = _rangeNameToRange(rangeName)
        for u in range(*r):
            g = GlyphName(uniNumber=u)
            name = g.getName()
    print(time.time() - t)
예제 #17
0
def process(self):
    self.edit("GREEK PROSGEGRAMMENI", "iotaadscript")
    self.processAs("Greek and Coptic")
    self.compress()

if __name__ == "__main__":
    from glyphNameFormatter.exporters import printRange
    printRange("Greek Extended")

    # https://github.com/LettError/glyphNameFormatter/issues/38
    from glyphNameFormatter import GlyphName
    g = GlyphName(0x1FBE)
    assert g.getName() == "iotaadscript"
            self.replace('FINAL FORM', "fina")
            self.replace('ISOLATED FORM', "isol")
            self.replace('WITH SUPERSCRIPT', "")
            self.replace('WITH', "")
            self.replace("LIGATURE", "")
            self.replace("ARABIC", "")
            self.replace("SYMBOL", "")
            self.replace("LETTER", "")
            self.lower()
            self.camelCase()
            return True

    return False


if __name__ == "__main__":
    from glyphNameFormatter import GlyphName

    print("\ndoNotProcessAsLigatureRanges", doNotProcessAsLigatureRanges)
    odd = 0xfe76
    for a, b in doNotProcessAsLigatureRanges:
        for u in range(a,b+1):
            try:
                g = GlyphName(uniNumber=u)
                n = g.getName()
                print(hex(u), n, g.uniName)
                
            except:
                import traceback
                traceback.print_exc()
예제 #19
0
    with open(namFilePath, "r", encoding="utf-8") as namFile:
        lines = namFile.read()
        for line in lines.split("\n"):
            if len(line):
                if line.startswith(" "):
                    unistr = None
                    character = None
                    description = None
                    name = line.replace(" ", "")
                elif line.startswith("0x"):
                    lineSplit = line.split(" ")
                    unistr = lineSplit[0]
                    uni = int(unistr, 16)
                    character = lineSplit[1]
                    description = " ".join(lineSplit[2:])
                    gn = GlyphName(uni)
                    name = gn.getName()
                # Format the entry
                if not name in allNames:
                    if not name or not name.endswith(".sc"):
                        allGlyphInfo.append([
                            name, unistr, character, description, namCategory,
                            optional
                        ])
                        allNames.append(name)

# My custom sorting order for GF-latin-core
sortOrder = "A B C D E F G H I J K L M N O P Q R S T U V W X Y Z a b c d e f g h i j k l m n o p q r s t u v w x y z zero one two three four five six seven eight nine period comma colon semicolon periodcentered ellipsis exclam exclamdown question questiondown quotesingle quotedbl quoteleft quoteright quotesinglbase quotedblleft quotedblright quotedblbase guilsinglleft guilsinglright guillemetleft guillemetright parenleft parenright bracketleft bracketright braceleft braceright slash bar brokenbar backslash fraction divisionslash bullet hyphen hyphensoft endash emdash underscore plus minus multiply divide plusminus equal less greater logicalnot mu.math asterisk asciicircum asciitilde percent degree onesuperior twosuperior threesuperior four.superior onequarter onehalf threequarters ordmasculine ordfeminine copyright registered at numbersign dollar cent sterling yen Euro currency ampersand section paragraph dieresis grave macron acute cedilla circumflex ring tilde dieresis.cap grave.cap macron.cap acute.cap cedilla.cap circumflex.cap ring.cap tilde.cap Agrave Aacute Acircumflex Atilde Adieresis Aring AE Ccedilla Egrave Eacute Ecircumflex Edieresis Igrave Iacute Icircumflex Idieresis Eth Ntilde Ograve Oacute Ocircumflex Otilde Odieresis Oslash OE Ugrave Uacute Ucircumflex Udieresis Yacute Ydieresis Thorn germandbls agrave aacute acircumflex atilde adieresis aring ae ccedilla egrave eacute ecircumflex edieresis igrave iacute icircumflex idieresis dotlessi eth ntilde ograve oacute ocircumflex otilde odieresis oslash oe ugrave uacute ucircumflex udieresis yacute thorn ydieresis space nbspace NULL CR"
sortOrder = sortOrder.split(" ")

# Apply index values temporarly, for sorting