Re: Sending GdkEvents to Gtk Widget
- From: Andy Stewart <lazycat manatee gmail com>
- To: Bharathwaaj Srinivasan <bharathwaaj s gmail com>
- Cc: gtk-list gnome org
- Subject: Re: Sending GdkEvents to Gtk Widget
- Date: Tue, 13 Jul 2010 00:19:22 +0800
Hi Bharathwaaj,
Bharathwaaj Srinivasan <bharathwaaj s gmail com> writes:
> Hi Andy,
>
> I couldn't understand the meaning of serializeEvent.
Because it's Haskell. :)
I will explain at below.
>
> But still I simply tried the following in the socket source callback from GLib.
>
> GdkEvent event;
> memset(&event, 0, sizeof(GdkEvent));
> event.key.type = GDK_KEY_PRESS;
> event.key.keyval = GDK_Tab;
> event.key.send_event = TRUE;
This is wrong,
you should get field value from event that return by signal "key_press_event",
and not build those filed by yourself.
Then you can send *all* GdkEvent to another process, and not just Tab key.
Here is C structure of GdkEventKey:
typedef struct {
GdkEventType type;
GdkWindow *window;
gint8 send_event;
guint32 time;
guint state;
guint keyval;
gint length;
gchar *string;
guint16 hardware_keycode;
guint8 group;
guint is_modifier : 1;
} GdkEventKey;
On *server* process, you should hang some function on singal
"key_press_event", then you can get keyPress event when you typing
something at server side.
Then you need pick-up public field from keyPress event.
Example:
... singalEvent is get in "key_press_event" signal ...
...
serialize_event_type = signalEvent.key.type
serialize_event_keyval = signalEvent.key.keyval
serialize_event_send_event = signalEvent.key.send_event
...
Note, you need serialize *all* public field in GdkEventKey except
*GdkWindow* field.
Because, when you send event to *client* process, you want propagate
event in *client* process, so you need *client* process widget GdkWindow
and not *server* one.
After you serialize event value, you need send to network, below i
explain how to handle at client side.
> gdk_threads_enter();
> printf("Sending Tab event to gtk_idle_add_full\n");
> gtk_idle_add_full(G_PRIORITY_DEFAULT, (GSourceFunc)gtk_main_do_event, NULL, &event,
> NULL);
> gdk_threads_leave();
>
> This also lead to the same behaviour. The WebKit Gtk main window freezed from responding for further
> events.
Because you haven't set field GdkWindow of GdkEventKey, it's 0 by your
memset.
When you call gtk_main_do_event, gtk_main_do_event will
lookup GdkWindow field to decide which widget need receive event, since
GdkWindow field is 0, your *client* process will freezed.
So client should do like this.
1) When your *client* receive serialize event from network, then use
below code to fill all flied except *GdkWindow* field:
GdkEvent event;
memset(&event, 0, sizeof(GdkEvent));
...
event.key.type = serialize_event_type
event.key.keyval = serialize_event_keyval
event.key.send_event = serialize_event_send_event
...
2) Then fill *GdkWindow* field with client widget.
You need get GdkWindow pointer from WebKit widget.
widget_window_ptr = webkitWidget.window
Then fill event GdkWindow field with webkit GdkWindow pointer.
event.key.window = widget_window_ptr
That's all.
Cheers,
-- Andy
>
> I also tried replacing gtk_idle_add_full with g_idle_add_full. Still same behaviour.
>
> Please help me if i'm missing something.
>
> Kind regards,
> Bharath
>
> On Mon, Jul 12, 2010 at 12:33 PM, Andy Stewart <lazycat manatee gmail com> wrote:
>
> Hi Bharathwaaj,
>
> I'm a developer of gtk2hs (Haskell binding to gtk+).
>
> I have fix same problem (WebKit widget and GdkEvent) at Haskell side.
> (https://patch-tag.com/r/AndyStewart/gtk-serialized-event/snapshot/current/content/pretty/Graphics/UI/Gtk/Gdk/
> SerializedEvent.hsc)
> This is screenshot : http://farm5.static.flickr.com/4080/4758242386_5230d3d54d_b.jpg
>
> Though i use Haskell, but i can explain how to pass GdkEvent from one
> process to another.
>
> Below are step:
>
> 1) Serialize GdkEvent at *server* process.
> 2) Then send SerializeEvent over the network
> 3) When *client* process receive SerializeEvent from network, re-build
> GdkEvent.
> 4) Then you can use gtk_main_do_event propagate same event on current
> focus widget, or use gtk_widget_event propagate event on specify widget.
>
> Only trick is you need use idle_add_full wrap gtk_main_do_event to make
> sure gtk_main_do_event running in *main thread* and not *listen event
> thread*.
>
> Hope above will help you. :)
>
> Cheers,
>
> -- Andy
>
> Bharathwaaj Srinivasan <bharathwaaj s gmail com> writes:
>
> > Hi,
> >
> > Is it possible to send GdkEvents to a GtkWidget from the application?
> >
> > Currently I've a GIOChannel which is listening to a socket and the GSource is attached to the
> Glib
> > main loop.
> >
> > g_type_init();
> > g_thread_init(NULL);
> > gdk_threads_init();
> > gdk_threads_enter();
> > gtk_init(NULL, NULL);
> >
> > channel = g_io_channel_unix_new (fd);
> > g_io_channel_set_encoding (channel, NULL, NULL);
> > g_io_channel_set_buffered (channel, FALSE);
> >
> > source = g_io_create_watch (channel, G_IO_IN);
> > g_source_set_priority (source, G_PRIORITY_DEFAULT);
> > g_source_set_can_recurse (source, TRUE);
> > g_source_set_callback (source, (GSourceFunc) event_handler, NULL, NULL);
> > g_source_attach (source, NULL);
> >
> > g_source_unref (source);
> > g_io_channel_unref(channel);
> >
> > gtk_main();
> > gdk_threads_leave();
> >
> > GdkEvents (Keyboard events) are passed from say another process by writing to the socket fd.
> >
> > Glib calls the callback "event_handler" for data available to read. The event_handler callback
> reads
> > the GdkEvent passed by
> > another process and calls gtk_main_do_event to pass the event to the widget.
> >
> > But this doesn't work and the application freezes.
> >
> > I use gdk_threads_enter and gdk_threads_leave in the callback and before gtk_main for making
> gtk
> > thread aware as the
> > callback comes from Glib.
> >
> > Kindly help me in providing a mechanism to pass GdkEvents from the top. If this is not
> possible,
> > please explain why.
> >
> > The main purpose for which I need this is I'm using GtkWebKit and I send Tab key event to make
> the
> > focus move to the next
> > element in the Webview.
> >
> > Events are being fed from another process.
> >
> > Kind regards,
> > Bharath
> >
> > _______________________________________________
> > gtk-list mailing list
> > gtk-list gnome org
> > http://mail.gnome.org/mailman/listinfo/gtk-list
>
> _______________________________________________
> gtk-list mailing list
> gtk-list gnome org
> http://mail.gnome.org/mailman/listinfo/gtk-list
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]