1
/* This file is part of Maliit framework
3
* Copyright (C) 2012 One Laptop per Child Association
5
* Contact: maliit-discuss@lists.maliit.org
7
* This library is free software; you can redistribute it and/or
8
* modify it under the terms of the GNU Lesser General Public
9
* License as published by the Free Software Foundation; either
10
* version 2.1 of the licence, or (at your option) any later version.
12
* This library is distributed in the hope that it will be useful,
13
* but WITHOUT ANY WARRANTY; without even the implied warranty of
14
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15
* Lesser General Public License for more details.
17
* You should have received a copy of the GNU Lesser General Public
18
* License along with this library; if not, write to the
19
* Free Software Foundation, Inc., 59 Temple Place - Suite 330,
20
* Boston, MA 02111-1307, USA.
23
#include <dbus/dbus-glib.h>
25
#include "maliitattributeextensionregistry.h"
26
#include "maliitmarshallers.h"
27
#include "meego-im-connector.h"
29
struct _MaliitAttributeExtensionRegistryPrivate
31
GHashTable *extensions;
34
static MaliitAttributeExtensionRegistry *global_singleton;
36
G_DEFINE_TYPE (MaliitAttributeExtensionRegistry, maliit_attribute_extension_registry, G_TYPE_OBJECT)
39
maliit_attribute_extension_registry_finalize (GObject *object)
41
global_singleton = NULL;
43
G_OBJECT_CLASS (maliit_attribute_extension_registry_parent_class)->finalize (object);
47
extension_notify (gpointer data,
48
GObject *where_the_object_was)
50
MaliitAttributeExtensionRegistry *registry = MALIIT_ATTRIBUTE_EXTENSION_REGISTRY (data);
51
MaliitAttributeExtensionRegistryPrivate *priv = registry->priv;
53
MaliitAttributeExtension *extension;
55
g_hash_table_iter_init (&iter, priv->extensions);
56
while (g_hash_table_iter_next (&iter, NULL, (gpointer *)&extension)) {
57
if ((gpointer)extension == (gpointer)where_the_object_was) {
58
g_hash_table_iter_steal (&iter);
65
maliit_attribute_extension_registry_dispose (GObject *object)
67
MaliitAttributeExtensionRegistry *registry = MALIIT_ATTRIBUTE_EXTENSION_REGISTRY (object);
68
MaliitAttributeExtensionRegistryPrivate *priv = registry->priv;
70
if (priv->extensions) {
71
GHashTable *extensions = priv->extensions;
73
priv->extensions = NULL;
74
g_hash_table_unref (extensions);
77
G_OBJECT_CLASS (maliit_attribute_extension_registry_parent_class)->dispose (object);
81
maliit_attribute_extension_registry_constructor (GType type,
83
GObjectConstructParam *params)
87
if (global_singleton) {
88
object = g_object_ref (G_OBJECT (global_singleton));
90
object = G_OBJECT_CLASS (maliit_attribute_extension_registry_parent_class)->constructor (type,
93
/* We are doing an additional reference here, so object will not
94
* be destroyed when last owner removes its reference. This is a
95
* leak, but for now it ensures that singleton have a lifetime of
96
* application. This needs to be fixed, when object lifetimes are
97
* fixed in gtk-input-context. */
98
global_singleton = MALIIT_ATTRIBUTE_EXTENSION_REGISTRY (g_object_ref (object));
105
maliit_attribute_extension_registry_class_init (MaliitAttributeExtensionRegistryClass *registry_class)
107
GObjectClass *g_object_class = G_OBJECT_CLASS (registry_class);
109
g_object_class->finalize = maliit_attribute_extension_registry_finalize;
110
g_object_class->dispose = maliit_attribute_extension_registry_dispose;
111
g_object_class->constructor = maliit_attribute_extension_registry_constructor;
113
g_type_class_add_private (registry_class, sizeof (MaliitAttributeExtensionRegistryPrivate));
117
extension_weak_unref (MaliitAttributeExtension *extension,
118
MaliitAttributeExtensionRegistry *registry)
120
g_object_weak_unref (G_OBJECT (extension),
126
extension_weak_unref_global (gpointer data)
128
MaliitAttributeExtension *extension = MALIIT_ATTRIBUTE_EXTENSION (data);
130
extension_weak_unref (extension,
135
register_all_extensions (MeegoIMProxy *proxy, gpointer user_data)
137
MaliitAttributeExtensionRegistry *registry = user_data;
138
GList *extensions = maliit_attribute_extension_registry_get_extensions (registry);
141
for (iter = extensions; iter; iter = iter->next) {
142
MaliitAttributeExtension *extension = MALIIT_ATTRIBUTE_EXTENSION (iter->data);
144
if (!meego_im_proxy_register_extension (proxy,
145
maliit_attribute_extension_get_id (extension),
146
maliit_attribute_extension_get_filename (extension))) {
147
g_warning ("Could not register an extension in mass registerer - no proxy");
149
GHashTable *attributes = maliit_attribute_extension_get_attributes (extension);
150
GHashTableIter attributes_iter;
154
g_hash_table_iter_init (&attributes_iter, attributes);
156
while (g_hash_table_iter_next (&attributes_iter, &key, &value)) {
157
maliit_attribute_extension_registry_extension_changed(registry, extension, key, value);
162
g_list_free (extensions);
166
maliit_attribute_extension_registry_init (MaliitAttributeExtensionRegistry *registry)
168
MeegoImConnector *connector = meego_im_connector_get_singleton();
170
MaliitAttributeExtensionRegistryPrivate *priv = G_TYPE_INSTANCE_GET_PRIVATE (registry,
171
MALIIT_TYPE_ATTRIBUTE_EXTENSION_REGISTRY,
172
MaliitAttributeExtensionRegistryPrivate);
174
priv->extensions = g_hash_table_new_full (g_direct_hash,
177
extension_weak_unref_global);
178
registry->priv = priv;
180
g_signal_connect(connector->proxy, "connection-established",
181
G_CALLBACK(register_all_extensions), registry);
184
MaliitAttributeExtensionRegistry *
185
maliit_attribute_extension_registry_get_instance (void)
187
return MALIIT_ATTRIBUTE_EXTENSION_REGISTRY (g_object_new (MALIIT_TYPE_ATTRIBUTE_EXTENSION_REGISTRY,
192
maliit_attribute_extension_registry_add_extension (MaliitAttributeExtensionRegistry *registry,
193
MaliitAttributeExtension *extension)
195
GHashTable *extensions;
198
g_return_if_fail (MALIIT_IS_ATTRIBUTE_EXTENSION_REGISTRY (registry));
199
g_return_if_fail (MALIIT_IS_ATTRIBUTE_EXTENSION (extension));
201
extensions = registry->priv->extensions;
202
id = maliit_attribute_extension_get_id (extension);
204
if (!g_hash_table_lookup_extended (extensions, GINT_TO_POINTER (id), NULL, NULL)) {
205
MeegoImConnector *connector = meego_im_connector_get_singleton();
207
g_object_weak_ref (G_OBJECT (extension),
211
g_hash_table_insert (extensions,
212
GINT_TO_POINTER (id),
214
meego_im_proxy_register_extension(connector->proxy,
216
maliit_attribute_extension_get_filename (extension));
221
maliit_attribute_extension_registry_remove_extension (MaliitAttributeExtensionRegistry *registry,
222
MaliitAttributeExtension *extension)
224
GHashTable *extensions;
227
g_return_if_fail (MALIIT_IS_ATTRIBUTE_EXTENSION_REGISTRY (registry));
228
g_return_if_fail (MALIIT_IS_ATTRIBUTE_EXTENSION (extension));
230
extensions = registry->priv->extensions;
231
id = maliit_attribute_extension_get_id (extension);
233
if (g_hash_table_lookup_extended (extensions, GINT_TO_POINTER (id), NULL, NULL)) {
234
MeegoImConnector *connector = meego_im_connector_get_singleton();
236
g_hash_table_remove (extensions,
237
GINT_TO_POINTER (id));
238
meego_im_proxy_unregister_extension(connector->proxy,
243
/* For glib < 2.30 */
245
#define G_VALUE_INIT { 0, { { 0 } } }
249
maliit_attribute_extension_registry_extension_changed (MaliitAttributeExtensionRegistry *registry,
250
MaliitAttributeExtension *extension,
256
g_return_if_fail (MALIIT_IS_ATTRIBUTE_EXTENSION_REGISTRY (registry));
257
g_return_if_fail (MALIIT_IS_ATTRIBUTE_EXTENSION (extension));
258
g_return_if_fail (key != NULL);
259
g_return_if_fail (value != NULL);
261
parts = g_strsplit (key + 1, "/", 3);
266
if (g_strv_length (parts) == 3) {
267
GValue g_value = G_VALUE_INIT;
269
dbus_g_value_parse_g_variant (value, &g_value);
270
if (G_VALUE_TYPE (&g_value) != G_TYPE_INVALID) {
271
MeegoImConnector *connector = meego_im_connector_get_singleton();
272
gchar *target = g_strdup_printf ("/%s", parts[0]);
274
meego_im_proxy_set_extended_attribute (connector->proxy,
275
maliit_attribute_extension_get_id(extension),
281
g_value_unset (&g_value);
283
g_warning ("Could not convert variant into value");
286
g_warning("Key `%s' is not valid. It needs to be `/target/item/key'", key);
292
fill_list_with_extensions (gpointer key G_GNUC_UNUSED,
296
MaliitAttributeExtension *extension = MALIIT_ATTRIBUTE_EXTENSION (value);
297
GList **list = (GList **)user_data;
299
*list = g_list_prepend (*list, extension);
303
maliit_attribute_extension_registry_get_extensions (MaliitAttributeExtensionRegistry *registry)
307
g_return_val_if_fail (MALIIT_IS_ATTRIBUTE_EXTENSION_REGISTRY (registry), NULL);
310
g_hash_table_foreach (registry->priv->extensions,
311
fill_list_with_extensions,
318
maliit_attribute_extension_registry_update_attribute (MaliitAttributeExtensionRegistry *registry,
321
const gchar *target_item,
322
const gchar *attribute,
325
MaliitAttributeExtension *extension;
327
g_return_if_fail (MALIIT_IS_ATTRIBUTE_EXTENSION_REGISTRY (registry));
328
g_return_if_fail (id >= 0);
329
g_return_if_fail (target != NULL);
330
g_return_if_fail (target_item != NULL);
331
g_return_if_fail (attribute != NULL);
332
g_return_if_fail (value != NULL);
334
if (g_hash_table_lookup_extended (registry->priv->extensions,
335
GINT_TO_POINTER (id),
337
(gpointer *)&extension)) {
338
gchar *key = g_strdup_printf ("%s/%s/%s", target, target_item, attribute);
340
maliit_attribute_extension_update_attribute (extension,
345
g_warning ("Extension %d was not found.", id);