Unityでボーリングゲームを作る #3 倒れていないオブジェクトを数える

投稿者: | 2020-01-26


倒れずに立ったままのピンの数だけを数えてみます。

まずボーリングのピンのプレハブに「Pin」タグを付けます。

新しく空のゲームオブジェクトを作って、新規スクリプトを付けました。

このスクリプトで、ピンの回転値からそのピンが倒れているかを判断して、倒れていなければ数に入れます。

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


public class GameScript3 : MonoBehaviour
{
    public Text text;
    GameObject[] pins;
    public float q = 0.01f;

    // Start is called before the first frame update
    void Start()
    {
        text.text = "";
    }

    // Update is called once per frame
    void Update()
    {
        if(Input.GetKeyDown(KeyCode.C))
        {
            if (text.text == "")
            {
                text.text = CountStandingPins().ToString();
            }
            else {
                text.text = "";
            }
            
        }
    }

    int CountStandingPins()
    {
        pins = GameObject.FindGameObjectsWithTag("Pin"); //「Pin」タグのついたオブジェクトを探して、全て配列pinsにいれる

        if(pins.Length == 0)
        {
            return 0;
        }
        else
        {
            int n = 0;

            foreach(GameObject pin in pins)
            {
                if(pin.transform.rotation.x * pin.transform.rotation.x < q && pin.transform.rotation.z * pin.transform.rotation.z < q)
                {
                    n++;
                }
           }
            return n; // 立っているピンの個数を返す
        }     
    }

}

テスト用に「C」キーを押すと倒れていないピンのオブジェクトの数が画面に表示されるようにしました。ピンの数が表示されている時に「C」キーを押すとテキストが消えます。

関数CountStandingPins()を作って、その中でシーン上の「Pin」タグのついたオブジェクトを検索し、配列に入れています。

pins = GameObject.FindGameObjectsWithTag("Pin"); 

配列の中にピンのオブジェクトがあれば、foreach文で一つ一つ見ていって、X,Z座標の回転値の2乗の値が十分小さければ、倒れてないと判断してカウントしています。

int n = 0;

foreach(GameObject pin in pins)
{
    if(pin.transform.rotation.x * pin.transform.rotation.x < q && pin.transform.rotation.z * pin.transform.rotation.z < q)
    {
        n++;
    }
}
return n; // 立っているピンの個数を返す

transform.rotationの値はマイナスにもなるので2乗を使っています。

Y座標は上向きを軸にした回転値であり、いくら回転していても倒れないのでX座標とZ座標だけを見ています。

これで、倒れているピンのオブジェクトの数を数えられました。

ピンのプレハブにもスクリプトを付けて、とりあえず落下したらピンのオブジェクトが破壊されるようにしています。

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

public class PinScript : MonoBehaviour
{
    // Start is called before the first frame update
    void Start()
    {
        
    }

    // Update is called once per frame
    void Update()
    {
        if(transform.position.y < -5f)
        {
            Destroy(gameObject);
        }
    }
}

ピンが落下すると、ヒエラルキーウィンドウの「bowling_pin」というオブジェクトが消えます。

ボーリングレーンの準備

ボーリングの規格のサイズに合わせてレーンを作ったつもりなのですが、ボールがうまくガターの溝にはまらなかったので、溝の幅を大きくしました。

Blenderで少しずつ大きくしては、Unityに持ってきてボールを投げてみるというのを繰り返しました。

結構大きくなりましたが、ちゃんと溝にはまってくれます。

また、そのままではボールが摩擦によって減速してしまったので、Projectの適当なフォルダで右クリックして、Create -> Physic Materialから物理特性マテリアルを作りました。
そしてとりあえず摩擦の値を0にしました。

これをレーンのメッシュコライダーのMaterialにアタッチしました。

これでレーン上のオブジェクトがよく滑るようになりました。

ボールとピンの重さ

ボールとピンの重さにリアルな値を設定してみました。オブジェクトの重さはオブジェクトに付けたRigidbodyコンポーネントのmassの値で変更できます。

単位はKg(キログラム)です。


スケールを3倍にしているので、そのままの値を入れるのは適切でないかもしれません。

コメントを残す

メールアドレスが公開されることはありません。