欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页

UGF游戏框架实例开发教程—FlappyBird(五)菜单流程的代码编写

程序员文章站 2024-03-18 20:42:34
...

在正式开始写代码之前,我们需要先将命名空间给重命名一下

随便找一个Scripts下的文件,修改命名空间为FlappyBird

UGF游戏框架实例开发教程—FlappyBird(五)菜单流程的代码编写


修改命名空间后,有几个地方需要重新设置

UGF游戏框架实例开发教程—FlappyBird(五)菜单流程的代码编写

UGF游戏框架实例开发教程—FlappyBird(五)菜单流程的代码编写


UGF游戏框架实例开发教程—FlappyBird(五)菜单流程的代码编写


UGF游戏框架实例开发教程—FlappyBird(五)菜单流程的代码编写


OK,接下来处理流程相关的东西,创建两个类,分别命名为ProcedureMenu和ProcedureMain,代表菜单流程与主流程,作为流程类,需要继承ProcedureBase

namespace FlappyBird
{
    /// <summary>
    /// 菜单流程
    /// </summary>
    public class ProcedureMenu : ProcedureBase
    {

    }

}


namespace FlappyBird
{
    /// <summary>
    /// 主流程
    /// </summary>
    public class ProcedureMain : ProcedureBase
    {

    }

}


然后找到ProcedureComponent所在的游戏物体,勾选所有流程类,并设置入口流程

UGF游戏框架实例开发教程—FlappyBird(五)菜单流程的代码编写


打开ProcedureChangeScene(这个流程负责切换场景的处理),找到TODO的地方,编写如下代码

 protected override void OnUpdate(ProcedureOwner procedureOwner, float elapseSeconds, float realElapseSeconds)
        {
            base.OnUpdate(procedureOwner, elapseSeconds, realElapseSeconds);

            if (!m_IsChangeSceneComplete)
            {
                return;
            }

            //TODO:在这里根据切换到的场景编号进行对应的流程切换
            switch (gotoSceneId)
            {
                case 1:
                    ChangeState<ProcedureMenu>(procedureOwner);
                    break;

                case 2:
                    ChangeState<ProcedureMain>(procedureOwner);
                    break;

                default:
                    break;
            }
        }


接着打开ProcedurePreload(负责处理预加载的流程),找到TODO的地方,编写如下代码

protected override void OnUpdate(ProcedureOwner procedureOwner, float elapseSeconds, float realElapseSeconds)
        {
            base.OnUpdate(procedureOwner, elapseSeconds, realElapseSeconds);

            IEnumerator<bool> iter = m_LoadedFlag.Values.GetEnumerator();
            while (iter.MoveNext())
            {
                if (!iter.Current)
                {
                    return;
                }
            }

            // TODO:这里开始,切换到你的场景,场景编号可在DefaultConfig中配置
            procedureOwner.SetData<VarInt>(Constant.ProcedureData.NextSceneId, GameEntry.Config.GetInt("Scene.Menu"));
            ChangeState<ProcedureChangeScene>(procedureOwner);
        }


这些TODO的地方处理完成后,可以开始编写菜单流程的相关代码了

using UnityGameFramework.Runtime;
using GameFramework.Procedure;
using ProcedureOwner = GameFramework.Fsm.IFsm<GameFramework.Procedure.IProcedureManager>;

namespace FlappyBird
{
    /// <summary>
    /// 菜单流程
    /// </summary>
    public class ProcedureMenu : ProcedureBase
    {
        public bool IsStartGame { get; set; }

        protected override void OnEnter(ProcedureOwner procedureOwner)
        {
            base.OnEnter(procedureOwner);

            IsStartGame = false;

            //打开UI界面
            GameEntry.UI.OpenUIForm(UIFormId.MenuForm, this);
        }

        protected override void OnUpdate(ProcedureOwner procedureOwner, float elapseSeconds, float realElapseSeconds)
        {
            base.OnUpdate(procedureOwner, elapseSeconds, realElapseSeconds);

            if (IsStartGame)
            {
                //切换到主要场景
                procedureOwner.SetData<VarInt>(Constant.ProcedureData.NextSceneId, GameEntry.Config.GetInt("Scene.Main"));
                ChangeState<ProcedureChangeScene>(procedureOwner);
            }
        }

      
    }

}

这里的OnEnter和OnUpdate是流程的生命周期方法,在UGF中,流程是一种特殊的状态,受状态机管理,所以也有相应的生命周期方法


在上面那段代码中,我们打开了菜单UI,所以我们接下来需要编写菜单UI的相关代码

先去UIComponent里添加一个UIGroup,并且指定InstanceRoot

UGF游戏框架实例开发教程—FlappyBird(五)菜单流程的代码编写



把MenuForm拖到UI Form Instances下面,然后新建一个MenuForm脚本,继承UGuiForm,编写如下代码

