オープンキャンパスで使用したunityプロジェクト

はじめに

2022年7月16日に行われた福知山公立大学オープンキャンパスで山本ゼミでは脱出ゲームを を行うこととなった。
その中で私はお客が使用するwebページの作成と脱出ゲーム内で使用する unityプログラムの作成を行った。ここではunityプログラムについて記述する。


unityプログラム

脱出ゲームにお客が参加するには専用webページからユーザ登録を行う。 ユーザ登録を行うと各お客にQRコード(3桁の数字)が発行される。このQRコードには脱出ゲ ームのクリア状況が保存され、これをunityで読み 込むとクリア状況に応じた演出が行われるようになっている。

以下はデモ動画である。

デモ動画のように各客のクリア状況に合わせてアニメーションが 再生される。オープンキャンパスでは音声も再生されていたが、 デモ動画では音声を再生させていない。
再生されるアニメーションは以下の4通りある。

使用したVRMダウンロードサイト

VRoidHub  AvatarSample_A
VRoidHub  AvatarSample_B
VRoidHub  AvatarSample_C
ニコニコ立体  アリシア・ソリッド


使用したソースコード

        
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.Networking;
using System.IO;
using System.Text;
using UnityEngine.UI;

public class Move : MonoBehaviour
{
    int count = 0;
    float resetTime = 0;
    float setrunTime = 0;
    float runTime = 0;
    string id = "";
    string setid;
    string customerinformation;

    int idline = 0;
    int passline = 4;
    int avaid;
    int avaline = 3;
    int avaNumber = 4; //アバターの数

    int pattern = 0;

    bool pin = false;

    public GameObject panel;
    private GameObject abaTarget;
    private AudioClip testsounds;
    private GameObject prefab;
    private AudioSource audiosouce;
    private Animator animator;

    private GameObject jimaku;
    private GameObject setjimaku;

    Image fadeImage;
    float fadeSpeed = 0.02f;
    float red, green, blue, alfa;

    bool isFadeOut = false;
    bool isFadeIn = false;

    bool oneSet;

    public GameObject Jimaku;
    public Image serihu;

    private Sprite setJimaku;
    
    // Start is called before the first frame update
    void Start()
    {
        fadeImage = panel.GetComponent<Image>();
        red = fadeImage.color.r;
        blue = fadeImage.color.b;
        green = fadeImage.color.g;
        alfa = fadeImage.color.a;

        bool oneset = false;
    }

    // Update is called once per frame
    void Update()
    {
        checkCode();

        if (oneSet)
        {
            runTime += Time.deltaTime;
        }
    }
    void FixedUpdate()
    {
        if (oneSet)
        {
            fadeOutIn();
        }
    }

    void fadeOutIn()
    {
        if (isFadeOut)
        {
            fadeout();
        }
        if (isFadeIn && runTime - setrunTime >= 1.0)
        {
            fadein();
        }
    }
    IEnumerator ChekingSound()
    {
        //Debug.Log("音声の再生チェック開始");
        while (true)
        {
            yield return new WaitForFixedUpdate();
            if (!audiosouce.isPlaying)
            {
                animator.SetBool("serihu" + pattern, false);
                //Debug.Log("終了");
                pin = false;
                isFadeOut = true;
                fadeOutIn();
                break;
            }
        }
    }

    void fadeout()
    {
        fadeImage.enabled = true;
        alfa += fadeSpeed;
        SetAlpha();
        if (alfa >= 1)
        {
            setrunTime = runTime;
            isFadeOut = false;
            isFadeIn = true;

            if (pin)
            {
                prefab = (GameObject)Resources.Load("Prefabs/VRM/Avatar" + avaid + "/Avatar" + avaid);
                Debug.Log("Jimaku/avatar" + avaid + "jimaku" + pattern);
                abaTarget = Instantiate(prefab, new Vector3(-0.5f, 0.0f, 0.0f), Quaternion.Euler(0, 26, 0));

                setJimaku = Resources.Load<Sprite>("Jimaku/avatar" + avaid + "jimaku" + pattern);
                serihu.sprite = setJimaku;
                Jimaku.SetActive(true);
                //setjimaku = Instantiate(jimaku, new Vector3(0.3f, 1.1f, 0.42f), Quaternion.Euler(0, 180, 0));
                audiosouce = abaTarget.GetComponent<AudioSource>();
                animator = abaTarget.GetComponent<Animator>();
                testsounds = (AudioClip)Resources.Load("souds/serihu" + avaid + "joukyou" + pattern); //音声ファイルが揃ったらこっちを使う
                //testsounds = (AudioClip)Resources.Load("souds/serihu");
                Debug.Log("pattern : " + pattern);
            }
            else
            {
                Destroy(abaTarget);
                Jimaku.SetActive(false);
            }
        }
    }
    void fadein()
    {
        alfa -= fadeSpeed;
        SetAlpha();
        if (alfa <= 0)
        {
            isFadeIn = false;
            fadeImage.enabled = false;
            setrunTime=0;
            if (pin)
            {
                audiosouce.PlayOneShot(testsounds);
                animator.SetBool("serihu" + pattern, true);
                StartCoroutine(ChekingSound());
            }
            else
            {
                oneSet = false;
                runTime = 0;
                pattern = 0;
            }
        }
    }

