diff options
author | Matthew Barnes <mbarnes@src.gnome.org> | 2008-08-30 06:32:46 +0800 |
---|---|---|
committer | Matthew Barnes <mbarnes@src.gnome.org> | 2008-08-30 06:32:46 +0800 |
commit | e0c501b7018f12d37b10e32923f95b7a01c7982c (patch) | |
tree | 0114cbe9529000ec06dbe4ebe927e8c6cafbf0ba /addressbook/gui | |
parent | 02a9eb68308537fe712e757017ae4bb372863a8c (diff) | |
download | gsoc2013-evolution-e0c501b7018f12d37b10e32923f95b7a01c7982c.tar.gz gsoc2013-evolution-e0c501b7018f12d37b10e32923f95b7a01c7982c.tar.zst gsoc2013-evolution-e0c501b7018f12d37b10e32923f95b7a01c7982c.zip |
Progress update:
- Contacts module partially working!
- Implement UI merging. Also merge EInfoLabel into ESidebar.
The shell window now manages the icon and labels and keeps
them up-to-date via EShellView properties.
svn path=/branches/kill-bonobo/; revision=36214
Diffstat (limited to 'addressbook/gui')
-rw-r--r-- | addressbook/gui/component/Makefile.am | 5 | ||||
-rw-r--r-- | addressbook/gui/component/addressbook-config.c | 2 | ||||
-rw-r--r-- | addressbook/gui/component/addressbook-view.c | 328 | ||||
-rw-r--r-- | addressbook/gui/component/autocompletion-config.c | 139 | ||||
-rw-r--r-- | addressbook/gui/component/autocompletion-config.h | 8 | ||||
-rw-r--r-- | addressbook/gui/component/e-book-shell-module.c | 24 | ||||
-rw-r--r-- | addressbook/gui/component/e-book-shell-view-actions.c | 77 | ||||
-rw-r--r-- | addressbook/gui/component/e-book-shell-view-private.c | 124 | ||||
-rw-r--r-- | addressbook/gui/component/e-book-shell-view-private.h | 23 | ||||
-rw-r--r-- | addressbook/gui/component/e-book-shell-view.c | 105 | ||||
-rw-r--r-- | addressbook/gui/contact-editor/e-contact-editor.h | 4 | ||||
-rw-r--r-- | addressbook/gui/contact-editor/eab-editor.h | 1 | ||||
-rw-r--r-- | addressbook/gui/widgets/Makefile.am | 3 | ||||
-rw-r--r-- | addressbook/gui/widgets/eab-gui-util.c | 5 | ||||
-rw-r--r-- | addressbook/gui/widgets/eab-popup-control.h | 1 |
15 files changed, 391 insertions, 458 deletions
diff --git a/addressbook/gui/component/Makefile.am b/addressbook/gui/component/Makefile.am index 6726d2b050..7eaa46b079 100644 --- a/addressbook/gui/component/Makefile.am +++ b/addressbook/gui/component/Makefile.am @@ -20,7 +20,7 @@ INCLUDES = \ $(LDAP_CFLAGS) \ $(EVOLUTION_ADDRESSBOOK_CFLAGS) -component_LTLIBRARIES = libevolution-addressbook.la +module_LTLIBRARIES = libevolution-addressbook.la libevolution_addressbook_la_SOURCES = \ addressbook-config.c \ @@ -31,9 +31,6 @@ libevolution_addressbook_la_SOURCES = \ autocompletion-config.h \ addressbook.c \ addressbook.h \ - addressbook-view.c \ - addressbook-view.h \ - component-factory.c \ e-book-shell-module.c \ e-book-shell-view.c \ e-book-shell-view.h \ diff --git a/addressbook/gui/component/addressbook-config.c b/addressbook/gui/component/addressbook-config.c index 740e2c0575..3907f6648d 100644 --- a/addressbook/gui/component/addressbook-config.c +++ b/addressbook/gui/component/addressbook-config.c @@ -53,8 +53,6 @@ #define LDAPS_PORT_STRING "636" #define GLADE_FILE_NAME "ldap-config.glade" -#define CONFIG_CONTROL_FACTORY_ID "OAFIID:GNOME_Evolution_Addressbook_ConfigControlFactory:" BASE_VERSION -#define LDAP_CONFIG_CONTROL_ID "OAFIID:GNOME_Evolution_LDAPStorage_ConfigControl:" BASE_VERSION GtkWidget* supported_bases_create_table (char *name, char *string1, char *string2, int num1, int num2); diff --git a/addressbook/gui/component/addressbook-view.c b/addressbook/gui/component/addressbook-view.c index b45329b37e..34a15c2921 100644 --- a/addressbook/gui/component/addressbook-view.c +++ b/addressbook/gui/component/addressbook-view.c @@ -111,10 +111,6 @@ static void activate_source (AddressbookView *view, ESource *source); static void addressbook_view_init (AddressbookView *view); static void addressbook_view_class_init (AddressbookViewClass *klass); -static void addressbook_view_dispose (GObject *object); - -static ESource *find_first_source (ESourceList *source_list); -static ESource *get_primary_source (AddressbookView *view); static void set_status_message (EABView *eav, const char *message, AddressbookView *view) @@ -234,26 +230,6 @@ load_uri_for_selection (ESourceSelector *selector, activate_source (view, selected_source); } -static ESource * -find_first_source (ESourceList *source_list) -{ - GSList *groups, *sources, *l, *m; - - groups = e_source_list_peek_groups (source_list); - for (l = groups; l; l = l->next) { - ESourceGroup *group = l->data; - - sources = e_source_group_peek_sources (group); - for (m = sources; m; m = m->next) { - ESource *source = m->data; - - return source; - } - } - - return NULL; -} - static void save_primary_selection (AddressbookView *view) { @@ -270,38 +246,6 @@ save_primary_selection (AddressbookView *view) e_source_peek_uid (source), NULL); } -static ESource * -get_primary_source (AddressbookView *view) -{ - AddressbookViewPrivate *priv = view->priv; - ESource *source; - char *uid; - - uid = gconf_client_get_string (priv->gconf_client, - "/apps/evolution/addressbook/display/primary_addressbook", - NULL); - if (uid) { - source = e_source_list_peek_source_by_uid (priv->source_list, uid); - g_free (uid); - } else { - /* Try to create a default if there isn't one */ - source = find_first_source (priv->source_list); - } - - return source; -} - -static void -load_primary_selection (AddressbookView *view) -{ - AddressbookViewPrivate *priv = view->priv; - ESource *source; - - source = get_primary_source (view); - if (source) - e_source_selector_set_primary_selection (E_SOURCE_SELECTOR (priv->selector), source); -} - /* Folder popup menu callbacks */ typedef struct { AddressbookView *view; @@ -377,31 +321,6 @@ delete_addressbook_cb(EPopup *ep, EPopupItem *pitem, void *data) } static void -new_addressbook_cb(EPopup *ep, EPopupItem *pitem, void *data) -{ - addressbook_config_create_new_source (gtk_widget_get_toplevel(ep->target->widget)); -} - -static void -save_addressbook_cb(EPopup *ep, EPopupItem *pitem, void *data) -{ - AddressbookView *view = data; - EABView *v = get_current_view (view); - if (v) - eab_view_save_as (v, TRUE); -} - -static void -edit_addressbook_cb(EPopup *ep, EPopupItem *pitem, void *data) -{ - AddressbookView *view = data; - if (view) - edit_addressbook_folder (view); -} - -/* Callbacks. */ - -static void primary_source_selection_changed_callback (ESourceSelector *selector, AddressbookView *view) { @@ -409,55 +328,6 @@ primary_source_selection_changed_callback (ESourceSelector *selector, save_primary_selection (view); } -static EPopupItem abv_source_popups[] = { - { E_POPUP_ITEM, "10.new", N_("_New Address Book"), new_addressbook_cb, NULL, "address-book-new", 0, 0 }, - { E_POPUP_ITEM, "20.saveasvcard", N_("Save As vCard..."), save_addressbook_cb, NULL,"document-save-as", 0, EAB_POPUP_SOURCE_PRIMARY }, - - { E_POPUP_BAR, "30.bar" }, - { E_POPUP_ITEM, "30.delete", N_("_Delete"), delete_addressbook_cb, NULL, "edit-delete", 0, EAB_POPUP_SOURCE_USER|EAB_POPUP_SOURCE_PRIMARY }, - - { E_POPUP_BAR, "99.bar" }, - { E_POPUP_ITEM, "99.properties", N_("_Properties"), edit_addressbook_cb, NULL,"document-properties", 0, EAB_POPUP_SOURCE_PRIMARY }, -}; - -static void -abv_source_popup_free(EPopup *ep, GSList *list, void *data) -{ - g_slist_free(list); -} - -static gboolean -popup_event_callback(ESourceSelector *selector, ESource *source, GdkEventButton *event, AddressbookView *view) -{ - EABPopup *ep; - EABPopupTargetSource *t; - GSList *menus = NULL; - int i; - GtkMenu *menu; - - /** @HookPoint-EABPopup:Addressbook Source Selector Context Menu - * @Id: org.gnome.evolution.addressbook.source.popup - * @Class: org.gnome.evolution.addresbook.popup:1.0 - * @Target: EABPopupTargetSource - * - * The context menu on the source selector in the contacts window. - */ - - ep = eab_popup_new("org.gnome.evolution.addressbook.source.popup"); - t = eab_popup_target_new_source(ep, selector); - t->target.widget = (GtkWidget *)view->priv->notebook; - - for (i=0;i<sizeof(abv_source_popups)/sizeof(abv_source_popups[0]);i++) - menus = g_slist_prepend(menus, &abv_source_popups[i]); - - e_popup_add_items((EPopup *)ep, menus, NULL, abv_source_popup_free, view); - - menu = e_popup_create_menu_once((EPopup *)ep, (EPopupTarget *)t, 0); - gtk_menu_popup(menu, NULL, NULL, NULL, NULL, event?event->button:0, event?event->time:gtk_get_current_event_time()); - - return TRUE; -} - static gboolean selector_tree_drag_drop (GtkWidget *widget, GdkDragContext *context, @@ -696,58 +566,6 @@ selector_tree_drag_leave (GtkWidget *widget, GdkDragContext *context, guint time gtk_tree_view_set_drag_dest_row(GTK_TREE_VIEW (widget), NULL, GTK_TREE_VIEW_DROP_BEFORE); } - -static void -destroy_callback(gpointer data, GObject *where_object_was) -{ - AddressbookView *view = data; - g_object_unref (view); -} - -GType -addressbook_view_get_type (void) -{ - static GType type = 0; - - if (!type) { - static const GTypeInfo info = { - sizeof (AddressbookViewClass), - NULL, /* base_init */ - NULL, /* base_finalize */ - (GClassInitFunc) addressbook_view_class_init, - NULL, /* class_finalize */ - NULL, /* class_data */ - sizeof (EABView), - 0, /* n_preallocs */ - (GInstanceInitFunc) addressbook_view_init, - }; - - type = g_type_register_static (PARENT_TYPE, "AddressbookView", &info, 0); - } - - return type; -} - -static void -addressbook_view_class_init (AddressbookViewClass *klass) -{ - GObjectClass *object_class = G_OBJECT_CLASS (klass); - - object_class->dispose = addressbook_view_dispose; - - parent_class = g_type_class_peek_parent (klass); -} - -static gboolean -source_selector_key_press_event_callback (GtkWidget *widget, GdkEventKey *event, AddressbookView *view) -{ - if (event->keyval == GDK_Delete) { - delete_addressbook_folder (view); - return TRUE; - } - return FALSE; -} - static void addressbook_view_init (AddressbookView *view) { @@ -755,84 +573,21 @@ addressbook_view_init (AddressbookView *view) GtkWidget *selector_scrolled_window; AtkObject *a11y; - view->priv = - priv = g_new0 (AddressbookViewPrivate, 1); - - priv->gconf_client = addressbook_component_peek_gconf_client (addressbook_component_peek ()); - - priv->uid_to_view = g_hash_table_new_full (g_str_hash, g_str_equal, (GDestroyNotify)g_free, (GDestroyNotify)g_object_unref); - priv->uid_to_editor = g_hash_table_new_full (g_str_hash, g_str_equal, (GDestroyNotify)g_free, (GDestroyNotify)g_free); - - priv->notebook = gtk_notebook_new (); - gtk_notebook_set_show_tabs (GTK_NOTEBOOK (priv->notebook), FALSE); - gtk_notebook_set_show_border (GTK_NOTEBOOK (priv->notebook), FALSE); - - g_object_weak_ref (G_OBJECT (priv->notebook), destroy_callback, view); - - /* Create the control. */ - priv->folder_view_control = bonobo_control_new (priv->notebook); - - gtk_widget_show (priv->notebook); - - e_book_get_addressbooks (&priv->source_list, NULL); - g_signal_connect (priv->source_list, - "changed", - G_CALLBACK (source_list_changed_cb), view); - - priv->creatable_items_handler = e_user_creatable_items_handler_new ("contacts", NULL, NULL); priv->menu = eab_menu_new("org.gnome.evolution.addressbook.view"); g_signal_connect (priv->folder_view_control, "activate", G_CALLBACK (control_activate_cb), view); - priv->activity_handler = e_activity_handler_new (); - - priv->statusbar_widget = e_task_bar_new (); - gtk_widget_show (priv->statusbar_widget); - - e_activity_handler_attach_task_bar (priv->activity_handler, - E_TASK_BAR (priv->statusbar_widget)); - - priv->info_widget = e_info_label_new("x-office-address-book"); - e_info_label_set_info((EInfoLabel*)priv->info_widget, _("Contacts"), ""); - gtk_widget_show (priv->info_widget); - - priv->selector = e_source_selector_new (priv->source_list); - g_signal_connect (priv->selector, "drag-motion", G_CALLBACK (selector_tree_drag_motion), view); g_signal_connect (priv->selector, "drag-leave", G_CALLBACK (selector_tree_drag_leave), view); g_signal_connect (priv->selector, "drag-drop", G_CALLBACK (selector_tree_drag_drop), view); g_signal_connect (priv->selector, "drag-data-received", G_CALLBACK (selector_tree_drag_data_received), view); gtk_drag_dest_set (priv->selector, GTK_DEST_DEFAULT_ALL, drag_types, num_drag_types, GDK_ACTION_COPY | GDK_ACTION_MOVE); - a11y = gtk_widget_get_accessible (GTK_WIDGET (priv->selector)); - atk_object_set_name (a11y, _("Contact Source Selector")); - - e_source_selector_show_selection (E_SOURCE_SELECTOR (priv->selector), FALSE); - gtk_widget_show (priv->selector); - - selector_scrolled_window = gtk_scrolled_window_new (NULL, NULL); - gtk_scrolled_window_set_shadow_type (GTK_SCROLLED_WINDOW (selector_scrolled_window), GTK_SHADOW_IN); - gtk_scrolled_window_set_policy (GTK_SCROLLED_WINDOW (selector_scrolled_window), - GTK_POLICY_AUTOMATIC, GTK_POLICY_AUTOMATIC); - gtk_container_add (GTK_CONTAINER (selector_scrolled_window), priv->selector); - gtk_widget_show (selector_scrolled_window); - - priv->sidebar_widget = gtk_vbox_new(FALSE, 0); - gtk_box_pack_start(GTK_BOX (priv->sidebar_widget), priv->info_widget, FALSE, TRUE, 0); - gtk_box_pack_start(GTK_BOX (priv->sidebar_widget), selector_scrolled_window, TRUE, TRUE, 0); - gtk_widget_show (priv->sidebar_widget); g_signal_connect_object (priv->selector, "primary_selection_changed", G_CALLBACK (primary_source_selection_changed_callback), G_OBJECT (view), 0); - g_signal_connect_after (priv->selector, "key_press_event", - G_CALLBACK (source_selector_key_press_event_callback), - G_OBJECT (view)); - g_signal_connect_object (priv->selector, "popup_event", - G_CALLBACK (popup_event_callback), - G_OBJECT (view), 0); - load_primary_selection (view); load_uri_for_selection (E_SOURCE_SELECTOR (priv->selector), view, TRUE); } @@ -849,43 +604,6 @@ destroy_editor (char *key, gtk_widget_destroy (GTK_WIDGET (closure->editor)); } -static void -addressbook_view_dispose (GObject *object) -{ - AddressbookView *view = ADDRESSBOOK_VIEW (object); - AddressbookViewPrivate *priv = view->priv; - - if (view->priv) { - if (priv->book) - g_object_unref (priv->book); - - g_free(priv->passwd); - - if (priv->source_list) - g_object_unref (priv->source_list); - - if (priv->uid_to_view) - g_hash_table_destroy (priv->uid_to_view); - - if (priv->uid_to_editor) { - g_hash_table_foreach (priv->uid_to_editor, (GHFunc)destroy_editor, NULL); - g_hash_table_destroy (priv->uid_to_editor); - } - - if (priv->creatable_items_handler) - g_object_unref (priv->creatable_items_handler); - - if (priv->menu) - g_object_unref (priv->menu); - - g_free (view->priv); - view->priv = NULL; - } - - if (G_OBJECT_CLASS (parent_class)->dispose) - (* G_OBJECT_CLASS (parent_class)->dispose) (object); -} - typedef struct { EABView *view; ESource *source; @@ -1033,52 +751,6 @@ activate_source (AddressbookView *view, } } -AddressbookView * -addressbook_view_new (void) -{ - return g_object_new (ADDRESSBOOK_TYPE_VIEW, NULL); -} - -EActivityHandler* -addressbook_view_peek_activity_handler (AddressbookView *view) -{ - g_return_val_if_fail (ADDRESSBOOK_IS_VIEW (view), NULL); - - return view->priv->activity_handler; -} - -GtkWidget* -addressbook_view_peek_info_label (AddressbookView *view) -{ - g_return_val_if_fail (ADDRESSBOOK_IS_VIEW (view), NULL); - - return view->priv->info_widget; -} - -GtkWidget* -addressbook_view_peek_sidebar (AddressbookView *view) -{ - g_return_val_if_fail (ADDRESSBOOK_IS_VIEW (view), NULL); - - return view->priv->sidebar_widget; -} - -GtkWidget* -addressbook_view_peek_statusbar (AddressbookView *view) -{ - g_return_val_if_fail (ADDRESSBOOK_IS_VIEW (view), NULL); - - return view->priv->statusbar_widget; -} - -BonoboControl* -addressbook_view_peek_folder_view (AddressbookView *view) -{ - g_return_val_if_fail (ADDRESSBOOK_IS_VIEW (view), NULL); - - return view->priv->folder_view_control; -} - void addressbook_view_edit_contact (AddressbookView* view, const char* source_uid, diff --git a/addressbook/gui/component/autocompletion-config.c b/addressbook/gui/component/autocompletion-config.c index b410d74634..060ce01aee 100644 --- a/addressbook/gui/component/autocompletion-config.c +++ b/addressbook/gui/component/autocompletion-config.c @@ -16,47 +16,32 @@ * License along with this program; if not, write to the * Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, * Boston, MA 02110-1301, USA. - * - * Authors: Chris Toshok <toshok@ximian.com> */ -#ifdef HAVE_CONFIG_H -#include <config.h> -#endif - - #include "autocompletion-config.h" -#include "Evolution.h" - -#include <bonobo/bonobo-exception.h> - -#include <libedataserver/e-source-list.h> -#include <libedataserverui/e-source-selector.h> +#include <e-shell.h> #include <gtk/gtk.h> #include <glib/gi18n.h> - - -typedef struct { - EvolutionConfigControl *config_control; - - GtkWidget *control_widget; - - ESourceList *source_list; -} AutocompletionConfig; +#include <e-preferences-window.h> +#include <libedataserver/e-source-list.h> +#include <libedataserverui/e-source-selector.h> static void -source_selection_changed (ESourceSelector *selector, - AutocompletionConfig *ac) +source_selection_changed_cb (ESourceSelector *source_selector) { + ESourceList *source_list; GSList *selection; GSList *l; GSList *groups; + source_list = e_source_selector_get_source_list (source_selector); + /* first we clear all the completion flags from all sources */ - for (groups = e_source_list_peek_groups (ac->source_list); groups; groups = groups->next) { + for (groups = e_source_list_peek_groups (source_list); groups; groups = groups->next) { ESourceGroup *group = E_SOURCE_GROUP (groups->data); GSList *sources; + for (sources = e_source_group_peek_sources (group); sources; sources = sources->next) { ESource *source = E_SOURCE (sources->data); @@ -66,86 +51,78 @@ source_selection_changed (ESourceSelector *selector, /* then we loop over the selector's selection, setting the property on those sources */ - selection = e_source_selector_get_selection (selector); + selection = e_source_selector_get_selection (source_selector); for (l = selection; l; l = l->next) { - e_source_set_property (E_SOURCE (l->data), "completion", "true"); + ESource *source = E_SOURCE (l->data); + + e_source_set_property (source, "completion", "true"); } e_source_selector_free_selection (selection); - e_source_list_sync (ac->source_list, NULL); /* XXX we should pop up a dialog if this fails */ + /* XXX we should pop up a dialog if this fails */ + e_source_list_sync (source_list, NULL); } static void -config_control_destroy_notify (void *data, - GObject *where_the_config_control_was) -{ - AutocompletionConfig *ac = (AutocompletionConfig *) data; - - g_object_unref (ac->source_list); - - g_free (ac); -} - -static void -initialize_selection (AutocompletionConfig *ac) +initialize_selection (ESourceSelector *source_selector) { + ESourceList *source_list; GSList *groups; - for (groups = e_source_list_peek_groups (ac->source_list); groups; groups = groups->next) { + source_list = e_source_selector_get_source_list (source_selector); + + for (groups = e_source_list_peek_groups (source_list); groups; groups = groups->next) { ESourceGroup *group = E_SOURCE_GROUP (groups->data); GSList *sources; + for (sources = e_source_group_peek_sources (group); sources; sources = sources->next) { ESource *source = E_SOURCE (sources->data); - const char *completion = e_source_get_property (source, "completion"); + const char *completion; + + completion = e_source_get_property (source, "completion"); if (completion && !g_ascii_strcasecmp (completion, "true")) - e_source_selector_select_source (E_SOURCE_SELECTOR (ac->control_widget), - source); + e_source_selector_select_source (source_selector, source); } } } -EvolutionConfigControl* -autocompletion_config_control_new (void) +void +autocompletion_config_init (void) { - AutocompletionConfig *ac; - CORBA_Environment ev; - GtkWidget *scrolledwin; - - ac = g_new0 (AutocompletionConfig, 1); + ESourceList *source_list; + GtkWidget *scrolled_window; + GtkWidget *source_selector; + GtkWidget *preferences_window; - CORBA_exception_init (&ev); + source_list = e_source_list_new_for_gconf_default ( + "/apps/evolution/addressbook/sources"); - ac->source_list = e_source_list_new_for_gconf_default ("/apps/evolution/addressbook/sources"); /* XXX should we watch for the source list to change and update it in the control? what about our local changes? */ /* g_signal_connect (ac->source_list, "changed", G_CALLBACK (source_list_changed), ac); */ - scrolledwin = gtk_scrolled_window_new (NULL, NULL); - - gtk_scrolled_window_set_policy (GTK_SCROLLED_WINDOW (scrolledwin), - GTK_POLICY_AUTOMATIC, - GTK_POLICY_AUTOMATIC); - gtk_scrolled_window_set_shadow_type (GTK_SCROLLED_WINDOW (scrolledwin), - GTK_SHADOW_IN); - - ac->control_widget = e_source_selector_new (ac->source_list); - - gtk_container_add (GTK_CONTAINER (scrolledwin), ac->control_widget); - - initialize_selection (ac); - - gtk_widget_show (ac->control_widget); - gtk_widget_show (scrolledwin); - - ac->config_control = evolution_config_control_new (scrolledwin); - - g_signal_connect (ac->control_widget, "selection_changed", - G_CALLBACK (source_selection_changed), ac); - - g_object_weak_ref (G_OBJECT (ac->config_control), config_control_destroy_notify, ac); - - CORBA_exception_free (&ev); - - return ac->config_control; + scrolled_window = gtk_scrolled_window_new (NULL, NULL); + gtk_scrolled_window_set_policy ( + GTK_SCROLLED_WINDOW (scrolled_window), + GTK_POLICY_AUTOMATIC, GTK_POLICY_AUTOMATIC); + gtk_scrolled_window_set_shadow_type ( + GTK_SCROLLED_WINDOW (scrolled_window), GTK_SHADOW_IN); + gtk_widget_show (scrolled_window); + + source_selector = e_source_selector_new (source_list); + g_signal_connect ( + source_selector, "selection_changed", + G_CALLBACK (source_selection_changed_cb), NULL); + gtk_container_add (GTK_CONTAINER (scrolled_window), source_selector); + gtk_widget_show (source_selector); + + initialize_selection (E_SOURCE_SELECTOR (source_selector)); + + e_preferences_window_add_page ( + e_shell_get_preferences_window (), + "autocompletion", + "preferences-autocompletion", + _("Autocompletion"), + scrolled_window, + 200); } - diff --git a/addressbook/gui/component/autocompletion-config.h b/addressbook/gui/component/autocompletion-config.h index d55ef2cd79..1ad958235e 100644 --- a/addressbook/gui/component/autocompletion-config.h +++ b/addressbook/gui/component/autocompletion-config.h @@ -23,8 +23,12 @@ #ifndef _AUTOCOMPLETION_CONFIG_H #define _AUTOCOMPLETION_CONFIG_H -#include "evolution-config-control.h" +#include <glib.h> -EvolutionConfigControl* autocompletion_config_control_new (void); +G_BEGIN_DECLS + +void autocompletion_config_init (void); + +G_END_DECLS #endif /* _AUTOCOMPLETION_CONFIG_H */ diff --git a/addressbook/gui/component/e-book-shell-module.c b/addressbook/gui/component/e-book-shell-module.c index 25693234ee..aaaa6fecdb 100644 --- a/addressbook/gui/component/e-book-shell-module.c +++ b/addressbook/gui/component/e-book-shell-module.c @@ -18,11 +18,22 @@ * Boston, MA 02110-1301, USA. */ +#include <string.h> +#include <glib/gi18n.h> +#include <libebook/e-book.h> +#include <libedataserver/e-url.h> +#include <libedataserver/e-source.h> +#include <libedataserver/e-source-list.h> +#include <libedataserver/e-source-group.h> + #include <e-shell.h> #include <e-shell-module.h> #include <e-shell-window.h> -#include "e-book-shell-view.h" +#include <eab-gui-util.h> +#include <e-book-shell-view.h> +#include <addressbook-config.h> +#include <autocompletion-config.h> #define MODULE_NAME "addressbook" #define MODULE_ALIASES "" @@ -174,7 +185,7 @@ book_module_book_loaded_cb (EBook *book, if (g_str_equal (action_name, "contact-new")) eab_show_contact_editor (book, contact, TRUE, TRUE); - if (g_str_equal (action_name, "contact-list-new") == 0) + if (g_str_equal (action_name, "contact-list-new")) eab_show_contact_list_editor (book, contact, TRUE, TRUE); g_object_unref (contact); @@ -189,6 +200,7 @@ action_contact_new_cb (GtkAction *action, GConfClient *client; ESourceList *source_list; const gchar *key; + gchar *uid; /* This callback is used for both contacts and contact lists. */ @@ -260,6 +272,8 @@ book_module_is_busy (EShellModule *shell_module) static gboolean book_module_shutdown (EShellModule *shell_module) { + /* FIXME */ + return TRUE; } static gboolean @@ -282,7 +296,7 @@ book_module_handle_uri (EShellModule *shell_module, return FALSE; } - while (*cp != NULL) { + while (*cp != '\0') { gchar *header; gchar *content; gsize length; @@ -345,7 +359,7 @@ book_module_window_created (EShellModule *shell_module, source_entries, G_N_ELEMENTS (source_entries)); } -static EShellmoduleInfo module_info = { +static EShellModuleInfo module_info = { MODULE_NAME, MODULE_ALIASES, @@ -378,4 +392,6 @@ e_shell_module_init (GTypeModule *type_module) g_signal_connect_swapped ( shell, "window-created", G_CALLBACK (book_module_window_created), shell_module); + + autocompletion_config_init (); } diff --git a/addressbook/gui/component/e-book-shell-view-actions.c b/addressbook/gui/component/e-book-shell-view-actions.c index 8d2d1a7739..d5f961ec66 100644 --- a/addressbook/gui/component/e-book-shell-view-actions.c +++ b/addressbook/gui/component/e-book-shell-view-actions.c @@ -20,8 +20,11 @@ #include "e-book-shell-view-private.h" +#include <e-util/e-error.h> #include <e-util/e-util.h> +#include <addressbook-config.h> + static void action_address_book_copy_cb (GtkAction *action, EBookShellView *book_shell_view) @@ -101,6 +104,19 @@ action_address_book_move_cb (GtkAction *action, } static void +action_address_book_new_cb (GtkAction *action, + EBookShellView *book_shell_view) +{ + EShellView *shell_view; + EShellWindow *shell_window; + + shell_view = E_SHELL_VIEW (book_shell_view); + shell_window = e_shell_view_get_window (shell_view); + + addressbook_config_create_new_source (GTK_WIDGET (shell_window)); +} + +static void action_address_book_properties_cb (GtkAction *action, EBookShellView *book_shell_view) { @@ -127,7 +143,7 @@ action_address_book_properties_cb (GtkAction *action, GtkWidget *editor; editor = addressbook_config_edit_source ( - GTK_WINDOW (shell_window), source); + GTK_WIDGET (shell_window), source); closure = g_new (EditorUidClosure, 1); closure->editor = editor; @@ -342,19 +358,26 @@ static GtkActionEntry contact_entries[] = { N_("Move the contacts of the selected address book to another"), G_CALLBACK (action_address_book_move_cb) }, + { "address-book-new", + "address-book-new", + N_("_New Address Book"), + NULL, + N_("Create a new address book"), + G_CALLBACK (action_address_book_new_cb) }, + { "address-book-properties", GTK_STOCK_PROPERTIES, N_("Address _Book Properties"), NULL, - N_("Change the properties of the selected address book"), + N_("Show properties of the selected address book"), G_CALLBACK (action_address_book_properties_cb) }, { "address-book-save-as", GTK_STOCK_SAVE_AS, - N_("S_ave Address Book as VCard"), + N_("S_ave Address Book as vCard"), NULL, - N_("Save the contacts of the selected address book as a VCard"), - G_CALLBACK (action_address_book_save_as) }, + N_("Save the contacts of the selected address book as a vCard"), + G_CALLBACK (action_address_book_save_as_cb) }, { "address-book-stop", GTK_STOCK_STOP, @@ -435,9 +458,9 @@ static GtkActionEntry contact_entries[] = { { "contact-save-as", GTK_STOCK_SAVE_AS, - N_("Save as VCard..."), + N_("Save as vCard..."), NULL, - N_("Save selected contacts as a VCard"), + N_("Save selected contacts as a vCard"), G_CALLBACK (action_contact_save_as_cb) }, { "contact-select-all", @@ -452,7 +475,39 @@ static GtkActionEntry contact_entries[] = { N_("_Send Message to Contact..."), NULL, N_("Send a message to the selected contacts"), - G_CALLBACK (action_contact_send_message_cb) } + G_CALLBACK (action_contact_send_message_cb) }, + + /*** Menus ***/ + + { "actions-menu", + NULL, + N_("_Actions"), + NULL, + NULL, + NULL }, + + /*** Address Book Popup Actions ***/ + + { "address-book-popup-delete", + GTK_STOCK_DELETE, + NULL, + NULL, + N_("Delete this address book"), + G_CALLBACK (action_address_book_delete_cb) }, + + { "address-book-popup-properties", + GTK_STOCK_PROPERTIES, + NULL, + NULL, + N_("Show properties of this address book"), + G_CALLBACK (action_address_book_properties_cb) }, + + { "address-book-popup-save-as", + GTK_STOCK_SAVE_AS, + N_("_Save as vCard..."), + NULL, + N_("Save the contents of this address book as a vCard"), + G_CALLBACK (action_address_book_save_as_cb) } }; static GtkToggleActionEntry contact_toggle_entries[] = { @@ -473,6 +528,7 @@ e_book_shell_view_actions_init (EBookShellView *book_shell_view) EShellWindow *shell_window; GtkActionGroup *action_group; GtkUIManager *manager; + GtkAction *action; const gchar *domain; shell_view = E_SHELL_VIEW (book_shell_view); @@ -491,4 +547,9 @@ e_book_shell_view_actions_init (EBookShellView *book_shell_view) action_group, contact_toggle_entries, G_N_ELEMENTS (contact_toggle_entries), book_shell_view); gtk_ui_manager_insert_action_group (manager, action_group, 0); + + /* Fine tuning. */ + + action = ACTION (CONTACT_DELETE); + g_object_set (action, "short-label", _("Delete"), NULL); } diff --git a/addressbook/gui/component/e-book-shell-view-private.c b/addressbook/gui/component/e-book-shell-view-private.c index cfc12662f0..0bf0832c58 100644 --- a/addressbook/gui/component/e-book-shell-view-private.c +++ b/addressbook/gui/component/e-book-shell-view-private.c @@ -20,12 +20,70 @@ #include "e-book-shell-view-private.h" +static gboolean +book_shell_view_show_popup_menu (GdkEventButton *event, + EShellView *shell_view) +{ + GtkWidget *menu; + EShellWindow *shell_window; + const gchar *widget_path; + + widget_path = "/address-book-popup"; + shell_window = e_shell_view_get_window (shell_view); + menu = e_shell_window_get_managed_widget (shell_window, widget_path); + + if (event != NULL) + gtk_menu_popup ( + GTK_MENU (menu), NULL, NULL, NULL, NULL, + event->button, event->time); + else + gtk_menu_popup ( + GTK_MENU (menu), NULL, NULL, NULL, NULL, + 0, gtk_get_current_event_time ()); + + return TRUE; +} + +static gboolean +book_shell_view_selector_button_press_event_cb (EShellView *shell_view, + GdkEventButton *event) +{ + if (event->button == 3 && event->type == GDK_BUTTON_PRESS) + return book_shell_view_show_popup_menu (event, shell_view); + + return FALSE; +} + +static gboolean +book_shell_view_selector_popup_menu_cb (EShellView *shell_view) +{ + return book_shell_view_show_popup_menu (NULL, shell_view); +} + +static gboolean +book_shell_view_selector_key_press_event_cb (EShellView *shell_view, + GdkEventKey *event) +{ + EShellWindow *shell_window; + + /* Needed for the ACTION() macro. */ + shell_window = e_shell_view_get_window (shell_view); + + if (event->keyval == GDK_Delete) { + gtk_action_activate (ACTION (ADDRESS_BOOK_DELETE)); + return TRUE; + } + + return FALSE; +} + void e_book_shell_view_private_init (EBookShellView *book_shell_view) { EBookShellViewPrivate *priv = book_shell_view->priv; GHashTable *uid_to_view; GHashTable *uid_to_editor; + GtkWidget *container; GtkWidget *widget; uid_to_view = g_hash_table_new_full ( @@ -39,8 +97,11 @@ e_book_shell_view_private_init (EBookShellView *book_shell_view) (GDestroyNotify) g_free); priv->contact_actions = gtk_action_group_new ("contacts"); + priv->activity_handler = e_activity_handler_new (); + priv->uid_to_view = uid_to_view; + priv->uid_to_editor = uid_to_editor; - e_book_shell_view_actions_init (book_shell_view); + e_book_get_addressbooks (&priv->source_list, NULL); widget = gtk_notebook_new (); gtk_notebook_set_show_tabs (GTK_NOTEBOOK (widget), FALSE); @@ -48,7 +109,43 @@ e_book_shell_view_private_init (EBookShellView *book_shell_view) priv->notebook = g_object_ref_sink (widget); gtk_widget_show (widget); - e_book_get_addressbooks (&priv->source_list, NULL); + widget = e_task_bar_new (); + e_activity_handler_attach_task_bar ( + priv->activity_handler, E_TASK_BAR (widget)); + priv->task_bar = g_object_ref (widget); + gtk_widget_show (widget); + + widget = gtk_scrolled_window_new (NULL, NULL); + gtk_scrolled_window_set_policy ( + GTK_SCROLLED_WINDOW (widget), + GTK_POLICY_AUTOMATIC, GTK_POLICY_AUTOMATIC); + gtk_scrolled_window_set_shadow_type ( + GTK_SCROLLED_WINDOW (widget), GTK_SHADOW_IN); + priv->scrolled_window = g_object_ref_sink (widget); + gtk_widget_show (widget); + + container = widget; + + widget = e_source_selector_new (priv->source_list); + e_source_selector_show_selection (E_SOURCE_SELECTOR (widget), FALSE); + gtk_container_add (GTK_CONTAINER (container), widget); + priv->selector = g_object_ref (widget); + gtk_widget_show (widget); + + g_signal_connect_swapped ( + widget, "button-press-event", + G_CALLBACK (book_shell_view_selector_button_press_event_cb), + book_shell_view); + + g_signal_connect_swapped ( + widget, "key-press-event", + G_CALLBACK (book_shell_view_selector_key_press_event_cb), + book_shell_view); + + g_signal_connect_swapped ( + widget, "popup-menu", + G_CALLBACK (book_shell_view_selector_popup_menu_cb), + book_shell_view); } void @@ -56,11 +153,20 @@ e_book_shell_view_private_dispose (EBookShellView *book_shell_view) { EBookShellViewPrivate *priv = book_shell_view->priv; + DISPOSE (priv->contact_actions); + DISPOSE (priv->notebook); - DISPOSE (priv->source_list); + DISPOSE (priv->scrolled_window); + DISPOSE (priv->selector); + DISPOSE (priv->task_bar); + + DISPOSE (priv->activity_handler); g_hash_table_remove_all (priv->uid_to_view); g_hash_table_remove_all (priv->uid_to_editor); + + DISPOSE (priv->book); + DISPOSE (priv->source_list); } void @@ -70,6 +176,8 @@ e_book_shell_view_private_finalize (EBookShellView *book_shell_view) g_hash_table_destroy (priv->uid_to_view); g_hash_table_destroy (priv->uid_to_editor); + + g_free (priv->password); } EABView * @@ -87,3 +195,13 @@ e_book_shell_view_get_current_view (EBookShellView *book_shell_view) return EAB_VIEW (widget); } + +void +e_book_shell_view_editor_weak_notify (EditorUidClosure *closure, + GObject *where_the_object_was) +{ + GHashTable *hash_table; + + hash_table = closure->view->priv->uid_to_editor; + g_hash_table_remove (hash_table, closure->uid); +} diff --git a/addressbook/gui/component/e-book-shell-view-private.h b/addressbook/gui/component/e-book-shell-view-private.h index 025efd26fc..426b8e9d11 100644 --- a/addressbook/gui/component/e-book-shell-view-private.h +++ b/addressbook/gui/component/e-book-shell-view-private.h @@ -23,6 +23,16 @@ #include "e-book-shell-view.h" +#include <string.h> +#include <glib/gi18n.h> +#include <gdk/gdkkeysyms.h> +#include <libebook/e-book.h> +#include <libedataserverui/e-source-selector.h> + +#include <eab-menu.h> +#include <e-activity-handler.h> +#include <e-addressbook-view.h> + #include <e-book-shell-view-actions.h> #define E_BOOK_SHELL_VIEW_GET_PRIVATE(obj) \ @@ -60,15 +70,12 @@ struct _EBookShellViewPrivate { /*** Other Stuff ***/ GtkWidget *notebook; - BonoboControl *folder_view_control; + GtkWidget *scrolled_window; + GtkWidget *selector; + GtkWidget *task_bar; - GtkWidget *statusbar_widget; EActivityHandler *activity_handler; - GtkWidget *info_widget; - GtkWidget *sidebar_widget; - GtkWidget *selector; - GHashTable *uid_to_view; GHashTable *uid_to_editor; @@ -76,7 +83,6 @@ struct _EBookShellViewPrivate { guint activity_id; ESourceList *source_list; gchar *password; - EUserCreatableItemsHandler *creatable_items_handler; EABMenu *menu; }; @@ -94,6 +100,9 @@ void e_book_shell_view_actions_init (EBookShellView *book_shell_view); EABView * e_book_shell_view_get_current_view (EBookShellView *book_shell_view); +void e_book_shell_view_editor_weak_notify + (EditorUidClosure *closure, + GObject *where_the_object_was); G_END_DECLS diff --git a/addressbook/gui/component/e-book-shell-view.c b/addressbook/gui/component/e-book-shell-view.c index 9a55cb0667..13098ab84a 100644 --- a/addressbook/gui/component/e-book-shell-view.c +++ b/addressbook/gui/component/e-book-shell-view.c @@ -23,6 +23,48 @@ GType e_book_shell_view_type = 0; static gpointer parent_class; +static ESource * +book_shell_view_get_primary_source (EBookShellView *book_shell_view) +{ + GConfClient *client; + ESourceList *source_list; + ESource *source = NULL; + const gchar *key; + gchar *uid; + + source_list = book_shell_view->priv->source_list; + + client = gconf_client_get_default (); + key = "/apps/evolution/addressbook/display/primary_addressbook"; + uid = gconf_client_get_string (client, key, NULL); + g_object_unref (client); + + if (uid != NULL) { + source = e_source_list_peek_source_by_uid (source_list, uid); + g_free (uid); + } else { + GSList *groups; + + /* Dig up the first source in the source list. + * XXX libedataserver should provide API for this. */ + groups = e_source_list_peek_groups (source_list); + while (groups != NULL) { + ESourceGroup *source_group = groups->data; + GSList *sources; + + sources = e_source_group_peek_sources (source_group); + if (sources != NULL) { + source = sources->data; + break; + } + + groups = g_slist_next (groups); + } + } + + return source; +} + static void book_shell_view_update_actions (EBookShellView *book_shell_view, EABView *view) @@ -111,16 +153,6 @@ book_shell_view_update_actions (EBookShellView *book_shell_view, } static void -book_shell_view_editor_weak_notify (EditorUidClosure *closure, - GObject *where_the_object_was) -{ - GHashTable *hash_table; - - hash_table = closure->view->priv->uid_to_editor; - g_hash_table_remove (hash_table, closure->uid); -} - -static void book_shell_view_source_list_changed_cb (EBookShellView *book_shell_view, ESourceList *source_list) { @@ -162,7 +194,7 @@ book_shell_view_source_list_changed_cb (EBookShellView *book_shell_view, closure = g_hash_table_lookup (priv->uid_to_editor, uid); g_object_weak_unref ( G_OBJECT (closure->editor), (GWeakNotify) - book_shell_view_editor_weak_notify, closure); + e_book_shell_view_editor_weak_notify, closure); gtk_widget_destroy (closure->editor); g_hash_table_remove (priv->uid_to_editor, uid); } @@ -196,19 +228,56 @@ book_shell_view_finalize (GObject *object) G_OBJECT_CLASS (parent_class)->finalize (object); } +static void +book_shell_view_constructed (GObject *object) +{ + e_book_shell_view_actions_init (E_BOOK_SHELL_VIEW (object)); + + /* Chain up to parent's constructed() method. */ + G_OBJECT_CLASS (parent_class)->constructed (object); +} + static GtkWidget * book_shell_view_get_content_widget (EShellView *shell_view) { + EBookShellViewPrivate *priv; + + priv = E_BOOK_SHELL_VIEW_GET_PRIVATE (shell_view); + + return priv->notebook; } static GtkWidget * book_shell_view_get_sidebar_widget (EShellView *shell_view) { + EBookShellViewPrivate *priv; + + priv = E_BOOK_SHELL_VIEW_GET_PRIVATE (shell_view); + + return priv->scrolled_window; } static GtkWidget * book_shell_view_get_status_widget (EShellView *shell_view) { + EBookShellViewPrivate *priv; + + priv = E_BOOK_SHELL_VIEW_GET_PRIVATE (shell_view); + + return priv->task_bar; +} + +static void +book_shell_view_changed (EShellView *shell_view, + gboolean visible) +{ + EBookShellViewPrivate *priv; + GtkActionGroup *action_group; + + priv = E_BOOK_SHELL_VIEW_GET_PRIVATE (shell_view); + + action_group = priv->contact_actions; + gtk_action_group_set_visible (action_group, visible); } static void @@ -218,17 +287,19 @@ book_shell_view_class_init (EBookShellViewClass *class, GObjectClass *object_class; EShellViewClass *shell_view_class; - parent_class = g_type_class_peek-parent (class); + parent_class = g_type_class_peek_parent (class); g_type_class_add_private (class, sizeof (EBookShellViewPrivate)); object_class = G_OBJECT_CLASS (class); object_class->dispose = book_shell_view_dispose; object_class->finalize = book_shell_view_finalize; + object_class->constructed = book_shell_view_constructed; shell_view_class = E_SHELL_VIEW_CLASS (class); shell_view_class->label = N_("Contacts"); shell_view_class->icon_name = "x-office-address-book"; shell_view_class->type_module = type_module; + shell_view_class->changed = book_shell_view_changed; shell_view_class->get_content_widget = book_shell_view_get_content_widget; @@ -241,15 +312,23 @@ book_shell_view_class_init (EBookShellViewClass *class, static void book_shell_view_init (EBookShellView *book_shell_view) { + ESourceSelector *selector; + ESource *source; + book_shell_view->priv = E_BOOK_SHELL_VIEW_GET_PRIVATE (book_shell_view); e_book_shell_view_private_init (book_shell_view); g_signal_connect_swapped ( - priv->source_list, "changed", + book_shell_view->priv->source_list, "changed", G_CALLBACK (book_shell_view_source_list_changed_cb), book_shell_view); + + selector = E_SOURCE_SELECTOR (book_shell_view->priv->selector); + source = book_shell_view_get_primary_source (book_shell_view); + if (source != NULL) + e_source_selector_set_primary_selection (selector, source); } GType diff --git a/addressbook/gui/contact-editor/e-contact-editor.h b/addressbook/gui/contact-editor/e-contact-editor.h index 27bdefedb5..c6dd17a6ac 100644 --- a/addressbook/gui/contact-editor/e-contact-editor.h +++ b/addressbook/gui/contact-editor/e-contact-editor.h @@ -22,7 +22,6 @@ #include <libgnomeui/gnome-app.h> #include <libgnomeui/gnome-app-helper.h> -#include <bonobo/bonobo-ui-component.h> #include <glade/glade.h> #include "addressbook/gui/contact-editor/eab-editor.h" @@ -62,9 +61,6 @@ struct _EContactEditor EBook *target_book; EContact *contact; - /* UI handler */ - BonoboUIComponent *uic; - GladeXML *gui; GtkWidget *app; diff --git a/addressbook/gui/contact-editor/eab-editor.h b/addressbook/gui/contact-editor/eab-editor.h index 7736403546..aad4e9bf54 100644 --- a/addressbook/gui/contact-editor/eab-editor.h +++ b/addressbook/gui/contact-editor/eab-editor.h @@ -22,7 +22,6 @@ #include <libgnomeui/gnome-app.h> #include <libgnomeui/gnome-app-helper.h> -#include <bonobo/bonobo-ui-component.h> #include <glade/glade.h> #include <libebook/e-book.h> diff --git a/addressbook/gui/widgets/Makefile.am b/addressbook/gui/widgets/Makefile.am index 88c7f07011..99a875d278 100644 --- a/addressbook/gui/widgets/Makefile.am +++ b/addressbook/gui/widgets/Makefile.am @@ -61,6 +61,9 @@ libeabwidgets_la_SOURCES = \ gal-view-factory-minicard.c \ gal-view-factory-minicard.h +libeabwidgets_la_LIBADD = \ + $(top_builddir)/widgets/misc/libemiscwidgets.la + MARSHAL_GENERATED = eab-marshal.c eab-marshal.h @EVO_MARSHAL_RULE@ diff --git a/addressbook/gui/widgets/eab-gui-util.c b/addressbook/gui/widgets/eab-gui-util.c index 42ce9cd8f2..651a44bfa7 100644 --- a/addressbook/gui/widgets/eab-gui-util.c +++ b/addressbook/gui/widgets/eab-gui-util.c @@ -48,7 +48,6 @@ #include "addressbook/gui/contact-editor/eab-editor.h" #include "addressbook/gui/contact-editor/e-contact-editor.h" #include "addressbook/gui/contact-list-editor/e-contact-list-editor.h" -#include "addressbook/gui/component/addressbook-component.h" #include "addressbook/gui/component/addressbook.h" /* the NULL's in this table correspond to the status codes @@ -781,6 +780,7 @@ typedef struct { static void eab_send_to_contact_and_email_num_list (GList *contact_list) { +#if 0 /* NOT READY FOR COMPOSER YET */ EMsgComposer *composer; EComposerHeaderTable *table; GPtrArray *to_array; @@ -844,6 +844,7 @@ eab_send_to_contact_and_email_num_list (GList *contact_list) e_destination_freev (convert.destinations); gtk_widget_show (GTK_WIDGET (composer)); +#endif } static const char * @@ -868,6 +869,7 @@ get_email (EContact *contact, EContactField field_id, gchar **to_free) static void eab_send_contact_list_as_attachment (GList *contacts) { +#if 0 /* NOT READY FOR COMPOSER YET */ EMsgComposer *composer; EComposerHeaderTable *table; CamelMimePart *attachment; @@ -943,6 +945,7 @@ eab_send_contact_list_as_attachment (GList *contacts) } gtk_widget_show (GTK_WIDGET (composer)); +#endif } void diff --git a/addressbook/gui/widgets/eab-popup-control.h b/addressbook/gui/widgets/eab-popup-control.h index 75fff81471..09ae811e1d 100644 --- a/addressbook/gui/widgets/eab-popup-control.h +++ b/addressbook/gui/widgets/eab-popup-control.h @@ -28,6 +28,7 @@ #ifndef __EAB_POPUP_CONTROL_H__ #define __EAB_POPUP_CONTROL_H__ +#include <bonobo/bonobo-control.h> #include <bonobo/bonobo-event-source.h> #include <libebook/e-book.h> #include <libebook/e-contact.h> |