diff --git a/Editor/RecyclerView/RecyclerViewEditor.cs b/Editor/RecyclerView/RecyclerViewEditor.cs index fcd07a0..ecad732 100644 --- a/Editor/RecyclerView/RecyclerViewEditor.cs +++ b/Editor/RecyclerView/RecyclerViewEditor.cs @@ -329,20 +329,10 @@ namespace AlicizaX.UI.Editor using (new EditorGUI.DisabledScope(isPlaying)) { - bool previousScrollValue = _scroll.boolValue; - EditorGUILayout.PropertyField(_scroll); - - if (_scroll.boolValue != previousScrollValue) - { - HandleScrollToggle(); - } - } - - if (_scroll.boolValue) - { - DrawScrollBarSettings(isPlaying); + EditorGUILayout.PropertyField(_scroll, new GUIContent("Scroll Mode")); } + DrawScrollBarSettings(isPlaying); EditorGUILayout.PropertyField(_snap); } EditorGUILayout.EndVertical(); @@ -369,8 +359,6 @@ namespace AlicizaX.UI.Editor private void DrawScrollerSection(bool isPlaying) { - if (!_scroll.boolValue) return; - EditorGUILayout.BeginVertical("box"); { EditorGUILayout.LabelField("Scroller Settings", EditorStyles.boldLabel); @@ -500,29 +488,6 @@ namespace AlicizaX.UI.Editor _selectedScrollerIndex = 0; } - private void HandleScrollToggle() - { - if (!_scroll.boolValue) - { - RemoveScrollerComponent(); - ClearScrollBar(); - } - } - - private void RemoveScrollerComponent() - { - var recyclerView = target as RecyclerView; - if (recyclerView == null) return; - - var scrollerComponent = recyclerView.GetComponent(); - if (scrollerComponent != null) - { - Undo.DestroyObjectImmediate(scrollerComponent as MonoBehaviour); - } - - ClearScrollerReferences(); - } - #endregion #region Scrollbar Handling diff --git a/Editor/RecyclerView/Res/ScrollView.prefab b/Editor/RecyclerView/Res/ScrollView.prefab index 04a6fe1..d2c96be 100644 --- a/Editor/RecyclerView/Res/ScrollView.prefab +++ b/Editor/RecyclerView/Res/ScrollView.prefab @@ -100,7 +100,7 @@ MonoBehaviour: wheelSpeed: 30 templates: [] content: {fileID: 7227160576944475251} - showScrollBar: 0 + scrollbarVisibility: 0 scrollbar: {fileID: 0} _layoutManagerTypeName: AlicizaX.UI.LinearLayoutManager layoutManager: diff --git a/Runtime/RecyclerView/Layout/LayoutManager.cs b/Runtime/RecyclerView/Layout/LayoutManager.cs index 1df24b6..e9757a8 100644 --- a/Runtime/RecyclerView/Layout/LayoutManager.cs +++ b/Runtime/RecyclerView/Layout/LayoutManager.cs @@ -250,4 +250,11 @@ namespace AlicizaX.UI AlwaysShow = 1, WhenScrollable = 2 } + + public enum ScrollMode + { + AlwaysDisable = 0, + AlwaysShow = 1, + WhenScrollable = 2 + } } diff --git a/Runtime/RecyclerView/RecyclerView.cs b/Runtime/RecyclerView/RecyclerView.cs index f1d497c..92ba3d9 100644 --- a/Runtime/RecyclerView/RecyclerView.cs +++ b/Runtime/RecyclerView/RecyclerView.cs @@ -3,6 +3,7 @@ using System.Collections.Generic; using System.Threading; using UnityEngine; using UnityEngine.EventSystems; +using UnityEngine.Serialization; using UnityEngine.UI; namespace AlicizaX.UI @@ -51,7 +52,7 @@ namespace AlicizaX.UI /// /// 是否启用滚动能力�? /// - [HideInInspector] [SerializeField] private bool scroll; + [HideInInspector] [SerializeField] private ScrollMode scroll = ScrollMode.AlwaysShow; /// /// 是否在停止滚动后自动吸附到最近项�? @@ -87,6 +88,7 @@ namespace AlicizaX.UI /// /// 是否显示滚动条�? /// + [FormerlySerializedAs("showScrollBar")] [HideInInspector] [SerializeField] private ScrollbarVisibility scrollbarVisibility; /// @@ -221,7 +223,7 @@ namespace AlicizaX.UI /// /// 获取或设置是否启用滚动能力�? /// - public bool Scroll + public ScrollMode Scroll { get => scroll; set @@ -231,10 +233,9 @@ namespace AlicizaX.UI if (scroller != null) { - scroller.InputEnabled = scroll; - scroller.WheelSpeed = wheelSpeed; scroller.Snap = snap; + UpdateScrollerState(); } RequestLayout(); @@ -249,9 +250,8 @@ namespace AlicizaX.UI get => snap; set { - bool newSnap = value & scroll; - if (snap == newSnap) return; - snap = newSnap; + if (snap == value) return; + snap = value; if (scroller != null) { @@ -687,7 +687,7 @@ namespace AlicizaX.UI /// private void ConfigureScrollbar() { - if (scrollbarVisibility == ScrollbarVisibility.AlwaysHide || scrollbar == null) return; + if (scrollbar == null) return; scrollbar.onValueChanged.AddListener(OnScrollbarChanged); @@ -1145,7 +1145,7 @@ namespace AlicizaX.UI /// 是否使用平滑滚动�?/param> public void ScrollTo(int index, bool smooth = false) { - if (!scroll || scroller == null) return; + if (scroll == ScrollMode.AlwaysDisable || scroller == null) return; scroller.ScrollTo(layoutManager.IndexToPosition(index), smooth); @@ -1167,7 +1167,7 @@ namespace AlicizaX.UI /// 平滑滚动时长,单位为秒�?/param> public void ScrollToWithAlignment(int index, ScrollAlignment alignment, float offset = 0f, bool smooth = false, float duration = 0.3f) { - if (!scroll || scroller == null) return; + if (scroll == ScrollMode.AlwaysDisable || scroller == null) return; float targetPosition = CalculateScrollPositionWithAlignment(index, alignment, offset); @@ -1392,16 +1392,17 @@ namespace AlicizaX.UI } bool shouldShow = ShouldShowScrollbar(); + bool shouldInteract = shouldShow && ShouldEnableScrollbarInteraction(); if (scrollbarVisibleState != shouldShow || scrollbar.gameObject.activeSelf != shouldShow) { scrollbarVisibleState = shouldShow; scrollbar.gameObject.SetActive(shouldShow); } - if (scrollbarInteractableState != shouldShow || scrollbar.interactable != shouldShow) + if (scrollbarInteractableState != shouldInteract || scrollbar.interactable != shouldInteract) { - scrollbarInteractableState = shouldShow; - scrollbar.interactable = shouldShow; + scrollbarInteractableState = shouldInteract; + scrollbar.interactable = shouldInteract; } if (shouldShow) @@ -1417,7 +1418,7 @@ namespace AlicizaX.UI /// 应显示滚动条时返�?;否则返�?�?/returns> private bool ShouldShowScrollbar() { - if (scrollbarVisibility == ScrollbarVisibility.AlwaysHide || !scroll || scrollbar == null || scroller == null || layoutManager == null) + if (scrollbarVisibility == ScrollbarVisibility.AlwaysHide || scrollbar == null || scroller == null || layoutManager == null) { return false; } @@ -1437,11 +1438,6 @@ namespace AlicizaX.UI return false; } - if (!ShouldLimitScrollToOverflow()) - { - return true; - } - return HasScrollableContent(); } @@ -1523,16 +1519,31 @@ namespace AlicizaX.UI return; } - scroller.InputEnabled = scroll && (!ShouldLimitScrollToOverflow() || HasScrollableContent()); + scroller.InputEnabled = ShouldEnableScrollInput(); } /// /// 判断是否需要将滚动能力限制在内容溢出场景下才启用�? /// /// 需要仅在内容溢出时启用滚动返回 ;否则返�?�?/returns> - private bool ShouldLimitScrollToOverflow() + private bool ShouldEnableScrollInput() { - return scrollbarVisibility == ScrollbarVisibility.WhenScrollable && SupportsOverflowCheck(); + if (scroll == ScrollMode.AlwaysDisable) + { + return false; + } + + if (scroll == ScrollMode.AlwaysShow) + { + return true; + } + + return SupportsOverflowCheck() && HasScrollableContent(); + } + + private bool ShouldEnableScrollbarInteraction() + { + return ShouldEnableScrollInput() && HasValidScrollMetrics() && HasScrollableContent(); } ///