/* X Communication module for terminals which understand the X protocol.
Copyright (C) 1989, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001,
- 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009
+ 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010
Free Software Foundation, Inc.
This file is part of GNU Emacs.
BLOCK_INPUT;
{
+#ifdef USE_GTK
+ /* Use Gdk routines to draw. This way, we won't draw over scroll bars
+ when the scroll bars and the edit widget share the same X window. */
+ GdkGCValues vals;
+ GdkGC *gc;
+ vals.foreground.pixel = (FRAME_FOREGROUND_PIXEL (f)
+ ^ FRAME_BACKGROUND_PIXEL (f));
+ vals.function = GDK_XOR;
+ gc = gdk_gc_new_with_values (FRAME_GTK_WIDGET (f)->window,
+ &vals,
+ GDK_GC_FUNCTION
+ | GDK_GC_FOREGROUND);
+#define XFillRectangle(d, win, gc, x, y, w, h) \
+ gdk_draw_rectangle (FRAME_GTK_WIDGET (f)->window, \
+ gc, TRUE, x, y, w, h)
+#else
GC gc;
/* Create a GC that will use the GXxor function to flip foreground
gc = XCreateGC (FRAME_X_DISPLAY (f), FRAME_X_WINDOW (f),
GCFunction | GCForeground, &values);
}
-
+#endif
{
/* Get the height not including a menu bar widget. */
int height = FRAME_TEXT_LINES_TO_PIXEL_HEIGHT (f, FRAME_LINES (f));
(height - flash_height
- FRAME_INTERNAL_BORDER_WIDTH (f)),
width, flash_height);
+
}
else
/* If it is short, flash it all. */
flash_left, FRAME_INTERNAL_BORDER_WIDTH (f),
width, height - 2 * FRAME_INTERNAL_BORDER_WIDTH (f));
+#ifdef USE_GTK
+ g_object_unref (G_OBJECT (gc));
+#undef XFillRectangle
+#else
XFreeGC (FRAME_X_DISPLAY (f), gc);
+#endif
x_flush (f);
}
}
{
XEvent *xev = (XEvent *) gxev;
+ BLOCK_INPUT;
if (current_count >= 0)
{
struct x_display_info *dpyinfo;
/* Filter events for the current X input method.
GTK calls XFilterEvent but not for key press and release,
so we do it here. */
- if (xev->type == KeyPress || xev->type == KeyRelease)
- if (dpyinfo && x_filter_event (dpyinfo, xev))
- return GDK_FILTER_REMOVE;
+ if ((xev->type == KeyPress || xev->type == KeyRelease)
+ && dpyinfo
+ && x_filter_event (dpyinfo, xev))
+ {
+ UNBLOCK_INPUT;
+ return GDK_FILTER_REMOVE;
+ }
#endif
if (! dpyinfo)
current_finish = X_EVENT_NORMAL;
else
- {
- current_count +=
- handle_one_xevent (dpyinfo, xev, ¤t_finish,
- current_hold_quit);
- }
+ current_count +=
+ handle_one_xevent (dpyinfo, xev, ¤t_finish,
+ current_hold_quit);
}
else
current_finish = x_dispatch_event (xev, xev->xany.display);
+ UNBLOCK_INPUT;
+
if (current_finish == X_EVENT_GOTO_OUT || current_finish == X_EVENT_DROP)
return GDK_FILTER_REMOVE;
{
x_clear_area (FRAME_X_DISPLAY (f), FRAME_X_WINDOW (f),
x, y, width, height, False);
+#ifdef USE_GTK
+ /* Must queue a redraw, because scroll bars might have been cleared. */
+ if (FRAME_GTK_WIDGET (f))
+ gtk_widget_queue_draw (FRAME_GTK_WIDGET (f));
+#endif
}
{
Pixmap icon_pixmap, icon_mask;
-#ifndef USE_X_TOOLKIT
+#if !defined USE_X_TOOLKIT && !defined USE_GTK
Window window = FRAME_OUTER_WINDOW (f);
#endif
int argc;
char *argv[NUM_ARGV];
char **argv2 = argv;
- GdkAtom atom;
guint id;
#ifndef HAVE_GTK_MULTIDISPLAY
if (!EQ (Vinitial_window_system, Qx))
terminal->kboard = (KBOARD *) xmalloc (sizeof (KBOARD));
init_kboard (terminal->kboard);
terminal->kboard->Vwindow_system = Qx;
+
+ /* Add the keyboard to the list before running Lisp code (via
+ Qvendor_specific_keysyms below), since these are not traced
+ via terminals but only through all_kboards. */
+ terminal->kboard->next_kboard = all_kboards;
+ all_kboards = terminal->kboard;
+
if (!EQ (XSYMBOL (Qvendor_specific_keysyms)->function, Qunbound))
{
char *vendor = ServerVendor (dpy);
- /* Temporarily hide the partially initialized terminal */
+
+ /* Protect terminal from GC before removing it from the
+ list of terminals. */
+ struct gcpro gcpro1;
+ Lisp_Object gcpro_term;
+ XSETTERMINAL (gcpro_term, terminal);
+ GCPRO1 (gcpro_term);
+
+ /* Temporarily hide the partially initialized terminal. */
terminal_list = terminal->next_terminal;
UNBLOCK_INPUT;
terminal->kboard->Vsystem_key_alist
BLOCK_INPUT;
terminal->next_terminal = terminal_list;
terminal_list = terminal;
+ UNGCPRO;
}
- terminal->kboard->next_kboard = all_kboards;
- all_kboards = terminal->kboard;
/* Don't let the initial kboard remain current longer than necessary.
That would cause problems if a file loaded on startup tries to
prompt in the mini-buffer. */
x_delete_display (dpyinfo)
struct x_display_info *dpyinfo;
{
- int i;
struct terminal *t;
/* Close all frames and delete the generic struct terminal for this
x_delete_terminal (struct terminal *terminal)
{
struct x_display_info *dpyinfo = terminal->display_info.x;
- int i;
/* Protect against recursive calls. delete_frame in
delete_terminal calls us back when it deletes our last frame. */