【Blender、Unity】サンタ娘がトナカイ(?)に乗ってプレゼント爆弾を投げる【C#】

サンタトナカイ/トップ

Blender2.79b
Unity2019.2.2f1
Windows10

サンタトナカイ/トップ

今年はクリスマスらしいことをしようとサンタ娘がトナカイ(?)に乗ってプレゼント爆弾を投げるゲームの動画にしました。

来年はもっと高度なゲームにしたいものです。

■トナカイとサンタ娘とプレゼントボックス

トナカイは以前紹介した乗馬のアセットを改造したものです。
サンタ娘の操作とカメラもそこから。
Horse Realistic(Can be Called)のPrefabを使いましたが、2019だとメッシュが崩れるので、メッシュとアーマチュアをHorse Polyに変更します。
サンタ娘もメッシュとアーマチュアをRiderから変更したものです。
Blenderで作った角はCGアーマチュアのNeck2の子オブジェクトにしたら具合が良かったです。

サンタトナカイ/角

あと忘れてはいけないのは馬の元のアーマチュアからMount Pointsを移しておくことで、これがないと乗馬できません。
以前と同じくCGアーマチュアのSpine1の子オブジェクトにしておきます。

プレゼントボックスは以前Blenderで作ったものですが、空のオブジェクトにプレゼントボックスと爆発のPrefabを子オブジェクトとして置きました。
その2つの表示を入れ替える形で爆弾が爆発するように見せています。

サンタトナカイ/Hierarchy/プレゼント爆弾

■他のソースコード

どれも簡単なものですが備忘録的に載せておくことにします。
BGMはAudioSourceコンポーネントをそのまま使いました。

モンスターのスクリプトはこちら。
単に追いかけてきて爆発のコライダーに触れると倒れるだけです。
あとその時に撃破数のカウンターをひとつ足します。

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.AI;
[RequireComponent(typeof(CapsuleCollider))]
[RequireComponent(typeof(Rigidbody))]
[RequireComponent(typeof(NavMeshAgent))]
public class Monster : MonoBehaviour
{
private GameObject player;
NavMeshAgent agent;
Animator animator;
Rigidbody rb;
CapsuleCollider caps;
bool defeat = true;
void Start()
{
agent = GetComponent<NavMeshAgent>();
animator = GetComponent<Animator>();
caps = GetComponent<CapsuleCollider>();
rb = GetComponent<Rigidbody>();
player = GameObject.Find("SantaRider");
}
void Update()
{
agent.destination = player.transform.position;
rb.constraints = RigidbodyConstraints.FreezePosition;
}
private void OnTriggerEnter(Collider other)
{
if (other.gameObject.tag == "Explosion" && defeat)
{
agent.isStopped = true;
animator.SetBool("IsDead", true);
caps.enabled = false;
GameObject defeatObj = GameObject.Find("DefeatCount");
DefeatCount defeatScr = defeatObj.GetComponent<DefeatCount>();
defeatScr.AddCount();
defeat = false;
}
}
}
view raw 49.cs hosted with ❤ by GitHub

AnimatorControllerはこのようなシンプルなものです。

サンタトナカイ/モンスター/AnimatorController

スポンサーリンク

次はモンスター生成のスクリプトです。
1秒ごとに生成し、そのたびにモンスター数のカウンターを1つ足します。

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class Generator : MonoBehaviour
{
public GameObject greenMan;
private float time;
private float interval = 1f;
DefeatCount defeatCount;
void Start()
{
defeatCount = GameObject.Find("DefeatCount").GetComponent<DefeatCount>();
}
void Update()
{
time += Time.deltaTime;
if(time > interval)
{
GameObject copy = Instantiate(greenMan, this.transform.position,
Quaternion.identity);
defeatCount.AddMonsterCount();
time = 0;
}
}
}
view raw 49a.cs hosted with ❤ by GitHub

次はカウンターのスクリプトです。
モンスターが撃破された時にAddCount()が、モンスターが生成された時はAddMonsterCount()が呼ばれることでテキストの数字を足していきます。

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UI;
public class DefeatCount : MonoBehaviour
{
public Text text;
private int count = 0;
private int monster = 0;
void Awake()
{
text.text = count.ToString() + " / " + monster.ToString();
}
void Update()
{
text.text = count.ToString() + " / " + monster.ToString();
}
public void AddCount()
{
count += 1;
}
public void AddMonsterCount()
{
monster += 1;
}
}
view raw 49b.cs hosted with ❤ by GitHub

次はプレゼント爆弾のスクリプトです。
子オブジェクトのプレゼントボックスと爆弾の表示/非表示を入れ替える形になっています。
爆弾のPrefabが表示されてから1秒後に非表示になりますが、Destroy()でも問題なかったはずですが試行錯誤の中でそのままになりました。

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class PresentBomb : MonoBehaviour
{
private GameObject present;
private GameObject explosion;
private bool bomb = true;
AudioSource audioSource;
void Start()
{
present = transform.Find("Present").gameObject;
explosion = transform.Find("Detonator-Spray").gameObject;
present.SetActive(true);
explosion.SetActive(false);
audioSource = GetComponent<AudioSource>();
}
private void OnCollisionEnter(UnityEngine.Collision collision)
{
if (bomb)
{
present.SetActive(false);
explosion.SetActive(true);
bomb = false;
audioSource.Play();
Invoke("BombDestroy", 1f);
}
}
private void BombDestroy()
{
explosion.SetActive(false);
//Destroy(this.gameObject);
}
}
view raw 49c.cs hosted with ❤ by GitHub

次はプレゼント爆弾の生成と発射のスクリプトです。
Eキーで生成し、爆弾のRigidbodyを取得してAddForceで真上に打ち出します。
思うように飛ばず悩みましたが、それは子オブジェクトの方にもRigidbodyをつけていたせいでした。
生成する位置は空のオブジェクトを馬の子オブジェクトにしたもので、Inspectorから登録します。

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class ShotPresent : MonoBehaviour
{
public GameObject present;
public GameObject shotPos;
Rigidbody rb;
void Update()
{
if (Input.GetKeyDown(KeyCode.E))
{
GameObject copy = Instantiate(present, shotPos.transform.position,
Quaternion.identity);
rb = copy.GetComponent<Rigidbody>();
rb.AddForce(transform.up * 500);
}
}
}
view raw 49d.cs hosted with ❤ by GitHub

■使用した無料アセット

Character Monster 1
追いかけてくる緑の人。
走るアニメーションがLoopになっていないことに要注意。

Winter Zone Mini
Terrainの雪景色の素材です。
Cameraにブリザードを追加するPrefabもあります。

Detonator Explosion Framework
色んな爆発があります。

Christmas Music – Loop Instrumental
クリスマスの曲です。

■関連記事

「Blender標準テクニック」でアニメ美少女作成に挑戦!その成果を発表します

【Blender、Unity】ハロウィンパレード2019の動画を作りました【C#】

スポンサーリンク

目次に戻る