tomazsaraiva / unity-canvas-page-slider

A Scrollable Page Viewer for Unity
https://tomazsaraiva.github.io/unity-canvas-page-slider/
28 stars 2 forks source link

Enhanment: PageScroller.SetPage teleports immediately but it should animate transition #6

Closed jpetays closed 3 months ago

jpetays commented 3 months ago

PageScroller.SetPage teleports immediately to requested page but it should animate transition from current page to target page in the same way as using swipe.
I made these changes to make it work for me:

        /// <summary>
        /// Teleport immediately or use animation for SetPage() transition.
        /// </summary>
        [Tooltip("Teleport immediately to new page instead of using animation when SetPage() is called")]
        [SerializeField] private bool _teleportOnSetPage;

...

        public void SetPage(int index)
        {
            if (_teleportOnSetPage)
            {
                _scrollRect.horizontalNormalizedPosition = GetTargetPagePosition(index);

                var previousPage = _currentPage;
                _targetPage = index;
                _currentPage = index;
                OnPageChangeEnded?.Invoke(previousPage, _currentPage);
                return;
            }
            // Calculate simulated drag direction and amount for the animation.
            float dir = index - _currentPage;
            if (dir < 0 && _currentPage == 0)
            {
                // No can do.
                return;
            }
            // Mark 'drag' start point.
            _targetPage = index;
            OnBeginDrag(null);

            // Move scrollRect slightly to correct direction so that animation can play correctly.
            const float stepAmount = 0.01f;
            var pageWidth = 1f / GetPageCount();
            var dragStep = dir * stepAmount * pageWidth;
            _scrollRect.horizontalNormalizedPosition += dragStep;

            // Start the animation immediately.
            OnEndDrag(null);
        }
jpetays commented 3 months ago

I have a three page setup where middle page is the start page.
Above changes were not enough because PageSlider calls SetPage on Start() to set initial page. For this initial call we require always teleport!

Fix SetPage():

public void SetPage(int index, bool forceTeleport = false)

Fix PageSlider:

        private IEnumerator Start()
        {
            _scroller.OnPageChangeStarted.AddListener(PageScroller_PageChangeStarted);
            _scroller.OnPageChangeEnded.AddListener(PageScroller_PageChangeEnded);

            yield return new WaitForEndOfFrame();

            if (_startPageIndex == 0) yield break;
            _scroller.SetPage(_startPageIndex, forceTeleport: true);
        }
tomazsaraiva commented 3 months ago

Added in develop. Thanks for your great contributions!