using System; using System.Collections; using System.Collections.Generic; using System.Linq; using Cute; using UnityEngine; namespace Wizard; public class ChatLogUI : MonoBehaviour { public class PartsForPlate { public ChatDeckView DeckView { get; private set; } public PartsForPlate(ChatDeckView chatDeckView) { DeckView = chatDeckView; } } public const int INVALID_UNREAD_MESSAGE_ID = -1; public const int SCROLL_OBJECT_NUM = 10; private const int SCROLL_OBJECT_MARGIN = 10; [SerializeField] private UIButton _buttonToNewMessage; [SerializeField] private UIScrollView _scrollView; [SerializeField] private UIWrapVariableContentVertical _wrapVariableContent; [SerializeField] private UIScrollBarWrapContent _scrollBarWrapContent; [SerializeField] private WrapVariableContentsScrollBarSize _wrapContentScrollBarSize; private UIPanel _panelScrollView; private float _startBaseClipRegionY; private float _startBaseClipRegionW; private ChatLogPlate _logPlateOriginal; private ChatLogPlate _logPlateForSizeCalcDummyObject; private List _plateList = new List(); private List _loadedResourceList = new List(); [SerializeField] private ChatDeckView _chatDeckView; private bool _isCreateFinish; private Action _onInitializeOldestLog; private int _unreadMessageId; private int _oldUnreadMessageId = -1; private List _dependOpenCloseAnimationList = new List(); private float _scrollViewBasePosY; private bool _isFollowingAnimation; private Coroutine _bottomScrollViewAnimationCoroutin; private float _bottomScrollViewAnimationDistance; private IChatSettings _chatSettings; private ChatConnectController _chatConnectController; private List _stampList; private PartsForPlate _partsForPlate; public bool IsEnableUpdateUI { get; private set; } public List ChatVisibleLogList { get; private set; } = new List(); public List ChatAllLogList { get; private set; } = new List(); public void Init(IChatSettings chatSettings, ChatConnectController chatConnectController, List stampList) { _chatSettings = chatSettings; _chatConnectController = chatConnectController; _stampList = stampList; _logPlateOriginal = chatSettings.PrefabChatLogPlate; _chatDeckView.Init(chatSettings.ApiSettings, chatConnectController, CloseChatLogContent); _partsForPlate = new PartsForPlate(_chatDeckView); } public void ShowDeckViewByDeckLog(ChatMessageInfo.DeckLogData deckLogData, Action onOpen = null, Action onClose = null, Action>> onDeleteDeckSuccess = null) { _chatDeckView.ShowDeckViewByDeckLog(deckLogData, onOpen, onClose, onDeleteDeckSuccess); } public void ShowDeckViewByDeckData(DeckData deck, Action onOpen, Action onClose, bool isActiveRedButton, bool isActiveDeckIntroductionObj) { _chatDeckView.ShowDeckViewByDeckData(deck, onOpen, onClose, isActiveRedButton, isActiveDeckIntroductionObj); } public void CloseDeckView() { _chatDeckView.CloseDeckView(); } public bool IsShowDeckView() { return _chatDeckView.IsShowDeckCardView(); } public void CreateChatLogView(List messageList, Action onInitializeOldestLog, Action onFinCallBack, int unreadMessageId = -1) { _onInitializeOldestLog = onInitializeOldestLog; _panelScrollView = _scrollView.GetComponent(); Vector4 baseClipRegion = _panelScrollView.baseClipRegion; _startBaseClipRegionY = baseClipRegion.y; _startBaseClipRegionW = baseClipRegion.w; _buttonToNewMessage.onClick.Clear(); _buttonToNewMessage.onClick.Add(new EventDelegate(delegate { MoveNewMessagePosition(); })); _buttonToNewMessage.gameObject.SetActive(value: false); _unreadMessageId = unreadMessageId; AddChatLogInfo(messageList, Chat.eRequestDirection.OLD); List chatLogAssetPathList = GetChatLogAssetPathList(ChatVisibleLogList); for (int num = 0; num < _stampList.Count; num++) { string assetTypePath = Toolbox.ResourcesManager.GetAssetTypePath(_stampList[num].ToString(), ResourcesManager.AssetLoadPathType.Stamp); chatLogAssetPathList.Add(assetTypePath); } LoadResources(chatLogAssetPathList, delegate { CreateScrollView(ChatVisibleLogList); ResetScrollDefaultPosition(unreadMessageId); onFinCallBack.Call(); _isCreateFinish = true; }); } public void CloseChatLogView() { UnloadResources(); } public void ResetScrollDefaultPosition(int unreadMessageId = -1) { int centerIndex = Mathf.Max(ChatVisibleLogList.Count - 1, 0); if (unreadMessageId != -1) { int num = ChatVisibleLogList.FindIndex((ChatMessageInfo log) => log.MessageId == unreadMessageId); if (num >= 0) { centerIndex = num; } } _wrapVariableContent.ResetScrollPositionByIndex(centerIndex); } public void SetEnableUpdateUI() { if (IsEnableUpdateUI) { return; } IsEnableUpdateUI = true; if (_oldUnreadMessageId != -1) { UpdateChatLogSizeByIndex(ChatVisibleLogList.FindIndex((ChatMessageInfo info) => info.MessageId == _oldUnreadMessageId)); _oldUnreadMessageId = -1; } _wrapContentScrollBarSize.ContentUpdate(); _wrapVariableContent.WrapContent(); } public void AddChatLogView(ChatInfo chatInfo, Chat.eRequestDirection eDirection, bool in_enableUpdateUI = true, Action onFinCallBack = null) { if (chatInfo.MessageList.Count <= 0) { onFinCallBack.Call(); return; } AddChatLogInfo(chatInfo.MessageList, eDirection); if (chatInfo.VisibleMessageList.Count <= 0) { onFinCallBack.Call(); return; } if (eDirection == Chat.eRequestDirection.NEW && IsEnableUpdateUI && !in_enableUpdateUI) { _oldUnreadMessageId = _unreadMessageId; _unreadMessageId = chatInfo.VisibleMessageList[0].MessageId; } IsEnableUpdateUI = in_enableUpdateUI; bool flag = _wrapVariableContent.IsBottom(); List chatLogAssetPathList = GetChatLogAssetPathList(chatInfo.VisibleMessageList); LoadResources(chatLogAssetPathList); AddScrollPlate(chatInfo.VisibleMessageList, eDirection); if (eDirection == Chat.eRequestDirection.NEW && flag && IsEnableUpdateUI) { MoveNewMessagePosition(); } onFinCallBack.Call(); } public void MoveNewMessagePosition() { if (_wrapVariableContent.IsScrollEnableSize()) { _wrapVariableContent.ResetScrollPositionBottomEasing(); } } public void ChangeLogViewSizeByInputUIAnimation(ChatOpenCloseAnimation sendUIAnimation) { _scrollBarWrapContent.gameObject.SetActive(value: false); _buttonToNewMessage.gameObject.SetActive(value: false); if (!_dependOpenCloseAnimationList.Contains(sendUIAnimation)) { _dependOpenCloseAnimationList.Add(sendUIAnimation); } if (_dependOpenCloseAnimationList.All((ChatOpenCloseAnimation x) => x.IsAnimationStartFromOpenedOrClosed)) { _isFollowingAnimation = IsEnableFollowAnimation(); float num = (_isFollowingAnimation ? GetDependOpenCloseAnimationHeight() : 0f); _scrollViewBasePosY = _scrollView.transform.localPosition.y - num; if (_isFollowingAnimation && _bottomScrollViewAnimationCoroutin == null) { _bottomScrollViewAnimationCoroutin = StartCoroutine(CalcHeightBottomScrollViewAnimation()); } } } private IEnumerator CalcHeightBottomScrollViewAnimation() { float distance = _wrapVariableContent.GetDistanceBetweenBottomItemAndScrollBottomPos(); float durationTime = _dependOpenCloseAnimationList.Max((ChatOpenCloseAnimation x) => x.AnimationTime); _bottomScrollViewAnimationDistance = 0f; CustomEasing easing = new CustomEasing(CustomEasing.eType.outQuad, 0f, distance, durationTime); while (easing.IsMoving) { _bottomScrollViewAnimationDistance = easing.GetCurVal(Time.deltaTime); yield return null; } _bottomScrollViewAnimationDistance = distance; _bottomScrollViewAnimationCoroutin = null; } private void CloseChatLogContent(int messageId) { int num = ChatVisibleLogList.FindIndex((ChatMessageInfo log) => log.MessageId == messageId); if (num >= 0) { ChatVisibleLogList[num].CloseContent(); UpdateChatLogSizeByIndex(num); } } private void UpdateChatLogSizeByIndex(int index) { if (index >= 0 && ChatVisibleLogList.Count >= index) { _wrapVariableContent.UpdateItemSize(index, GetHeightPlateSize(ChatVisibleLogList[index])); _wrapContentScrollBarSize.ContentUpdate(); } } private bool IsEnableFollowAnimation() { if (!_wrapVariableContent.IsScrollEnableSize()) { return false; } if (!_wrapVariableContent.IsBottom()) { return false; } if (_wrapVariableContent.TopOverflowItemSize() < GetDependOpenCloseAnimationHeight()) { return false; } return true; } private float GetDependOpenCloseAnimationHeight() { float num = 0f; foreach (ChatOpenCloseAnimation dependOpenCloseAnimation in _dependOpenCloseAnimationList) { float num2 = num; num2 = ((!dependOpenCloseAnimation.IsMoving) ? ((!dependOpenCloseAnimation.IsOpen) ? 0f : dependOpenCloseAnimation.OpenHeight) : dependOpenCloseAnimation.CurrentPosHeight); num = Mathf.Max(num, num2); } return num; } private void Update() { UpdateButtonToNewMessage(); } private void UpdateButtonToNewMessage() { if (IsEnableUpdateUI && _dependOpenCloseAnimationList.Count <= 0) { _buttonToNewMessage.gameObject.SetActive(!_wrapVariableContent.IsBottom()); } } private void LateUpdate() { if (IsUpdateLogViewSize()) { UpdateLogViewSizeDependAnimation(); } } private bool IsUpdateLogViewSize() { return _dependOpenCloseAnimationList.Any((ChatOpenCloseAnimation x) => x.IsMoving || !x.IsOpen); } private void UpdateLogViewSizeDependAnimation() { float dependOpenCloseAnimationHeight = GetDependOpenCloseAnimationHeight(); Vector4 baseClipRegion = _panelScrollView.baseClipRegion; baseClipRegion.y = _startBaseClipRegionY + dependOpenCloseAnimationHeight * 0.5f; baseClipRegion.w = _startBaseClipRegionW - dependOpenCloseAnimationHeight; _panelScrollView.baseClipRegion = baseClipRegion; float num = _scrollViewBasePosY; if (_isFollowingAnimation) { num += dependOpenCloseAnimationHeight + _bottomScrollViewAnimationDistance; } _wrapVariableContent.MoveScrollPanel(num); _dependOpenCloseAnimationList.RemoveAll((ChatOpenCloseAnimation x) => !x.IsMoving && !x.IsOpen); _scrollBarWrapContent.gameObject.SetActive(_dependOpenCloseAnimationList.Count == 0 && _wrapVariableContent.IsScrollEnableSize()); } private void AddChatLogInfo(List addChatLogList, Chat.eRequestDirection eDirection) { if (eDirection == Chat.eRequestDirection.OLD) { for (int num = addChatLogList.Count - 1; num >= 0; num--) { ChatAllLogList.Insert(0, addChatLogList[num]); } } else { ChatAllLogList.AddRange(addChatLogList); } ChatVisibleLogList = ChatAllLogList.Where((ChatMessageInfo log) => log.IsVisibleMessage).ToList(); } private List GetChatLogAssetPathList(List logList) { List list = new List(); List list2 = new List(); for (int i = 0; i < logList.Count; i++) { list.AddRange(logList[i].GetResourcePathList()); } list = list.Distinct().ToList(); for (int j = 0; j < list.Count; j++) { string item = list[j]; if (!_loadedResourceList.Contains(item)) { list2.Add(item); } } return list2; } private void LoadResources(List resourcePathList, Action callBack = null) { if (resourcePathList.Count <= 0) { callBack.Call(); return; } UIManager.GetInstance().StartCoroutine(Toolbox.ResourcesManager.LoadAssetGroupAsync(resourcePathList, delegate { _loadedResourceList.AddRange(resourcePathList); callBack.Call(); })); } private void CreateScrollView(List addChatLogList) { _wrapVariableContent.gameObject.SetActive(value: false); _scrollBarWrapContent.m_WrapContents = _wrapVariableContent; _scrollBarWrapContent.gameObject.SetActive(value: true); _scrollView.gameObject.SetActive(value: true); _wrapVariableContent.Init(10, 0, 0, OnInitializeItem); _wrapVariableContent.gameObject.SetActive(value: true); if (ChatVisibleLogList.Count > 0) { AddScrollPlate(addChatLogList, Chat.eRequestDirection.OLD); } } private void AddScrollPlate(List addChatLogList, Chat.eRequestDirection eDirection) { List list = new List(); foreach (ChatMessageInfo addChatLog in addChatLogList) { int heightPlateSize = GetHeightPlateSize(addChatLog); if (heightPlateSize > 0) { list.Add(heightPlateSize); } } _wrapVariableContent.AddItemList(list, eDirection == Chat.eRequestDirection.NEW); if (_plateList.Count < 10) { _wrapVariableContent.enabled = true; for (int i = _plateList.Count; i < ChatVisibleLogList.Count && i < 10; i++) { ChatLogPlate item = CreateLogPlate(_wrapVariableContent.gameObject); _plateList.Add(item); } for (int j = 0; j < _plateList.Count; j++) { _plateList[j].gameObject.SetActive(value: true); } _wrapVariableContent.SortBasedOnScrollMovement(); if (!_wrapVariableContent.IsScrollEnableSize()) { _scrollView.ResetPosition(); } } if (IsEnableUpdateUI) { _wrapContentScrollBarSize.ContentUpdate(); _wrapVariableContent.WrapContent(); } } private int GetHeightPlateSize(ChatMessageInfo logInfo) { if (_logPlateForSizeCalcDummyObject == null) { _logPlateForSizeCalcDummyObject = CreateLogPlate(base.gameObject); _logPlateForSizeCalcDummyObject.gameObject.SetActive(value: false); } return _logPlateForSizeCalcDummyObject.GetHeightSize(logInfo, logInfo.MessageId == _unreadMessageId) + 10; } private ChatLogPlate CreateLogPlate(GameObject rootObj) { ChatLogPlate component = NGUITools.AddChild(rootObj, _logPlateOriginal.gameObject).GetComponent(); component.Init(_chatSettings, _chatConnectController, _partsForPlate, IsLoadedResources); return component; } private void OnInitializeItem(GameObject go, int wrapIndex, int realIndex) { int num = -realIndex; if (num >= ChatVisibleLogList.Count || num < 0) { go.SetActive(value: false); return; } go.SetActive(value: true); ChatMessageInfo chatMessageInfo = ChatVisibleLogList[num]; go.GetComponent().SetData(chatMessageInfo, chatMessageInfo.MessageId == _unreadMessageId); if (num == 0 && _isCreateFinish) { _onInitializeOldestLog.Call(); } } private void OnDestroy() { UnloadResources(); } private bool IsLoadedResources(List checkResourceList) { for (int i = 0; i < checkResourceList.Count; i++) { if (!_loadedResourceList.Contains(checkResourceList[i])) { return false; } } return true; } private void UnloadResources() { if (_loadedResourceList != null) { Toolbox.ResourcesManager.RemoveAssetGroup(_loadedResourceList); _loadedResourceList.Clear(); } } }