VRで炎の大佐になろう

#はじめに
本エントリーは[初めてのアドベントカレンダー](https://qiita.com/advent-calendar/2021/first-try)の25日目の記事となります。
ここまで読んでいただいた方々は、お付き合いいただきありがとうございました。
初めましての方はこれまでのエントリーをぜひ読んでください！

#概要
「〇〇爆発しろ！」というセリフを聞いたことはないでしょうか。
実際に爆発させるわけにはいかないので、VR空間で何とかできないかと考えた結果、某錬金術師漫画で素晴らしい大佐がいらっしゃったのを思い出したので作ってみました。

![Videotogif.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/349246/73822be2-23f1-2711-b5e9-a9c2f49ddf7e.gif)

これで皆さんも好きなだけ爆発させましょう！
※スクリプトのみ掲載しています。詳しい作り方、apkファイルが必要であればコメントかtwitterにでも連絡ください。

#開発環境
Windows10
Unity 2020.3.10f1

#スクリプトについて

###着火部分
CustomHandprefab_Rにつけているスクリプトです。
親指と中指がついている状態でフラグをつけ、フラグがついた状態で親指と中指が離れると火が手首の方向に出るようになっています。

```cs:FingerPinch.cs
using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class FingerPinch : MonoBehaviour
{
    [SerializeField]
    OVRHand ovrHand;

    bool Pinched_flag = false;
    public GameObject bullet;

    void Update()
    {
        if (ovrHand.GetFingerIsPinching(OVRHand.HandFinger.Thumb) &&
            ovrHand.GetFingerIsPinching(OVRHand.HandFinger.Middle))
        {
            Pinched_flag = true;
        }
        if (!(ovrHand.GetFingerIsPinching(OVRHand.HandFinger.Thumb) &&
            ovrHand.GetFingerIsPinching(OVRHand.HandFinger.Middle)))
        {
            if (Pinched_flag == true)
            {
                Pinched_flag = false;
                GameObject runcherBullet = GameObject.Instantiate(bullet) as GameObject; 
                runcherBullet.GetComponent<Rigidbody>().velocity = transform.forward * 8.0f; 
                runcherBullet.transform.position = transform.position;
            }
        }
    }
}
```

球を発射する部分は以下の記事にお世話になりました。

https://qiita.com/Eureka/items/e0ca38903d7b56a29dcc

###爆発部分
発射される火のプレハブについているスクリプトです。
何かに当たった瞬間、火のプレハブを削除し、爆発エフェクトを出しつつ周りにあるものを吹き飛ばすようになっています。


```cs:on_collision_delete.cs
using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class on_collision_delete : MonoBehaviour
{
    [SerializeField] float m_force = 20;
    [SerializeField] float m_radius = 5;
    [SerializeField] float m_upwards = 0;

    //倒したときのエフェクト
    public GameObject breakEffect;

    // Update is called once per frame
    void OnCollisionEnter(Collision collision)
    {
        Destroy(gameObject);
        //エフェクトを発生させる
        GenerateEffect();
    }

    //エフェクトを生成する
    void GenerateEffect()
    {
        //エフェクトを生成する
        GameObject effect = Instantiate(breakEffect) as GameObject;
        effect.transform.position = gameObject.transform.position;
        // 範囲内のRigidbodyにAddExplosionForce
        Collider[] hitColliders = Physics.OverlapSphere(effect.transform.position, m_radius);
        for (int i = 0; i < hitColliders.Length; i++)
        {
            var rb = hitColliders[i].GetComponent<Rigidbody>();
            if (rb)
            {
                rb.AddExplosionForce(m_force, effect.transform.position, m_radius, m_upwards, ForceMode.Impulse);
            }
        }

    }
}

```

爆発で押しのける部分は以下のサイトにお世話になりました。
https://raspberly.hateblo.jp/entry/AddExplosionForce

###エフェクトについて
AssetstoreのParticlePackからMiddleframeとBigexplosionを用いています。

https://assetstore.unity.com/packages/essentials/tutorial-projects/unity-particle-pack-127325?locale=ja-JP



#まとめ
簡単にですが、核となる発射と爆発のスクリプトを掲載させていただきました。
同じことをやりたいと思ってる方の参考になれば幸いです。
途中にも書きましたが、詳しい内容が気になる方がいらっしゃればコメントください。
卒論が終わり次第頑張って書いてみます。
VRで魔法などを打つことに興味があるので、これからも何か作っていく所存です。

#おわりに
初めてのアドベントカレンダーにご参加いただいた方々、誠にありがとうございました！
自分が記事を書いてみたいという思いを叶えるために始めたことでしたが、多くの方にもご参加いただけて本当に嬉しかったです。
今回の宣伝や記事の執筆だけでなく、ハッカソンなどでもお世話になった@hironomiu、多くの宣伝をしていただいたチームメンバーの@y-yanaには特に感謝を申し上げます。
改めて、ここまでお付き合いいただきありがとうございました！
皆様のアウトプットがさらに進むことをお祈り申し上げます。