小松鼠踩一踩游戏

文章介绍了Unity游戏中的门面设计模式,用于统一管理AudioManager、UIManager、GameManager和SaveManager。AudioManager负责音频资源的加载和播放,UIManager处理UI面板的加载和关闭,BaseManager作为抽象基类提供了管理器的通用框架。此外,文章还涉及到UI按钮的引用和角色交互的奖惩机制。
摘要由CSDN通过智能技术生成


一、 介绍和知识点

玩家通过跳跃踩砖块,达到相应的百分比,即可过关。
有3个关卡
可以暂停
在这里插入图片描述
在这里插入图片描述

堆栈
数据字典
枚举
UnityFacade 门面设计模式
从资源文件中获取音频文件


九、UnityFacade 门面设计模式

这是一个UnityFacade类的代码,它是一个单例类,用于管理游戏中的各种Manager,包括AudioManagerUIManagerGameManagerSaveManager。下面是代码的逐行注释:

```csharp
using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class UnityFacade : MonoBehaviour
{
    private AudioManager _audioManager; //声明一个私有的AudioManager对象
    private UIManager _uiManager; //声明一个私有的UIManager对象
    private GameManager _gameManager; //声明一个私有的GameManager对象
    private SaveManager _saveManager; //声明一个私有的SaveManager对象
    private float _timer; //声明一个私有的计时器变量

    //声明一个公有的计时器属性
    public float Timer
    {
        get { return _timer; }
        set { _timer = value; }
    }

    //声明一个公有的GameManager属性
    public GameManager GameManager
    {
        get { return _gameManager; }
    }

    //声明一个公有的UIManager属性
    public UIManager UiManager
    {
        get { return _uiManager; }
    }

    //声明一个公有的AudioManager属性
    public AudioManager AudioManager
    {
        get { return _audioManager; }
    }

    //声明一个公有的SaveManager属性
    public SaveManager SaveManager
    {
        get { return _saveManager; }
    }

    //声明一个私有的静态UnityFacade对象
    private static UnityFacade _instance;

    //声明一个公有的静态UnityFacade对象,用于获取UnityFacade的单例
    public static UnityFacade Instance
    {
        get { return _instance; }
    }

    //在Awake中初始化单例
    private void Awake()
    {
        if (_instance == null)
        {
            _instance = this;
        }
    }

    void Start()
    {
        //实例化所有Manager
        _audioManager = new AudioManager();
        _uiManager = new UIManager();
        _gameManager = new GameManager();
        _saveManager = new SaveManager();
        //调用所有的Manager的OnInit方法
        _audioManager.OnInit();
        _uiManager.OnInit();
        _saveManager.OnInit();
        _gameManager.OnInit();
    }

    // Update is called once per frame
    void Update()
    {
        //调用所有Manager的OnUpdate方法
        _audioManager.OnUpdate();
        _uiManager.OnUpdate();
        _gameManager.OnUpdate();
        _saveManager.OnUpdate();
    }

    //在销毁对象时调用所有Manager的OnDestroy方法
    private void OnDestroy()
    {
        _audioManager.OnDestroy();
        _uiManager.OnDestroy();
        _gameManager.OnDestroy();
        _saveManager.OnDestroy();
    }

    //启动计时器倒计时
    public void StartTimerCountDown()
    {
        StartCoroutine(_gameManager.TimerCountIEnumerator());
    }

    //生成奖励物品
    public void SpawnAward()
    {
        _gameManager.SpawnAward();
    }

    //生成惩罚物品
    public void SpawnPunishment()
    {
        _gameManager.SpawnPunishment();
    }
}

UnityFacade类是一个单例类,用于管理游戏中的各种Manager,包括AudioManager、UIManager、GameManager和SaveManager。在Start函数中,实例化所有Manager并调用其OnInit方法,然后在Update函数中调用所有Manager的OnUpdate方法,确保所有Manager都在运行。在OnDestroy函数中,调用所有Manager的OnDestroy方法,确保在销毁对象时所有Manager都被正确销毁。此外,UnityFacade类还提供了一些公有方法,如StartTimerCountDown、SpawnAward和SpawnPunishment,用于管理游戏中的一些功能。


二、 声音全局管理器

这段代码的作用是实现游戏中的音频管理,具体包括以下功能:

  1. 创建音频管理器:在OnInit方法中,创建一个名为"AudiManager"的GameObject,并将其作为音频管理器的根节点。同时,创建名为"BGM"和"Sound"的子节点,并将背景音乐和音效的AudioSource组件分别添加到这两个子节点上。

  2. 加载音频资源:在LoadAudioResources方法中,使用Resources.Load方法加载所有的背景音乐和音效资源,并将它们存储在对应的字典中。其中,BGMType和SoundType是两个枚举类型,用于区分不同的背景音乐和音效。

  3. 播放背景音乐:通过PlayBGM方法,可以播放指定类型的背景音乐。在此方法中,通过字典查找找到对应的音频资源,并将其设置为_bgmAudioSource的clip属性,最后调用Play方法开始播放背景音乐。

  4. 停止背景音乐:通过StopBGM方法,可以停止当前正在播放的背景音乐。

  5. 播放音效:通过PlaySound方法,可以播放指定类型的音效。在此方法中,通过字典查找找到对应的音频资源,并调用PlayOneShot方法播放音效。

  6. 单例模式:通过将AudioManager继承自BaseManager,并利用BaseManager的单例模式,确保全局只有一个音频管理器实例。

  7. 枚举类型:通过BGMType和SoundType枚举类型,区分不同的背景音乐和音效。

  8. 继承和虚方法:将AudioManager继承自BaseManager,并重写OnInit方法,实现了音频管理器的抽象和多态。

  9. Resources功能:使用Unity中的Resources.Load方法加载音频资源,实现了游戏中的音频动态加载和卸载。

  10. 委托和事件:通过定义PlayBGMEvent和StopBGMEvent委托类型和相应的事件,使得其他游戏对象可以订阅和响应这些事件,实现了游戏中音频播放和停止的协作功能。



```C#
using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class AudioManager : BaseManager
{
    //定义两个音源组件
    private AudioSource _bgmAudioSource;
    private AudioSource _soundAudioSource;
    //定义背景音乐和音效的字典
    private Dictionary<BGMType, AudioClip> _bgmDict;
    private Dictionary<SoundType, AudioClip> _soundDict;

    //初始化方法
    public override void OnInit()
    {
        //创建音频管理器、背景音乐、音效三个游戏对象,并设置它们的父节点
        GameObject audioManagerGo = new GameObject("AudioManager");
        GameObject bgm = new GameObject("BGM");
        GameObject sound = new GameObject("Sound");
        bgm.transform.SetParent(audioManagerGo.transform);
        sound.transform.SetParent(audioManagerGo.transform);
        //给背景音乐和音效游戏对象添加音源组件
        _bgmAudioSource = bgm.AddComponent<AudioSource>();
        _soundAudioSource = sound.AddComponent<AudioSource>();
        //设置音源组件的初始值,背景音乐循环播放,音效不循环,都不立即播放
        _bgmAudioSource.loop = true;
        _bgmAudioSource.playOnAwake = true;
        _soundAudioSource.loop = false;
        _soundAudioSource.playOnAwake = false;
        //设置背景音乐的默认音量
        _bgmAudioSource.volume = 0.1f;
        //加载声音资源
        LoadAudioResources();
    }

    //加载声音资源
    private void LoadAudioResources()
    {
        //背景音乐资源的加载
        AudioClip aboutUsClip = Resources.Load<AudioClip>("BGM/AboutUs");
        AudioClip gameBgm1Clip = Resources.Load<AudioClip>("BGM/GameBgm1");
        AudioClip gameBgm2Clip = Resources.Load<AudioClip>("BGM/GameBgm2");
        AudioClip gameBgm3Clip = Resources.Load<AudioClip>("BGM/GameBgm3");
        AudioClip gameBgm4Clip = Resources.Load<AudioClip>("BGM/GameBgm4");
        AudioClip gameBgm5Clip = Resources.Load<AudioClip>("BGM/GameBgm5");
        AudioClip mainPanelClip = Resources.Load<AudioClip>("BGM/MainPanel");
        //将背景音乐资源添加到字典中
        _bgmDict = new Dictionary<BGMType, AudioClip>();
        _bgmDict.Add(BGMType.AboutUS, aboutUsClip);
        _bgmDict.Add(BGMType.BGM_1, gameBgm1Clip);
        _bgmDict.Add(BGMType.BGM_2, gameBgm2Clip);
        _bgmDict.Add(BGMType.BGM_3, gameBgm3Clip);
        _bgmDict.Add(BGMType.BGM_4, gameBgm4Clip);
        _bgmDict.Add(BGMType.BGM_5, gameBgm5Clip);
        _bgmDict.Add(BGMType.Main_Panel, mainPanelClip);

        //音效音乐资源的加载
        AudioClip awardClip = Resources.Load<AudioClip>("Sounds/Award");
        AudioClip brickClip = Resources.Load<AudioClip>("Sounds/Brick");
        AudioClip brick1Clip = Resources.Load<AudioClip>("Sounds/Brick1");
        AudioClip brickDestroyClip = Resources.Load<AudioClip>("Sounds/Brick_Destroy");
        AudioClip buttonClip = Resources.Load<AudioClip>("Sounds/Button");
        AudioClip failedClip = Resources.Load<AudioClip>("Sounds/Failed");
        AudioClip fallDownClip = Resources.Load<AudioClip>("Sounds/Fall_Down");
        AudioClip jumpClip = Resources.Load<AudioClip>("Sounds/Jump");
        AudioClip punishmentClip = Resources.Load<AudioClip>("Sounds/Punishment");
        AudioClip winClip = Resources.Load<AudioClip>("Sounds/Win");
        AudioClip winPerfectClip = Resources.Load<AudioClip>("Sounds/WinPerfect");
        //将音效资源添加到字典中
        _soundDict = new Dictionary<SoundType, AudioClip>();
        _soundDict.Add(SoundType.Award, awardClip);
        _soundDict.Add(SoundType.Brick, brickClip);
        _soundDict.Add(SoundType.Brick_1, brick1Clip);
        _soundDict.Add(SoundType.Brick_Destroy, brickDestroyClip);
        _soundDict.Add(SoundType.Button, buttonClip);
        _soundDict.Add(SoundType.Failed, failedClip);
        _soundDict.Add(SoundType.Fall_Down, fallDownClip);
        _soundDict.Add(SoundType.Jump, jumpClip);
        _soundDict.Add(SoundType.Punishment, punishmentClip);
        _soundDict.Add(SoundType.Win, winClip);
        _soundDict.Add(SoundType.WinPerfect, winPerfectClip);
    }

    //播放背景音乐
    public void PlayBGM(BGMType bgmType)
    {
        //停止当前背景音乐的播放
        _bgmAudioSource.Stop();
        //设置新的背景音乐,并播放
        _bgmAudioSource.clip = _bgmDict[bgmType];
        _bgmAudioSource.Play();
    }

    //播放音效
    public void PlaySound(SoundType soundType)
    {
        //停止当前音效的播放
        _soundAudioSource.Stop();
        //设置新的音效,并播放
        _soundAudioSource.clip = _soundDict[soundType];
        _soundAudioSource.Play();
    }

    //关闭BGM播放
    public void StopBGM()
    {
        _bgmAudioSource.Stop();
    }

    //音量控制
    public void ControlVolume(float bgmVolume, float soundVolume)
    {
        _bgmAudioSource.volume = bgmVolume;
        _soundAudioSource.volume = soundVolume;
    }

    //以下三个方法都是空实现,不做任何操作
    public override void OnUpdate()
    {
    }

    public override void OnDestroy()
    {
    }
}

