Files
SoulliesOfficial 649b7a5ddc 更新
2026-05-23 08:27:50 -04:00

193 lines
5.8 KiB
C#
Raw Permalink Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
using System;
using System.Collections.Generic;
using Cielonos.MainGame.Inventory;
using Sirenix.OdinInspector;
using SLSUtilities.UI;
using TMPro;
using UnityEngine;
using UnityEngine.UI;
namespace Cielonos.MainGame.UI
{
/// <summary>
/// 机械台 UI 页面。
/// 左侧为可选装备列表Selector右侧为物品详情面板ItemDetailPanel
/// 玩家点击列表条目选中物品,点击 Confirm 确认获取。
/// </summary>
public class MechanicalTableUIPage : UIPageBase
{
[Title("Selectors")]
public GameObject selectorPrefab;
public RectTransform selectorContainer;
public List<MechanicalTableSelector> selectors = new List<MechanicalTableSelector>();
[Title("Detail Panel")]
public ItemDetailPanel itemDetailPanel;
[Title("Buttons")]
public Button confirmButton;
public Button closeButton;
private MechanicalTableSelector currentSelected;
private Action<int> onConfirmCallback;
/// <summary>当前选中的 Selector 索引,-1 表示未选中。</summary>
public int SelectedIndex => currentSelected != null ? selectors.IndexOf(currentSelected) : -1;
protected override void Start()
{
base.Start();
if (confirmButton != null)
{
confirmButton.onClick.AddListener(OnConfirmClicked);
}
if (closeButton != null)
{
closeButton.onClick.AddListener(OnCloseClicked);
}
}
/// <summary>
/// 用物品预制体列表填充选择器,并注册确认回调。
/// 每次调用会清除旧选择器并重新生成。
/// </summary>
/// <param name="itemPrefabs">物品预制体列表,每个预制体必须包含 ItemBase 组件。</param>
/// <param name="onConfirm">玩家点击 Confirm 后的回调,参数为选中的物品索引。</param>
public void SetOffers(List<GameObject> itemPrefabs, Action<int> onConfirm)
{
onConfirmCallback = onConfirm;
ClearSelectors();
if (itemPrefabs == null) return;
for (int i = 0; i < itemPrefabs.Count; i++)
{
GameObject prefab = itemPrefabs[i];
if (prefab == null) continue;
ItemBase itemComponent = prefab.GetComponent<ItemBase>();
if (itemComponent == null)
{
Debug.LogWarning($"[MechanicalTableUIPage] 预制体 '{prefab.name}' 缺少 ItemBase 组件,已跳过。");
continue;
}
MechanicalTableSelector selector = CreateSelector();
selector.Setup(itemComponent);
}
// 重置选中状态
currentSelected = null;
RefreshConfirmButton();
// 详情面板默认隐藏
if (itemDetailPanel != null)
{
itemDetailPanel.ClearPanel();
}
}
/// <summary>
/// 由 MechanicalTableSelector 调用,选中指定的选择器。
/// </summary>
public void SelectItem(MechanicalTableSelector selector)
{
if (selector == null || !selectors.Contains(selector)) return;
// 取消上一个选中
if (currentSelected != null)
{
currentSelected.SetSelected(false);
}
// 设置新选中
currentSelected = selector;
currentSelected.SetSelected(true);
// 更新详情面板
if (itemDetailPanel != null)
{
itemDetailPanel.SetItem(currentSelected.item);
}
// 启用确认按钮
RefreshConfirmButton();
}
protected override void OnPageOpened()
{
RefreshConfirmButton();
}
protected override void OnPageClosed()
{
currentSelected = null;
onConfirmCallback = null;
}
private void OnConfirmClicked()
{
if (currentSelected == null) return;
int index = SelectedIndex;
if (index < 0) return;
// 先缓存回调,因为 Close() 会清除引用
Action<int> callback = onConfirmCallback;
Close();
callback?.Invoke(index);
}
private void OnCloseClicked()
{
Close();
}
private MechanicalTableSelector CreateSelector()
{
if (selectorPrefab == null || selectorContainer == null)
{
Debug.LogError("[MechanicalTableUIPage] selectorPrefab 或 selectorContainer 未配置。");
return null;
}
GameObject obj = Instantiate(selectorPrefab, selectorContainer);
MechanicalTableSelector selector = obj.GetComponent<MechanicalTableSelector>();
if (selector == null)
{
Debug.LogError("[MechanicalTableUIPage] selectorPrefab 缺少 MechanicalTableSelector 组件。");
Destroy(obj);
return null;
}
selectors.Add(selector);
return selector;
}
private void ClearSelectors()
{
foreach (MechanicalTableSelector selector in selectors)
{
if (selector != null)
{
Destroy(selector.gameObject);
}
}
selectors.Clear();
currentSelected = null;
}
private void RefreshConfirmButton()
{
if (confirmButton != null)
{
confirmButton.interactable = currentSelected != null;
}
}
}
}