簡単なゲーム作成の第7回目を進めていきます。今回は「カード勝敗判定」を繰り返すために、利用したカードを消していきます。とりあえず、今回で一旦はカードゲーム作成は終了です。
はじめに
今回はPart7です。Part1は下記から。
Part6までで一通り動き、カードの画像を変更しました。
ゲーム作成開始
現状だと一回カードを出して判定したら終わりなので、何度も繰り返し判定できるように変更していきます。
カードを削除
まずは「場に出して判定が終了したカードを消します」。OperatorのOpenCard内、カードの勝敗判定後にDestCardを追加。
public void OpenCard() { enemyobj.EnemyCardSelect(); JudgeCard(); DestCard(); }
DestCardで場に出ているカードオブジェクトを削除するのですが、敵の場に出ているカードオブジェクトが分からないので、どのカードが場に出ているのかEnemyクラスを下記のように変更。
using System.Collections.Generic; using UnityEngine; public class Enemy : MonoBehaviour { public int intEnemyCardNumber; public int selectCardNumber; public List<GameObject> EmCardlist = new List<GameObject>(); public void EnemyCardSelect() { EmCardlist.Clear(); foreach (Transform child in transform) { EmCardlist.Add(child.gameObject); } selectCardNumber = Random.Range(0, EmCardlist.Count - 1); EmCardlist[selectCardNumber].transform.localPosition = new Vector3(70, -350, 0); intEnemyCardNumber = EmCardlist[selectCardNumber].GetComponent<CardScript>().CardNumebr; } }
OperatorクラスにDestCardを作成。自分が選んだカードと敵のカード(場に出ているカード)をDestroyしています。
private void DestCard() { GameObject playercardObject = Cards.GetComponent<Cards>().SelectCard; int enemycardnum = EmCards.GetComponent<Enemy>().selectCardNumber; GameObject enemycardObject = EmCards.GetComponent<Enemy>().EmCardlist[enemycardnum]; Destroy(playercardObject); Destroy(enemycardObject); Result.GetComponent<Text>().text = ""; }
このままだとオープンしたらカードが直ぐに消えるので、DestCardをInvokeで遅延させて実行します。秒数は適当で良いかと。
public void OpenCard() { enemyobj.EnemyCardSelect(); JudgeCard(); Invoke("DestCard", 2f); }
これで実行。判定結果が出た後に場に出たカードが消えればOK。これで一応、何度か実行できるようになります。
最後に
とりあえずのゲームの形となりましたが、現状ではバグを含め修正する箇所が山のようにありますが、ゲームの根幹部分というよりはバグ修正や機能追加になるので一旦カードゲーム作成はここまでにします。
最後にスクリプトを全て記載しておきます。
スクリプトの一覧
まずは「カードを配る、判定する」などの役目を持つOperator。
using System.Collections; using System.Collections.Generic; using UnityEngine; using UnityEngine.UI; public class Operator : MonoBehaviour { public GameObject CardPrefab; public GameObject Cards; public GameObject EmCards; public GameObject Result; public Sprite[] m_Sprite; private void Start() { //Player dealCards(1, -700, Cards); dealCards(2, -350, Cards); dealCards(2, 0, Cards); dealCards(2, 350, Cards); dealCards(3, 700, Cards); //Enemy dealCards(1, -700, EmCards); dealCards(2, -350, EmCards); dealCards(2, 0, EmCards); dealCards(2, 350, EmCards); dealCards(3, 700, EmCards); } void dealCards(int iNumber,float fPosition,GameObject objParent) { GameObject prefab = (GameObject)Instantiate(CardPrefab); prefab.GetComponent<CardScript>().iCardNumber = iNumber; prefab.transform.SetParent(objParent.transform, false); prefab.transform.localPosition = new Vector3(fPosition, 0, 0); SpriteRenderer m_SpriteRenderer; m_SpriteRenderer = prefab.GetComponent<SpriteRenderer>(); m_SpriteRenderer.sprite = m_Sprite[iNumber - 1]; } public void OpenCard() { EmCards.GetComponent<Enemy>().EnemyCardSelect(); JugeCard(); Invoke("DestCard", 2f); } private void JugeCard() { int myCardNm = Cards.GetComponent<Cards>().intCardNumer; int enCardNm = EmCards.GetComponent<Enemy>().intEnemyCardNumber; Text txtResult = Result.GetComponent<Text>(); //1がグー、2がチョキ、3がパー if ((myCardNm - enCardNm + 3) % 3 == 0) { //引き分け txtResult.text = "DRAW"; } else if ((myCardNm - enCardNm + 3) % 3 == 1) { //負け txtResult.text = "LOSE"; } else { //勝ち txtResult.text = "WIN"; } } private void DestCard() { GameObject playercardObject = Cards.GetComponent<Cards>().SelectCard; int emlistNum = EmCards.GetComponent<Enemy>().intRamNumber; GameObject enemycardObject = EmCards.GetComponent<Enemy>().EmCardlist[emlistNum]; Destroy(playercardObject); Destroy(enemycardObject); Text txtResult = Result.GetComponent<Text>(); txtResult.text = ""; } }
ここで直す必要があるのは、プレイヤーがカードを選択せずにOPENボタンを押した時に「カード選択を促すメッセージを表示」したり、初めのカードを配る部分はループを使ったりでもう少し綺麗にまとめたり。途中の勝敗状況や最終結果なども表示するべきですね。
次が「カードが選択したとき」のCardScript
using UnityEngine; using UnityEngine.UI; public class CardScript : MonoBehaviour { public int CardNumebr; private Cards cards; private void Start() { cards = transform.parent.gameObject.GetComponent<Cards>(); } public void ChoiceCard() { if (cards.SelectCard != null) { cards.SelectCard.GetComponent<Transform>().localPosition = cards.InitPosition; } cards.SelectCard = this.gameObject; cards.InitPosition = this.transform.localPosition; int num = int.Parse(this.transform.Find("Text").GetComponent<Text>().text); cards.intCardNumber = CardNumebr; transform.localPosition = new Vector3(-400, 350, 0); } }
次が「敵のカードを自動で選択する」Enemy。
using System.Collections.Generic; using UnityEngine; public class Enemy : MonoBehaviour { public int intEnemyCardNumber; public int selectCardNumber; public List<GameObject> EmCardlist = new List<GameObject>(); public void EnemyCardSelect() { EmCardlist.Clear(); foreach (Transform child in transform) { EmCardlist.Add(child.gameObject); } selectCardNumber = Random.Range(0, EmCardlist.Count - 1); EmCardlist[selectCardNumber].transform.localPosition = new Vector3(70, -350, 0); intEnemyCardNumber = EmCardlist[selectCardNumber].GetComponent<CardScript>().CardNumebr; } }
次が「プレイヤーのカードを管理」しているCards。
using UnityEngine; public class Cards : MonoBehaviour { public GameObject SelectCard; public Vector3 InitPosition; public int intCardNumber; }
こうしてみると計画性ゼロで作ったので、ぐちゃぐちゃですね。
ゲームを作る前には簡単なクラス図的なのを作って、どこにどんな役割を持たせるのか、ある程度考えてから進めた方が良いですね。当たり前ですが(笑)