AIプログラムとかUnityゲーム開発について

探索や学習などを活用したAI系ゲームを作りたいと思います。

ユニークIDの保存

サーバーに配置データを保存するにあたり、ユーザーを区別するためにユニークIDを発行しなければならない。
また、ユニークIDはローカルに保存しておいて、アプリを起動するたびに同じIDが読み込まれるようにする必要がある。



データをセーブするには、以前の記事に書いたSaveData.csを使う。

yasu9780.hatenablog.com



セーブデータは以下のような構造とする。

    class Player
    {
        public string uuid;
        public int mode;
        public Vector3[] pos;
        public int[] type;
        public Player()
        {
            uuid = "";
            mode = 0;
            pos = new Vector3[100*3];
            type = new int[100 * 3];
            for (int i = 0; i < 100 * 3; i++) type[i] = -1;
        }
    }
    Player player;

ユニークIDはuuidに保存されている。


起動時に、以下のような処理を入れる

   void Start () {

        player = SaveData.GetClass<Player>("p1", new Player());
        if(player.uuid=="")
        {
            System.Guid guid = System.Guid.NewGuid();
            player.uuid = guid.ToString();

            SaveData.SetClass<Player>("p1", player);
            SaveData.Save();
        }
        Debug.Log("uuid=" + player.uuid);

p1というキーで保存されているデータを読み込む。
初回はデータが無いので、new Player()の結果が返ってくる。
コンストラクターがuuidに""に代入しているので、初回はuuidが空として、uuid発行処理が走る。UUIDを発行したので、p1をキーとしてplayerをセーブする。

一度アプリを終了させ、次回の起動では、SaveData.GetClassの読み込みでuuidが入っているので、uuid発行処理は今度は走らない。

これで、初回時はuuid発行。以後は同じuuidが起動時にセットされるという処理ができた。

キャラ配置をVPSサーバーに保存・読み込み成功

キャラを配置して、Saveボタンを押すと、キャラ配置データをCSVにして、HTTPのGETでVPSサーバーのCGIに転送
LOADボタンを押すと、VPSサーバーのCGIからデータを取得して、キャラ配置を再現。
f:id:yasu9780:20170324194944p:plain


phpMyAdminで確認すると、MySQLに保存したCSVデータが入っているレコードができている。

f:id:yasu9780:20170324194950p:plain

テスト用で、useridは1になっているが、スマホ上のユニークIDをユーザーIDとして実行すれば、
ユニークIDごとに配置データをVPS上に保存できる。

後は、別のスマホから保存した配置データをLOADできるようにすれば、違うユーザー同士で対戦が可能になる。



回転向きは固定なので保存する必要なし。本来はY座標も固定なんですが、いちおう保存します。typeはキャラ種別。

        if(no == 2 && !battle) // save
        {
            string temp = "";
            for (int i = 0; i < 100; i++)
            {
                if (ch[i] == null) continue;
                temp += chcc[i].type + ",";
                temp += ch[i].transform.position.x.ToString("0.0") + ",";
                temp += ch[i].transform.position.y.ToString("0.0") + ",";
                temp += ch[i].transform.position.z.ToString("0.0") + "@";
            }

            StartCoroutine(HttpGet("http://VPSURL/?u=1&d="+temp,0));
        }

魔法のエフェクト追加

http://27.120.88.154/rts7.gif
範囲攻撃は突き抜けるので、縦に並んでいる敵には有利ですね。
最後は、ダブルノックアウトw


assetStoreのこのパーティクルエフェクトを買いました。
Pinwheel Fantasy Effect
https://www.assetstore.unity3d.com/jp/#!/content/50310

ドキュメントを見ると、作者はベトナムの方でした。
30種類ぐらい入って$2ぐらいでお得でした。
パーティクルシステムも勉強しないと、ちょっといじりたいなと思ってもなかなかできないですね。

Vector3 pos = transform.position + Vector3.up*2.2f+transform.forward*1;
GameObject obj;
if (type == 3 ) // 魔法使い
{
        obj = (GameObject)Instantiate(Resources.Load("Magic"), pos, transform.rotation);
        obj.GetComponent<Magic>().power = attackPower;
        obj.GetComponent<Magic>().enemy = enemy;
        obj.GetComponent<Magic>().target = targetcc.gameObject;

        Vector3 pos2 = transform.position + Vector3.up * 0f;
        GameObject obj2;
        obj2 = (GameObject)Instantiate(Resources.Load("VenomSpell"), pos2, transform.rotation);
        Destroy(obj2, 3f);
}

Magicはトリガー付きの球です(MeshRenderが非表示)。攻撃力とターゲットを設定して生成。
緑色の魔法陣エフェクトを自分の足元で生成。Destroyは第二引数に時間を設定しておくと、指定時間後に自動削除されるので便利です。



親から、攻撃力と敵を与えられて生成される。Startで敵の方向ベクトルを作っておいて、後はひたすらその方向に移動していく。
球の大きなトリガーがついているので、触れた敵のGetDamage()を呼び出してダメージを与えます。
これが弓では何か敵に当たると、そこでデストロイしてますが、範囲攻撃の魔法はDestoryしないので、指定時間までは連続で殺傷できます。
ここでは寿命を3秒にしてますが、放っているキャラに応じて変えたい場合は、powerのように外部から値を渡せばいいです。

magic.cs

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class Magic : MonoBehaviour
{
    public float power;
    public GameObject target;
    public int enemy;

    Character targetcc;
    Main main;
    float timer;
    Vector3 fw;

    void Start()
    {
        main = GameObject.Find("Main").GetComponent<Main>();
        timer = 3f;
        targetcc = target.GetComponent<Character>();

        fw = (target.transform.position + Vector3.up * 2.5f - transform.position).normalized;

        Vector3 pos2 = transform.position + Vector3.up * 0f;
        GameObject obj2;
        obj2 = (GameObject)Instantiate(Resources.Load("IceSpear2"), pos2, transform.rotation,this.transform);
        Destroy(obj2, 3f);
    }

    void Update()
    {
        if (timer > 0) timer -= Time.deltaTime;
        else
        {
            Destroy(this.gameObject);
            return;
        }
        transform.position += fw * Time.deltaTime * 7;
    }
    void OnTriggerEnter(Collider other)
    {
        Character cc = other.GetComponent<Character>();
        //Debug.Log(other.name);
        if (cc != null && cc.enemy!=enemy ) cc.getDamage(power);
    }
}


Start()で、Destroy(this.gameObject,3f)としておけばupdate()でtimer更新はいらないですね。

SchoolGirlsSimulatorのロシア人のレビュー

SchoolGirls Simulator - Google Play の Android アプリ

Дарья Севрюк(2017/03/23、17:14) 0 0
ロシア語からの自動翻訳 - 元のレビューを表示
主よ!これは私が今まで彼の13年間プレーした最高のゲームです!ファンタスティック!私は言葉を持っていません!
唯一の管理は非常に快適ではありませんが、あなたは慣れます!あなたはこのゲーム、あなた自身でこのゲームのヒロイン感を再生します!
私は、これは神の遊びであり、最も大きなプラスは、それがインターネットなしであるということです何の言葉もありません!
ヒーローあなたは自分自身を作成することができます! 、zhresh、ezdiesh、殺すと言って、飛びます!いないファンタジーゲーム!
しかし、一つの小さな欠点は、英語のすべてが、あまりにも、ロシア語を追加してくださいということです!私は非常に感謝されます!

レビュー投稿ありがとうございます!
よく解らないけど、褒めてもらっているのかな?( ゚Д゚)
ロシア語はもちろん解らないから、英語にしてみてみよう。

Speak! This is the best game I've ever played in my 13 years! Fantastic !
 I have no words! Only control is not very convenient but then you can get used to it! 
When you play this game, it feels like you are the heroine of this game! I have no words this is the most divine game and the biggest plus is that it is without the Internet!
You can create a hero yourself! Fly, kill, ride, eat, say! Not a game but a fantasy !!!
 But one small disadvantage is that everything in English, please add Russian, too! I'll be very grateful!

そうそう。インターネットに接続はいらないんですよ。リソース関係は全部pkgに入ってますので、実行時になにかダウンロードしたりはしません。

あと、確かに操作性に問題があるかも。
ジョイパッド操作をスマホ上に再現してるだけなんで、本来は、スマホの最適なインタフェースは、指タッチとかドラッグなんだよね。
移動も、ジョイパッドじゃなくて、タッチした場所に移動するみたいなインタフェースが本当は望ましいのかもしれない。
Bluetoothゲームパッドなんか980円でamazonで買えるけど、普及率は低いというか、携帯端末にわざわざジョイパッドつなぐ人も少ないよね。

英語 (アメリカ合衆国)16.83%

スペイン語 (アメリカ合衆国)11.88%

日本語 (日本)10.89%

ロシア語 (ロシア)10.89%

ポルトガル語 (ブラジル)7.92%

ロシア語ユーザーはけっこう多いですね。
ロシア語版はいづれやりたいです。
google自動翻訳になっちゃいますけど。ただ、英語から訳すとして、それがまあまああってるかどうかがさっぱり解らないのが困りますね(^^;