//定义背景音乐类型枚举
public enum BGMType
{
    AboutUS,
    BGM_1,
    BGM_2,
    BGM_3,
    BGM_4,
    BGM_5,
    Main_Panel
}

//定义音效类型枚举
public enum SoundType
{
    Award, Brick, Brick_1, Brick_Destroy, Button, Failed, Fall_Down, Jump, Punishment, Win, WinPerfect
}

测试音频代码

下面这两段代码,用于测试音频组件,可以复用

在这里插入图片描述



using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class aaa : MonoBehaviour
{
	private AudioManager _audioManager;

	public AudioManager AudioManager
	{
		get { return _audioManager; }
	}

	private static aaa _instance;

	public static aaa Instance
	{
		get { return _instance; }
	}

	private void Awake()
	{
		if (_instance == null)
		{
			_instance = this;
		}
	}

	// Use this for initialization
	void Start()
	{
		//实例化所有Manager
		_audioManager = new AudioManager();
		// 调用所有的Manager的OnInit方法
		_audioManager.OnInit();
	}

	// Update is called once per frame
	void Update()
	{
		_audioManager.OnUpdate();
	}

	private void OnDestroy()
	{
		_audioManager.OnDestroy();
	}
}


using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UI;

public class TestAudioPanel : MonoBehaviour
{

