本日はUnity枠です。
現在BlenderからUnity製アプリケーションに向けてネットワーク経由でメッシュ情報を双方向に通信するパッケージを開発しています。
MixedRealityModelingToolsという仮称で開発していますが今回は昨日に引き続きBlender側のコア機能を紹介します。
〇MessagePackとは?
今回はデータのシリアル化、デシリアライズにMessagePackを使用しています。
これはC#、Pythonなど多くのプラットフォームで使用することができるバイナリデータの交換用フォーマットで、Json形式のデータとしてバイナリを格納することで非常にデータをコンパクトにすることができます。
筆者の開発中のツールでは高速な通信を実現するためにMessagePackを使用しています。
〇メッシュをUnityに送信する関数
先述の通りUnity側とBlender側ではMessagePackでシリアライズ化したデータを送信して受け取ります。
これを実現する関数が以下になります。
import msgpack ・・・ def send_mesh_data_to_unity(mesh_data): vertices, triangles, normals = mesh_data # Convert numpy arrays to list vertices_list = np.array(vertices, dtype='<f4').flatten().tolist() triangles_list = np.array(triangles, dtype='<i4').flatten().tolist() normals_list = np.array(normals, dtype='<f4').flatten().tolist() # データを辞書として構築 data_dict = { 'vertices': vertices_list, 'triangles': triangles_list, 'normals': normals_list } # MessagePackでシリアライズ serialized_mesh_data = msgpack.packb(data_dict) #print(f"Serialized data (bytes): {serialized_mesh_data.hex()}") verification_mesh_data(serialized_mesh_data) # ここでデシリアライズの確認を行う try: deserialized_data = msgpack.unpackb(serialized_mesh_data) print("Deserialization success!") #print(deserialized_data) # もし必要ならば、デシリアライズされたデータを出力する except Exception as e: print(f"Deserialization error: {e}") return # エラーが発生した場合、関数をここで終了する for client in server_thread.clients: try: client.sendall(serialized_mesh_data) #print(serialized_mesh_data) except Exception as e: print(f"Error while sending mesh data to client: {e}")
import msgpackにてmsgpackを使用しています。このためにはBelnder側にMessagePackを導入する必要があります。この点は別途説明します。
MessagePackは前述のとおりJson形式(正式にはJsonのような)でデータを格納しバイナリ化します。
これを定義しているのが以下です。
data_dict = { 'vertices': vertices_list, 'triangles': triangles_list, 'normals': normals_list }
ここでは頂点、メッシュのインデックス、法線の3つのデータを格納しています。
ここで辞書として追加したデータをMessagePackでシリアライズ化します。
serialized_mesh_data = msgpack.packb(data_dict)
送信する前のデータ(=実際のデータ)は次のようになっています。
'vertices': [1.0, 1.0, 1.0, 1.0, 1.0, -1.0, 1.0, -1.0, 1.0, 1.0, -1.0, -1.0, -1.0, 1.0, 1.0, -1.0, 1.0, -1.0, -1.0, -1.0, 1.0, -1.0, -1.0, -1.0], 'triangles': [4, 2, 0, 2, 7, 3, 6, 5, 7, 1, 7, 5, 0, 3, 1, 4, 1, 5, 4, 6, 2, 2, 6, 7, 6, 4, 5, 1, 3, 7, 0, 2, 3, 4, 0, 1], 'normals': [0.5773503184318542, 0.5773503184318542, 0.5773503184318542, 0.5773503184318542, 0.5773503184318542, -0.5773503184318542, 0.5773503184318542, -0.5773503184318542, 0.5773503184318542, 0.5773503184318542, -0.5773503184318542, -0.5773503184318542, -0.5773503184318542, 0.5773503184318542, 0.5773503184318542, -0.5773503184318542, 0.5773503184318542, -0.5773503184318542, -0.5773503184318542, -0.5773503184318542, 0.5773503184318542, -0.5773503184318542, -0.5773503184318542, -0.5773503184318542]
これをバイナリデータとして次のようになります。
\x83\xa8vertices\xdc\x00\x18\xcb?\xf0\x00\x00\x00\x00\x00\x00\xcb?\xf0\x00\x00\x00\x00\x00\x00\xcb?\xf0\x00\x00\x00\x00\x00\x00\xcb?\xf0\x00\x00\x00\x00\x00\x00\xcb?\xf0\x00\x00\x00\x00\x00\x00\xcb\xbf\xf0\x00\x00\x00\x00\x00\x00\xcb?\xf0\x00\x00\x00\x00\x00\x00\xcb\xbf\xf0\x00\x00\x00\x00\x00\x00\xcb?\xf0\x00\x00\x00\x00\x00\x00\xcb?\xf0\x00\x00\x00\x00\x00\x00\xcb\xbf\xf0\x00\x00\x00\x00\x00\x00\xcb\xbf\xf0\x00\x00\x00\x00\x00\x00\xcb\xbf\xf0\x00\x00\x00\x00\x00\x00\xcb?\xf0\x00\x00\x00\x00\x00\x00\xcb?\xf0\x00\x00\x00\x00\x00\x00\xcb\xbf\xf0\x00\x00\x00\x00\x00\x00\xcb?\xf0\x00\x00\x00\x00\x00\x00\xcb\xbf\xf0\x00\x00\x00\x00\x00\x00\xcb\xbf\xf0\x00\x00\x00\x00\x00\x00\xcb\xbf\xf0\x00\x00\x00\x00\x00\x00\xcb?\xf0\x00\x00\x00\x00\x00\x00\xcb\xbf\xf0\x00\x00\x00\x00\x00\x00\xcb\xbf\xf0\x00\x00\x00\x00\x00\x00\xcb\xbf\xf0\x00\x00\x00\x00\x00\x00\xa9triangles\xdc\x00$\x04\x02\x00\x02\x07\x03\x06\x05\x07\x01\x07\x05\x00\x03\x01\x04\x01\x05\x04\x06\x02\x02\x06\x07\x06\x04\x05\x01\x03\x07\x00\x02\x03\x04\x00\x01\xa7normals\xdc\x00\x18\xcb?\xe2y\xa7`\x00\x00\x00\xcb?\xe2y\xa7`\x00\x00\x00\xcb?\xe2y\xa7`\x00\x00\x00\xcb?\xe2y\xa7`\x00\x00\x00\xcb?\xe2y\xa7`\x00\x00\x00\xcb\xbf\xe2y\xa7`\x00\x00\x00\xcb?\xe2y\xa7`\x00\x00\x00\xcb\xbf\xe2y\xa7`\x00\x00\x00\xcb?\xe2y\xa7`\x00\x00\x00\xcb?\xe2y\xa7`\x00\x00\x00\xcb\xbf\xe2y\xa7`\x00\x00\x00\xcb\xbf\xe2y\xa7`\x00\x00\x00\xcb\xbf\xe2y\xa7`\x00\x00\x00\xcb?\xe2y\xa7`\x00\x00\x00\xcb?\xe2y\xa7`\x00\x00\x00\xcb\xbf\xe2y\xa7`\x00\x00\x00\xcb?\xe2y\xa7`\x00\x00\x00\xcb\xbf\xe2y\xa7`\x00\x00\x00\xcb\xbf\xe2y\xa7`\x00\x00\x00\xcb\xbf\xe2y\xa7`\x00\x00\x00\xcb?\xe2y\xa7`\x00\x00\x00\xcb\xbf\xe2y\xa7`\x00\x00\x00\xcb\xbf\xe2y\xa7`\x00\x00\x00\xcb\xbf\xe2y\xa7`\x00\x00\x00
\x○○という形式でデータが格納されており、○○部が16進数に変換したデータは以下になります。
131168220024203240000000203240000000203240000000203240000000203240000000203191240000000203240000000203191240000000203240000000203240000000203191240000000203191240000000203191240000000203240000000203240000000203191240000000203240000000203191240000000203191240000000203191240000000203240000000203191240000000203191240000000203191240000000169220042027365717503141546226764513702340116722002420322616700020322616700020322616700020322616700020322616700020319122616700020322616700020319122616700020322616700020322616700020319122616700020319122616700020319122616700020322616700020322616700020319122616700020322616700020319122616700020319122616700020319122616700020322616700020319122616700020319122616700020319122616700
このようにしてシリアライズしたデータを次のようにclient.sendall()でクライアントに送信します。
client.sendall(serialized_mesh_data)
以上でBlenderからUnityにデータを渡す処理になります。
次回はUnity側について紹介します。