-
Notifications
You must be signed in to change notification settings - Fork 3
/
col.py
70 lines (56 loc) · 2.55 KB
/
col.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
import struct, array, sys
class ColGroup:
def readHeader(self, fin):
self.surfaceId, self.numTriIndices, self.flags, self.unknown3, self.indicesOffset, self.terrainTypesOffset, self.unknownOffset2, self.unknownOffset3 = struct.unpack(">HHHHIIII", fin.read(24))
self.indexBuffer = array.array('H')
self.terrainTypes = array.array('B')
self.tribuf2 = array.array('B')
self.tribuf3 = array.array('h')
def readBuffers(self, fin):
fin.seek(self.indicesOffset)
self.indexBuffer.fromfile(fin, self.numTriIndices*3)
if sys.byteorder != 'big': self.indexBuffer.byteswap()
fin.seek(self.terrainTypesOffset)
self.terrainTypes.fromfile(fin, self.numTriIndices)
fin.seek(self.unknownOffset2)
self.tribuf2.fromfile(fin, self.numTriIndices)
if self.unknownOffset3 != 0:
fin.seek(self.unknownOffset3)
self.tribuf3.fromfile(fin, self.numTriIndices)
if sys.byteorder != 'big': self.tribuf3.byteswap()
def __repr__(self):
return "surfaceId=%x, ntri=%d, flags=%d"%(self.surfaceId, len(self.indexBuffer)//3, self.flags)
class ColReader:
def read(self, fin):
numCoords, coordsOffset, numGroups, groupsOffset = struct.unpack('>IIII', fin.read(16))
assert fin.tell() == groupsOffset
fin.seek(groupsOffset)
self.groups = [ColGroup() for i in range(numGroups)]
for group in self.groups:
group.readHeader(fin)
assert len({group.surfaceId for group in self.groups}) == len(self.groups)
assert fin.tell() == coordsOffset
fin.seek(coordsOffset)
self.vertexBuffer = array.array('f')
self.vertexBuffer.fromfile(fin, numCoords*3)
if sys.byteorder != 'big': self.vertexBuffer.byteswap()
for group in self.groups:
group.readBuffers(fin)
assert max(group.indexBuffer) < len(self.vertexBuffer)/3, (max(group.indexBuffer), len(self.vertexBuffer))
def __repr__(self):
return hex(self.unknown0)+'|'+repr(self.groups)
if 0:
import os
for dirpath, dirnames, filenames in os.walk("."):
for name in filenames:
if not name.lower().endswith(".col"): continue
fin = open(os.path.join(dirpath, name), 'rb')
c = ColReader()
c.read(fin)
fin.close()
if __name__ == "__main__":
fin = open(sys.argv[1], 'rb')
c = ColReader()
c.read(fin)
fin.close()
for g in c.groups: print(g)