def decompileCoord_(axisTags, data, offset): coord = {} pos = offset for axis in axisTags: coord[axis] = fi2fl(struct.unpack(">h", data[pos:pos + 2])[0], 14) pos += 2 return coord, pos
def decompile(self, data, ttFont): version, nTables = struct.unpack(">HH", data[:4]) apple = False if (len(data) >= 8) and (version == 1): # AAT Apple's "new" format. Hm. version, nTables = struct.unpack(">LL", data[:8]) self.version = fi2fl(version, 16) data = data[8:] apple = True else: self.version = version data = data[4:] tablesIndex = [] self.kernTables = [] for i in range(nTables): if self.version == 1.0: # Apple length, coverage, tupleIndex = struct.unpack(">lHH", data[:8]) version = coverage & 0xff else: version, length = struct.unpack(">HH", data[:4]) length = int(length) if version not in kern_classes: subtable = KernTable_format_unkown(version) else: subtable = kern_classes[version]() subtable.apple = apple subtable.decompile(data[:length], ttFont) self.kernTables.append(subtable) data = data[length:]
def decompile(self, data, ttFont): version, nTables = struct.unpack(">HH", data[:4]) apple = False if (len(data) >= 8) and (version == 1): # AAT Apple's "new" format. Hm. version, nTables = struct.unpack(">LL", data[:8]) self.version = fi2fl(version, 16) data = data[8:] apple = True else: self.version = version data = data[4:] self.kernTables = [] for i in range(nTables): if self.version == 1.0: # Apple length, coverage, subtableFormat = struct.unpack( ">LBB", data[:6]) else: # in OpenType spec the "version" field refers to the common # subtable header; the actual subtable format is stored in # the 8-15 mask bits of "coverage" field. # This "version" is always 0 so we ignore it here _, length, subtableFormat, coverage = struct.unpack( ">HHBB", data[:6]) if subtableFormat not in kern_classes: subtable = KernTable_format_unkown(subtableFormat) else: subtable = kern_classes[subtableFormat](apple) subtable.decompile(data[:length], ttFont) self.kernTables.append(subtable) data = data[length:]
def xmlWrite(self, xmlWriter, font, value, name, attrs): if value >= 0x10000: value = fi2fl(value, 16) if value % 1 != 0: # Write as hex value = "0x%08x" % fl2fi(value, 16) xmlWriter.simpletag(name, attrs + [("value", value)]) xmlWriter.newline()
def decompile(self, data, ttFont): axisTags = [axis.axisTag for axis in ttFont["fvar"].axes] header = {} headerSize = sstruct.calcsize(AVAR_HEADER_FORMAT) header = sstruct.unpack(AVAR_HEADER_FORMAT, data[0:headerSize]) majorVersion = header["majorVersion"] if majorVersion != 1: raise TTLibError("unsupported 'avar' version %d" % majorVersion) pos = headerSize for axis in axisTags: segments = self.segments[axis] = {} numPairs = struct.unpack(">H", data[pos:pos + 2])[0] pos = pos + 2 for _ in range(numPairs): fromValue, toValue = struct.unpack(">hh", data[pos:pos + 4]) segments[fi2fl(fromValue, 14)] = fi2fl(toValue, 14) pos = pos + 4
def decompile(self, data, axisTags): sstruct.unpack2(FVAR_INSTANCE_FORMAT, data, self) pos = sstruct.calcsize(FVAR_INSTANCE_FORMAT) for axis in axisTags: value = struct.unpack(">l", data[pos:pos + 4])[0] self.coordinates[axis] = fi2fl(value, 16) pos += 4 if pos + 2 <= len(data): self.postscriptNameID = struct.unpack(">H", data[pos:pos + 2])[0] else: self.postscriptNameID = 0xFFFF
def decompile(self, data, glyfTable): flags, glyphID = struct.unpack(">HH", data[:4]) self.flags = int(flags) glyphID = int(glyphID) self.glyphName = glyfTable.getGlyphName(int(glyphID)) #print ">>", reprflag(self.flags) data = data[4:] if self.flags & ARG_1_AND_2_ARE_WORDS: if self.flags & ARGS_ARE_XY_VALUES: self.x, self.y = struct.unpack(">hh", data[:4]) else: x, y = struct.unpack(">HH", data[:4]) self.firstPt, self.secondPt = int(x), int(y) data = data[4:] else: if self.flags & ARGS_ARE_XY_VALUES: self.x, self.y = struct.unpack(">bb", data[:2]) else: x, y = struct.unpack(">BB", data[:2]) self.firstPt, self.secondPt = int(x), int(y) data = data[2:] if self.flags & WE_HAVE_A_SCALE: scale, = struct.unpack(">h", data[:2]) self.transform = [[fi2fl(scale, 14), 0], [0, fi2fl(scale, 14)]] # fixed 2.14 data = data[2:] elif self.flags & WE_HAVE_AN_X_AND_Y_SCALE: xscale, yscale = struct.unpack(">hh", data[:4]) self.transform = [[fi2fl(xscale, 14), 0], [0, fi2fl(yscale, 14)]] # fixed 2.14 data = data[4:] elif self.flags & WE_HAVE_A_TWO_BY_TWO: (xscale, scale01, scale10, yscale) = struct.unpack(">hhhh", data[:8]) self.transform = [[fi2fl(xscale, 14), fi2fl(scale01, 14)], [fi2fl(scale10, 14), fi2fl(yscale, 14)]] # fixed 2.14 data = data[8:] more = self.flags & MORE_COMPONENTS haveInstructions = self.flags & WE_HAVE_INSTRUCTIONS self.flags = self.flags & (ROUND_XY_TO_GRID | USE_MY_METRICS | SCALED_COMPONENT_OFFSET | UNSCALED_COMPONENT_OFFSET | NON_OVERLAPPING) return more, haveInstructions, data
def decompile(self, data, glyfTable): flags, glyphID = struct.unpack(">HH", data[:4]) self.flags = int(flags) glyphID = int(glyphID) self.glyphName = glyfTable.getGlyphName(int(glyphID)) # print ">>", reprflag(self.flags) data = data[4:] if self.flags & ARG_1_AND_2_ARE_WORDS: if self.flags & ARGS_ARE_XY_VALUES: self.x, self.y = struct.unpack(">hh", data[:4]) else: x, y = struct.unpack(">HH", data[:4]) self.firstPt, self.secondPt = int(x), int(y) data = data[4:] else: if self.flags & ARGS_ARE_XY_VALUES: self.x, self.y = struct.unpack(">bb", data[:2]) else: x, y = struct.unpack(">BB", data[:2]) self.firstPt, self.secondPt = int(x), int(y) data = data[2:] if self.flags & WE_HAVE_A_SCALE: scale, = struct.unpack(">h", data[:2]) self.transform = [[fi2fl(scale, 14), 0], [0, fi2fl(scale, 14)]] # fixed 2.14 data = data[2:] elif self.flags & WE_HAVE_AN_X_AND_Y_SCALE: xscale, yscale = struct.unpack(">hh", data[:4]) self.transform = [[fi2fl(xscale, 14), 0], [0, fi2fl(yscale, 14)]] # fixed 2.14 data = data[4:] elif self.flags & WE_HAVE_A_TWO_BY_TWO: (xscale, scale01, scale10, yscale) = struct.unpack(">hhhh", data[:8]) self.transform = [ [fi2fl(xscale, 14), fi2fl(scale01, 14)], [fi2fl(scale10, 14), fi2fl(yscale, 14)], ] # fixed 2.14 data = data[8:] more = self.flags & MORE_COMPONENTS haveInstructions = self.flags & WE_HAVE_INSTRUCTIONS self.flags = self.flags & ( ROUND_XY_TO_GRID | USE_MY_METRICS | SCALED_COMPONENT_OFFSET | UNSCALED_COMPONENT_OFFSET | NON_OVERLAPPING ) return more, haveInstructions, data
def decompile(self, data, ttFont): version, nTables = struct.unpack(">HH", data[:4]) apple = False if (len(data) >= 8) and (version == 1): # AAT Apple's "new" format. Hm. version, nTables = struct.unpack(">LL", data[:8]) self.version = fi2fl(version, 16) data = data[8:] apple = True else: self.version = version data = data[4:] self.kernTables = [] for i in range(nTables): if self.version == 1.0: # Apple length, coverage, subtableFormat = struct.unpack( ">LBB", data[:6]) else: # in OpenType spec the "version" field refers to the common # subtable header; the actual subtable format is stored in # the 8-15 mask bits of "coverage" field. # This "version" is always 0 so we ignore it here _, length, subtableFormat, coverage = struct.unpack( ">HHBB", data[:6]) if nTables == 1 and subtableFormat == 0: # The "length" value is ignored since some fonts # (like OpenSans and Calibri) have a subtable larger than # its value. nPairs, = struct.unpack(">H", data[6:8]) calculated_length = (nPairs * 6) + 14 if length != calculated_length: log.warning( "'kern' subtable longer than defined: " "%d bytes instead of %d bytes" % (calculated_length, length) ) length = calculated_length if subtableFormat not in kern_classes: subtable = KernTable_format_unkown(subtableFormat) else: subtable = kern_classes[subtableFormat](apple) subtable.decompile(data[:length], ttFont) self.kernTables.append(subtable) data = data[length:]
def decompile(self, data, ttFont): version, nTables = struct.unpack(">HH", data[:4]) apple = False if (len(data) >= 8) and (version == 1): # AAT Apple's "new" format. Hm. version, nTables = struct.unpack(">LL", data[:8]) self.version = fi2fl(version, 16) data = data[8:] apple = True else: self.version = version data = data[4:] self.kernTables = [] for i in range(nTables): if self.version == 1.0: # Apple length, coverage, subtableFormat = struct.unpack( ">LBB", data[:6]) else: # in OpenType spec the "version" field refers to the common # subtable header; the actual subtable format is stored in # the 8-15 mask bits of "coverage" field. # This "version" is always 0 so we ignore it here _, length, subtableFormat, coverage = struct.unpack( ">HHBB", data[:6]) if nTables == 1 and subtableFormat == 0: # The "length" value is ignored since some fonts # (like OpenSans and Calibri) have a subtable larger than # its value. nPairs, = struct.unpack(">H", data[6:8]) calculated_length = (nPairs * 6) + 14 if length != calculated_length: log.warning("'kern' subtable longer than defined: " "%d bytes instead of %d bytes" % (calculated_length, length)) length = calculated_length if subtableFormat not in kern_classes: subtable = KernTable_format_unkown(subtableFormat) else: subtable = kern_classes[subtableFormat](apple) subtable.decompile(data[:length], ttFont) self.kernTables.append(subtable) data = data[length:]
def decompile(self, data, offset): # initial offset is from the start of trak table to the current TrackData trackDataHeader = data[offset:offset + TRACK_DATA_FORMAT_SIZE] if len(trackDataHeader) != TRACK_DATA_FORMAT_SIZE: raise TTLibError('not enough data to decompile TrackData header') sstruct.unpack(TRACK_DATA_FORMAT, trackDataHeader, self) offset += TRACK_DATA_FORMAT_SIZE nSizes = self.nSizes sizeTableOffset = self.sizeTableOffset sizeTable = [] for i in range(nSizes): sizeValueData = data[sizeTableOffset:sizeTableOffset + SIZE_VALUE_FORMAT_SIZE] if len(sizeValueData) < SIZE_VALUE_FORMAT_SIZE: raise TTLibError( 'not enough data to decompile TrackData size subtable') sizeValue, = struct.unpack(SIZE_VALUE_FORMAT, sizeValueData) sizeTable.append(fi2fl(sizeValue, 16)) sizeTableOffset += SIZE_VALUE_FORMAT_SIZE for i in range(self.nTracks): entry = TrackTableEntry() entryData = data[offset:offset + TRACK_TABLE_ENTRY_FORMAT_SIZE] if len(entryData) < TRACK_TABLE_ENTRY_FORMAT_SIZE: raise TTLibError( 'not enough data to decompile TrackTableEntry record') sstruct.unpack(TRACK_TABLE_ENTRY_FORMAT, entryData, entry) perSizeOffset = entry.offset for j in range(nSizes): size = sizeTable[j] perSizeValueData = data[perSizeOffset:perSizeOffset + PER_SIZE_VALUE_FORMAT_SIZE] if len(perSizeValueData) < PER_SIZE_VALUE_FORMAT_SIZE: raise TTLibError( 'not enough data to decompile per-size track values') perSizeValue, = struct.unpack(PER_SIZE_VALUE_FORMAT, perSizeValueData) entry[size] = perSizeValue perSizeOffset += PER_SIZE_VALUE_FORMAT_SIZE self[entry.track] = entry offset += TRACK_TABLE_ENTRY_FORMAT_SIZE
def unpack(fmt, data, obj=None): if obj is None: obj = {} data = tobytes(data) formatstring, names, fixes = getformat(fmt) if isinstance(obj, dict): d = obj else: d = obj.__dict__ elements = struct.unpack(formatstring, data) for i in range(len(names)): name = names[i] value = elements[i] if name in fixes: # fixed point conversion value = fi2fl(value, fixes[name]) elif isinstance(value, bytes): try: value = tostr(value) except UnicodeDecodeError: pass d[name] = value return obj
def decompile(self, data, offset): # initial offset is from the start of trak table to the current TrackData trackDataHeader = data[offset:offset+TRACK_DATA_FORMAT_SIZE] if len(trackDataHeader) != TRACK_DATA_FORMAT_SIZE: raise TTLibError('not enough data to decompile TrackData header') sstruct.unpack(TRACK_DATA_FORMAT, trackDataHeader, self) offset += TRACK_DATA_FORMAT_SIZE nSizes = self.nSizes sizeTableOffset = self.sizeTableOffset sizeTable = [] for i in range(nSizes): sizeValueData = data[sizeTableOffset:sizeTableOffset+SIZE_VALUE_FORMAT_SIZE] if len(sizeValueData) < SIZE_VALUE_FORMAT_SIZE: raise TTLibError('not enough data to decompile TrackData size subtable') sizeValue, = struct.unpack(SIZE_VALUE_FORMAT, sizeValueData) sizeTable.append(fi2fl(sizeValue, 16)) sizeTableOffset += SIZE_VALUE_FORMAT_SIZE for i in range(self.nTracks): entry = TrackTableEntry() entryData = data[offset:offset+TRACK_TABLE_ENTRY_FORMAT_SIZE] if len(entryData) < TRACK_TABLE_ENTRY_FORMAT_SIZE: raise TTLibError('not enough data to decompile TrackTableEntry record') sstruct.unpack(TRACK_TABLE_ENTRY_FORMAT, entryData, entry) perSizeOffset = entry.offset for j in range(nSizes): size = sizeTable[j] perSizeValueData = data[perSizeOffset:perSizeOffset+PER_SIZE_VALUE_FORMAT_SIZE] if len(perSizeValueData) < PER_SIZE_VALUE_FORMAT_SIZE: raise TTLibError('not enough data to decompile per-size track values') perSizeValue, = struct.unpack(PER_SIZE_VALUE_FORMAT, perSizeValueData) entry[size] = perSizeValue perSizeOffset += PER_SIZE_VALUE_FORMAT_SIZE self[entry.track] = entry offset += TRACK_TABLE_ENTRY_FORMAT_SIZE
def read(self, reader, font, tableDict): value = reader.readLong() assert (value >> 16) == 1, "Unsupported version 0x%08x" % value return fi2fl(value, 16)
def read(self, reader, font, tableDict): return fi2fl(reader.readLong(), 16)
def read(self, reader, font, tableDict): return fi2fl(reader.readShort(), 14)
def xmlRead(self, attrs, content, font): value = attrs["value"] value = float(int(value, 0)) if value.startswith("0") else float(value) if value >= 0x10000: value = fi2fl(value, 16) return value
def read(self, reader, font, tableDict): value = reader.readLong() return fi2fl(value, 16)