UGF游戏框架实例开发教程—FlappyBird(五)菜单流程的代码编写

    /// <summary>
    /// 菜单界面脚本
    /// </summary>
    public class MenuForm : UGuiForm
    {
        /// <summary>
        /// 菜单流程
        /// </summary>
        private ProcedureMenu m_ProcedureMenu = null;

        protected override void OnOpen(object userData)
        {
            base.OnOpen(userData);
            m_ProcedureMenu = (ProcedureMenu)userData;
        }

        protected override void OnClose(object userData)
        {
            m_ProcedureMenu = null;
            base.OnClose(userData);
        }

        public void OnStartButtonClick()
        {
            m_ProcedureMenu.IsStartGame = true;
        }

        public void OnSettingButtonClick()
        {
            GameEntry.UI.OpenUIForm(UIFormId.SettingForm);
        }


把这个脚本拖到MenuForm上面,然后把MenuForm下的两个按钮的Button组件删除,添加CommonButton脚本,在OnClick委托中注册MenuForm的PlaySound方法,参数输入1

UGF游戏框架实例开发教程—FlappyBird(五)菜单流程的代码编写


然后分别将MenuForm里的按钮监听方法注册到对应的按钮上

UGF游戏框架实例开发教程—FlappyBird(五)菜单流程的代码编写

UGF游戏框架实例开发教程—FlappyBird(五)菜单流程的代码编写


应用预制体变更,完善菜单流程类的代码

using UnityGameFramework.Runtime;
using GameFramework.Procedure;
using ProcedureOwner = GameFramework.Fsm.IFsm<GameFramework.Procedure.IProcedureManager>;
using GameFramework.Event;

namespace FlappyBird
{
    /// <summary>
    /// 菜单流程
    /// </summary>
    public class ProcedureMenu : ProcedureBase
    {
        public bool IsStartGame { get; set; }

        /// <summary>
        /// 菜单界面脚本
        /// </summary>
        private MenuForm m_MenuForm = null;

        protected override void OnEnter(ProcedureOwner procedureOwner)
        {
            base.OnEnter(procedureOwner);

            IsStartGame = false;

            //订阅UI打开成功事件
            GameEntry.Event.Subscribe(OpenUIFormSuccessEventArgs.EventId, OnOpenUIFormSuccess);

            //打开UI界面
            GameEntry.UI.OpenUIForm(UIFormId.MenuForm, this);
        }

        protected override void OnUpdate(ProcedureOwner procedureOwner, float elapseSeconds, float realElapseSeconds)
        {
            base.OnUpdate(procedureOwner, elapseSeconds, realElapseSeconds);

            if (IsStartGame)
            {
                //切换到主场景
                procedureOwner.SetData<VarInt>(Constant.ProcedureData.NextSceneId, GameEntry.Config.GetInt("Scene.Main"));
                ChangeState<ProcedureChangeScene>(procedureOwner);
            }
        }

        protected override void OnLeave(ProcedureOwner procedureOwner, bool isShutdown)
        {
            base.OnLeave(procedureOwner, isShutdown);

            if (m_MenuForm != null)
            {
                m_MenuForm.Close(isShutdown);
                m_MenuForm = null;
            }

            //取消订阅UI打开成功事件
            GameEntry.Event.Unsubscribe(OpenUIFormSuccessEventArgs.EventId, OnOpenUIFormSuccess);
        }

        private void OnOpenUIFormSuccess(object sender, GameEventArgs e)
        {
            OpenUIFormSuccessEventArgs ne = (OpenUIFormSuccessEventArgs)e;
            if (ne.UserData != this)
            {
                return;
            }

            m_MenuForm = (MenuForm)ne.UIForm.Logic;
        }


    }

}


我们刚才在MenuForm里编写了打开设置界面的代码,因此我们也需要来编写设置面板的脚本

创建一个SettingForm脚本拖到对应UI物体上,为其编写如下代码

    /// <summary>
    /// 设置界面脚本
    /// </summary>
    public class SettingForm : UGuiForm
    {
        public void OnCloseButtonClick()
        {
            Close();
        }

        public void OnMusicSettingValueChange(float value)
        {
            GameEntry.Sound.SetVolume("Music", value);
        }

        public void OnSoundSettingValueChange(float value)
        {
            GameEntry.Sound.SetVolume("Sound", value);
            GameEntry.Sound.SetVolume("UISound", value);
        }
    }

在这个脚本里监听了按钮的点击与两个Slider的变化,因此我们也需要将这三个方法注册进去

UGF游戏框架实例开发教程—FlappyBird(五)菜单流程的代码编写

UGF游戏框架实例开发教程—FlappyBird(五)菜单流程的代码编写

UGF游戏框架实例开发教程—FlappyBird(五)菜单流程的代码编写


应用预制体变更,现在我们可以点击运行来看看项目能不能跑起来了

UGF游戏框架实例开发教程—FlappyBird(五)菜单流程的代码编写


点击设置,调整音乐大小

UGF游戏框架实例开发教程—FlappyBird(五)菜单流程的代码编写


点击开始按钮,进入Main场景

UGF游戏框架实例开发教程—FlappyBird(五)菜单流程的代码编写


虽然没有做UI,但已经可以听到背景音乐了