	public Button playSoundBtn;
	public Button playBGMBtn;
	public Slider volumeSlider;
	
	// Use this for initialization
	void Start () {
		playSoundBtn.onClick.AddListener(delegate { PlaySoundButtonClicked(); });
		playBGMBtn.onClick.AddListener(delegate { PlayBGMButtonClicked(); });
		volumeSlider.onValueChanged.AddListener(delegate(float arg0) { SliderValueChanged(arg0); });
	}
	
	// Update is called once per frame
	void Update () {
		
	}

	private void PlaySoundButtonClicked()
	{
		aaa.Instance.AudioManager.PlaySound(SoundType.Button);
	}

	private void PlayBGMButtonClicked()
	{
		aaa.Instance.AudioManager.PlayBGM(BGMType.Main_Panel);
	}

	private void SliderValueChanged(float value)
	{
		aaa.Instance.AudioManager.ControlVolume(value,value);
	}
	

}


UI全局管理器

父类抽象类 BaseManager

该抽象类定义了一个基本的管理器,其具体实现可以继承该类并实现三个抽象方法,以满足具体的需求。其中,OnInit() 方法用于初始化管理器、OnUpdate() 方法用于在每帧更新管理器、OnDestroy() 方法用于销毁管理器。这样,我们就可以通过继承该类来编写各种各样的管理器,从而更好地管理游戏中的各种资源、对象和逻辑。

