ゲーム結果のデータを送ってみよう

9d2c38e6fe48e61528f6b2d34370768f

この章で学ぶこと

ゲーム結果のデータを送ってみよう

この章では、Unity からシンプルなゲーム結果ポイントを JsonUtility を使って JSON データを作成してサーバに送ってみます。

授業をはじめる前に教材の更新

以下のテキストを参考に Unity 側とサーバー側の教材を更新します。

授業をはじめる前に教材の更新

サーバの起動

0a3a35f3418068b7713ddaa729f2c660

  • ターミナルで npx node-red -u week03-chapter01 でサーバ起動
  • ポートタブで今回のサーバ起動を公開
  • シークレットウィンドウで今回のサーバが公開されているか確認します

こちらの手順を進めます。

alt text

Node-RED エディタでフローを見てみましょう。

✅ポイント

  • 今回は POST リクエストで 1 つの仕組みを作っています
  • /api/post/result というパスで POST リクエストでアクセスすると {"result":"OK"} という JSON データが取得できます
    • こちらに POST リクエストするとき Unity 側から {"point":1000} というダミーのゲーム結果ポイントをサーバに送ります
    • 取得した {"result":"OK"} を Unity 内の result というプロパティで扱ってシーンのテキストに反映します

今回の Unity シーンを起動

6049726527f3133083e8ca07d1e6261c

Project タブから Assets > Scenes を選択します。 Week03-Chapter01 をダブルクリックして起動しましょう。

Week03_Chapter01_CubeEvent.cs 変更

Assets/Scripts/Week03_Chapter01_CubeEvent.cs をエディタで開きます。

using UnityEngine;
using UnityEngine.EventSystems;

using System.Collections;       // IEnumerator のための参照
using UnityEngine.Networking;   // UnityWebRequest のための参照
using System;                   // Serializable のための参照
using System.Text;              // Encoding のための参照

public class Week03_Chapter01_CubeEvent : MonoBehaviour, IPointerClickHandler
{
    // 受信した JSON データを Unity で扱うデータにする ResultResponseData ベースクラス
    [Serializable]
    public class ResultResponseData
    {
        // result というプロパティ名で string 型で変換
        public string result;
    }

    // 送信する Unity データを JSON データ化する PointRequestData ベースクラス
    [Serializable]
    public class PointRequestData
    {
        // point というプロパティ名で int 型で変換
        public int point;
    }

    // アクセスする URL
    // サーバーURL + /api/post/result でアクセス
    string urlGitHub = "ここにサーバーURLを入れる";

    public void OnPointerClick(PointerEventData eventData)
    {
        // マウスクリックイベント
        // Debug.Log($"オブジェクト {this.name} がクリックされたよ!");

        // HTTP リクエストを非同期処理を待つためコルーチンとして呼び出す
        StartCoroutine("PostPointData");
    }

    // POST リクエストする本体
    IEnumerator PostPointData()
    {
        // HTTP リクエストする(POST メソッド) UnityWebRequest を呼び出し
        // アクセスする先は変数 urlGitHub で設定
        UnityWebRequest request = new UnityWebRequest(urlGitHub, "POST");


        // PointRequestData ベースクラスを器として呼び出す
        PointRequestData pointRequestData = new PointRequestData();
        // データを設定
        pointRequestData.point = 1000; // ダミーで 1000 pt のゲーム結果を送る

        // 送信データを JsonUtility.ToJson で JSON 文字列を作成
        // pointRequestData の構造に基づいて変換してくれる
        string strJSON = JsonUtility.ToJson(pointRequestData);
        Debug.Log($"strJSON : {strJSON}");
        // 送信データを Encoding.UTF8.GetBytes で byte データ化
        byte[] bodyRaw = Encoding.UTF8.GetBytes(strJSON);

        // アップロード(Unity→サーバ)のハンドラを作成
        request.uploadHandler = new UploadHandlerRaw(bodyRaw);
        // ダウンロード(サーバ→Unity)のハンドラを作成
        request.downloadHandler = new DownloadHandlerBuffer();

        // JSON で送ると HTTP ヘッダーで宣言する
        request.SetRequestHeader("Content-Type", "application/json");

        // リクエスト開始
        yield return request.SendWebRequest();

        // 結果によって分岐
        switch (request.result)
        {
            case UnityWebRequest.Result.InProgress:
                Debug.Log("リクエスト中");
                break;

            case UnityWebRequest.Result.Success:
                Debug.Log("リクエスト成功");

                // コンソールに表示
                Debug.Log($"responseData: {request.downloadHandler.text}");

                // ResultResponseData クラスで Unity で扱えるデータ化
                ResultResponseData resultResponse = JsonUtility.FromJson<ResultResponseData>(request.downloadHandler.text);

                // MessageText に結果テキスト割り当て
                GameObject.Find("MessageText").GetComponent<TextMesh>().text = resultResponse.result;

                break;
        }

    }
}

