]> git.0d.be Git - empathy.git/blob - libempathy-gtk/empathy-account-widget.c
Make use of tp-glib debug system.
[empathy.git] / libempathy-gtk / empathy-account-widget.c
1 /* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */
2 /*
3  * Copyright (C) 2006-2007 Imendio AB
4  * Copyright (C) 2007-2008 Collabora Ltd.
5  *
6  * This program is free software; you can redistribute it and/or
7  * modify it under the terms of the GNU General Public License as
8  * published by the Free Software Foundation; either version 2 of the
9  * License, or (at your option) any later version.
10  *
11  * This program is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14  * General Public License for more details.
15  *
16  * You should have received a copy of the GNU General Public
17  * License along with this program; if not, write to the
18  * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
19  * Boston, MA 02111-1307, USA.
20  * 
21  * Authors: Xavier Claessens <xclaesse@gmail.com>
22  *          Martyn Russell <martyn@imendio.com>
23  */
24
25 #include <config.h>
26
27 #include <string.h>
28
29 #include <gtk/gtk.h>
30 #include <glib/gi18n.h>
31
32 #include <libmissioncontrol/mc-account.h>
33 #include <libmissioncontrol/mc-protocol.h>
34
35 #include <libempathy/empathy-utils.h>
36
37 #include "empathy-account-widget.h"
38 #include "empathy-ui-utils.h"
39
40 #define DEBUG_FLAG EMPATHY_DEBUG_ACCOUNT
41 #include <libempathy/empathy-debug.h>
42
43 static gboolean 
44 account_widget_entry_focus_cb (GtkWidget     *widget,
45                                GdkEventFocus *event,
46                                McAccount     *account)
47 {
48         const gchar *str;
49         const gchar *param_name;
50
51         str = gtk_entry_get_text (GTK_ENTRY (widget));
52         param_name = g_object_get_data (G_OBJECT (widget), "param_name");
53
54         if (G_STR_EMPTY (str)) {
55                 gchar *value = NULL;
56
57                 mc_account_unset_param (account, param_name);
58                 mc_account_get_param_string (account, param_name, &value);
59                 DEBUG ("Unset %s and restore to %s", param_name, value);
60                 gtk_entry_set_text (GTK_ENTRY (widget), value ? value : "");
61                 g_free (value);
62         } else {
63                 DEBUG ("Setting %s to %s", param_name,
64                         strstr (param_name, "password") ? "***" : str);
65                 mc_account_set_param_string (account, param_name, str);
66         }
67
68         return FALSE;
69 }
70
71 static void
72 account_widget_int_changed_cb (GtkWidget *widget,
73                                McAccount *account)
74 {
75         const gchar *param_name;
76         gint         value;
77
78         value = gtk_spin_button_get_value_as_int (GTK_SPIN_BUTTON (widget));
79         param_name = g_object_get_data (G_OBJECT (widget), "param_name");
80
81         if (value == 0) {
82                 mc_account_unset_param (account, param_name);
83                 mc_account_get_param_int (account, param_name, &value);
84                 DEBUG ("Unset %s and restore to %d", param_name, value);
85                 gtk_spin_button_set_value (GTK_SPIN_BUTTON (widget), value);
86         } else {
87                 DEBUG ("Setting %s to %d", param_name, value);
88                 mc_account_set_param_int (account, param_name, value);
89         }
90 }
91
92 static void  
93 account_widget_checkbutton_toggled_cb (GtkWidget *widget,
94                                        McAccount *account)
95 {
96         gboolean     value;
97         gboolean     default_value;
98         const gchar *param_name;
99
100         value = gtk_toggle_button_get_active (GTK_TOGGLE_BUTTON (widget));
101         param_name = g_object_get_data (G_OBJECT (widget), "param_name");
102
103         /* FIXME: This is ugly! checkbox don't have a "not-set" value so we
104          * always unset the param and set the value if different from the
105          * default value. */
106         mc_account_unset_param (account, param_name);
107         mc_account_get_param_boolean (account, param_name, &default_value);
108
109         if (default_value == value) {
110                 DEBUG ("Unset %s and restore to %d", param_name, default_value);
111         } else {
112                 DEBUG ("Setting %s to %d", param_name, value);
113                 mc_account_set_param_boolean (account, param_name, value);
114         }
115 }
116
117 static void
118 account_widget_forget_clicked_cb (GtkWidget *button,
119                                   GtkWidget *entry)
120 {
121         McAccount   *account;
122         const gchar *param_name;
123
124         param_name = g_object_get_data (G_OBJECT (entry), "param_name");
125         account = g_object_get_data (G_OBJECT (entry), "account");
126
127         DEBUG ("Unset %s", param_name);
128         mc_account_unset_param (account, param_name);
129         gtk_entry_set_text (GTK_ENTRY (entry), "");
130 }
131
132 static void
133 account_widget_password_changed_cb (GtkWidget *entry,
134                                     GtkWidget *button)
135 {
136         const gchar *str;
137
138         str = gtk_entry_get_text (GTK_ENTRY (entry));
139         gtk_widget_set_sensitive (button, !G_STR_EMPTY (str));
140 }
141
142 static void  
143 account_widget_jabber_ssl_toggled_cb (GtkWidget *checkbutton_ssl,
144                                       GtkWidget *spinbutton_port)
145 {
146         McAccount *account;
147         gboolean   value;
148         gint       port = 0;
149
150         value = gtk_toggle_button_get_active (GTK_TOGGLE_BUTTON (checkbutton_ssl));
151         account = g_object_get_data (G_OBJECT (spinbutton_port), "account");
152         mc_account_get_param_int (account, "port", &port);
153
154         if (value) {
155                 if (port == 5222 || port == 0) {
156                         port = 5223;
157                 }
158         } else {
159                 if (port == 5223 || port == 0) {
160                         port = 5222;
161                 }
162         }
163
164         gtk_spin_button_set_value (GTK_SPIN_BUTTON (spinbutton_port), port);
165 }
166
167 static void
168 account_widget_setup_widget (GtkWidget   *widget,
169                              McAccount   *account,
170                              const gchar *param_name)
171 {
172         g_object_set_data_full (G_OBJECT (widget), "param_name", 
173                                 g_strdup (param_name), g_free);
174         g_object_set_data_full (G_OBJECT (widget), "account", 
175                                 g_object_ref (account), g_object_unref);
176
177         if (GTK_IS_SPIN_BUTTON (widget)) {
178                 gint value = 0;
179
180                 mc_account_get_param_int (account, param_name, &value);
181                 gtk_spin_button_set_value (GTK_SPIN_BUTTON (widget), value);
182
183                 g_signal_connect (widget, "value-changed",
184                                   G_CALLBACK (account_widget_int_changed_cb),
185                                   account);
186         }
187         else if (GTK_IS_ENTRY (widget)) {
188                 gchar *str = NULL;
189
190                 mc_account_get_param_string (account, param_name, &str);
191                 gtk_entry_set_text (GTK_ENTRY (widget), str ? str : "");
192                 g_free (str);
193
194                 if (strstr (param_name, "password")) {
195                         gtk_entry_set_visibility (GTK_ENTRY (widget), FALSE);
196                 }
197
198                 g_signal_connect (widget, "focus-out-event",
199                                   G_CALLBACK (account_widget_entry_focus_cb),
200                                   account);
201         }
202         else if (GTK_IS_TOGGLE_BUTTON (widget)) {
203                 gboolean value = FALSE;
204
205                 mc_account_get_param_boolean (account, param_name, &value);
206                 gtk_toggle_button_set_active (GTK_TOGGLE_BUTTON (widget), value);
207
208                 g_signal_connect (widget, "toggled",
209                                   G_CALLBACK (account_widget_checkbutton_toggled_cb),
210                                   account);
211         } else {
212                 DEBUG ("Unknown type of widget for param %s", param_name);
213         }
214 }
215
216 static gchar *
217 account_widget_generic_format_param_name (const gchar *param_name)
218 {
219         gchar *str;
220         gchar *p;
221
222         str = g_strdup (param_name);
223         
224         if (str && g_ascii_isalpha (str[0])) {
225                 str[0] = g_ascii_toupper (str[0]);
226         }
227         
228         while ((p = strchr (str, '-')) != NULL) {
229                 if (p[1] != '\0' && g_ascii_isalpha (p[1])) {
230                         p[0] = ' ';
231                         p[1] = g_ascii_toupper (p[1]);
232                 }
233
234                 p++;
235         }
236         
237         return str;
238 }
239
240 static void
241 accounts_widget_generic_setup (McAccount *account,
242                                GtkWidget *table_common_settings,
243                                GtkWidget *table_advanced_settings)
244 {
245         McProtocol *protocol;
246         McProfile  *profile;
247         GSList     *params, *l;
248
249         profile = mc_account_get_profile (account);
250         protocol = mc_profile_get_protocol (profile);
251
252         if (!protocol) {
253                 /* The CM is not installed, MC shouldn't list them
254                  * see SF bug #1688779
255                  * FIXME: We should display something asking the user to 
256                  * install the CM
257                  */
258                 g_object_unref (profile);
259                 return;
260         }
261
262         params = mc_protocol_get_params (protocol);
263
264         for (l = params; l; l = l->next) {
265                 McProtocolParam *param;
266                 GtkWidget       *table_settings;
267                 guint            n_rows = 0;
268                 GtkWidget       *widget = NULL;
269                 gchar           *param_name_formatted;
270
271                 param = l->data;
272                 if (param->flags & MC_PROTOCOL_PARAM_REQUIRED) {
273                         table_settings = table_common_settings;
274                 } else {
275                         table_settings = table_advanced_settings;
276                 }
277                 param_name_formatted = account_widget_generic_format_param_name (param->name);
278                 g_object_get (table_settings, "n-rows", &n_rows, NULL);
279                 gtk_table_resize (GTK_TABLE (table_settings), ++n_rows, 2);
280
281                 if (param->signature[0] == 's') {
282                         gchar *str;
283
284                         str = g_strdup_printf (_("%s:"), param_name_formatted);
285                         widget = gtk_label_new (str);
286                         gtk_misc_set_alignment (GTK_MISC (widget), 0, 0.5);
287                         g_free (str);
288
289                         gtk_table_attach (GTK_TABLE (table_settings),
290                                           widget,
291                                           0, 1,
292                                           n_rows - 1, n_rows,
293                                           GTK_FILL, 0,
294                                           0, 0);
295
296                         widget = gtk_entry_new ();
297                         gtk_table_attach (GTK_TABLE (table_settings),
298                                           widget,
299                                           1, 2,
300                                           n_rows - 1, n_rows,
301                                           GTK_FILL | GTK_EXPAND, 0,
302                                           0, 0);
303                 }
304                 /* int types: ynqiuxt. double type is 'd' */
305                 else if (param->signature[0] == 'y' ||
306                          param->signature[0] == 'n' ||
307                          param->signature[0] == 'q' ||
308                          param->signature[0] == 'i' ||
309                          param->signature[0] == 'u' ||
310                          param->signature[0] == 'x' ||
311                          param->signature[0] == 't' ||
312                          param->signature[0] == 'd') {
313                         gchar   *str = NULL;
314                         gdouble  minint = 0;
315                         gdouble  maxint = 0;
316                         gdouble  step = 1;
317
318                         switch (param->signature[0]) {
319                         case 'y': minint = G_MININT8;  maxint = G_MAXINT8;   break;
320                         case 'n': minint = G_MININT16; maxint = G_MAXINT16;  break;
321                         case 'q': minint = 0;          maxint = G_MAXUINT16; break;
322                         case 'i': minint = G_MININT32; maxint = G_MAXINT32;  break;
323                         case 'u': minint = 0;          maxint = G_MAXUINT32; break;
324                         case 'x': minint = G_MININT64; maxint = G_MAXINT64;  break;
325                         case 't': minint = 0;          maxint = G_MAXUINT64; break;
326                         case 'd': minint = G_MININT32; maxint = G_MAXINT32; step = 0.1; break;
327                         }
328
329                         str = g_strdup_printf (_("%s:"), param_name_formatted);
330                         widget = gtk_label_new (str);
331                         gtk_misc_set_alignment (GTK_MISC (widget), 0, 0.5);
332                         g_free (str);
333
334                         gtk_table_attach (GTK_TABLE (table_settings),
335                                           widget,
336                                           0, 1,
337                                           n_rows - 1, n_rows,
338                                           GTK_FILL, 0,
339                                           0, 0);
340
341                         widget = gtk_spin_button_new_with_range (minint, maxint, step);
342                         gtk_table_attach (GTK_TABLE (table_settings),
343                                           widget,
344                                           1, 2,
345                                           n_rows - 1, n_rows,
346                                           GTK_FILL | GTK_EXPAND, 0,
347                                           0, 0);
348                 }
349                 else if (param->signature[0] == 'b') {
350                         widget = gtk_check_button_new_with_label (param_name_formatted);
351                         gtk_table_attach (GTK_TABLE (table_settings),
352                                           widget,
353                                           0, 2,
354                                           n_rows - 1, n_rows,
355                                           GTK_FILL | GTK_EXPAND, 0,
356                                           0, 0);
357                 } else {
358                         DEBUG ("Unknown signature for param %s: %s",
359                                 param_name_formatted, param->signature);
360                 }
361
362                 if (widget) {
363                         account_widget_setup_widget (widget, account, param->name);
364                 }
365
366                 g_free (param_name_formatted);
367         }
368
369         g_slist_free (params);
370         g_object_unref (profile);
371         g_object_unref (protocol);
372 }
373
374 static void
375 account_widget_handle_params_valist (McAccount   *account,
376                                      GladeXML    *gui,
377                                      const gchar *first_widget_name,
378                                      va_list      args)
379 {
380         GtkWidget   *widget;
381         const gchar *widget_name;
382
383         for (widget_name = first_widget_name; widget_name; widget_name = va_arg (args, gchar*)) {
384                 const gchar *param_name;
385
386                 param_name = va_arg (args, gchar*);
387
388                 widget = glade_xml_get_widget (gui, widget_name);
389
390                 if (!widget) {
391                         g_warning ("Glade is missing widget '%s'.", widget_name);
392                         continue;
393                 }
394
395                 account_widget_setup_widget (widget, account, param_name);
396         }
397 }
398
399 void
400 empathy_account_widget_handle_params (McAccount   *account,
401                                       GladeXML    *gui,
402                                       const gchar *first_widget_name,
403                                       ...)
404 {
405         va_list args;
406
407         g_return_if_fail (MC_IS_ACCOUNT (account));
408
409         va_start (args, first_widget_name);
410         account_widget_handle_params_valist (account, gui,
411                                              first_widget_name,
412                                              args);
413         va_end (args);
414 }
415
416 void
417 empathy_account_widget_add_forget_button (McAccount   *account,
418                                           GladeXML    *glade,
419                                           const gchar *button,
420                                           const gchar *entry)
421 {
422         GtkWidget *button_forget;
423         GtkWidget *entry_password;
424         gchar     *password = NULL;
425         
426         button_forget = glade_xml_get_widget (glade, button);
427         entry_password = glade_xml_get_widget (glade, entry);
428
429         mc_account_get_param_string (account, "password", &password);
430         gtk_widget_set_sensitive (button_forget, !G_STR_EMPTY (password));
431         g_free (password);
432
433         g_signal_connect (button_forget, "clicked",
434                           G_CALLBACK (account_widget_forget_clicked_cb),
435                           entry_password);
436         g_signal_connect (entry_password, "changed",
437                           G_CALLBACK (account_widget_password_changed_cb),
438                           button_forget);
439 }
440
441 GtkWidget *
442 empathy_account_widget_generic_new (McAccount *account)
443 {
444         GladeXML  *glade;
445         GtkWidget *widget;
446         GtkWidget *table_common_settings;
447         GtkWidget *table_advanced_settings;
448         gchar     *filename;
449
450         g_return_val_if_fail (MC_IS_ACCOUNT (account), NULL);
451
452         filename = empathy_file_lookup ("empathy-account-widget-generic.glade",
453                                         "libempathy-gtk");
454         glade = empathy_glade_get_file (filename,
455                                         "vbox_generic_settings",
456                                         NULL,
457                                         "vbox_generic_settings", &widget,
458                                         "table_common_settings", &table_common_settings,
459                                         "table_advanced_settings", &table_advanced_settings,
460                                         NULL);
461         g_free (filename);
462
463         accounts_widget_generic_setup (account, table_common_settings, table_advanced_settings);
464
465         g_object_unref (glade);
466
467         gtk_widget_show_all (widget);
468
469         return widget;
470 }
471
472 GtkWidget *
473 empathy_account_widget_salut_new (McAccount *account)
474 {
475         GladeXML  *glade;
476         GtkWidget *widget;
477         gchar     *filename;
478
479         filename = empathy_file_lookup ("empathy-account-widget-salut.glade",
480                                         "libempathy-gtk");
481         glade = empathy_glade_get_file (filename,
482                                         "vbox_salut_settings",
483                                         NULL,
484                                         "vbox_salut_settings", &widget,
485                                         NULL);
486         g_free (filename);
487
488         empathy_account_widget_handle_params (account, glade,
489                         "entry_published", "published-name",
490                         "entry_nickname", "nickname",
491                         "entry_first_name", "first-name",
492                         "entry_last_name", "last-name",
493                         "entry_email", "email",
494                         "entry_jid", "jid",
495                         NULL);
496
497         g_object_unref (glade);
498
499         gtk_widget_show (widget);
500
501         return widget;
502 }
503
504 GtkWidget *
505 empathy_account_widget_msn_new (McAccount *account)
506 {
507         GladeXML  *glade;
508         GtkWidget *widget;
509         gchar     *filename;
510
511         filename = empathy_file_lookup ("empathy-account-widget-msn.glade",
512                                         "libempathy-gtk");
513         glade = empathy_glade_get_file (filename,
514                                         "vbox_msn_settings",
515                                         NULL,
516                                         "vbox_msn_settings", &widget,
517                                         NULL);
518         g_free (filename);
519
520         empathy_account_widget_handle_params (account, glade,
521                         "entry_id", "account",
522                         "entry_password", "password",
523                         "entry_server", "server",
524                         "spinbutton_port", "port",
525                         NULL);
526
527         empathy_account_widget_add_forget_button (account, glade,
528                                                   "button_forget",
529                                                   "entry_password");
530
531         g_object_unref (glade);
532
533         gtk_widget_show (widget);
534
535         return widget;
536 }
537
538 GtkWidget *
539 empathy_account_widget_jabber_new (McAccount *account)
540 {
541         GladeXML  *glade;
542         GtkWidget *widget;
543         GtkWidget *spinbutton_port;
544         GtkWidget *checkbutton_ssl;
545         gchar     *filename;
546
547         filename = empathy_file_lookup ("empathy-account-widget-jabber.glade",
548                                         "libempathy-gtk");
549         glade = empathy_glade_get_file (filename,
550                                         "vbox_jabber_settings",
551                                         NULL,
552                                         "vbox_jabber_settings", &widget,
553                                         "spinbutton_port", &spinbutton_port,
554                                         "checkbutton_ssl", &checkbutton_ssl,
555                                         NULL);
556         g_free (filename);
557
558         empathy_account_widget_handle_params (account, glade,
559                         "entry_id", "account",
560                         "entry_password", "password",
561                         "entry_resource", "resource",
562                         "entry_server", "server",
563                         "spinbutton_port", "port",
564                         "spinbutton_priority", "priority",
565                         "checkbutton_ssl", "old-ssl",
566                         "checkbutton_ignore_ssl_errors", "ignore-ssl-errors",
567                         "checkbutton_encryption", "require-encryption",
568                         NULL);
569
570         empathy_account_widget_add_forget_button (account, glade,
571                                                   "button_forget",
572                                                   "entry_password");
573
574         g_signal_connect (checkbutton_ssl, "toggled",
575                           G_CALLBACK (account_widget_jabber_ssl_toggled_cb),
576                           spinbutton_port);
577
578         g_object_unref (glade);
579
580         gtk_widget_show (widget);
581
582         return widget;
583 }
584
585 GtkWidget *
586 empathy_account_widget_icq_new (McAccount *account)
587 {
588         GladeXML  *glade;
589         GtkWidget *widget;
590         GtkWidget *spinbutton_port;
591         gchar     *filename;
592
593         filename = empathy_file_lookup ("empathy-account-widget-icq.glade",
594                                         "libempathy-gtk");
595         glade = empathy_glade_get_file (filename,
596                                         "vbox_icq_settings",
597                                         NULL,
598                                         "vbox_icq_settings", &widget,
599                                         "spinbutton_port", &spinbutton_port,
600                                         NULL);
601         g_free (filename);
602
603         empathy_account_widget_handle_params (account, glade,
604                         "entry_uin", "account",
605                         "entry_password", "password",
606                         "entry_server", "server",
607                         "spinbutton_port", "port",
608                         "entry_charset", "charset",
609                         NULL);
610
611         empathy_account_widget_add_forget_button (account, glade,
612                                                   "button_forget",
613                                                   "entry_password");
614
615         g_object_unref (glade);
616
617         gtk_widget_show (widget);
618
619         return widget;
620 }
621
622 GtkWidget *
623 empathy_account_widget_aim_new (McAccount *account)
624 {
625         GladeXML  *glade;
626         GtkWidget *widget;
627         GtkWidget *spinbutton_port;
628         gchar     *filename;
629
630         filename = empathy_file_lookup ("empathy-account-widget-aim.glade",
631                                         "libempathy-gtk");
632         glade = empathy_glade_get_file (filename,
633                                         "vbox_aim_settings",
634                                         NULL,
635                                         "vbox_aim_settings", &widget,
636                                         "spinbutton_port", &spinbutton_port,
637                                         NULL);
638         g_free (filename);
639
640         empathy_account_widget_handle_params (account, glade,
641                         "entry_screenname", "account",
642                         "entry_password", "password",
643                         "entry_server", "server",
644                         "spinbutton_port", "port",
645                         NULL);
646
647         empathy_account_widget_add_forget_button (account, glade,
648                                                   "button_forget",
649                                                   "entry_password");
650
651         g_object_unref (glade);
652
653         gtk_widget_show (widget);
654
655         return widget;
656 }
657
658 GtkWidget *
659 empathy_account_widget_yahoo_new (McAccount *account)
660 {
661         GladeXML  *glade;
662         GtkWidget *widget;
663         gchar     *filename;
664
665         filename = empathy_file_lookup ("empathy-account-widget-yahoo.glade",
666                                         "libempathy-gtk");
667         glade = empathy_glade_get_file (filename,
668                                         "vbox_yahoo_settings",
669                                         NULL,
670                                         "vbox_yahoo_settings", &widget,
671                                         NULL);
672         g_free (filename);
673
674         empathy_account_widget_handle_params (account, glade,
675                         "entry_id", "account",
676                         "entry_password", "password",
677                         "entry_server", "server",
678                         "entry_serverjp", "serverjp",
679                         "entry_locale", "room-list-locale",
680                         "entry_charset", "charset",
681                         "spinbutton_port", "port",
682                         "checkbutton_yahoojp", "yahoojp",
683                         "checkbutton_ignore_invites", "ignore-invites",
684                         NULL);
685
686         empathy_account_widget_add_forget_button (account, glade,
687                                                   "button_forget",
688                                                   "entry_password");
689
690         g_object_unref (glade);
691
692         gtk_widget_show (widget);
693
694         return widget;
695 }
696
697 GtkWidget *
698 empathy_account_widget_groupwise_new (McAccount *account)
699 {
700         GladeXML  *glade;
701         GtkWidget *widget;
702         gchar     *filename;
703
704         filename = empathy_file_lookup ("empathy-account-widget-groupwise.glade",
705                                         "libempathy-gtk");
706         glade = empathy_glade_get_file (filename,
707                                         "vbox_groupwise_settings",
708                                         NULL,
709                                         "vbox_groupwise_settings", &widget,
710                                         NULL);
711         g_free (filename);
712
713         empathy_account_widget_handle_params (account, glade,
714                         "entry_id", "account",
715                         "entry_password", "password",
716                         "entry_server", "server",
717                         "spinbutton_port", "port",
718                         NULL);
719
720         empathy_account_widget_add_forget_button (account, glade,
721                                                   "button_forget",
722                                                   "entry_password");
723
724         g_object_unref (glade);
725
726         gtk_widget_show (widget);
727
728         return widget;
729 }
730