Search Unity

  1. Welcome to the Unity Forums! Please take the time to read our Code of Conduct to familiarize yourself with the forum rules and how to post constructively.

Question How to get smooth inertia scrolling on a scroll rect with a mouse scroll wheel?

Discussion in 'UGUI & TextMesh Pro' started by ArnoldRauers_Tinytouchtales, Nov 30, 2022.

  1. ArnoldRauers_Tinytouchtales

    ArnoldRauers_Tinytouchtales

    Joined:
    Jan 25, 2015
    Posts:
    32
    Hi,

    is there a way to get the same inertia behavior on a scroll rect that you get when click-dragging the list,
    when you use a mouse scroll wheel? The scroll wheel just moves the list without any smoothing.

    Thanks!
     
  2. ArnoldRauers_Tinytouchtales

    ArnoldRauers_Tinytouchtales

    Joined:
    Jan 25, 2015
    Posts:
    32
    Ok, with the help of my boy OpenAI Chatbot I came up with this. Works pretty well. You can use this script to replace the regular Scroll Rect script.

    Code (CSharp):
    1. using System.Collections;
    2. using System.Collections.Generic;
    3. using UnityEngine;
    4. using UnityEngine.EventSystems;
    5. using UnityEngine.UI;
    6.  
    7. public class InertiaScrollRect : ScrollRect, IScrollHandler, IDragHandler
    8. {
    9.     // The speed at which the scrolling will slow down when inertia is applied
    10.     float decelerationRate = 2;
    11.  
    12.     // The current velocity of the scrolling
    13.     private float scrollVelocity;
    14.  
    15.     // A flag that indicates whether inertia is currently being applied
    16.     private bool isInertiaActive = true;
    17.  
    18.     // Stop inertia when you click on the list
    19.     public override void OnInitializePotentialDrag(PointerEventData eventData)
    20.     {
    21.         StopInertia();
    22.     }
    23.  
    24.     public override void OnScroll(PointerEventData eventData)
    25.     {
    26.         // Calculate the amount of scrolling that should be applied based on the mouse wheel delta
    27.  
    28.         // I had to tone the regular scroll sensitivy of 1 way down for this to be not too fast
    29.         // You can probaly mess around with the values here
    30.         float scrollDelta = eventData.scrollDelta.y * (scrollSensitivity * 0.001f);
    31.  
    32.         // If inertia is currently being applied, we need to stop it before we can apply
    33.         // the new scroll delta.
    34.         if (isInertiaActive)
    35.         {
    36.             StopInertia();
    37.         }
    38.  
    39.         float normalizedPosition = verticalNormalizedPosition;
    40.  
    41.         // Apply the scroll delta to the current normalized position
    42.         normalizedPosition += scrollDelta;
    43.  
    44.         // Set the new normalized position of the scroll rect
    45.          SetNormalizedPosition(normalizedPosition,1);
    46.  
    47.         // Start inertia scrolling with the current scroll velocity
    48.         StartInertia(scrollDelta / Time.deltaTime);
    49.     }
    50.  
    51.     // Update is called once per frame
    52.     void Update()
    53.     {
    54.         if (isInertiaActive)
    55.         {
    56.  
    57.             // Calculate the new scroll position based on the current scroll velocity
    58.             float scrollDelta = scrollVelocity * Time.deltaTime;
    59.  
    60.             float normalizedPosition = verticalNormalizedPosition;
    61.  
    62.             // Apply the scroll delta to the current normalized position
    63.             normalizedPosition += scrollDelta;
    64.  
    65.             if (normalizedPosition <= 0 || normalizedPosition >= 1)
    66.             {
    67.                 // The content has reached the top or bottom, so stop applying inertia
    68.                 StopInertia();
    69.             }
    70.             else
    71.             {
    72.                 // The content has not reached the top or bottom, so set the new normalized position
    73.                 // and continue applying inertia.
    74.                 SetNormalizedPosition(normalizedPosition, 1);
    75.  
    76.                 // Reduce the scroll velocity according to the deceleration rate
    77.                 scrollVelocity -= scrollVelocity * decelerationRate * Time.deltaTime;
    78.  
    79.                 // Check if the scroll velocity has reached 0
    80.                 if (Mathf.Abs(scrollVelocity) <= 0)
    81.                 {
    82.                     // The scroll velocity has reached 0, so stop applying inertia
    83.                     StopInertia();
    84.                 }
    85.             }
    86.         }
    87.     }
    88.  
    89.     // Start inertia scrolling with the specified scroll velocity
    90.     private void StartInertia(float velocity)
    91.     {
    92.         scrollVelocity = velocity;
    93.         isInertiaActive = true;
    94.     }
    95.  
    96.     // Stop applying inertia to the scrolling
    97.     private void StopInertia()
    98.     {
    99.         scrollVelocity = 0;
    100.         isInertiaActive = false;
    101.     }
    102. }
     
  3. rodrigolaiz

    rodrigolaiz

    Joined:
    Apr 4, 2022
    Posts:
    2
    Oh boy...!