From 8bbb375ac1c9a6f97b0f1a0abc1de2669adf77fc Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Erick=20P=C3=A9rez=20Castellanos?= Date: Mon, 4 Jun 2012 06:54:27 -0400 Subject: [PATCH] Added initial version of GcalEditable family of widgets. --- src/Makefile.am | 4 + src/gcal-editable-entry.c | 164 ++++++++++++++++++++++++++++++++++ src/gcal-editable-entry.h | 57 ++++++++++++ src/gcal-editable.c | 179 ++++++++++++++++++++++++++++++++++++++ src/gcal-editable.h | 72 +++++++++++++++ src/gcal-event-view.c | 7 +- src/gcal-month-view.c | 6 +- src/gcal-month-view.h | 1 + src/gcal-toolbar.c | 2 +- src/gcal-utils.h | 15 +++- 10 files changed, 498 insertions(+), 9 deletions(-) create mode 100644 src/gcal-editable-entry.c create mode 100644 src/gcal-editable-entry.h create mode 100644 src/gcal-editable.c create mode 100644 src/gcal-editable.h diff --git a/src/Makefile.am b/src/Makefile.am index c120fc04..0f2dc1d3 100644 --- a/src/Makefile.am +++ b/src/Makefile.am @@ -33,6 +33,10 @@ gnome_calendar_SOURCES = \ gcal-event-widget.h \ gcal-event-view.c \ gcal-event-view.h \ + gcal-editable.c \ + gcal-editable.h \ + gcal-editable-entry.c \ + gcal-editable-entry.h \ gcal-manager.c \ gcal-manager.h \ gcal-utils.c \ diff --git a/src/gcal-editable-entry.c b/src/gcal-editable-entry.c new file mode 100644 index 00000000..874e8528 --- /dev/null +++ b/src/gcal-editable-entry.c @@ -0,0 +1,164 @@ +/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 2 -*- */ +/* + * gcal-editable-entry.c + * + * Copyright (C) 2012 - Erick Pérez Castellanos + * + * 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, see . + */ + +#include "gcal-editable-entry.h" + +struct _GcalEditableEntryPrivate +{ + GtkWidget *edit_widget; + + gboolean update_view; +}; + +static void gcal_editable_entry_constructed (GObject *object); + +static gchar* gcal_editable_entry_update_view_widget (GcalEditable *editable); + +static void gcal_editable_entry_enter_edit_mode (GcalEditable *editable); + +static gboolean gcal_editable_entry_key_pressed (GtkWidget *widget, + GdkEventKey *event, + gpointer user_data); + +static void gcal_editable_entry_activated (GtkEntry *entry, + gpointer user_data); + +G_DEFINE_TYPE (GcalEditableEntry, gcal_editable_entry, GCAL_TYPE_EDITABLE); + +static void gcal_editable_entry_class_init (GcalEditableEntryClass *klass) +{ + GcalEditableClass *editable_class; + GObjectClass *object_class; + + editable_class = GCAL_EDITABLE_CLASS (klass); + editable_class->update_view_widget = gcal_editable_entry_update_view_widget; + editable_class->enter_edit_mode = gcal_editable_entry_enter_edit_mode; + editable_class->leave_edit_mode = NULL; + + object_class = G_OBJECT_CLASS (klass); + object_class->constructed = gcal_editable_entry_constructed; + + g_type_class_add_private ((gpointer)klass, sizeof (GcalEditableEntryPrivate)); +} + + + +static void gcal_editable_entry_init (GcalEditableEntry *self) +{ + self->priv = G_TYPE_INSTANCE_GET_PRIVATE (self, + GCAL_TYPE_EDITABLE_ENTRY, + GcalEditableEntryPrivate); +} + +static void +gcal_editable_entry_constructed (GObject *object) +{ + GcalEditableEntryPrivate *priv; + + priv = GCAL_EDITABLE_ENTRY (object)->priv; + + if (G_OBJECT_CLASS (gcal_editable_entry_parent_class)->constructed != NULL) + G_OBJECT_CLASS (gcal_editable_entry_parent_class)->constructed (object); + + priv->edit_widget = gtk_entry_new (); + gtk_widget_show (priv->edit_widget); + gcal_editable_set_edit_widget (GCAL_EDITABLE (object), priv->edit_widget); + + g_signal_connect (priv->edit_widget, + "key-press-event", + G_CALLBACK (gcal_editable_entry_key_pressed), + object); + g_signal_connect (priv->edit_widget, + "activate", + G_CALLBACK (gcal_editable_entry_activated), + object); + + priv->update_view = TRUE; +} + +static gchar* +gcal_editable_entry_update_view_widget (GcalEditable *editable) +{ + GcalEditableEntryPrivate *priv; + gchar *contents; + + g_return_val_if_fail (GCAL_IS_EDITABLE_ENTRY (editable), NULL); + priv = GCAL_EDITABLE_ENTRY (editable)->priv; + contents = g_strdup (gtk_entry_get_text (GTK_ENTRY (priv->edit_widget))); + return priv->update_view ? contents : NULL; +} + +static void +gcal_editable_entry_enter_edit_mode (GcalEditable *editable) +{ + GcalEditableEntryPrivate *priv; + const gchar *contents; + + g_return_if_fail (GCAL_IS_EDITABLE_ENTRY (editable)); + priv = GCAL_EDITABLE_ENTRY (editable)->priv; + + contents = gcal_editable_get_view_contents (editable); + gtk_entry_set_text (GTK_ENTRY (priv->edit_widget), contents); + gtk_editable_select_region (GTK_EDITABLE (priv->edit_widget), 0, -1); + + gtk_widget_grab_focus (priv->edit_widget); +} + +static gboolean +gcal_editable_entry_key_pressed (GtkWidget *widget, + GdkEventKey *event, + gpointer user_data) +{ + GcalEditableEntryPrivate *priv; + + g_return_val_if_fail (GCAL_IS_EDITABLE_ENTRY (user_data), FALSE); + priv = GCAL_EDITABLE_ENTRY (user_data)->priv; + + if (event->keyval == GDK_KEY_Escape) + { + priv->update_view = FALSE; + gcal_editable_leave_edit_mode (GCAL_EDITABLE (user_data)); + return TRUE; + } + return FALSE; +} + +static void +gcal_editable_entry_activated (GtkEntry *entry, + gpointer user_data) +{ + if (gtk_entry_get_text_length (entry) != 0) + { + gcal_editable_leave_edit_mode (GCAL_EDITABLE (user_data)); + } +} + +/** + * gcal_editable_entry_new: + * @date: + * + * Since: 0.1 + * Returns: (transfer full): + **/ +GtkWidget* +gcal_editable_entry_new (void) +{ + return g_object_new (GCAL_TYPE_EDITABLE_ENTRY, NULL); +} diff --git a/src/gcal-editable-entry.h b/src/gcal-editable-entry.h new file mode 100644 index 00000000..b3017b6b --- /dev/null +++ b/src/gcal-editable-entry.h @@ -0,0 +1,57 @@ +/* + * gcal-editable.h + * + * Copyright (C) 2012 - Erick Pérez Castellanos + * + * 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, see . + */ + +#ifndef __GCAL_EDITABLE_ENTRY_H__ +#define __GCAL_EDITABLE_ENTRY_H__ + +#include "gcal-editable.h" + +G_BEGIN_DECLS + +#define GCAL_TYPE_EDITABLE_ENTRY (gcal_editable_entry_get_type ()) +#define GCAL_EDITABLE_ENTRY(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), GCAL_TYPE_EDITABLE_ENTRY, GcalEditableEntry)) +#define GCAL_EDITABLE_ENTRY_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass), GCAL_TYPE_EDITABLE_ENTRY, GcalEditableEntryClass)) +#define GCAL_IS_EDITABLE_ENTRY(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), GCAL_TYPE_EDITABLE_ENTRY)) +#define GCAL_IS_EDITABLE_ENTRY_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass), GCAL_TYPE_EDITABLE_ENTRY)) +#define GCAL_EDITABLE_ENTRY_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS((obj), GCAL_TYPE_EDITABLE_ENTRY, GcalEditableEntryClass)) + +typedef struct _GcalEditableEntry GcalEditableEntry; +typedef struct _GcalEditableEntryClass GcalEditableEntryClass; +typedef struct _GcalEditableEntryPrivate GcalEditableEntryPrivate; + +struct _GcalEditableEntry +{ + GcalEditable parent; + + /* add your public declarations here */ + GcalEditableEntryPrivate *priv; +}; + +struct _GcalEditableEntryClass +{ + GcalEditableClass parent_class; +}; + +GType gcal_editable_entry_get_type (void); + +GtkWidget* gcal_editable_entry_new (void); + +G_END_DECLS + +#endif /* __GCAL_EDITABLE_ENTRY_H__ */ diff --git a/src/gcal-editable.c b/src/gcal-editable.c new file mode 100644 index 00000000..b4a3dd95 --- /dev/null +++ b/src/gcal-editable.c @@ -0,0 +1,179 @@ +/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 2 -*- */ +/* + * gcal-editable.c + * + * Copyright (C) 2012 - Erick Pérez Castellanos + * + * 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, see . + */ + +#include "gcal-editable.h" +#include "gcal-utils.h" + +struct _GcalEditablePrivate +{ + GtkWidget *view_widget; + GtkWidget *event_box; + + GcalEditableMode mode : 1; +}; + +static void gcal_editable_constructed (GObject *object); + +static gboolean gcal_editable_button_pressed (GtkWidget *widget, + GdkEventButton *event, + gpointer user_data); + +G_DEFINE_TYPE (GcalEditable, gcal_editable, GTK_TYPE_NOTEBOOK); + +static void gcal_editable_class_init (GcalEditableClass *klass) +{ + GObjectClass *object_class; + + object_class = G_OBJECT_CLASS (klass); + object_class->constructed = gcal_editable_constructed; + + klass->update_view_widget = NULL; + klass->enter_edit_mode = gcal_editable_enter_edit_mode; + klass->leave_edit_mode = gcal_editable_leave_edit_mode; + + g_type_class_add_private ((gpointer)klass, sizeof (GcalEditablePrivate)); +} + + + +static void gcal_editable_init (GcalEditable *self) +{ + self->priv = G_TYPE_INSTANCE_GET_PRIVATE (self, + GCAL_TYPE_EDITABLE, + GcalEditablePrivate); +} + +static void +gcal_editable_constructed (GObject *object) +{ + GcalEditablePrivate *priv; + + priv = GCAL_EDITABLE (object)->priv; + + priv->mode = GCAL_VIEW_MODE; + priv->view_widget = gtk_label_new (NULL); + priv->event_box = gtk_event_box_new (); + gtk_container_add (GTK_CONTAINER (priv->event_box), + priv->view_widget); + gtk_widget_show_all (priv->event_box); + gtk_notebook_insert_page (GTK_NOTEBOOK (object), + priv->event_box, + NULL, + 0); + + gtk_notebook_set_current_page (GTK_NOTEBOOK (object), 0); + gtk_notebook_set_show_tabs (GTK_NOTEBOOK (object), FALSE); + + g_signal_connect (priv->event_box, + "button-press-event", + G_CALLBACK (gcal_editable_button_pressed), object); +} + +static gboolean +gcal_editable_button_pressed (GtkWidget *widget, + GdkEventButton *event, + gpointer user_data) +{ + if (event->type == GDK_2BUTTON_PRESS) + gcal_editable_enter_edit_mode (user_data); + + return TRUE; +} + +/* Public API */ +void +gcal_editable_set_view_contents (GcalEditable *editable, + const gchar *contents) +{ + GcalEditablePrivate *priv; + + g_return_if_fail (GCAL_IS_EDITABLE (editable)); + priv = editable->priv; + + gtk_label_set_text (GTK_LABEL (priv->view_widget), contents); +} + +void +gcal_editable_set_edit_widget (GcalEditable *editable, + GtkWidget *widget) +{ + g_return_if_fail (GCAL_IS_EDITABLE (editable)); + + if (gtk_notebook_get_nth_page (GTK_NOTEBOOK (editable), 1) != NULL) + gtk_notebook_remove_page (GTK_NOTEBOOK (editable), 1); + + gtk_notebook_insert_page (GTK_NOTEBOOK (editable), widget, NULL, 1); +} + +const gchar* +gcal_editable_get_view_contents (GcalEditable *editable) +{ + GcalEditablePrivate *priv; + + g_return_val_if_fail (GCAL_IS_EDITABLE (editable), NULL); + priv = GCAL_EDITABLE (editable)->priv; + return gtk_label_get_text (GTK_LABEL (priv->view_widget)); +} + +void +gcal_editable_enter_edit_mode (GcalEditable *editable) +{ + GcalEditablePrivate *priv; + + g_return_if_fail (GCAL_IS_EDITABLE (editable)); + priv = editable->priv; + + if (priv->mode == GCAL_VIEW_MODE) + { + gtk_notebook_set_current_page (GTK_NOTEBOOK (editable), 1); + + if (GCAL_EDITABLE_GET_CLASS (editable)->enter_edit_mode != NULL) + GCAL_EDITABLE_GET_CLASS (editable)->enter_edit_mode (editable); + + priv->mode = GCAL_EDIT_MODE; + } +} + +void +gcal_editable_leave_edit_mode (GcalEditable *editable) +{ + GcalEditablePrivate *priv; + gchar *str; + + g_return_if_fail (GCAL_IS_EDITABLE (editable)); + priv = editable->priv; + + if (priv->mode == GCAL_EDIT_MODE) + { + str = GCAL_EDITABLE_GET_CLASS (editable)->update_view_widget (editable); + if (str != NULL) + { + gtk_label_set_text (GTK_LABEL (priv->view_widget), str); + g_free (str); + } + + gtk_notebook_set_current_page (GTK_NOTEBOOK (editable), 0); + + if (GCAL_EDITABLE_GET_CLASS (editable)->leave_edit_mode != NULL) + GCAL_EDITABLE_GET_CLASS (editable)->leave_edit_mode (editable); + + priv->mode = GCAL_VIEW_MODE; + } +} diff --git a/src/gcal-editable.h b/src/gcal-editable.h new file mode 100644 index 00000000..c7dfa43f --- /dev/null +++ b/src/gcal-editable.h @@ -0,0 +1,72 @@ +/* + * gcal-editable.h + * + * Copyright (C) 2012 - Erick Pérez Castellanos + * + * 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, see . + */ + +#ifndef __GCAL_EDITABLE_H__ +#define __GCAL_EDITABLE_H__ + +#include + +G_BEGIN_DECLS + +#define GCAL_TYPE_EDITABLE (gcal_editable_get_type ()) +#define GCAL_EDITABLE(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), GCAL_TYPE_EDITABLE, GcalEditable)) +#define GCAL_EDITABLE_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass), GCAL_TYPE_EDITABLE, GcalEditableClass)) +#define GCAL_IS_EDITABLE(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), GCAL_TYPE_EDITABLE)) +#define GCAL_IS_EDITABLE_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass), GCAL_TYPE_EDITABLE)) +#define GCAL_EDITABLE_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS((obj), GCAL_TYPE_EDITABLE, GcalEditableClass)) + +typedef struct _GcalEditable GcalEditable; +typedef struct _GcalEditableClass GcalEditableClass; +typedef struct _GcalEditablePrivate GcalEditablePrivate; + +struct _GcalEditable +{ + GtkNotebook parent; + + /* add your public declarations here */ + GcalEditablePrivate *priv; +}; + +struct _GcalEditableClass +{ + GtkNotebookClass parent_class; + + /* virtual methods */ + gchar* (*update_view_widget) (GcalEditable *editable); + void (*enter_edit_mode) (GcalEditable *editable); + void (*leave_edit_mode) (GcalEditable *editable); +}; + +GType gcal_editable_get_type (void); + +void gcal_editable_set_view_contents (GcalEditable *editable, + const gchar *contents); + +void gcal_editable_set_edit_widget (GcalEditable *editable, + GtkWidget *widget); + +const gchar* gcal_editable_get_view_contents (GcalEditable *editable); + +void gcal_editable_enter_edit_mode (GcalEditable *editable); + +void gcal_editable_leave_edit_mode (GcalEditable *editable); + +G_END_DECLS + +#endif /* __GCAL_EDITABLE_H__ */ diff --git a/src/gcal-event-view.c b/src/gcal-event-view.c index 6420ce9b..52511132 100644 --- a/src/gcal-event-view.c +++ b/src/gcal-event-view.c @@ -18,6 +18,7 @@ */ #include "gcal-event-view.h" +#include "gcal-editable-entry.h" #include @@ -93,8 +94,10 @@ gcal_event_view_constructed (GObject *object) if (G_OBJECT_CLASS (gcal_event_view_parent_class)->constructed != NULL) G_OBJECT_CLASS (gcal_event_view_parent_class)->constructed (object); - priv->e_what = gtk_entry_new (); - priv->e_host = gtk_entry_new (); + priv->e_what = gcal_editable_entry_new (); + gcal_editable_enter_edit_mode (GCAL_EDITABLE (priv->e_what)); + priv->e_host = gcal_editable_entry_new (); + gcal_editable_enter_edit_mode (GCAL_EDITABLE (priv->e_host)); priv->e_since = gtk_entry_new (); priv->e_until = gtk_entry_new (); diff --git a/src/gcal-month-view.c b/src/gcal-month-view.c index 4d9d1aad..fd09c8d6 100644 --- a/src/gcal-month-view.c +++ b/src/gcal-month-view.c @@ -118,7 +118,7 @@ static void gcal_month_view_draw_month_grid (GcalMonthView *mont_vi gint x, gint y); -static gboolean gcal_month_view_is_in_range (GcalView *view, +static gboolean gcal_month_view_is_in_range (GcalView *view, icaltimetype *date); @@ -746,7 +746,7 @@ gcal_month_view_new (icaltimetype *date) * * Since: 0.1 * Return value: the first day of the month - * Returns: (transfer full): + * Returns: (transfer full): Release with g_free **/ icaltimetype* gcal_month_view_get_initial_date (GcalMonthView *view) @@ -766,7 +766,7 @@ gcal_month_view_get_initial_date (GcalMonthView *view) * * Since: 0.1 * Return value: the last day of the month - * Returns: (transfer full): + * Returns: (transfer full): Release with g_free **/ icaltimetype* gcal_month_view_get_final_date (GcalMonthView *view) diff --git a/src/gcal-month-view.h b/src/gcal-month-view.h index 7ac7541b..0fed3fa5 100644 --- a/src/gcal-month-view.h +++ b/src/gcal-month-view.h @@ -55,6 +55,7 @@ GType gcal_month_view_get_type (void); GtkWidget* gcal_month_view_new (icaltimetype *date); icaltimetype* gcal_month_view_get_initial_date (GcalMonthView *view); + icaltimetype* gcal_month_view_get_final_date (GcalMonthView *view); G_END_DECLS diff --git a/src/gcal-toolbar.c b/src/gcal-toolbar.c index 11feac98..66c89085 100644 --- a/src/gcal-toolbar.c +++ b/src/gcal-toolbar.c @@ -383,7 +383,7 @@ gcal_toolbar_set_mode (GcalToolbar *toolbar, case GCAL_TOOLBAR_OVERVIEW: gcal_toolbar_set_overview_mode (toolbar); return; - case GCAL_TOOLBAR_EVENT: + case GCAL_TOOLBAR_VIEW_EVENT: gcal_toolbar_set_event_mode (toolbar); } } diff --git a/src/gcal-utils.h b/src/gcal-utils.h index 107bb68b..b49b8fc0 100644 --- a/src/gcal-utils.h +++ b/src/gcal-utils.h @@ -23,6 +23,8 @@ #include #include +#define ICAL_TIME_TYPE (icaltime_get_type ()) + typedef enum { GCAL_VIEW_TYPE_DAILY = 0, @@ -35,12 +37,19 @@ typedef enum typedef enum { GCAL_TOOLBAR_OVERVIEW = 0, - GCAL_TOOLBAR_EVENT + GCAL_TOOLBAR_VIEW_EVENT } GcalToolbarMode; -#define ICAL_TIME_TYPE (icaltime_get_type ()) +typedef enum +{ + GCAL_EDIT_MODE = 0, + GCAL_VIEW_MODE, +} GcalEditableMode; -GType icaltime_get_type (void) G_GNUC_CONST; +typedef +const gchar* (*GcalTranslateFunc) (GtkWidget *source_widget); + +GType icaltime_get_type (void) G_GNUC_CONST; void gcal_gtk_tree_view_set_activate_on_single_click (GtkTreeView *tree_view, gboolean should_activate);