NLDClient-yudde/ProjectNLD/Assets/Code/Scripts/Gameplay/UI/UI_LevelSelectController.cs

601 lines
20 KiB
C#
Raw Blame History

This file contains ambiguous Unicode characters!

This file contains ambiguous Unicode characters that may be confused with others in your current locale. If your use case is intentional and legitimate, you can safely ignore this warning. Use the Escape button to highlight these characters.

using System.Collections.Generic;
using System.Threading;
using cfg.LevelCfg;
using Cysharp.Threading.Tasks;
using Framework;
using Gameplay.Level;
using PhxhSDK;
using TMPro;
using UnityEngine;
using UnityEngine.Serialization;
using Utils;
using Button = UnityEngine.UI.Button;
using Image = UnityEngine.UI.Image;
public class UI_LevelSelectController : UIWindow
{
//UI GameObj
///Auto Gen Start///
public Button Button_Back;
public TMP_Text Text_Back;
public Button Button_Home;
public Button Button_MainLevel;
public TMP_Text Text_MainLevel;
public TMP_Text Text_MainLevelNum;
public TMP_Text Text_MainLevelName;
public Image Image_MainlevelLogo;
public Image Image_BlackBar;
public TMP_Text Text_MainLevelProcess;
public Button Button_BranchLevel;
public Button Button_DungeonlEVEL;
public Image Image_ChapterBG;
public Image Image_LevelBG;
public Image Image_LevelTitle;
public TMP_Text Text_ChapterNum;
public TMP_Text Text_ChapterName;
public Image Image_ProcessBG;
public Image Image_LevelProcess;
public Image Image_ProcessBar;
public TMP_Text Text_StarNum;
public Image Image_SelectBG;
public Button Button_Plot;
public TMP_Text Text_Read;
public Button Button_Easy;
public TMP_Text Text_Simple;
public Button Button_Hard;
public TMP_Text Text_Hard;
public Image Image_WhiteRect;
[FormerlySerializedAs("Image_Read")] public Image Image_Plot;
[FormerlySerializedAs("Image_Simple")] public Image Image_Easy;
public Image Image_RedRect;
public Image Image_Hard;
///Auto Gen End///
private enum PageType
{
Mode = 1,
LevelGroup = 2,
Level = 3,
}
private PageType _currPage = PageType.Mode;
private LevelGroupType _currGroupType;
private LevelGroupInfo _currLevelGroupInfo;
private ChapterInfo _currEasyChapterInfo;
private ChapterInfo _currHardChapterInfo;
private ChapterInfo _currPlotChapterInfo;
private ChapterInfo _currChapterInfo;
private LevelInfo _currSelectLevelInfo;
private List<LevelGroupInfo> _showLevelGroupInfoList = new();
private List<LevelInfo> _showLevelInfoList = new();
private RectTransform UI_ModeChoose;
private RectTransform UI_LevelGroupChoose;
private RectTransform UI_LevelChoose;
private RectTransform _modeParent;
private Framework.PhxhScrollView _levelGroupScrollView;
private Framework.PhxhScrollView _levelScrollView;
private RectTransform _starRewardsParent;
private const string STAR_REWARD_PREFAB_PATH = "Assets/Art/UI/Prefab/LevelSelect/Button_StarReward.prefab";
private List<GameObject> _starRewardPool = new();
private List<GameObject> _showStarReward = new();
private float _totalMoveTime = 1f;
private CancellationTokenSource _cts;
public override void OnAwake()
{
//bind UI GameObj
UI_LevelSelectBinder.GetComponents(this);
BindProperty();
BindEvent();
RegisterSignal();
}
private void BindProperty()
{
UI_ModeChoose = transform.Find("UI_ModeChoose") as RectTransform;
UI_LevelGroupChoose = transform.Find("UI_LevelGroupChoose") as RectTransform;
UI_LevelChoose = transform.Find("UI_LevelChoose") as RectTransform;
_modeParent = UI_ModeChoose.Find("Scroll View/Viewport/Content") as RectTransform;
_levelGroupScrollView = UI_LevelGroupChoose.Find("Image_ChapterBG/Scroll View").GetComponent< Framework.PhxhScrollView>();
_levelScrollView = UI_LevelChoose.Find("Image_LevelBG/Scroll View").GetComponent< Framework.PhxhScrollView>();
_starRewardsParent = Image_LevelProcess.transform.Find("StarRewardProgress/starRewards") as RectTransform;
_levelGroupScrollView.SetUpdateFunc(OnRenderLevelGroup);
_levelGroupScrollView.SetItemCountFunc(GetLevelGroupCount);
_levelGroupScrollView.SetButton(SetOnLevelGroupClick);
_levelScrollView.SetUpdateFunc(OnRenderLevelInfo);
_levelScrollView.SetItemCountFunc(GetLevelCount);
_levelScrollView.SetButton(SetOnLevelClick);
}
private void BindEvent()
{
BindButton("UI_Topbtn/Button_Back", OnClickBack);
BindButton("UI_Topbtn/Button_Home", OnClickHome);
BindButton("UI_LevelChoose/Image_ProcessBG/Image_SelectBG/Button_Easy", OnClickEasy);
BindButton("UI_LevelChoose/Image_ProcessBG/Image_SelectBG/Button_Hard", OnClickHard);
BindButton("UI_LevelChoose/Image_ProcessBG/Image_SelectBG/Button_Plot", OnClickPlot);
var modeButtonCount = _modeParent.childCount;
for (int i = 0; i < modeButtonCount; i++)
{
var modeButton = _modeParent.GetChild(i).GetComponent<Button>();
modeButton.onClick.RemoveAllListeners();
var index = i;
modeButton.onClick.AddListener(() =>
{
var levelGroupType = (LevelGroupType)index;
EnterSelectLevelGroup(levelGroupType);
});
}
}
private void RegisterSignal()
{
EventManager.Instance.Register(EventManager.EventName.ChapterInfoChange, OnChapterInfoChanged);
}
private void UnRegisterSignal()
{
EventManager.Instance.Unregister(EventManager.EventName.ChapterInfoChange, OnChapterInfoChanged);
}
private void Refresh()
{
RefreshPage();
switch (_currPage)
{
case PageType.Mode:
RefreshMode();
break;
case PageType.LevelGroup:
RefreshLevelGroup();
break;
case PageType.Level:
RefreshLevel();
break;
}
}
//将当前UI看成是三个页面选模式选关卡组选关
private void RefreshPage()
{
UI_ModeChoose.gameObject.SetActive(_currPage == PageType.Mode);
UI_LevelGroupChoose.gameObject.SetActive(_currPage == PageType.LevelGroup);
UI_LevelChoose.gameObject.SetActive(_currPage == PageType.Level);
}
private void RefreshMode()
{
}
private void RefreshLevelGroup()
{
RefreshLevelGroupToShow();
_levelGroupScrollView.UpdateData(true);
}
private void RefreshLevelGroupToShow()
{
_showLevelGroupInfoList.Clear();
var allLevelGroup = LevelManager.Instance.GetAllLevelGroupInfo();
foreach (var levelGroupInfo in allLevelGroup)
{
if (levelGroupInfo.GroupType == _currGroupType && !levelGroupInfo.IsLock)
{
_showLevelGroupInfoList.Add(levelGroupInfo);
}
}
_showLevelGroupInfoList.Sort((a, b) => { return a.Index.CompareTo(b.Index); });
}
private void RefreshLevel()
{
RefreshLevelToShow();
_levelScrollView.UpdateData(true);
}
private void RefreshLevelToShow()
{
_showLevelInfoList.Clear();
foreach (LevelInfo levelInfo in _currChapterInfo)
{
if (!levelInfo.IsLock)
_showLevelInfoList.Add(levelInfo);
}
_showLevelInfoList.Sort((a, b) => a.Index.CompareTo(b.Index));
}
private void EnterSelectLevelGroup(LevelGroupType type)
{
_currGroupType = type;
_currPage = PageType.LevelGroup;
Refresh();
}
private void ExitSelectLevelGroup()
{
_currPage = PageType.Mode;
Refresh();
}
private void EnterSelectLevel(LevelGroupInfo levelGroupInfo)
{
_currLevelGroupInfo = levelGroupInfo;
_currPage = PageType.Level;
var defaultChapter = InitChapter();
if (defaultChapter != null)
ChangeChapter(defaultChapter);
}
private void ExitSelectLevel()
{
_currLevelGroupInfo = null;
_currEasyChapterInfo = null;
_currHardChapterInfo = null;
_currPlotChapterInfo = null;
_currChapterInfo = null;
_currSelectLevelInfo = null;
_currPage = PageType.LevelGroup;
Refresh();
}
private ChapterInfo InitChapter()
{
_currEasyChapterInfo = _currLevelGroupInfo.EasyChapter;
_currHardChapterInfo = _currLevelGroupInfo.HardChapter;
_currPlotChapterInfo = _currLevelGroupInfo.PlotChapter;
Button_Easy.interactable = IsChapterValid(_currEasyChapterInfo);
Button_Hard.interactable = IsChapterValid(_currHardChapterInfo);
Button_Plot.interactable = IsChapterValid(_currPlotChapterInfo);
var result =
IsChapterValid(_currEasyChapterInfo) ? _currEasyChapterInfo :
IsChapterValid(_currHardChapterInfo) ? _currHardChapterInfo : _currPlotChapterInfo;
return result;
}
private bool IsChapterValid(ChapterInfo chapter)
{
return chapter != null && !chapter.IsLock;
}
private async void ChangeChapter(ChapterInfo currChapterInfo)
{
if (_currChapterInfo == currChapterInfo)
return;
_currChapterInfo = currChapterInfo;
Image_Plot.gameObject.SetActive(currChapterInfo == _currPlotChapterInfo);
Image_Easy.gameObject.SetActive(currChapterInfo == _currEasyChapterInfo);
Image_Hard.gameObject.SetActive(currChapterInfo == _currHardChapterInfo);
ReturnAllStarReward();
int maxTarget = currChapterInfo.StarList[^1];
var progressLength = _starRewardsParent.rect.width;
var currStarCount = currChapterInfo.StarCount;
var currRewardIndexMax = currChapterInfo.OwnRewardMaxIndex;
for (int i = 0; i < currChapterInfo.StarList.Length; i++)
{
var target = currChapterInfo.StarList[i];
var starReward = await GetAStarReward();
var button = starReward.GetComponent<Button>();
button.onClick.RemoveAllListeners();
var index = i + 1;
if (_currChapterInfo.CanGetReward(index))
{
button.enabled = true;
button.onClick.AddListener(() => { OnClickStarReward(index); });
}
else
button.enabled = false;
_showStarReward.Add(starReward);
var targetText = starReward.transform.Find("target_green").GetComponent<TMP_Text>();
var targetWhiteText = starReward.transform.Find("target_white").GetComponent<TMP_Text>();
targetText.text = target.ToString();
targetWhiteText.text = target.ToString();
var x = ((float)target / maxTarget) * progressLength;
var rectTrans = starReward.transform as RectTransform;
rectTrans.anchoredPosition = new Vector2(x, rectTrans.anchoredPosition.y);
SetStarRewardEnable(starReward, false);
}
var ratio = (float)currStarCount / maxTarget;
Text_StarNum.text = currStarCount.ToString();
_cts?.Cancel();
_cts?.Dispose();
_cts = new CancellationTokenSource();
PlayProgressAnimation(ratio, progressLength, _cts.Token);
Refresh();
}
private void SetStarRewardEnable(GameObject starReward, bool isEnable)
{
var starRewardGreen = starReward.transform.Find("starReward_green").gameObject;
var starReward_white = starReward.transform.Find("starReward_white").gameObject;
var star_green = starReward.transform.Find("star_green").gameObject;
var star_white = starReward.transform.Find("star_white").gameObject;
var target_green = starReward.transform.Find("target_green").gameObject;
var target_white = starReward.transform.Find("target_white").gameObject;
starRewardGreen.SetActive(isEnable);
starReward_white.SetActive(!isEnable);
star_green.SetActive(isEnable);
star_white.SetActive(!isEnable);
target_green.SetActive(isEnable);
target_white.SetActive(!isEnable);
}
private async void PlayProgressAnimation(float ratio, float progressLength, CancellationToken token)
{
Image_ProcessBar.rectTransform.anchoredPosition = new Vector2(0, Image_ProcessBar.rectTransform.anchoredPosition.y);
var currMoveTime = 0f;
var rewardTList = new List<float>();
var maxStarCount = _currChapterInfo.StarList[^1];
foreach (var starCount in _currChapterInfo.StarList)
{
var t = (float)starCount / maxStarCount;
rewardTList.Add(t);
}
var currStarIndex = 0;
while (currMoveTime < ratio * _totalMoveTime)
{
currMoveTime += Time.deltaTime;
var t = currMoveTime / _totalMoveTime;
var x = Mathf.Min(progressLength * ratio, progressLength * t);
Image_ProcessBar.rectTransform.anchoredPosition =
new Vector2(x, Image_ProcessBar.rectTransform.anchoredPosition.y);
if (t >= rewardTList[0])
{
rewardTList.RemoveAt(0);
SetStarRewardEnable(_showStarReward[currStarIndex], true);
currStarIndex++;
}
var isCanceled = await UniTask.DelayFrame(1, PlayerLoopTiming.Update, token).SuppressCancellationThrow();
if (isCanceled)
return;
}
}
private async UniTask<GameObject> GetAStarReward()
{
GameObject result = null;
if (_starRewardPool.Count > 0)
{
result = _starRewardPool[^1];
_starRewardPool.RemoveAt(_starRewardPool.Count - 1);
}
else
{
var prefab = await AssetManager.Instance.LoadAssetAsync<GameObject>(STAR_REWARD_PREFAB_PATH);
if (prefab == null)
{
return null;
}
GameObject go = Instantiate(prefab, _starRewardsParent.transform);
result = go;
}
result.SetActive(true);
return result;
}
private void ReturnAllStarReward()
{
foreach (var go in _showStarReward)
{
go.SetActive(false);
_starRewardPool.Add(go);
}
_showStarReward.Clear();
}
private void ShowLevelDetail()
{
if (_currSelectLevelInfo == null)
return;
UIManager.Instance.OpenWindow(UINameConst.UI_BeforeFight, _currSelectLevelInfo.ID);
//LevelManager.Instance.TryEnterLevel(_currSelectLevelInfo.ID, CloseSelf);
}
private int GetLevelGroupCount()
{
return _showLevelGroupInfoList.Count;
}
private void OnRenderLevelGroup(int index, RectTransform item)
{
if (index >= _showLevelGroupInfoList.Count || index < 0)
{
DebugUtil.LogError($"index out of range,index:{index}");
return;
}
var levelGroupInfo = _showLevelGroupInfoList[index];
var Text_ChapterNum = item.Find("Text_ChapterNum").GetComponent<TMP_Text>();
var Text_ChapterName = item.Find("Text_ChapterName").GetComponent<TMP_Text>();
var Image_ProcessBarEasy = item.Find("UI_Easy/Image_ProcessBarEasy").GetComponent<Image>();
var Text_EasyStarNow = item.Find("UI_Easy/Text_EasyStarNow").GetComponent<TMP_Text>();
var Text_EasyStarMax = item.Find("UI_Easy/Text_EasyStarMax").GetComponent<TMP_Text>();
var Image_ProcessBarHard = item.Find("UI_Hard/Image_ProcessBarHard").GetComponent<Image>();
var Text_HardStarNow = item.Find("UI_Hard/Text_HardStarNow").GetComponent<TMP_Text>();
var Text_HardStarMax = item.Find("UI_Hard/Text_HardStarMax").GetComponent<TMP_Text>();
Text_ChapterNum.text = string.Format("{0:D2}", levelGroupInfo.Index);
Text_ChapterName.text = levelGroupInfo.Name;
var starCountEasy = levelGroupInfo.EasyChapter?.StarCount ?? 0;
var starMaxEasy = levelGroupInfo.EasyChapter?.StarMax ?? 0;
Image_ProcessBarEasy.fillAmount = (float)starCountEasy / starMaxEasy;
Text_EasyStarNow.text = starCountEasy.ToString();
Text_EasyStarMax.text = starMaxEasy.ToString();
var starCountHard = levelGroupInfo.HardChapter?.StarCount ?? 0;
var starMaxHard = levelGroupInfo.HardChapter?.StarMax ?? 0;
Image_ProcessBarHard.fillAmount = (float)starCountHard / starMaxHard;
Text_HardStarNow.text = starCountHard.ToString();
Text_HardStarMax.text = starMaxHard.ToString();
}
private void SetOnLevelGroupClick(GameObject obj)
{
BindButton(obj, () =>
{
var index = CommonUtils.GetTransformIndex(obj.transform);
if (index >= _showLevelGroupInfoList.Count || index < 0)
{
DebugUtil.LogError($"index out of range,index:{index}");
return;
}
var selectedLevelGroup = _showLevelGroupInfoList[index];
EnterSelectLevel(selectedLevelGroup);
Refresh();
});
}
private int GetLevelCount()
{
return _showLevelInfoList.Count;
}
private async void OnRenderLevelInfo(int index, RectTransform item)
{
if (index < 0 || index >= _showLevelInfoList.Count)
{
DebugUtil.LogError("index out of range,index:{0}", index);
return;
}
var levelInfo = _showLevelInfoList[index];
var Text_LevelNum = item.Find("Text_LevelNum").GetComponent<TMP_Text>();
var Text_LevelName = item.Find("Text_LevelName").GetComponent<TMP_Text>();
var Image_Star01 = item.Find("LevelStar/Image_Star01").gameObject;
var Image_Star02 = item.Find("LevelStar/Image_Star02").gameObject;
var Image_Star03 = item.Find("LevelStar/Image_Star03").gameObject;
var Image_environment = item.Find("MapLogo/Image_environment").GetComponent<Image>();
var Image_weather = item.Find("MapLogo/Image_weather").GetComponent<Image>();
var Image_daynight = item.Find("MapLogo/Image_daynight").GetComponent<Image>();
Text_LevelNum.text = $"{_currLevelGroupInfo.Index:D2}-{levelInfo.Index:D2}";
Text_LevelName.text = levelInfo.Name;
var starCount = levelInfo.StarCount;
Image_Star01.SetActive(starCount >= 1);
Image_Star02.SetActive(starCount >= 2);
Image_Star03.SetActive(starCount >= 3);
Image_environment.sprite = await CommonUtils.GetEnvironmentIcon(levelInfo.EnvironmentType);
Image_weather.sprite = await CommonUtils.GetWeatherIcon(levelInfo.WeatherType);
Image_daynight.sprite = await CommonUtils.GetDayNightIcon(levelInfo.DayNightType);
}
private void SetOnLevelClick(GameObject go)
{
BindButton(go, () =>
{
var index = CommonUtils.GetTransformIndex(go.transform);
if (index >= _showLevelInfoList.Count || index < 0)
{
DebugUtil.LogError("index out of range!,{0}", index);
}
var levelInfo = _showLevelInfoList[index];
if (levelInfo != null)
{
_currSelectLevelInfo = levelInfo;
ShowLevelDetail();
}
});
}
#region Event
private void OnClickBack()
{
switch (_currPage)
{
case PageType.Mode:
CloseSelf();
break;
case PageType.LevelGroup:
ExitSelectLevelGroup();
break;
case PageType.Level:
ExitSelectLevel();
break;
}
}
private void OnClickHome()
{
CloseSelf();
}
private void OnClickEasy()
{
if (_currEasyChapterInfo != null)
ChangeChapter(_currEasyChapterInfo);
}
private void OnClickHard()
{
if (_currHardChapterInfo != null)
ChangeChapter(_currHardChapterInfo);
}
private void OnClickPlot()
{
if (_currPlotChapterInfo != null)
ChangeChapter(_currPlotChapterInfo);
}
private void OnClickStarReward(int index)
{
LevelManager.Instance.GetStarReward(_currChapterInfo.ID, index);
}
private void OnChapterInfoChanged()
{
Refresh();
}
#endregion Event
#region override method
protected override void OnOpenWindow()
{
Refresh();
}
//invoke when open window
protected override void OnOpenWindow(object data = null)
{
Refresh();
}
//invoke when reload window
protected override void OnReloadWindow(object data = null)
{
Refresh();
}
//invoke when close window
protected override void OnCloseWindow(bool destroy = false)
{
UnRegisterSignal();
_currPage = PageType.Mode;
_cts?.Cancel();
_cts?.Dispose();
}
#endregion
}