Statistics
| Revision:

root / src / addressadd.c @ 528

History | View | Annotate | Download (12.6 kB)

1
/*
2
 * Sylpheed -- a GTK+ based, lightweight, and fast e-mail client
3
 * Copyright (C) 2001 Match Grun
4
 *
5
 * This program is free software; you can redistribute it and/or modify
6
 * it under the terms of the GNU General Public License as published by
7
 * the Free Software Foundation; either version 2 of the License, or
8
 * (at your option) any later version.
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
13
 * GNU General Public License for more details.
14
 *
15
 * You should have received a copy of the GNU General Public License
16
 * along with this program; if not, write to the Free Software
17
 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
18
 */
19
20
/*
21
 * Add address to address book dialog.
22
 */
23
24
#ifdef HAVE_CONFIG_H
25
#  include "config.h"
26
#endif
27
28
#include "defs.h"
29
30
#include <glib.h>
31
#include <glib/gi18n.h>
32
#include <gdk/gdkkeysyms.h>
33
#include <gtk/gtkwindow.h>
34
#include <gtk/gtksignal.h>
35
#include <gtk/gtkvbox.h>
36
#include <gtk/gtkhbox.h>
37
#include <gtk/gtklabel.h>
38
#include <gtk/gtkentry.h>
39
#include <gtk/gtkhbbox.h>
40
#include <gtk/gtkbutton.h>
41
#include <gtk/gtkstatusbar.h>
42
#include <gtk/gtktable.h>
43
#include <gtk/gtkhseparator.h>
44
#include <gtk/gtkstock.h>
45
46
#include "gtkutils.h"
47
#include "stock_pixmap.h"
48
#include "prefs_common.h"
49
#include "addressadd.h"
50
#include "addritem.h"
51
#include "addrbook.h"
52
#include "addrindex.h"
53
#include "editaddress.h"
54
#include "manage_window.h"
55
56
typedef struct {
57
        AddressBookFile        *book;
58
        ItemFolder        *folder;
59
} FolderInfo;
60
61
static struct _AddressAdd_dlg {
62
        GtkWidget *window;
63
        GtkWidget *label_name;
64
        GtkWidget *label_address;
65
        GtkWidget *label_remarks;
66
        GtkWidget *tree_folder;
67
        GtkWidget *ok_btn;
68
        GtkWidget *cancel_btn;
69
        GtkWidget *statusbar;
70
        gint status_cid;
71
        FolderInfo *fiSelected;
72
} addressadd_dlg;
73
74
static GdkPixmap *folderXpm;
75
static GdkBitmap *folderXpmMask;
76
static GdkPixmap *bookXpm;
77
static GdkBitmap *bookXpmMask;
78
79
static gboolean addressadd_cancelled;
80
81
static FolderInfo *addressadd_create_folderinfo( AddressBookFile *abf, ItemFolder *folder )
82
{
83
        FolderInfo *fi = g_new0( FolderInfo, 1 );
84
        fi->book   = abf;
85
        fi->folder = folder;
86
        return fi;
87
}
88
89
static void addressadd_free_folderinfo( FolderInfo *fi ) {
90
        fi->book   = NULL;
91
        fi->folder = NULL;
92
        g_free( fi );
93
}
94
95
/*
96
* Edit functions.
97
*/
98
static void addressadd_status_show( gchar *msg ) {
99
        if( addressadd_dlg.statusbar != NULL ) {
100
                gtk_statusbar_pop( GTK_STATUSBAR(addressadd_dlg.statusbar), addressadd_dlg.status_cid );
101
                if( msg ) {
102
                        gtk_statusbar_push( GTK_STATUSBAR(addressadd_dlg.statusbar), addressadd_dlg.status_cid, msg );
103
                }
104
        }
105
}
106
107
static gint addressadd_delete_event( GtkWidget *widget, GdkEventAny *event, gboolean *cancelled ) {
108
        addressadd_cancelled = TRUE;
109
        gtk_main_quit();
110
        return TRUE;
111
}
112
113
static gboolean addressadd_key_pressed( GtkWidget *widget, GdkEventKey *event, gboolean *cancelled ) {
114
        if (event && event->keyval == GDK_Escape) {
115
                addressadd_cancelled = TRUE;
116
                gtk_main_quit();
117
        }
118
        return FALSE;
119
}
120
121
static void addressadd_ok( GtkWidget *widget, gboolean *cancelled ) {
122
        addressadd_cancelled = FALSE;
123
        gtk_main_quit();
124
}
125
126
static void addressadd_cancel( GtkWidget *widget, gboolean *cancelled ) {
127
        addressadd_cancelled = TRUE;
128
        gtk_main_quit();
129
}
130
131
static void addressadd_folder_select( GtkCTree *ctree, gint row, gint column,
132
                                        GdkEvent *event, gpointer data )
