在游戏开发之中,我们会遇到一些提示面板存在多个选项供玩家选择,比如是否确定购买该物品,一个是一个否。或者是是否选择存档一,一个选择,一个放弃存档。这种提示框在游戏之中非常常见,然而,我们不可能为此制作多个UI,那么如何通过一个UI以及部分提示内容的框架代码达到以上的效果呢?
我们获取到这类需求,开始大致思考思路:首先,两个按钮造成的事件是不同的,不同的提示框选择的内容也是不同的,那么我们可以将他们制作成委托事件,使用回调的方式让他们每次创建都可以保证逻辑根据具体的事件内容发生变化。至于按钮的文字显示以及窗口的文字显示就另外制作逻辑让他们发生改变。这些逻辑我们可以将他们制作到同一个方法体之中。捋清楚思路之后,我们开始写代码:
using UnityEngine.Events;
using UnityEngine.UI;
public class TipPanel : TipPanelBase
{
/// <summary>
/// 左右两边按钮按下之后调用的函数内容
/// </summary>
private UnityAction _callBack1;
private UnityAction _callBack2;
public override void Start()
{
base.Start();
}
public override void HideMe()
{
base.HideMe();
}
public override void ShowMe()
{
base.ShowMe();
}
protected override void BtnYesClick()
{
base.BtnYesClick();
_callBack1?.Invoke();
}
protected override void BtnNoClick()
{
base.BtnNoClick();
_callBack2?.Invoke();
}
/// <summary>
/// 初始化提示页面的方法
/// </summary>
/// <param name="txt">文本信息</param>
/// <param name="txtB1">按钮1显示内容</param>
/// <param name="txtB2">按钮2显示内容</param>
public void Init(string txt,string txtB1="是",string txtB2="再想想")
{
GetControl<Text>("txtTip").text = txt;
GetControl<Text>("txt1").text = txtB1;
GetControl<Text>("txt2").text = txtB2;
}
/// <summary>
/// 用于设置按钮点击事件的回调函数
/// </summary>
/// <param name="callBackLeft"></param>
/// <param name="callBackRight"></param>
public void SetEvent(UnityAction callBackLeft, UnityAction callBackRight)
{
_callBack1 = callBackLeft;
_callBack2 = callBackRight;
}
}
我们首先根据之前的思路,制作出面板逻辑,随后由于该逻辑可能在整个游戏之中能够使用,所以我们创建一个MyGameMgr的单例模式管理器,使其贯穿整个游戏,在该管理器之中添加以下调用逻辑的方法:
/// <summary>
/// 用于改变提示内容的方法
/// </summary>
/// <param name="txTTip">提示文字内容</param>
/// <param name="callBackLeft">左边按钮触发的回调函数</param>
/// <param name="callBackRight">右边按钮触发的回调函数</param>
/// <param name="txtB1">左边按钮的文本显示内容</param>
/// <param name="txtB2">右边按钮显示的文本显示内容</param>
public void ChangeTipPanelTip(string txTTip, UnityAction callBackLeft, UnityAction callBackRight,
string txtB1 = "是", string txtB2 = "再想想")
{
UIMgr.Instance.ShowPanel<TipPanel>(E_LoadingMethod.Res,E_UI_Layer.System,false, (panel) =>
{
panel.Init(txTTip,txtB1,txtB2);
panel.SetEvent(callBackLeft,callBackRight);
});
}
这样看来就可以完成之前我们的猜测了,那么我们开始使用这一小段逻辑:
在此之前我接到了一个关于提示面板的需求:进入游戏之后选择职业,选择职业之后点击确定开始弹窗是否选择XX职业,左键是,右键再想想,如果点击左键就创建对应的职业玩家,并且初始化内容,同时关闭职业选择的页面,游戏进入第一回合。如果点击右键玩家就重新选择职业。得到这样的需求之后,我们根据之前做好的提示小框架开始使用我们的代码:
MyCardGameMgr.Instance.ChangeTipPanelTip($"确定以{MyCardGameMgr.Instance.Careers.Name}职业进行游戏吗?", () =>
{
MyCardGameMgr.Instance.HeroTarge = ResMgr.Instance.Load<GameObject>(MyCardGameMgr.Instance.Careers.HeroRes).transform;
GameObject.Find("Main Camera").GetComponent<CameraMove>().target = MyCardGameMgr.Instance.HeroTarge;
//更新玩家信息
MyCardGameMgr.Instance.HeroTarge.gameObject.GetComponent<PlayerMoveC>().InitInfo();
MapMgr.Instance.PlayerMoveCs = MyCardGameMgr.Instance.HeroTarge.gameObject.GetComponent<PlayerMoveC>();
UIMgr.Instance.HidePanel<CareerChoicesPanel>(true);
UIMgr.Instance.ShowPanel<ChoosePanel>(E_LoadingMethod.Res,E_UI_Layer.Top);
UIMgr.Instance.ShowPanel<GamePanel>();
UIMgr.Instance.HidePanel<TipPanel>(true);
}, () =>
{
UIMgr.Instance.HidePanel<TipPanel>(true);
});
(以上的数据使用了二进制进行读取)
如果是存档,面板内容不同,我们也可以完美实现事件替换:
核心代码如下:
/// <summary>
/// 用于保护存档的机制
/// </summary>
private void SaveProtect(int num)
{
if(MyCardGameMgr.Instance.PlayerSavesList.Count<num-1)
MyCardGameMgr.Instance.ChangeTipPanelTip($"当前的存档{MyCardGameMgr.Instance.PlayerSavesList.Count+1}还未使用,请先使用存档{MyCardGameMgr.Instance.PlayerSavesList.Count+1}", () =>
{
_txtDic[MyCardGameMgr.Instance.PlayerSavesList.Count+1].text = DateTime.Now.ToString("yyyy-MM-dd HH:mm");
_stringDic.Add(MyCardGameMgr.Instance.PlayerSavesList.Count + 1,_txtDic[MyCardGameMgr.Instance.PlayerSavesList.Count + 1].text);
MyCardGameMgr.Instance.PlayerSavesList.Add(MyCardGameMgr.Instance.PlayerSaves);
/*BinaryMgr.Instance.AutoCreatFile<Dictionary<int,string>>(MyCardGameMgr.Instance.StringDic,false,false);
BinaryMgr.Instance.AutoCreatFile<List<PlayerSaves>>(MyCardGameMgr.Instance.PlayerSavesList,false,false);*/
UIMgr.Instance.HidePanel<TipPanel>(true);
}, () =>
{
UIMgr.Instance.HidePanel<TipPanel>(true);
},$"使用存档{MyCardGameMgr.Instance.PlayerSavesList.Count+1}","放弃存档");
else
{
SaveThis(num,_txtDic[num]);
}
}
你会发现他们能够成功适配各种环境了,并且在整场游戏之中都能够调用。
以上是我对于有选项的提示面板的制作思路,如果你有更好的欢迎与我交流。此篇提供思路以及部分源码,希望大家能够喜欢,有帮助就请点赞收藏吧!