diff options
-rw-r--r-- | calendar/ChangeLog | 23 | ||||
-rw-r--r-- | calendar/cal-client/cal-client.c | 102 | ||||
-rw-r--r-- | calendar/cal-client/cal-client.h | 9 | ||||
-rw-r--r-- | calendar/gui/dialogs/Makefile.am | 3 | ||||
-rw-r--r-- | calendar/gui/dialogs/e-timezone-dialog.c | 526 | ||||
-rw-r--r-- | calendar/gui/dialogs/e-timezone-dialog.glade | 264 | ||||
-rw-r--r-- | calendar/gui/dialogs/e-timezone-dialog.h | 72 | ||||
-rw-r--r-- | calendar/idl/evolution-calendar.idl | 16 | ||||
-rw-r--r-- | calendar/pcs/cal.c | 42 |
9 files changed, 1057 insertions, 0 deletions
diff --git a/calendar/ChangeLog b/calendar/ChangeLog index 67cbb6f918..f25155b5d0 100644 --- a/calendar/ChangeLog +++ b/calendar/ChangeLog @@ -1,3 +1,26 @@ +2001-06-14 Damon Chaplin <damon@ximian.com> + + * gui/dialogs/e-timezone-dialog.[hc]: + * gui/dialogs/e-timezone-dialog.glade: new dialog for setting the + time zone. + + * gui/dialogs/Makefile.am: added timezone dialog files. + + * idl/evolution-calendar.idl: added CalTimezoneInfo struct and seq, + and getBuiltinTimezoneInfo method. + + * pcs/cal.c (impl_Cal_get_builtin_timezone_info): implemented method. + (cal_class_init): added method to epv. + + * cal-client/cal-client.c (struct CalClientPrivate): added + timezone_info array to contain cached info on builtin timezone city + names and coordinates. + (cal_client_get_builtin_timezone_info): new function to get the info + about builtin timezones. + + * cal-client/cal-client.h: added CalTimezoneInfo struct, to contain + the city names and coords of the builtin timezones. + 2001-06-13 JP Rosevear <jpr@ximian.com> * gui/dialogs/comp-editor-util.c (comp_editor_date_label): remove diff --git a/calendar/cal-client/cal-client.c b/calendar/cal-client/cal-client.c index cd8c8713d6..d761370c74 100644 --- a/calendar/cal-client/cal-client.c +++ b/calendar/cal-client/cal-client.c @@ -50,6 +50,11 @@ struct _CalClientPrivate { /* The calendar client interface object we are contacting */ GNOME_Evolution_Calendar_Cal cal; + + /* An array of CalTimezone structs containing information on builtin + timezones. We cache this so we only request it once from the + server. */ + GArray *timezone_info; }; @@ -66,6 +71,8 @@ static void cal_client_class_init (CalClientClass *class); static void cal_client_init (CalClient *client); static void cal_client_destroy (GtkObject *object); +static void cal_client_free_builtin_timezone_info (GArray *zones); + static guint cal_client_signals[LAST_SIGNAL]; static GtkObjectClass *parent_class; @@ -155,6 +162,7 @@ cal_client_init (CalClient *client) priv->load_state = CAL_CLIENT_LOAD_NOT_LOADED; priv->uri = NULL; priv->factory = CORBA_OBJECT_NIL; + priv->timezone_info = NULL; } /* Gets rid of the factory that a client knows about */ @@ -269,6 +277,11 @@ cal_client_destroy (GtkObject *object) priv->uri = NULL; } + if (priv->timezone_info) { + cal_client_free_builtin_timezone_info (priv->timezone_info); + priv->timezone_info = NULL; + } + g_free (priv); client->priv = NULL; @@ -1506,6 +1519,95 @@ cal_client_remove_object (CalClient *client, const char *uid) return retval; } +/* Builds a list of CalComponentAlarms structures */ +static GArray * +build_timezone_info_array (GNOME_Evolution_Calendar_CalTimezoneInfoSeq *seq) +{ + GArray *zones; + CalTimezoneInfo zone; + int i; + + zones = g_array_new (FALSE, FALSE, sizeof (CalTimezoneInfo)); + + for (i = 0; i < seq->_length; i++) { + GNOME_Evolution_Calendar_CalTimezoneInfo *tzinfo; + + tzinfo = seq->_buffer + i; + + zone.location = g_strdup (tzinfo->location); + zone.latitude = tzinfo->latitude; + zone.longitude = tzinfo->longitude; + + g_array_append_val (zones, zone); + } + + return zones; +} + +/** + * cal_client_get_builtin_timezone_info: + * @client: A calendar client. + * + * Returns information on the builtin timezones, i.e. their names and + * locations. This is so we can use the map to select a timezone. + * + * Return value: An array of #CalTimezoneInfo structures. The caller should not + * change or free this array. The CalClient will free it when it is destroyed. + **/ +GArray * +cal_client_get_builtin_timezone_info (CalClient *client) +{ + CalClientPrivate *priv; + CORBA_Environment ev; + GNOME_Evolution_Calendar_CalTimezoneInfoSeq *seq; + + g_return_val_if_fail (client != NULL, NULL); + g_return_val_if_fail (IS_CAL_CLIENT (client), NULL); + + priv = client->priv; + + /* If we have already got this data from the server just return it. */ + if (priv->timezone_info) + return priv->timezone_info; + + CORBA_exception_init (&ev); + + seq = GNOME_Evolution_Calendar_Cal_getBuiltinTimezoneInfo (priv->cal, + &ev); + if (ev._major != CORBA_NO_EXCEPTION) { + g_message ("cal_client_get_builtin_timezone_info(): could not get the builtin timezone info"); + CORBA_exception_free (&ev); + return NULL; + } + CORBA_exception_free (&ev); + + priv->timezone_info = build_timezone_info_array (seq); + CORBA_free (seq); + + return priv->timezone_info; +} + +/** + * cal_client_free_builtin_timezone_info: + * @zones: An array of timezone info returned from + * cal_client_get_builtin_timezone_info(). + * + * Frees the builtin timezone information structures. + **/ +static void +cal_client_free_builtin_timezone_info (GArray *zones) +{ + CalTimezoneInfo *zone; + int i; + + for (i = 0; i < zones->len; i++) { + zone = &g_array_index (zones, CalTimezoneInfo, i); + g_free (zone->location); + } + + g_array_free (zones, TRUE); +} + /** * cal_client_get_query: * @client: A calendar client. diff --git a/calendar/cal-client/cal-client.h b/calendar/cal-client/cal-client.h index 1f0211ef32..6d5891f7e1 100644 --- a/calendar/cal-client/cal-client.h +++ b/calendar/cal-client/cal-client.h @@ -65,6 +65,13 @@ typedef enum { CAL_CLIENT_LOAD_LOADED } CalClientLoadState; +/* A timezone name and its coordinates in the world. */ +typedef struct _CalTimezoneInfo CalTimezoneInfo; +struct _CalTimezoneInfo { + char *location; + double latitude; + double longitude; +}; struct _CalClient { GtkObject object; @@ -126,6 +133,8 @@ gboolean cal_client_remove_object (CalClient *client, const char *uid); CalQuery *cal_client_get_query (CalClient *client, const char *sexp); +GArray *cal_client_get_builtin_timezone_info (CalClient *client); + END_GNOME_DECLS diff --git a/calendar/gui/dialogs/Makefile.am b/calendar/gui/dialogs/Makefile.am index 74c65d72ab..de97ea2d45 100644 --- a/calendar/gui/dialogs/Makefile.am +++ b/calendar/gui/dialogs/Makefile.am @@ -32,6 +32,8 @@ libcal_dialogs_a_SOURCES = \ comp-editor-util.h \ delete-comp.c \ delete-comp.h \ + e-timezone-dialog.c \ + e-timezone-dialog.h \ event-editor.c \ event-editor.h \ event-page.c \ @@ -51,6 +53,7 @@ glade_DATA = \ alarm-notify.glade \ alarm-page.glade \ cal-prefs-dialog.glade \ + e-timezone-dialog.glade \ event-page.glade \ recurrence-page.glade \ task-details-page.glade \ diff --git a/calendar/gui/dialogs/e-timezone-dialog.c b/calendar/gui/dialogs/e-timezone-dialog.c new file mode 100644 index 0000000000..7e9fce6cb8 --- /dev/null +++ b/calendar/gui/dialogs/e-timezone-dialog.c @@ -0,0 +1,526 @@ +/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */ +/* Evolution calendar - Timezone selector dialog + * + * Copyright (C) 2001 Ximian, Inc. + * + * Authors: Damon Chaplin <damon@ximian.com> + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. + */ + +#include <config.h> +#include <gtk/gtksignal.h> +#include <gtk/gtkcombo.h> +#include <gtk/gtkentry.h> +#include <gtk/gtklabel.h> +#include <gnome.h> +#include <glade/glade.h> +#include <widgets/misc/e-map.h> +#include "e-timezone-dialog.h" + +#define E_TIMEZONE_DIALOG_MAP_POINT_NORMAL_RGBA 0xc070a0ff +#define E_TIMEZONE_DIALOG_MAP_POINT_HOVER_RGBA 0xffff60ff +#define E_TIMEZONE_DIALOG_MAP_POINT_SELECTED_1_RGBA 0xff60e0ff +#define E_TIMEZONE_DIALOG_MAP_POINT_SELECTED_2_RGBA 0x000000ff + +struct _ETimezoneDialogPrivate { + /* Glade XML data */ + GladeXML *xml; + + /* Client to use */ + CalClient *client; + + GArray *zones; + + EMapPoint *point_selected; + EMapPoint *point_hover; + + EMap *map; + + /* The timeout used to flash the nearest point. */ + guint timeout_id; + + /* Widgets from the Glade file */ + GtkWidget *app; + GtkWidget *map_window; + GtkWidget *timezone_preview; + GtkWidget *timezone_combo; +}; + + +static void e_timezone_dialog_class_init (ETimezoneDialogClass *class); +static void e_timezone_dialog_init (ETimezoneDialog *etd); +static void e_timezone_dialog_destroy (GtkObject *object); + +static gboolean get_widgets (ETimezoneDialog *etd); +static gboolean on_map_timeout (gpointer data); +static gboolean on_map_motion (GtkWidget *widget, + GdkEventMotion *event, + gpointer data); +static gboolean on_map_visibility_changed (GtkWidget *w, + GdkEventVisibility *event, + gpointer data); +static gboolean on_map_button_pressed (GtkWidget *w, + GdkEventButton *event, + gpointer data); + +static char* get_zone_from_point (ETimezoneDialog *etd, + EMapPoint *point); + +static GtkObjectClass *parent_class; + + +GtkType +e_timezone_dialog_get_type (void) +{ + static GtkType e_timezone_dialog_type = 0; + + if (!e_timezone_dialog_type) { + static const GtkTypeInfo e_timezone_dialog_info = { + "ETimezoneDialog", + sizeof (ETimezoneDialog), + sizeof (ETimezoneDialogClass), + (GtkClassInitFunc) e_timezone_dialog_class_init, + (GtkObjectInitFunc) e_timezone_dialog_init, + NULL, /* reserved_1 */ + NULL, /* reserved_2 */ + (GtkClassInitFunc) NULL + }; + + e_timezone_dialog_type = gtk_type_unique (GTK_TYPE_OBJECT, + &e_timezone_dialog_info); + } + + return e_timezone_dialog_type; +} + +/* Class initialization function for the event editor */ +static void +e_timezone_dialog_class_init (ETimezoneDialogClass *class) +{ + GtkObjectClass *object_class; + + object_class = (GtkObjectClass *) class; + + parent_class = gtk_type_class (GTK_TYPE_OBJECT); + + object_class->destroy = e_timezone_dialog_destroy; +} + +/* Object initialization function for the event editor */ +static void +e_timezone_dialog_init (ETimezoneDialog *etd) +{ + ETimezoneDialogPrivate *priv; + + priv = g_new0 (ETimezoneDialogPrivate, 1); + etd->priv = priv; + + priv->point_selected = NULL; + priv->point_hover = NULL; + priv->timeout_id = 0; +} + +/* Destroy handler for the event editor */ +static void +e_timezone_dialog_destroy (GtkObject *object) +{ + ETimezoneDialog *etd; + ETimezoneDialogPrivate *priv; + + g_return_if_fail (object != NULL); + g_return_if_fail (E_IS_TIMEZONE_DIALOG (object)); + + etd = E_TIMEZONE_DIALOG (object); + priv = etd->priv; + + if (priv->timeout_id) { + g_source_remove (priv->timeout_id); + priv->timeout_id = 0; + } + + if (priv->client) { + gtk_signal_disconnect_by_data (GTK_OBJECT (priv->client), etd); + gtk_object_unref (GTK_OBJECT (priv->client)); + priv->client = NULL; + } + + if (priv->xml) { + gtk_object_unref (GTK_OBJECT (priv->xml)); + priv->xml = NULL; + } + + g_free (priv); + etd->priv = NULL; + + if (GTK_OBJECT_CLASS (parent_class)->destroy) + (* GTK_OBJECT_CLASS (parent_class)->destroy) (object); +} + + +ETimezoneDialog * +e_timezone_dialog_construct (ETimezoneDialog *etd) +{ + ETimezoneDialogPrivate *priv; + GtkWidget *map; + + g_return_val_if_fail (etd != NULL, NULL); + g_return_val_if_fail (E_IS_TIMEZONE_DIALOG (etd), NULL); + + priv = etd->priv; + + /* Load the content widgets */ + + priv->xml = glade_xml_new (EVOLUTION_GLADEDIR "/e-timezone-dialog.glade", + NULL); + if (!priv->xml) { + g_message ("e_timezone_dialog_construct(): Could not load the Glade XML file!"); + goto error; + } + + if (!get_widgets (etd)) { + g_message ("e_timezone_dialog_construct(): Could not find all widgets in the XML file!"); + goto error; + } + + map = GTK_WIDGET (e_map_new ()); + priv->map = E_MAP (map); + gtk_widget_set_events (map, gtk_widget_get_events (map) + | GDK_VISIBILITY_NOTIFY_MASK); + + gtk_entry_set_editable (GTK_ENTRY (GTK_COMBO (priv->timezone_combo)->entry), FALSE); + + gtk_container_add (GTK_CONTAINER (priv->map_window), map); + gtk_widget_show (map); + + gtk_signal_connect (GTK_OBJECT (map), "motion-notify-event", + GTK_SIGNAL_FUNC (on_map_motion), etd); + gtk_signal_connect (GTK_OBJECT (map), "visibility-notify-event", + GTK_SIGNAL_FUNC (on_map_visibility_changed), etd); + gtk_signal_connect (GTK_OBJECT (map), "button-press-event", + GTK_SIGNAL_FUNC (on_map_button_pressed), etd); + + return etd; + + error: + + gtk_object_unref (GTK_OBJECT (etd)); + return NULL; +} + +/* Gets the widgets from the XML file and returns if they are all available. + * For the widgets whose values can be simply set with e-dialog-utils, it does + * that as well. + */ +static gboolean +get_widgets (ETimezoneDialog *etd) +{ + ETimezoneDialogPrivate *priv; + + priv = etd->priv; + +#define GW(name) glade_xml_get_widget (priv->xml, name) + + priv->app = GW ("timezone-dialog"); + priv->map_window = GW ("map-window"); + priv->timezone_combo = GW ("timezone-combo"); + priv->timezone_preview = GW ("timezone-preview"); + + return (priv->app + && priv->map_window + && priv->timezone_combo + && priv->timezone_preview); +} + + +/** + * e_timezone_dialog_new: + * + * Creates a new event editor dialog. + * + * Return value: A newly-created event editor dialog, or NULL if the event + * editor could not be created. + **/ +ETimezoneDialog * +e_timezone_dialog_new (void) +{ + ETimezoneDialog *etd; + + etd = E_TIMEZONE_DIALOG (gtk_type_new (E_TYPE_TIMEZONE_DIALOG)); + return e_timezone_dialog_construct (E_TIMEZONE_DIALOG (etd)); +} + + + +/* This flashes the currently selected timezone in the map. */ +static gboolean +on_map_timeout (gpointer data) +{ + ETimezoneDialog *etd; + ETimezoneDialogPrivate *priv; + + etd = E_TIMEZONE_DIALOG (data); + priv = etd->priv; + + if (!priv->point_selected) + return TRUE; + + if (e_map_point_get_color_rgba (priv->point_selected) + == E_TIMEZONE_DIALOG_MAP_POINT_SELECTED_1_RGBA) + e_map_point_set_color_rgba (priv->map, priv->point_selected, + E_TIMEZONE_DIALOG_MAP_POINT_SELECTED_2_RGBA); + else + e_map_point_set_color_rgba (priv->map, priv->point_selected, + E_TIMEZONE_DIALOG_MAP_POINT_SELECTED_1_RGBA); + + return TRUE; +} + + +static gboolean +on_map_motion (GtkWidget *widget, GdkEventMotion *event, gpointer data) +{ + ETimezoneDialog *etd; + ETimezoneDialogPrivate *priv; + double longitude, latitude; + char *old_zone, *new_zone; + + etd = E_TIMEZONE_DIALOG (data); + priv = etd->priv; + + e_map_window_to_world (priv->map, (double) event->x, (double) event->y, + &longitude, &latitude); + + if (priv->point_hover && priv->point_hover != priv->point_selected) + e_map_point_set_color_rgba (priv->map, priv->point_hover, + E_TIMEZONE_DIALOG_MAP_POINT_NORMAL_RGBA); + + priv->point_hover = e_map_get_closest_point (priv->map, longitude, + latitude, TRUE); + + if (priv->point_hover != priv->point_selected) + e_map_point_set_color_rgba (priv->map, priv->point_hover, + E_TIMEZONE_DIALOG_MAP_POINT_HOVER_RGBA); + + gtk_label_get (GTK_LABEL (priv->timezone_preview), &old_zone); + new_zone = get_zone_from_point (etd, priv->point_hover); + if (strcmp (old_zone, new_zone)) + gtk_label_set_text (GTK_LABEL (priv->timezone_preview), + new_zone); + + return TRUE; +} + + +static gboolean +on_map_visibility_changed (GtkWidget *w, GdkEventVisibility *event, + gpointer data) +{ + ETimezoneDialog *etd; + ETimezoneDialogPrivate *priv; + + etd = E_TIMEZONE_DIALOG (data); + priv = etd->priv; + + if (event->state != GDK_VISIBILITY_FULLY_OBSCURED) { + /* Map is visible, at least partly, so make sure we flash the + selected point. */ + if (!priv->timeout_id) + priv->timeout_id = gtk_timeout_add (100, on_map_timeout, etd); + } else { + /* Map is invisible, so don't waste resources on the timeout.*/ + if (priv->timeout_id) { + g_source_remove (priv->timeout_id); + priv->timeout_id = 0; + } + } + + return FALSE; +} + + +static gboolean +on_map_button_pressed (GtkWidget *w, GdkEventButton *event, gpointer data) +{ + ETimezoneDialog *etd; + ETimezoneDialogPrivate *priv; + double longitude, latitude; + + etd = E_TIMEZONE_DIALOG (data); + priv = etd->priv; + + e_map_window_to_world (priv->map, (double) event->x, (double) event->y, + &longitude, &latitude); + + if (event->button != 1) { + e_map_zoom_out (priv->map); + } else { + if (e_map_get_magnification (priv->map) <= 1.0) + e_map_zoom_to_location (priv->map, longitude, + latitude); + + if (priv->point_selected) + e_map_point_set_color_rgba (priv->map, + priv->point_selected, + E_TIMEZONE_DIALOG_MAP_POINT_NORMAL_RGBA); + priv->point_selected = priv->point_hover; + + gtk_entry_set_text (GTK_ENTRY (GTK_COMBO (priv->timezone_combo)->entry), + get_zone_from_point (etd, priv->point_selected)); + } + + return TRUE; +} + + +static char* +get_zone_from_point (ETimezoneDialog *etd, + EMapPoint *point) +{ + ETimezoneDialogPrivate *priv; + CalTimezoneInfo *zone; + double longitude, latitude; + int i; + + priv = etd->priv; + + if (point == NULL || priv->zones == NULL) + return ""; + + e_map_point_get_location (point, &longitude, &latitude); + + for (i = 0; i < priv->zones->len; i++) { + zone = &g_array_index (priv->zones, CalTimezoneInfo, i); + + if (zone->longitude - 0.005 <= longitude && + zone->longitude + 0.005 >= longitude && + zone->latitude - 0.005 <= latitude && + zone->latitude + 0.005 >= latitude) + { + return zone->location; + } + } + + g_assert_not_reached (); + + return NULL; +} + + +CalClient* +e_timezone_dialog_get_cal_client (ETimezoneDialog *etd) +{ + + return etd->priv->client; +} + + +void +e_timezone_dialog_set_cal_client (ETimezoneDialog *etd, + CalClient *client) +{ + ETimezoneDialogPrivate *priv; + CalTimezoneInfo *zone; + GList *tzlist = NULL; + char *current_zone; + int i; + + g_return_if_fail (etd != NULL); + g_return_if_fail (E_IS_TIMEZONE_DIALOG (etd)); + g_return_if_fail (IS_CAL_CLIENT (client)); + + priv = etd->priv; + + priv->zones = cal_client_get_builtin_timezone_info (client); + + if (!priv->zones) { + g_warning ("No timezone info found"); + return; + } + + /* Put the "None" and "UTC" entries at the top of the combo's list. */ + tzlist = g_list_prepend (tzlist, _("None")); + tzlist = g_list_prepend (tzlist, _("UTC")); + + current_zone = gtk_entry_get_text (GTK_ENTRY (GTK_COMBO (priv->timezone_combo)->entry)); + + for (i = 0; i < priv->zones->len; i++) { + zone = &g_array_index (priv->zones, CalTimezoneInfo, i); + if (!strcmp (current_zone, zone->location)) { + priv->point_selected = e_map_add_point (priv->map, + zone->location, + zone->longitude, + zone->latitude, + E_TIMEZONE_DIALOG_MAP_POINT_NORMAL_RGBA); + } else { + e_map_add_point (priv->map, zone->location, + zone->longitude, zone->latitude, + E_TIMEZONE_DIALOG_MAP_POINT_NORMAL_RGBA); + } + tzlist = g_list_prepend (tzlist, zone->location); + } + + tzlist = g_list_reverse (tzlist); + gtk_combo_set_popdown_strings (GTK_COMBO (priv->timezone_combo), + tzlist); + g_list_free (tzlist); + +} + + +char* +e_timezone_dialog_get_timezone (ETimezoneDialog *etd) +{ + ETimezoneDialogPrivate *priv; + + g_return_val_if_fail (etd != NULL, NULL); + g_return_val_if_fail (E_IS_TIMEZONE_DIALOG (etd), NULL); + + priv = etd->priv; + + return gtk_entry_get_text (GTK_ENTRY (GTK_COMBO (priv->timezone_combo)->entry)); +} + + +void +e_timezone_dialog_set_timezone (ETimezoneDialog *etd, + char *timezone) +{ + ETimezoneDialogPrivate *priv; + + g_return_if_fail (etd != NULL); + g_return_if_fail (E_IS_TIMEZONE_DIALOG (etd)); + + priv = etd->priv; + + gtk_entry_set_text (GTK_ENTRY (GTK_COMBO (priv->timezone_combo)->entry), + get_zone_from_point (etd, priv->point_selected)); + +} + + +GtkWidget* +e_timezone_dialog_get_toplevel (ETimezoneDialog *etd) +{ + ETimezoneDialogPrivate *priv; + + g_return_val_if_fail (etd != NULL, NULL); + g_return_val_if_fail (E_IS_TIMEZONE_DIALOG (etd), NULL); + + priv = etd->priv; + + return priv->app; +} + diff --git a/calendar/gui/dialogs/e-timezone-dialog.glade b/calendar/gui/dialogs/e-timezone-dialog.glade new file mode 100644 index 0000000000..2b2019dfc2 --- /dev/null +++ b/calendar/gui/dialogs/e-timezone-dialog.glade @@ -0,0 +1,264 @@ +<?xml version="1.0"?> +<GTK-Interface> + +<project> + <name>timezone-dialog</name> + <program_name>timezone-dialog</program_name> + <directory></directory> + <source_directory>src</source_directory> + <pixmaps_directory>pixmaps</pixmaps_directory> + <language>C</language> + <gnome_support>True</gnome_support> + <gettext_support>True</gettext_support> +</project> + +<widget> + <class>GnomeDialog</class> + <name>timezone-dialog</name> + <visible>False</visible> + <title>Select a Time Zone</title> + <type>GTK_WINDOW_TOPLEVEL</type> + <position>GTK_WIN_POS_NONE</position> + <modal>False</modal> + <default_width>500</default_width> + <default_height>400</default_height> + <allow_shrink>False</allow_shrink> + <allow_grow>True</allow_grow> + <auto_shrink>False</auto_shrink> + <auto_close>False</auto_close> + <hide_on_close>True</hide_on_close> + + <widget> + <class>GtkVBox</class> + <child_name>GnomeDialog:vbox</child_name> + <name>dialog-vbox1</name> + <homogeneous>False</homogeneous> + <spacing>8</spacing> + <child> + <padding>4</padding> + <expand>True</expand> + <fill>True</fill> + </child> + + <widget> + <class>GtkHButtonBox</class> + <child_name>GnomeDialog:action_area</child_name> + <name>dialog-action_area1</name> + <layout_style>GTK_BUTTONBOX_END</layout_style> + <spacing>8</spacing> + <child_min_width>85</child_min_width> + <child_min_height>27</child_min_height> + <child_ipad_x>7</child_ipad_x> + <child_ipad_y>0</child_ipad_y> + <child> + <padding>0</padding> + <expand>False</expand> + <fill>True</fill> + <pack>GTK_PACK_END</pack> + </child> + + <widget> + <class>GtkButton</class> + <name>ok-button</name> + <can_default>True</can_default> + <has_default>True</has_default> + <can_focus>True</can_focus> + <stock_button>GNOME_STOCK_BUTTON_OK</stock_button> + </widget> + + <widget> + <class>GtkButton</class> + <name>cancel-button</name> + <can_default>True</can_default> + <can_focus>True</can_focus> + <stock_button>GNOME_STOCK_BUTTON_CANCEL</stock_button> + </widget> + </widget> + + <widget> + <class>GtkTable</class> + <name>table1</name> + <rows>3</rows> + <columns>1</columns> + <homogeneous>False</homogeneous> + <row_spacing>4</row_spacing> + <column_spacing>0</column_spacing> + <child> + <padding>0</padding> + <expand>True</expand> + <fill>True</fill> + </child> + + <widget> + <class>GtkLabel</class> + <name>label1</name> + <label>Use the left mouse button to zoom in on an area of the map and select a time zone. + Use the right mouse button to zoom out.</label> + <justify>GTK_JUSTIFY_CENTER</justify> + <wrap>False</wrap> + <xalign>0</xalign> + <yalign>0.5</yalign> + <xpad>0</xpad> + <ypad>0</ypad> + <child> + <left_attach>0</left_attach> + <right_attach>1</right_attach> + <top_attach>0</top_attach> + <bottom_attach>1</bottom_attach> + <xpad>0</xpad> + <ypad>2</ypad> + <xexpand>True</xexpand> + <yexpand>False</yexpand> + <xshrink>False</xshrink> + <yshrink>False</yshrink> + <xfill>False</xfill> + <yfill>False</yfill> + </child> + </widget> + + <widget> + <class>GtkFrame</class> + <name>frame1</name> + <label>Time Zones</label> + <label_xalign>0</label_xalign> + <shadow_type>GTK_SHADOW_ETCHED_IN</shadow_type> + <child> + <left_attach>0</left_attach> + <right_attach>1</right_attach> + <top_attach>1</top_attach> + <bottom_attach>2</bottom_attach> + <xpad>0</xpad> + <ypad>0</ypad> + <xexpand>False</xexpand> + <yexpand>True</yexpand> + <xshrink>False</xshrink> + <yshrink>False</yshrink> + <xfill>True</xfill> + <yfill>True</yfill> + </child> + + <widget> + <class>GtkVBox</class> + <name>vbox1</name> + <border_width>4</border_width> + <homogeneous>False</homogeneous> + <spacing>4</spacing> + + <widget> + <class>GtkScrolledWindow</class> + <name>map-window</name> + <hscrollbar_policy>GTK_POLICY_ALWAYS</hscrollbar_policy> + <vscrollbar_policy>GTK_POLICY_ALWAYS</vscrollbar_policy> + <hupdate_policy>GTK_UPDATE_CONTINUOUS</hupdate_policy> + <vupdate_policy>GTK_UPDATE_CONTINUOUS</vupdate_policy> + <child> + <padding>0</padding> + <expand>True</expand> + <fill>True</fill> + </child> + + <widget> + <class>Placeholder</class> + </widget> + </widget> + + <widget> + <class>GtkVBox</class> + <name>vbox2</name> + <homogeneous>False</homogeneous> + <spacing>0</spacing> + <child> + <padding>0</padding> + <expand>False</expand> + <fill>False</fill> + </child> + + <widget> + <class>GtkLabel</class> + <name>timezone-preview</name> + <label></label> + <justify>GTK_JUSTIFY_CENTER</justify> + <wrap>False</wrap> + <xalign>0.5</xalign> + <yalign>0.5</yalign> + <xpad>0</xpad> + <ypad>0</ypad> + <child> + <padding>0</padding> + <expand>False</expand> + <fill>False</fill> + </child> + </widget> + </widget> + </widget> + </widget> + + <widget> + <class>GtkHBox</class> + <name>hbox1</name> + <homogeneous>False</homogeneous> + <spacing>4</spacing> + <child> + <left_attach>0</left_attach> + <right_attach>1</right_attach> + <top_attach>2</top_attach> + <bottom_attach>3</bottom_attach> + <xpad>0</xpad> + <ypad>0</ypad> + <xexpand>False</xexpand> + <yexpand>False</yexpand> + <xshrink>False</xshrink> + <yshrink>False</yshrink> + <xfill>True</xfill> + <yfill>True</yfill> + </child> + + <widget> + <class>GtkLabel</class> + <name>label3</name> + <label>Selection:</label> + <justify>GTK_JUSTIFY_CENTER</justify> + <wrap>False</wrap> + <xalign>0.5</xalign> + <yalign>0.5</yalign> + <xpad>0</xpad> + <ypad>0</ypad> + <child> + <padding>0</padding> + <expand>False</expand> + <fill>False</fill> + </child> + </widget> + + <widget> + <class>GtkCombo</class> + <name>timezone-combo</name> + <value_in_list>False</value_in_list> + <ok_if_empty>True</ok_if_empty> + <case_sensitive>False</case_sensitive> + <use_arrows>True</use_arrows> + <use_arrows_always>False</use_arrows_always> + <items></items> + <child> + <padding>0</padding> + <expand>True</expand> + <fill>True</fill> + </child> + + <widget> + <class>GtkEntry</class> + <child_name>GtkCombo:entry</child_name> + <name>combo-entry1</name> + <can_focus>True</can_focus> + <editable>False</editable> + <text_visible>True</text_visible> + <text_max_length>0</text_max_length> + <text></text> + </widget> + </widget> + </widget> + </widget> + </widget> +</widget> + +</GTK-Interface> diff --git a/calendar/gui/dialogs/e-timezone-dialog.h b/calendar/gui/dialogs/e-timezone-dialog.h new file mode 100644 index 0000000000..bb253934f7 --- /dev/null +++ b/calendar/gui/dialogs/e-timezone-dialog.h @@ -0,0 +1,72 @@ +/* Evolution calendar - Timezone selector dialog + * + * Copyright (C) 2001 Ximian, Inc. + * + * Authors: Damon Chaplin <damon@ximian.com> + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. + */ + +#ifndef __E_TIMEZONE_DIALOG_H__ +#define __E_TIMEZONE_DIALOG_H__ + +#include <libgnome/gnome-defs.h> +#include <gtk/gtkobject.h> +#include <cal-client/cal-client.h> + + + +#define E_TYPE_TIMEZONE_DIALOG (e_timezone_dialog_get_type ()) +#define E_TIMEZONE_DIALOG(obj) (GTK_CHECK_CAST ((obj), E_TYPE_TIMEZONE_DIALOG, ETimezoneDialog)) +#define E_TIMEZONE_DIALOG_CLASS(klass) (GTK_CHECK_CLASS_CAST ((klass), E_TYPE_TIMEZONE_DIALOG, \ + ETimezoneDialogClass)) +#define E_IS_TIMEZONE_DIALOG(obj) (GTK_CHECK_TYPE ((obj), E_TYPE_TIMEZONE_DIALOG)) +#define E_IS_TIMEZONE_DIALOG_CLASS(klass) (GTK_CHECK_CLASS_TYPE ((klass), E_TYPE_TIMEZONE_DIALOG)) + + +typedef struct _ETimezoneDialog ETimezoneDialog; +typedef struct _ETimezoneDialogClass ETimezoneDialogClass; +typedef struct _ETimezoneDialogPrivate ETimezoneDialogPrivate; + +struct _ETimezoneDialog { + GtkObject object; + + /* Private data */ + ETimezoneDialogPrivate *priv; +}; + +struct _ETimezoneDialogClass { + GtkObjectClass parent_class; +}; + + +GtkType e_timezone_dialog_get_type (void); +ETimezoneDialog* e_timezone_dialog_construct (ETimezoneDialog *etd); + +ETimezoneDialog* e_timezone_dialog_new (void); + +CalClient* e_timezone_dialog_get_cal_client (ETimezoneDialog *etd); +void e_timezone_dialog_set_cal_client (ETimezoneDialog *etd, + CalClient *client); + +char* e_timezone_dialog_get_timezone (ETimezoneDialog *etd); +void e_timezone_dialog_set_timezone (ETimezoneDialog *etd, + char *timezone); + +GtkWidget* e_timezone_dialog_get_toplevel (ETimezoneDialog *etd); + + + +#endif /* __E_TIMEZONE_DIALOG_H__ */ diff --git a/calendar/idl/evolution-calendar.idl b/calendar/idl/evolution-calendar.idl index e21f77fe2e..cec986210a 100644 --- a/calendar/idl/evolution-calendar.idl +++ b/calendar/idl/evolution-calendar.idl @@ -98,6 +98,18 @@ module Calendar { /* Used to represent a list of components plus their triggers */ typedef sequence<CalComponentAlarms> CalComponentAlarmsSeq; + + /* Used to transfer builtin timezone information. */ + struct CalTimezoneInfo { + string location; + double latitude; + double longitude; + }; + + /* Used to transfer a list of timezone info */ + typedef sequence<CalTimezoneInfo> CalTimezoneInfoSeq; + + interface Query; interface Listener; @@ -163,6 +175,10 @@ module Calendar { */ Query getQuery (in string sexp, in QueryListener ql) raises (CouldNotCreate); + + /* Returns information about all the builtin timezones. */ + CalTimezoneInfoSeq getBuiltinTimezoneInfo () + raises (NotFound); }; /* Listener for changes in a calendar */ diff --git a/calendar/pcs/cal.c b/calendar/pcs/cal.c index 6eb951133b..a76d3a7f38 100644 --- a/calendar/pcs/cal.c +++ b/calendar/pcs/cal.c @@ -21,6 +21,7 @@ */ #include <config.h> +#include <ical.h> #include "cal.h" #include "query.h" @@ -377,6 +378,46 @@ impl_Cal_get_query (PortableServer_Servant servant, return query_copy; } +/* Cal::getBuiltinTimezoneInfo method */ +static GNOME_Evolution_Calendar_CalTimezoneInfoSeq * +impl_Cal_get_builtin_timezone_info (PortableServer_Servant servant, + CORBA_Environment *ev) +{ + GNOME_Evolution_Calendar_CalTimezoneInfoSeq *seq; + icalarray *zones; + icaltimezone *zone; + int n, i; + char *location; + + zones = icaltimezone_get_builtin_timezones (); + if (!zones) { + CORBA_exception_set (ev, CORBA_USER_EXCEPTION, + ex_GNOME_Evolution_Calendar_Cal_NotFound, + NULL); + return CORBA_OBJECT_NIL; + } + + n = zones->num_elements; + + seq = GNOME_Evolution_Calendar_CalTimezoneInfoSeq__alloc (); + CORBA_sequence_set_release (seq, TRUE); + seq->_length = n; + seq->_buffer = CORBA_sequence_GNOME_Evolution_Calendar_CalTimezoneInfo_allocbuf (n); + + /* Fill the sequence */ + + for (i = 0; i < n; i++) { + zone = icalarray_element_at (zones, i); + location = icaltimezone_get_location (zone); + + seq->_buffer[i].location = CORBA_string_dup (location); + seq->_buffer[i].latitude = icaltimezone_get_latitude (zone); + seq->_buffer[i].longitude = icaltimezone_get_longitude (zone); + } + + return seq; +} + /** * cal_construct: * @cal: A calendar client interface. @@ -507,6 +548,7 @@ cal_class_init (CalClass *klass) epv->updateObject = impl_Cal_update_object; epv->removeObject = impl_Cal_remove_object; epv->getQuery = impl_Cal_get_query; + epv->getBuiltinTimezoneInfo = impl_Cal_get_builtin_timezone_info; } |