Merge lp:~ted/libdbusmenu/serializable-menuitem into lp:libdbusmenu/0.5

Proposed by Ted Gould
Status: Merged
Merged at revision: 197
Proposed branch: lp:~ted/libdbusmenu/serializable-menuitem
Merge into: lp:libdbusmenu/0.5
Diff against target: 687 lines (+489/-18)
11 files modified
.bzrignore (+3/-0)
docs/libdbusmenu-gtk/reference/Makefile.am (+1/-1)
docs/libdbusmenu-gtk/reference/libdbusmenu-gtk-docs.sgml (+1/-1)
libdbusmenu-glib/client.c (+69/-7)
libdbusmenu-glib/client.h (+7/-1)
libdbusmenu-gtk/Makefile.am (+5/-2)
libdbusmenu-gtk/client.c (+4/-4)
libdbusmenu-gtk/dbusmenu-gtk.h (+1/-0)
libdbusmenu-gtk/menuitem.h (+2/-2)
libdbusmenu-gtk/serializablemenuitem.c (+288/-0)
libdbusmenu-gtk/serializablemenuitem.h (+108/-0)
To merge this branch: bzr merge lp:~ted/libdbusmenu/serializable-menuitem
Reviewer Review Type Date Requested Status
Mikkel Kamstrup Erlandsen (community) Needs Fixing
Review via email: mp+47604@code.launchpad.net

Description of the change

This adds a new object that can be subclassed from to create menuitems with enough data that they can be transported across dbusmenu transparently.

To post a comment you must log in.
Revision history for this message
Mikkel Kamstrup Erlandsen (kamstrup) wrote :

The function prototypes DbusmenuClientTypeHandler and DbusmenuClientTypeDestroyHandler needs documentation.

Can we avoid double namespacing on these two functions?:

dbusmenu_gtk_serializable_menu_item_build_dbusmenu_menuitem()
dbusmenu_gtk_serializable_menu_item_set_dbusmenu_menuitem()

Becomes:

dbusmenu_gtk_serializable_menu_item_build_menuitem()
dbusmenu_gtk_serializable_menu_item_set_menuitem()

Can you add some section docs describing what the purpose of DbusmenuGtkSerializableMenuItem is, and how to use it? After reviewing this code I am still not entirely sure what it's supposed to do :-)

review: Needs Fixing
Revision history for this message
Ted Gould (ted) wrote :

On Thu, 2011-01-27 at 09:49 +0000, Mikkel Kamstrup Erlandsen wrote:
> The function prototypes DbusmenuClientTypeHandler and
> DbusmenuClientTypeDestroyHandler needs documentation.

r215

> Can we avoid double namespacing on these two functions?:
>
> dbusmenu_gtk_serializable_menu_item_build_dbusmenu_menuitem()
> dbusmenu_gtk_serializable_menu_item_set_dbusmenu_menuitem()
>
> Becomes:
>
> dbusmenu_gtk_serializable_menu_item_build_menuitem()
> dbusmenu_gtk_serializable_menu_item_set_menuitem()

Yes, was looking for a good way to shorten these, thanks!

r214

> Can you add some section docs describing what the purpose of
> DbusmenuGtkSerializableMenuItem is, and how to use it? After
> reviewing this code I am still not entirely sure what it's
> supposed to do :-)

r216

Preview Diff

