ITの隊長のブログ

ITの隊長のブログです。Rubyを使って仕事しています。最近も色々やっているお(^ω^ = ^ω^)

まだ良くわかっていないんだけど色々なメモをする

スポンサードリンク

やりたいこと

  • Prefab用意して、Scriptから指定した分のGameObject(人)をばんばん作る
  • 作った人をManagerクラスかなにかに保持しておく
  • Cinemachineのfollowを切り替えられるようなクラスから、Managerクラスの人リストを引っ張ってきて、対象を切り替えられるようにしたい(これがやりたいこと)

よしやるぞ!

PrefabをInstantiate

ekulabo.com

よーし簡単そうだーってAssetを読み込む旅にでる。

Asset読み込みの旅

qiita.com

light11.hatenadiary.com

shikaku-sh.hatenablog.com

なるほど〜〜?なんかとりあえず色々種類を知る。

そしてなにか面倒ということを知る。

Addressables.InstantiateAsync を使うぞ!

神記事に出会う

blog.applibot.co.jp

よしやろうと思う。ドキュメント・・・

docs.unity3d.com

読みづらい。とりあえず試してみたところ、上手く言った。わーい。

NavMeshにInstantiateしたPrefabを配置したい

docs.unity3d.com

Cinemachineでどうやってfollow対象を切り替える?

nekojara.city

ayousanz.hatenadiary.jp

カメラ用のクラスもここで用意した。あとはManagerからひっぱるだけ。

インスタンス化したクラスを呼ぶ

futabazemi.net

2つのGameObjectがあるけどどっちが先に処理されるの?

tsubakit1.hateblo.jp

nekojara.city

なるほど。設定してみた。

しかし、うまくいかなかった。そうかコルーチンでやっているからか。というわけでawaitをができないかという旅にでた

awaitを使う旅

qiita.com

zenn.dev

初心者のためのTask.Run(), async/awaitの使い方 - Qiita

qiita.com

色々試したがだめで、どうやらAsync設定したメソッドがあると順序守るのむずいっぽいということになっている

コルーチンとUniRXをつかったらとりあえずManagerクラス側ではawaitを利用してちゃんと順序守ることはできたので、下記の様にした。

  • ManagerクラスStart()、カメラクラスStart()はほぼ同時 → Managerクラスでは生成したオブジェクトをリストに突っ込んでおく、カメラクラスでは何もしない
  • カメラクラス側でManagerクラスを引っ張ってきて、Updateメソッドでリストの数が0以外で前と変化がなくなるまで監視し続ける
  • 変化なくなったらカメラのfollowに突っ込むように変換して、キーボードのアクションできりかえられるようする

にした、嫌だこの設計。できれば順序よくやりたいが現時点だとよくわかっていない(特にカメラ側の監視とかいらないしバグのぬか床になりそう)

メインスレッドでしか使えない関数が多い件

baba-s.hatenablog.com

Task.Run(async () => await Method()) とかやるとすぐこれにハマるのでやめた。

GameObjectをComponentに貼り付けたScript(Class)にキャストしたいんだけど・・・?

無理です。GetComponentを使おう。

r-ngtm.hatenablog.com

docs.unity3d.com

qiita.com

qiita.com

なぜかPrefabにsetされているComponentのインスタンス化のタイミングが変

  private async void Start()
  {
        await StartCoroutine(Load("Assets/Prefabs/Robo.prefab"));
  }

    private IEnumerator Load(string address)
    {
        Vector3 point;
        var range = 200.0f;
        for (int i = 0; i < 5; i++)
        {
            if (RandomPoint(Vector3.zero, range, out point))
            {
                AsyncOperationHandle<GameObject> handle = Addressables.LoadAssetAsync<GameObject>(address);
                if (handle.Result != null)
                {
                    GameObject g = Instantiate(handle.Result, point, Quaternion.identity);
                    Human h = handle.Result.GetComponent<Human>();
                    this.humans.Add(h);
                }
                yield return handle;
            }
        }
    }

こう書くと、なぜかGetComponentで取得したHumanの位置が全部同じなので???になりました。 また、Humanクラス側でStartメソッドにログとか履くようにしてたが、コルーチンが終わった後にStartされたり、値が全然違うしさらに???となっていました。

んで、色々調べて下記の様に修正した。

                    GameObject g = Instantiate(handle.Result, point, Quaternion.identity) as GameObject;
                    Human h = g.GetComponent<Human>();

修正したら、あいかわらずコルーチン後にHumanクラス側の処理が走るが、位置などの値は同じになりました。そして無事カメラも追走?するように修正できました。

雑感

とてもとても大変でした。