using UnityEngine; using UnityEngine.UI; using UnityEngine.EventSystems; using System.Collections.Generic; using System.Collections; using System.IO; using DG.Tweening; public class dlcButton : MonoBehaviour, IPointerEnterHandler, IPointerExitHandler { private static readonly bool VerboseLogs = false; [Header("Inspector")] public Image dlc_profileImgae; public Text dlcName; public Text dlcID; public Text dlcProducer; public Text dlcPubliushDate; public Text dlcSongsAmount; public Image dlc_nowSelectedImageBoarder; [Header("Inspector")] public GameObject dlcDetailParent; public Text dlcDescription; [Header("Inspector")] public dlcData dlcDataSO; [Header("Inspector")] public List dlcContent = new List(); [Header("Inspector")] public string editorSearchFolder = "Assets/Resources/dlc_dlcIndex"; public string runtimeResourcesFolder = "Resources/dlc_dlcIndex"; private Button _btn; public bool Resolved { get; private set; } // Shared cache to avoid repeated Resources.LoadAll scans private static Dictionary cachedById = new Dictionary(); private static List cachedAll = new List(); private static bool cacheBuilt = false; private static bool cacheBuilding = false; // Selection management (shared across all dlcButton instances) private static List allButtons = new List(); private static int selectedIndex = -1; private const string PlayerPrefsKey = "dlc_selected_index"; private const string SelectedDlcIdPrefsKey = "dlc_selected_id"; // When true, Select() applies visual selection but does NOT persist to // PlayerPrefs. Used during restore so re-selecting (including fallback) // never overwrites the user's genuine last choice. public static bool SuppressSelectionPersist = false; private int instanceIndex = -1; private Coroutine hoverCoroutine; private void UpdateSongsAmountText() { if (dlcSongsAmount != null) { dlcSongsAmount.text = dlcContent != null ? dlcContent.Count.ToString() : "0"; } } public static void ResetSelectionState() { allButtons.Clear(); selectedIndex = -1; } public void OnPointerEnter(PointerEventData eventData) { if (hoverCoroutine != null) StopCoroutine(hoverCoroutine); hoverCoroutine = StartCoroutine(HandleHover()); } public void OnPointerExit(PointerEventData eventData) { if (hoverCoroutine != null) StopCoroutine(hoverCoroutine); HideDlcDetail(); } public void SetDlcData(dlcData so) { dlcDataSO = so; ApplyDlcData(so); } private IEnumerator HandleHover() { yield return new WaitForSecondsRealtime(0.5f); // 灏濊瘯浠庡満鏅腑鏌ユ壘 dlcDetailParent (濡傛灉鑷韩寮曠敤鐨勪负绌? if (dlcDetailParent == null) { var details = GameObject.FindObjectsByType(FindObjectsInactive.Include, FindObjectsSortMode.None); foreach (var b in details) { if (b != this && b.dlcDetailParent != null) { dlcDetailParent = b.dlcDetailParent; dlcDescription = b.dlcDescription; break; } } } if (dlcDetailParent != null) { dlcDetailParent.SetActive(true); UI_OrderedEntryAnimator.PlayFadeOnly(dlcDetailParent, 0, 0.12f, 0f, true); // 鏇存柊绠€浠嬩俊鎭? if (dlcDescription != null) { if (dlcDataSO != null) { dlcDescription.text = string.IsNullOrEmpty(dlcDataSO.dlcDescription) ? LocalizationService.Get("dlc.no_description", "暂无DLC简介信息。") : dlcDataSO.dlcDescription; } else { dlcDescription.text = LocalizationService.Get("dlc.no_description", "暂无DLC简介信息。"); } } } } private void HideDlcDetail() { if (dlcDetailParent == null) { return; } CanvasGroup group = dlcDetailParent.GetComponent(); if (group == null) { group = dlcDetailParent.AddComponent(); } group.DOKill(); group.DOFade(0f, 0.1f) .SetEase(Ease.OutQuad) .SetUpdate(true) .SetTarget(dlcDetailParent) .OnComplete(() => { if (dlcDetailParent != null) { dlcDetailParent.SetActive(false); group.alpha = 1f; } }); } void Awake() { _btn = GetComponent