Fix FSF address (Tobias Mueller, #470445)
[platform/upstream/evolution-data-server.git] / servers / exchange / storage / e-folder-type-registry.c
1 /* -*- Mode: C; indent-tabs-mode: t; c-basic-offset: 8; tab-width: 8 -*- */
2 /* e-folder-type-registry.c
3  *
4  * Copyright (C) 2000, 2001 Ximian, Inc.
5  *
6  * This program is free software; you can redistribute it and/or
7  * modify it under the terms of version 2 of the GNU Lesser General Public
8  * License as published by the Free Software Foundation.
9  *
10  * This program 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  * General Public License for more details.
14  *
15  * You should have received a copy of the GNU Lesser General Public
16  * License along with this program; if not, write to the
17  * Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
18  * Boston, MA 02110-1301, USA.
19  *
20  * Author: Ettore Perazzoli
21  */
22
23 #ifdef HAVE_CONFIG_H
24 #include <config.h>
25 #endif
26
27 #include "e-folder-type-registry.h"
28
29 #define PARENT_TYPE G_TYPE_OBJECT
30 static GObjectClass *parent_class = NULL;
31
32 typedef struct {
33         char *name;
34         char *icon_name;
35
36         char *display_name;
37         char *description;
38
39         gboolean user_creatable;
40
41         GList *accepted_dnd_types; /* char * */
42
43         GObject *handler;
44
45 } FolderType;
46
47 struct EFolderTypeRegistryPrivate {
48         GHashTable *name_to_type;
49 };
50
51 /* FolderType handling.  */
52
53 static FolderType *
54 folder_type_new (const char *name,
55                  const char *icon_name,
56                  const char *display_name,
57                  const char *description,
58                  gboolean user_creatable,
59                  int num_accepted_dnd_types,
60                  const char **accepted_dnd_types)
61 {
62         FolderType *new;
63         int i;
64
65         new = g_new0 (FolderType, 1);
66
67         new->name           = g_strdup (name);
68         new->icon_name      = g_strdup (icon_name);
69         new->display_name   = g_strdup (display_name);
70         new->description    = g_strdup (description);
71
72         new->user_creatable = user_creatable;
73
74         new->accepted_dnd_types = NULL;
75         for (i = 0; i < num_accepted_dnd_types; i++)
76                 new->accepted_dnd_types = g_list_prepend (new->accepted_dnd_types,
77                                                           g_strdup (accepted_dnd_types[i]));
78         new->accepted_dnd_types = g_list_reverse (new->accepted_dnd_types);
79
80         new->handler = NULL;
81
82         return new;
83 }
84
85 static void
86 folder_type_free (FolderType *folder_type)
87 {
88         g_free (folder_type->name);
89         g_free (folder_type->icon_name);
90         g_free (folder_type->display_name);
91         g_free (folder_type->description);
92
93         if (folder_type->handler != NULL)
94                 g_object_unref (folder_type->handler);
95
96         g_free (folder_type);
97 }
98
99 static FolderType *
100 get_folder_type (EFolderTypeRegistry *folder_type_registry,
101                  const char *type_name)
102 {
103         EFolderTypeRegistryPrivate *priv;
104
105         priv = folder_type_registry->priv;
106
107         return g_hash_table_lookup (priv->name_to_type, type_name);
108 }
109
110 static gboolean
111 register_folder_type (EFolderTypeRegistry *folder_type_registry,
112                       const char *name,
113                       const char *icon_name,
114                       const char *display_name,
115                       const char *description,
116                       gboolean user_creatable,
117                       int num_accepted_dnd_types,
118                       const char **accepted_dnd_types)
119 {
120         EFolderTypeRegistryPrivate *priv;
121         FolderType *folder_type;
122
123         priv = folder_type_registry->priv;
124
125         /* Make sure we don't add the same type twice.  */
126         if (get_folder_type (folder_type_registry, name) != NULL)
127                 return FALSE;
128
129         folder_type = folder_type_new (name, icon_name,
130                                        display_name, description,
131                                        user_creatable,
132                                        num_accepted_dnd_types, accepted_dnd_types);
133         g_hash_table_insert (priv->name_to_type, folder_type->name, folder_type);
134
135         return TRUE;
136 }
137
138 static gboolean
139 set_handler (EFolderTypeRegistry *folder_type_registry,
140              const char *name,
141              GObject *handler)
142 {
143         EFolderTypeRegistryPrivate *priv;
144         FolderType *folder_type;
145
146         priv = folder_type_registry->priv;
147
148         folder_type = get_folder_type (folder_type_registry, name);
149         if (folder_type == NULL)
150                 return FALSE;
151         if (folder_type->handler != NULL)
152                 return FALSE;
153
154         g_object_ref (handler);
155         folder_type->handler = handler;
156
157         return TRUE;
158 }
159
160 /* GObject methods.  */
161
162 static void
163 hash_forall_free_folder_type (gpointer key,
164                               gpointer value,
165                               gpointer data)
166 {
167         FolderType *folder_type;
168
169         folder_type = (FolderType *) value;
170         folder_type_free (folder_type);
171 }
172
173 static void
174 impl_finalize (GObject *object)
175 {
176         EFolderTypeRegistry *folder_type_registry;
177         EFolderTypeRegistryPrivate *priv;
178
179         folder_type_registry = E_FOLDER_TYPE_REGISTRY (object);
180         priv = folder_type_registry->priv;
181
182         g_hash_table_foreach (priv->name_to_type, hash_forall_free_folder_type, NULL);
183         g_hash_table_destroy (priv->name_to_type);
184
185         g_free (priv);
186
187         (* G_OBJECT_CLASS (parent_class)->finalize) (object);
188 }
189
190 static void
191 e_folder_type_registry_class_init (EFolderTypeRegistryClass *class)
192 {
193         GObjectClass *object_class;
194
195         object_class = G_OBJECT_CLASS (class);
196         object_class->finalize = impl_finalize;
197
198         parent_class = g_type_class_ref (PARENT_TYPE);
199 }
200
201 static void
202 e_folder_type_registry_init (EFolderTypeRegistry *folder_type_registry)
203 {
204         EFolderTypeRegistryPrivate *priv;
205
206         priv = g_new0 (EFolderTypeRegistryPrivate, 1);
207         priv->name_to_type = g_hash_table_new (g_str_hash, g_str_equal);
208
209         folder_type_registry->priv = priv;
210 }
211
212 EFolderTypeRegistry *
213 e_folder_type_registry_new (void)
214 {
215         return g_object_new (E_TYPE_FOLDER_TYPE_REGISTRY, NULL);
216 }
217
218 gboolean
219 e_folder_type_registry_register_type (EFolderTypeRegistry *folder_type_registry,
220                                       const char *type_name,
221                                       const char *icon_name,
222                                       const char *display_name,
223                                       const char *description,
224                                       gboolean user_creatable,
225                                       int num_accepted_dnd_types,
226                                       const char **accepted_dnd_types)
227 {
228         g_return_val_if_fail (E_IS_FOLDER_TYPE_REGISTRY (folder_type_registry), FALSE);
229         g_return_val_if_fail (type_name != NULL, FALSE);
230         g_return_val_if_fail (icon_name != NULL, FALSE);
231
232         return register_folder_type (folder_type_registry, type_name, icon_name,
233                                      display_name, description, user_creatable,
234                                      num_accepted_dnd_types, accepted_dnd_types);
235 }
236
237 gboolean
238 e_folder_type_registry_set_handler_for_type  (EFolderTypeRegistry *folder_type_registry,
239                                               const char *type_name,
240                                               GObject *handler)
241 {
242         g_return_val_if_fail (E_IS_FOLDER_TYPE_REGISTRY (folder_type_registry), FALSE);
243         //g_return_val_if_fail (EVOLUTION_IS_SHELL_COMPONENT_CLIENT (handler), FALSE);
244
245         return set_handler (folder_type_registry, type_name, handler);
246 }
247
248 gboolean
249 e_folder_type_registry_type_registered  (EFolderTypeRegistry *folder_type_registry,
250                                          const char *type_name)
251 {
252         EFolderTypeRegistryPrivate *priv;
253
254         g_return_val_if_fail (E_IS_FOLDER_TYPE_REGISTRY (folder_type_registry), FALSE);
255         g_return_val_if_fail (type_name != NULL, FALSE);
256
257         priv = folder_type_registry->priv;
258
259         if (get_folder_type (folder_type_registry, type_name) == NULL)
260                 return FALSE;
261
262         return TRUE;
263 }
264
265 void
266 e_folder_type_registry_unregister_type (EFolderTypeRegistry *folder_type_registry,
267                                         const char *type_name)
268 {
269         EFolderTypeRegistryPrivate *priv;
270         FolderType *folder_type;
271
272         g_return_if_fail (E_IS_FOLDER_TYPE_REGISTRY (folder_type_registry));
273         g_return_if_fail (type_name != NULL);
274
275         priv = folder_type_registry->priv;
276
277         folder_type = get_folder_type (folder_type_registry, type_name);
278         if (folder_type == NULL)
279                 return;
280
281         g_hash_table_remove (priv->name_to_type, folder_type->name);
282         folder_type_free (folder_type);
283 }
284
285 static void
286 get_type_names_hash_forall (void *key,
287                             void *value,
288                             void *data)
289 {
290         GList **type_name_list;
291
292         type_name_list = (GList **) data;
293
294         *type_name_list = g_list_prepend (*type_name_list, g_strdup ((const char *) key));
295 }
296
297 GList *
298 e_folder_type_registry_get_type_names (EFolderTypeRegistry *folder_type_registry)
299 {
300         GList *type_name_list;
301         EFolderTypeRegistryPrivate *priv;
302
303         g_return_val_if_fail (E_IS_FOLDER_TYPE_REGISTRY (folder_type_registry), NULL);
304
305         priv = folder_type_registry->priv;
306
307         type_name_list = NULL;
308         g_hash_table_foreach (priv->name_to_type, get_type_names_hash_forall, &type_name_list);
309
310         return type_name_list;
311 }
312
313 const char *
314 e_folder_type_registry_get_icon_name_for_type (EFolderTypeRegistry *folder_type_registry,
315                                                const char *type_name)
316 {
317         const FolderType *folder_type;
318
319         g_return_val_if_fail (E_IS_FOLDER_TYPE_REGISTRY (folder_type_registry), NULL);
320         g_return_val_if_fail (type_name != NULL, NULL);
321
322         folder_type = get_folder_type (folder_type_registry, type_name);
323         if (folder_type == NULL)
324                 return NULL;
325
326         return folder_type->icon_name;
327 }
328
329 GObject *
330 e_folder_type_registry_get_handler_for_type (EFolderTypeRegistry *folder_type_registry,
331                                              const char *type_name)
332 {
333         const FolderType *folder_type;
334
335         g_return_val_if_fail (E_IS_FOLDER_TYPE_REGISTRY (folder_type_registry), NULL);
336         g_return_val_if_fail (type_name != NULL, NULL);
337
338         folder_type = get_folder_type (folder_type_registry, type_name);
339         if (folder_type == NULL)
340                 return NULL;
341
342         return folder_type->handler;
343 }
344
345 gboolean
346 e_folder_type_registry_type_is_user_creatable  (EFolderTypeRegistry *folder_type_registry,
347                                                 const char          *type_name)
348 {
349         const FolderType *folder_type;
350
351         g_return_val_if_fail (E_IS_FOLDER_TYPE_REGISTRY (folder_type_registry), FALSE);
352         g_return_val_if_fail (type_name != NULL, FALSE);
353
354         folder_type = get_folder_type (folder_type_registry, type_name);
355         if (folder_type == NULL)
356                 return FALSE;
357
358         return folder_type->user_creatable;
359 }
360
361 const char *
362 e_folder_type_registry_get_display_name_for_type (EFolderTypeRegistry *folder_type_registry,
363                                                   const char *type_name)
364 {
365         const FolderType *folder_type;
366
367         g_return_val_if_fail (E_IS_FOLDER_TYPE_REGISTRY (folder_type_registry), NULL);
368         g_return_val_if_fail (type_name != NULL, NULL);
369
370         folder_type = get_folder_type (folder_type_registry, type_name);
371         if (folder_type == NULL)
372                 return NULL;
373
374         return folder_type->display_name;
375 }
376
377 const char *
378 e_folder_type_registry_get_description_for_type (EFolderTypeRegistry *folder_type_registry,
379                                                  const char *type_name)
380 {
381         const FolderType *folder_type;
382
383         g_return_val_if_fail (E_IS_FOLDER_TYPE_REGISTRY (folder_type_registry), NULL);
384         g_return_val_if_fail (type_name != NULL, NULL);
385
386         folder_type = get_folder_type (folder_type_registry, type_name);
387         if (folder_type == NULL)
388                 return NULL;
389
390         return folder_type->description;
391 }
392
393 GList *
394 e_folder_type_registry_get_accepted_dnd_types_for_type (EFolderTypeRegistry *folder_type_registry,
395                                                         const char *type_name)
396 {
397         const FolderType *folder_type;
398
399         g_return_val_if_fail (E_IS_FOLDER_TYPE_REGISTRY (folder_type_registry), NULL);
400         g_return_val_if_fail (type_name != NULL, NULL);
401
402         folder_type = get_folder_type (folder_type_registry, type_name);
403         if (folder_type == NULL)
404                 return NULL;
405
406         return folder_type->accepted_dnd_types;
407 }
408 G_DEFINE_TYPE (EFolderTypeRegistry, e_folder_type_registry, G_TYPE_OBJECT)