-
Notifications
You must be signed in to change notification settings - Fork 10
/
Copy pathbin.py
117 lines (91 loc) · 3.95 KB
/
bin.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
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
import bpy
import mathutils
import re
import os
import struct
import meshio
from math import radians
def readBIN_to_meshio(filepath):
firstFile = open(filepath, 'rb')
# read number of bodies
bytes = firstFile.read()
firstFile.close()
isFirstFile = ((len(bytes) % 48) != 0)
# currently assume that numBodies is always 1
(numBodies,), bytes = struct.unpack('i', bytes[:4]), bytes[4:]
numBodies *= isFirstFile
field_datas = []
for i in range(0, numBodies):
# determine length of file name string
(strLength,), bytes = struct.unpack('i', bytes[:4]), bytes[4:]
# read file name
objFile, bytes = bytes[:strLength], bytes[strLength:]
if i == 0:
objFileString = objFile.decode('ascii')
cur_field_data = {}
cur_field_data["translation"] = None
cur_field_data["scaling"] = None
cur_field_data["rotation"] = None
cur_field_data["transformation_matrix"] = None
# Read scaling factors in first file
(sx,), bytes = struct.unpack('f', bytes[:4]), bytes[4:]
(sy,), bytes = struct.unpack('f', bytes[:4]), bytes[4:]
(sz,), bytes = struct.unpack('f', bytes[:4]), bytes[4:]
cur_field_data["scaling"] = (sx, sy, sz)
(isWall,), bytes = struct.unpack('?', bytes[:1]), bytes[1:]
(colr,), bytes = struct.unpack('f', bytes[:4]), bytes[4:]
(colg,), bytes = struct.unpack('f', bytes[:4]), bytes[4:]
(colb,), bytes = struct.unpack('f', bytes[:4]), bytes[4:]
(cola,), bytes = struct.unpack('f', bytes[:4]), bytes[4:]
field_datas.append(cur_field_data)
# if the object name is empty, then we know that it is not a "first file"
# and we just simply reopen it and start from the beginning
if isFirstFile:
# create mesh from referenced object
dirPath = os.path.dirname(filepath)
objPath = os.path.join(dirPath, objFileString)
mesh = meshio.read(objPath)
else:
otherFile = open(filepath, 'rb')
# reopen same file
bytes = otherFile.read()
otherFile.close()
# since there is no object referenced, create empty mesh
mesh = meshio.Mesh([], [])
i = 0
while len(bytes) != 0:
cur_field_data = {}
cur_field_data["translation"] = None
cur_field_data["scaling"] = (1, 1, 1)
cur_field_data["rotation"] = None
cur_field_data["transformation_matrix"] = None
# Read translation in first file
(x,), bytes = struct.unpack('f', bytes[:4]), bytes[4:]
(y,), bytes = struct.unpack('f', bytes[:4]), bytes[4:]
(z,), bytes = struct.unpack('f', bytes[:4]), bytes[4:]
cur_field_data["translation"] = (x, y, z)
# Read rotation in first file
r = []
for _ in range(0,9):
(value,), bytes = struct.unpack('f', bytes[:4]), bytes[4:]
r.append(value)
rotationMatrix = mathutils.Matrix()
rotationMatrix[0][0:3] = r[0], r[3], r[6]
rotationMatrix[1][0:3] = r[1], r[4], r[7]
rotationMatrix[2][0:3] = r[2], r[5], r[8]
cur_field_data["rotation"] = rotationMatrix.to_quaternion()
cur_field_data["transformation_matrix"] = mathutils.Matrix.LocRotScale(
cur_field_data["translation"],
cur_field_data["rotation"],
cur_field_data["scaling"])
if isFirstFile:
field_datas[i]["translation"] = cur_field_data["translation"]
field_datas[i]["rotation"] = cur_field_data["rotation"]
field_datas[i]["transformation_matrix"] = cur_field_data["transformation_matrix"]
else:
field_datas.append(cur_field_data)
i += 1
mesh.field_data = field_datas[0]
return mesh
# no need for write function
meshio.register_format("bin", [".bin"], readBIN_to_meshio, {".bin": None})