From: Timo Savola <timo.savola@iki.fi>
Subject: XEmbed patch
Date: Wed, 01 Feb 2006 21:09:19 +0200 [thread overview]
Message-ID: <1138820959.9429.54.camel@localhost.localdomain> (raw)
[-- Attachment #1: Type: text/plain, Size: 1241 bytes --]
Here is a patch (against CVS HEAD) that adds XEmbed support for all X
flavours and makes keyboard focus work for the GTK version. It needs
the gtkplug, parentid and parent-fix patches [1].
[1] http://lists.gnu.org/archive/html/emacs-devel/2005-12/msg01558.html
Some issues:
* The current implementation is minimal although all XEmbed message
types and parameters are enumerated in src/xterm.h. It is not clear
to me if the additional protocol features are feasible for Emacs or
how to implement them.
* Emacs requests focus only when the buffer area is clicked. It might
be a good idea to request focus also when the menubar or the toolbar
is clicked.
* I'm not sure if src/xterm.h and src/xterm.c are the correct files for
the XEmbed enums and utility functions.
* The implementation of XEMBED_FOCUS_{IN,OUT} seems clumsy.
* I tested only --with-x and --with-gtk configurations.
* The keyboard focus works correctly (at least) under Metacity, but
there seems to be a problem when using the Ion 3 window manager. The
original GtkPlug version could only be used with Ion because it seems
to treat embedded windows like top-levels as far as focus is
concerned; the embedder application is not in charge.
timo
[-- Attachment #2: emacs-xembed.patch --]
[-- Type: text/x-patch, Size: 6386 bytes --]
Wed Feb 1 17:55:17 EET 2006 Timo Savola <timo.savola@iki.fi>
* xembed
diff -rN -u old-work/src/xterm.c new-work-1/src/xterm.c
--- old-work/src/xterm.c 2006-02-01 17:56:27.055682312 +0200
+++ new-work-1/src/xterm.c 2006-02-01 17:45:11.000000000 +0200
@@ -3284,6 +3284,15 @@
FOCUS_IMPLICIT : FOCUS_EXPLICIT),
dpyinfo, frame, bufp);
break;
+
+ case ClientMessage:
+ if (event->xclient.message_type == dpyinfo->Xatom_XEMBED)
+ {
+ enum xembed_message msg = event->xclient.data.l[1];
+ x_focus_changed ((msg == XEMBED_FOCUS_IN ? FocusIn : FocusOut),
+ FOCUS_EXPLICIT, dpyinfo, frame, bufp);
+ }
+ break;
}
}
@@ -5836,6 +5845,18 @@
}
#endif /* USE_TOOLKIT_SCROLL_BARS */
+ /* XEmbed messages from the embedder (if any). */
+ if (event.xclient.message_type
+ == dpyinfo->Xatom_XEMBED)
+ {
+ enum xembed_message msg = event.xclient.data.l[1];
+ if (msg == XEMBED_FOCUS_IN || msg == XEMBED_FOCUS_OUT)
+ x_detect_focus_change (dpyinfo, &event, &inev.ie);
+
+ *finish = X_EVENT_GOTO_OUT;
+ goto done;
+ }
+
f = x_any_window_to_frame (dpyinfo, event.xclient.window);
if (!f)
@@ -6734,6 +6755,10 @@
else
construct_mouse_click (&inev.ie, &event.xbutton, f);
}
+
+ if (FRAME_X_EMBEDDED_P (f))
+ xembed_send_message (f, event.xbutton.time,
+ XEMBED_REQUEST_FOCUS, 0, 0, 0);
}
}
else
@@ -8535,6 +8560,51 @@
x_lower_frame (f);
}
\f
+/* XEmbed implementation. */
+
+void
+xembed_set_info (f, flags)
+ struct frame *f;
+ enum xembed_info flags;
+{
+ Atom atom;
+ unsigned long data[2];
+
+ atom = XInternAtom (FRAME_X_DISPLAY (f), "_XEMBED_INFO", False);
+
+ data[0] = XEMBED_VERSION;
+ data[1] = flags;
+
+ XChangeProperty (FRAME_X_DISPLAY (f), FRAME_X_WINDOW (f), atom, atom,
+ 32, PropModeReplace, (unsigned char *) data, 2);
+}
+
+void
+xembed_send_message (f, time, message, detail, data1, data2)
+ struct frame *f;
+ Time time;
+ enum xembed_message message;
+ long detail;
+ long data1;
+ long data2;
+{
+ XEvent event;
+
+ event.xclient.type = ClientMessage;
+ event.xclient.window = FRAME_X_OUTPUT(f)->parent_desc;
+ event.xclient.message_type = FRAME_X_DISPLAY_INFO (f)->Xatom_XEMBED;
+ event.xclient.format = 32;
+ event.xclient.data.l[0] = time;
+ event.xclient.data.l[1] = message;
+ event.xclient.data.l[2] = detail;
+ event.xclient.data.l[3] = data1;
+ event.xclient.data.l[4] = data2;
+
+ XSendEvent (FRAME_X_DISPLAY (f), FRAME_X_OUTPUT(f)->parent_desc,
+ False, NoEventMask, &event);
+ XSync (FRAME_X_DISPLAY (f), False);
+}
+\f
/* Change of visibility. */
/* This tries to wait until the frame is really visible.
@@ -8575,14 +8645,22 @@
if (! EQ (Vx_no_window_manager, Qt))
x_wm_set_window_state (f, NormalState);
#ifdef USE_X_TOOLKIT
- /* This was XtPopup, but that did nothing for an iconified frame. */
- XtMapWidget (f->output_data.x->widget);
+ if (FRAME_X_EMBEDDED_P (f))
+ xembed_set_info (f, XEMBED_MAPPED);
+ else
+ {
+ /* This was XtPopup, but that did nothing for an iconified frame. */
+ XtMapWidget (f->output_data.x->widget);
+ }
#else /* not USE_X_TOOLKIT */
#ifdef USE_GTK
gtk_widget_show_all (FRAME_GTK_OUTER_WIDGET (f));
gtk_window_deiconify (GTK_WINDOW (FRAME_GTK_OUTER_WIDGET (f)));
#else
- XMapRaised (FRAME_X_DISPLAY (f), FRAME_X_WINDOW (f));
+ if (FRAME_X_EMBEDDED_P (f))
+ xembed_set_info (f, XEMBED_MAPPED);
+ else
+ XMapRaised (FRAME_X_DISPLAY (f), FRAME_X_WINDOW (f));
#endif /* not USE_GTK */
#endif /* not USE_X_TOOLKIT */
#if 0 /* This seems to bring back scroll bars in the wrong places
@@ -8734,6 +8812,10 @@
if (FRAME_GTK_OUTER_WIDGET (f))
gtk_widget_hide (FRAME_GTK_OUTER_WIDGET (f));
else
+#else
+ if (FRAME_X_EMBEDDED_P (f))
+ xembed_set_info (f, 0);
+ else
#endif
{
#ifdef HAVE_X11R4
@@ -10479,6 +10561,9 @@
dpyinfo->Xatom_Scrollbar = XInternAtom (dpyinfo->display, "SCROLLBAR",
False);
+ dpyinfo->Xatom_XEMBED = XInternAtom (dpyinfo->display, "_XEMBED",
+ False);
+
dpyinfo->cut_buffers_initialized = 0;
connection = ConnectionNumber (dpyinfo->display);
diff -rN -u old-work/src/xterm.h new-work-1/src/xterm.h
--- old-work/src/xterm.h 2006-02-01 17:56:27.047683528 +0200
+++ new-work-1/src/xterm.h 2006-02-01 17:54:32.000000000 +0200
@@ -327,6 +327,9 @@
/* Atom used in toolkit scroll bar client messages. */
Atom Xatom_Scrollbar;
+ /* Atom used in XEmbed client messages. */
+ Atom Xatom_XEMBED;
+
#ifdef MULTI_KBOARD
struct kboard *kboard;
#endif
@@ -1091,6 +1094,66 @@
extern int x_session_have_connection P_ ((void));
#endif
+/* XEmbed implementation. */
+
+#define XEMBED_VERSION 0
+
+enum xembed_info
+ {
+ XEMBED_MAPPED = 1 << 0
+ };
+
+enum xembed_message
+ {
+ XEMBED_EMBEDDED_NOTIFY = 0,
+ XEMBED_WINDOW_ACTIVATE = 1,
+ XEMBED_WINDOW_DEACTIVATE = 2,
+ XEMBED_REQUEST_FOCUS = 3,
+ XEMBED_FOCUS_IN = 4,
+ XEMBED_FOCUS_OUT = 5,
+ XEMBED_FOCUS_NEXT = 6,
+ XEMBED_FOCUS_PREV = 7,
+
+ XEMBED_MODALITY_ON = 10,
+ XEMBED_MODALITY_OFF = 11,
+ XEMBED_REGISTER_ACCELERATOR = 12,
+ XEMBED_UNREGISTER_ACCELERATOR = 13,
+ XEMBED_ACTIVATE_ACCELERATOR = 14
+ };
+
+enum xembed_focus
+ {
+ XEMBED_FOCUS_CURRENT = 0,
+ XEMBED_FOCUS_FIRST = 1,
+ XEMBED_FOCUS_LAST = 2
+ };
+
+enum xembed_modifier
+ {
+ XEMBED_MODIFIER_SHIFT = 1 << 0,
+ XEMBED_MODIFIER_CONTROL = 1 << 1,
+ XEMBED_MODIFIER_ALT = 1 << 2,
+ XEMBED_MODIFIER_SUPER = 1 << 3,
+ XEMBED_MODIFIER_HYPER = 1 << 4
+ };
+
+enum xembed_accelerator
+ {
+ XEMBED_ACCELERATOR_OVERLOADED = 1 << 0
+ };
+
+/* Defined in xterm.c */
+
+extern void xembed_set_info P_ ((struct frame *f, enum xembed_info flags));
+extern void xembed_send_message P_ ((struct frame *f, Time time,
+ enum xembed_message message,
+ long detail, long data1, long data2));
+
+/* Is the frame embedded into another application? */
+
+#define FRAME_X_EMBEDDED_P(f) (FRAME_X_OUTPUT(f)->explicit_parent != 0)
+
+
#define FONT_TYPE_FOR_UNIBYTE(font, ch) 0
#define FONT_TYPE_FOR_MULTIBYTE(font, ch) 0
[-- Attachment #3: Type: text/plain, Size: 142 bytes --]
_______________________________________________
Emacs-devel mailing list
Emacs-devel@gnu.org
http://lists.gnu.org/mailman/listinfo/emacs-devel
next reply other threads:[~2006-02-01 19:09 UTC|newest]
Thread overview: 2+ messages / expand[flat|nested] mbox.gz Atom feed top
2006-02-01 19:09 Timo Savola [this message]
2006-02-04 18:27 ` XEmbed patch Richard M. Stallman
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
List information: https://www.gnu.org/software/emacs/
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=1138820959.9429.54.camel@localhost.localdomain \
--to=timo.savola@iki.fi \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
Code repositories for project(s) associated with this public inbox
https://git.savannah.gnu.org/cgit/emacs.git
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).