[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
=== modified file '.bzrignore'
--- .bzrignore 2010-12-02 20:13:09 +0000
+++ .bzrignore 2011-01-26 23:16:59 +0000
@@ -220,3 +220,6 @@
220libdbusmenu-gtk/DbusmenuGtk-0.4.vapi220libdbusmenu-gtk/DbusmenuGtk-0.4.vapi
221libdbusmenu-gtk/dbusmenu-gtk-0.4.pc221libdbusmenu-gtk/dbusmenu-gtk-0.4.pc
222libdbusmenu-gtk/dbusmenu-gtk3-0.4.pc222libdbusmenu-gtk/dbusmenu-gtk3-0.4.pc
223libdbusmenu-gtk/libdbusmenu_gtk_la-serializablemenuitem.lo
224docs/libdbusmenu-gtk/reference/html/DbusmenuGtkSerializableMenuItem.html
225docs/libdbusmenu-gtk/reference/tmpl/serializablemenuitem.sgml
223226
=== modified file 'docs/libdbusmenu-gtk/reference/Makefile.am'
--- docs/libdbusmenu-gtk/reference/Makefile.am 2010-11-23 21:19:52 +0000
+++ docs/libdbusmenu-gtk/reference/Makefile.am 2011-01-26 23:16:59 +0000
@@ -54,7 +54,7 @@
5454
55# Header files to ignore when scanning.55# Header files to ignore when scanning.
56# e.g. IGNORE_HFILES=gtkdebug.h gtkintl.h56# e.g. IGNORE_HFILES=gtkdebug.h gtkintl.h
57IGNORE_HFILES=57IGNORE_HFILES=genericmenuitem.h
5858
59# Images to copy into HTML directory.59# Images to copy into HTML directory.
60# e.g. HTML_IMAGES=$(top_srcdir)/gtk/stock-icons/stock_about_24.png60# e.g. HTML_IMAGES=$(top_srcdir)/gtk/stock-icons/stock_about_24.png
6161
=== modified file 'docs/libdbusmenu-gtk/reference/libdbusmenu-gtk-docs.sgml'
--- docs/libdbusmenu-gtk/reference/libdbusmenu-gtk-docs.sgml 2010-06-09 16:24:31 +0000
+++ docs/libdbusmenu-gtk/reference/libdbusmenu-gtk-docs.sgml 2011-01-26 23:16:59 +0000
@@ -13,8 +13,8 @@
13 <title>API</title>13 <title>API</title>
14 <xi:include href="xml/menu.xml"/>14 <xi:include href="xml/menu.xml"/>
15 <xi:include href="xml/client.xml"/>15 <xi:include href="xml/client.xml"/>
16 <xi:include href="xml/genericmenuitem.xml"/>
17 <xi:include href="xml/menuitem.xml"/>16 <xi:include href="xml/menuitem.xml"/>
17 <xi:include href="xml/serializablemenuitem.xml"/>
1818
19 </chapter>19 </chapter>
20 <chapter id="object-tree">20 <chapter id="object-tree">
2121
=== modified file 'libdbusmenu-glib/client.c'
--- libdbusmenu-glib/client.c 2011-01-26 23:12:22 +0000
+++ libdbusmenu-glib/client.c 2011-01-26 23:16:59 +0000
@@ -120,6 +120,15 @@
120 guint timestamp;120 guint timestamp;
121};121};
122122
123typedef struct _type_handler_t type_handler_t;
124struct _type_handler_t {
125 DbusmenuClient * client;
126 DbusmenuClientTypeHandler cb;
127 DbusmenuClientTypeDestroyHandler destroy_cb;
128 gpointer user_data;
129 gchar * type;
130};
131
123132
124#define DBUSMENU_CLIENT_GET_PRIVATE(o) (DBUSMENU_CLIENT(o)->priv)133#define DBUSMENU_CLIENT_GET_PRIVATE(o) (DBUSMENU_CLIENT(o)->priv)
125#define DBUSMENU_INTERFACE "com.canonical.dbusmenu"134#define DBUSMENU_INTERFACE "com.canonical.dbusmenu"
@@ -148,6 +157,7 @@
148static void menuproxy_build_cb (GObject * object, GAsyncResult * res, gpointer user_data);157static void menuproxy_build_cb (GObject * object, GAsyncResult * res, gpointer user_data);
149static void menuproxy_name_changed_cb (GObject * object, GParamSpec * pspec, gpointer user_data);158static void menuproxy_name_changed_cb (GObject * object, GParamSpec * pspec, gpointer user_data);
150static void menuproxy_signal_cb (GDBusProxy * proxy, gchar * sender, gchar * signal, GVariant * params, gpointer user_data);159static void menuproxy_signal_cb (GDBusProxy * proxy, gchar * sender, gchar * signal, GVariant * params, gpointer user_data);
160static void type_handler_destroy (gpointer user_data);
151161
152/* Globals */162/* Globals */
153static GDBusNodeInfo * dbusmenu_node_info = NULL;163static GDBusNodeInfo * dbusmenu_node_info = NULL;
@@ -310,7 +320,7 @@
310 priv->dbusproxy = 0;320 priv->dbusproxy = 0;
311321
312 priv->type_handlers = g_hash_table_new_full(g_str_hash, g_str_equal,322 priv->type_handlers = g_hash_table_new_full(g_str_hash, g_str_equal,
313 g_free, NULL);323 g_free, type_handler_destroy);
314324
315 priv->delayed_idle = 0;325 priv->delayed_idle = 0;
316 priv->delayed_property_list = g_array_new(TRUE, FALSE, sizeof(gchar *));326 priv->delayed_property_list = g_array_new(TRUE, FALSE, sizeof(gchar *));
@@ -1153,17 +1163,17 @@
1153 gboolean handled = FALSE;1163 gboolean handled = FALSE;
11541164
1155 const gchar * type;1165 const gchar * type;
1156 DbusmenuClientTypeHandler newfunc = NULL;1166 type_handler_t * th = NULL;
1157 1167
1158 type = dbusmenu_menuitem_property_get(propdata->item, DBUSMENU_MENUITEM_PROP_TYPE);1168 type = dbusmenu_menuitem_property_get(propdata->item, DBUSMENU_MENUITEM_PROP_TYPE);
1159 if (type != NULL) {1169 if (type != NULL) {
1160 newfunc = g_hash_table_lookup(priv->type_handlers, type);1170 th = (type_handler_t *)g_hash_table_lookup(priv->type_handlers, type);
1161 } else {1171 } else {
1162 newfunc = g_hash_table_lookup(priv->type_handlers, DBUSMENU_CLIENT_TYPES_DEFAULT);1172 th = (type_handler_t *)g_hash_table_lookup(priv->type_handlers, DBUSMENU_CLIENT_TYPES_DEFAULT);
1163 }1173 }
11641174
1165 if (newfunc != NULL) {1175 if (th != NULL && th->cb != NULL) {
1166 handled = newfunc(propdata->item, propdata->parent, propdata->client);1176 handled = th->cb(propdata->item, propdata->parent, propdata->client, th->user_data);
1167 }1177 }
11681178
1169 #ifdef MASSIVEDEBUGGING1179 #ifdef MASSIVEDEBUGGING
@@ -1679,6 +1689,19 @@
1679 return priv->root;1689 return priv->root;
1680}1690}
16811691
1692/* Remove the type handler when we're all done with it */
1693static void
1694type_handler_destroy (gpointer user_data)
1695{
1696 type_handler_t * th = (type_handler_t *)user_data;
1697 if (th->destroy_cb != NULL) {
1698 th->destroy_cb(th->client, th->type, th->user_data);
1699 }
1700 g_free(th->type);
1701 g_free(th);
1702 return;
1703}
1704
1682/**1705/**
1683 dbusmenu_client_add_type_handler:1706 dbusmenu_client_add_type_handler:
1684 @client: Client where we're getting types coming in1707 @client: Client where we're getting types coming in
@@ -1703,6 +1726,37 @@
1703gboolean1726gboolean
1704dbusmenu_client_add_type_handler (DbusmenuClient * client, const gchar * type, DbusmenuClientTypeHandler newfunc)1727dbusmenu_client_add_type_handler (DbusmenuClient * client, const gchar * type, DbusmenuClientTypeHandler newfunc)
1705{1728{
1729 return dbusmenu_client_add_type_handler_full(client, type, newfunc, NULL, NULL);
1730}
1731
1732/**
1733 dbusmenu_client_add_type_handler_full:
1734 @client: Client where we're getting types coming in
1735 @type: A text string that will be matched with the 'type'
1736 property on incoming menu items
1737 @newfunc: The function that will be executed with those new
1738 items when they come in.
1739 @user_data: Data passed to @newfunc when it is called
1740 @destroy_func: A function that is called when the type handler is
1741 removed (usually on client destruction) which will free
1742 the resources in @user_data.
1743
1744 This function connects into the type handling of the #DbusmenuClient.
1745 Every new menuitem that comes in immediately gets asked for it's
1746 properties. When we get those properties we check the 'type'
1747 property and look to see if it matches a handler that is known
1748 by the client. If so, the @newfunc function is executed on that
1749 #DbusmenuMenuitem. If not, then the DbusmenuClient::new-menuitem
1750 signal is sent.
1751
1752 In the future the known types will be sent to the server so that it
1753 can make choices about the menu item types availble.
1754
1755 Return value: If registering the new type was successful.
1756*/
1757gboolean
1758dbusmenu_client_add_type_handler_full (DbusmenuClient * client, const gchar * type, DbusmenuClientTypeHandler newfunc, gpointer user_data, DbusmenuClientTypeDestroyHandler destroy_func)
1759{
1706 g_return_val_if_fail(DBUSMENU_IS_CLIENT(client), FALSE);1760 g_return_val_if_fail(DBUSMENU_IS_CLIENT(client), FALSE);
1707 g_return_val_if_fail(type != NULL, FALSE);1761 g_return_val_if_fail(type != NULL, FALSE);
17081762
@@ -1723,6 +1777,14 @@
1723 return FALSE;1777 return FALSE;
1724 }1778 }
17251779
1726 g_hash_table_insert(priv->type_handlers, g_strdup(type), newfunc);1780 type_handler_t * th = g_new0(type_handler_t, 1);
1781 th->client = client;
1782 th->cb = newfunc;
1783 th->destroy_cb = destroy_func;
1784 th->user_data = user_data;
1785 th->type = g_strdup(type);
1786
1787 g_hash_table_insert(priv->type_handlers, g_strdup(type), th);
1727 return TRUE;1788 return TRUE;
1728}1789}
1790
17291791
=== modified file 'libdbusmenu-glib/client.h'
--- libdbusmenu-glib/client.h 2010-11-18 03:07:51 +0000
+++ libdbusmenu-glib/client.h 2011-01-26 23:16:59 +0000
@@ -110,7 +110,8 @@
110 DbusmenuClientPrivate * priv;110 DbusmenuClientPrivate * priv;
111};111};
112112
113typedef gboolean (*DbusmenuClientTypeHandler) (DbusmenuMenuitem * newitem, DbusmenuMenuitem * parent, DbusmenuClient * client);113typedef gboolean (*DbusmenuClientTypeHandler) (DbusmenuMenuitem * newitem, DbusmenuMenuitem * parent, DbusmenuClient * client, gpointer user_data);
114typedef void (*DbusmenuClientTypeDestroyHandler) (DbusmenuClient * client, const gchar * type, gpointer user_data);
114115
115GType dbusmenu_client_get_type (void);116GType dbusmenu_client_get_type (void);
116DbusmenuClient * dbusmenu_client_new (const gchar * name,117DbusmenuClient * dbusmenu_client_new (const gchar * name,
@@ -119,6 +120,11 @@
119gboolean dbusmenu_client_add_type_handler (DbusmenuClient * client,120gboolean dbusmenu_client_add_type_handler (DbusmenuClient * client,
120 const gchar * type,121 const gchar * type,
121 DbusmenuClientTypeHandler newfunc);122 DbusmenuClientTypeHandler newfunc);
123gboolean dbusmenu_client_add_type_handler_full (DbusmenuClient * client,
124 const gchar * type,
125 DbusmenuClientTypeHandler newfunc,
126 gpointer user_data,
127 DbusmenuClientTypeDestroyHandler destory_func);
122void dbusmenu_client_send_event (DbusmenuClient * client,128void dbusmenu_client_send_event (DbusmenuClient * client,
123 gint id,129 gint id,
124 const gchar * name,130 const gchar * name,
125131
=== modified file 'libdbusmenu-gtk/Makefile.am'
--- libdbusmenu-gtk/Makefile.am 2011-01-21 16:35:55 +0000
+++ libdbusmenu-gtk/Makefile.am 2011-01-26 23:16:59 +0000
@@ -23,7 +23,8 @@
23 dbusmenu-gtk.h \23 dbusmenu-gtk.h \
24 client.h \24 client.h \
25 menu.h \25 menu.h \
26 menuitem.h26 menuitem.h \
27 serializablemenuitem.h
2728
28libdbusmenu_gtk_la_SOURCES = \29libdbusmenu_gtk_la_SOURCES = \
29 client.h \30 client.h \
@@ -33,7 +34,9 @@
33 menu.h \34 menu.h \
34 menu.c \35 menu.c \
35 menuitem.h \36 menuitem.h \
36 menuitem.c37 menuitem.c \
38 serializablemenuitem.h \
39 serializablemenuitem.c
3740
38libdbusmenu_gtk_la_LDFLAGS = \41libdbusmenu_gtk_la_LDFLAGS = \
39 -version-info $(LIBDBUSMENU_CURRENT):$(LIBDBUSMENU_REVISION):$(LIBDBUSMENU_AGE) \42 -version-info $(LIBDBUSMENU_CURRENT):$(LIBDBUSMENU_REVISION):$(LIBDBUSMENU_AGE) \
4043
=== modified file 'libdbusmenu-gtk/client.c'
--- libdbusmenu-gtk/client.c 2011-01-18 21:59:36 +0000
+++ libdbusmenu-gtk/client.c 2011-01-26 23:16:59 +0000
@@ -54,8 +54,8 @@
54static void move_child (DbusmenuMenuitem * mi, DbusmenuMenuitem * child, guint new, guint old, DbusmenuGtkClient * gtkclient);54static void move_child (DbusmenuMenuitem * mi, DbusmenuMenuitem * child, guint new, guint old, DbusmenuGtkClient * gtkclient);
55static void item_activate (DbusmenuClient * client, DbusmenuMenuitem * mi, guint timestamp, gpointer userdata);55static void item_activate (DbusmenuClient * client, DbusmenuMenuitem * mi, guint timestamp, gpointer userdata);
5656
57static gboolean new_item_normal (DbusmenuMenuitem * newitem, DbusmenuMenuitem * parent, DbusmenuClient * client);57static gboolean new_item_normal (DbusmenuMenuitem * newitem, DbusmenuMenuitem * parent, DbusmenuClient * client, gpointer user_data);
58static gboolean new_item_seperator (DbusmenuMenuitem * newitem, DbusmenuMenuitem * parent, DbusmenuClient * client);58static gboolean new_item_seperator (DbusmenuMenuitem * newitem, DbusmenuMenuitem * parent, DbusmenuClient * client, gpointer user_data);
5959
60static void process_visible (DbusmenuMenuitem * mi, GtkMenuItem * gmi, GVariant * value);60static void process_visible (DbusmenuMenuitem * mi, GtkMenuItem * gmi, GVariant * value);
61static void process_sensitive (DbusmenuMenuitem * mi, GtkMenuItem * gmi, GVariant * value);61static void process_sensitive (DbusmenuMenuitem * mi, GtkMenuItem * gmi, GVariant * value);
@@ -684,7 +684,7 @@
684/* The base type handler that builds a plain ol'684/* The base type handler that builds a plain ol'
685 GtkMenuItem to represent, well, the GtkMenuItem */685 GtkMenuItem to represent, well, the GtkMenuItem */
686static gboolean686static gboolean
687new_item_normal (DbusmenuMenuitem * newitem, DbusmenuMenuitem * parent, DbusmenuClient * client)687new_item_normal (DbusmenuMenuitem * newitem, DbusmenuMenuitem * parent, DbusmenuClient * client, gpointer user_data)
688{688{
689 g_return_val_if_fail(DBUSMENU_IS_MENUITEM(newitem), FALSE);689 g_return_val_if_fail(DBUSMENU_IS_MENUITEM(newitem), FALSE);
690 g_return_val_if_fail(DBUSMENU_IS_GTKCLIENT(client), FALSE);690 g_return_val_if_fail(DBUSMENU_IS_GTKCLIENT(client), FALSE);
@@ -719,7 +719,7 @@
719/* Type handler for the seperators where it builds719/* Type handler for the seperators where it builds
720 a GtkSeparator to act as the GtkMenuItem */720 a GtkSeparator to act as the GtkMenuItem */
721static gboolean721static gboolean
722new_item_seperator (DbusmenuMenuitem * newitem, DbusmenuMenuitem * parent, DbusmenuClient * client)722new_item_seperator (DbusmenuMenuitem * newitem, DbusmenuMenuitem * parent, DbusmenuClient * client, gpointer user_data)
723{723{
724 g_return_val_if_fail(DBUSMENU_IS_MENUITEM(newitem), FALSE);724 g_return_val_if_fail(DBUSMENU_IS_MENUITEM(newitem), FALSE);
725 g_return_val_if_fail(DBUSMENU_IS_GTKCLIENT(client), FALSE);725 g_return_val_if_fail(DBUSMENU_IS_GTKCLIENT(client), FALSE);
726726
=== modified file 'libdbusmenu-gtk/dbusmenu-gtk.h'
--- libdbusmenu-gtk/dbusmenu-gtk.h 2011-01-21 16:35:55 +0000
+++ libdbusmenu-gtk/dbusmenu-gtk.h 2011-01-26 23:16:59 +0000
@@ -36,5 +36,6 @@
36#include <libdbusmenu-gtk/client.h>36#include <libdbusmenu-gtk/client.h>
37#include <libdbusmenu-gtk/menu.h>37#include <libdbusmenu-gtk/menu.h>
38#include <libdbusmenu-gtk/menuitem.h>38#include <libdbusmenu-gtk/menuitem.h>
39#include <libdbusmenu-gtk/serializablemenuitem.h>
3940
40#endif /* __DBUSMENU_GLIB_H__ */41#endif /* __DBUSMENU_GLIB_H__ */
4142
=== modified file 'libdbusmenu-gtk/menuitem.h'
--- libdbusmenu-gtk/menuitem.h 2010-12-13 13:40:01 +0000
+++ libdbusmenu-gtk/menuitem.h 2011-01-26 23:16:59 +0000
@@ -26,8 +26,8 @@
26<http://www.gnu.org/licenses/>26<http://www.gnu.org/licenses/>
27*/27*/
2828
29#ifndef __DBUSMENU_GTKMENUITEM_H__29#ifndef DBUSMENU_GTK_MENUITEM_H__
30#define __DBUSMENU_GTKMENUITEM_H__ 130#define DBUSMENU_GTK_MENUITEM_H__ 1
3131
32#include <glib.h>32#include <glib.h>
33#include <gdk-pixbuf/gdk-pixbuf.h>33#include <gdk-pixbuf/gdk-pixbuf.h>
3434
=== added file 'libdbusmenu-gtk/serializablemenuitem.c'
--- libdbusmenu-gtk/serializablemenuitem.c 1970-01-01 00:00:00 +0000
+++ libdbusmenu-gtk/serializablemenuitem.c 2011-01-26 23:16:59 +0000
@@ -0,0 +1,288 @@
1/*
2An object to act as a base class for easy GTK widgets that can be
3transfered over dbusmenu.
4
5Copyright 2011 Canonical Ltd.
6
7Authors:
8 Ted Gould <ted@canonical.com>
9
10This program is free software: you can redistribute it and/or modify it
11under the terms of either or both of the following licenses:
12
131) the GNU Lesser General Public License version 3, as published by the
14Free Software Foundation; and/or
152) the GNU Lesser General Public License version 2.1, as published by
16the Free Software Foundation.
17
18This program is distributed in the hope that it will be useful, but
19WITHOUT ANY WARRANTY; without even the implied warranties of
20MERCHANTABILITY, SATISFACTORY QUALITY or FITNESS FOR A PARTICULAR
21PURPOSE. See the applicable version of the GNU Lesser General Public
22License for more details.
23
24You should have received a copy of both the GNU Lesser General Public
25License version 3 and version 2.1 along with this program. If not, see
26<http://www.gnu.org/licenses/>
27*/
28
29#ifdef HAVE_CONFIG_H
30#include "config.h"
31#endif
32
33#include "client.h"
34#include "serializablemenuitem.h"
35
36/**
37 DbusmenuGtkSerializableMenuItemPrivate:
38 @mi: Menuitem to watch the property changes from
39*/
40struct _DbusmenuGtkSerializableMenuItemPrivate {
41 DbusmenuMenuitem * mi;
42};
43
44/* Properties */
45enum {
46 PROP_0,
47 PROP_MENUITEM
48};
49
50/* Private macro, only used in object init */
51#define DBUSMENU_GTK_SERIALIZABLE_MENU_ITEM_GET_PRIVATE(o) \
52(G_TYPE_INSTANCE_GET_PRIVATE ((o), DBUSMENU_TYPE_GTK_SERIALIZABLE_MENU_ITEM, DbusmenuGtkSerializableMenuItemPrivate))
53
54/* Function prototypes */
55static void dbusmenu_gtk_serializable_menu_item_class_init (DbusmenuGtkSerializableMenuItemClass *klass);
56static void dbusmenu_gtk_serializable_menu_item_init (DbusmenuGtkSerializableMenuItem *self);
57static void dbusmenu_gtk_serializable_menu_item_dispose (GObject *object);
58static void dbusmenu_gtk_serializable_menu_item_finalize (GObject *object);
59static void set_property (GObject * obj,
60 guint id,
61 const GValue * value,
62 GParamSpec * pspec);
63static void get_property (GObject * obj,
64 guint id,
65 GValue * value,
66 GParamSpec * pspec);
67
68/* GObject boiler plate */
69G_DEFINE_TYPE (DbusmenuGtkSerializableMenuItem, dbusmenu_gtk_serializable_menu_item, GTK_TYPE_MENU_ITEM);
70
71/* Initialize the stuff in the class structure */
72static void
73dbusmenu_gtk_serializable_menu_item_class_init (DbusmenuGtkSerializableMenuItemClass *klass)
74{
75 GObjectClass *object_class = G_OBJECT_CLASS (klass);
76
77 g_type_class_add_private (klass, sizeof (DbusmenuGtkSerializableMenuItemPrivate));
78
79 object_class->dispose = dbusmenu_gtk_serializable_menu_item_dispose;
80 object_class->finalize = dbusmenu_gtk_serializable_menu_item_finalize;
81 object_class->set_property = set_property;
82 object_class->get_property = get_property;
83
84 g_object_class_install_property (object_class, PROP_MENUITEM,
85 g_param_spec_object(DBUSMENU_GTK_SERIALIZABLE_MENU_ITEM_PROP_MENUITEM, "DBusmenu Menuitem attached to item",
86 "A menuitem who's properties are being watched and where changes should be watched for updates. It is the responsibility of subclasses to set up the signal handlers for those property changes.",
87 DBUSMENU_TYPE_MENUITEM,
88 G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));
89
90 return;
91}
92
93/* Initialize the object structures and private structure */
94static void
95dbusmenu_gtk_serializable_menu_item_init (DbusmenuGtkSerializableMenuItem *self)
96{
97 self->priv = DBUSMENU_GTK_SERIALIZABLE_MENU_ITEM_GET_PRIVATE(self);
98
99 self->priv->mi = NULL;
100
101 return;
102}
103
104/* Free all references to objects */
105static void
106dbusmenu_gtk_serializable_menu_item_dispose (GObject *object)
107{
108 DbusmenuGtkSerializableMenuItem * smi = DBUSMENU_GTK_SERIALIZABLE_MENU_ITEM(object);
109 g_return_if_fail(smi != NULL);
110
111 if (smi->priv->mi != NULL) {
112 g_object_unref(G_OBJECT(smi->priv->mi));
113 smi->priv->mi = NULL;
114 }
115
116
117 G_OBJECT_CLASS (dbusmenu_gtk_serializable_menu_item_parent_class)->dispose (object);
118 return;
119}
120
121/* Free memory */
122static void
123dbusmenu_gtk_serializable_menu_item_finalize (GObject *object)
124{
125
126
127
128 G_OBJECT_CLASS (dbusmenu_gtk_serializable_menu_item_parent_class)->finalize (object);
129 return;
130}
131
132/* Set an object property */
133static void
134set_property (GObject * obj, guint id, const GValue * value, GParamSpec * pspec)
135{
136 DbusmenuGtkSerializableMenuItem * smi = DBUSMENU_GTK_SERIALIZABLE_MENU_ITEM(obj);
137
138 switch (id) {
139 case PROP_MENUITEM:
140 smi->priv->mi = g_value_get_object(value);
141 break;
142 default:
143 g_return_if_reached();
144 break;
145 }
146
147 return;
148}
149
150/* Get an object property */
151static void
152get_property (GObject * obj, guint id, GValue * value, GParamSpec * pspec)
153{
154 DbusmenuGtkSerializableMenuItem * smi = DBUSMENU_GTK_SERIALIZABLE_MENU_ITEM(obj);
155
156 switch (id) {
157 case PROP_MENUITEM:
158 g_value_set_object(value, smi->priv->mi);
159 break;
160 default:
161 g_return_if_reached();
162 break;
163 }
164
165 return;
166}
167
168/**
169 dbusmenu_gtk_serializable_menu_item_build_dbusmenu_menuitem:
170 @smi: #DbusmenuGtkSerializableMenuItem to build a #DbusmenuMenuitem mirroring
171
172 This function is for menu items that are instanciated from
173 GTK and have their properites set using GTK functions. This
174 builds a #DbusmenuMenuitem that then has the properties that
175 should be sent over the bus to create a new item of this
176 type on the other side.
177
178 Return value: (transfer full) A #DbusmenuMenuitem who's values will be
179 set by this object.
180*/
181DbusmenuMenuitem *
182dbusmenu_gtk_serializable_menu_item_build_dbusmenu_menuitem (DbusmenuGtkSerializableMenuItem * smi)
183{
184 g_return_val_if_fail(DBUSMENU_IS_GTK_SERIALIZABLE_MENU_ITEM(smi), NULL);
185
186 DbusmenuGtkSerializableMenuItemClass * klass = DBUSMENU_GTK_SERIALIZABLE_MENU_ITEM_GET_CLASS(smi);
187 if (klass->build_dbusmenu_menuitem != NULL) {
188 return klass->build_dbusmenu_menuitem(smi);
189 }
190
191 return NULL;
192}
193
194/* Callback to the generic type handler */
195typedef struct _type_handler_t type_handler_t;
196struct _type_handler_t {
197 DbusmenuGtkSerializableMenuItemClass * class;
198 GType type;
199};
200
201/* Handle the type with this item. */
202static gboolean
203type_handler (DbusmenuMenuitem * newitem, DbusmenuMenuitem * parent, DbusmenuClient * client, gpointer user_data)
204{
205 type_handler_t * th = (type_handler_t *)user_data;
206
207 DbusmenuGtkSerializableMenuItem * smi = DBUSMENU_GTK_SERIALIZABLE_MENU_ITEM(g_object_new(th->type, NULL));
208 g_return_val_if_fail(smi != NULL, FALSE);
209
210 dbusmenu_gtk_serializable_menu_item_set_dbusmenu_menuitem(smi, newitem);
211 dbusmenu_gtkclient_newitem_base(DBUSMENU_GTKCLIENT(client), newitem, GTK_MENU_ITEM(smi), parent);
212
213 return TRUE;
214}
215
216/* Destruction is inevitable */
217static void
218type_destroy_handler (DbusmenuClient * client, const gchar * type, gpointer user_data)
219{
220 g_return_if_fail(user_data != NULL);
221 type_handler_t * th = (type_handler_t *)user_data;
222 g_type_class_unref(th->class);
223 g_free(user_data);
224 return;
225}
226
227/**
228 dbusmenu_gtk_serializable_menu_item_register_to_client:
229 @client: #DbusmenuClient that we should register a type at.
230 @item_type: The #GType of a class that is a subclass of #DbusmenuGtkSerializableMenuItem
231
232 Registers a generic handler for dealing with all subclasses of
233 #DbusmenuGtkSerializableMenuItem. This handler responds to the callback,
234 creates a new object and attaches it to the appropriate #DbusmenuMenuitem
235 object.
236*/
237void
238dbusmenu_gtk_serializable_menu_item_register_to_client (DbusmenuClient * client, GType item_type)
239{
240 g_return_if_fail(g_type_is_a(item_type, DBUSMENU_TYPE_GTK_SERIALIZABLE_MENU_ITEM));
241
242 gpointer type_class = g_type_class_ref(item_type);
243 g_return_if_fail(type_class != NULL);
244
245 DbusmenuGtkSerializableMenuItemClass * class = DBUSMENU_GTK_SERIALIZABLE_MENU_ITEM_CLASS(type_class);
246
247 if (class->get_type_string == NULL) {
248 g_type_class_unref(type_class);
249 g_error("No 'get_type_string' in subclass of DbusmenuGtkSerializableMenuItem");
250 return;
251 }
252
253 /* Register type */
254 type_handler_t * th = g_new0(type_handler_t, 1);
255 th->class = class;
256 th->type = item_type;
257 if (!dbusmenu_client_add_type_handler_full(client, class->get_type_string(), type_handler, th, type_destroy_handler)) {
258 type_destroy_handler(client, class->get_type_string(), th);
259 }
260
261 /* Register defaults */
262 /* TODO: Need API on another branch */
263
264 return;
265}
266
267/**
268 dbusmenu_gtk_serializable_menu_item_set_dbusmenu_menuitem:
269 @smi: #DbusmenuGtkSerializableMenuItem to set the @DbusmenuGtkSerializableMenuItem::dbusmenu-menuitem of
270 @mi: Menuitem to get the properties from
271
272 This function is used on the server side to signal to the object
273 that it should get its' property change events from @mi instead
274 of expecting calls to its' API. A call to this function sets the
275 property and subclasses should listen to the notify signal to
276 pick up this property being set.
277*/
278void
279dbusmenu_gtk_serializable_menu_item_set_dbusmenu_menuitem (DbusmenuGtkSerializableMenuItem * smi, DbusmenuMenuitem * mi)
280{
281 g_return_if_fail(DBUSMENU_IS_GTK_SERIALIZABLE_MENU_ITEM(smi));
282 g_return_if_fail(mi != NULL);
283
284 smi->priv->mi = mi;
285 g_object_notify(G_OBJECT(smi), DBUSMENU_GTK_SERIALIZABLE_MENU_ITEM_PROP_MENUITEM);
286
287 return;
288}
0289
=== added file 'libdbusmenu-gtk/serializablemenuitem.h'
--- libdbusmenu-gtk/serializablemenuitem.h 1970-01-01 00:00:00 +0000
+++ libdbusmenu-gtk/serializablemenuitem.h 2011-01-26 23:16:59 +0000
@@ -0,0 +1,108 @@
1/*
2An object to act as a base class for easy GTK widgets that can be
3transfered over dbusmenu.
4
5Copyright 2011 Canonical Ltd.
6
7Authors:
8 Ted Gould <ted@canonical.com>
9
10This program is free software: you can redistribute it and/or modify it
11under the terms of either or both of the following licenses:
12
131) the GNU Lesser General Public License version 3, as published by the
14Free Software Foundation; and/or
152) the GNU Lesser General Public License version 2.1, as published by
16the Free Software Foundation.
17
18This program is distributed in the hope that it will be useful, but
19WITHOUT ANY WARRANTY; without even the implied warranties of
20MERCHANTABILITY, SATISFACTORY QUALITY or FITNESS FOR A PARTICULAR
21PURPOSE. See the applicable version of the GNU Lesser General Public
22License for more details.
23
24You should have received a copy of both the GNU Lesser General Public
25License version 3 and version 2.1 along with this program. If not, see
26<http://www.gnu.org/licenses/>
27*/
28
29#ifndef DBUSMENU_GTK_SERIALIZABLE_MENU_ITEM_H__
30#define DBUSMENU_GTK_SERIALIZABLE_MENU_ITEM_H__ 1
31
32#include <glib.h>
33#include <glib-object.h>
34#include <gtk/gtk.h>
35#include <libdbusmenu-glib/menuitem.h>
36#include <libdbusmenu-glib/client.h>
37
38G_BEGIN_DECLS
39
40#define DBUSMENU_TYPE_GTK_SERIALIZABLE_MENU_ITEM (dbusmenu_gtk_serializable_menu_item_get_type ())
41#define DBUSMENU_GTK_SERIALIZABLE_MENU_ITEM(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), DBUSMENU_TYPE_GTK_SERIALIZABLE_MENU_ITEM, DbusmenuGtkSerializableMenuItem))
42#define DBUSMENU_GTK_SERIALIZABLE_MENU_ITEM_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), DBUSMENU_TYPE_GTK_SERIALIZABLE_MENU_ITEM, DbusmenuGtkSerializableMenuItemClass))
43#define DBUSMENU_IS_GTK_SERIALIZABLE_MENU_ITEM(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), DBUSMENU_TYPE_GTK_SERIALIZABLE_MENU_ITEM))
44#define DBUSMENU_IS_GTK_SERIALIZABLE_MENU_ITEM_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), DBUSMENU_TYPE_GTK_SERIALIZABLE_MENU_ITEM))
45#define DBUSMENU_GTK_SERIALIZABLE_MENU_ITEM_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), DBUSMENU_TYPE_GTK_SERIALIZABLE_MENU_ITEM, DbusmenuGtkSerializableMenuItemClass))
46
47#define DBUSMENU_GTK_SERIALIZABLE_MENU_ITEM_PROP_MENUITEM "dbusmenu-menuitem"
48
49typedef struct _DbusmenuGtkSerializableMenuItem DbusmenuGtkSerializableMenuItem;
50typedef struct _DbusmenuGtkSerializableMenuItemClass DbusmenuGtkSerializableMenuItemClass;
51typedef struct _DbusmenuGtkSerializableMenuItemPrivate DbusmenuGtkSerializableMenuItemPrivate;
52
53/**
54 DbusmenuGtkSerializableMenuItemClass:
55 @parent_class: Inherit from GtkMenuItem
56 @get_type_string: Static function to get a string describing this type
57 @get_default_properties: Return a hashtable of defaults for the menu item type
58 @build_dbusmenu_menuitem: Build a menuitem that can be sent over dbus
59 @_dbusmenu_gtk_serializable_menu_item_reserved1: Reserved for future use.
60 @_dbusmenu_gtk_serializable_menu_item_reserved2: Reserved for future use.
61 @_dbusmenu_gtk_serializable_menu_item_reserved3: Reserved for future use.
62 @_dbusmenu_gtk_serializable_menu_item_reserved4: Reserved for future use.
63 @_dbusmenu_gtk_serializable_menu_item_reserved5: Reserved for future use.
64 @_dbusmenu_gtk_serializable_menu_item_reserved6: Reserved for future use.
65*/
66struct _DbusmenuGtkSerializableMenuItemClass {
67 GtkMenuItemClass parent_class;
68
69 /* Subclassable functions */
70 const gchar * (*get_type_string) (void);
71 GHashTable * (*get_default_properties) (void);
72
73 DbusmenuMenuitem * (*build_dbusmenu_menuitem) (DbusmenuGtkSerializableMenuItem * smi);
74
75 /* Signals */
76
77
78
79 /* Empty Space */
80 /*< Private >*/
81 void (*_dbusmenu_gtk_serializable_menu_item_reserved1) (void);
82 void (*_dbusmenu_gtk_serializable_menu_item_reserved2) (void);
83 void (*_dbusmenu_gtk_serializable_menu_item_reserved3) (void);
84 void (*_dbusmenu_gtk_serializable_menu_item_reserved4) (void);
85 void (*_dbusmenu_gtk_serializable_menu_item_reserved5) (void);
86 void (*_dbusmenu_gtk_serializable_menu_item_reserved6) (void);
87};
88
89/**
90 DbusmenuGtkSerializableMenuItem:
91 @parent: Inherit from GtkMenuItem
92 @priv: Blind structure of private variables
93*/
94struct _DbusmenuGtkSerializableMenuItem {
95 GtkMenuItem parent;
96
97 DbusmenuGtkSerializableMenuItemPrivate * priv;
98};
99
100GType dbusmenu_gtk_serializable_menu_item_get_type (void);
101
102DbusmenuMenuitem * dbusmenu_gtk_serializable_menu_item_build_dbusmenu_menuitem (DbusmenuGtkSerializableMenuItem * smi);
103void dbusmenu_gtk_serializable_menu_item_register_to_client (DbusmenuClient * client, GType item_type);
104void dbusmenu_gtk_serializable_menu_item_set_dbusmenu_menuitem (DbusmenuGtkSerializableMenuItem * smi, DbusmenuMenuitem * mi);
105
106G_END_DECLS
107
108#endif

Subscribers

People subscribed via source and target branches