【制作実習】UnityのAndroid無料版でネットーワークプログラミングの調査

Unityのネットワークゲーミングサーバーといえば、Photonが注目を集めているようだ。

しかしだ。

現在では、このサービスを利用するためのandroid向けAPIはPro版にしか対応していない。

どうもAPIの内部で使用しているソケットがPRO版でしか使えないものだからみたい。

ギョギョギョ、と。

そうなの、と。

調べてみても、androidの無料版でネットワークゲームを実装する方法にかんするネタは見つけられなかった。

まだ試しては無いけれども、スクラッチでC#のソケットを使ってUDP通信やらRPCやらを実装するのは、セキュリティ的な制限がかかっているのかもしれない。

にしては、PRO版だと可能なのはどういうことよ。大人の事情なんでしょうかね。

また時間のあるときに、UnityのC#スクリプトから生ソケットで通信するスクリプトを書いて試してみようとは思うけれども、たぶん無理そうな予感。

自作するのも大変そうだしね。

そこで、別の方法を模索していたところ、次の方法で落ち着いた。

まず、コールアンドマジックでは、FPSやTPSで要求されるほど、リアルタイム性は必要がない。

用途としては、シーン開始前などにマップやイベント情報をダウンロードできることと、多少の遅延は許容できる程度のチャット機能、ターンベースのバトルが出来れる程度の通信機能があればよい。

なので、HTTP通信でテキスト情報を送受信する方法があればよい。(もちろん、andoroid無料版で使えること)

ネットやらライブラリ辞典やらを調べてみると、ありました。

WWW www = new WWW("http://host:port/");
yield return www;

という方法。

自サーバー上にNode.jsのサーバーを立てて、単純なテキストを返すサービスを実装して試してみた。

android無料版でビルドしたAPKから(もちろん実機)ちゃんと通信できました。

ただし、通信速度は遅い。

平均して0.5~1秒程度だが、遅いときは2~3秒かかるリクエストもある。

ギリ許容できるかどうかという範囲。

今回のリリースは、開発環境もゲームエンジンもアセットも可能な限り無償版で仕上げるという目標を掲げている。

とりあえず最低限の方法が見つかったので、通信速度に関しては、キャッシュ機構やインターフェースを工夫するなどして対応することにしたい。

ちなみに、クライアント側で試してみたロジックは以下となる。
以下のスクリプトを空のゲームオブジェクトにアサインして、テキストメッシュを画面の適当な場所に配置して参照を渡せばよい。

using UnityEngine;
using System.Collections;

public class GameMainScr : MonoBehaviour {

	public Rect buttonRect;

	public TextMesh data;

	public bool loading = false;

	void Start () {
		buttonRect.width = 150;
		buttonRect.height = 80;
		buttonRect.x = (Screen.width - buttonRect.width) / 2;
		buttonRect.y = (Screen.height - buttonRect.height) / 2;
	}

	void OnGUI()
	{
		GUI.enabled = !loading;

		if (GUI.Button(buttonRect, "GET"))
		{
			loading = true;
			StartCoroutine("GetFromHTTP");
		}
	}

	IEnumerator GetFromHTTP()
	{
		Debug.Log ("GetFromHTTP");

		WWW www = null;

		try
		{
			www = new WWW("http://host-or-ip:port/");

			yield return www;

			Debug.Log ("www.isDone:" + www.isDone);
			Debug.Log ("www.error:" + www.error);

			if (string.IsNullOrEmpty(www.error))
			{
				data.text = www.text;
			} 
			else 
			{
				data.text = www.error;
			}

		}
		finally
		{
			loading = false;
			if (www != null) 
			{
				www.Dispose();
			}
		}
	}
}

サーバーサイドの構築については次回の記事で紹介します。

4年前

コメントを残す

メールアドレスが公開されることはありません。