133
{
134
        addressadd_dlg.fiSelected = gtk_clist_get_row_data( GTK_CLIST(ctree), row );
135
}
136
137
static gboolean addressadd_tree_button( GtkCTree *ctree, GdkEventButton *event, gpointer data ) {
138
        if( ! event ) return FALSE;
139
        if( event->button == 1 ) {
140
                /* Handle double click */
141
                if( event->type == GDK_2BUTTON_PRESS ) {
142
                        addressadd_cancelled = FALSE;
143
                        gtk_main_quit();
144
                }
145
        }
146
147
        return FALSE;
148
}
149
150
static void addressadd_create( void ) {
151
        GtkWidget *window;
152
        GtkWidget *vbox;
153
        GtkWidget *table;
154
        GtkWidget *label;
155
        GtkWidget *label_name;
156
        GtkWidget *label_addr;
157
        GtkWidget *label_rems;
158
        GtkWidget *tree_folder;
159
        GtkWidget *vlbox;
160
        GtkWidget *tree_win;
161
        GtkWidget *hbbox;
162
        GtkWidget *hsep;
163
        GtkWidget *ok_btn;
164
        GtkWidget *cancel_btn;
165
        GtkWidget *hsbox;
166
        GtkWidget *statusbar;
167
        gint top;
168
169
        window = gtk_window_new(GTK_WINDOW_TOPLEVEL);
170
        gtk_widget_set_size_request( window, 300, 400 );
171
        gtk_container_set_border_width( GTK_CONTAINER(window), 0 );
172
        gtk_window_set_title( GTK_WINDOW(window), _("Add Address to Book") );
173
        gtk_window_set_position( GTK_WINDOW(window), GTK_WIN_POS_MOUSE );
174
        gtk_window_set_modal( GTK_WINDOW(window), TRUE );
175
        g_signal_connect( G_OBJECT(window), "delete_event",
176
                          G_CALLBACK(addressadd_delete_event), NULL );
177
        g_signal_connect( G_OBJECT(window), "key_press_event",
178
                          G_CALLBACK(addressadd_key_pressed), NULL );
179
180
        vbox = gtk_vbox_new(FALSE, 8);
181
        gtk_container_add(GTK_CONTAINER(window), vbox);
182
        gtk_container_set_border_width( GTK_CONTAINER(vbox), 0 );
183
184
        table = gtk_table_new(3, 2, FALSE);
185
        gtk_box_pack_start(GTK_BOX(vbox), table, FALSE, FALSE, 0);
186
        gtk_container_set_border_width( GTK_CONTAINER(table), 8 );
187
        gtk_table_set_row_spacings(GTK_TABLE(table), 8);
188
        gtk_table_set_col_spacings(GTK_TABLE(table), 8);
189
190
        /* First row */
191
        top = 0;
192
        label = gtk_label_new(_("Name"));
193
        gtk_table_attach(GTK_TABLE(table), label, 0, 1, top, (top + 1), GTK_FILL, 0, 0, 0);
194
        gtk_misc_set_alignment(GTK_MISC(label), 0, 0.5);
195
196
        label_name = gtk_label_new("");
197
        gtk_table_attach(GTK_TABLE(table), label_name, 1, 2, top, (top + 1), GTK_FILL, 0, 0, 0);
198
        gtk_misc_set_alignment(GTK_MISC(label_name), 0, 0.5);
199
200
        /* Second row */
201
        top = 1;
202
        label = gtk_label_new(_("Address"));
203
        gtk_table_attach(GTK_TABLE(table), label, 0, 1, top, (top + 1), GTK_FILL, 0, 0, 0);
204
        gtk_misc_set_alignment(GTK_MISC(label), 0, 0);
205
206
        label_addr = gtk_label_new("");
207
        gtk_table_attach(GTK_TABLE(table), label_addr, 1, 2, top, (top + 1), GTK_FILL, 0, 0, 0);
208
        gtk_misc_set_alignment(GTK_MISC(label_addr), 0, 0.5);
209
210
        /* Third row */
211
        top = 2;
212
        label = gtk_label_new(_("Remarks"));
213
        gtk_table_attach(GTK_TABLE(table), label, 0, 1, top, (top + 1), GTK_FILL, 0, 0, 0);
214
        gtk_misc_set_alignment(GTK_MISC(label), 0, 0.5);
215
216
        label_rems = gtk_label_new("");
217
        gtk_table_attach(GTK_TABLE(table), label_rems, 1, 2, top, (top + 1), GTK_FILL, 0, 0, 0);
218
        gtk_misc_set_alignment(GTK_MISC(label_rems), 0, 0.5);
219
220
        /* Address book/folder tree */
221
        vlbox = gtk_vbox_new(FALSE, 8);
222
        gtk_box_pack_start(GTK_BOX(vbox), vlbox, TRUE, TRUE, 0);
223
        gtk_container_set_border_width( GTK_CONTAINER(vlbox), 8 );
224
225
        tree_win = gtk_scrolled_window_new( NULL, NULL );
226
        gtk_scrolled_window_set_policy( GTK_SCROLLED_WINDOW(tree_win),
227
                                        GTK_POLICY_AUTOMATIC,
228
                                        GTK_POLICY_ALWAYS );
229
        gtk_box_pack_start( GTK_BOX(vlbox), tree_win, TRUE, TRUE, 0 );
230
231
        tree_folder = gtk_ctree_new( 1, 0 );
232
        gtk_container_add( GTK_CONTAINER(tree_win), tree_folder );
233
        gtk_clist_column_titles_show( GTK_CLIST(tree_folder) );
234
        gtk_clist_set_column_title( GTK_CLIST(tree_folder), 0, _( "Select Address Book Folder" ) );
235
        gtk_ctree_set_line_style( GTK_CTREE(tree_folder), GTK_CTREE_LINES_DOTTED );
236
        gtk_clist_set_selection_mode( GTK_CLIST(tree_folder), GTK_SELECTION_BROWSE );
237
        gtk_ctree_set_expander_style( GTK_CTREE(tree_folder), GTK_CTREE_EXPANDER_SQUARE );
238
        gtk_ctree_set_indent( GTK_CTREE(tree_folder), CTREE_INDENT );
239
        gtk_clist_set_auto_sort( GTK_CLIST(tree_folder), TRUE );
240
241
        /* Status line */
242
        hsbox = gtk_hbox_new(FALSE, 0);
243
        gtk_box_pack_end(GTK_BOX(vbox), hsbox, FALSE, FALSE, BORDER_WIDTH);
244
        statusbar = gtk_statusbar_new();
245
        gtk_box_pack_start(GTK_BOX(hsbox), statusbar, TRUE, TRUE, BORDER_WIDTH);
246
247
        /* Button panel */
248
        gtkut_stock_button_set_create(&hbbox, &ok_btn, GTK_STOCK_OK,
249
                                      &cancel_btn, GTK_STOCK_CANCEL,
250
                                      NULL, NULL);
251
        gtk_box_pack_end(GTK_BOX(vbox), hbbox, FALSE, FALSE, 0);
252
        gtk_container_set_border_width( GTK_CONTAINER(hbbox), 0 );
253
        gtk_widget_grab_default(ok_btn);
254
255
        hsep = gtk_hseparator_new();
256
        gtk_box_pack_end(GTK_BOX(vbox), hsep, FALSE, FALSE, 0);
257
258
        g_signal_connect(G_OBJECT(ok_btn), "clicked",
259
                         G_CALLBACK(addressadd_ok), NULL);
260
        g_signal_connect(G_OBJECT(cancel_btn), "clicked",
261
                         G_CALLBACK(addressadd_cancel), NULL);
262
        g_signal_connect(G_OBJECT(tree_folder), "select_row",
263
                         G_CALLBACK(addressadd_folder_select), NULL);
264
        g_signal_connect(G_OBJECT(tree_folder), "button_press_event",
265
                         G_CALLBACK(addressadd_tree_button), NULL);
266
267
        gtk_widget_show_all(vbox);
268
269
        addressadd_dlg.window        = window;
270
        addressadd_dlg.label_name    = label_name;
271
        addressadd_dlg.label_address = label_addr;
272
        addressadd_dlg.label_remarks = label_rems;
273
        addressadd_dlg.tree_folder   = tree_folder;
274
        addressadd_dlg.ok_btn        = ok_btn;
275
        addressadd_dlg.cancel_btn    = cancel_btn;
276
        addressadd_dlg.statusbar     = statusbar;
277
        addressadd_dlg.status_cid    = gtk_statusbar_get_context_id( GTK_STATUSBAR(statusbar), "Address Add" );
278
279
        gtk_widget_show_all( window );
280
281
        stock_pixmap_gdk( window, STOCK_PIXMAP_BOOK, &bookXpm, &bookXpmMask );
282
        stock_pixmap_gdk( window, STOCK_PIXMAP_DIR_OPEN,
283
                          &folderXpm, &folderXpmMask );
284
}
285
286
static void addressadd_load_folder( GtkCTreeNode *parentNode, ItemFolder *parentFolder,
287
                                        FolderInfo *fiParent )
