839 lines
30 KiB
C#
839 lines
30 KiB
C#
using UnityEngine;
|
|
using UnityEngine.UI;
|
|
using System.Collections.Generic;
|
|
using DG.Tweening;
|
|
using UnityEngine.EventSystems;
|
|
|
|
public class notebookController : MonoBehaviour
|
|
{
|
|
private const string NotebookCategoryPrefsKey = "notebook.selected_category";
|
|
private const string NotebookFatherPrefsKey = "notebook.selected_father_id";
|
|
private const string NotebookSonPrefsKey = "notebook.selected_son_id";
|
|
|
|
[Header("select father types")]
|
|
public Toggle all_content_beforeAnything_toggle;
|
|
public Toggle idols_toggle;
|
|
public Toggle enemies_toggle;
|
|
public Toggle organizations_toggle;
|
|
public Toggle areas_toggle;
|
|
public Toggle terminologies_toggle;
|
|
public Toggle Logs_toggle;
|
|
public ToggleGroup categoryToggleGroup;
|
|
|
|
[Header("quit")]
|
|
public Button quit_button;
|
|
|
|
[Header("prefabs")]
|
|
public GameObject fatherItem_prefab;
|
|
public GameObject svContent;
|
|
|
|
[Header("paths")]
|
|
[SerializeField] private string editor_SO_path;
|
|
[SerializeField] private string runtime_SO_path;
|
|
|
|
[Header("Details Displaying")]
|
|
public Image detailsImage;
|
|
public Text passage_title;
|
|
public Text passage_text;
|
|
[SerializeField] float panel_Enter_Time = 0.35f;
|
|
[SerializeField] float panel_Exit_Time = 0.25f;
|
|
[SerializeField] float panel_Enter_Scale_From = 0.92f;
|
|
[SerializeField] float panel_Exit_Scale_To = 0.9f;
|
|
[SerializeField] Ease panel_Enter_Ease = Ease.OutCubic;
|
|
[SerializeField] Ease panel_Exit_Ease = Ease.InCubic;
|
|
|
|
private readonly List<notebook_faterType> cachedItems = new List<notebook_faterType>();
|
|
private Toggle[] categoryToggles;
|
|
private readonly Dictionary<RectTransform, Vector2> fatherBaseAnchors = new Dictionary<RectTransform, Vector2>();
|
|
private readonly Dictionary<Toggle, int> toggleInvokeFrame = new Dictionary<Toggle, int>();
|
|
private readonly Dictionary<fatherItemPrefab, LayoutElement> fatherSpacers = new Dictionary<fatherItemPrefab, LayoutElement>();
|
|
private readonly Dictionary<fatherItemPrefab, int> fatherAnimTokens = new Dictionary<fatherItemPrefab, int>();
|
|
private bool initialized = false;
|
|
private const float SonOffsetBase = 5f;
|
|
private const float SonOffsetPerItem = 110f;
|
|
private const float SonTweenDuration = 0.5f;
|
|
private const float SonFadeDuration = 0.25f;
|
|
|
|
private void Start()
|
|
{
|
|
Initialize();
|
|
RestoreNotebookSelectionOrDefault();
|
|
}
|
|
|
|
private void OnEnable()
|
|
{
|
|
Initialize();
|
|
RestoreNotebookSelectionOrDefault();
|
|
PlayEnterAnim();
|
|
}
|
|
|
|
private void Initialize()
|
|
{
|
|
StoreOwnershipLedger.EnsureInstance().InitializeIfNeeded();
|
|
LoadAllData();
|
|
if (initialized) return;
|
|
initialized = true;
|
|
categoryToggles = new[]
|
|
{
|
|
all_content_beforeAnything_toggle,
|
|
idols_toggle,
|
|
enemies_toggle,
|
|
organizations_toggle,
|
|
areas_toggle,
|
|
terminologies_toggle,
|
|
Logs_toggle
|
|
};
|
|
categoryToggleGroup = ResolveCategoryToggleGroup();
|
|
if (categoryToggleGroup != null)
|
|
categoryToggleGroup.allowSwitchOff = true;
|
|
if (categoryToggles != null)
|
|
{
|
|
for (int i = 0; i < categoryToggles.Length; i++)
|
|
{
|
|
var t = categoryToggles[i];
|
|
if (t == null) continue;
|
|
t.group = categoryToggleGroup;
|
|
}
|
|
}
|
|
BindToggle(all_content_beforeAnything_toggle, () => Refresh(notebook_faterType.notebook_fatherType.content));
|
|
BindToggle(idols_toggle, () => Refresh(notebook_faterType.notebook_fatherType.idols));
|
|
BindToggle(enemies_toggle, () => Refresh(notebook_faterType.notebook_fatherType.enemies));
|
|
BindToggle(organizations_toggle, () => Refresh(notebook_faterType.notebook_fatherType.organizations));
|
|
BindToggle(areas_toggle, () => Refresh(notebook_faterType.notebook_fatherType.areas));
|
|
BindToggle(terminologies_toggle, () => Refresh(notebook_faterType.notebook_fatherType.terminologies));
|
|
BindToggle(Logs_toggle, () => Refresh(notebook_faterType.notebook_fatherType.Logs));
|
|
if (quit_button != null)
|
|
{
|
|
quit_button.onClick.RemoveAllListeners();
|
|
quit_button.onClick.AddListener(CloseSelf);
|
|
}
|
|
}
|
|
|
|
private void BindToggle(Toggle toggle, System.Action onSelected)
|
|
{
|
|
if (toggle == null) return;
|
|
toggle.onValueChanged.RemoveAllListeners();
|
|
toggle.onValueChanged.AddListener(isOn =>
|
|
{
|
|
if (isOn) InvokeToggleAction(toggle, onSelected);
|
|
});
|
|
var relay = toggle.GetComponent<ToggleClickRelay>();
|
|
if (relay == null) relay = toggle.gameObject.AddComponent<ToggleClickRelay>();
|
|
relay.onClick = () =>
|
|
{
|
|
if (toggle != null && toggle.isOn) InvokeToggleAction(toggle, onSelected);
|
|
};
|
|
}
|
|
|
|
private ToggleGroup ResolveCategoryToggleGroup()
|
|
{
|
|
if (categoryToggleGroup != null) return categoryToggleGroup;
|
|
Toggle first = null;
|
|
if (categoryToggles != null)
|
|
{
|
|
for (int i = 0; i < categoryToggles.Length; i++)
|
|
{
|
|
if (categoryToggles[i] != null) { first = categoryToggles[i]; break; }
|
|
}
|
|
}
|
|
if (first == null) return null;
|
|
var parentGroup = first.GetComponentInParent<ToggleGroup>();
|
|
var contentGroup = svContent != null ? svContent.GetComponent<ToggleGroup>() : null;
|
|
if (parentGroup != null && parentGroup != contentGroup) return parentGroup;
|
|
var parent = first.transform.parent;
|
|
if (parent == null) return null;
|
|
var created = parent.GetComponent<ToggleGroup>();
|
|
if (created == null) created = parent.gameObject.AddComponent<ToggleGroup>();
|
|
return created;
|
|
}
|
|
|
|
private void LoadAllData()
|
|
{
|
|
cachedItems.Clear();
|
|
var set = new HashSet<notebook_faterType>();
|
|
#if UNITY_EDITOR
|
|
if (!string.IsNullOrEmpty(editor_SO_path))
|
|
{
|
|
var guids = UnityEditor.AssetDatabase.FindAssets("t:notebook_faterType", new[] { editor_SO_path });
|
|
for (int i = 0; i < guids.Length; i++)
|
|
{
|
|
var path = UnityEditor.AssetDatabase.GUIDToAssetPath(guids[i]);
|
|
var so = UnityEditor.AssetDatabase.LoadAssetAtPath<notebook_faterType>(path);
|
|
if (so == null) continue;
|
|
if (set.Add(so)) cachedItems.Add(so);
|
|
}
|
|
}
|
|
#endif
|
|
if (!string.IsNullOrEmpty(runtime_SO_path))
|
|
{
|
|
var resources = Resources.LoadAll<notebook_faterType>(runtime_SO_path);
|
|
for (int i = 0; i < resources.Length; i++)
|
|
{
|
|
var so = resources[i];
|
|
if (so == null) continue;
|
|
if (set.Add(so)) cachedItems.Add(so);
|
|
}
|
|
}
|
|
}
|
|
|
|
private void Refresh(notebook_faterType.notebook_fatherType? type)
|
|
{
|
|
if (fatherItem_prefab == null || svContent == null) return;
|
|
notebook_faterType.notebook_fatherType effectiveType = type ?? LoadSavedCategory();
|
|
SaveSelectedCategory(effectiveType);
|
|
ClearContent();
|
|
var fatherGroup = svContent.GetComponent<ToggleGroup>();
|
|
if (fatherGroup == categoryToggleGroup) fatherGroup = null;
|
|
Toggle firstFatherToggle = null;
|
|
fatherItemPrefab firstFatherComp = null;
|
|
notebook_faterType firstFatherData = null;
|
|
Toggle restoredFatherToggle = null;
|
|
fatherItemPrefab restoredFatherComp = null;
|
|
notebook_faterType restoredFatherData = null;
|
|
int savedFatherId = LoadSavedFatherId();
|
|
for (int i = 0; i < cachedItems.Count; i++)
|
|
{
|
|
var so = cachedItems[i];
|
|
if (so == null) continue;
|
|
if (!so.isUnlocked) continue;
|
|
if (so.fatherType != effectiveType) continue;
|
|
var obj = Instantiate(fatherItem_prefab, svContent.transform);
|
|
var comp = obj.GetComponent<fatherItemPrefab>();
|
|
if (comp == null) continue;
|
|
if (comp.father_name != null) comp.father_name.text = so.class_name;
|
|
comp.SetFatherImage(so.class_image);
|
|
if (comp.father_description != null) comp.father_description.text = so.class_description;
|
|
SetupFatherItem(comp, so, fatherGroup);
|
|
UI_OrderedEntryAnimator.PlaySingle(obj, i, 0.18f, 0.012f, -14f, 0.97f, true);
|
|
if (firstFatherToggle == null)
|
|
{
|
|
firstFatherToggle = ResolveFatherToggle(comp);
|
|
firstFatherComp = comp;
|
|
firstFatherData = so;
|
|
}
|
|
if (restoredFatherToggle == null && so.class_id == savedFatherId)
|
|
{
|
|
restoredFatherToggle = ResolveFatherToggle(comp);
|
|
restoredFatherComp = comp;
|
|
restoredFatherData = so;
|
|
}
|
|
}
|
|
CacheFatherBasePositions();
|
|
AutoSelectFather(
|
|
restoredFatherToggle != null ? restoredFatherToggle : firstFatherToggle,
|
|
restoredFatherComp != null ? restoredFatherComp : firstFatherComp,
|
|
restoredFatherData != null ? restoredFatherData : firstFatherData);
|
|
}
|
|
|
|
private void SetupFatherItem(fatherItemPrefab comp, notebook_faterType so, ToggleGroup fatherGroup)
|
|
{
|
|
if (comp == null) return;
|
|
ClearSonContainer(comp);
|
|
if (comp.son_obj != null) comp.son_obj.SetActive(false);
|
|
if (comp.son_prefab_toPut != null) comp.son_prefab_toPut.SetActive(false);
|
|
Toggle toggle = ResolveFatherToggle(comp);
|
|
if (toggle == null) return;
|
|
if (fatherGroup != null) toggle.group = fatherGroup;
|
|
toggle.onValueChanged.RemoveAllListeners();
|
|
toggle.onValueChanged.AddListener(isOn =>
|
|
{
|
|
if (isOn)
|
|
{
|
|
SaveSelectedFather(so.class_id);
|
|
}
|
|
ApplySonState(comp, so, isOn);
|
|
});
|
|
ApplySonState(comp, so, toggle.isOn);
|
|
}
|
|
|
|
private void ApplySonState(fatherItemPrefab comp, notebook_faterType so, bool isOn)
|
|
{
|
|
if (comp == null) return;
|
|
int token = NextAnimToken(comp);
|
|
if (isOn)
|
|
{
|
|
ClearSonDetails();
|
|
EnsureSonsLoaded(comp, so);
|
|
UpdateFatherSpacer(comp, so, true, token);
|
|
FadeSonContainer(comp, true, token, null);
|
|
}
|
|
else
|
|
{
|
|
FadeSonContainer(comp, false, token, () => ClearSonContainer(comp));
|
|
UpdateFatherSpacer(comp, so, false, token);
|
|
}
|
|
}
|
|
|
|
private void ClearSonDetails()
|
|
{
|
|
if (detailsImage != null)
|
|
{
|
|
detailsImage.sprite = null;
|
|
detailsImage.enabled = false;
|
|
}
|
|
if (passage_title != null)
|
|
{
|
|
passage_title.text = string.Empty;
|
|
}
|
|
if (passage_text != null)
|
|
{
|
|
passage_text.text = string.Empty;
|
|
}
|
|
}
|
|
|
|
private void EnsureSonsLoaded(fatherItemPrefab comp, notebook_faterType so)
|
|
{
|
|
if (comp == null || so == null) return;
|
|
if (comp.son_prefab == null || comp.son_prefab_toPut == null) return;
|
|
if (so.sonList == null || so.sonList.Count == 0) return;
|
|
ClearSonContainer(comp);
|
|
var parent = comp.son_prefab_toPut.transform;
|
|
var prefab = comp.son_prefab;
|
|
ToggleGroup sonGroup = null;
|
|
if (comp.son_prefab_toPut != null) sonGroup = comp.son_prefab_toPut.GetComponent<ToggleGroup>();
|
|
if (sonGroup == null && comp.son_obj != null) sonGroup = comp.son_obj.GetComponent<ToggleGroup>();
|
|
Dictionary<Toggle, int> sonIdByToggle = new Dictionary<Toggle, int>();
|
|
Dictionary<int, notebook_faterType.notebook_sonClass> sonById = new Dictionary<int, notebook_faterType.notebook_sonClass>();
|
|
Toggle firstSonToggle = null;
|
|
notebook_faterType.notebook_sonClass firstUnlockedSon = null;
|
|
bool appliedSelectedSon = false;
|
|
for (int i = 0; i < so.sonList.Count; i++)
|
|
{
|
|
var son = so.sonList[i];
|
|
if (son == null) continue;
|
|
if (!son.son_isUnlocked) continue;
|
|
var obj = Instantiate(prefab, parent);
|
|
UI_OrderedEntryAnimator.PlaySingle(obj, i, 0.16f, 0.018f, -10f, 0.97f, true);
|
|
var sonComp = obj.GetComponent<sonItemPrefab>();
|
|
Toggle sonToggle = null;
|
|
if (sonComp != null && sonComp.sonToggle != null) sonToggle = sonComp.sonToggle;
|
|
if (sonToggle == null) sonToggle = obj.GetComponent<Toggle>();
|
|
if (sonToggle == null) sonToggle = obj.GetComponentInChildren<Toggle>(true);
|
|
if (sonGroup != null && sonToggle != null) sonToggle.group = sonGroup;
|
|
if (firstSonToggle == null && sonToggle != null)
|
|
{
|
|
firstSonToggle = sonToggle;
|
|
firstUnlockedSon = son;
|
|
}
|
|
if (sonToggle != null)
|
|
{
|
|
sonIdByToggle[sonToggle] = son.son_id;
|
|
}
|
|
if (!sonById.ContainsKey(son.son_id))
|
|
{
|
|
sonById.Add(son.son_id, son);
|
|
}
|
|
if (sonComp == null) continue;
|
|
if (sonComp.sonName != null) sonComp.sonName.text = son.son_name;
|
|
if (sonComp.sonDescription != null) sonComp.sonDescription.text = son.son_description;
|
|
sonComp.SetSonImage(son.son_image);
|
|
if (sonToggle != null)
|
|
{
|
|
sonToggle.onValueChanged.RemoveAllListeners();
|
|
sonToggle.onValueChanged.AddListener(isOn =>
|
|
{
|
|
if (isOn)
|
|
{
|
|
ApplySonDetails(so, son);
|
|
}
|
|
});
|
|
if (sonToggle.isOn)
|
|
{
|
|
ApplySonDetails(so, son);
|
|
appliedSelectedSon = true;
|
|
}
|
|
}
|
|
}
|
|
|
|
if (!appliedSelectedSon)
|
|
{
|
|
int savedSonId = LoadSavedSonId();
|
|
Toggle restoredSonToggle = null;
|
|
notebook_faterType.notebook_sonClass restoredSon = null;
|
|
if (savedSonId > 0)
|
|
{
|
|
foreach (KeyValuePair<Toggle, int> pair in sonIdByToggle)
|
|
{
|
|
if (pair.Key == null)
|
|
{
|
|
continue;
|
|
}
|
|
|
|
if (pair.Value == savedSonId)
|
|
{
|
|
restoredSonToggle = pair.Key;
|
|
sonById.TryGetValue(savedSonId, out restoredSon);
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
|
|
if (restoredSonToggle != null && restoredSon != null)
|
|
{
|
|
SelectSon(restoredSonToggle, so, restoredSon);
|
|
}
|
|
else if (firstSonToggle != null && firstUnlockedSon != null)
|
|
{
|
|
SelectSon(firstSonToggle, so, firstUnlockedSon);
|
|
}
|
|
else if (firstUnlockedSon != null)
|
|
{
|
|
ApplySonDetails(so, firstUnlockedSon);
|
|
}
|
|
}
|
|
}
|
|
|
|
private void ApplySonDetails(notebook_faterType father, notebook_faterType.notebook_sonClass son)
|
|
{
|
|
if (son == null) return;
|
|
if (father != null)
|
|
{
|
|
SaveSelectedFather(father.class_id);
|
|
}
|
|
SaveSelectedSon(son.son_id);
|
|
if (detailsImage != null)
|
|
{
|
|
detailsImage.sprite = son.son_detailsImage;
|
|
detailsImage.enabled = son.son_detailsImage != null;
|
|
}
|
|
if (passage_title != null) passage_title.text = son.son_title;
|
|
if (passage_text != null) passage_text.text = son.son_passage;
|
|
PlayDetailsRefresh();
|
|
}
|
|
|
|
private void InvokeToggleAction(Toggle toggle, System.Action onSelected)
|
|
{
|
|
if (toggle == null || onSelected == null) return;
|
|
int frame = Time.frameCount;
|
|
if (toggleInvokeFrame.TryGetValue(toggle, out var lastFrame) && lastFrame == frame) return;
|
|
toggleInvokeFrame[toggle] = frame;
|
|
onSelected.Invoke();
|
|
}
|
|
|
|
private class ToggleClickRelay : MonoBehaviour, IPointerClickHandler
|
|
{
|
|
public System.Action onClick;
|
|
public void OnPointerClick(PointerEventData eventData)
|
|
{
|
|
onClick?.Invoke();
|
|
}
|
|
}
|
|
|
|
private void CacheFatherBasePositions()
|
|
{
|
|
if (svContent == null) return;
|
|
var parent = svContent.transform as RectTransform;
|
|
if (parent == null) return;
|
|
LayoutRebuilder.ForceRebuildLayoutImmediate(parent);
|
|
fatherBaseAnchors.Clear();
|
|
for (int i = 0; i < parent.childCount; i++)
|
|
{
|
|
var child = parent.GetChild(i) as RectTransform;
|
|
if (child == null) continue;
|
|
fatherBaseAnchors[child] = child.anchoredPosition;
|
|
}
|
|
}
|
|
|
|
private void UpdateFatherSpacer(fatherItemPrefab comp, notebook_faterType so, bool expand, int token)
|
|
{
|
|
if (svContent == null || comp == null) return;
|
|
var parent = svContent.transform as RectTransform;
|
|
if (parent == null) return;
|
|
int count = expand ? GetUnlockedSonCount(so) : 0;
|
|
float targetHeight = count > 0 ? (SonOffsetBase + (SonOffsetPerItem * count)) : 0f;
|
|
if (!fatherSpacers.TryGetValue(comp, out var spacer) || spacer == null)
|
|
{
|
|
if (!expand) return;
|
|
var spacerObj = new GameObject("NotebookSpacer", typeof(RectTransform), typeof(LayoutElement));
|
|
spacerObj.transform.SetParent(parent, false);
|
|
spacer = spacerObj.GetComponent<LayoutElement>();
|
|
spacer.minHeight = 0f;
|
|
spacer.flexibleHeight = 0f;
|
|
spacer.preferredHeight = 0f;
|
|
var spacerRectInit = spacerObj.transform as RectTransform;
|
|
if (spacerRectInit != null)
|
|
{
|
|
spacerRectInit.pivot = new Vector2(0.5f, 1f);
|
|
spacerRectInit.sizeDelta = new Vector2(spacerRectInit.sizeDelta.x, 0f);
|
|
}
|
|
fatherSpacers[comp] = spacer;
|
|
}
|
|
var spacerRect = spacer.transform as RectTransform;
|
|
int targetIndex = comp.transform.GetSiblingIndex() + 1;
|
|
if (spacerRect != null && spacerRect.GetSiblingIndex() != targetIndex)
|
|
spacerRect.SetSiblingIndex(targetIndex);
|
|
DOTween.Kill(spacer, false);
|
|
if (expand)
|
|
{
|
|
DOTween.To(() => spacer.preferredHeight, h =>
|
|
{
|
|
spacer.preferredHeight = h;
|
|
spacer.minHeight = h;
|
|
if (spacerRect != null)
|
|
spacerRect.sizeDelta = new Vector2(spacerRect.sizeDelta.x, h);
|
|
}, targetHeight, SonTweenDuration)
|
|
.SetTarget(spacer)
|
|
.SetEase(Ease.OutCubic)
|
|
.OnUpdate(() => LayoutRebuilder.ForceRebuildLayoutImmediate(parent));
|
|
}
|
|
else
|
|
{
|
|
DOTween.To(() => spacer.preferredHeight, h =>
|
|
{
|
|
spacer.preferredHeight = h;
|
|
spacer.minHeight = h;
|
|
if (spacerRect != null)
|
|
spacerRect.sizeDelta = new Vector2(spacerRect.sizeDelta.x, h);
|
|
}, 0f, SonTweenDuration)
|
|
.SetTarget(spacer)
|
|
.SetEase(Ease.OutCubic)
|
|
.OnUpdate(() => LayoutRebuilder.ForceRebuildLayoutImmediate(parent))
|
|
.OnComplete(() =>
|
|
{
|
|
if (!IsTokenCurrent(comp, token)) return;
|
|
if (spacer != null)
|
|
{
|
|
fatherSpacers.Remove(comp);
|
|
if (Application.isPlaying) Destroy(spacer.gameObject);
|
|
else DestroyImmediate(spacer.gameObject);
|
|
}
|
|
});
|
|
}
|
|
LayoutRebuilder.ForceRebuildLayoutImmediate(parent);
|
|
}
|
|
|
|
private void FadeSonContainer(fatherItemPrefab comp, bool show, int token, System.Action onComplete)
|
|
{
|
|
var rect = GetSonRect(comp);
|
|
if (rect == null)
|
|
{
|
|
onComplete?.Invoke();
|
|
return;
|
|
}
|
|
rect.DOKill();
|
|
if (show)
|
|
{
|
|
rect.gameObject.SetActive(true);
|
|
var cg = rect.GetComponent<CanvasGroup>();
|
|
if (cg == null) cg = rect.gameObject.AddComponent<CanvasGroup>();
|
|
cg.alpha = 0f;
|
|
cg.DOKill();
|
|
cg.DOFade(1f, SonFadeDuration).SetTarget(cg).SetEase(Ease.OutCubic);
|
|
}
|
|
else
|
|
{
|
|
var cg = rect.GetComponent<CanvasGroup>();
|
|
if (cg == null)
|
|
{
|
|
rect.gameObject.SetActive(false);
|
|
onComplete?.Invoke();
|
|
return;
|
|
}
|
|
cg.DOKill();
|
|
cg.DOFade(0f, SonFadeDuration).SetTarget(cg).SetEase(Ease.OutCubic).OnComplete(() =>
|
|
{
|
|
if (!IsTokenCurrent(comp, token)) return;
|
|
rect.gameObject.SetActive(false);
|
|
onComplete?.Invoke();
|
|
});
|
|
}
|
|
}
|
|
|
|
private int NextAnimToken(fatherItemPrefab comp)
|
|
{
|
|
if (comp == null) return 0;
|
|
if (!fatherAnimTokens.TryGetValue(comp, out var token)) token = 0;
|
|
token++;
|
|
fatherAnimTokens[comp] = token;
|
|
return token;
|
|
}
|
|
|
|
private bool IsTokenCurrent(fatherItemPrefab comp, int token)
|
|
{
|
|
if (comp == null) return false;
|
|
return fatherAnimTokens.TryGetValue(comp, out var current) && current == token;
|
|
}
|
|
|
|
private RectTransform GetSonRect(fatherItemPrefab comp)
|
|
{
|
|
if (comp == null) return null;
|
|
if (comp.son_prefab_toPut != null) return comp.son_prefab_toPut.transform as RectTransform;
|
|
if (comp.son_obj != null) return comp.son_obj.transform as RectTransform;
|
|
return null;
|
|
}
|
|
|
|
private int GetUnlockedSonCount(notebook_faterType so)
|
|
{
|
|
if (so == null || so.sonList == null) return 0;
|
|
int count = 0;
|
|
for (int i = 0; i < so.sonList.Count; i++)
|
|
{
|
|
var son = so.sonList[i];
|
|
if (son == null) continue;
|
|
if (!son.son_isUnlocked) continue;
|
|
count++;
|
|
}
|
|
return count;
|
|
}
|
|
|
|
private void PlayEnterAnim()
|
|
{
|
|
var rect = transform as RectTransform;
|
|
if (rect == null) rect = GetComponent<RectTransform>();
|
|
if (rect == null) return;
|
|
rect.DOKill();
|
|
var cg = GetComponent<CanvasGroup>();
|
|
if (cg == null) cg = gameObject.AddComponent<CanvasGroup>();
|
|
cg.DOKill();
|
|
rect.localScale = Vector3.one * panel_Enter_Scale_From;
|
|
cg.alpha = 0f;
|
|
rect.DOScale(Vector3.one, panel_Enter_Time).SetEase(panel_Enter_Ease);
|
|
cg.DOFade(1f, panel_Enter_Time).SetEase(panel_Enter_Ease);
|
|
}
|
|
|
|
private void CloseSelf()
|
|
{
|
|
var rect = transform as RectTransform;
|
|
if (rect == null) rect = GetComponent<RectTransform>();
|
|
if (rect == null)
|
|
{
|
|
Destroy(gameObject);
|
|
return;
|
|
}
|
|
rect.DOKill();
|
|
var cg = GetComponent<CanvasGroup>();
|
|
if (cg == null) cg = gameObject.AddComponent<CanvasGroup>();
|
|
cg.DOKill();
|
|
Sequence seq = DOTween.Sequence();
|
|
seq.Join(rect.DOScale(Vector3.one * panel_Exit_Scale_To, panel_Exit_Time).SetEase(panel_Exit_Ease));
|
|
seq.Join(cg.DOFade(0f, panel_Exit_Time).SetEase(panel_Exit_Ease));
|
|
seq.OnComplete(() =>
|
|
{
|
|
if (this != null) Destroy(gameObject);
|
|
});
|
|
}
|
|
|
|
private void ClearSonContainer(fatherItemPrefab comp)
|
|
{
|
|
if (comp == null || comp.son_prefab_toPut == null) return;
|
|
var parent = comp.son_prefab_toPut.transform;
|
|
var rect = parent as RectTransform;
|
|
if (rect != null) rect.DOKill();
|
|
for (int i = parent.childCount - 1; i >= 0; i--)
|
|
{
|
|
var child = parent.GetChild(i);
|
|
if (child == null) continue;
|
|
if (Application.isPlaying) Destroy(child.gameObject);
|
|
else DestroyImmediate(child.gameObject);
|
|
}
|
|
}
|
|
|
|
private void ClearContent()
|
|
{
|
|
var parent = svContent.transform;
|
|
for (int i = parent.childCount - 1; i >= 0; i--)
|
|
{
|
|
var child = parent.GetChild(i);
|
|
if (child == null) continue;
|
|
if (Application.isPlaying) Destroy(child.gameObject);
|
|
else DestroyImmediate(child.gameObject);
|
|
}
|
|
fatherBaseAnchors.Clear();
|
|
fatherSpacers.Clear();
|
|
}
|
|
|
|
private Toggle ResolveFatherToggle(fatherItemPrefab comp)
|
|
{
|
|
if (comp == null) return null;
|
|
Toggle toggle = null;
|
|
if (comp.father_obj != null) toggle = comp.father_obj.GetComponent<Toggle>();
|
|
if (toggle == null) toggle = comp.GetComponent<Toggle>();
|
|
if (toggle == null) toggle = comp.GetComponentInChildren<Toggle>(true);
|
|
if (toggle == null) toggle = comp.GetComponentInParent<Toggle>();
|
|
return toggle;
|
|
}
|
|
|
|
private void AutoSelectFather(Toggle targetFatherToggle, fatherItemPrefab targetFatherComp, notebook_faterType targetFatherData)
|
|
{
|
|
if (targetFatherToggle == null || targetFatherComp == null || targetFatherData == null)
|
|
{
|
|
ClearSonDetails();
|
|
return;
|
|
}
|
|
|
|
targetFatherToggle.SetIsOnWithoutNotify(true);
|
|
SaveSelectedFather(targetFatherData.class_id);
|
|
ApplySonState(targetFatherComp, targetFatherData, true);
|
|
}
|
|
|
|
private void RestoreNotebookSelectionOrDefault()
|
|
{
|
|
notebook_faterType.notebook_fatherType savedCategory = ResolveInitialCategory();
|
|
SaveSelectedCategory(savedCategory);
|
|
Toggle targetToggle = GetCategoryToggle(savedCategory);
|
|
if (targetToggle != null)
|
|
{
|
|
SetCategorySelectionWithoutNotify(savedCategory);
|
|
Refresh(savedCategory);
|
|
return;
|
|
}
|
|
|
|
if (all_content_beforeAnything_toggle != null)
|
|
{
|
|
SetCategorySelectionWithoutNotify(notebook_faterType.notebook_fatherType.content);
|
|
Refresh(notebook_faterType.notebook_fatherType.content);
|
|
return;
|
|
}
|
|
|
|
Refresh(notebook_faterType.notebook_fatherType.content);
|
|
}
|
|
|
|
private notebook_faterType.notebook_fatherType ResolveInitialCategory()
|
|
{
|
|
notebook_faterType.notebook_fatherType savedCategory = LoadSavedCategory();
|
|
if (HasVisibleFatherForCategory(savedCategory))
|
|
{
|
|
return savedCategory;
|
|
}
|
|
|
|
return notebook_faterType.notebook_fatherType.content;
|
|
}
|
|
|
|
private bool HasVisibleFatherForCategory(notebook_faterType.notebook_fatherType category)
|
|
{
|
|
for (int i = 0; i < cachedItems.Count; i++)
|
|
{
|
|
notebook_faterType item = cachedItems[i];
|
|
if (item == null || !item.isUnlocked)
|
|
{
|
|
continue;
|
|
}
|
|
|
|
if (item.fatherType == category)
|
|
{
|
|
return true;
|
|
}
|
|
}
|
|
|
|
return false;
|
|
}
|
|
|
|
private Toggle GetCategoryToggle(notebook_faterType.notebook_fatherType category)
|
|
{
|
|
switch (category)
|
|
{
|
|
case notebook_faterType.notebook_fatherType.content:
|
|
return all_content_beforeAnything_toggle;
|
|
case notebook_faterType.notebook_fatherType.idols:
|
|
return idols_toggle;
|
|
case notebook_faterType.notebook_fatherType.enemies:
|
|
return enemies_toggle;
|
|
case notebook_faterType.notebook_fatherType.organizations:
|
|
return organizations_toggle;
|
|
case notebook_faterType.notebook_fatherType.areas:
|
|
return areas_toggle;
|
|
case notebook_faterType.notebook_fatherType.terminologies:
|
|
return terminologies_toggle;
|
|
case notebook_faterType.notebook_fatherType.Logs:
|
|
return Logs_toggle;
|
|
default:
|
|
return all_content_beforeAnything_toggle;
|
|
}
|
|
}
|
|
|
|
private void SetCategorySelectionWithoutNotify(notebook_faterType.notebook_fatherType category)
|
|
{
|
|
if (categoryToggles == null)
|
|
{
|
|
return;
|
|
}
|
|
|
|
for (int i = 0; i < categoryToggles.Length; i++)
|
|
{
|
|
Toggle toggle = categoryToggles[i];
|
|
if (toggle == null)
|
|
{
|
|
continue;
|
|
}
|
|
|
|
bool shouldBeOn = toggle == GetCategoryToggle(category);
|
|
toggle.SetIsOnWithoutNotify(shouldBeOn);
|
|
}
|
|
}
|
|
|
|
private void SaveSelectedCategory(notebook_faterType.notebook_fatherType category)
|
|
{
|
|
PlayerPrefs.SetInt(NotebookCategoryPrefsKey, (int)category);
|
|
PlayerPrefs.Save();
|
|
}
|
|
|
|
private notebook_faterType.notebook_fatherType LoadSavedCategory()
|
|
{
|
|
int defaultValue = (int)notebook_faterType.notebook_fatherType.content;
|
|
int raw = PlayerPrefs.GetInt(NotebookCategoryPrefsKey, defaultValue);
|
|
if (!System.Enum.IsDefined(typeof(notebook_faterType.notebook_fatherType), raw))
|
|
{
|
|
raw = defaultValue;
|
|
}
|
|
|
|
notebook_faterType.notebook_fatherType category = (notebook_faterType.notebook_fatherType)raw;
|
|
if (category == notebook_faterType.notebook_fatherType.none)
|
|
{
|
|
category = notebook_faterType.notebook_fatherType.content;
|
|
}
|
|
|
|
return category;
|
|
}
|
|
|
|
private void SaveSelectedFather(int fatherId)
|
|
{
|
|
if (fatherId <= 0)
|
|
{
|
|
return;
|
|
}
|
|
|
|
PlayerPrefs.SetInt(NotebookFatherPrefsKey, fatherId);
|
|
PlayerPrefs.Save();
|
|
}
|
|
|
|
private int LoadSavedFatherId()
|
|
{
|
|
return PlayerPrefs.GetInt(NotebookFatherPrefsKey, -1);
|
|
}
|
|
|
|
private void SaveSelectedSon(int sonId)
|
|
{
|
|
if (sonId <= 0)
|
|
{
|
|
return;
|
|
}
|
|
|
|
PlayerPrefs.SetInt(NotebookSonPrefsKey, sonId);
|
|
PlayerPrefs.Save();
|
|
}
|
|
|
|
private int LoadSavedSonId()
|
|
{
|
|
return PlayerPrefs.GetInt(NotebookSonPrefsKey, -1);
|
|
}
|
|
|
|
private void SelectSon(Toggle toggle, notebook_faterType father, notebook_faterType.notebook_sonClass son)
|
|
{
|
|
if (toggle != null)
|
|
{
|
|
toggle.SetIsOnWithoutNotify(true);
|
|
}
|
|
|
|
ApplySonDetails(father, son);
|
|
}
|
|
|
|
private void PlayDetailsRefresh()
|
|
{
|
|
GameObject target = null;
|
|
if (detailsImage != null) target = detailsImage.gameObject;
|
|
if (target == null && passage_title != null) target = passage_title.gameObject;
|
|
if (target == null && passage_text != null) target = passage_text.gameObject;
|
|
UI_OrderedEntryAnimator.PlayRefresh(target, 0.16f, -8f, 0.99f, true);
|
|
}
|
|
}
|