using System.Collections; 
using System.Collections.Generic; 
using UnityEngine; 

public abstract class BaseManager  // 定义抽象类 BaseManager
{

    public abstract void OnInit();  // 声明抽象方法 OnInit()
    public abstract void OnUpdate();  // 声明抽象方法 OnUpdate()
    public abstract void OnDestroy();  // 声明抽象方法 OnDestroy()

}


子类 UIManager

这段代码主要实现了一个UI管理器,其中包括了以下功能:

  1. 加载面板:根据传入的面板类型,从预设体字典中获取对应的预设体并实例化,然后执行该面板的OnEnter方法,同时将该面板入栈。
  2. 关闭(弹出)顶层面板:从栈中弹出顶层面板,并执行该面板的OnExit方法,同时恢复下一个面板的OnResume方法。
  3. 初始化:获取Canvas的Transform属性,初始化预设体字典和已实例化面板字典,并加载第一个面板。
  4. 枚举类型:定义了PanelType枚举类型,包括了所有的面板类型。

补充说明:

  1. BaseManager是一个抽象类,该UIManager类继承自BaseManager,并且需要实现其中的三个虚函数:OnInit、OnUpdate和OnDestroy。
  2. 该UIManager类中还定义了一个InstantiatedPanelDict属性,用于获取已实例化面板字典。
