[Top][All Lists]

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: Gtk scrollbar: thumb too short

From: Luc Teirlinck
Subject: Re: Gtk scrollbar: thumb too short
Date: Mon, 14 Apr 2003 20:24:32 -0500 (CDT)

Richard Stallman wrote:

   There is some chance we will change the behavior of the native
   scrollbar; people have proposed some interesting ideas.  However,
   people have not yet implemented them, and if they do, we will have
   to try them out before deciding whether to use them.  So I would
   say the chance of a change is less than 50%.

If I understand correctly Kai made three proposals:

1. Implement stickiness.
2. Only allow overscrolling if the end of the buffer was visible at
   the start of scrolling.
3. Use the Motiv - current GTK behavior but color the piece of the
   scrollbar that corresponds to the empty space at the bottom

If I understand correctly, you only considered 1. and 2. worth a try.

Personally, I only feel comfortable implementing 2. and only for the
native scrollbar.  (I am not familiar enough with the other

Below is a rough implementation, only meant for people to "play" with
to see if they like it.  If people are interested, I would make the
new behavior customizable and one could then decide what the default
behavior should be.  Note that my implementation only applies to the
native scrollbar.

Description of new behavior:

First time scrolling stops with the last screenfull of real text
visible, unless the end of the buffer is visible at the outset and
stays visible.  In other words, if you scroll up to see what is above
and scroll back down, you can not (immediately) overscroll.  To
overscroll, you have to first scroll to the bottom (unless you already
are there), grab the thumb (*not* click above the thumb) and scroll
down, without first scrolling up.

I personally would only recommend making the new behavior a
customizable option, with the old behavior the default.

Since this is just a rough implementation, I do not yet send a diff,
but instead the new versions of scroll-bar-drag and scroll-bar-drag-1.
One can put these in a file in emacs-lisp-mode, do C-M-x and start
playing.  Of course, like any new behavior, one first has to get used
to it, and then use it in some actual "real work", before one can
really judge.  The new behavior is meant for people who only
occasionally want to overscroll, and most of the time only want to
scroll to the end of the buffer.  In the final version, you will
always be able to temporarily (or on a buffer-by-buffer basis) change
your usual default, using the customizable variable I would define.
First, however, I want to check whether there is any interest.

===File ~/dragstuff.el======================================
(defun scroll-bar-drag-1 (event)
  (let* ((start-position (event-start event))
         (window (nth 0 start-position))
         (portion-whole (nth 2 start-position)))
      (set-buffer (window-buffer window))
      ;; Calculate position relative to the accessible part of the buffer.
      (goto-char (+ (point-min)
                    (scroll-bar-scale portion-whole
                                      (- (point-max) (point-min)))))
      (set-window-start window (point))
      (if (eq (window-end nil t) (point-max))
          (when (and (boundp end-visible) (not end-visible))
            (goto-char (point-max))
            (recenter -1))
        (setq end-visible nil)))))

(defun scroll-bar-drag (event)
  "Scroll the window by dragging the scroll bar slider.
If you click outside the slider, the window scrolls to bring the slider there."
  (interactive "e")
  (let* (done
         (echo-keystrokes 0)
         (end-position (event-end event))
         (window (nth 0 end-position))
    (with-current-buffer (window-buffer window)
      (setq before-scroll point-before-scroll))
      (select-window window)
      (setq end-visible (= (point-max) (window-end nil t)))
      (setq before-scroll
            (or before-scroll (point))))
    (scroll-bar-drag-1 event)
      (while (not done)
        (setq event (read-event))
        (if (eq (car-safe event) 'mouse-movement)
            (setq event (read-event)))
        (cond ((eq (car-safe event) 'scroll-bar-movement)
               (scroll-bar-drag-1 event))
               ;; Exit when we get the drag event; ignore that event.
               (setq done t)))))
    (sit-for 0)
    (with-current-buffer (window-buffer window)
      (setq point-before-scroll before-scroll))))


reply via email to

[Prev in Thread] Current Thread [Next in Thread]