今回は戦闘時のコマンドのUIを実装していきたいと思います
・攻撃方法を敵をタップするのではなく、攻撃用のボタンを押すように変更した。
ヒエラルキーにCanvasを新規作成、名前をCommandUICanvasに変更。子オブジェクトにButtonを3つ配置。テキストはそれぞれ「攻撃」「特殊」「やめる」に変更。「やめる」ボタンは、「攻撃」ボタンを押して敵を選択するときに、コマンドの選択に戻りたい時に使うボタンなので、コマンドを選択するときは非表示に、ターゲットを選択するときに表示させるようにする。「攻撃」ボタンは押したら「攻撃」ボタンを非表示にする。
見た目はこんな感じ
スクリプト「CommandManager.cs」を新規作成。CommandUICanvasに貼り付ける。
スクリプト「CommandManager.cs」を編集。
クリックで展開
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class CommandUIManager : MonoBehaviour
{
public GameObject attackBttonn;
public GameObject specialButton;
public GameObject cancelBttonn;
void Start()
{
}
void Update()
{
}
public void SetBattleCommand()
{
attackButton.gameObject.SetActive(true);
specialButton.gameObject.SetActive(true);
cancelButton.gameObject.SetActive(false);
}
public void SetCommandForTargetSelect()
{
attackButton.gameObject.SetActive(false);
specialButton.gameObject.SetActive(false);
cancelButton.gameObject.SetActive(true);
}
}
公開したボタン用の変数にそれぞれCommandUICanvasのボタンを割り当てる.。
関数も各々作成していく。(SetBattleCommand関数、SetCommandForTargetSelect)
戦闘開始時に実行される、BattleManager.csのSetUp関数に、
commandUI.gameObject.SetActive(true);
commandUI.SetBattleCommand();
を追加し、戦闘開始時にコマンドが使えるようにする。さらに戦闘開始時には敵をタップできないように、SetUp関数内の以下の処理を削除
canAttackTap = true;
攻撃ボタンが押された時に、CommandUIManagerのSetCommandForTargetを、キャンセルボタンが押された時にCommandUIManagerの
SetBattleCommandをそ実行するように、「攻撃」ボタンと「やめる」ボタンのButtonコンポーネントのOn Click()のリストにそれぞれ関数を登録する。さらに、「攻撃」ボタン押下でBattleManage.csのCanAttackTapをtrueに、「やめる」ボタン押下でfalseになるように設定、敵をタップしたらCommandUIを非表示にする。敵のターンが終了したらサイドCommandUIを表示する。
QuestManagerのStart関数にcommandUIの非アクティブ処理を追加。敵とエンカウントしたらアクティブに、戦闘が終了したら非アクティブにする。
実装後のQuestManager.csとBattleManager.csのコードはそれぞれこんな感じです。
クリックで展開
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using DG.Tweening;
public class BattleManager : MonoBehaviour
{
public Transform playerDamagePanel;
public QuestManager questManager;
public PlayerUIManager playerUI;
public EnemyUIManager enemyUI;
public CommandUIManager commandUI;
public PlayerManager player;
EnemyManager enemy;
private bool canAttackTap;
private void Start()
{
enemyUI.gameObject.SetActive(false);
playerUI.SetupUI(player);
}
public void SetUp(EnemyManager enemyManager)
{
SoundManager.instance.PlayBGM("Battle");
enemyUI.gameObject.SetActive(true);
enemy = enemyManager;
enemyUI.SetupUI(enemy);
playerUI.SetupUI(player);
commandUI.gameObject.SetActive(true);
commandUI.SetBattleCommand();
enemy.AddEventListenerOnTap(PlayerAttack);
}
public void PlayerAttack()
{
if (canAttackTap)
{
StopAllCoroutines();
SoundManager.instance.PlaySE(1);
int damage = player.Attack(enemy);
enemyUI.UpdateUI(enemy);
DialogTextManager.instance.SetScenarios(new string[] {
"プレイヤーの攻撃!\n" + enemy.name + "に" + damage + "ダメージを与えた。" });
canAttackTap = false;
commandUI.gameObject.SetActive(false);
if (enemy.hp <= 0)
{
StartCoroutine(EndBattle());
}
else
{
StartCoroutine(EnemyTurn());
}
}
}
IEnumerator EnemyTurn()
{
yield return new WaitForSeconds(2f);
SoundManager.instance.PlaySE(1);
playerDamagePanel.DOShakePosition(0.3f, 0.5f, 20, 0, false, true);
int damage = enemy.Attack(player);
playerUI.UpdateUI(player);
DialogTextManager.instance.SetScenarios(new string[] {
enemy.name + "の攻撃!\nプレイヤーは"+ damage + "を受けた。" });
yield return new WaitForSeconds(1f);
if (player.hp <= 0)
{
questManager.PlayerDeath();
}
else
{
commandUI.gameObject.SetActive(true);
commandUI.SetBattleCommand();
}
}
IEnumerator EndBattle()
{
yield return new WaitForSeconds(2f);
SoundManager.instance.PlaySE(3);
enemy.transform.DOScale(new Vector3(2.0f, 2.0f, 2.0f), 1f);
SpriteRenderer enemySpriteRenderer = enemy.GetComponent<SpriteRenderer>();
enemySpriteRenderer.DOColor(new Color(1f, 0f, 0f, 0f), 1f);
yield return new WaitForSeconds(2f);
DialogTextManager.instance.SetScenarios(new string[] {
enemy.name + "を倒した" });
enemyUI.gameObject.SetActive(false);
Destroy(enemy.gameObject);
SoundManager.instance.PlayBGM("Quest");
enemyUI.gameObject.SetActive(false);
questManager.EndBattle();
}
public bool CanAttackProperty
{
get { return canAttackTap; }
set { canAttackTap = value; }
}
public void SetCanAttackTap(bool canTap)
{
canAttackTap = canTap;
}
}
クリックで展開
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using DG.Tweening;
public class QuestManager : MonoBehaviour
{
public StageUIManager stageUI;
public GameObject[] enemyPrefabs;
public BattleManager battleManager;
public SceneTransisitonManager sceneTransisitonManager;
public GameObject questBG;
public CommandUIManager commandUI;
int[] encountTable = {-1, -1, 0, -1, 0, -1 };
int currentStage = 0;
private void Start()
{
stageUI.UpdateUI(currentStage);
commandUI.gameObject.SetActive(false);
DialogTextManager.instance.SetScenarios(new string[] { "洞窟についた。"});
}
IEnumerator Searching()
{
DialogTextManager.instance.SetScenarios(new string[] { "探索中..." });
questBG.transform.DOScale(new Vector3(1.5f, 1.5f, 1.5f), 2f)
.OnComplete(() => questBG.transform.localScale = new Vector3(1, 1, 1));
SpriteRenderer questBGSpriteRenderer = questBG.GetComponent<SpriteRenderer>();
questBGSpriteRenderer.DOFade(0, 2f)
.OnComplete(() => questBGSpriteRenderer.DOFade(1, 0));
yield return new WaitForSeconds(2f);
currentStage++;
stageUI.UpdateUI(currentStage);
if (encountTable.Length <= currentStage)
{
QuestClear();
}
else if (encountTable[currentStage] == 0)
{
EncountEnemy();
}
else
{
stageUI.ShowButtons();
}
}
public void OnNextButton()
{
SoundManager.instance.PlaySE(0);
stageUI.HideButtons();
StartCoroutine(Searching()) ;
}
public void OnToTownButton()
{
}
void EncountEnemy()
{
DialogTextManager.instance.SetScenarios(new string[] { "モンスターに遭遇した!" });
stageUI.HideButtons();
commandUI.gameObject.SetActive(true);
int randomEnemyID = Random.Range(0,enemyPrefabs.Length);
GameObject enemyObj = Instantiate(enemyPrefabs[randomEnemyID]);
EnemyManager enemy = enemyObj.GetComponent<EnemyManager>();
battleManager.SetUp(enemy);
}
public void EndBattle()
{
commandUI.gameObject.SetActive(false);
stageUI.ShowButtons();
}
void QuestClear()
{
DialogTextManager.instance.SetScenarios(new string[] { "宝箱を手に入れた。\n街に戻ろう" });
SoundManager.instance.StopBGM();
JingleManager.instance.PlayJingle(0);
stageUI.ShowClearText();
}
public void PlayerDeath()
{
sceneTransisitonManager.LoadTo("Town");
}
}
あとついでに、ダイアログにエネミーの名前を反映するようにしておきました。
今回は以上です。