```csharp
using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class UIManager : BaseManager
{
    private Transform _canvasTransform; //Canvas的Transform组件
    private Dictionary<PanelType, GameObject> _uiPanelPrefabDict; //UI面板预制体字典
    private Dictionary<PanelType, BasePanel> _instantiatedPanelDict; //实例化的UI面板字典
    private Stack<BasePanel> _panelStack; //UI面板栈

    public Dictionary<PanelType, BasePanel> InstantiatedPanelDict
    {
        get { return _instantiatedPanelDict; }
    }

    /// <summary>
    /// 加载面板
    /// </summary>
    /// <param name="panelType"></param>
    /// <returns></returns>
    public BasePanel PushPanel(PanelType panelType)
    {
        //从实例化的面板字典中获取该面板
        BasePanel panel = null;
        _instantiatedPanelDict.TryGetValue(panelType, out panel);
        if (panel == null)
        {
            //说明该面板从未实例化过(从未入栈),此处需要实例化
            GameObject panelPrefab = _uiPanelPrefabDict[panelType];
            GameObject panelGO = GameObject.Instantiate(panelPrefab, _canvasTransform, false);
            panel = panelGO.GetComponent<BasePanel>();
            _instantiatedPanelDict.Add(panelType, panel); //将该面板加入实例化的面板字典中
        }
        else
        {
            //说明该面板已经实例化,入栈后被出栈,处于被禁用状态,需要重新启用
            panel.gameObject.SetActive(true);
        }

        //执行该Panel的OnEnter
        panel.OnEnter();
        if (_panelStack.Count > 0)
        {
            BasePanel peekPanel = _panelStack.Peek();
            peekPanel.OnPause();
        }
        _panelStack.Push(panel); //将该面板入栈
        return panel;
    }

    /// <summary>
    /// 关闭(弹出)顶层面板
    /// </summary>
    public void PopPanel()
    {
        if (_panelStack.Count > 0)
        {
            BasePanel peekPanel = _panelStack.Pop();
            peekPanel.OnExit();
            if (_panelStack.Count > 0)
            {
                BasePanel secPeekPanel = _panelStack.Peek();
                secPeekPanel.OnResume();
            }
        }
    }

    public override void OnInit()
    {
        //获取挂载Canvas的Transform属性
        _canvasTransform = GameObject.Find("Canvas").transform;
        //初始化面板预制体字典
        _uiPanelPrefabDict = new Dictionary<PanelType, GameObject>();
        _uiPanelPrefabDict.Add(PanelType.Main, Resources.Load<GameObject>("UIPanel/Panel_Main"));
        _uiPanelPrefabDict.Add(PanelType.Game, Resources.Load<GameObject>("UIPanel/Panel_Game"));
        _uiPanelPrefabDict.Add(PanelType.Result, Resources.Load<GameObject>("UIPanel/Panel_Result"));
        _uiPanelPrefabDict.Add(PanelType.Battle, Resources.Load<GameObject>("UIPanel/Panel_Battle"));
        _uiPanelPrefabDict.Add(PanelType.Fail, Resources.Load<GameObject>("UIPanel/Panel_Fail"));
        _uiPanelPrefabDict.Add(PanelType.Success, Resources.Load<GameObject>("UIPanel/Panel_Success"));
        _uiPanelPrefabDict.Add(PanelType.Pause, Resources.Load<GameObject>("UIPanel/Panel_Pause"));
        _uiPanelPrefabDict.Add(PanelType.Level, Resources.Load<GameObject>("UIPanel/Panel_Level"));
        _uiPanelPrefabDict.Add(PanelType.Index, Resources.Load<GameObject>("UIPanel/Panel_Index"));
        //初始化
        _instantiatedPanelDict = new Dictionary<PanelType, BasePanel>();
        _panelStack = new Stack<BasePanel>();
        //加载第一个Panel
        // PushPanel(PanelType.Main);
    }

    public override void OnUpdate()
    {

    }

    public override void OnDestroy()
    {

    }
}

public enum PanelType
{
    Main,
    Game,
    Result,
    Battle,
    Fail,
    Success,
    Pause,
    Level,
    Index
}







这段代码实现了一个UI管理器,用于管理游戏中的UI面板。其中,PushPanel()函数用于加载面板,PopPanel()函数用于关闭顶层面板,OnInit()函数用于在UI管理器被初始化时加载第一个面板。

UI管理器中使用了一个面板栈_panelStack,用于存储当前打开的所有UI面板,实现了UI面板的层级管理。同时,还使用了两个面板字典_uiPanelPrefabDict_instantiatedPanelDict,用于存储预制体和实例化的面板。

代码中使用了单例模式实现了UI管理器的唯一性。同时,还继承了BaseManager类,实现了对游戏管理器的统一管理。


四、 UI按钮的引用

父类 BasePanel

这四个方法是状态机中状态的生命周期方法,用于管理状态的进入、暂停、恢复和退出。

具体来说,当一个状态被切换到时,首先会调用OnEnter()方法,用于初始化状态的数据和变量。当状态被暂停时(例如切换到其他状态),会调用OnPause()方法,用于暂停状态的逻辑和动画。当状态恢复时(例如从其他状态切换回该状态),会调用OnResume()方法,用于恢复状态的逻辑和动画。当状态被退出时,会调用OnExit()方法,用于清理状态的数据和变量。

using System.Collections;                      
using System.Collections.Generic;              
using UnityEngine;                              

public abstract class BasePanel : MonoBehaviour  // 定义一个抽象类 BasePanel,继承自 MonoBehaviour 类
{

    public abstract void OnEnter();              // 声明一个抽象方法 OnEnter,由子类实现

    public abstract void OnPause();              // 声明一个抽象方法 OnPause,由子类实现

    public abstract void OnResume();             // 声明一个抽象方法 OnResume,由子类实现

    public abstract void OnExit();               // 声明一个抽象方法 OnExit,由子类实现

}


子类主面板 MainPanel

  1. 定义MainPanel类,继承自BasePanel。
  2. 定义开始按钮和关闭按钮两个公共属性。
  3. 在Start()方法中添加开始按钮和关闭按钮的点击事件监听器。
  4. 在StartButtonClicked()方法中调用UnityFacade.Instance.UiManager.PushPanel()方法,实现面板的切换到GamePanel。
  5. 在CloseButtonClicked()方法中调用UnityFacade.Instance.UiManager.PopPanel()方法,实现当前面板的弹出。
  6. 在OnEnter()方法中实现面板进入时的操作。
  7. 在OnPause()方法中禁用开始按钮和关闭按钮,实现面板暂停时的操作。
  8. 在OnResume()方法中启用开始按钮和关闭按钮,实现面板恢复时的操作。
  9. 在OnExit()方法中隐藏当前面板,实现面板退出时的操作。


```using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UI;

