# HG changeset patch # User Gerd Moellmann # Date 948815713 0 # Node ID c8b20597f0fda03b9d87b274da343bd731cad885 # Parent 0036f90725f61e031ac21819dbc238b318df9b49 (toplevel): Include atimer.h. (toolkit_scroll_bar_interaction): New variable. (Fxt_process_timeouts): Removed. (x_process_timeouts): New function. (xt_action_hook): Clear toolkit_scroll_bar_interaction. (x_send_scroll_bar_event): Set toolkit_scroll_bar_interaction. (x_make_frame_visible): Call poll_for_input_1 instead of input_poll_signal. Don't call alarm. (x_initialize): Install timer calling x_process_timeouts. diff -r 0036f90725f6 -r c8b20597f0fd src/xterm.c --- a/src/xterm.c Tue Jan 25 15:54:07 2000 +0000 +++ b/src/xterm.c Tue Jan 25 15:55:13 2000 +0000 @@ -88,6 +88,7 @@ #include "keyboard.h" #include "intervals.h" #include "process.h" +#include "atimer.h" #ifdef USE_X_TOOLKIT #include @@ -298,6 +299,9 @@ struct cursor_pos output_cursor; +/* Non-zero means user is interacting with a toolkit scroll bar. */ + +static int toolkit_scroll_bar_interaction; /* Mouse movement. @@ -7178,21 +7182,27 @@ } -DEFUN ("xt-process-timeouts", Fxt_process_timeouts, Sxt_process_timeouts, - 0, 0, 0, - "Arrange for Xt timeout callbacks to be called.") - () -{ #ifdef USE_X_TOOLKIT - BLOCK_INPUT; - while (XtAppPending (Xt_app_con) & XtIMTimer) - XtAppProcessEvent (Xt_app_con, XtIMTimer); - UNBLOCK_INPUT; + +/* Atimer callback function for TIMER. Called every 0.1s to process + Xt timeouts, if needed. We must avoid calling XtAppPending as + much as possible because that function does an implicit XFlush + that slows us down. */ + +static void +x_process_timeouts (timer) + struct atimer *timer; +{ + if (toolkit_scroll_bar_interaction || popup_activated_flag) + { + BLOCK_INPUT; + while (XtAppPending (Xt_app_con) & XtIMTimer) + XtAppProcessEvent (Xt_app_con, XtIMTimer); + UNBLOCK_INPUT; + } +} + #endif /* USE_X_TOOLKIT */ - - return Qnil; -} - /* Scroll bar support. */ @@ -7200,6 +7210,7 @@ /* Given an X window ID, find the struct scroll_bar which manages it. This can be called in GC, so we have to make sure to strip off mark bits. */ + static struct scroll_bar * x_window_to_scroll_bar (window_id) Window window_id; @@ -7301,8 +7312,6 @@ end_action = "EndScroll"; #endif /* USE_MOTIF */ - /* Although LessTif uses XtTimeouts like Xaw3d, the timer hack to - let Xt timeouts be processed doesn't work. */ if (scroll_bar_p && strcmp (action_name, end_action) == 0 && WINDOWP (window_being_scrolled)) @@ -7315,6 +7324,9 @@ XSCROLL_BAR (w->vertical_scroll_bar)->dragging = Qnil; window_being_scrolled = Qnil; last_scroll_bar_part = -1; + + /* Xt timeouts no longer needed. */ + toolkit_scroll_bar_interaction = 0; } } @@ -7345,6 +7357,9 @@ ev->data.l[3] = (long) portion; ev->data.l[4] = (long) whole; + /* Make Xt timeouts work while the scroll bar is active. */ + toolkit_scroll_bar_interaction = 1; + /* Setting the event mask to zero means that the message will be sent to the client that created the window, and if that window no longer exists, no event will be sent. */ @@ -11370,8 +11385,10 @@ /* It could be confusing if a real alarm arrives while processing the fake one. Turn it off and let the handler reset it. */ - alarm (0); - input_poll_signal (0); + int old_poll_suppress_count = poll_suppress_count; + poll_suppress_count = 1; + poll_for_input_1 (); + poll_suppress_count = old_poll_suppress_count; } /* See if a MapNotify event has been processed. */ @@ -12918,8 +12935,7 @@ tail = x_display_name_list; while (CONSP (tail) && CONSP (XCDR (tail))) { - if (EQ (XCAR (XCDR (tail)), - dpyinfo->name_list_element)) + if (EQ (XCAR (XCDR (tail)), dpyinfo->name_list_element)) { XCDR (tail) = XCDR (XCDR (tail)); break; @@ -13017,7 +13033,19 @@ XtToolkitInitialize (); Xt_app_con = XtCreateApplicationContext (); XtAppSetFallbackResources (Xt_app_con, Xt_default_resources); -#endif + + /* Install an asynchronous timer that processes Xt timeout events + every 0.1s. This is necessary because some widget sets use + timeouts internally, for example the LessTif menu bar, or the + Xaw3d scroll bar. When Xt timouts aren't processed, these + widgets don't behave normally. */ + { + EMACS_TIME interval; + EMACS_SET_SECS_USECS (interval, 0, 100000); + start_atimer (ATIMER_CONTINUOUS, interval, x_process_timeouts, 0); + } +#endif + #if USE_TOOLKIT_SCROLL_BARS xaw3d_arrow_scroll = False; xaw3d_pick_top = True; @@ -13074,7 +13102,6 @@ x_toolkit_scroll_bars_p = 0; #endif - defsubr (&Sxt_process_timeouts); staticpro (&last_mouse_motion_frame); last_mouse_motion_frame = Qnil; }