    void SetAlpha()
    {
        fadeImage.color = new Color(red, green, blue, alfa);
    }

    void idreset()
    {
        setid = "";
    }
    void AbatorMove()
    {
        //Debug.Log(customerinformation);
    }

    IEnumerator GetText(string target)
    {
        UnityWebRequest www = UnityWebRequest.Get("https://www.48v.me/~mizunoshota/oc/h/users/" + target + ".csv");
        yield return www.SendWebRequest();

        if (!oneSet)
        {
            if (www.isNetworkError || www.isHttpError)
            {
                Debug.Log(www.error);
            }
            if (log.isNetworkError || www.isHttpError)
            {
                Debug.Log(log.error);
            }
            else
            {
                // 結果をテキストして保持
                string lines = www.downloadHandler.text;
                string logs = log.downloadHandler.text;
                string[] li = lines.Split("\n");
                for (int i = 0; i < li.Length; i++)
                {
                    string[] lineSepa = li[i].Split(",");

                    if (target == lineSepa[idline])
                    {
                        for (int v = passline; v < passline + 3; v++)
                        {
                            if (lineSepa[v].Substring(0, 4) == "True")
                            {

                                pattern += 1;
                            }
}

                        avaid = int.Parse(lineSepa[avaline]);
                        //Debug.Log(avaid);
                        oneSet = true;
                        isFadeOut = true;
                        pin = true;
                        customerinformation = lineSepa[avaline];
                        AbatorMove();
                    }
                }

            }

        }

    }

    void checkCode()
    {
        resetTime += Time.deltaTime;

        if (Input.GetKeyDown(KeyCode.R))
        {
            id = "";
        }
        if (resetTime >= 10.0)
        {
            id = "";
            resetTime = 0;
        }
        if (Input.GetKeyDown(KeyCode.Alpha0))
        {

            id += "0";
            count += 1;
        }
        if (Input.GetKeyDown(KeyCode.Alpha1))
        {
            id += "1";
            count += 1;
        }
        if (Input.GetKeyDown(KeyCode.Alpha2))
        {
            id += "2";
            count += 1;
        }
        if (Input.GetKeyDown(KeyCode.Alpha3))
        {
            id += "3";
            count += 1;
        }
        if (Input.GetKeyDown(KeyCode.Alpha4))
        {
            id += "4";
            count += 1;
        }
        if (Input.GetKeyDown(KeyCode.Alpha5))
        {
            id += "5";
            count += 1;
        }
        if (Input.GetKeyDown(KeyCode.Alpha6))
        {
            id += "6";
            count += 1;
        }
        if (Input.GetKeyDown(KeyCode.Alpha7))
        {
            id += "7";
            count += 1;
        }
        if (Input.GetKeyDown(KeyCode.Alpha8))
        {
            id += "8";
            count += 1;
        }
        if (Input.GetKeyDown(KeyCode.Alpha9))
        {
            id += "9";
            count += 1;
        }

        if (id.Length == 3)
        {
            resetTime = 0;
            setid = id;
            Debug.Log(setid);
            StartCoroutine(GetText(setid));
            idreset();
            id = "";
            count = 0;
        }
    }
}
        

参考

UnityのSEが鳴り終わったタイミングで処理を実行する(callback)
【Unity】Humanoidアニメの作り方【無料完結】
ヒエラルキーのオブジェクト取得
Unityで簡単なタイピングソフトを作成する

使用したアセット
Free Medieval Room