0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

[Unity]カギを入手して扉をあけよう!

Last updated at Posted at 2023-11-26

限定公開から全体公開に移行しました。
この記事は、2019年に作成したものです。


今回は、迷路などで最初は通ることができない道を鍵取得などの特定条件を満たしたときに通れるようになる処理を作成していきます。

この記事で学べること

  • Unityでbool(真偽)を扱うことができるようになる。
  • 特定のタイミングでGameObjectを消すことができるようになる。
  • タグの使い方を知ることができる。

#1.まずはカギと扉を作ろう!
まずは自由に鍵を作ります!(別のツールやassetを使ってもOK!)

自分はUnity内でSphereとCapsuleを組み合わせてこんな感じの鍵をつくりました!
スクリーンショット 2020-09-09 21.46.16.png

次にできた鍵を一つの階層にまとめる。

スクリーンショット 2020-09-09 21.49.37.png

次に以下の写真の手順で**Keyという名前のtagを作成してカギの一番上の階層**につけましょう。
<手順1>
image.png
<手順2>
image.png
<手順3>
image.png


同じように「扉」を作成しましょう。

スクリーンショット 2021-04-23 16.51.35.png

さばとは簡単にこんな感じの扉を作成しました。

カギと同じように扉にもdoorという名前のtagを付ける。

カギと扉を作成出来たら次はプログラムを考えて行きましょう。

#2.キャラクターがカギに触れたときのプログラムを書く。

まずどのようにプログラムを作成していくか考えます。

まだ作成したことがなければ以下のように考えると思います。

作成時の疑問点
1. 鍵を取得した状態をどのように反映させるか。
2. 取得した状態でどうすれば壁を消し通ることができるのか。

まず疑問1から考えましょう!

疑問1(鍵を取得した状態をどのように反映させるか)

作成方法はたくさんがあるが、今回は鍵が一つしか出てこないことを想定して変数に**「取得している」「取得していない」**の状態を保存することで作成していきます。

二択の状態を保存するのに適している変数の型にboolというものがあるので今回はboolを使用して作成していきます。(intで0,1で置き換えてもOK!)

boolとは**true(真)またはfalse(偽)**のどちらかを入れることができる型でプログラムではよく使うので覚えておいてください。


ではまず、PlayerにGetKeyState.csというC#スクリプトを作成してください。

作成したらbool型の変数を作成し名前はisGetKeyとし初期値はfalseとします。
今回はStart関数とUpdate関数は使用しないので消してしまってもOKです!

GetKeyState.cs
using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class GetKeyState : MonoBehaviour
{
    private bool isGetKey = false; //★この行を追加
    
    void Start()
    {
        
 //  ~~~~~~省略~~~~~~

これで保存するための変数の作成できました。

次に触れたときにカギを取得し、isGetKeytrueにするプログラムを作成していきます。

update関数の下に新しくOnCollisionEnterと呼ばれる触れた時のプログラムを追加します。
さらにif文で触れたGameObjectのタグがKeyならという処理を入れてあげ、そのif文の中でisGetKeyをtrueにしましょう!

GetKeyState.cs

// ~~~~~~~省略~~~~~~~~
 void Update()
    {
        
    }
    //何かに触れたとき
    private void OnCollisionEnter(Collision other)
    {
        //もし触れたオブジェクトのタグが"Key"なら
        if (other.gameObject.CompareTag("key"))
        {
            //isGetKeyをTrue(真)にする。
            isGetKey = true;
        }
    }
}

このように書くとobjectに触れたときisGetKeyがtrueになるプログラムが作成できました!

しかしこのままでは触れれば内部的にはisGetKeytrueになるのですが、見た目は何も変わっていないのでisGetKeyをtrueにした後にはちゃんとカギを消してあげましょう

GetKeyState.cs
//~~~~省略~~~~~
private void OnCollisionEnter(Collision other)
{
    if (other.gameObject.CompareTag("key"))
    {
        isGetKey = true;
        //keyのobjectを削除する
        Destroy(other.gameObject);
    }
}

Destroy(gameobject) : ( )内のgameObjectを削除する。

これで疑問1は解決!

疑問2(取得した状態でどうすれば壁を消し通ることができるのか)

次に疑問2なのですが、ここまでやってきた人ならもうわかってきたと思います。

先ほど作成したOnCollisonEnterの中にもう一つ、扉用のif文を作成しその中でgameObjectを削除してあげましょう!

GetKeyState.cs

//~~~省略~~~~

 private void OnCollisionEnter(Collision other)
    {
        if (other.gameObject.CompareTag("key"))
        {
            isGetKey = true;
            Destroy(other.gameObject);
        }
        //もし触れたobjectのtagがdoorなら
        if (other.gameObject.CompareTag("door")&&isGetKey)
        {
            Destroy(other.gameObject);
        }
    }


これで完成です!お疲れさまでした!!

バグ解決のヒント

<触れても消えない場合>

  • tagはちゃんとついているか。
  • プログラムで書いたtag名とunity側で入力したtag名が一緒か。(大文字小文字気を付けて!)
  • objectにCollider当たり判定がついているか。または適切な位置にあるか。

まとめ

「鍵を入手して扉を開けよう!」はいかがだったでしょうか。タグを使う判定は様々なところで使えるのでしっかり学んでおきましょう!

もしわからないこと質問したいことがあればさばとに気軽に質問してください。

ではでは。

0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?