288
{
289
        GtkCTree *tree = GTK_CTREE( addressadd_dlg.tree_folder );
290
        GList *list;
291
        ItemFolder *folder;
292
        gchar *fName;
293
        gchar **name;
294
        GtkCTreeNode *node;
295
        FolderInfo *fi;
296
297
        list = parentFolder->listFolder;
298
        while( list ) {
299
                folder = list->data;
300
                fName = g_strdup( ADDRITEM_NAME(folder) );
301
                name = &fName;
302
                node = gtk_ctree_insert_node( tree, parentNode, NULL, name, FOLDER_SPACING,
303
                                folderXpm, folderXpmMask, folderXpm, folderXpmMask,
304
                                FALSE, TRUE );
305
                g_free( fName );
306
                fi = addressadd_create_folderinfo( fiParent->book, folder );
307
                gtk_ctree_node_set_row_data_full( tree, node, fi,
308
                                ( GtkDestroyNotify ) addressadd_free_folderinfo );
309
                addressadd_load_folder( node, folder, fi );
310
                list = g_list_next( list );
311
        }
312
}
313
314
static void addressadd_load_data( AddressIndex *addrIndex ) {
315
        AddressDataSource *ds;
316
        GList *list, *nodeDS;
317
        gchar **name;
318
        gchar *dsName;
319
        ItemFolder *rootFolder;
320
        AddressBookFile *abf;
321
        FolderInfo *fi;
322
        GtkCTree *tree = GTK_CTREE( addressadd_dlg.tree_folder );
323
        GtkCTreeNode *node;
324
325
        gtk_clist_clear( GTK_CLIST( tree ) );
326
        list = addrindex_get_interface_list( addrIndex );
327
        while( list ) {
328
                AddressInterface *interface = list->data;
329
                if( interface->type == ADDR_IF_BOOK ) {
330
                        nodeDS = interface->listSource;
331
                        while( nodeDS ) {
332
                                ds = nodeDS->data;
333
                                dsName = g_strdup( addrindex_ds_get_name( ds ) );
334
335
                                /* Read address book */
336
                                if( ! addrindex_ds_get_read_flag( ds ) ) {
337
                                        addrindex_ds_read_data( ds );
338
                                }
339
340
                                /* Add node for address book */
341
                                abf = ds->rawDataSource;
342
                                name = &dsName;
343
                                node = gtk_ctree_insert_node( tree, NULL, NULL,
344
                                                name, FOLDER_SPACING, bookXpm,
345
                                                bookXpmMask, bookXpm, bookXpmMask,
346
                                                FALSE, TRUE );
347
                                g_free( dsName );
348
349
                                fi = addressadd_create_folderinfo( abf, NULL );
350
                                gtk_ctree_node_set_row_data_full( tree, node, fi,
351
                                                ( GtkDestroyNotify ) addressadd_free_folderinfo );
352
353
                                rootFolder = addrindex_ds_get_root_folder( ds );
354
                                addressadd_load_folder( node, rootFolder, fi );
355
356
                                nodeDS = g_list_next( nodeDS );
357
                        }
358
                }
359
                list = g_list_next( list );
360
        }
361
}
362
363
gboolean addressadd_selection( AddressIndex *addrIndex, const gchar *name, const gchar *address, const gchar *remarks ) {
364
        gboolean retVal = FALSE;
365
        ItemPerson *person = NULL;
366
367
        addressadd_cancelled = FALSE;
368
        if( ! addressadd_dlg.window ) addressadd_create();
369
        gtk_widget_grab_focus(addressadd_dlg.ok_btn);
370
        gtk_widget_show(addressadd_dlg.window);
371
        manage_window_set_transient(GTK_WINDOW(addressadd_dlg.window));
372
373
        addressadd_dlg.fiSelected = NULL;
374
        addressadd_status_show( "" );
375
        addressadd_load_data( addrIndex );
376
        gtk_clist_select_row( GTK_CLIST( addressadd_dlg.tree_folder ), 0, 0 );
377
        gtk_widget_show(addressadd_dlg.window);
378
379
        gtk_label_set_text( GTK_LABEL(addressadd_dlg.label_name ), "" );
380
        gtk_label_set_text( GTK_LABEL(addressadd_dlg.label_address ), "" );
381
        gtk_label_set_text( GTK_LABEL(addressadd_dlg.label_remarks ), "" );
382
        if( name )
383
                gtk_label_set_text( GTK_LABEL(addressadd_dlg.label_name ), name );
384
        if( address )
385
                gtk_label_set_text( GTK_LABEL(addressadd_dlg.label_address ), address );
386
        if( remarks )
387
                gtk_label_set_text( GTK_LABEL(addressadd_dlg.label_remarks ), remarks );
388
389
        gtk_main();
390
        gtk_widget_hide( addressadd_dlg.window );
391
392
        if( ! addressadd_cancelled ) {
393
                if( addressadd_dlg.fiSelected ) {
394
                        FolderInfo *fi = addressadd_dlg.fiSelected;
395
                        person = addrbook_add_contact( fi->book, fi->folder, name, address, remarks );
396
                        if( person ) {
397
                                if( addressbook_edit_person( fi->book, NULL, person, FALSE ) == NULL )
398
                                        addrbook_remove_person( fi->book, person );
399
                                else
400
                                        retVal = TRUE;
401
                        }
402
                }
403
        }
404
405
        gtk_clist_clear( GTK_CLIST( addressadd_dlg.tree_folder ) );
406
407
        return retVal;
408
}
409
410
/*
411
* End of Source.
412
*/
413