[Top][All Lists]
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
Re: Emacs + LessTif serious scroll judder when point-max is visible
From: |
Stefan Monnier |
Subject: |
Re: Emacs + LessTif serious scroll judder when point-max is visible |
Date: |
Fri, 30 Nov 2001 16:54:03 -0500 |
> > Richard Stallman <address@hidden> writes:
> >
> > > Could you please respond?
> > >
> > > From: "Marshall, Simon" <address@hidden>
> > > Subject: FW: Emacs + LessTif serious scroll judder when
> > point-max is visible
> > > To: "'Emacs Developers'" <address@hidden>
> > > Date: Thu, 29 Nov 2001 11:43:09 -0000
> > >
> > > Hi folks, I seem to remember someone (Gerd?) saying that
> > there could be
> > > a workaround for this problem, but that it would have to wait until
> > > after 21.1.
> >
> > If I've said that, which I don't remember, I don't remember what I had
> > in mind. Maybe it was Stefan?
>
> That rings a bell, maybe it was... Stefan?
Yes, it might have been me.
If you feel like it, you can try the patch below which I've
been using but am not satisfied with. I haven't actually tried in
with Motif/Lesstif, but (modulo bugs) it should solve the jitter
problem at the cost of a less useful thumb-positioning.
Could people on emacs-devel try it out and tell me what they think
about it ?
Maybe we should use this patch for Motif but not for Xaw3d
(the jitter is usually less severe with Xaw3d) ?
Stefan
Index: xterm.c
===================================================================
RCS file: /cvs/emacs/src/xterm.c,v
retrieving revision 1.689
diff -u -r1.689 xterm.c
--- xterm.c 2001/11/28 17:07:59 1.689
+++ xterm.c 2001/11/30 21:50:44
@@ -847,8 +847,8 @@
break;
case OVERLAY_ARROW_BITMAP:
- wd = left_width;
- h = left_height;
+ wd = ov_width;
+ h = ov_height;
bits = ov_bits;
x = (WINDOW_TO_FRAME_PIXEL_X (w, 0)
- wd
@@ -864,8 +864,8 @@
break;
case CONTINUED_LINE_BITMAP:
- wd = right_width;
- h = right_height;
+ wd = continued_width;
+ h = continued_height;
bits = continued_bits;
x = window_box_right (w, -1);
x += (FRAME_X_RIGHT_FRINGE_WIDTH (f) - wd) / 2;
@@ -8264,13 +8264,6 @@
static Boolean xaw3d_arrow_scroll;
-/* Whether the drag scrolling maintains the mouse at the top of the
- thumb. If not, resizing the thumb needs to be done more carefully
- to avoid jerkyness. */
-
-static Boolean xaw3d_pick_top;
-
-
/* Action hook installed via XtAppAddActionHook when toolkit scroll
bars are used.. The hook is responsible for detecting when
the user ends an interaction with the scroll bar, and generates
@@ -8481,31 +8474,10 @@
XtVaGetValues (widget, XmNsliderSize, &slider_size, NULL);
UNBLOCK_INPUT;
- /* At the max position of the scroll bar, do a line-wise
- movement. Without doing anything, we would be called with
- the same cs->value again and again. If we want to make
- sure that we can reach the end of the buffer, we have to do
- something.
-
- Implementation note: setting bar->dragging always to
- cs->value gives a smoother movement at the max position.
- Setting it to nil when doing line-wise movement gives
- a better slider behavior. */
-
- if (cs->value + slider_size == XM_SB_MAX
- || (dragging_down_p
- && last_scroll_bar_part == scroll_bar_down_arrow))
- {
- part = scroll_bar_down_arrow;
- bar->dragging = Qnil;
- }
- else
- {
- whole = XM_SB_RANGE;
- portion = min (cs->value - XM_SB_MIN, XM_SB_MAX - slider_size);
- part = scroll_bar_handle;
- bar->dragging = make_number (cs->value);
- }
+ whole = XM_SB_RANGE - slider_size;
+ portion = min (cs->value - XM_SB_MIN, whole);
+ part = scroll_bar_handle;
+ bar->dragging = make_number (cs->value);
}
break;
@@ -8524,6 +8496,7 @@
#else /* !USE_MOTIF, i.e. Xaw. */
+#define XAW_SB_RANGE 10000000
/* Xaw scroll bar callback. Invoked when the thumb is dragged.
WIDGET is the scroll bar widget. CLIENT_DATA is a pointer to the
@@ -8546,19 +8519,10 @@
XtVaGetValues (widget, XtNshown, &shown, XtNheight, &height, NULL);
UNBLOCK_INPUT;
- whole = 10000000;
- portion = shown < 1 ? top * whole : 0;
+ whole = XAW_SB_RANGE - (XAW_SB_RANGE * shown);
+ portion = min (XAW_SB_RANGE * top, whole);
+ part = scroll_bar_handle;
- if (shown < 1 && (abs (top + shown - 1) < 1.0/height))
- /* Some derivatives of Xaw refuse to shrink the thumb when you reach
- the bottom, so we force the scrolling whenever we see that we're
- too close to the bottom (in x_set_toolkit_scroll_bar_thumb
- we try to ensure that we always stay two pixels away from the
- bottom). */
- part = scroll_bar_down_arrow;
- else
- part = scroll_bar_handle;
-
window_being_scrolled = bar->window;
bar->dragging = make_number (portion);
last_scroll_bar_part = part;
@@ -8762,8 +8726,7 @@
{
char *initial = "";
char *val = initial;
- XtVaGetValues (widget, XtNscrollVCursor, (XtPointer) &val,
- XtNpickTop, (XtPointer) &xaw3d_pick_top, NULL);
+ XtVaGetValues (widget, XtNscrollVCursor, (XtPointer) &val, NULL);
if (val == initial)
{ /* ARROW_SCROLL */
xaw3d_arrow_scroll = True;
@@ -8807,8 +8770,24 @@
struct frame *f = XFRAME (WINDOW_FRAME (XWINDOW (bar->window)));
Widget widget = SCROLL_BAR_X_WIDGET (FRAME_X_DISPLAY (f), bar);
float top, shown;
+
+ /* We use an estimate of 30 chars per line rather than the real
+ `portion' value. This has the disadvantage that the thumb size
+ is not very representative, but it makes our life a lot easier.
+ Otherwise, we have to constantly adjust the thumb size, which
+ we can't always do quickly enough: while dragging, the size of
+ the thumb might prevent the user from dragging the thumb all the
+ way to the end. but Motif and some versions of Xaw3d don't allow
+ updating the thumb size while dragging. Also, even if we can update
+ its size, the update will often happen too late.
+ If you don't believe it, check out revision 1.650 of xterm.c to see
+ what hoops we were going through and the still poor behavior we got. */
+ portion = XWINDOW (bar->window)->height * 30;
+ /* When the thumb is at the bottom, position == whole.
+ So we need to increase `whole' to make space for the thumb. */
+ whole += portion;
- if (whole == 0)
+ if (whole <= 0)
top = 0, shown = 1;
else
{
@@ -8818,96 +8797,30 @@
BLOCK_INPUT;
+ if (NILP (bar->dragging))
#ifdef USE_MOTIF
- {
- int size, value;
-
- /* Slider size. Must be in the range [1 .. MAX - MIN] where MAX
- is the scroll bar's maximum and MIN is the scroll bar's minimum
- value. */
- size = shown * XM_SB_RANGE;
- size = min (size, XM_SB_RANGE);
- size = max (size, 1);
-
- /* Position. Must be in the range [MIN .. MAX - SLIDER_SIZE]. */
- value = top * XM_SB_RANGE;
- value = min (value, XM_SB_MAX - size);
- value = max (value, XM_SB_MIN);
+ {
+ int size, value;
- if (NILP (bar->dragging))
+ /* Slider size. Must be in the range [1 .. MAX - MIN] where MAX
+ is the scroll bar's maximum and MIN is the scroll bar's minimum
+ value. */
+ size = shown * XM_SB_RANGE;
+ size = min (size, XM_SB_RANGE);
+ size = max (size, 1);
+
+ /* Position. Must be in the range [MIN .. MAX - SLIDER_SIZE]. */
+ value = top * XM_SB_RANGE;
+ value = min (value, XM_SB_MAX - size);
+ value = max (value, XM_SB_MIN);
+
XmScrollBarSetValues (widget, value, size, 0, 0, False);
- else if (last_scroll_bar_part == scroll_bar_down_arrow)
- /* This has the negative side effect that the slider value is
- not what it would be if we scrolled here using line-wise or
- page-wise movement. */
- XmScrollBarSetValues (widget, value, XM_SB_RANGE - value, 0, 0, False);
- else
- {
- /* If currently dragging, only update the slider size.
- This reduces flicker effects. */
- int old_value, old_size, increment, page_increment;
-
- XmScrollBarGetValues (widget, &old_value, &old_size,
- &increment, &page_increment);
- XmScrollBarSetValues (widget, old_value,
- min (size, XM_SB_RANGE - old_value),
- 0, 0, False);
- }
- }
+ }
#else /* !USE_MOTIF i.e. use Xaw */
- {
- float old_top, old_shown;
- Dimension height;
- XtVaGetValues (widget,
- XtNtopOfThumb, &old_top,
- XtNshown, &old_shown,
- XtNheight, &height,
- NULL);
-
- /* Massage the top+shown values. */
- if (NILP (bar->dragging) || last_scroll_bar_part == scroll_bar_down_arrow)
- top = max (0, min (1, top));
- else
- top = old_top;
- /* Keep two pixels available for moving the thumb down. */
- shown = max (0, min (1 - top - (2.0 / height), shown));
-
/* If the call to XawScrollbarSetThumb below doesn't seem to work,
check that your system's configuration file contains a define
for `NARROWPROTO'. See s/freebsd.h for an example. */
- if (top != old_top || shown != old_shown)
- {
- if (NILP (bar->dragging))
- XawScrollbarSetThumb (widget, top, shown);
- else
- {
-#ifdef HAVE_XAW3D
- ScrollbarWidget sb = (ScrollbarWidget) widget;
- int scroll_mode = 0;
-
- /* `scroll_mode' only exists with Xaw3d + ARROW_SCROLLBAR. */
- if (xaw3d_arrow_scroll)
- {
- /* Xaw3d stupidly ignores resize requests while dragging
- so we have to make it believe it's not in dragging mode. */
- scroll_mode = sb->scrollbar.scroll_mode;
- if (scroll_mode == 2)
- sb->scrollbar.scroll_mode = 0;
- }
-#endif
- /* Try to make the scrolling a tad smoother. */
- if (!xaw3d_pick_top)
- shown = min (shown, old_shown);
-
- XawScrollbarSetThumb (widget, top, shown);
-
-#ifdef HAVE_XAW3D
- if (xaw3d_arrow_scroll && scroll_mode == 2)
- sb->scrollbar.scroll_mode = scroll_mode;
-#endif
- }
- }
- }
+ XawScrollbarSetThumb (widget, top, shown);
#endif /* !USE_MOTIF */
UNBLOCK_INPUT;
@@ -9879,7 +9792,7 @@
EXPECTED is nonzero if the caller knows input is available. */
-int
+static int
XTread_socket (sd, bufp, numchars, expected)
register int sd;
/* register */ struct input_event *bufp;
@@ -14710,7 +14623,6 @@
#ifdef USE_TOOLKIT_SCROLL_BARS
xaw3d_arrow_scroll = False;
- xaw3d_pick_top = True;
#endif
/* Note that there is no real way portable across R3/R4 to get the
[Prev in Thread] |
Current Thread |
[Next in Thread] |
- Re: Emacs + LessTif serious scroll judder when point-max is visible,
Stefan Monnier <=