1 /* The event_stream interface for X11 with gtk, and/or tty frames.
2 Copyright (C) 1991-5, 1997 Free Software Foundation, Inc.
3 Copyright (C) 1995 Sun Microsystems, Inc.
4 Copyright (C) 1996 Ben Wing.
5 Copyright (C) 2000 William Perry.
7 This file is part of SXEmacs
9 SXEmacs is free software: you can redistribute it and/or modify
10 it under the terms of the GNU General Public License as published by
11 the Free Software Foundation, either version 3 of the License, or
12 (at your option) any later version.
14 SXEmacs is distributed in the hope that it will be useful,
15 but WITHOUT ANY WARRANTY; without even the implied warranty of
16 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 GNU General Public License for more details.
19 You should have received a copy of the GNU General Public License
20 along with this program. If not, see <http://www.gnu.org/licenses/>. */
23 /* This file is heavily based upon event-Xt.c */
25 /* Synched up with: Not in FSF. */
30 #include "console-gtk.h"
32 #include "mem/blocktype.h"
35 #include "ui/console.h"
36 #include "ui/TTY/console-tty.h"
37 #include "events/events.h"
39 #include "objects-gtk.h"
41 #include "ui/redisplay.h"
44 #include "gtk-xemacs.h"
47 #include "sysproc.h" /* for MAXDESC */
51 #include "mule/file-coding.h"
54 #include <gdk/gdkkeysyms.h>
61 # include "ui/menubar.h"
64 #if defined (HAVE_OFFIX_DND)
65 #include "X11/offix.h"
68 #include "events/events-mod.h"
72 static struct event_stream *gtk_event_stream;
74 /* Do we accept events sent by other clients? */
75 int gtk_allow_sendevents;
77 static int process_events_occurred;
78 static int tty_events_occurred;
80 /* Mask of bits indicating the descriptors that we wait for input on */
81 extern SELECT_TYPE input_wait_mask, process_only_mask, tty_only_mask;
83 static Lisp_Object gtk_keysym_to_emacs_keysym();
84 void debug_process_finalization(struct Lisp_Process *p);
85 gboolean emacs_gtk_event_handler(GtkWidget * wid /* unused */ ,
87 gpointer closure /* unused */ );
89 static int last_quit_check_signal_tick_count;
91 Lisp_Object Qkey_mapping;
92 Lisp_Object Qsans_modifiers;
94 void enqueue_gtk_dispatch_event(Lisp_Object event);
97 * Identify if the keysym is a modifier. This implementation mirrors x.org's
98 * IsModifierKey(), but for GDK keysyms.
101 #define IS_MODIFIER_KEY(keysym) \
102 ((((keysym) >= GDK_Shift_L) && ((keysym) <= GDK_Hyper_R)) \
103 || (((keysym) >= GDK_ISO_Lock) && \
104 ((keysym) <= GDK_ISO_Last_Group_Lock)) \
105 || ((keysym) == GDK_Mode_switch) \
106 || ((keysym) == GDK_Num_Lock))
108 #define IS_MODIFIER_KEY(keysym) \
109 ((((keysym) >= GDK_Shift_L) && ((keysym) <= GDK_Hyper_R)) \
110 || ((keysym) == GDK_Mode_switch) \
111 || ((keysym) == GDK_Num_Lock))
115 /************************************************************************/
116 /* magic-event handling */
117 /************************************************************************/
118 static void handle_focus_event_1(struct frame *f, int in_p)
120 /* We don't want to handle the focus change now, because we might
121 be in an accept-process-output, sleep-for, or sit-for. So
124 Actually, we half handle it: we handle it as far as changing the
125 box cursor for redisplay, but we don't call any hooks or do any
126 select-frame stuff until after the sit-for.
130 GTK_WIDGET_SET_FLAGS(FRAME_GTK_TEXT_WIDGET(f), GTK_HAS_FOCUS);
132 GTK_WIDGET_UNSET_FLAGS(FRAME_GTK_TEXT_WIDGET(f), GTK_HAS_FOCUS);
134 gtk_widget_grab_focus(FRAME_GTK_TEXT_WIDGET(f));
135 gtk_widget_draw_focus(FRAME_GTK_TEXT_WIDGET(f));
143 conser = Fcons(frm, Fcons(FRAME_DEVICE(f), in_p ? Qt : Qnil));
146 emacs_handle_focus_change_preliminary(conser);
147 enqueue_magic_eval_event(emacs_handle_focus_change_final,
153 /* both GDK_MAP and GDK_VISIBILITY_NOTIFY can cause this
154 JV is_visible has the same semantics as f->visible*/
155 static void change_frame_visibility(struct frame *f, int is_visible)
161 if (!FRAME_VISIBLE_P(f) && is_visible) {
162 FRAME_VISIBLE_P(f) = is_visible;
163 /* This improves the double flicker when uniconifying a frame
164 some. A lot of it is not showing a buffer which has changed
165 while the frame was iconified. To fix it further requires
166 the good 'ol double redisplay structure. */
167 MARK_FRAME_WINDOWS_STRUCTURE_CHANGED(f);
168 va_run_hook_with_args(Qmap_frame_hook, 1, frame);
169 } else if (FRAME_VISIBLE_P(f) && !is_visible) {
170 FRAME_VISIBLE_P(f) = 0;
171 va_run_hook_with_args(Qunmap_frame_hook, 1, frame);
172 } else if (FRAME_VISIBLE_P(f) * is_visible < 0) {
173 FRAME_VISIBLE_P(f) = -FRAME_VISIBLE_P(f);
174 if (FRAME_REPAINT_P(f))
175 MARK_FRAME_WINDOWS_STRUCTURE_CHANGED(f);
176 va_run_hook_with_args(Qmap_frame_hook, 1, frame);
180 static void handle_map_event(struct frame *f, GdkEvent * event)
185 if (event->any.type == GDK_MAP) {
186 FRAME_GTK_TOTALLY_VISIBLE_P(f) = 1;
187 change_frame_visibility(f, 1);
189 FRAME_GTK_TOTALLY_VISIBLE_P(f) = 0;
190 change_frame_visibility(f, 0);
191 /* Calling Fframe_iconified_p is the only way we have to
192 correctly update FRAME_ICONIFIED_P */
193 Fframe_iconified_p(frame);
197 static void handle_client_message(struct frame *f, GdkEvent * event)
203 /* The event-Xt code used to handle WM_DELETE_WINDOW here, but we
204 handle that directly in frame-gtk.c */
206 if (event->client.message_type == gdk_atom_intern("WM_PROTOCOLS", 0) &&
207 (GdkAtom) event->client.data.l[0] ==
208 gdk_atom_intern("WM_TAKE_FOCUS", 0)) {
209 handle_focus_event_1(f, 1);
213 static void emacs_gtk_handle_magic_event(struct Lisp_Event *emacs_event)
215 /* This function can GC */
216 GdkEvent *event = &emacs_event->event.magic.underlying_gdk_event;
217 struct frame *f = XFRAME(EVENT_CHANNEL(emacs_event));
219 if (!FRAME_LIVE_P(f))
222 switch (event->any.type) {
223 case GDK_CLIENT_EVENT:
224 handle_client_message(f, event);
227 case GDK_FOCUS_CHANGE:
228 handle_focus_event_1(f, event->focus_change.in);
233 handle_map_event(f, event);
236 case GDK_ENTER_NOTIFY:
237 if (event->crossing.detail != GDK_NOTIFY_INFERIOR) {
241 /* FRAME_X_MOUSE_P (f) = 1; */
242 va_run_hook_with_args(Qmouse_enter_frame_hook, 1,
247 case GDK_LEAVE_NOTIFY:
248 if (event->crossing.detail != GDK_NOTIFY_INFERIOR) {
252 /* FRAME_X_MOUSE_P (f) = 0; */
253 va_run_hook_with_args(Qmouse_leave_frame_hook, 1,
258 case GDK_VISIBILITY_NOTIFY: /* window visiblity has changed */
259 if (event->visibility.window ==
260 GET_GTK_WIDGET_WINDOW(FRAME_GTK_SHELL_WIDGET(f))) {
261 FRAME_GTK_TOTALLY_VISIBLE_P(f) =
262 (event->visibility.state ==
263 GDK_VISIBILITY_UNOBSCURED);
264 /* Note that the fvwm pager only sends VisibilityNotify when
265 changing pages. Is this all we need to do ? JV */
266 /* Nope. We must at least trigger a redisplay here.
267 Since this case seems similar to MapNotify, I've
268 factored out some code to change_frame_visibility().
269 This triggers the necessary redisplay and runs
270 (un)map-frame-hook. - dkindred@cs.cmu.edu */
271 /* Changed it again to support the tristate visibility flag */
272 change_frame_visibility(f, (event->visibility.state
274 GDK_VISIBILITY_FULLY_OBSCURED)
284 /************************************************************************/
285 /* Gtk to Emacs event conversion */
286 /************************************************************************/
288 static int keysym_obeys_caps_lock_p(guint sym, struct device *d)
290 struct gtk_device *gd = DEVICE_GTK_DATA(d);
291 /* Eeeeevil hack. Don't apply Caps_Lock to things that aren't alphabetic
292 characters, where "alphabetic" means something more than simply A-Z.
293 That is, if Caps_Lock is down, typing ESC doesn't produce Shift-ESC.
294 But if shift-lock is down, then it does. */
295 if (gd->lock_interpretation == GDK_Shift_Lock)
299 ((sym >= GDK_A) && (sym <= GDK_Z)) ||
300 ((sym >= GDK_a) && (sym <= GDK_z)) ||
301 ((sym >= GDK_Agrave) && (sym <= GDK_Odiaeresis)) ||
302 ((sym >= GDK_agrave) && (sym <= GDK_odiaeresis)) ||
303 ((sym >= GDK_Ooblique) && (sym <= GDK_Thorn)) ||
304 ((sym >= GDK_oslash) && (sym <= GDK_thorn));
307 static void set_last_server_timestamp(struct device *d, GdkEvent * gdk_event)
310 switch (gdk_event->type) {
312 case GDK_KEY_RELEASE:
313 t = gdk_event->key.time;
315 case GDK_BUTTON_PRESS:
316 case GDK_2BUTTON_PRESS:
317 case GDK_3BUTTON_PRESS:
318 case GDK_BUTTON_RELEASE:
319 t = gdk_event->button.time;
321 case GDK_ENTER_NOTIFY:
322 case GDK_LEAVE_NOTIFY:
323 t = gdk_event->crossing.time;
325 case GDK_MOTION_NOTIFY:
326 t = gdk_event->motion.time;
328 case GDK_PROPERTY_NOTIFY:
329 t = gdk_event->property.time;
331 case GDK_SELECTION_CLEAR:
332 case GDK_SELECTION_REQUEST:
333 case GDK_SELECTION_NOTIFY:
334 t = gdk_event->selection.time;
339 DEVICE_GTK_LAST_SERVER_TIMESTAMP(d) = t;
342 static Lisp_Object gtk_keysym_to_emacs_keysym(guint keysym, int simple_p)
345 if (keysym >= GDK_exclam && keysym <= GDK_asciitilde)
346 /* We must assume that the X keysym numbers for the ASCII graphic
347 characters are the same as their ASCII codes. */
348 return make_char(keysym);
351 /* These would be handled correctly by the default case, but by
352 special-casing them here we don't garbage a string or call
373 /* !!#### not Mule-ized */
374 name = gdk_keyval_name(keysym);
375 if (!name || !name[0])
376 /* This happens if there is a mismatch between the Xlib of
377 SXEmacs and the Xlib of the X server...
379 Let's hard-code in some knowledge of common keysyms introduced
380 in recent X11 releases. Snarfed from X11/keysymdef.h
382 Probably we should add some stuff here for X11R6. */
385 return KEYSYM("kp-home");
387 return KEYSYM("kp-left");
389 return KEYSYM("kp-up");
391 return KEYSYM("kp-right");
393 return KEYSYM("kp-down");
395 return KEYSYM("kp-prior");
397 return KEYSYM("kp-next");
399 return KEYSYM("kp-end");
401 return KEYSYM("kp-begin");
403 return KEYSYM("kp-insert");
405 return KEYSYM("kp-delete");
408 return KEYSYM("SunF36"); /* labeled F11 */
410 return KEYSYM("SunF37"); /* labeled F12 */
414 int sz = snprintf(buf, sizeof(buf),
415 "unknown-keysym-0x%X",
417 assert(sz >= 0 && sz < sizeof(buf));
421 /* If it's got a one-character name, that's good enough. */
423 return make_char(name[0]);
425 /* If it's in the "Keyboard" character set, downcase it.
426 The case of those keysyms is too totally random for us to
427 force anyone to remember them.
428 The case of the other character sets is significant, however.
430 if ((((unsigned int)keysym) & (~0x1FF)) ==
431 ((unsigned int)0xFE00)) {
434 for (s1 = name, s2 = buf; *s1; s1++, s2++) {
438 *s2 = tolower(*(unsigned char *)s1);
449 gtk_to_emacs_keysym(struct device *d, GdkEventKey * event, int simple_p)
450 /* simple_p means don't try too hard (ASCII only) */
452 if (event->length != 1) {
454 /* Generate multiple emacs events */
456 Lisp_Object instream, fb_instream;
458 struct gcpro gcpro1, gcpro2;
461 make_fixed_buffer_input_stream((unsigned char *)event->
462 string, event->length);
464 /* ### Use Fget_coding_system (Vcomposed_input_coding_system) */
466 make_decoding_input_stream(XLSTREAM(fb_instream),
467 Fget_coding_system(Qundecided));
469 istr = XLSTREAM(instream);
471 GCPRO2(instream, fb_instream);
472 while ((ch = Lstream_get_emchar(istr)) != EOF) {
473 Lisp_Object emacs_event = Fmake_event(Qnil, Qnil);
474 struct Lisp_Event *ev = XEVENT(emacs_event);
475 ev->channel = DEVICE_CONSOLE(d);
476 ev->event_type = key_press_event;
477 ev->timestamp = event->time;
478 ev->event.key.modifiers = 0;
479 ev->event.key.keysym = make_char(ch);
480 enqueue_gtk_dispatch_event(emacs_event);
484 Lstream_delete(istr);
485 Lstream_delete(XLSTREAM(fb_instream));
488 for (i = 0; i < event->length; i++) {
489 Lisp_Object emacs_event = Fmake_event(Qnil, Qnil);
490 struct Lisp_Event *ev = XEVENT(emacs_event);
491 ev->channel = DEVICE_CONSOLE(d);
492 ev->event_type = key_press_event;
493 ev->timestamp = event->time;
494 ev->event.key.modifiers = 0;
495 ev->event.key.keysym = make_char(event->string[i]);
496 enqueue_gtk_dispatch_event(emacs_event);
499 if (IS_MODIFIER_KEY(event->keyval)
500 || (event->keyval == GDK_Mode_switch))
502 return (gtk_keysym_to_emacs_keysym(event->keyval, simple_p));
504 if (IS_MODIFIER_KEY(event->keyval)
505 || (event->keyval == GDK_Mode_switch))
507 return (gtk_keysym_to_emacs_keysym(event->keyval, simple_p));
511 /************************************************************************/
513 /************************************************************************/
515 static int timeout_id_tick;
520 struct GTK_timeout *next;
521 } *pending_timeouts, *completed_timeouts;
523 struct GTK_timeout_blocktype {
524 Blocktype_declare(struct GTK_timeout);
525 } *the_GTK_timeout_blocktype;
527 /* called by the gtk main loop */
528 static gint gtk_timeout_callback(gpointer closure)
530 struct GTK_timeout *timeout = (struct GTK_timeout *)closure;
531 struct GTK_timeout *t2 = pending_timeouts;
533 /* Remove this one from the list of pending timeouts */
535 pending_timeouts = pending_timeouts->next;
537 while (t2->next && t2->next != timeout)
540 t2->next = t2->next->next;
542 /* Add this one to the list of completed timeouts */
543 timeout->next = completed_timeouts;
544 completed_timeouts = timeout;
548 static int emacs_gtk_add_timeout(EMACS_TIME thyme)
550 struct GTK_timeout *timeout =
551 Blocktype_alloc(the_GTK_timeout_blocktype);
552 EMACS_TIME current_time;
555 timeout->id = timeout_id_tick++;
556 timeout->next = pending_timeouts;
557 pending_timeouts = timeout;
558 EMACS_GET_TIME(current_time);
559 EMACS_SUB_TIME(thyme, thyme, current_time);
560 milliseconds = EMACS_SECS(thyme) * 1000 + EMACS_USECS(thyme) / 1000;
561 if (milliseconds < 1)
563 timeout->timeout_id = gtk_timeout_add(milliseconds,
564 gtk_timeout_callback,
569 static void emacs_gtk_remove_timeout(int id)
571 struct GTK_timeout *timeout, *t2;
575 /* Find the timeout on the list of pending ones, if it's still there. */
576 if (pending_timeouts) {
577 if (id == pending_timeouts->id) {
578 timeout = pending_timeouts;
579 pending_timeouts = pending_timeouts->next;
581 t2 = pending_timeouts;
582 while (t2->next && t2->next->id != id)
584 if (t2->next) { /*found it */
586 t2->next = t2->next->next;
589 /* if it was pending, we have removed it from the list */
591 gtk_timeout_remove(timeout->timeout_id);
594 /* It could be that the call back was already called but we didn't convert
595 into an Emacs event yet */
596 if (!timeout && completed_timeouts) {
597 /* Code duplication! */
598 if (id == completed_timeouts->id) {
599 timeout = completed_timeouts;
600 completed_timeouts = completed_timeouts->next;
602 t2 = completed_timeouts;
603 while (t2->next && t2->next->id != id)
605 if (t2->next) { /*found it */
607 t2->next = t2->next->next;
612 /* If we found the thing on the lists of timeouts,
613 and removed it, deallocate
616 Blocktype_free(the_GTK_timeout_blocktype, timeout);
619 static void gtk_timeout_to_emacs_event(struct Lisp_Event *emacs_event)
621 struct GTK_timeout *timeout = completed_timeouts;
623 completed_timeouts = completed_timeouts->next;
624 emacs_event->event_type = timeout_event;
625 /* timeout events have nil as channel */
626 emacs_event->timestamp = 0; /* #### wrong!! */
627 emacs_event->event.timeout.interval_id = timeout->id;
628 Blocktype_free(the_GTK_timeout_blocktype, timeout);
631 /************************************************************************/
632 /* process and tty events */
633 /************************************************************************/
635 struct what_is_ready_closure {
641 static Lisp_Object *filedesc_with_input;
642 static struct what_is_ready_closure **filedesc_to_what_closure;
644 static void init_what_input_once(void)
648 filedesc_with_input = xnew_array(Lisp_Object, MAXDESC);
649 filedesc_to_what_closure =
650 xnew_array(struct what_is_ready_closure *, MAXDESC);
652 for (i = 0; i < MAXDESC; i++) {
653 filedesc_to_what_closure[i] = 0;
654 filedesc_with_input[i] = Qnil;
657 process_events_occurred = 0;
658 tty_events_occurred = 0;
661 static void mark_what_as_being_ready(struct what_is_ready_closure *closure)
663 if (NILP(filedesc_with_input[closure->fd])) {
664 SELECT_TYPE temp_mask;
666 FD_SET(closure->fd, &temp_mask);
667 /* Check to make sure there's *really* input available.
668 Sometimes things seem to get confused and this gets called
669 for the tty fd when there's really only input available
670 on some process's fd. (It will subsequently get called
671 for that process's fd, so returning without setting any
672 flags will take care of it.) To see the problem, uncomment
673 the stderr_out below, turn NORMAL_QUIT_CHECK_TIMEOUT_MSECS
674 down to 25, do sh -c 'sxemacs -nw -q -f shell 2>/tmp/log'
675 and press return repeatedly. (Seen under AIX & Linux.)
676 -dkindred@cs.cmu.edu */
677 if (!poll_fds_for_input(temp_mask)) {
680 ("mark_what_as_being_ready: no input available (fd=%d)\n",
685 filedesc_with_input[closure->fd] = closure->what;
686 if (PROCESSP(closure->what)) {
687 /* Don't increment this if the current process is already marked
688 * as having input. */
689 process_events_occurred++;
691 tty_events_occurred++;
697 gtk_what_callback(gpointer closure, gint source, GdkInputCondition why)
699 /* If closure is 0, then we got a fake event from a signal handler.
700 The only purpose of this is to make XtAppProcessEvent() stop
703 mark_what_as_being_ready((struct what_is_ready_closure *)
706 fake_event_occurred++;
707 drain_signal_event_pipe();
711 static void select_filedesc(int fd, Lisp_Object what)
713 struct what_is_ready_closure *closure;
715 /* If somebody is trying to select something that's already selected
716 for, then something went wrong. The generic routines ought to
717 detect this and error before here. */
718 assert(!filedesc_to_what_closure[fd]);
720 closure = xnew(struct what_is_ready_closure);
722 closure->what = what;
723 closure->id = gdk_input_add(fd, GDK_INPUT_READ,
724 (GdkInputFunction) gtk_what_callback,
726 filedesc_to_what_closure[fd] = closure;
729 static void unselect_filedesc(int fd)
731 struct what_is_ready_closure *closure = filedesc_to_what_closure[fd];
734 if (!NILP(filedesc_with_input[fd])) {
735 /* We are unselecting this process before we have drained the rest of
736 the input from it, probably from status_notify() in the command loop.
737 This can happen like so:
739 - We are waiting in XtAppNextEvent()
740 - Process generates output
741 - Process is marked as being ready
742 - Process dies, SIGCHLD gets generated before we return (!?)
743 It could happen I guess.
744 - sigchld_handler() marks process as dead
745 - Somehow we end up getting a new KeyPress event on the queue
746 at the same time (I'm really so sure how that happens but I'm
747 not sure it can't either so let's assume it can...).
748 - Key events have priority so we return that instead of the proc.
749 - Before dispatching the lisp key event we call status_notify()
750 - Which deselects the process that SIGCHLD marked as dead.
752 Thus we never remove it from _with_input and turn it into a lisp
753 event, so we need to do it here. But this does not mean that we're
754 throwing away the last block of output - status_notify() has already
755 taken care of running the proc filter or whatever.
757 filedesc_with_input[fd] = Qnil;
758 if (PROCESSP(closure->what)) {
759 assert(process_events_occurred > 0);
760 process_events_occurred--;
762 assert(tty_events_occurred > 0);
763 tty_events_occurred--;
766 gdk_input_remove(closure->id);
768 filedesc_to_what_closure[fd] = 0;
771 static void emacs_gtk_select_process(struct Lisp_Process *p)
774 int infd = event_stream_unixoid_select_process(p);
776 XSETPROCESS(process, p);
777 select_filedesc(infd, process);
780 static void emacs_gtk_unselect_process(struct Lisp_Process *p)
782 int infd = event_stream_unixoid_unselect_process(p);
784 unselect_filedesc(infd);
788 emacs_gtk_create_stream_pair(void *inhandle, void *outhandle,
789 Lisp_Object * instream, Lisp_Object * outstream,
792 USID u = event_stream_unixoid_create_stream_pair
793 (inhandle, outhandle, instream, outstream, flags);
800 emacs_gtk_delete_stream_pair(Lisp_Object instream, Lisp_Object outstream)
802 event_stream_unixoid_delete_stream_pair(instream, outstream);
803 return USID_DONTHASH;
806 /* This is called from GC when a process object is about to be freed.
807 If we've still got pointers to it in this file, we're gonna lose hard.
809 void debug_process_finalization(struct Lisp_Process *p)
813 Lisp_Object instr, outstr;
815 get_process_streams(p, &instr, &outstr);
816 /* if it still has fds, then it hasn't been killed yet. */
818 assert(NILP(outstr));
819 /* Better not still be in the "with input" table; we know it's got no fds. */
820 for (i = 0; i < MAXDESC; i++) {
821 Lisp_Object process = filedesc_fds_with_input[i];
822 assert(!PROCESSP(process) || XPROCESS(process) != p);
827 static void gtk_process_to_emacs_event(struct Lisp_Event *emacs_event)
832 assert(process_events_occurred > 0);
833 for (i = 0; i < MAXDESC; i++) {
834 process = filedesc_with_input[i];
835 if (PROCESSP(process))
839 filedesc_with_input[i] = Qnil;
840 process_events_occurred--;
841 /* process events have nil as channel */
842 emacs_event->event_type = process_event;
843 emacs_event->timestamp = 0; /* #### */
844 emacs_event->event.process.process = process;
847 static void emacs_gtk_select_console(struct console *con)
852 if (CONSOLE_GTK_P(con))
853 return; /* Gtk consoles are automatically selected for when we initialize them */
854 infd = event_stream_unixoid_select_console(con);
855 XSETCONSOLE(console, con);
856 select_filedesc(infd, console);
859 static void emacs_gtk_unselect_console(struct console *con)
864 if (CONSOLE_GTK_P(con))
865 return; /* X consoles are automatically selected for when we initialize them */
866 infd = event_stream_unixoid_unselect_console(con);
867 XSETCONSOLE(console, con);
868 unselect_filedesc(infd);
871 /* read an event from a tty, if one is available. Returns non-zero
872 if an event was available. Note that when this function is
873 called, there should always be a tty marked as ready for input.
874 However, the input condition might actually be EOF, so there
875 may not really be any input available. (In this case,
876 read_event_from_tty_or_stream_desc() will arrange for the TTY device
879 static int gtk_tty_to_emacs_event(struct Lisp_Event *emacs_event)
883 assert(tty_events_occurred > 0);
884 for (i = 0; i < MAXDESC; i++) {
885 Lisp_Object console = filedesc_with_input[i];
886 if (CONSOLEP(console)) {
887 assert(tty_events_occurred > 0);
888 tty_events_occurred--;
889 filedesc_with_input[i] = Qnil;
890 if (read_event_from_tty_or_stream_desc
891 (emacs_event, XCONSOLE(console), i))
899 /************************************************************************/
900 /* Drag 'n Drop handling */
901 /************************************************************************/
902 #ifdef HAVE_DRAGNDROP
903 #define TARGET_URI_LIST 0x00
904 #define TARGET_TEXT_PLAIN 0x01
905 #define TARGET_FILE_NAME 0x02
906 #define TARGET_NETSCAPE 0x03
908 static GdkAtom preferred_targets[10];
911 dragndrop_data_received(GtkWidget * widget,
912 GdkDragContext * context,
914 gint y, GtkSelectionData * data, guint info, guint time)
916 Lisp_Object event = Fmake_event(Qnil, Qnil);
917 struct device *d = gtk_any_window_to_device(widget->window);
918 struct frame *f = gtk_any_widget_or_parent_to_frame(d, widget);
919 struct Lisp_Event *ev = XEVENT(event);
920 Lisp_Object l_type = Qnil, l_data = Qnil;
921 Lisp_Object l_dndlist = Qnil, l_item = Qnil;
922 struct gcpro gcpro1, gcpro2, gcpro3, gcpro4;
924 GCPRO4(l_type, l_data, l_dndlist, l_item);
926 ev->event_type = misc_user_event;
927 ev->timestamp = time;
929 XSETFRAME(ev->channel, f);
931 ev->event.misc.x = x;
932 ev->event.misc.y = y;
934 if (data->type == preferred_targets[TARGET_URI_LIST]) {
935 /* newline-separated list of URLs */
937 const char *string_data = (char *)data->data;
939 l_type = Qdragdrop_URL;
941 for (start = 0, end = 0; string_data && string_data[end]; end++) {
942 if ((string_data[end] == '\r')
943 && (string_data[end + 1] == '\n')) {
945 make_string(&string_data[start],
947 l_dndlist = Fcons(l_item, l_dndlist);
952 } else if (data->type == preferred_targets[TARGET_TEXT_PLAIN]) {
953 /* Arbitrary string */
954 l_type = Qdragdrop_MIME;
955 l_dndlist = list1(list3(list1(build_string("text/plain")),
956 build_string("8_bit"),
957 make_ext_string(data->data,
958 strlen((char *)data->
960 } else if (data->type == preferred_targets[TARGET_FILE_NAME]) {
961 /* Random filename */
962 char *hurl = dnd_url_hexify_string(data->data, "file:");
964 l_dndlist = list1(make_string((Bufbyte *) hurl, strlen(hurl)));
965 l_type = Qdragdrop_URL;
968 } else if (data->type == preferred_targets[TARGET_NETSCAPE]) {
970 l_dndlist = list1(make_string((Extbyte *) data->data,
971 strlen((char *)data->data)));
972 l_type = Qdragdrop_URL;
974 /* Unknown type - what to do?
975 We just pass it up to lisp - we already have a mime type.
977 l_type = Qdragdrop_MIME;
980 (list1(build_string(gdk_atom_name(data->type))),
981 build_string("8bit"),
982 make_ext_string((Extbyte *) data->data, data->length,
986 ev->event.misc.function = Qdragdrop_drop_dispatch;
987 ev->event.misc.object = Fcons(l_type, l_dndlist);
991 gtk_drag_finish(context, TRUE, FALSE, time);
992 enqueue_gtk_dispatch_event(event);
996 dragndrop_dropped(GtkWidget * widget,
997 GdkDragContext * drag_context,
998 gint x, gint y, guint time, gpointer user_data)
1000 /* Netscape drops things like:
1008 gmc drops things like
1009 application/x-mc-desktop-icon
1022 GList *list = drag_context->targets;
1026 if (!preferred_targets[0]) {
1027 preferred_targets[TARGET_URI_LIST] =
1028 gdk_atom_intern("text/uri-list", FALSE);
1029 preferred_targets[TARGET_TEXT_PLAIN] =
1030 gdk_atom_intern("text/plain", FALSE);
1031 preferred_targets[TARGET_FILE_NAME] =
1032 gdk_atom_intern("FILE_NAME", FALSE);
1033 preferred_targets[TARGET_NETSCAPE] =
1034 gdk_atom_intern("_NETSCAPE_URL", FALSE);
1037 stderr_out("Drop info available in the following formats: \n");
1039 stderr_out("\t%s\n", gdk_atom_name((GdkAtom) list->data));
1042 list = drag_context->targets;
1045 while (list && !found) {
1046 for (i = 0; preferred_targets[i] && !found; i++) {
1047 if ((GdkAtom) list->data == preferred_targets[i]) {
1048 found = (GdkAtom) list->data;
1055 found = (GdkAtom) drag_context->targets->data;
1058 gtk_drag_get_data(GTK_WIDGET(user_data), drag_context, found, time);
1061 #endif /* HAVE_DRAGNDROP */
1063 /************************************************************************/
1064 /* get the next event from gtk */
1065 /************************************************************************/
1067 static Lisp_Object dispatch_event_queue, dispatch_event_queue_tail;
1069 void enqueue_gtk_dispatch_event(Lisp_Object event)
1071 enqueue_event(event, &dispatch_event_queue, &dispatch_event_queue_tail);
1074 static Lisp_Object dequeue_gtk_dispatch_event(void)
1076 return dequeue_event(&dispatch_event_queue, &dispatch_event_queue_tail);
1079 /* This business exists because menu events "happen" when
1080 menubar_selection_callback() is called from somewhere deep
1081 within XtAppProcessEvent in emacs_Xt_next_event(). The
1082 callback needs to terminate the modal loop in that function
1083 or else it will continue waiting until another event is
1086 Same business applies to scrollbar events. */
1089 signal_special_gtk_user_event(Lisp_Object channel, Lisp_Object function,
1092 Lisp_Object event = Fmake_event(Qnil, Qnil);
1094 XEVENT(event)->event_type = misc_user_event;
1095 XEVENT(event)->channel = channel;
1096 XEVENT(event)->event.eval.function = function;
1097 XEVENT(event)->event.eval.object = object;
1099 enqueue_gtk_dispatch_event(event);
1102 static void emacs_gtk_next_event(struct Lisp_Event *emacs_event)
1104 we_didnt_get_an_event:
1106 while (NILP(dispatch_event_queue) &&
1107 !completed_timeouts &&
1108 !fake_event_occurred &&
1109 !process_events_occurred && !tty_events_occurred) {
1110 gtk_main_iteration();
1113 if (!NILP(dispatch_event_queue)) {
1114 Lisp_Object event, event2;
1115 XSETEVENT(event2, emacs_event);
1116 event = dequeue_gtk_dispatch_event();
1117 Fcopy_event(event, event2);
1118 Fdeallocate_event(event);
1119 } else if (tty_events_occurred) {
1120 if (!gtk_tty_to_emacs_event(emacs_event))
1121 goto we_didnt_get_an_event;
1122 } else if (completed_timeouts)
1123 gtk_timeout_to_emacs_event(emacs_event);
1124 else if (fake_event_occurred) {
1125 /* A dummy event, so that a cycle of the command loop will occur. */
1126 fake_event_occurred = 0;
1127 /* eval events have nil as channel */
1128 emacs_event->event_type = eval_event;
1129 emacs_event->event.eval.function = Qidentity;
1130 emacs_event->event.eval.object = Qnil;
1131 } else /* if (process_events_occurred) */
1132 gtk_process_to_emacs_event(emacs_event);
1136 gtk_event_to_emacs_event(struct frame *frame, GdkEvent * gdk_event,
1137 struct Lisp_Event *emacs_event)
1139 struct device *d = NULL;
1140 struct gtk_device *gd = NULL;
1141 gboolean accept_any_window = FALSE;
1144 frame = XFRAME(Fselected_frame(Vdefault_gtk_device));
1145 accept_any_window = TRUE;
1148 d = XDEVICE(FRAME_DEVICE(frame));
1149 gd = DEVICE_GTK_DATA(d);
1151 set_last_server_timestamp(d, gdk_event);
1153 switch (gdk_event->type) {
1154 /* SXEmacs handles double and triple clicking on its own, and if
1155 we capture these events, it royally confuses the code in
1157 case GDK_2BUTTON_PRESS:
1158 case GDK_3BUTTON_PRESS:
1161 case GDK_BUTTON_PRESS:
1162 case GDK_BUTTON_RELEASE:
1163 /* We need to ignore button events outside our main window or
1164 things get ugly. The standard scrollbars in Gtk try to be
1165 nice and pass the button press events up to the parent
1166 widget. This causes us no end of grief though. Effects
1167 range from setting point to the wrong place to selecting
1170 GdkWindow *w = gdk_window_at_pointer(NULL, NULL);
1172 /* If you press mouse button and drag it around, and release
1173 it outside the window, you will get a NULL GdkWindow at
1174 pointer. We need to forward these events on to SXEmacs so
1175 that the mouse selection voodoo works.
1177 if (w && (w != gdk_window_lookup(GDK_ROOT_WINDOW()))) {
1179 GtkWidget *wid = NULL;
1182 wid = gtk_get_event_widget(&ev);
1184 if (!GTK_IS_XEMACS(wid) && !accept_any_window) {
1188 if (!accept_any_window)
1189 gtk_widget_grab_focus(FRAME_GTK_TEXT_WIDGET
1195 unsigned int modifiers = 0;
1196 int shift_p, lock_p;
1197 gboolean key_event_p =
1198 (gdk_event->type == GDK_KEY_PRESS);
1199 unsigned int *state =
1200 key_event_p ? &gdk_event->key.state : &gdk_event->
1203 /* If this is a synthetic KeyPress or Button event, and the user
1204 has expressed a disinterest in this security hole, then drop
1206 /* #### BILL!!! Should this be a generic check for ANY synthetic
1208 if ((gdk_event->any.send_event)
1209 && !gtk_allow_sendevents)
1212 DEVICE_GTK_MOUSE_TIMESTAMP(d) =
1213 DEVICE_GTK_GLOBAL_MOUSE_TIMESTAMP(d) =
1214 key_event_p ? gdk_event->key.time : gdk_event->
1217 if (*state & GDK_CONTROL_MASK)
1218 modifiers |= XEMACS_MOD_CONTROL;
1219 if (*state & gd->MetaMask)
1220 modifiers |= XEMACS_MOD_META;
1221 if (*state & gd->SuperMask)
1222 modifiers |= XEMACS_MOD_SUPER;
1223 if (*state & gd->HyperMask)
1224 modifiers |= XEMACS_MOD_HYPER;
1225 if (*state & gd->AltMask)
1226 modifiers |= XEMACS_MOD_ALT;
1229 int numero_de_botao = -1;
1233 gdk_event->button.button;
1235 /* the button gets noted either in the button or the modifiers
1236 field, but not both. */
1237 if (numero_de_botao != 1
1238 && (*state & GDK_BUTTON1_MASK))
1239 modifiers |= XEMACS_MOD_BUTTON1;
1240 if (numero_de_botao != 2
1241 && (*state & GDK_BUTTON2_MASK))
1242 modifiers |= XEMACS_MOD_BUTTON2;
1243 if (numero_de_botao != 3
1244 && (*state & GDK_BUTTON3_MASK))
1245 modifiers |= XEMACS_MOD_BUTTON3;
1246 if (numero_de_botao != 4
1247 && (*state & GDK_BUTTON4_MASK))
1248 modifiers |= XEMACS_MOD_BUTTON4;
1249 if (numero_de_botao != 5
1250 && (*state & GDK_BUTTON5_MASK))
1251 modifiers |= XEMACS_MOD_BUTTON5;
1254 /* Ignore the Caps_Lock key if:
1255 - any other modifiers are down, so that Caps_Lock doesn't
1256 turn C-x into C-X, which would suck.
1257 - the event was a mouse event. */
1258 if (modifiers || !key_event_p)
1259 *state &= (~GDK_LOCK_MASK);
1261 shift_p = *state & GDK_SHIFT_MASK;
1262 lock_p = *state & GDK_LOCK_MASK;
1264 if (shift_p || lock_p)
1265 modifiers |= XEMACS_MOD_SHIFT;
1268 GdkEventKey *key_event = &gdk_event->key;
1271 #ifdef HAVE_MENUBARS
1272 /* If the user wants see if the event is a menu bar accelerator.
1273 The process of checking absorbs the event and starts menu
1274 processing so send a null event into XEmacs to make sure it
1277 if (!NILP(Vmenu_accelerator_enabled)
1279 gtk_accel_groups_activate(GTK_OBJECT
1280 (FRAME_GTK_SHELL_WIDGET
1284 zero_event(emacs_event);
1289 /* This used to compute the frame from the given X window and
1290 store it here, but we really don't care about the frame. */
1291 emacs_event->channel = DEVICE_CONSOLE(d);
1293 /* Keysym mucking has already been done inside the
1294 GdkEventKey parsing */
1295 keysym = gtk_to_emacs_keysym(d, key_event, 0);
1297 /* If the emacs keysym is nil, then that means that the X
1298 keysym was either a Modifier or NoSymbol, which
1299 probably means that we're in the midst of reading a
1300 Multi_key sequence, or a "dead" key prefix, or XIM
1301 input. Ignore it. */
1305 /* More Caps_Lock garbage: Caps_Lock should *only* add the
1306 shift modifier to two-case keys (that is, A-Z and
1307 related characters). So at this point (after looking up
1308 the keysym) if the keysym isn't a dual-case alphabetic,
1309 and if the caps lock key was down but the shift key
1310 wasn't, then turn off the shift modifier. Gag barf */
1311 /* #### type lossage: assuming equivalence of emacs and
1313 /* !!#### maybe fix for Mule */
1314 if (lock_p && !shift_p &&
1315 !(CHAR_OR_CHAR_INTP(keysym)
1316 && keysym_obeys_caps_lock_p
1317 ((guint) XCHAR_OR_CHAR_INT(keysym), d)))
1318 modifiers &= (~XEMACS_MOD_SHIFT);
1320 /* If this key contains two distinct keysyms, that is,
1321 "shift" generates a different keysym than the
1322 non-shifted key, then don't apply the shift modifier
1323 bit: it's implicit. Otherwise, if there would be no
1324 other way to tell the difference between the shifted
1325 and unshifted version of this key, apply the shift bit.
1326 Non-graphics, like Backspace and F1 get the shift bit
1327 in the modifiers slot. Neither the characters "a",
1328 "A", "2", nor "@" normally have the shift bit set.
1329 However, "F1" normally does. */
1330 if (modifiers & XEMACS_MOD_SHIFT) {
1331 if (CHAR_OR_CHAR_INTP(keysym)) {
1332 modifiers &= ~XEMACS_MOD_SHIFT;
1336 emacs_event->event_type = key_press_event;
1337 emacs_event->timestamp = key_event->time;
1338 emacs_event->event.key.modifiers = modifiers;
1339 emacs_event->event.key.keysym = keysym;
1340 } else { /* Mouse press/release event */
1342 GdkEventButton *button_event =
1344 XSETFRAME(emacs_event->channel, frame);
1346 emacs_event->event_type =
1347 (button_event->type ==
1348 GDK_BUTTON_RELEASE) ? button_release_event
1349 : button_press_event;
1351 emacs_event->event.button.modifiers = modifiers;
1352 emacs_event->timestamp = button_event->time;
1353 emacs_event->event.button.button =
1354 button_event->button;
1355 emacs_event->event.button.x = button_event->x;
1356 emacs_event->event.button.y = button_event->y;
1360 case GDK_KEY_RELEASE:
1363 case GDK_MOTION_NOTIFY:
1365 GdkEventMotion *ev = &gdk_event->motion;
1366 unsigned int modifiers = 0;
1368 GdkModifierType mask;
1370 /* We use MOTION_HINT_MASK, so we will get only one motion
1371 event until the next time we call gdk_window_get_pointer or
1372 the user clicks the mouse. So call gdk_window_get_pointer
1373 now (meaning that the event will be in sync with the server
1374 just before Fnext_event() returns). If the mouse is still
1375 in motion, then the server will immediately generate
1376 exactly one more motion event, which will be on the queue
1377 waiting for us next time around. */
1378 gdk_window_get_pointer(ev->window, &x, &y, &mask);
1380 DEVICE_GTK_MOUSE_TIMESTAMP(d) = ev->time;
1382 XSETFRAME(emacs_event->channel, frame);
1383 emacs_event->event_type = pointer_motion_event;
1384 emacs_event->timestamp = ev->time;
1385 emacs_event->event.motion.x = x;
1386 emacs_event->event.motion.y = y;
1387 if (mask & GDK_SHIFT_MASK)
1388 modifiers |= XEMACS_MOD_SHIFT;
1389 if (mask & GDK_CONTROL_MASK)
1390 modifiers |= XEMACS_MOD_CONTROL;
1391 if (mask & gd->MetaMask)
1392 modifiers |= XEMACS_MOD_META;
1393 if (mask & gd->SuperMask)
1394 modifiers |= XEMACS_MOD_SUPER;
1395 if (mask & gd->HyperMask)
1396 modifiers |= XEMACS_MOD_HYPER;
1397 if (mask & gd->AltMask)
1398 modifiers |= XEMACS_MOD_ALT;
1399 if (mask & GDK_BUTTON1_MASK)
1400 modifiers |= XEMACS_MOD_BUTTON1;
1401 if (mask & GDK_BUTTON2_MASK)
1402 modifiers |= XEMACS_MOD_BUTTON2;
1403 if (mask & GDK_BUTTON3_MASK)
1404 modifiers |= XEMACS_MOD_BUTTON3;
1405 if (mask & GDK_BUTTON4_MASK)
1406 modifiers |= XEMACS_MOD_BUTTON4;
1407 if (mask & GDK_BUTTON5_MASK)
1408 modifiers |= XEMACS_MOD_BUTTON5;
1410 /* Currently ignores Shift_Lock but probably shouldn't
1411 (but it definitely should ignore Caps_Lock). */
1412 emacs_event->event.motion.modifiers = modifiers;
1416 default: /* it's a magic event */
1423 static const char *event_name(GdkEvent *);
1425 static gboolean generic_event_handler(GtkWidget * widget, GdkEvent * event)
1427 Lisp_Object emacs_event = Qnil;
1428 if (!GTK_IS_XEMACS(widget)) {
1429 stderr_out("Got a %s event for a non-SXEmacs widget\n",
1434 emacs_event = Fmake_event(Qnil, Qnil);
1436 if (gtk_event_to_emacs_event
1437 (GTK_XEMACS_FRAME(widget), event, XEVENT(emacs_event))) {
1438 enqueue_gtk_dispatch_event(emacs_event);
1441 Fdeallocate_event(emacs_event);
1446 gint emacs_gtk_key_event_handler(GtkWidget * widget, GdkEventKey * event)
1448 return (generic_event_handler(widget, (GdkEvent *) event));
1451 gint emacs_gtk_button_event_handler(GtkWidget * widget, GdkEventButton * event)
1453 return (generic_event_handler(widget, (GdkEvent *) event));
1456 gint emacs_gtk_motion_event_handler(GtkWidget * widget, GdkEventMotion * event)
1458 return (generic_event_handler(widget, (GdkEvent *) event));
1461 gboolean emacs_shell_event_handler(GtkWidget * wid /* unused */ ,
1462 GdkEvent * event, gpointer closure)
1464 struct frame *frame = (struct frame *)closure;
1465 Lisp_Object lisp_event = Fmake_event(Qnil, Qnil);
1466 struct Lisp_Event *emacs_event = XEVENT(lisp_event);
1467 GdkEvent *gdk_event_copy =
1468 &emacs_event->event.magic.underlying_gdk_event;
1469 struct device *d = XDEVICE(FRAME_DEVICE(frame));
1470 gboolean ignore_p = FALSE;
1472 set_last_server_timestamp(d, event);
1474 #define FROB(event_member) gdk_event_copy->event_member = event->event_member
1476 switch (event->type) {
1477 case GDK_SELECTION_REQUEST:
1478 case GDK_SELECTION_CLEAR:
1479 case GDK_SELECTION_NOTIFY:
1482 case GDK_PROPERTY_NOTIFY:
1485 case GDK_CLIENT_EVENT:
1495 case GDK_ENTER_NOTIFY:
1496 case GDK_LEAVE_NOTIFY:
1499 case GDK_FOCUS_CHANGE:
1502 case GDK_VISIBILITY_NOTIFY:
1507 /* Hrmm... do we really want to swallow all the other events as magic? */
1508 *gdk_event_copy = *event;
1513 emacs_event->event_type = magic_event;
1514 XSETFRAME(emacs_event->channel, frame);
1517 stderr_out("Ignoring event... (%s)\n", event_name(event));
1518 Fdeallocate_event(lisp_event);
1521 enqueue_gtk_dispatch_event(lisp_event);
1526 /************************************************************************/
1527 /* input pending / C-g checking */
1528 /************************************************************************/
1529 static void gtk_check_for_quit_char(struct device *d);
1531 static void check_for_tty_quit_char(struct device *d)
1533 SELECT_TYPE temp_mask;
1534 int infd = DEVICE_INFD(d);
1535 struct console *con = XCONSOLE(DEVICE_CONSOLE(d));
1536 Emchar quit_char = CONSOLE_QUIT_CHAR(con);
1538 FD_ZERO(&temp_mask);
1539 FD_SET(infd, &temp_mask);
1545 if (!poll_fds_for_input(temp_mask))
1548 event = Fmake_event(Qnil, Qnil);
1549 if (!read_event_from_tty_or_stream_desc
1550 (XEVENT(event), con, infd))
1551 /* EOF, or something ... */
1553 /* #### bogus. quit-char should be allowed to be any sort
1555 the_char = event_to_character(XEVENT(event), 1, 0, 0);
1556 if (the_char >= 0 && the_char == quit_char) {
1558 /* do not queue the C-g. See above. */
1562 /* queue the read event to be read for real later. */
1563 enqueue_gtk_dispatch_event(event);
1567 static void emacs_gtk_quit_p(void)
1569 Lisp_Object devcons, concons;
1571 CONSOLE_LOOP(concons) {
1572 struct console *con = XCONSOLE(XCAR(concons));
1573 if (!con->input_enabled)
1576 CONSOLE_DEVICE_LOOP(devcons, con) {
1578 d = XDEVICE(XCAR(devcons));
1580 if (DEVICE_GTK_P(d))
1581 /* emacs may be exiting */
1582 gtk_check_for_quit_char(d);
1583 else if (DEVICE_TTY_P(d))
1584 check_for_tty_quit_char(d);
1589 #include <gdk/gdkx.h>
1591 static void drain_gtk_queue(void)
1593 /* We can't just spin through here and wait for GTKs idea of the
1594 event queue to get empty, or the queue never gets drained. The
1595 situation is as follows. A process event gets signalled, we put
1596 it on the queue, then we go into Fnext_event(), which calls
1597 drain_gtk_queue(). But gtk_events_pending() will always return
1598 TRUE if there are file-descriptor (aka our process) events
1599 pending. Using GDK_events_pending() only shows us windowing
1603 while (gdk_events_pending())
1604 gtk_main_iteration();
1607 static int emacs_gtk_event_pending_p(int user_p)
1612 /* If `user_p' is false, then this function returns whether there are any
1613 X, timeout, or fd events pending (that is, whether emacs_gtk_next_event()
1614 would return immediately without blocking).
1616 if `user_p' is true, then this function returns whether there are any
1617 *user generated* events available (that is, whether there are keyboard
1618 or mouse-click events ready to be read). This also implies that
1619 emacs_Xt_next_event() would not block.
1621 In a non-SIGIO world, this also checks whether the user has typed ^G,
1622 since this is a convenient place to do so. We don't need to do this
1623 in a SIGIO world, since input causes an interrupt.
1626 /* This function used to simply check whether there were any X
1627 events (or if user_p was 1, it iterated over all the pending
1628 X events using XCheckIfEvent(), looking for keystrokes and
1629 button events). That worked in the old cheesoid event loop,
1630 which didn't go through XtAppDispatchEvent(), but it doesn't
1631 work any more -- X events may not result in anything. For
1632 example, a button press in a blank part of the menubar appears
1633 as an X event but will not result in any Emacs events (a
1634 button press that activates the menubar results in an Emacs
1635 event through the stop_next_event mechanism).
1637 The only accurate way of determining whether these X events
1638 translate into Emacs events is to go ahead and dispatch them
1639 until there's something on the dispatch queue. */
1641 /* See if there are any user events already on the queue. */
1642 EVENT_CHAIN_LOOP(event, dispatch_event_queue)
1643 if (!user_p || command_event_p(event))
1646 /* See if there's any TTY input available.
1648 if (poll_fds_for_input(tty_only_mask))
1652 /* If not user_p and there are any timer or file-desc events
1653 pending, we know there will be an event so we're through. */
1654 /* XtInputMask pending_value; */
1656 /* Note that formerly we just checked the value of XtAppPending()
1657 to determine if there was file-desc input. This doesn't
1658 work any more with the signal_event_pipe; XtAppPending()
1659 will says "yes" in this case but there isn't really any
1660 input. Another way of fixing this problem is for the
1661 signal_event_pipe to generate actual input in the form
1662 of an identity eval event or something. (#### maybe this
1663 actually happens?) */
1665 if (poll_fds_for_input(process_only_mask))
1668 /* #### Is there any way to do this in Gtk? I don't think there
1669 is a 'peek' for events */
1671 pending_value = XtAppPending(Xt_app_con);
1673 if (pending_value & XtIMTimer)
1678 /* XtAppPending() can be super-slow, esp. over a network connection.
1679 Quantify results have indicated that in some cases the
1680 call to detect_input_pending() completely dominates the
1681 running time of redisplay(). Fortunately, in a SIGIO world
1682 we can more quickly determine whether there are any X events:
1683 if an event has happened since the last time we checked, then
1684 a SIGIO will have happened. On a machine with broken SIGIO,
1685 we'll still be in an OK state -- the sigio_happened flag
1686 will get set at least once a second, so we'll be no more than
1687 one second behind reality. (In general it's OK if we
1688 erroneously report no input pending when input is actually
1689 pending() -- preemption is just a bit less efficient, that's
1690 all. It's bad bad bad if you err the other way -- you've
1691 promised that `next-event' won't block but it actually will,
1692 and some action might get delayed until the next time you
1696 /* quit_check_signal_tick_count is volatile so try to avoid race conditions
1697 by using a temporary variable */
1698 tick_count_val = quit_check_signal_tick_count;
1699 if (last_quit_check_signal_tick_count != tick_count_val) {
1700 last_quit_check_signal_tick_count = tick_count_val;
1702 /* We need to drain the entire queue now -- if we only
1703 drain part of it, we may later on end up with events
1704 actually pending but detect_input_pending() returning
1705 false because there wasn't another SIGIO. */
1709 EVENT_CHAIN_LOOP(event, dispatch_event_queue)
1710 if (!user_p || command_event_p(event))
1717 /************************************************************************/
1718 /* initialization */
1719 /************************************************************************/
1721 void syms_of_event_gtk(void)
1723 defsymbol(&Qkey_mapping, "key-mapping");
1724 defsymbol(&Qsans_modifiers, "sans-modifiers");
1727 void reinit_vars_of_event_gtk(void)
1729 gtk_event_stream = xnew(struct event_stream);
1730 gtk_event_stream->event_pending_p = emacs_gtk_event_pending_p;
1731 gtk_event_stream->next_event_cb = emacs_gtk_next_event;
1732 gtk_event_stream->handle_magic_event_cb = emacs_gtk_handle_magic_event;
1733 gtk_event_stream->add_timeout_cb = emacs_gtk_add_timeout;
1734 gtk_event_stream->remove_timeout_cb = emacs_gtk_remove_timeout;
1735 gtk_event_stream->select_console_cb = emacs_gtk_select_console;
1736 gtk_event_stream->unselect_console_cb = emacs_gtk_unselect_console;
1737 gtk_event_stream->select_process_cb = emacs_gtk_select_process;
1738 gtk_event_stream->unselect_process_cb = emacs_gtk_unselect_process;
1739 gtk_event_stream->quit_p_cb = emacs_gtk_quit_p;
1740 gtk_event_stream->create_stream_pair_cb = emacs_gtk_create_stream_pair;
1741 gtk_event_stream->delete_stream_pair_cb = emacs_gtk_delete_stream_pair;
1743 the_GTK_timeout_blocktype = Blocktype_new(struct GTK_timeout_blocktype);
1745 /* this function only makes safe calls */
1746 init_what_input_once();
1749 void vars_of_event_gtk(void)
1751 reinit_vars_of_event_gtk();
1753 dispatch_event_queue = Qnil;
1754 staticpro(&dispatch_event_queue);
1755 dispatch_event_queue_tail = Qnil;
1756 staticpro(&dispatch_event_queue_tail);
1758 DEFVAR_BOOL("gtk-allow-sendevents", >k_allow_sendevents /*
1759 *Non-nil means to allow synthetic events. Nil means they are ignored.
1760 Beware: allowing emacs to process SendEvents opens a big security hole.
1762 gtk_allow_sendevents = 0;
1764 last_quit_check_signal_tick_count = 0;
1767 void init_event_gtk_late(void)
1768 { /* called when already initialized */
1769 timeout_id_tick = 1;
1770 pending_timeouts = 0;
1771 completed_timeouts = 0;
1773 event_stream = gtk_event_stream;
1776 /* Shut GDK the hell up */
1777 gdk_error_trap_push();
1780 gdk_input_add(signal_event_pipe[0], GDK_INPUT_READ,
1781 (GdkInputFunction) gtk_what_callback, NULL);
1784 /* Bogus utility routines */
1785 static const char *event_name(GdkEvent * ev)
1787 return (gtk_event_name(ev->any.type));
1790 /* This is down at the bottom of the file so I can avoid polluting the
1791 generic code with this X specific CRAP! */
1793 #include <gdk/gdkx.h>
1794 #include <X11/keysym.h>
1795 /* #### BILL!!! Fix this please! */
1797 /************************************************************************/
1798 /* keymap handling */
1799 /************************************************************************/
1801 /* X bogusly doesn't define the interpretations of any bits besides
1802 ModControl, ModShift, and ModLock; so the Interclient Communication
1803 Conventions Manual says that we have to bend over backwards to figure
1804 out what the other modifier bits mean. According to ICCCM:
1806 - Any keycode which is assigned ModControl is a "control" key.
1808 - Any modifier bit which is assigned to a keycode which generates Meta_L
1809 or Meta_R is the modifier bit meaning "meta". Likewise for Super, Hyper,
1812 - Any keypress event which contains ModControl in its state should be
1813 interpreted as a "control" character.
1815 - Any keypress event which contains a modifier bit in its state which is
1816 generated by a keycode whose corresponding keysym is Meta_L or Meta_R
1817 should be interpreted as a "meta" character. Likewise for Super, Hyper,
1820 - It is illegal for a keysym to be associated with more than one modifier
1823 This means that the only thing that emacs can reasonably interpret as a
1824 "meta" key is a key whose keysym is Meta_L or Meta_R, and which generates
1825 one of the modifier bits Mod1-Mod5.
1827 Unfortunately, many keyboards don't have Meta keys in their default
1828 configuration. So, if there are no Meta keys, but there are "Alt" keys,
1829 emacs will interpret Alt as Meta. If there are both Meta and Alt keys,
1830 then the Meta keys mean "Meta", and the Alt keys mean "Alt" (it used to
1831 mean "Symbol," but that just confused the hell out of way too many people).
1833 This works with the default configurations of the 19 keyboard-types I've
1836 Emacs detects keyboard configurations which violate the above rules, and
1837 prints an error message on the standard-error-output. (Perhaps it should
1838 use a pop-up-window instead.)
1841 static void gtk_reset_key_mapping(struct device *d)
1843 Display *display = GDK_DISPLAY();
1844 struct gtk_device *xd = DEVICE_GTK_DATA(d);
1845 XModifierKeymap *map = (XModifierKeymap *) xd->x_keysym_map;
1846 KeySym *keysym, *keysym_end;
1847 Lisp_Object hashtable;
1848 int key_code_count, keysyms_per_code;
1852 XDisplayKeycodes(display,
1853 &xd->x_keysym_map_min_code,
1854 &xd->x_keysym_map_max_code);
1856 xd->x_keysym_map_max_code - xd->x_keysym_map_min_code + 1;
1857 map = (XModifierKeymap *)
1858 XGetKeyboardMapping(display, xd->x_keysym_map_min_code,
1860 &xd->x_keysym_map_keysyms_per_code);
1862 xd->x_keysym_map = (void *)map;
1863 hashtable = xd->x_keysym_map_hashtable;
1864 if (HASH_TABLEP(hashtable)) {
1865 Fclrhash(hashtable);
1867 xd->x_keysym_map_hashtable = hashtable =
1868 make_lisp_hash_table(128, HASH_TABLE_NON_WEAK,
1872 for (keysym = (KeySym *) map,
1873 keysyms_per_code = xd->x_keysym_map_keysyms_per_code,
1874 keysym_end = keysym + (key_code_count * keysyms_per_code);
1875 keysym < keysym_end; keysym += keysyms_per_code) {
1878 if (keysym[0] == NoSymbol)
1882 char *name = XKeysymToString(keysym[0]);
1884 gtk_keysym_to_emacs_keysym(keysym[0], 0);
1886 Fputhash(build_string(name), Qsans_modifiers,
1888 Fputhash(sym, Qsans_modifiers, hashtable);
1892 for (j = 1; j < keysyms_per_code; j++) {
1893 if (keysym[j] != keysym[0] && keysym[j] != NoSymbol) {
1894 char *name = XKeysymToString(keysym[j]);
1896 gtk_keysym_to_emacs_keysym(keysym[j], 0);
1898 && NILP(Fgethash(sym, hashtable, Qnil))) {
1899 Fputhash(build_string(name), Qt,
1901 Fputhash(sym, Qt, hashtable);
1908 static const char *index_to_name(int indice)
1915 case ControlMapIndex:
1916 return "ModControl";
1932 /* Boy, I really wish C had local functions... */
1933 struct c_doesnt_have_closures { /* #### not yet used */
1934 int warned_about_overlapping_modifiers;
1935 int warned_about_predefined_modifiers;
1936 int warned_about_duplicate_modifiers;
1944 static void gtk_reset_modifier_mapping(struct device *d)
1946 Display *display = GDK_DISPLAY();
1947 struct gtk_device *xd = DEVICE_GTK_DATA(d);
1948 int modifier_index, modifier_key, column, mkpm;
1949 int warned_about_overlapping_modifiers = 0;
1950 /* int warned_about_predefined_modifiers = 0; */
1951 /* int warned_about_duplicate_modifiers = 0; */
1957 XModifierKeymap *map = (XModifierKeymap *) xd->x_modifier_keymap;
1959 xd->lock_interpretation = 0;
1962 XFreeModifiermap(map);
1964 gtk_reset_key_mapping(d);
1966 xd->x_modifier_keymap = map = XGetModifierMapping(display);
1968 /* Boy, I really wish C had local functions...
1971 /* The call to warn_when_safe must be on the same line as the string or
1972 make-msgfile won't pick it up properly (the newline doesn't confuse
1973 it, but the backslash does). */
1975 #define store_modifier(name,old) \
1976 old = modifier_index;
1978 mkpm = map->max_keypermod;
1979 for (modifier_index = 0; modifier_index < 8; modifier_index++)
1980 for (modifier_key = 0; modifier_key < mkpm; modifier_key++) {
1981 KeySym last_sym = 0;
1982 for (column = 0; column < 4; column += 2) {
1984 map->modifiermap[modifier_index * mkpm +
1988 XKeycodeToKeysym(display, code,
1990 if (sym == last_sym)
1994 case XK_Mode_switch:
1995 store_modifier("Mode_switch", mode_bit);
1998 store_modifier("Meta_L", meta_bit);
2001 store_modifier("Meta_R", meta_bit);
2004 store_modifier("Super_L", super_bit);
2007 store_modifier("Super_R", super_bit);
2010 store_modifier("Hyper_L", hyper_bit);
2013 store_modifier("Hyper_R", hyper_bit);
2016 store_modifier("Alt_L", alt_bit);
2019 store_modifier("Alt_R", alt_bit);
2023 check_modifier("Control_L",
2027 check_modifier("Control_R",
2031 check_modifier("Shift_L", ShiftMask);
2034 check_modifier("Shift_R", ShiftMask);
2037 case XK_Shift_Lock: /* check_modifier ("Shift_Lock", LockMask); */
2038 xd->lock_interpretation = XK_Shift_Lock;
2040 case XK_Caps_Lock: /* check_modifier ("Caps_Lock", LockMask); */
2041 xd->lock_interpretation = XK_Caps_Lock;
2044 /* It probably doesn't make any sense for a modifier bit to be
2045 assigned to a key that is not one of the above, but OpenWindows
2046 assigns modifier bits to a couple of random function keys for
2047 no reason that I can discern, so printing a warning here would
2052 #undef store_modifier
2053 #undef check_modifier
2057 /* If there was no Meta key, then try using the Alt key instead.
2058 If there is both a Meta key and an Alt key, then the Alt key
2059 is not disturbed and remains an Alt key. */
2060 if (!meta_bit && alt_bit)
2061 meta_bit = alt_bit, alt_bit = 0;
2063 /* mode_bit overrides everything, since it's processed down inside of
2064 XLookupString() instead of by us. If Meta and Mode_switch both
2065 generate the same modifier bit (which is an error), then we don't
2066 interpret that bit as Meta, because we can't make XLookupString()
2067 not interpret it as Mode_switch; and interpreting it as both would
2068 be totally wrong. */
2070 const char *warn = 0;
2071 if (mode_bit == meta_bit)
2072 warn = "Meta", meta_bit = 0;
2073 else if (mode_bit == hyper_bit)
2074 warn = "Hyper", hyper_bit = 0;
2075 else if (mode_bit == super_bit)
2076 warn = "Super", super_bit = 0;
2077 else if (mode_bit == alt_bit)
2078 warn = "Alt", alt_bit = 0;
2081 (Qkey_mapping, Qwarning,
2082 "SXEmacs: %s is being used for both Mode_switch and %s.",
2083 index_to_name(mode_bit), warn),
2084 warned_about_overlapping_modifiers = 1;
2087 #undef index_to_name
2089 xd->MetaMask = (meta_bit ? (1 << meta_bit) : 0);
2090 xd->HyperMask = (hyper_bit ? (1 << hyper_bit) : 0);
2091 xd->SuperMask = (super_bit ? (1 << super_bit) : 0);
2092 xd->AltMask = (alt_bit ? (1 << alt_bit) : 0);
2093 xd->ModeMask = (mode_bit ? (1 << mode_bit) : 0); /* unused */
2097 void gtk_init_modifier_mapping(struct device *d)
2099 struct gtk_device *gd = DEVICE_GTK_DATA(d);
2100 gd->x_keysym_map_hashtable = Qnil;
2101 gd->x_keysym_map = NULL;
2102 gd->x_modifier_keymap = NULL;
2103 gtk_reset_modifier_mapping(d);
2107 static int gtk_key_is_modifier_p(KeyCode keycode, struct device *d)
2109 struct gtk_device *xd = DEVICE_GTK_DATA(d);
2111 KeySym *map = (KeySym *) xd->x_keysym_map;
2114 if (keycode < xd->x_keysym_map_min_code ||
2115 keycode > xd->x_keysym_map_max_code)
2118 syms = &map[(keycode - xd->x_keysym_map_min_code) *
2119 xd->x_keysym_map_keysyms_per_code];
2120 for (i = 0; i < xd->x_keysym_map_keysyms_per_code; i++)
2121 if (IsModifierKey(syms[i]) || syms[i] == XK_Mode_switch) /* why doesn't IsModifierKey count this? */
2127 struct _quit_predicate_closure {
2128 struct device *device;
2133 quit_char_predicate(Display * display, XEvent * event, XPointer data)
2135 struct _quit_predicate_closure *cl =
2136 (struct _quit_predicate_closure *)data;
2137 struct device *d = cl->device;
2138 struct frame *f = NULL;
2139 struct gtk_device *gd = DEVICE_GTK_DATA(d);
2141 Bool *critical = cl->critical;
2143 GdkWindow *window = gdk_window_lookup(event->xany.window);
2144 guint32 keycode = 0;
2145 GdkEventKey gdk_event;
2148 f = gtk_any_window_to_frame(d, window);
2153 if ((event->type != KeyPress) ||
2157 & (gd->MetaMask | gd->HyperMask | gd->SuperMask | gd->AltMask))) {
2163 XLookupString(&(event->xkey), dummy, 200, (KeySym *) & keycode,
2167 memset(&gdk_event, 0, sizeof(gdk_event));
2168 gdk_event.type = GDK_KEY_PRESS;
2169 gdk_event.window = window;
2170 gdk_event.keyval = keycode;
2171 gdk_event.state = event->xkey.state;
2173 /* This duplicates some code that exists elsewhere, but it's relatively
2174 fast and doesn't cons. */
2175 keysym = gtk_to_emacs_keysym(d, &gdk_event, 1);
2178 if (CHAR_OR_CHAR_INTP(keysym))
2179 c = XCHAR_OR_CHAR_INT(keysym);
2180 /* Highly doubtful that these are the quit character, but... */
2181 else if (EQ(keysym, QKbackspace))
2183 else if (EQ(keysym, QKtab))
2185 else if (EQ(keysym, QKlinefeed))
2187 else if (EQ(keysym, QKreturn))
2189 else if (EQ(keysym, QKescape))
2191 else if (EQ(keysym, QKspace))
2193 else if (EQ(keysym, QKdelete))
2198 if (event->xkey.state & gd->MetaMask)
2200 if ((event->xkey.state & ControlMask) && !(c >= 'A' && c <= 'Z'))
2201 c &= 0x1F; /* unshifted control characters */
2202 quit_char = CONSOLE_QUIT_CHAR(XCONSOLE(DEVICE_CONSOLE(d)));
2206 /* If we've got Control-Shift-G instead of Control-G, that means
2207 we have a critical_quit. Caps_Lock is its own modifier, so it
2208 won't cause ^G to act differently than before. */
2209 if (event->xkey.state & ControlMask)
2211 if (c == quit_char) {
2219 static void gtk_check_for_quit_char(struct device *d)
2223 Bool critical_quit = False;
2224 struct _quit_predicate_closure closure;
2226 XEventsQueued(GDK_DISPLAY(), QueuedAfterReading);
2229 closure.critical = &critical_quit;
2232 XCheckIfEvent(GDK_DISPLAY(), &event, quit_char_predicate,
2236 Vquit_flag = (critical_quit ? Qcritical : Qt);