【Unity2D 入門】横スクロールアクションゲームを作ってみたい -ダメージを受けるとHPゲージが減る処理

raharu(仮名)(プログラマー)
これがダイバージェンス1%の先の世界か。。。

一応クソゲー作っているんですけど、腐ってもゲームなのですから
「ゲームオーバー」が無いと「ゲーム」とは言えません。

とりあえずmobに当たったらダメージを受ける!ただこれだけの事をしたいのです。

HPバーを用意する

赤い画像と黒いが像を用意します。

f:id:raharu0425:20140110160411j:plain

f:id:raharu0425:20140110160531j:plain

Hierarchy > GUI Textureでオブジェクトを2つ作成して、
Texture に先ほどの画像を適応します。

ゲーム画面上でいい感じになるように位置とサイズを指定します。

f:id:raharu0425:20140110160817p:plain

赤も黒も同じ位置なので黒色のバーは下に隠れいているので見えませんが、
ゲーム画面上だとこんな位置になりました!いい感じじゃないっすか。

f:id:raharu0425:20140110161015p:plain

mobにタグをつける

mobオブジェクトのtagボタンを押して、add Tagでmobを作成します。
これで、mobオブジェクトには「mob」というタグ付けがされました。

f:id:raharu0425:20140110162235p:plain

さて、これで準備完了です。

スクリプトを書いていきたいんですけど。
どういう事になるかと言うと。

  1. playerがmobとぶつかったという判定をできるようにする
  2. ぶつかったら、hpbarを減らす

という簡単に言えばこれだけです。
playerのScriptからhpbarを呼び出す事も実際可能ですが、
役割的には、hpbarが引数を受け取ってダメージ分ゲージを減らしていくというのが自然な感じがするのでこっちでやります。

playerがmobとぶつかったという判定をできるようにする

わかりやすいように、C#を新しく作成してplayerにaddします。

damage.cs

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
using UnityEngine;
using System.Collections;

public class damage : MonoBehaviour {

    public GameObject hpbar;

    // Use this for initialization
    void Start () {
    
    }
    
    // Update is called once per frame
    void Update () {
    
    }

    void OnCollisionEnter2D(Collision2D col){

        //  on damage
        if(col.gameObject.tag == "mob"){
            hpbar.gameObject.SendMessage("onDamage", 10);
        }
    }
}

public GameObject hpbar;
には何も入ってないのでhpbarを指定します。

void OnCollisionEnter2D(Collision2D col){
最初OnCollisionEnterを使おうと思ったんですけど、エラーが出まくってなんぞ!と思ったら
OnCollisionEnter2Dが有るみたいです。。。そうなのか。。

if(col.gameObject.tag == “mob”)
ぶつかったGameObjectのタグがmobだったらという条件式です。

hpbar.gameObject.SendMessage(“onDamage”, 10);
上部で宣言したhpbarのonDamageメソッドに対して10という引数を渡します。

hpbarオブジェクトにスクリプトを追加する

今度はhpbarという名前のスクリプトを作ります。
中身はこんな感じ。

hpbar.cs

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
using UnityEngine;
using System.Collections;

public class hpbar : MonoBehaviour {

    // Use this for initialization
    void Start () {
    
    }
    
    // Update is called once per frame
    void Update () {
    
    }

    void onDamage(int damage)
    {
        Rect hpRect = guiTexture.pixelInset;
        hpRect.width = (hpRect.width - 10);

        if(hpRect.width <= 0){
            hpRect.width = 0;
        }
        guiTexture.pixelInset = hpRect;
    }
}

guiTexture.pixelInset
hpvarオブジェクトバーの位置をとれます。

この書き方ができるなら
guiTexture.pixelInset.width = 値
で良いじゃんと思いましが、だめでした。

一旦Rect型で変数を呼び出して、それを入れてやる必要があるのですね、うむ。ここら辺まだC系の言語に慣れないですね。

if(hpRect.width <= 0)
ただサイズを小さくしているだけだと負数になって左にバーがのびて行ってしまうので
もしも負数になったら0のままで、という条件式です。

さて、エミュレートしてみましょう。

f:id:raharu0425:20140110163605p:plain

ゲージへってる!もう少しまともな事をするならダメージが受けてから1秒間は無敵とかできれば良いのですが、
今日はこれまで。次回はもっとゲームっぽくできようにしたいところです。

参考サイト

http://answers.unity3d.com/questions/453596/cannot-modify-a-value-type-return-value-of.html http://kdey.cocolog-nifty.com/blog/2011/12/guitexturehp-5f.html