環境構築とライブラリの準備
Protocol Buffers(Protobuf)をUnityで利用するには、C#用のランタイムライブラリと、.protoファイルからC#ソースコードを生成するためのコンパイラ(protoc)が必要です。
1. 公式リポジトリからソースコードとWindows用バイナリ(win64)をダウンロードします。
2. Visual StudioでC#プロジェクトを開き、メニューバーから「ツール > NuGet パッケージマネージャー > ソリューションの NuGet パッケージの管理」へ進みます。Google.Protobufを検索し、ダウンロードしたコンパイラとバージョンを合わせて(例: 3.25.3)インストールします。
3. ビルド完了後、生成されたDLLファイルをUnityプロジェクトのPluginsフォルダ等に配置します。
スキーマ定義とコード生成
テキストファイルを作成し、拡張子を.protoに変更してスキーマを定義します。ここでは例としてUserProfile.protoを作成します。
syntax = "proto3";
package GameModels;
message UserProfile {
string username = 1;
int32 level = 2;
int64 score = 3;
message ContactMethod {
string address = 1;
DeviceCategory platform = 2;
}
repeated ContactMethod contacts = 4;
}
enum DeviceCategory {
UNKNOWN = 0;
PC = 1;
CONSOLE = 2;
MOBILE = 3;
}次に、このファイルをコンパイルするためのバッチファイル(build_proto.bat)を同じディレクトリに作成し、protocのコマンドを記述して実行します。実行後にUserProfile.csが生成されます。
Unityでのシリアライズユーティリティ実装
生成されたC#スクリプトをUnityのProtoフォルダに配置します。次に、Protobufのエンコード・デコード処理を簡略化するための汎用クラスProtobufConverter.csを作成します。
using Google.Protobuf;
public static class ProtobufConverter
{
public static byte[] Encode(IMessage msg)
{
return msg.ToByteArray();
}
public static T Decode<T>(byte[] data) where T : IMessage, new()
{
var template = new T();
return (T)template.Descriptor.Parser.ParseFrom(data);
}
}動作確認
最後に、シリアライズとデシリアライズが正しく行われるかテストするスクリプトProtoDemo.csを作成し、メインカメラ等にアタッチして実行します。
using GameModels;
using UnityEngine;
public class ProtoDemo : MonoBehaviour
{
void Start()
{
var profile = new UserProfile
{
Username = "hero",
Level = 42,
Score = 15000
};
profile.Contacts.Add(new UserProfile.Types.ContactMethod
{
Address = "support@mail.com",
Platform = DeviceCategory.PC
});
byte[] encodedData = ProtobufConverter.Encode(profile);
Debug.Log($"エンコード後のバイト長: {encodedData.Length}");
var decodedProfile = ProtobufConverter.Decode<UserProfile>(encodedData);
Debug.Log($"ユーザー名: {decodedProfile.Username}");
Debug.Log($"レベル: {decodedProfile.Level}");
Debug.Log($"スコア: {decodedProfile.Score}");
Debug.Log($"プラットフォーム: {decodedProfile.Contacts[0].Platform} - 連絡先: {decodedProfile.Contacts[0].Address}");
}
}