赞
踩
首先创建一个Canvas叫Level Complete Canvas,然后给它添加文字和阴影图片
除此之外我们还要在之前的Main Canvas(之前的,改了个名而已)创建新UI Slider,然后把Handle部分换一张SPrite比如狐狸那张,然后改变background和fill的颜色
前面的和成功的Canvas一样,唯一不同的是要创建两个Button,一个是返回一个是重新开始本关
因此我们要创建两个Public方法供Button调用,这里我们创建个空对象就叫LevelController来管理我们的关卡
给它一个同名的脚本:
- using System.Collections;
- using System.Collections.Generic;
- using UnityEngine;
-
- public class LevelController : MonoBehaviour
- {
- [SerializeField] float waitToLoad = 3f;
- [SerializeField] GameObject winLabel;
- [SerializeField] GameObject lostLabel;
- int numberOfAttackers = 0;
- bool levelTimerFinished = false; //判断滑动条的Value是否到1
-
- private void Start()
- {
- //先把输赢的canvas隐藏
- winLabel.SetActive(false);
- lostLabel.SetActive(false);
- }
- public void AttackerSpawn() //给Attacker调用
- {
- numberOfAttackers++;
- }
- public void AttackerKilled() //同样给attacker调用
- {
- numberOfAttackers--;
- if (numberOfAttackers <= 0 && levelTimerFinished)
- {
- StartCoroutine(HandleWinCondition());
- }
- }
- IEnumerator HandleWinCondition() //当关卡成功时候
- {
- winLabel.SetActive(true);
- GetComponent<AudioSource>().Play();
- yield return new WaitForSeconds(waitToLoad);
- FindObjectOfType<LevelLoader>().LoadNextScene();
- }
- public void HandleLoseCondition() //当关卡失败后
- {
- lostLabel.SetActive(true);
- Time.timeScale = 0;
- }
- public void LevelTimerFinished() //滑动条的值为1时候
- {
- levelTimerFinished = true;
- StopSpawners();
- }
- private void StopSpawners() //停止生产敌人
- {
- AttackSpawner[] spawnArray = FindObjectsOfType<AttackSpawner>();
- foreach (var spawner in spawnArray)
- {
- spawner.StopSpawning();
- }
- }
- }
然后再挂载到上面
那我们怎么判断关卡是不是失败呢?和植物大战僵尸一样,当进入房子的敌人超过一定数量时游戏直接判负,显示游戏失败。 这里用一个空对象给它一个Trigger
- using System.Collections;
- using System.Collections.Generic;
- using UnityEngine;
-
- public class DamageCollider : MonoBehaviour
- {
- private void OnTriggerEnter2D(Collider2D other)
- {
- FindObjectOfType<Lives>().TakeLife();
- }
- }
在Main Canvas时我们又创建一个Text
- using System.Collections;
- using System.Collections.Generic;
- using UnityEngine;
- using UnityEngine.UI;
- public class Lives : MonoBehaviour
- {
- [SerializeField] int damage = 1;
- [SerializeField] int lives = 5;
- Text livesText;
- private void Start()
- {
- livesText = GetComponent<Text>();
- UpdateDisplay();
- }
-
- private void UpdateDisplay()
- {
- livesText.text = lives.ToString();
- }
-
- public void TakeLife()
- {
- lives -= damage;
- UpdateDisplay();
-
- if (lives <= 0)
- {
- FindObjectOfType<LevelController>().HandleLoseCondition();
- //FindObjectOfType<LevelLoader>().LoadYouLose();
- }
- }
- }
之前的LevelLoader已经不需要了,取而代之的是LevelController
制作完以上两点后,我们也可以设置一个让不同路生成不同种类的敌人。用数组的形式在AttackerSpawner上
- using System.Collections;
- using System.Collections.Generic;
- using UnityEngine;
-
- public class AttackSpawner : MonoBehaviour
- {
- [SerializeField] Attacker[] attackPrefabArray;
- [SerializeField] float minSpawnDelay = 1f;
- [SerializeField] float maxSpawnDelay = 5f;
- bool spawn = true;
- IEnumerator Start()
- {
- while (spawn)
- {
- yield return new WaitForSeconds(Random.Range(minSpawnDelay, maxSpawnDelay)); //延迟生成Attacker对象
- SpawnAttack();
- }
- }
- private void SpawnAttack()
- {
- var attackerIndex = Random.Range(0, attackPrefabArray.Length);
- Spawn(attackPrefabArray[attackerIndex]);
- }
- public void StopSpawning()
- {
- spawn = false;
- }
- private void Spawn(Attacker myAttacker)
- {
- Attacker newattacker = Instantiate(myAttacker, transform.position, transform.rotation) as Attacker;
- newattacker.transform.SetParent(transform); //并把对象转化为我们Spawenr的子对象,简化hierarchy窗口
- }
- }
- using System;
- using System.Collections;
- using System.Collections.Generic;
- using UnityEngine;
-
- public class Attacker : MonoBehaviour
- {
- GameObject currentTarget;
- [Range(0, 5)]
- float currentSpeed = 1f;
-
- private void Awake()
- {
- FindObjectOfType<LevelController>().AttackerSpawn();
- }
- private void OnDestroy()
- {
- LevelController level = FindObjectOfType<LevelController>();
- if (level != null)
- {
- level.AttackerKilled();
- }
- }
- void Update()
- {
- transform.Translate(Vector2.left * currentSpeed * Time.deltaTime);
- UpdateAnimationState();
- }
-
- private void UpdateAnimationState()
- {
- if (!currentTarget)
- {
- GetComponent<Animator>().SetBool("isAttacking", false);
- }
- }
-
- public void SetMovementSpeed(float speed)
- {
- currentSpeed = speed;
- }
- public void Attack(GameObject target)
- {
- GetComponent<Animator>().SetBool("isAttacking", true); //播放吃植物动画
- currentTarget = target;//锁定植物
- }
- public void StrikeCurrentTarget(float damage)
- {
- if (!currentTarget) return;
- Health health = currentTarget.GetComponent<Health>();
- if (health)
- {
- health.DealDamage(damage);//扣植物的血
- }
- }
-
- }
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。