Commit ae9a8f66 authored by Mark McLoughlin's avatar Mark McLoughlin Committed by Mark McLoughlin
Browse files

Mmmmmm, bloat ....

2004-01-12  Mark McLoughlin  <mark@skynet.ie>

	Patch to make the calendar popup display your tasks and
	appointments from Evolution. Based on patches from
	William Jon McCann <mccann@jhu.edu> (bug #128283)
	and Martin Grimme  <martin@pycage.de> and
	Christian Kellner  <gicmo@xatom.net> (bug #128283).

	Still in need of work. UI loving, mainly. Small TODO
	list in clock.c.

	* GNOME_ClockApplet_Factory.server.in.in: make the applet
	out of process.

	* Makefile.am: build the cut-n-paste subdir, make a binary
	instead of an shlib, build the calendar bits.

	* clock.c: add tasks and appointments to the calendar popup.

	* calendar-client.[ch]: hide all the book-keeping behind
	a nice API.

	* calendar-debug.h: debugging utils.

	* calendar-sources.[ch]: keep track of Evolution's selected
	sources.

	* cut-n-paste/eel-pango-extensions.[ch]: copy eel's method
	for creating a PangoLayout with text ellipsized at a given
	width.

	* cut-n-paste/eggcellrenderertext.[ch]: copy GtkCellRendererText
	and add ellipsizing support.

	* cut-n-paste/eggintl.h: i18n support.

	* cut-n-paste/eggmarshalers.list: marhsallers.

	* cut-n-paste/eggtreeprivate.h: copy bit from gtktreeprivate.h,
	but they're not really used.
parent b99eacb0
......@@ -7,3 +7,4 @@ Makefile
GNOME_ClockApplet_Factory.server
GNOME_ClockApplet_Factory.server.in
clock.schemas
clock-applet
2004-01-12 Mark McLoughlin <mark@skynet.ie>
Patch to make the calendar popup display your tasks and
appointments from Evolution. Based on patches from
William Jon McCann <mccann@jhu.edu> (bug #128283)
and Martin Grimme <martin@pycage.de> and
Christian Kellner <gicmo@xatom.net> (bug #128283).
Still in need of work. UI loving, mainly. Small TODO
list in clock.c.
* GNOME_ClockApplet_Factory.server.in.in: make the applet
out of process.
* Makefile.am: build the cut-n-paste subdir, make a binary
instead of an shlib, build the calendar bits.
* clock.c: add tasks and appointments to the calendar popup.
* calendar-client.[ch]: hide all the book-keeping behind
a nice API.
* calendar-debug.h: debugging utils.
* calendar-sources.[ch]: keep track of Evolution's selected
sources.
* cut-n-paste/eel-pango-extensions.[ch]: copy eel's method
for creating a PangoLayout with text ellipsized at a given
width.
* cut-n-paste/eggcellrenderertext.[ch]: copy GtkCellRendererText
and add ellipsizing support.
* cut-n-paste/eggintl.h: i18n support.
* cut-n-paste/eggmarshalers.list: marhsallers.
* cut-n-paste/eggtreeprivate.h: copy bit from gtktreeprivate.h,
but they're not really used.
2004-01-09 Kaushal Kumar <kaushal.kumar@wipro.com>
* GNOME_ClockApplet_Factory.server.in.in: Added info for bug-reporting.
......
<oaf_info>
<oaf_server iid="OAFIID:GNOME_ClockApplet_Factory"
type="shlib"
location="@APPLET_LIBDIR@/libclock-applet-2">
type="exe"
location="@LIBEXECDIR@/clock-applet">
<oaf_attribute name="repo_ids" type="stringv">
<item value="IDL:Bonobo/GenericFactory:1.0"/>
......
SUBDIRS = cut-n-paste
INCLUDES = \
-I$(srcdir)/../../libpanel-applet \
-I$(top_builddir)/libpanel-applet \
......@@ -11,18 +13,26 @@ INCLUDES = \
-DPREFIX=\""$(prefix)"\" \
-DGNOMELOCALEDIR=\""$(prefix)/$(DATADIRNAME)/locale"\"
libclock_applet_2_la_SOURCES = clock.c
if HAVE_LIBECAL
CALENDAR_SOURCES = \
calendar-client.c \
calendar-client.h \
calendar-sources.c \
calendar-sources.h \
calendar-debug.h
endif
clock_applet_SOURCES = clock.c $(CALENDAR_SOURCES)
libclock_applet_2_la_LDFLAGS = -module -avoid-version -no-undefined
libclock_applet_2_la_LIBADD = \
clock_applet_LDADD = \
../../libpanel-applet/libpanel-applet-2.la \
cut-n-paste/libclockcnp.la \
$(CLOCK_LIBS)
appletdir = $(libdir)
applet_LTLIBRARIES = libclock-applet-2.la
libexec_PROGRAMS = clock-applet
GNOME_ClockApplet_Factory.server.in: GNOME_ClockApplet_Factory.server.in.in
sed -e "s|\@APPLET_LIBDIR\@|$(appletdir)|" $< > $@
sed -e "s|\@LIBEXECDIR\@|$(libexecdir)|" $< > $@
uidir = $(datadir)/gnome-2.0/ui
ui_DATA = GNOME_ClockApplet.xml
......
This diff is collapsed.
/*
* Copyright (C) 2004 Free Software Foundation, Inc.
*
* 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.
*
* Authors:
* Mark McLoughlin <mark@skynet.ie>
* William Jon McCann <mccann@jhu.edu>
* Martin Grimme <martin@pycage.de>
* Christian Kellner <gicmo@xatom.net>
*/
#ifndef __CALENDAR_CLIENT_H__
#define __CALENDAR_CLIENT_H__
#include <glib-object.h>
#include <gdk/gdk.h>
G_BEGIN_DECLS
typedef enum
{
CALENDAR_EVENT_APPOINTMENT = 1 << 0,
CALENDAR_EVENT_TASK = 1 << 1,
CALENDAR_EVENT_ALL = (1 << 2) - 1
} CalendarEventType;
#define CALENDAR_TYPE_CLIENT (calendar_client_get_type ())
#define CALENDAR_CLIENT(o) (G_TYPE_CHECK_INSTANCE_CAST ((o), CALENDAR_TYPE_CLIENT, CalendarClient))
#define CALENDAR_CLIENT_CLASS(k) (G_TYPE_CHECK_CLASS_CAST ((k), CALENDAR_TYPE_CLIENT, CalendarClientClass))
#define CALENDAR_IS_CLIENT(o) (G_TYPE_CHECK_INSTANCE_TYPE ((o), CALENDAR_TYPE_CLIENT))
#define CALENDAR_IS_CLIENT_CLASS(k) (G_TYPE_CHECK_CLASS_TYPE ((k), CALENDAR_TYPE_CLIENT))
#define CALENDAR_CLIENT_GET_CLASS(o)(G_TYPE_INSTANCE_GET_CLASS ((o), CALENDAR_TYPE_CLIENT, CalendarClientClass))
typedef struct _CalendarClient CalendarClient;
typedef struct _CalendarClientClass CalendarClientClass;
typedef struct _CalendarClientPrivate CalendarClientPrivate;
struct _CalendarClient
{
GObject parent;
CalendarClientPrivate *priv;
};
struct _CalendarClientClass
{
GObjectClass parent_class;
void (* appointments_changed) (CalendarClient *client);
void (* tasks_changed) (CalendarClient *client);
};
typedef struct
{
GTime start_time;
GTime end_time;
} CalendarOccurrence;
typedef struct
{
char *uid;
char *summary;
char *description;
GTime start_time;
GTime end_time;
guint is_all_day : 1;
/* Only used internally */
GSList *occurrences;
} CalendarAppointment;
typedef struct
{
char *uid;
char *summary;
char *description;
GTime start_time;
GTime due_time;
guint percent_complete;
GTime completed_time;
} CalendarTask;
typedef struct
{
union
{
CalendarAppointment appointment;
CalendarTask task;
} event;
CalendarEventType type;
} CalendarEvent;
#define CALENDAR_EVENT(e) ((CalendarEvent *)(e))
#define CALENDAR_APPOINTMENT(e) ((CalendarAppointment *)(e))
#define CALENDAR_TASK(e) ((CalendarTask *)(e))
typedef void (* CalendarDayIter) (CalendarClient *client,
guint day,
gpointer user_data);
GType calendar_client_get_type (void) G_GNUC_CONST;
CalendarClient *calendar_client_new (void);
void calendar_client_select_month (CalendarClient *client,
guint month,
guint year);
void calendar_client_select_day (CalendarClient *client,
guint day);
GSList *calendar_client_get_events (CalendarClient *client,
CalendarEventType event_mask);
void calendar_client_foreach_appointment_day (CalendarClient *client,
CalendarDayIter iter_func,
gpointer user_data);
void calendar_client_set_task_completed (CalendarClient *client,
char *task_uid,
gboolean task_completed,
guint percent_complete);
gboolean calendar_client_launch_editor (CalendarClient *client,
CalendarEventType event_type,
GdkScreen *screen,
GError **error);
void calendar_event_free (CalendarEvent *event);
G_END_DECLS
#endif /* __CALENDAR_CLIENT_H__ */
/*
* Copyright (C) 2004 Free Software Foundation, Inc.
*
* 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.
*
* Authors:
* Mark McLoughlin <mark@skynet.ie>
*/
#ifndef __CALENDAR_DEBUG_H__
#define __CALENDAR_DEBUG_H__
#include <glib.h>
G_BEGIN_DECLS
#ifdef CALENDAR_ENABLE_DEBUG
#include <stdio.h>
#ifdef G_HAVE_ISO_VARARGS
# define dprintf(...) fprintf (stderr, __VA_ARGS__);
#elif defined(G_HAVE_GNUC_VARARGS)
# define dprintf(args...) fprintf (stderr, args);
#endif
#else /* if !defined (CALENDAR_DEBUG) */
#ifdef G_HAVE_ISO_VARARGS
# define dprintf(...)
#elif defined(G_HAVE_GNUC_VARARGS)
# define dprintf(args...)
#endif
#endif /* CALENDAR_ENABLE_DEBUG */
G_END_DECLS
#endif /* __CALENDAR_DEBUG_H__ */
/*
* Copyright (C) 2004 Free Software Foundation, Inc.
*
* 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.
*
* Authors:
* Mark McLoughlin <mark@skynet.ie>
* William Jon McCann <mccann@jhu.edu>
* Martin Grimme <martin@pycage.de>
* Christian Kellner <gicmo@xatom.net>
*/
#include <config.h>
#include "calendar-sources.h"
#include <libintl.h>
#include <string.h>
#include <gconf/gconf-client.h>
#include <libecal/e-cal.h>
#include <libedataserver/e-source-list.h>
#undef CALENDAR_ENABLE_DEBUG
#include "calendar-debug.h"
#ifndef _
#define _(x) gettext(x)
#endif
#ifndef N_
#define N_(x) x
#endif
#define CALENDAR_SOURCES_GET_PRIVATE(o) (G_TYPE_INSTANCE_GET_PRIVATE ((o), CALENDAR_TYPE_SOURCES, CalendarSourcesPrivate))
#define CALENDAR_SOURCES_EVO_DIR "/apps/evolution"
#define CALENDAR_SOURCES_APPOINTMENT_SOURCES_KEY CALENDAR_SOURCES_EVO_DIR "/calendar/sources"
#define CALENDAR_SOURCES_SELECTED_APPOINTMENT_SOURCES_DIR CALENDAR_SOURCES_EVO_DIR "/calendar/display"
#define CALENDAR_SOURCES_SELECTED_APPOINTMENT_SOURCES_KEY CALENDAR_SOURCES_SELECTED_APPOINTMENT_SOURCES_DIR "/selected_calendars"
#define CALENDAR_SOURCES_TASK_SOURCES_KEY CALENDAR_SOURCES_EVO_DIR "/tasks/sources"
#define CALENDAR_SOURCES_SELECTED_TASK_SOURCES_DIR CALENDAR_SOURCES_EVO_DIR "/calendar/tasks"
#define CALENDAR_SOURCES_SELECTED_TASK_SOURCES_KEY CALENDAR_SOURCES_SELECTED_APPOINTMENT_SOURCES_DIR "/selected_tasks"
typedef struct _CalendarSourceData CalendarSourceData;
struct _CalendarSourceData
{
ECalSourceType source_type;
CalendarSources *sources;
guint changed_signal;
GSList *clients;
GSList *selected_sources;
ESourceList *esource_list;
guint selected_sources_listener;
char *selected_sources_dir;
guint loaded : 1;
};
struct _CalendarSourcesPrivate
{
CalendarSourceData appointment_sources;
CalendarSourceData task_sources;
GConfClient *gconf_client;
};
static void calendar_sources_class_init (CalendarSourcesClass *klass);
static void calendar_sources_init (CalendarSources *sources);
static void calendar_sources_finalize (GObject *object);
enum
{
APPOINTMENT_SOURCES_CHANGED,
TASK_SOURCES_CHANGED,
LAST_SIGNAL
};
static guint signals [LAST_SIGNAL] = { 0, };
static GObjectClass *parent_class = NULL;
static CalendarSources *calendar_sources_singleton = NULL;
GType
calendar_sources_get_type (void)
{
static GType sources_type = 0;
if (!sources_type)
{
static const GTypeInfo sources_info =
{
sizeof (CalendarSourcesClass),
NULL, /* base_init */
NULL, /* base_finalize */
(GClassInitFunc) calendar_sources_class_init,
NULL, /* class_finalize */
NULL, /* class_data */
sizeof (CalendarSources),
0, /* n_preallocs */
(GInstanceInitFunc) calendar_sources_init,
};
sources_type = g_type_register_static (G_TYPE_OBJECT,
"CalendarSources",
&sources_info, 0);
}
return sources_type;
}
static void
calendar_sources_class_init (CalendarSourcesClass *klass)
{
GObjectClass *gobject_class = (GObjectClass *) klass;
parent_class = g_type_class_peek_parent (klass);
gobject_class->finalize = calendar_sources_finalize;
g_type_class_add_private (klass, sizeof (CalendarSourcesPrivate));
signals [APPOINTMENT_SOURCES_CHANGED] =
g_signal_new ("appointment-sources-changed",
G_TYPE_FROM_CLASS (gobject_class),
G_SIGNAL_RUN_LAST,
G_STRUCT_OFFSET (CalendarSourcesClass,
appointment_sources_changed),
NULL,
NULL,
g_cclosure_marshal_VOID__VOID,
G_TYPE_NONE,
0);
signals [TASK_SOURCES_CHANGED] =
g_signal_new ("task-sources-changed",
G_TYPE_FROM_CLASS (gobject_class),
G_SIGNAL_RUN_LAST,
G_STRUCT_OFFSET (CalendarSourcesClass,
task_sources_changed),
NULL,
NULL,
g_cclosure_marshal_VOID__VOID,
G_TYPE_NONE,
0);
}
static void
calendar_sources_init (CalendarSources *sources)
{
sources->priv = CALENDAR_SOURCES_GET_PRIVATE (sources);
sources->priv->appointment_sources.source_type = E_CAL_SOURCE_TYPE_EVENT;
sources->priv->appointment_sources.sources = sources;
sources->priv->appointment_sources.changed_signal = signals [APPOINTMENT_SOURCES_CHANGED];
sources->priv->task_sources.source_type = E_CAL_SOURCE_TYPE_TODO;
sources->priv->task_sources.sources = sources;
sources->priv->task_sources.changed_signal = signals [TASK_SOURCES_CHANGED];
sources->priv->gconf_client = gconf_client_get_default ();
}
static void
calendar_sources_finalize_source_data (CalendarSources *sources,
CalendarSourceData *source_data)
{
if (source_data->loaded)
{
GSList *l;
if (source_data->selected_sources_dir)
{
gconf_client_remove_dir (sources->priv->gconf_client,
source_data->selected_sources_dir,
NULL);
g_free (source_data->selected_sources_dir);
source_data->selected_sources_dir = NULL;
}
if (source_data->selected_sources_listener)
{
gconf_client_notify_remove (sources->priv->gconf_client,
source_data->selected_sources_listener);
source_data->selected_sources_listener = 0;
}
for (l = source_data->clients; l; l = l->next)
g_object_unref (l->data);
source_data->clients = NULL;
if (source_data->esource_list)
g_object_unref (source_data->esource_list);
source_data->esource_list = NULL;
for (l = source_data->selected_sources; l; l = l->next)
g_free (l->data);
g_slist_free (source_data->selected_sources);
source_data->selected_sources = NULL;
source_data->loaded = FALSE;
}
}
static void
calendar_sources_finalize (GObject *object)
{
CalendarSources *sources = CALENDAR_SOURCES (object);
calendar_sources_finalize_source_data (sources, &sources->priv->appointment_sources);
calendar_sources_finalize_source_data (sources, &sources->priv->task_sources);
if (sources->priv->gconf_client)
g_object_unref (sources->priv->gconf_client);
sources->priv->gconf_client = NULL;
if (G_OBJECT_CLASS (parent_class)->finalize)
G_OBJECT_CLASS (parent_class)->finalize (object);
}
CalendarSources *
calendar_sources_get (void)
{
if (calendar_sources_singleton)
return g_object_ref (calendar_sources_singleton);
calendar_sources_singleton = g_object_new (CALENDAR_TYPE_SOURCES, NULL);
g_object_add_weak_pointer (G_OBJECT (calendar_sources_singleton),
(gpointer *) &calendar_sources_singleton);
return calendar_sources_singleton;
}
static gboolean
is_source_selected (ESource *esource,
GSList *selected_sources)
{
const char *uid;
GSList *l;
uid = e_source_peek_uid (esource);
for (l = selected_sources; l; l = l->next)
{
const char *source = l->data;
if (!strcmp (source, uid))
return TRUE;
}
return FALSE;
}
static ECal *
load_esource (ESource *esource,
ECalSourceType source_type,
GSList *existing_clients)
{
ECal *retval;
GError *error;
if (existing_clients)
{
GSList *l;
for (l = existing_clients; l; l = l->next)
{
ECal *client = E_CAL (l->data);
if (e_source_equal (esource, e_cal_get_source (client)))
{
dprintf (" load_esource: found existing source ... returning that\n");
return g_object_ref (client);
}
}
}
retval = e_cal_new (esource, source_type);
if (!retval)
{
g_warning ("Could not load source '%s' from '%s'\n",
e_source_peek_name (esource),
e_source_peek_relative_uri (esource));
return NULL;
}
error = NULL;
if (!e_cal_open (retval, TRUE, &error))
{
g_assert (error != NULL);
g_warning ("Cannot open calendar from uri '%s': %s\n",
e_cal_get_uri (retval), error->message);
g_error_free (error);
g_object_unref (retval);
return NULL;
}
dprintf (" Loaded calendar from uri '%s'\n",
e_cal_get_uri (retval));
return retval;
}
/* - Order doesn't matter
* - Can just compare object pointers since we