[evolution] Bug #593751 - Show correct context menu in calendar views



commit aac2106c8a1eb8d10af2b5277e07af895a264320
Author: Milan Crha <mcrha redhat com>
Date:   Tue Nov 10 19:08:01 2009 +0100

    Bug #593751 - Show correct context menu in calendar views

 modules/calendar/e-cal-shell-view-actions.c |    8 +-
 modules/calendar/e-cal-shell-view-actions.h |   12 +++
 modules/calendar/e-cal-shell-view-private.c |   20 ++++-
 modules/calendar/e-cal-shell-view.c         |  140 ++++++++++++++++++++++++--
 4 files changed, 164 insertions(+), 16 deletions(-)
---
diff --git a/modules/calendar/e-cal-shell-view-actions.c b/modules/calendar/e-cal-shell-view-actions.c
index 4fa8b07..f3a0f20 100644
--- a/modules/calendar/e-cal-shell-view-actions.c
+++ b/modules/calendar/e-cal-shell-view-actions.c
@@ -1322,7 +1322,7 @@ static GtkActionEntry calendar_entries[] = {
 	  G_CALLBACK (action_event_delete_occurrence_all_cb) },
 
 	{ "event-all-day-new",
-	  NULL,
+	  "stock_new-24h-appointment",
 	  N_("New All Day _Event..."),
 	  NULL,
 	  N_("Create a new all day event"),
@@ -1336,7 +1336,7 @@ static GtkActionEntry calendar_entries[] = {
 	  G_CALLBACK (action_event_forward_cb) },
 
 	{ "event-meeting-new",
-	  NULL,
+	  "stock_new-meeting",
 	  N_("New _Meeting..."),
 	  NULL,
 	  N_("Create a new meeting"),
@@ -1350,7 +1350,7 @@ static GtkActionEntry calendar_entries[] = {
 	  G_CALLBACK (action_event_move_cb) },
 
 	{ "event-new",
-	  NULL,
+	  "appointment-new",
 	  N_("New _Appointment..."),
 	  NULL,
 	  N_("Create a new appointment"),
@@ -1364,7 +1364,7 @@ static GtkActionEntry calendar_entries[] = {
 	  G_CALLBACK (action_event_occurrence_movable_cb) },
 
 	{ "event-open",
-	  NULL,
+	  GTK_STOCK_OPEN,
 	  N_("_Open Appointment"),
 	  "<Control>o",
 	  N_("View the current appointment"),
diff --git a/modules/calendar/e-cal-shell-view-actions.h b/modules/calendar/e-cal-shell-view-actions.h
index b02906f..46d8992 100644
--- a/modules/calendar/e-cal-shell-view-actions.h
+++ b/modules/calendar/e-cal-shell-view-actions.h
@@ -77,6 +77,18 @@
 	E_SHELL_WINDOW_ACTION ((window), "event-delete-occurrence-all")
 #define E_SHELL_WINDOW_ACTION_EVENT_OPEN(window) \
 	E_SHELL_WINDOW_ACTION ((window), "event-open")
+#define E_SHELL_WINDOW_ACTION_OCCURRENCE_MOVABLE(window) \
+	E_SHELL_WINDOW_ACTION ((window), "event-occurrence-movable")
+#define E_SHELL_WINDOW_ACTION_EVENT_DELEGATE(window) \
+	E_SHELL_WINDOW_ACTION ((window), "event-delegate")
+#define E_SHELL_WINDOW_ACTION_EVENT_SCHEDULE(window) \
+	E_SHELL_WINDOW_ACTION ((window), "event-schedule")
+#define E_SHELL_WINDOW_ACTION_EVENT_FORWARD(window) \
+	E_SHELL_WINDOW_ACTION ((window), "event-forward")
+#define E_SHELL_WINDOW_ACTION_EVENT_REPLY(window) \
+	E_SHELL_WINDOW_ACTION ((window), "event-reply")
+#define E_SHELL_WINDOW_ACTION_EVENT_REPLY_ALL(window) \
+	E_SHELL_WINDOW_ACTION ((window), "event-reply-all")
 
 /* Memo Pad Actions */
 #define E_SHELL_WINDOW_ACTION_CALENDAR_MEMOPAD_CLIPBOARD_COPY(window) \
diff --git a/modules/calendar/e-cal-shell-view-private.c b/modules/calendar/e-cal-shell-view-private.c
index 8a7e376..7c4cdbf 100644
--- a/modules/calendar/e-cal-shell-view-private.c
+++ b/modules/calendar/e-cal-shell-view-private.c
@@ -226,8 +226,26 @@ cal_shell_view_popup_event_cb (EShellView *shell_view,
                                GdkEventButton *event)
 {
 	const gchar *widget_path;
+	GList *list;
+	gint n_selected;
+	GnomeCalendar *calendar;
+	ECalendarView *view;
+	ECalShellViewPrivate *priv;
+
+	priv = E_CAL_SHELL_VIEW_GET_PRIVATE (shell_view);
+
+	calendar = e_cal_shell_content_get_calendar (priv->cal_shell_content);
+	view = gnome_calendar_get_calendar_view (calendar, gnome_calendar_get_view (calendar));
+
+	list = e_calendar_view_get_selected_events (view);
+	n_selected = g_list_length (list);
+	g_list_free (list);
+
+	if (n_selected <= 0)
+		widget_path = "/calendar-empty-popup";
+	else
+		widget_path = "/calendar-event-popup";
 
-	widget_path = "/calendar-event-popup";
 	e_shell_view_show_popup_menu (shell_view, widget_path, event);
 }
 
diff --git a/modules/calendar/e-cal-shell-view.c b/modules/calendar/e-cal-shell-view.c
index 392f1fb..00a71f5 100644
--- a/modules/calendar/e-cal-shell-view.c
+++ b/modules/calendar/e-cal-shell-view.c
@@ -204,10 +204,66 @@ cal_shell_view_execute_search (EShellView *shell_view)
 	g_free (query);
 }
 
+static icalproperty *
+get_attendee_prop (icalcomponent *icalcomp, const gchar *address)
+{
+
+	icalproperty *prop;
+
+	if (!(address && *address))
+		return NULL;
+
+	for (prop = icalcomponent_get_first_property (icalcomp, ICAL_ATTENDEE_PROPERTY);
+			prop;
+			prop = icalcomponent_get_next_property (icalcomp, ICAL_ATTENDEE_PROPERTY)) {
+		const gchar *attendee = icalproperty_get_attendee (prop);
+
+		if (g_str_equal (itip_strip_mailto (attendee), address)) {
+			return prop;
+		}
+	}
+	return NULL;
+}
+
+static gboolean
+is_delegated (icalcomponent *icalcomp, const gchar *user_email)
+{
+	icalproperty *prop;
+	icalparameter *param;
+	const gchar *delto = NULL;
+
+	prop = get_attendee_prop (icalcomp, user_email);
+
+	if (prop) {
+		param = icalproperty_get_first_parameter (prop, ICAL_DELEGATEDTO_PARAMETER);
+		if (param)
+			delto = icalparameter_get_delegatedto (param);
+	} else
+		return FALSE;
+
+	prop = get_attendee_prop (icalcomp, itip_strip_mailto (delto));
+
+	if (prop) {
+		const gchar *delfrom = NULL;
+		icalparameter_partstat status = ICAL_PARTSTAT_NONE;
+
+		param = icalproperty_get_first_parameter (prop, ICAL_DELEGATEDFROM_PARAMETER);
+		if (param)
+			delfrom = icalparameter_get_delegatedfrom (param);
+		param = icalproperty_get_first_parameter (prop, ICAL_PARTSTAT_PARAMETER);
+		if (param)
+			status = icalparameter_get_partstat (param);
+		if ((delfrom && *delfrom) && g_str_equal (itip_strip_mailto (delfrom), user_email)
+				&& status != ICAL_PARTSTAT_DECLINED)
+			return TRUE;
+	}
+
+	return FALSE;
+}
+
 static void
 cal_shell_view_update_actions (EShellView *shell_view)
 {
-#if 0
 	ECalShellViewPrivate *priv;
 	ECalShellContent *cal_shell_content;
 	ECalShellSidebar *cal_shell_sidebar;
@@ -224,7 +280,10 @@ cal_shell_view_update_actions (EShellView *shell_view)
 	gboolean user_created_source;
 	gboolean editable = TRUE;
 	gboolean recurring = FALSE;
+	gboolean is_instance = FALSE;
 	gboolean sensitive;
+	gboolean is_meeting = FALSE;
+	gboolean is_delegatable = FALSE;
 	gint n_selected;
 
 	priv = E_CAL_SHELL_VIEW_GET_PRIVATE (shell_view);
@@ -244,18 +303,54 @@ cal_shell_view_update_actions (EShellView *shell_view)
 	n_selected = g_list_length (list);
 
 	for (iter = list; iter != NULL; iter = iter->next) {
-		ECalModelComponent *comp_data = iter->data;
-		gboolean read_only;
+		ECalendarViewEvent *event = iter->data;
+		gboolean read_only = TRUE;
+
+		if (!event || !event->comp_data)
+			continue;
+
+		e_cal_is_read_only (event->comp_data->client, &read_only, NULL);
+		editable = editable && !read_only;
+
+		if (e_cal_util_component_has_recurrences (event->comp_data->icalcomp))
+			recurring = TRUE;
+
+		if (e_cal_util_component_is_instance (event->comp_data->icalcomp)) {
+			recurring = TRUE;
+			is_instance = TRUE;
+		}
 
-		e_cal_is_read_only (comp_data->client, &read_only, NULL);
-		editable &= !read_only;
+		if (iter == list && !iter->next) {
+			ECalComponent *comp;
+			gchar *user_email = NULL;
+			gboolean user_org = FALSE;
 
-		if (e_cal_util_component_has_recurrences (comp_data->icalcomp))
-			recurring |= TRUE;
-		else if (e_cal_util_component_is_instance (comp_data->icalcomp))
-			recurring |= TRUE;
+			comp = e_cal_component_new ();
+			e_cal_component_set_icalcomponent (comp, icalcomponent_new_clone (event->comp_data->icalcomp));
+			user_email = itip_get_comp_attendee (comp, event->comp_data->client);
+
+			is_meeting = e_cal_util_component_has_attendee (event->comp_data->icalcomp);
+
+			if (e_cal_util_component_has_organizer (event->comp_data->icalcomp)) {
+				if (itip_organizer_is_user (comp, event->comp_data->client)) {
+					user_org = TRUE;
+				}
+			}
+
+			if (e_cal_get_static_capability (event->comp_data->client, CAL_STATIC_CAPABILITY_DELEGATE_SUPPORTED)) {
+				if (e_cal_get_static_capability (event->comp_data->client, CAL_STATIC_CAPABILITY_DELEGATE_TO_MANY))
+					is_delegatable = TRUE;
+				else if (!user_org && !is_delegated (event->comp_data->icalcomp, user_email))
+					is_delegatable = TRUE;
+			}
+
+			g_free (user_email);
+			g_object_unref (comp);
+		}
 	}
 
+	g_list_free (list);
+
 	source = e_source_selector_peek_primary_selection (selector);
 	if (source != NULL)
 		uri = e_source_peek_relative_uri (source);
@@ -274,7 +369,7 @@ cal_shell_view_update_actions (EShellView *shell_view)
 	gtk_action_set_sensitive (action, sensitive);
 
 	action = ACTION (CALENDAR_RENAME);
-	sensitive = has_primary_source;
+	sensitive = (source != NULL);
 	gtk_action_set_sensitive (action, sensitive);
 
 	action = ACTION (EVENT_CLIPBOARD_COPY);
@@ -304,7 +399,30 @@ cal_shell_view_update_actions (EShellView *shell_view)
 	action = ACTION (EVENT_OPEN);
 	sensitive = (n_selected == 1);
 	gtk_action_set_sensitive (action, sensitive);
-#endif
+
+	action = ACTION (OCCURRENCE_MOVABLE);
+	sensitive = (n_selected == 1) && editable && recurring && is_instance;
+	gtk_action_set_sensitive (action, sensitive);
+
+	action = ACTION (EVENT_DELEGATE);
+	sensitive = (n_selected == 1) && editable && is_delegatable && is_meeting;
+	gtk_action_set_sensitive (action, sensitive);
+
+	action = ACTION (EVENT_SCHEDULE);
+	sensitive = (n_selected == 1) && editable && !is_meeting;
+	gtk_action_set_sensitive (action, sensitive);
+
+	action = ACTION (EVENT_FORWARD);
+	sensitive = TRUE;
+	gtk_action_set_sensitive (action, sensitive);
+
+	action = ACTION (EVENT_REPLY);
+	sensitive = (n_selected == 1) && is_meeting;
+	gtk_action_set_sensitive (action, sensitive);
+
+	action = ACTION (EVENT_REPLY_ALL);
+	sensitive = (n_selected == 1) && is_meeting;
+	gtk_action_set_sensitive (action, sensitive);
 }
 
 static void



[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]