use 32-bit GlyphIDs in COLRv1 baseGlyphs and layers

For forward-compatibility, see https://github.com/googlefonts/colr-gradients-spec/issues/8
This commit is contained in:
Cosimo Lupo 2020-07-01 19:50:48 +01:00
parent 4578f96e9d
commit 690080b14d
No known key found for this signature in database
GPG Key ID: 179A8F0895A02F4F
4 changed files with 40 additions and 44 deletions

View File

@ -134,48 +134,38 @@ class OTTableReader(object):
offset = self.offset + offset
return self.__class__(self.data, self.localState, offset, self.tableTag)
def readUShort(self):
def readValue(self, typecode, staticSize):
pos = self.pos
newpos = pos + 2
value, = struct.unpack(">H", self.data[pos:newpos])
newpos = pos + staticSize
value, = struct.unpack(f">{typecode}", self.data[pos:newpos])
self.pos = newpos
return value
def readUShortArray(self, count):
def readUShort(self):
return self.readValue("H", staticSize=2)
def readArray(self, typecode, staticSize, count):
pos = self.pos
newpos = pos + count * 2
value = array.array("H", self.data[pos:newpos])
newpos = pos + count * staticSize
value = array.array(typecode, self.data[pos:newpos])
if sys.byteorder != "big": value.byteswap()
self.pos = newpos
return value
def readUShortArray(self, count):
return self.readArray("H", staticSize=2, count=count)
def readInt8(self):
pos = self.pos
newpos = pos + 1
value, = struct.unpack(">b", self.data[pos:newpos])
self.pos = newpos
return value
return self.readValue("b", staticSize=1)
def readShort(self):
pos = self.pos
newpos = pos + 2
value, = struct.unpack(">h", self.data[pos:newpos])
self.pos = newpos
return value
return self.readValue("h", staticSize=2)
def readLong(self):
pos = self.pos
newpos = pos + 4
value, = struct.unpack(">l", self.data[pos:newpos])
self.pos = newpos
return value
return self.readValue("l", staticSize=4)
def readUInt8(self):
pos = self.pos
newpos = pos + 1
value, = struct.unpack(">B", self.data[pos:newpos])
self.pos = newpos
return value
return self.readValue("B", staticSize=1)
def readUInt24(self):
pos = self.pos
@ -185,11 +175,7 @@ class OTTableReader(object):
return value
def readULong(self):
pos = self.pos
newpos = pos + 4
value, = struct.unpack(">L", self.data[pos:newpos])
self.pos = newpos
return value
return self.readValue("L", staticSize=4)
def readTag(self):
pos = self.pos
@ -417,6 +403,9 @@ class OTTableWriter(object):
# But we just care about first one right now.
return subwriter
def writeValue(self, typecode, value):
self.items.append(struct.pack(f">{typecode}", value))
def writeUShort(self, value):
assert 0 <= value < 0x10000, value
self.items.append(struct.pack(">H", value))

View File

@ -295,9 +295,10 @@ class Tag(SimpleValue):
class GlyphID(SimpleValue):
staticSize = 2
typecode = "H"
def readArray(self, reader, font, tableDict, count):
glyphOrder = font.getGlyphOrder()
gids = reader.readUShortArray(count)
gids = reader.readArray(self.typecode, self.staticSize, count)
try:
l = [glyphOrder[gid] for gid in gids]
except IndexError:
@ -305,9 +306,14 @@ class GlyphID(SimpleValue):
l = [font.getGlyphName(gid) for gid in gids]
return l
def read(self, reader, font, tableDict):
return font.getGlyphName(reader.readUShort())
return font.getGlyphName(reader.readValue(self.typecode, self.staticSize))
def write(self, writer, font, tableDict, value, repeatIndex=None):
writer.writeUShort(font.getGlyphID(value))
writer.writeValue(self.typecode, font.getGlyphID(value))
class GlyphID32(GlyphID):
staticSize = 4
typecode = "L"
class NameID(UShort):
@ -1725,6 +1731,7 @@ converterMapping = {
"Version": Version,
"Tag": Tag,
"GlyphID": GlyphID,
"GlyphID32": GlyphID32,
"NameID": NameID,
"DeciPoints": DeciPoints,
"Fixed": Fixed,

View File

@ -1578,7 +1578,7 @@ otData = [
]),
('BaseGlyphV1Record', [
('GlyphID', 'BaseGlyph', None, None, 'Glyph ID of reference glyph.'),
('GlyphID32', 'BaseGlyph', None, None, 'Glyph ID of reference glyph.'),
('LOffset', 'LayerV1List', None, None, 'Offset (from beginning of BaseGlyphV1List) to LayerV1List.'),
]),
@ -1588,7 +1588,7 @@ otData = [
]),
('LayerV1Record', [
('GlyphID', 'LayerGlyph', None, None, 'Glyph ID of layer glyph (must be in z-order from bottom to top).'),
('GlyphID32', 'LayerGlyph', None, None, 'Glyph ID of layer glyph (must be in z-order from bottom to top).'),
('LOffset', 'Paint', None, None, 'Offset (from beginning of LayerV1List) to Paint subtable.'),
]),

View File

@ -83,15 +83,15 @@ COLR_V1_DATA = (
b"\x00\t" # LayerRecord[2].LayerGlyph (9)
b"\x00\x02" # LayerRecord[2].PaletteIndex (2)
b"\x00\x00\x00\x01" # BaseGlyphV1List.BaseGlyphCount (1)
b"\x00\n" # BaseGlyphV1List.BaseGlyphV1Record[0].BaseGlyph (10)
b"\x00\x00\x00\n" # Offset to LayerV1List from beginning of BaseGlyphV1List (10)
b"\x00\x00\x00\n" # BaseGlyphV1List.BaseGlyphV1Record[0].BaseGlyph (10)
b"\x00\x00\x00\x0c" # Offset to LayerV1List from beginning of BaseGlyphV1List (12)
b"\x00\x00\x00\x03" # LayerV1List.LayerCount (3)
b"\x00\x0b" # LayerV1List.LayerV1Record[0].LayerGlyph (11)
b"\x00\x00\x00\x16" # Offset to Paint from beginning of LayerV1List (22)
b"\x00\x0c" # LayerV1List.LayerV1Record[1].LayerGlyph (12)
b"\x00\x00\x00 " # Offset to Paint from beginning of LayerV1List (32)
b"\x00\r" # LayerV1List.LayerV1Record[2].LayerGlyph (13)
b"\x00\x00\x00x" # Offset to Paint from beginning of LayerV1List (120)
b"\x00\x00\x00\x0b" # LayerV1List.LayerV1Record[0].LayerGlyph (11)
b"\x00\x00\x00\x1c" # Offset to Paint from beginning of LayerV1List (28)
b"\x00\x00\x00\x0c" # LayerV1List.LayerV1Record[1].LayerGlyph (12)
b"\x00\x00\x00&" # Offset to Paint from beginning of LayerV1List (38)
b"\x00\x00\x00\r" # LayerV1List.LayerV1Record[2].LayerGlyph (13)
b"\x00\x00\x00~" # Offset to Paint from beginning of LayerV1List (126)
b"\x00\x01" # Paint.Format (1)
b"\x00\x02" # Paint.Color.PaletteIndex (2)
b" \x00" # Paint.Color.Transparency.value (0.5)