#始めに!!
・皆さん初めまして!!とある学校で専門生してるamanon(仮名)と申します!
Unityを勉強してる皆様と情報共有できたらいいな~と思って初めてみました!
・Unity初心者さんや勉強中な人向けに記事を書いていきますのでよろしくお願いします!!
・第一回目はinterfaceです!(1回目にやる内容じゃないですが...(-_-;))
とても便利なので頑張って行きましょうー!!
##interfaceとは?
・クラスを作った人(作成側)とそのクラスを利用する側(利用者)でお約束事が出来る機能です
##interfaceの用途
・コードの疎結合化
・実装の中身は利用者側は知らなくていい!
・メソッドの中身は利用者側が仕様を決めれることが出来ます!
まとめてみましたが全然理解しなくて大丈夫ですよ!!
言葉だけじゃ伝わらない部分もあるのでソース交えながらやっていきましょう!!
##使い方
public interface I_Damageble()
{
//OK!!
public void Damage(int Value);
//エラー
public void Damage(int Value)
{
helth-=Value;
}
}
・今回はI_Damagebleというinterface(作成側)を作りDamageという関数を持たせました!
・interfaceはあくまでも機能だけ定義する事が出来て中身は作る事が出来ません!少し矛盾してるというか変ですよね.
・じゃあ関数なのに中身はどうやって実装するんだ?って思いますよね!そうです、中身は利用者側が実装しなければなりません!作っていきます!
public class Damageble:MonoBehaviour,I_Damageble <-ここに利用するinterface名
{
//HP
private int helth=0;
//ダメージ関数
public void Damage(int Value)
{
helth-=Value;
}
}
・Damagebleクラス(利用者)にI_Damageble(作成者)を継承させたらI_Damagebleの機能が使える事が出来ます!
・実際に継承させI_DamagebleのDamage関数の中身を実装してみました!
void OnCollisonEnter(Collison other)
{
//ohter(当たった情報)からIDamagebleを取得します!
//無い場合nullが返ってきます!
var id=other.gameobject.Getcopoment<IDamageble>();
//nullの場合に処理を実行するとIDamagebleの情報が無いのでエラー
// idにデーターが入った場合のみ実行する,nullの場合は処理しない
if (id!=null)
{
id.Damage(10);
}
}
・あとはこのDamage関数を当たり判定の関数の中で呼んであげればやる事は終わりです!
・FPSでプレイヤーが建物に当たった時にダメージ処理が実行されたらおかしいですよね。なのでnull処理は必ず入れてください。
##ここまで
interfaceの使い方を紹介しましたがどこが便利やねん!普通にダメージ関数を作った方が楽やんけ!!
と思った方もいらっしゃるかと思いますがこれから紹介していきます!!
void OnCollisonEnter(Collison other)
{
if(other.gameobject.tag=="Enemy")
{
Damage(10);
}
}
・おなじみの当たり判定処理ですね!!FPSやTPSなどでは問題ないですが宇宙区間で戦うシューティングを思い浮かべてみてください!
・もし岩や流星群、飛行機の破片が当たった時にダメージ処理したい場合それぞれの
オブジェクトに"Enemy"というタグを設定しますか?しないですよね(;^ω^)だって敵じゃないですので!
・じゃそれぞれにタグを設定しますか?
void OnCollisonEnter(Collison other)
{
if(other.gameobject.tag=="Enemy")
{
Damage(10);
}
if(other.gameobject.tag=="ryusei")
{
Damage(10);
}
if(other.gameobject.tag=="hahenn")
{
Damage(10);
}
if(other.gameobject.tag=="iwa")
{
Damage(10);
}
}
・いい案ではありますがhit時ダメージ処理をしたいオブジェクトが増えるたびにコードも増えてバグの原因になりかねません。
・チーム制作なんかでやっているとヒューマンエラーにもつながります。
##解決法
・ここで便利になってくるのがinterfeceです!
//流星クラス
public class ryusei:MonoBehaviour,I_Damageble
{
public void Damage(int value)
{
}
}
//岩クラス
public class iwa:MonoBehaviour,I_Damageble
{
public void Damage(int value)
{
}
}
//欠片クラス
public class kakera:MonoBehaviour,I_Damageble
{
public void Damage(int value)
{
}
}
//プレイヤークラス
public class Player:MonoBehaviour
{
void OnCollisonEnter(Collison other)
{
//これだけで欠片、岩、流星が当たった時の処理が出来ます
var id=other.gameobject.Getcopoment<IDamageble>();
if (id!=null)
{
id.Damage(10);
}
}
}
・それぞれのクラスにinterfaceを背負わせる事で当たったときそのオブジェクトは
interfaceを背負ってるか背負ってないかでダメージ処理が出来るので
わざわざ文字列で判定をとらなくていいですしコードも少なくて済みます!とても便利ですよね!!!
以上です!!お疲れ様でした!
##おわりに
ここまで目を通してくださりありがとうございました!当たり判定をいっぱい取る場合には有効な手法ですので使ってみてください!!
初めての試みで不慣れですがまた定期的に書いていこうと思います!よろしくお願いします