def compile(self, ttFont):
    if self.data:
        return (struct.pack('>HHH', self.format, self.length, self.language) + self.data)
    charCodes = list(self.cmap.keys())
    lenCharCodes = len(charCodes)
    if (lenCharCodes == 0):
        startCode = [65535]
        endCode = [65535]
    else:
        charCodes.sort()
        names = list(map(operator.getitem, ([self.cmap] * lenCharCodes), charCodes))
        nameMap = ttFont.getReverseGlyphMap()
        try:
            gids = list(map(operator.getitem, ([nameMap] * lenCharCodes), names))
        except KeyError:
            nameMap = ttFont.getReverseGlyphMap(rebuild=True)
            try:
                gids = list(map(operator.getitem, ([nameMap] * lenCharCodes), names))
            except KeyError:
                gids = []
                for name in names:
                    try:
                        gid = nameMap[name]
                    except KeyError:
                        try:
                            if (name[:3] == 'gid'):
                                gid = eval(name[3:])
                            else:
                                gid = ttFont.getGlyphID(name)
                        except:
                            raise KeyError(name)
                    gids.append(gid)
        cmap = {}
        list(map(operator.setitem, ([cmap] * len(charCodes)), charCodes, gids))
        lastCode = charCodes[0]
        endCode = []
        startCode = [lastCode]
        for charCode in charCodes[1:]:
            if (charCode == (lastCode + 1)):
                lastCode = charCode
                continue
            (start, end) = splitRange(startCode[(- 1)], lastCode, cmap)
            startCode.extend(start)
            endCode.extend(end)
            startCode.append(charCode)
            lastCode = charCode
        (start, end) = splitRange(startCode[(- 1)], lastCode, cmap)
        startCode.extend(start)
        endCode.extend(end)
        startCode.append(65535)
        endCode.append(65535)
    idDelta = []
    idRangeOffset = []
    glyphIndexArray = []
    for i in range((len(endCode) - 1)):
        indices = []
        for charCode in range(startCode[i], (endCode[i] + 1)):
            indices.append(cmap[charCode])
        if (indices == list(range(indices[0], (indices[0] + len(indices))))):
            idDelta.append(((indices[0] - startCode[i]) % 65536))
            idRangeOffset.append(0)
        else:
            idDelta.append(0)
            idRangeOffset.append((2 * ((len(endCode) + len(glyphIndexArray)) - i)))
            glyphIndexArray.extend(indices)
    idDelta.append(1)
    idRangeOffset.append(0)
    segCount = len(endCode)
    segCountX2 = (segCount * 2)
    (searchRange, entrySelector, rangeShift) = getSearchRange(segCount, 2)
    charCodeArray = array.array('H', ((endCode + [0]) + startCode))
    idDeltaArray = array.array('H', idDelta)
    restArray = array.array('H', (idRangeOffset + glyphIndexArray))
    if (sys.byteorder != 'big'):
        charCodeArray.byteswap()
        idDeltaArray.byteswap()
        restArray.byteswap()
    data = ((charCodeArray.tostring() + idDeltaArray.tostring()) + restArray.tostring())
    length = (struct.calcsize(cmap_format_4_format) + len(data))
    header = struct.pack(cmap_format_4_format, self.format, length, self.language, segCountX2, searchRange, entrySelector, rangeShift)
    return (header + data)
def compile(self, ttFont):
    if self.data:
        return (struct.pack('>HHH', self.format, self.length, self.language) + self.data)
    charCodes = list(self.cmap.keys())
    lenCharCodes = len(charCodes)
    if (lenCharCodes == 0):
        startCode = [65535]
        endCode = [65535]
    else:
        charCodes.sort()
        names = list(map(operator.getitem, ([self.cmap] * lenCharCodes), charCodes))
        nameMap = ttFont.getReverseGlyphMap()
        try:
            gids = list(map(operator.getitem, ([nameMap] * lenCharCodes), names))
        except KeyError:
            nameMap = ttFont.getReverseGlyphMap(rebuild=True)
            try:
                gids = list(map(operator.getitem, ([nameMap] * lenCharCodes), names))
            except KeyError:
                gids = []
                for name in names:
                    try:
                        gid = nameMap[name]
                    except KeyError:
                        try:
                            if (name[:3] == 'gid'):
                                gid = eval(name[3:])
                            else:
                                gid = ttFont.getGlyphID(name)
                        except:
                            raise KeyError(name)
                    gids.append(gid)
        cmap = {}
        list(map(operator.setitem, ([cmap] * len(charCodes)), charCodes, gids))
        lastCode = charCodes[0]
        endCode = []
        startCode = [lastCode]
        for charCode in charCodes[1:]:
            if (charCode == (lastCode + 1)):
                lastCode = charCode
                continue
            (start, end) = splitRange(startCode[(- 1)], lastCode, cmap)
            startCode.extend(start)
            endCode.extend(end)
            startCode.append(charCode)
            lastCode = charCode
        (start, end) = splitRange(startCode[(- 1)], lastCode, cmap)
        startCode.extend(start)
        endCode.extend(end)
        startCode.append(65535)
        endCode.append(65535)
    idDelta = []
    idRangeOffset = []
    glyphIndexArray = []
    for i in range((len(endCode) - 1)):
        indices = []
        for charCode in range(startCode[i], (endCode[i] + 1)):
            indices.append(cmap[charCode])
        if (indices == list(range(indices[0], (indices[0] + len(indices))))):
            idDelta.append(((indices[0] - startCode[i]) % 65536))
            idRangeOffset.append(0)
        else:
            idDelta.append(0)
            idRangeOffset.append((2 * ((len(endCode) + len(glyphIndexArray)) - i)))
            glyphIndexArray.extend(indices)
    idDelta.append(1)
    idRangeOffset.append(0)
    segCount = len(endCode)
    segCountX2 = (segCount * 2)
    (searchRange, entrySelector, rangeShift) = getSearchRange(segCount, 2)
    charCodeArray = array.array('H', ((endCode + [0]) + startCode))
    idDeltaArray = array.array('H', idDelta)
    restArray = array.array('H', (idRangeOffset + glyphIndexArray))
    if (sys.byteorder != 'big'):
        charCodeArray.byteswap()
        idDeltaArray.byteswap()
        restArray.byteswap()
    data = ((charCodeArray.tostring() + idDeltaArray.tostring()) + restArray.tostring())
    length = (struct.calcsize(cmap_format_4_format) + len(data))
    header = struct.pack(cmap_format_4_format, self.format, length, self.language, segCountX2, searchRange, entrySelector, rangeShift)
    return (header + data)