diff --git a/Widgets/NGridView.qml b/Widgets/NGridView.qml index b1d375464..17dc2d276 100644 --- a/Widgets/NGridView.qml +++ b/Widgets/NGridView.qml @@ -85,6 +85,32 @@ Item { // Scroll speed multiplier for mouse wheel (1.0 = default, higher = faster) property real wheelScrollMultiplier: 2.0 + property int smoothWheelAnimationDuration: Style.animationNormal + property real _wheelTargetY: 0 + + function clampScrollY(value) { + return Math.max(0, Math.min(value, gridView.contentHeight - gridView.height)); + } + + function applyWheelScroll(delta) { + if (!root.contentOverflows) + return; + + const step = delta * root.wheelScrollMultiplier; + + if (!Settings.data.general.smoothScrollEnabled || Settings.data.general.animationDisabled) { + gridView.contentY = root.clampScrollY(gridView.contentY - step); + root._wheelTargetY = gridView.contentY; + return; + } + + if (!wheelScrollAnimation.running) + root._wheelTargetY = gridView.contentY; + + root._wheelTargetY = root.clampScrollY(root._wheelTargetY - step); + wheelScrollAnimation.to = root._wheelTargetY; + wheelScrollAnimation.restart(); + } // Track selection index for gradient visibility (set externally) property int trackedSelectionIndex: -1 @@ -197,6 +223,7 @@ Item { implicitHeight: 200 Component.onCompleted: { + _wheelTargetY = gridView.contentY; createGradients(); } @@ -280,6 +307,31 @@ Item { // Enable flickable for smooth scrolling boundsBehavior: Flickable.StopAtBounds + NumberAnimation { + id: wheelScrollAnimation + target: gridView + property: "contentY" + duration: root.smoothWheelAnimationDuration + easing.type: Easing.OutCubic + } + + onDraggingChanged: { + if (dragging) { + wheelScrollAnimation.stop(); + root._wheelTargetY = contentY; + } + } + + onFlickingChanged: { + if (flicking) { + wheelScrollAnimation.stop(); + root._wheelTargetY = contentY; + } + } + + onContentHeightChanged: root._wheelTargetY = root.clampScrollY(root._wheelTargetY) + onHeightChanged: root._wheelTargetY = root.clampScrollY(root._wheelTargetY) + // Focus handling depends on keyNavigationEnabled focus: keyNavigationEnabled activeFocusOnTab: keyNavigationEnabled @@ -296,8 +348,7 @@ Item { acceptedDevices: PointerDevice.Mouse | PointerDevice.TouchPad onWheel: event => { const delta = event.pixelDelta.y !== 0 ? event.pixelDelta.y : event.angleDelta.y / 2; - const newY = gridView.contentY - (delta * root.wheelScrollMultiplier); - gridView.contentY = Math.max(0, Math.min(newY, gridView.contentHeight - gridView.height)); + root.applyWheelScroll(delta); event.accepted = true; } }