From 61e4964a8ad2e911928136c1f1667eb5ff55149e Mon Sep 17 00:00:00 2001 From: Po Lu Date: Wed, 21 Sep 2022 19:24:06 +0800 Subject: [PATCH] Improve scroll interpolation in pixel-s-precision-mode * lisp/pixel-scroll.el (pixel-scroll-precision-interpolate): New arg FACTOR. Use it to determine the interpolation factor if non-nil. Also, clear scroll remainder if direction changes, and determine deltas based on the absolute amount of time passed. (bug#57967) (pixel-scroll-interpolate-down, pixel-scroll-interpolate-up): Pass factor of 0 to scroll exactly 1 page. --- lisp/pixel-scroll.el | 40 ++++++++++++++++++++++++++-------------- 1 file changed, 26 insertions(+), 14 deletions(-) diff --git a/lisp/pixel-scroll.el b/lisp/pixel-scroll.el index c4d59728ae1..a04a34b01ea 100644 --- a/lisp/pixel-scroll.el +++ b/lisp/pixel-scroll.el @@ -603,19 +603,25 @@ the height of the current window." (when (< delta 0) (set-window-vscroll nil (- delta) t t))))) -(defun pixel-scroll-precision-interpolate (delta &optional old-window) +(defun pixel-scroll-precision-interpolate (delta &optional old-window factor) "Interpolate a scroll of DELTA pixels. OLD-WINDOW is the window which will be selected when redisplay takes place, or nil for the current window. This results in the -window being scrolled by DELTA pixels with an animation." +window being scrolled by DELTA pixels with an animation. FACTOR +is a scale by which DELTA will be modified. If nil, it defaults +to `pixel-scroll-precision-interpolation-factor'." (let ((percentage 0) (total-time pixel-scroll-precision-interpolation-total-time) - (factor pixel-scroll-precision-interpolation-factor) + (factor (or factor pixel-scroll-precision-interpolation-factor)) (last-time (float-time)) - (time-elapsed 0.0) + (time-elapsed 0) (between-scroll pixel-scroll-precision-interpolation-between-scroll) (rem (window-parameter nil 'interpolated-scroll-remainder)) - (time (window-parameter nil 'interpolated-scroll-remainder-time))) + (time (window-parameter nil 'interpolated-scroll-remainder-time)) + (last-delta 0)) + (unless (or (not rem) (eq (< delta 0) (< rem 0))) + ;; The direction changed. Clear the remainder. + (setq rem nil)) (when (and rem time (< (- (float-time) time) 1.0) (eq (< delta 0) (< rem 0))) @@ -632,14 +638,14 @@ window being scrolled by DELTA pixels with an animation." (setq time-elapsed (+ time-elapsed (- (float-time) last-time)) percentage (/ time-elapsed total-time)) - (let ((throw-on-input nil)) + (let* ((throw-on-input nil) + (absolute-delta (* (min 1 percentage) delta factor)) + (relative-delta (abs + (round (- absolute-delta last-delta))))) + (setq last-delta absolute-delta) (if (< delta 0) - (pixel-scroll-precision-scroll-down - (ceiling (abs (* (* delta factor) - (/ between-scroll total-time))))) - (pixel-scroll-precision-scroll-up - (ceiling (* (* delta factor) - (/ between-scroll total-time)))))) + (pixel-scroll-precision-scroll-down relative-delta) + (pixel-scroll-precision-scroll-up relative-delta))) (setq last-time (float-time))) (if (< percentage 1) (progn @@ -819,14 +825,20 @@ It is a vector of the form [ VELOCITY TIME SIGN ]." "Interpolate a scroll downwards by one page." (interactive) (if pixel-scroll-precision-interpolate-page - (pixel-scroll-precision-interpolate (- (window-text-height nil t))) + (pixel-scroll-precision-interpolate (- (window-text-height nil t)) + ;; Don't use an + ;; interpolation factor, + ;; since we want exactly 1 + ;; page to be scrolled. + 0) (cua-scroll-up))) (defun pixel-scroll-interpolate-up () "Interpolate a scroll upwards by one page." (interactive) (if pixel-scroll-precision-interpolate-page - (pixel-scroll-precision-interpolate (window-text-height nil t)) + (pixel-scroll-precision-interpolate (window-text-height nil t) + 0) (cua-scroll-down))) ;;;###autoload -- 2.39.2