1 /* vim:set et sts=4: */
2 /* ibus - The Input Bus
3 * Copyright (C) 2008-2009 Peng Huang <shawn.p.huang@gmail.com>
5 * This library is free software; you can redistribute it and/or
6 * modify it under the terms of the GNU Lesser General Public
7 * License as published by the Free Software Foundation; either
8 * version 2 of the License, or (at your option) any later version.
10 * This library is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 * Lesser General Public License for more details.
15 * You should have received a copy of the GNU Lesser General Public
16 * License along with this library; if not, write to the
17 * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
18 * Boston, MA 02111-1307, USA.
21 #include "ibusfactory.h"
22 #include "ibusengine.h"
23 #include "ibusshare.h"
24 #include "ibusinternal.h"
26 #define IBUS_FACTORY_GET_PRIVATE(o) \
27 (G_TYPE_INSTANCE_GET_PRIVATE ((o), IBUS_TYPE_FACTORY, IBusFactoryPrivate))
34 struct _IBusFactoryPrivate {
36 IBusConnection *connection;
38 GHashTable *engine_table;
40 typedef struct _IBusFactoryPrivate IBusFactoryPrivate;
42 /* functions prototype */
43 static void ibus_factory_class_init (IBusFactoryClass *klass);
44 static void ibus_factory_init (IBusFactory *factory);
45 static void ibus_factory_destroy (IBusFactory *factory);
46 static gboolean ibus_factory_ibus_message (IBusFactory *factory,
47 IBusConnection *connection,
48 IBusMessage *message);
50 static void _engine_destroy_cb (IBusEngine *engine,
51 IBusFactory *factory);
52 static void ibus_factory_info_class_init(IBusFactoryInfoClass *klass);
53 static void ibus_factory_info_init (IBusFactoryInfo *info);
54 static void ibus_factory_info_destroy (IBusFactoryInfo *info);
55 static gboolean ibus_factory_info_serialize (IBusFactoryInfo *info,
56 IBusMessageIter *iter);
57 static gboolean ibus_factory_info_deserialize
58 (IBusFactoryInfo *info,
59 IBusMessageIter *iter);
60 static gboolean ibus_factory_info_copy (IBusFactoryInfo *dest,
61 const IBusFactoryInfo *src);
63 static IBusServiceClass *factory_parent_class = NULL;
64 static IBusSerializableClass *factory_info_parent_class = NULL;
67 ibus_factory_get_type (void)
69 static GType type = 0;
71 static const GTypeInfo type_info = {
72 sizeof (IBusFactoryClass),
74 (GBaseFinalizeFunc) NULL,
75 (GClassInitFunc) ibus_factory_class_init,
76 NULL, /* class finalize */
77 NULL, /* class data */
80 (GInstanceInitFunc) ibus_factory_init,
84 type = g_type_register_static (IBUS_TYPE_SERVICE,
93 ibus_factory_new (IBusConnection *connection)
95 g_assert (IBUS_IS_CONNECTION (connection));
98 IBusFactoryPrivate *priv;
100 factory = (IBusFactory *) g_object_new (IBUS_TYPE_FACTORY,
101 "path", IBUS_PATH_FACTORY,
103 priv = IBUS_FACTORY_GET_PRIVATE (factory);
105 priv->connection = g_object_ref (connection);
106 ibus_service_add_to_connection ((IBusService *)factory, connection);
112 ibus_factory_class_init (IBusFactoryClass *klass)
114 // GObjectClass *gobject_class = G_OBJECT_CLASS (klass);
115 IBusObjectClass *ibus_object_class = IBUS_OBJECT_CLASS (klass);
117 factory_parent_class = (IBusServiceClass *) g_type_class_peek_parent (klass);
119 g_type_class_add_private (klass, sizeof (IBusFactoryPrivate));
121 ibus_object_class->destroy = (IBusObjectDestroyFunc) ibus_factory_destroy;
123 IBUS_SERVICE_CLASS (klass)->ibus_message = (ServiceIBusMessageFunc) ibus_factory_ibus_message;
128 ibus_factory_init (IBusFactory *factory)
130 IBusFactoryPrivate *priv;
131 priv = IBUS_FACTORY_GET_PRIVATE (factory);
134 priv->connection = NULL;
135 priv->engine_table = g_hash_table_new_full (g_str_hash,
139 priv->engine_list = NULL;
143 ibus_factory_destroy (IBusFactory *factory)
146 IBusFactoryPrivate *priv;
147 priv = IBUS_FACTORY_GET_PRIVATE (factory);
149 list = g_list_copy (priv->engine_list);
150 g_list_foreach (list, (GFunc) ibus_object_destroy, NULL);
151 g_list_free (priv->engine_list);
153 priv->engine_list = NULL;
155 if (priv->engine_table) {
156 g_hash_table_destroy (priv->engine_table);
159 if (priv->connection) {
160 ibus_service_remove_from_connection ((IBusService *)factory,
162 g_object_unref (priv->connection);
165 IBUS_OBJECT_CLASS(factory_parent_class)->destroy (IBUS_OBJECT (factory));
169 _engine_destroy_cb (IBusEngine *engine,
170 IBusFactory *factory)
172 IBusFactoryPrivate *priv;
173 priv = IBUS_FACTORY_GET_PRIVATE (factory);
175 priv->engine_list = g_list_remove (priv->engine_list, engine);
176 g_object_unref (engine);
180 ibus_factory_ibus_message (IBusFactory *factory,
181 IBusConnection *connection,
182 IBusMessage *message)
184 g_assert (IBUS_IS_FACTORY (factory));
185 g_assert (IBUS_IS_CONNECTION (connection));
186 g_assert (message != NULL);
188 IBusMessage *reply_message;
189 IBusFactoryPrivate *priv;
190 priv = IBUS_FACTORY_GET_PRIVATE (factory);
192 g_assert (priv->connection == connection);
194 if (ibus_message_is_method_call (message,
195 IBUS_INTERFACE_FACTORY,
204 retval = ibus_message_get_args (message,
206 G_TYPE_STRING, &engine_name,
210 reply_message = ibus_message_new_error_printf (message,
211 DBUS_ERROR_INVALID_ARGS,
212 "The 1st arg should be engine name");
213 ibus_connection_send (connection, reply_message);
214 ibus_message_unref (reply_message);
218 engine_type = (GType )g_hash_table_lookup (priv->engine_table, engine_name);
220 if (engine_type == G_TYPE_INVALID) {
221 reply_message = ibus_message_new_error_printf (message,
223 "Can not create engine %s", engine_name);
224 ibus_connection_send (connection, reply_message);
225 ibus_message_unref (reply_message);
230 path = g_strdup_printf ("/org/freedesktop/IBus/Engine/%d", ++priv->id);
232 engine = g_object_new (engine_type,
235 "connection", priv->connection,
238 priv->engine_list = g_list_append (priv->engine_list, engine);
239 g_signal_connect (engine,
241 G_CALLBACK (_engine_destroy_cb),
244 reply_message = ibus_message_new_method_return (message);
245 ibus_message_append_args (reply_message,
246 IBUS_TYPE_OBJECT_PATH, &path,
249 ibus_connection_send (connection, reply_message);
250 ibus_message_unref (reply_message);
254 return factory_parent_class->ibus_message ((IBusService *)factory,
260 ibus_factory_add_engine (IBusFactory *factory,
261 const gchar *engine_name,
264 g_assert (IBUS_IS_FACTORY (factory));
265 g_assert (engine_name);
266 g_assert (g_type_is_a (engine_type, IBUS_TYPE_ENGINE));
268 IBusFactoryPrivate *priv;
269 priv = IBUS_FACTORY_GET_PRIVATE (factory);
271 g_hash_table_insert (priv->engine_table, g_strdup (engine_name), (gpointer) engine_type);
276 ibus_factory_get_info (IBusFactory *factory)
278 IBusFactoryPrivate *priv;
279 priv = IBUS_FACTORY_GET_PRIVATE (factory);
286 ibus_factory_info_get_type (void)
288 static GType type = 0;
290 static const GTypeInfo type_info = {
291 sizeof (IBusFactoryInfoClass),
292 (GBaseInitFunc) NULL,
293 (GBaseFinalizeFunc) NULL,
294 (GClassInitFunc) ibus_factory_info_class_init,
295 NULL, /* class finialize */
296 NULL, /* class data */
297 sizeof (IBusFactoryInfo),
299 (GInstanceInitFunc) ibus_factory_info_init,
303 type = g_type_register_static (IBUS_TYPE_SERIALIZABLE,
313 ibus_factory_info_class_init (IBusFactoryInfoClass *klass)
315 IBusObjectClass *object_class = IBUS_OBJECT_CLASS (klass);
316 IBusSerializableClass *serializable_class = IBUS_SERIALIZABLE_CLASS (klass);
318 factory_info_parent_class = (IBusSerializableClass *) g_type_class_peek_parent (klass);
320 object_class->destroy = (IBusObjectDestroyFunc) ibus_factory_info_destroy;
322 serializable_class->serialize = (IBusSerializableSerializeFunc) ibus_factory_info_serialize;
323 serializable_class->deserialize = (IBusSerializableDeserializeFunc) ibus_factory_info_deserialize;
324 serializable_class->copy = (IBusSerializableCopyFunc) ibus_factory_info_copy;
326 g_string_append (serializable_class->signature, "osssss");
330 ibus_factory_info_init (IBusFactoryInfo *info)
336 info->authors = NULL;
337 info->credits = NULL;
341 ibus_factory_info_destroy (IBusFactoryInfo *info)
347 g_free (info->authors);
348 g_free (info->credits);
354 info->authors = NULL;
355 info->credits = NULL;
357 IBUS_OBJECT_CLASS (factory_info_parent_class)->destroy ((IBusObject *)info);
361 ibus_factory_info_serialize (IBusFactoryInfo *info,
362 IBusMessageIter *iter)
366 retval = factory_info_parent_class->serialize ((IBusSerializable *)info, iter);
367 g_return_val_if_fail (retval, FALSE);
369 retval = ibus_message_iter_append (iter, IBUS_TYPE_OBJECT_PATH, &info->path);
370 g_return_val_if_fail (retval, FALSE);
372 retval = ibus_message_iter_append (iter, G_TYPE_STRING, &info->name);
373 g_return_val_if_fail (retval, FALSE);
375 retval = ibus_message_iter_append (iter, G_TYPE_STRING, &info->lang);
376 g_return_val_if_fail (retval, FALSE);
378 retval = ibus_message_iter_append (iter, G_TYPE_STRING, &info->icon);
379 g_return_val_if_fail (retval, FALSE);
381 retval = ibus_message_iter_append (iter, G_TYPE_STRING, &info->authors);
382 g_return_val_if_fail (retval, FALSE);
384 retval = ibus_message_iter_append (iter, G_TYPE_STRING, &info->credits);
385 g_return_val_if_fail (retval, FALSE);
391 ibus_factory_info_deserialize (IBusFactoryInfo *info,
392 IBusMessageIter *iter)
396 retval = factory_info_parent_class->deserialize ((IBusSerializable *)info, iter);
397 g_return_val_if_fail (retval, FALSE);
399 retval = ibus_message_iter_get (iter, IBUS_TYPE_OBJECT_PATH, &info->path);
400 g_return_val_if_fail (retval, FALSE);
401 ibus_message_iter_next (iter);
402 info->path = g_strdup (info->path);
404 retval = ibus_message_iter_get (iter, G_TYPE_STRING, &info->name);
405 g_return_val_if_fail (retval, FALSE);
406 ibus_message_iter_next (iter);
407 info->name = g_strdup (info->name);
409 retval = ibus_message_iter_get (iter, G_TYPE_STRING, &info->lang);
410 g_return_val_if_fail (retval, FALSE);
411 ibus_message_iter_next (iter);
412 info->lang = g_strdup (info->lang);
414 retval = ibus_message_iter_get (iter, G_TYPE_STRING, &info->icon);
415 g_return_val_if_fail (retval, FALSE);
416 ibus_message_iter_next (iter);
417 info->icon = g_strdup (info->icon);
419 retval = ibus_message_iter_get (iter, G_TYPE_STRING, &info->authors);
420 g_return_val_if_fail (retval, FALSE);
421 ibus_message_iter_next (iter);
422 info->authors = g_strdup (info->authors);
424 retval = ibus_message_iter_get (iter, G_TYPE_STRING, &info->credits);
425 g_return_val_if_fail (retval, FALSE);
426 ibus_message_iter_next (iter);
427 info->credits = g_strdup (info->credits);
433 ibus_factory_info_copy (IBusFactoryInfo *dest,
434 const IBusFactoryInfo *src)
438 retval = factory_info_parent_class->copy ((IBusSerializable *)dest,
439 (IBusSerializable *)src);
440 g_return_val_if_fail (retval, FALSE);
442 g_return_val_if_fail (IBUS_IS_FACTORY_INFO (dest), FALSE);
443 g_return_val_if_fail (IBUS_IS_FACTORY_INFO (src), FALSE);
445 dest->path = g_strdup (src->path);
446 dest->name = g_strdup (src->name);
447 dest->lang = g_strdup (src->lang);
448 dest->icon = g_strdup (src->icon);
449 dest->authors = g_strdup (src->authors);
450 dest->credits = g_strdup (src->credits);
456 ibus_factory_info_new (const gchar *path,
460 const gchar *authors,
461 const gchar *credits)
470 IBusFactoryInfo *info;
472 info = (IBusFactoryInfo *) g_object_new (IBUS_TYPE_FACTORY_INFO, NULL);
474 info->path = g_strdup (path);
475 info->name = g_strdup (name);
476 info->lang = g_strdup (lang);
477 info->icon = g_strdup (icon);
478 info->authors = g_strdup (authors);
479 info->credits = g_strdup (credits);