List bug number.
[hildon] / hildon-widgets / hildon-insert-object-dialog.c
1 /*
2  * This file is part of hildon-libs
3  *
4  * Copyright (C) 2005 Nokia Corporation.
5  *
6  * Contact: Luc Pionchon <luc.pionchon@nokia.com>
7  *
8  * This library is free software; you can redistribute it and/or
9  * modify it under the terms of the GNU Lesser General Public License
10  * as published by the Free Software Foundation; either version 2.1 of
11  * the License, or (at your option) any later version.
12  *
13  * This library is distributed in the hope that it will be useful, but
14  * WITHOUT ANY WARRANTY; without even the implied warranty of
15  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16  * Lesser General Public License for more details.
17  *
18  * You should have received a copy of the GNU Lesser General Public
19  * License along with this library; if not, write to the Free Software
20  * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
21  * 02110-1301 USA
22  *
23  */
24
25 /* FIXME: should be moved to hildon-fm (file handling, depends on gnome-vfs) */
26
27 /**
28  * SECTION:hildon-insert-object-dialog
29  * @short_description: A dialog that enables the user to embed an object 
30  * into rich text
31  *
32  * #HildonInsertObjectDialog is a dialog that enables the user to insert a
33  * new or existing object into a Multi-line (Rich Text) Editor as an
34  * embedded object.
35  *
36  * FIXME: deprecated widget. Shall not be used anywhere.
37  * 
38  */ 
39
40 #ifdef HAVE_CONFIG_H
41 #include <config.h>
42 #endif
43
44 #include <gtk/gtkmain.h>
45 #include <gdk/gdkkeysyms.h>
46 #include <gtk/gtkdialog.h>
47 #include <gtk/gtkbutton.h>
48 #include <gtk/gtklabel.h>
49 #include <gtk/gtkentry.h>
50 #include <gtk/gtkcombobox.h>
51 #include <gtk/gtksizegroup.h>
52 #include <gtk/gtkbox.h>
53 #include <string.h>
54
55 #include <libintl.h>
56
57 #include <hildon-insert-object-dialog.h>
58 #include <hildon-widgets/hildon-caption.h>
59
60 #define _(String) dgettext(PACKAGE, String)
61
62 #define MAX_ERR_MSG 256
63
64 #define HILDON_INSERT_OBJECT_DIALOG_WIDTH 300
65 #define HILDON_INSERT_OBJECT_DIALOG_HEIGHT 100
66
67 #define PROJECT_TEMPLATE_DIR "/tmp"
68 #define RUN_AT_TERMINATION 0
69
70
71 static GtkDialogClass *parent_class;
72
73 struct _HildonInsertObjectDialogPrivate {
74     GtkButton *insertBtn;
75     GtkButton *existingBtn;
76     GtkButton *cancelBtn;
77     GtkEntry *entry;
78     GtkLabel *label;
79     GtkComboBox *combo;
80     GtkSizeGroup *group;
81
82     HildonCaption *comboCap;
83     HildonCaption *entryCap;
84     HildonCaption *locationCap;
85
86     GnomeVFSDirectoryHandle *dir;
87     char *mimetype;
88
89     guint keysnooper;
90 };
91
92 #define HILDON_INSERT_OBJECT_DIALOG_GET_PRIVATE(o)  \
93    (G_TYPE_INSTANCE_GET_PRIVATE ((o), \
94       HILDON_TYPE_INSERT_OBJECT_DIALOG, \
95       HildonInsertObjectDialogPrivate) )
96
97 static void
98 hildon_insert_object_dialog_class_init(HildonInsertObjectDialogClass *
99                                        class);
100 static void hildon_insert_object_dialog_init(HildonInsertObjectDialog *
101                                              dialog);
102 static void hildon_insert_object_dialog_finalize(GObject * obj_self);
103 static gint hildon_insert_object_dialog_key_snooper(GtkWidget * gadget,
104                                                     GdkEventKey * event,
105                                                     GtkWidget * widget);
106 static void hildon_insert_object_dialog_set_property(GObject * object,
107                                      guint prop_id,
108                                      const GValue * value,
109                                      GParamSpec * pspec);
110 static void hildon_insert_object_dialog_get_property(GObject * object,
111                                      guint prop_id,
112                                      GValue * value, GParamSpec * pspec);
113
114 enum {
115     PROP_0,
116     PROP_NAME,
117     PROP_MIME_TYPE
118 };
119
120 static gboolean hildon_insert_object_foo(gpointer data)
121 {
122     gnome_vfs_shutdown();
123     g_message("GnomeVFS shutdown succeed!\n");
124     return FALSE;
125 }
126
127 /* Private functions */
128 static void
129 hildon_insert_object_dialog_class_init(HildonInsertObjectDialogClass *
130                                        class)
131 {
132
133     GObjectClass *object_class = G_OBJECT_CLASS(class);
134
135     parent_class = g_type_class_peek_parent(class);
136     g_type_class_add_private(class,
137                              sizeof(HildonInsertObjectDialogPrivate));
138
139     object_class->finalize = hildon_insert_object_dialog_finalize;
140     object_class->set_property = hildon_insert_object_dialog_set_property;
141     object_class->get_property = hildon_insert_object_dialog_get_property;
142
143     g_object_class_install_property(object_class, PROP_NAME,
144         g_param_spec_string("name",
145                             "Name",
146                             "The text in name field",
147                             "", G_PARAM_READWRITE));
148
149     g_object_class_install_property(object_class, PROP_MIME_TYPE,
150         g_param_spec_string("mime-type",
151                             "Mime-Type",
152                             "The mime type selected in the combobox",
153                             GNOME_VFS_MIME_TYPE_UNKNOWN,
154                             G_PARAM_READABLE));
155 }
156
157 static void hildon_insert_object_dialog_finalize(GObject * obj_self)
158 {
159     HildonInsertObjectDialogPrivate *priv;
160     HildonInsertObjectDialog *dlg;
161
162     g_return_if_fail(HILDON_IS_INSERT_OBJECT_DIALOG(obj_self));
163
164     dlg = HILDON_INSERT_OBJECT_DIALOG(obj_self);
165     priv = HILDON_INSERT_OBJECT_DIALOG_GET_PRIVATE(dlg);
166
167     gtk_key_snooper_remove(priv->keysnooper);
168
169     if (G_OBJECT_CLASS(parent_class)->finalize)
170         G_OBJECT_CLASS(parent_class)->finalize(obj_self);
171 }
172
173
174 static void
175 hildon_insert_object_dialog_init(HildonInsertObjectDialog * dialog)
176 {
177
178     GnomeVFSResult result;
179     gchar *dir_path = "";
180     GnomeVFSFileInfo *file = gnome_vfs_file_info_new();
181     GList *mimelist = NULL;
182     GtkTreeModel *combo_tree = NULL;
183     GtkTreeIter combo_iter;
184     gboolean valid = FALSE;
185
186
187     dialog->priv = HILDON_INSERT_OBJECT_DIALOG_GET_PRIVATE(dialog);
188     gtk_dialog_set_has_separator(GTK_DIALOG(dialog), FALSE);
189
190     gtk_window_set_title(GTK_WINDOW(dialog), "ckdg_ti_insert_insert_objec");
191
192     dialog->priv->group =
193         GTK_SIZE_GROUP(gtk_size_group_new(GTK_SIZE_GROUP_HORIZONTAL));
194
195     dialog->priv->insertBtn =
196         GTK_BUTTON(gtk_dialog_add_button(GTK_DIALOG(dialog),
197                                          "ckdg_bd_insert_new",
198                                          GTK_RESPONSE_OK));
199
200     dialog->priv->existingBtn =
201         GTK_BUTTON(gtk_dialog_add_button
202                    (GTK_DIALOG(dialog), "ckdg_bd_insert_existing",
203                     HILDON_RESPONSE_INSERT_EXISTING));
204
205     dialog->priv->cancelBtn =
206         GTK_BUTTON(gtk_dialog_add_button(GTK_DIALOG(dialog),
207                                          "ckdg_bd_insert_cancel",
208                                          GTK_RESPONSE_CANCEL));
209
210     dialog->priv->label = GTK_LABEL(gtk_label_new(NULL));
211     dialog->priv->locationCap =
212         HILDON_CAPTION(hildon_caption_new(dialog->priv->group,
213                                           "Location",
214                                           GTK_WIDGET(dialog->priv->label),
215                                           NULL, HILDON_CAPTION_OPTIONAL));
216     gtk_box_pack_start(GTK_BOX(GTK_DIALOG(dialog)->vbox),
217                        GTK_WIDGET(dialog->priv->locationCap), FALSE, FALSE,
218                        0);
219
220     dialog->priv->entry = GTK_ENTRY(gtk_entry_new());
221     dialog->priv->entryCap =
222         HILDON_CAPTION(hildon_caption_new(dialog->priv->group,
223                                           "Name",
224                                           GTK_WIDGET(dialog->priv->entry),
225                                           NULL, HILDON_CAPTION_OPTIONAL));
226
227     gtk_box_pack_start(GTK_BOX(GTK_DIALOG(dialog)->vbox),
228                        GTK_WIDGET(dialog->priv->entryCap), FALSE, FALSE,
229                        0);
230
231     dialog->priv->combo = GTK_COMBO_BOX(gtk_combo_box_new_text());
232
233     dialog->priv->comboCap =
234         HILDON_CAPTION(hildon_caption_new(dialog->priv->group,
235                                           "Mime type",
236                                           GTK_WIDGET(dialog->priv->combo),
237                                           NULL, HILDON_CAPTION_OPTIONAL));
238
239     gtk_box_pack_start(GTK_BOX(GTK_DIALOG(dialog)->vbox),
240                        GTK_WIDGET(dialog->priv->comboCap), FALSE, FALSE,
241                        0);
242
243     dialog->priv->mimetype = (char *) GNOME_VFS_MIME_TYPE_UNKNOWN;
244
245     /* Initialize gnome-vfs */
246     if (gnome_vfs_initialized() == FALSE) {
247         gtk_quit_add(RUN_AT_TERMINATION, hildon_insert_object_foo, NULL);
248
249         if (gnome_vfs_init() == FALSE) {
250             g_error("GnomeVFS can not be run");
251             return;
252         } else
253             g_message("GnomeVFS init!");
254     } else
255         g_message("GnomeVFS initialized!");
256
257
258     /* Read registered mime types into combobox */
259     mimelist = gnome_vfs_get_registered_mime_types();
260
261     while (mimelist) {
262         if (gnome_vfs_mime_get_description((char *) (mimelist->data)) !=
263             NULL)
264             gtk_combo_box_append_text
265                 (dialog->priv->combo,
266                  gnome_vfs_mime_get_description
267                      ((char *) (mimelist->data)));
268         else
269             gtk_combo_box_append_text(dialog->priv->combo,
270                                       (char *) (mimelist->data));
271
272         mimelist = mimelist->next;
273     }
274
275     gnome_vfs_mime_registered_mime_type_list_free(mimelist);
276
277     /* Read directory path into label and first file into entry */
278     /* dir_path = g_strconcat( (const char *)g_get_current_dir(),
279        PROJECT_TEMPLATE_DIR, NULL); */
280     dir_path = g_strconcat(g_getenv((const char *) "PWD"),
281                            PROJECT_TEMPLATE_DIR, NULL);
282
283     result = gnome_vfs_directory_open(&(dialog->priv->dir), dir_path,
284                                       GNOME_VFS_FILE_INFO_DEFAULT |
285                                       GNOME_VFS_FILE_INFO_GET_MIME_TYPE);
286     if (result != GNOME_VFS_OK) {
287         g_warning("Could not read project templates directory\n");
288         gtk_label_set_label(dialog->priv->label,
289                             "Could not read project templates directory");
290         return;
291     } else {
292         gtk_label_set_label(dialog->priv->label, (gchar *) dir_path);
293
294         while (gnome_vfs_directory_read_next(dialog->priv->dir, file) ==
295                GNOME_VFS_OK) {
296             if (file->name != NULL
297                 && file->type == GNOME_VFS_FILE_TYPE_REGULAR) {
298                 gtk_entry_set_text(dialog->priv->entry,
299                                    (gchar *) file->name);
300
301                 combo_tree = gtk_combo_box_get_model(dialog->priv->combo);
302                 valid =
303                     gtk_tree_model_get_iter_first(combo_tree, &combo_iter);
304
305                 while (valid) {
306                     gchar *str_data;
307
308                     gtk_tree_model_get(combo_tree, &combo_iter, 0,
309                                        &str_data, -1);
310
311                     if (strcmp(str_data,
312                                gnome_vfs_mime_get_description
313                                ((char *) file->mime_type)) == 0) {
314                         dialog->priv->mimetype = (char *) file->mime_type;
315                         gtk_combo_box_set_active_iter(dialog->priv->combo,
316                                                       &combo_iter);
317                         g_free(str_data);
318                         break;
319                     }
320                     g_free(str_data);
321                     valid =
322                         gtk_tree_model_iter_next(combo_tree, &combo_iter);
323                 }
324
325                 break;
326             }
327
328         }
329     }
330
331
332     if (gnome_vfs_directory_close(dialog->priv->dir) != GNOME_VFS_OK)
333         g_warning("Could not close the project templates directory\n");
334     else
335         g_message("Gnome VFS dir closed \n");
336
337     g_free(dir_path);
338
339     dialog->priv->keysnooper =
340         (guint) (gtk_key_snooper_install
341                  ((GtkKeySnoopFunc)
342                   (hildon_insert_object_dialog_key_snooper),
343                   GTK_WIDGET(dialog)));
344
345     gtk_window_resize(GTK_WINDOW(dialog),
346                       HILDON_INSERT_OBJECT_DIALOG_WIDTH,
347                       HILDON_INSERT_OBJECT_DIALOG_HEIGHT);
348
349     gtk_widget_show_all(GTK_DIALOG(dialog)->vbox);
350     gtk_widget_show_all(GTK_DIALOG(dialog)->action_area);
351
352     gnome_vfs_file_info_unref(file);
353
354 }
355
356 static gint hildon_insert_object_dialog_key_snooper(GtkWidget * gadget,
357                                                     GdkEventKey * event,
358                                                     GtkWidget * widget)
359 {
360     if (event->type == GDK_KEY_RELEASE) {
361         switch (event->keyval) {
362         case GDK_I:
363         case GDK_i:
364             gtk_dialog_response(GTK_DIALOG(widget),
365                                 HILDON_RESPONSE_INSERT_EXISTING);
366             break;
367             /* case GDK_C: case GDK_c: gtk_dialog_response(
368                GTK_DIALOG(widget), GTK_RESPONSE_CANCEL ); break; */
369         }
370     }
371     return FALSE;
372 }
373
374
375 /* Public functions */
376 GType hildon_insert_object_dialog_get_type(void)
377 {
378     static GType dialog_type = 0;
379
380     if (!dialog_type) {
381         static const GTypeInfo dialog_info = {
382             sizeof(HildonInsertObjectDialogClass),
383             NULL,       /* base_init */
384             NULL,       /* base_finalize */
385             (GClassInitFunc) hildon_insert_object_dialog_class_init,
386             NULL,       /* class_finalize */
387             NULL,       /* class_data */
388             sizeof(HildonInsertObjectDialog),
389             0,  /* n_preallocs */
390             (GInstanceInitFunc) hildon_insert_object_dialog_init
391         };
392
393         dialog_type = g_type_register_static(GTK_TYPE_DIALOG,
394                                              "HildonInsertObjectDialog",
395                                              &dialog_info, 0);
396     }
397     return dialog_type;
398
399 }
400
401 /**
402  * hildon_insert_object_dialog_new:
403  * @parent: the parent window of the dialog
404  *
405  * Creates a new #HildonInsertObjectDialog widget.
406  *
407  * Returns: the newly created #HildonInsertObjectDialog
408  */
409 GtkWidget *hildon_insert_object_dialog_new(GtkWindow * parent)
410 {
411     GtkWidget *self = g_object_new(HILDON_TYPE_INSERT_OBJECT_DIALOG, NULL);
412
413     if (parent)
414         gtk_window_set_transient_for(GTK_WINDOW(self), parent);
415
416     return GTK_WIDGET(self);
417 }
418
419 /**
420  * hildon_insert_object_dialog_get_name:
421  * @dialog: the dialog
422  *
423  * Gets the text in name field of the file dialog. 
424  * This specifies the object to be inserted.
425  *
426  * Returns: a pointer to the name string
427  */
428 const gchar *hildon_insert_object_dialog_get_name(HildonInsertObjectDialog
429                                                   * dialog)
430 {
431
432     g_return_val_if_fail(HILDON_IS_INSERT_OBJECT_DIALOG(dialog), NULL);
433
434     return gtk_entry_get_text(dialog->priv->entry);
435 }
436
437 /**
438  * hildon_insert_object_dialog_get_mime_type:
439  * @dialog: the dialog
440  *
441  * Gets the mime type selected in the combobox.
442  *
443  * Returns: a pointer to the mime type string, must not be freed
444  */
445 const gchar
446     *hildon_insert_object_dialog_get_mime_type(HildonInsertObjectDialog *
447                                                dialog)
448 {
449     /* GtkTreeIter iter; gchar *return_string; GtkTreeModel *tree_model;
450
451        tree_model = gtk_combo_box_get_model(dialog->priv->combo);
452
453        if(gtk_combo_box_get_active_iter(dialog->priv->combo,&iter)){
454        gtk_tree_model_get (tree_model, &iter, 0, &return_string, -1);
455        return return_string; } else { return NULL; } */
456
457
458     return dialog->priv->mimetype;
459 }
460
461 static void
462 hildon_insert_object_dialog_set_property(GObject * object,
463                          guint prop_id,
464                          const GValue * value, GParamSpec * pspec)
465 {
466     HildonInsertObjectDialog *dialog;
467
468     dialog = HILDON_INSERT_OBJECT_DIALOG(object);
469
470     switch (prop_id) {
471     case PROP_NAME:
472        gtk_entry_set_text(dialog->priv->entry, g_value_get_string(value));
473         break;
474     default:
475         G_OBJECT_WARN_INVALID_PROPERTY_ID(object, prop_id, pspec);
476         break;
477     }
478 }
479
480 static void
481 hildon_insert_object_dialog_get_property(GObject * object,
482                          guint prop_id, GValue * value, GParamSpec * pspec)
483 {
484     HildonInsertObjectDialog *dialog;
485
486     dialog = HILDON_INSERT_OBJECT_DIALOG(object);
487
488     switch (prop_id) {
489     case PROP_NAME:
490         g_value_set_string(value, gtk_entry_get_text(dialog->priv->entry));
491         break;
492     case PROP_MIME_TYPE:
493         g_value_set_string(value, dialog->priv->mimetype);
494         break;
495     default:
496         G_OBJECT_WARN_INVALID_PROPERTY_ID(object, prop_id, pspec);
497         break;
498     }
499 }
500