以下を修正します。

// アクセスする URL
// サーバーURL + /api/post/result でアクセス
string urlGitHub = "ここにサーバーURLを入れる";

こちらをサーバー URL に /api/post/result というパスを加えて変更して保存します。

解説していきます。

// 受信した JSON データを Unity で扱うデータにする ResultResponseData ベースクラス
[Serializable]
public class ResultResponseData
{
    // result というプロパティ名で string 型で変換
    public string result;
}

受信した JSON データを Unity で扱うデータにする ResultResponseData ベースクラスです。今回は {"result":"OK"} というデータを受け取るので、それに対応しています。

// 送信する Unity データを JSON データ化する PointRequestData ベースクラス
[Serializable]
public class PointRequestData
{
    // point というプロパティ名で int 型で変換
    public int point;
}

送信する Unity データを JSON データ化する PointRequestData ベースクラスです。今回は仮のゲーム点数 1000 を送る {"point":1000} というデータを受け取るので、それに対応しています。

// PointRequestData ベースクラスを器として呼び出す
PointRequestData pointRequestData = new PointRequestData();
// データを設定
pointRequestData.point = 1000; // ダミーで 1000 pt のゲーム結果を送る

JSON データに変換するために Unity でのデータの器を作ります。PointRequestData ベースクラスを器として用意します。

そして、pointRequestData に pointRequestData.point という形で、 1000 pt のゲーム結果を設定しています。

// 送信データを JsonUtility.ToJson で JSON 文字列を作成
// pointRequestData の構造に基づいて変換してくれる
string strJSON = JsonUtility.ToJson(pointRequestData);
Debug.Log($"strJSON : {strJSON}");
// 送信データを Encoding.UTF8.GetBytes で byte データ化
byte[] bodyRaw = Encoding.UTF8.GetBytes(strJSON);

送信データを JsonUtility.ToJson で JSON 文字列を作成します。ToJson は、分かりやすくクラスの構造に合わせて変換してくれます。

今回は PointRequestData の内容に合わせて、point という int 型の値があるので {"point":1000} と変換し strJSON の変数に入れます。

そして、実際にデータを送るときは byte 列にする必要があるので strJSON を byte[] bodyRaw = Encoding.UTF8.GetBytes(strJSON); で Raw データ(生のデータ)として bodyRaw に格納して送信前の準備をします。

// アップロード(Unity→サーバ)のハンドラを作成
request.uploadHandler = new UploadHandlerRaw(bodyRaw);
// ダウンロード(サーバ→Unity)のハンドラを作成
request.downloadHandler = new DownloadHandlerBuffer();

// JSON で送ると HTTP ヘッダーで宣言する
request.SetRequestHeader("Content-Type", "application/json");

UploadHandlerRaw、DownloadHandlerBuffer でデータの送受信(アップロードとダウンロード)を用意していますが、今回は JSON データで送るので request.SetRequestHeader で送る前に「これは JSON で送りますよ」と HTTP ヘッダーで宣言しています。

これで POST リクエストが JSON で送られます。

// ResultResponseData クラスで Unity で扱えるデータ化
ResultResponseData resultResponse = JsonUtility.FromJson<ResultResponseData>(request.downloadHandler.text);

// MessageText に結果テキスト割り当て
GameObject.Find("MessageText").GetComponent<TextMesh>().text = resultResponse.result;

JSON データを受信する仕組みは、以前学んだとおりです。

受け取った {"result":"OK"} JSON データを ResultResponseData クラスで Unity で扱えるデータ化を行って、MessageText に結果テキスト割り当てています。

動かしてみる

ad833d19086696f4841ff7d11828b4fb

Play ボタンをクリックします。

alt text

再生されたあと、Cube をクリックするとサーバとデータのやり取りが行われて {"point":1000} がサーバーに送信されて、サーバーから取得した JSON データ {"result":"OK"} を JSONUtility で解析します。

172e77202148148d63c107761e7680fa

そして result 結果「OK」を Message テキストに割り当てました。

alt text

サーバー側でも debug ノードでデータ受信が行われていることも確認してみましょう!

alt text

このように受信されています。

今回の Codespace の終了

0a8b4cfb807e57ea1382292a757c6899

今回の Codespace 終了しておきましょう。

results matching ""

    No results matching ""