public class MainPanel : BasePanel //继承自BasePanel
{
    public Button startBtn; //开始按钮
    public Button closeBtn; //关闭按钮

    private void Start()
    {
        //添加开始按钮点击事件监听器
        startBtn.onClick.AddListener(delegate { StartButtonClicked(); });
        //添加关闭按钮点击事件监听器
        closeBtn.onClick.AddListener(delegate { CloseButtonClicked(); });
    }

    private void StartButtonClicked()
    {
        //点击开始按钮,推入GamePanel
        UnityFacade.Instance.UiManager.PushPanel(PanelType.Game);
    }

    private void CloseButtonClicked()
    {
        //点击关闭按钮,弹出当前面板
        UnityFacade.Instance.UiManager.PopPanel();
    }

    public override void OnEnter()
    {
        //面板进入时调用此方法
        Debug.Log("MainPanel加载了");
    }

    public override void OnPause()
    {
        //面板暂停时调用此方法,禁用开始按钮和关闭按钮
        startBtn.interactable = false;
        closeBtn.interactable = false;
    }

    public override void OnResume()
    {
        //面板恢复时调用此方法,启用开始按钮和关闭按钮
        startBtn.interactable = true;
        closeBtn.interactable = true;
    }

    public override void OnExit()
    {
        //面板退出时调用此方法,隐藏当前面板
        this.gameObject.SetActive(false);
    }
}```



子类 游戏中 GamePanel

这段代码实现了一个游戏面板(GamePanel),继承自一个基础面板(BasePanel),并实现了在面板中的按钮点击事件。具体来说,这个面板有两个按钮:resultBtn和closeBtn,点击resultBtn会跳转到一个结果面板(PanelType.Result),而点击closeBtn会关闭当前面板。

在 Start() 方法中,通过监听按钮的点击事件来实现按钮的功能,即 resultBtn 点击时调用 ResultButtonClicked() 方法,closeBtn 点击时调用 CloseButtonClicked() 方法。ResultButtonClicked() 方法中调用了 UnityFacade.UiManager.PushPanel() 方法,用于跳转到结果面板,而 CloseButtonClicked() 方法中调用了 UnityFacade.UiManager.PopPanel() 方法,用于关闭当前面板。

在 OnEnter() 方法中,当这个游戏面板被打开时,会输出一个 Debug.Log() 信息,提示面板被打开了。

在 OnPause() 方法中,当这个游戏面板被暂停时,会将 resultBtn 和 closeBtn 的 interactable 属性设置为 false,即这两个按钮将不再响应点击事件。

在 OnResume() 方法中,当这个游戏面板从暂停状态中恢复时,会将 resultBtn 和 closeBtn 的 interactable 属性设置为 true,即这两个按钮将重新响应点击事件。

在 OnExit() 方法中,当这个游戏面板被关闭时,会将这个游戏面板的 gameObject 设置为不可见,即关闭这个游戏面板。


using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UI;

// 继承自 BasePanel
public class GamePanel : BasePanel
{
    // 定义两个按钮
    public Button resultBtn;
    public Button closeBtn;

    // 在 Start 函数中添加按钮点击事件监听
    private void Start()
    {
        resultBtn.onClick.AddListener(delegate { ResultButtonClicked(); });
        closeBtn.onClick.AddListener(delegate { CloseButtonClicked(); });
    }

    // 点击结果按钮的处理函数
    private void ResultButtonClicked()
    {
        // 调用 UnityFacade 的 UiManager 的 PushPanel 函数,打开结果面板
        UnityFacade.Instance.UiManager.PushPanel(PanelType.Result);
    }

    // 点击关闭按钮的处理函数
    private void CloseButtonClicked()
    {
        // 调用 UnityFacade 的 UiManager 的 PopPanel 函数,关闭当前面板
        UnityFacade.Instance.UiManager.PopPanel();
    }

    // 进入面板时的处理函数
    public override void OnEnter()
    {
        Debug.Log("GamePanel打开了");
    }

    // 暂停面板时的处理函数
    public override void OnPause()
    {
        // 将两个按钮设置为不可用
        resultBtn.interactable = false;
        closeBtn.interactable = false;
    }

    // 恢复面板时的处理函数
    public override void OnResume()
    {
        // 将两个按钮设置为可用
        resultBtn.interactable = true;
        closeBtn.interactable = true;
    }

    // 退出面板时的处理函数
    public override void OnExit()
    {
        // 将自身的 gameObject 设置为不可见
        this.gameObject.SetActive(false);
    }
}

子类 游戏结果 ResultPanel

它实现了一个游戏面板,名为ResultPanel。这个面板里有一个按钮,名为closeBtn,点击它可以关闭当前面板。这个面板继承自BasePanel类,因此实现了BasePanel类中定义的四个方法:OnEnter、OnPause、OnResume、OnExit。其中,OnEnter方法是在面板打开时被调用的,OnPause方法是在面板被暂停时被调用的,OnResume方法是在面板恢复时被调用的,OnExit方法是在面板关闭时被调用的。在这里,OnEnter方法只是打印了一条调试信息。Start方法用于初始化面板,它给closeBtn按钮添加了一个事件监听器,当按钮被点击时,会执行CloseButtonClicked方法。CloseButtonClicked方法中,通过UnityFacade.Instance.UiManager.PopPanel()方法关闭当前面板。

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UI;

public class ResultPanel : BasePanel
{

	public Button closeBtn;
	
	
	
	public override void OnEnter()
	{
		Debug.Log("ResultPanel打开了");
	}

	public override void OnPause()
	{
		
	}

	public override void OnResume()
	{
		
	}

	public override void OnExit()
	{
		this.gameObject.SetActive(false);
	}

	// Use this for initialization
	void Start () {
		closeBtn.onClick.AddListener(delegate { CloseButtonClicked(); });
	}

	private void CloseButtonClicked()
	{
		UnityFacade.Instance.UiManager.PopPanel();
	}
	// Update is called once per frame
	void Update () {
		
	}
}


角色动画器、控制角色移动

角色可以跳跃、行走
在这里插入图片描述

在这里插入图片描述


游戏奖惩道具

掉血的砖块:用数组存储四张图片,踩一下hp-1。

public void Injured()
	{
		_hp--;
		if (_hp > 0)
		{
			if (_hp == 3)
			{
				UnityFacade.Instance.GameManager.AddTouchCount();
			}
			UnityFacade.Instance.AudioManager.PlaySound(SoundType.Brick);
			_spriteRenderer.sprite = sprites[4 - _hp];
		}
		else
		{
			UnityFacade.Instance.AudioManager.PlaySound(SoundType.Brick_Destroy);
			Destroy(this.gameObject);
		}
	}

在这里插入图片描述


保护罩:玩家得到后,不受任何伤害

  protectorGO.SetActive(true);

在这里插入图片描述

红色感叹号炸弹:计时器减少10秒钟


绿色感叹号:计时器时间增加10秒钟


死亡小球:玩家碰到后
直接游戏结束

在这里插入图片描述

private void Move()
	{
		if (Math.Abs(_rigidbody2D.velocity.x) < 0.05f&&_isOnGround)
		{
			if (_direction == MoveDirection.Left)
			{	
				_rigidbody2D.velocity=new Vector2((int)MoveDirection.Right*vSpeed,0);
				_direction = MoveDirection.Right;
			}else if (_direction == MoveDirection.Right)
			{
				_rigidbody2D.velocity=new Vector2((int)MoveDirection.Left*vSpeed,0);
				_direction = MoveDirection.Left;
			}
		}
	}

过关星星动画:
在这里插入图片描述


  • 1
    点赞
  • 6
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

忽然602

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值