[gthumb] allow to keep the comment and tags dialogs open after saving
- From: Paolo Bacchilega <paobac src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [gthumb] allow to keep the comment and tags dialogs open after saving
- Date: Mon, 5 Dec 2011 19:59:27 +0000 (UTC)
commit 2067d9c6c51cc1ed288a947d939a9a5d06f1143a
Author: Paolo Bacchilega <paobac src gnome org>
Date: Sun Dec 4 23:45:17 2011 +0100
allow to keep the comment and tags dialogs open after saving
[new feature]
extensions/edit_metadata/Makefile.am | 10 +-
extensions/edit_metadata/actions.c | 76 +----
extensions/edit_metadata/actions.h | 4 +-
extensions/edit_metadata/callbacks.c | 161 +----------
extensions/edit_metadata/callbacks.h | 2 -
extensions/edit_metadata/data/ui/tag-chooser.ui | 121 ++-------
extensions/edit_metadata/dlg-edit-metadata.c | 26 ++-
extensions/edit_metadata/dlg-edit-metadata.h | 4 +-
extensions/edit_metadata/gth-edit-comment-dialog.c | 217 ++++++++++++++
extensions/edit_metadata/gth-edit-comment-dialog.h | 84 ++++++
extensions/edit_metadata/gth-edit-comment-page.h | 53 ----
...edit-comment-page.c => gth-edit-general-page.c} | 99 ++++---
extensions/edit_metadata/gth-edit-general-page.h | 53 ++++
.../edit_metadata/gth-edit-metadata-dialog.c | 170 +----------
.../edit_metadata/gth-edit-metadata-dialog.h | 62 +---
extensions/edit_metadata/gth-edit-tags-dialog.c | 272 +++++++++++++++++
extensions/edit_metadata/gth-edit-tags-dialog.h | 56 ++++
extensions/edit_metadata/gth-tag-chooser-dialog.c | 308 --------------------
extensions/edit_metadata/gth-tag-chooser-dialog.h | 58 ----
extensions/edit_metadata/main.c | 6 +-
extensions/exiv2_tools/Makefile.am | 4 +-
extensions/exiv2_tools/gth-edit-exiv2-page.h | 53 ----
...{gth-edit-exiv2-page.c => gth-edit-iptc-page.c} | 66 ++--
extensions/exiv2_tools/gth-edit-iptc-page.h | 53 ++++
extensions/exiv2_tools/main.c | 4 +-
gthumb/dlg-preferences-extensions.c | 13 +-
gthumb/gth-browser-actions-callbacks.h | 2 +-
gthumb/gth-tags-entry.c | 163 ++++++++--
gthumb/gth-tags-entry.h | 26 ++-
29 files changed, 1076 insertions(+), 1150 deletions(-)
---
diff --git a/extensions/edit_metadata/Makefile.am b/extensions/edit_metadata/Makefile.am
index 77d3a9f..cca3a9c 100644
--- a/extensions/edit_metadata/Makefile.am
+++ b/extensions/edit_metadata/Makefile.am
@@ -12,12 +12,14 @@ libedit_metadata_la_SOURCES = \
dlg-edit-metadata.h \
gth-delete-metadata-task.c \
gth-delete-metadata-task.h \
- gth-edit-comment-page.c \
- gth-edit-comment-page.h \
+ gth-edit-comment-dialog.c \
+ gth-edit-comment-dialog.h \
+ gth-edit-general-page.c \
+ gth-edit-general-page.h \
gth-edit-metadata-dialog.c \
gth-edit-metadata-dialog.h \
- gth-tag-chooser-dialog.c \
- gth-tag-chooser-dialog.h \
+ gth-edit-tags-dialog.c \
+ gth-edit-tags-dialog.h \
gth-tag-task.c \
gth-tag-task.h \
main.c
diff --git a/extensions/edit_metadata/actions.c b/extensions/edit_metadata/actions.c
index d6e6631..58018bd 100644
--- a/extensions/edit_metadata/actions.c
+++ b/extensions/edit_metadata/actions.c
@@ -24,79 +24,27 @@
#include <gthumb.h>
#include "dlg-edit-metadata.h"
#include "gth-delete-metadata-task.h"
-#include "gth-tag-chooser-dialog.h"
-#include "gth-tag-task.h"
+#include "gth-edit-comment-dialog.h"
+#include "gth-edit-tags-dialog.h"
void
-gth_browser_activate_action_edit_metadata (GtkAction *action,
- GthBrowser *browser)
+gth_browser_activate_action_edit_comment (GtkAction *action,
+ GthBrowser *browser)
{
- dlg_edit_metadata (browser);
-}
-
-
-static void
-tag_chooser_dialog_response_cb (GtkDialog *dialog,
- int response_id,
- gpointer user_data)
-{
- GthBrowser *browser = user_data;
-
- switch (response_id) {
- case GTK_RESPONSE_HELP:
- show_help_dialog (GTK_WINDOW (browser), "assign-tags");
- break;
-
- case GTK_RESPONSE_OK:
- {
- GList *items;
- GList *file_data_list;
- GList *file_list;
- char **tags;
- GthTask *task;
-
- items = gth_file_selection_get_selected (GTH_FILE_SELECTION (gth_browser_get_file_list_view (browser)));
- file_data_list = gth_file_list_get_files (GTH_FILE_LIST (gth_browser_get_file_list (browser)), items);
- file_list = gth_file_data_list_to_file_list (file_data_list);
- tags = gth_tag_chooser_dialog_get_tags (GTH_TAG_CHOOSER_DIALOG (dialog));
- task = gth_tag_task_new (file_list, tags);
- gth_browser_exec_task (browser, task, FALSE);
- gtk_widget_destroy (GTK_WIDGET (dialog));
-
- g_object_unref (task);
- g_strfreev (tags);
- _g_object_list_unref (file_list);
- _g_object_list_unref (file_data_list);
- _gtk_tree_path_list_free (items);
- }
- break;
-
- case GTK_RESPONSE_DELETE_EVENT:
- case GTK_RESPONSE_CANCEL:
- gtk_widget_destroy (GTK_WIDGET (dialog));
- break;
- }
+ dlg_edit_metadata (browser,
+ GTH_TYPE_EDIT_COMMENT_DIALOG,
+ "edit-comment-dialog");
}
void
-gth_browser_activate_action_edit_tag_files (GtkAction *action,
- GthBrowser *browser)
+gth_browser_activate_action_edit_tags (GtkAction *action,
+ GthBrowser *browser)
{
- GtkWidget *dialog;
-
- dialog = gth_tag_chooser_dialog_new ();
- g_signal_connect (dialog,
- "delete-event",
- G_CALLBACK (gtk_true),
- NULL);
- g_signal_connect (dialog,
- "response",
- G_CALLBACK (tag_chooser_dialog_response_cb),
- browser);
- gtk_window_set_transient_for (GTK_WINDOW (dialog), GTK_WINDOW (browser));
- gtk_window_present (GTK_WINDOW (dialog));
+ dlg_edit_metadata (browser,
+ GTH_TYPE_EDIT_TAGS_DIALOG,
+ "edit-tags-dialog");
}
diff --git a/extensions/edit_metadata/actions.h b/extensions/edit_metadata/actions.h
index d7fe22e..f0b5837 100644
--- a/extensions/edit_metadata/actions.h
+++ b/extensions/edit_metadata/actions.h
@@ -26,8 +26,8 @@
#define DEFINE_ACTION(x) void x (GtkAction *action, gpointer data);
-DEFINE_ACTION(gth_browser_activate_action_edit_metadata)
-DEFINE_ACTION(gth_browser_activate_action_edit_tag_files)
+DEFINE_ACTION(gth_browser_activate_action_edit_comment)
+DEFINE_ACTION(gth_browser_activate_action_edit_tags)
DEFINE_ACTION(gth_browser_activate_action_tool_delete_metadata)
#endif /* ACTIONS_H */
diff --git a/extensions/edit_metadata/callbacks.c b/extensions/edit_metadata/callbacks.c
index 09d9033..8f4cb3f 100644
--- a/extensions/edit_metadata/callbacks.c
+++ b/extensions/edit_metadata/callbacks.c
@@ -58,19 +58,13 @@ static const char *fixed_ui_info =
" </toolbar>"
" <popup name='FileListPopup'>"
" <placeholder name='File_LastActions'>"
-" <menu action='Edit_QuickTag'>"
-" <separator name='TagListSeparator'/>"
-" <menuitem action='Edit_QuickTagOther'/>"
-" </menu>"
+" <menuitem action='Edit_Tags'/>"
" <menuitem action='Edit_Metadata'/>"
" </placeholder>"
" </popup>"
" <popup name='FilePopup'>"
" <placeholder name='File_LastActions'>"
-" <menu action='Edit_QuickTag'>"
-" <separator name='TagListSeparator'/>"
-" <menuitem action='Edit_QuickTagOther'/>"
-" </menu>"
+" <menuitem action='Edit_Tags'/>"
" <menuitem action='Edit_Metadata'/>"
" </placeholder>"
" </popup>"
@@ -106,13 +100,13 @@ static GthActionEntryExt edit_metadata_action_entries[] = {
N_("Comment"), "<control>M",
N_("Edit the comment and other information of the selected files"),
GTH_ACTION_FLAG_IS_IMPORTANT,
- G_CALLBACK (gth_browser_activate_action_edit_metadata) },
+ G_CALLBACK (gth_browser_activate_action_edit_comment) },
- { "Edit_QuickTagOther", NULL,
- N_("Other..."), NULL,
- N_("Choose another tag"),
+ { "Edit_Tags", "tag",
+ N_("Tags"), NULL,
+ N_("Set the tags of the selected files"),
GTH_ACTION_FLAG_NONE,
- G_CALLBACK (gth_browser_activate_action_edit_tag_files) },
+ G_CALLBACK (gth_browser_activate_action_edit_tags) },
{ "Tool_DeleteMetadata", NULL,
N_("Delete Metadata"), NULL,
@@ -126,30 +120,16 @@ typedef struct {
GthBrowser *browser;
GtkActionGroup *actions;
guint viewer_ui_merge_id;
- gboolean tag_menu_loaded;
- guint monitor_events;
} BrowserData;
static void
browser_data_free (BrowserData *data)
{
- if (data->monitor_events != 0) {
- g_signal_handler_disconnect (gth_main_get_default_monitor (), data->monitor_events);
- data->monitor_events = 0;
- }
g_free (data);
}
-static void
-monitor_tags_changed_cb (GthMonitor *monitor,
- BrowserData *data)
-{
- data->tag_menu_loaded = FALSE;
-}
-
-
void
edit_metadata__gth_browser_construct_cb (GthBrowser *browser)
{
@@ -179,11 +159,6 @@ edit_metadata__gth_browser_construct_cb (GthBrowser *browser)
g_error_free (error);
}
- data->monitor_events = g_signal_connect (gth_main_get_default_monitor (),
- "tags-changed",
- G_CALLBACK (monitor_tags_changed_cb),
- data);
-
g_object_set_data_full (G_OBJECT (browser), BROWSER_DATA_KEY, data, (GDestroyNotify) browser_data_free);
}
@@ -239,120 +214,6 @@ edit_metadata__gth_browser_update_sensitivity_cb (GthBrowser *browser)
}
-static void
-tag_item_activate_cb (GtkMenuItem *menuitem,
- gpointer user_data)
-{
- GthBrowser *browser = user_data;
- GList *items;
- GList *file_data_list;
- GList *file_list;
- char *tag;
- char **tags;
- GthTask *task;
-
- if (gtk_menu_item_get_submenu (menuitem) != NULL)
- return;
-
- items = gth_file_selection_get_selected (GTH_FILE_SELECTION (gth_browser_get_file_list_view (browser)));
- file_data_list = gth_file_list_get_files (GTH_FILE_LIST (gth_browser_get_file_list (browser)), items);
- file_list = gth_file_data_list_to_file_list (file_data_list);
-
- tag = g_object_get_data (G_OBJECT (menuitem), "tag");
- tags = g_new0 (char *, 2);
- tags[0] = g_strdup (tag);
- tags[1] = NULL;
-
- task = gth_tag_task_new (file_list, tags);
- gth_browser_exec_task (browser, task, FALSE);
-
- g_object_unref (task);
- g_strfreev (tags);
- _g_object_list_unref (file_list);
- _g_object_list_unref (file_data_list);
- _gtk_tree_path_list_free (items);
-}
-
-
-static void
-insert_tag_menu_item (BrowserData *data,
- GtkWidget *menu,
- const char *tag,
- int pos)
-{
- GtkWidget *item;
- GtkWidget *image;
-
- item = gtk_image_menu_item_new_with_label (tag);
- gtk_image_menu_item_set_always_show_image (GTK_IMAGE_MENU_ITEM (item), TRUE);
-
- image = gtk_image_new_from_icon_name ("tag", GTK_ICON_SIZE_MENU);
- gtk_widget_show (image);
- gtk_image_menu_item_set_image (GTK_IMAGE_MENU_ITEM (item), image);
- gtk_widget_show (item);
- gtk_menu_shell_insert (GTK_MENU_SHELL (menu), item, pos);
- g_object_set_data_full (G_OBJECT (item), "tag", g_strdup (tag), g_free);
- g_signal_connect (item, "activate", G_CALLBACK (tag_item_activate_cb), data->browser);
-}
-
-
-static void
-update_tag_menu (BrowserData *data)
-{
- GtkWidget *list_menu;
- GtkWidget *file_menu;
- GtkWidget *separator;
- char **tags;
- int i;
-
- list_menu = gtk_menu_item_get_submenu (GTK_MENU_ITEM (gtk_ui_manager_get_widget (gth_browser_get_ui_manager (data->browser), "/FileListPopup/File_LastActions/Edit_QuickTag")));
- separator = gtk_ui_manager_get_widget (gth_browser_get_ui_manager (data->browser), "/FileListPopup/File_LastActions/Edit_QuickTag/TagListSeparator");
- _gtk_container_remove_children (GTK_CONTAINER (list_menu), NULL, separator);
-
- file_menu = gtk_menu_item_get_submenu (GTK_MENU_ITEM (gtk_ui_manager_get_widget (gth_browser_get_ui_manager (data->browser), "/FilePopup/File_LastActions/Edit_QuickTag")));
- separator = gtk_ui_manager_get_widget (gth_browser_get_ui_manager (data->browser), "/FilePopup/File_LastActions/Edit_QuickTag/TagListSeparator");
- _gtk_container_remove_children (GTK_CONTAINER (file_menu), NULL, separator);
-
- tags = g_strdupv (gth_tags_file_get_tags (gth_main_get_default_tag_file ()));
- for (i = 0; tags[i] != NULL; i++) {
- insert_tag_menu_item (data, list_menu, tags[i], i);
- insert_tag_menu_item (data, file_menu, tags[i], i);
- }
-
- g_strfreev (tags);
-}
-
-
-void
-edit_metadata__gth_browser_file_list_popup_before_cb (GthBrowser *browser)
-{
- BrowserData *data;
-
- data = g_object_get_data (G_OBJECT (browser), BROWSER_DATA_KEY);
- g_return_if_fail (data != NULL);
-
- if (! data->tag_menu_loaded) {
- data->tag_menu_loaded = TRUE;
- update_tag_menu (data);
- }
-}
-
-
-void
-edit_metadata__gth_browser_file_popup_before_cb (GthBrowser *browser)
-{
- BrowserData *data;
-
- data = g_object_get_data (G_OBJECT (browser), BROWSER_DATA_KEY);
- g_return_if_fail (data != NULL);
-
- if (! data->tag_menu_loaded) {
- data->tag_menu_loaded = TRUE;
- update_tag_menu (data);
- }
-}
-
-
gpointer
edit_metadata__gth_browser_file_list_key_press_cb (GthBrowser *browser,
GdkEventKey *event)
@@ -366,11 +227,15 @@ edit_metadata__gth_browser_file_list_key_press_cb (GthBrowser *browser,
switch (gdk_keyval_to_lower (event->keyval)) {
case GDK_KEY_c:
- gth_browser_activate_action_edit_metadata (NULL, browser);
+ gth_browser_activate_action_edit_comment (NULL, browser);
+ result = GINT_TO_POINTER (1);
+ break;
+
+ case GDK_KEY_t:
+ gth_browser_activate_action_edit_tags (NULL, browser);
result = GINT_TO_POINTER (1);
break;
}
return result;
}
-
diff --git a/extensions/edit_metadata/callbacks.h b/extensions/edit_metadata/callbacks.h
index 8d4435e..258d1ce 100644
--- a/extensions/edit_metadata/callbacks.h
+++ b/extensions/edit_metadata/callbacks.h
@@ -27,8 +27,6 @@
void edit_metadata__gth_browser_construct_cb (GthBrowser *browser);
void edit_metadata__gth_browser_set_current_page_cb (GthBrowser *browser);
void edit_metadata__gth_browser_update_sensitivity_cb (GthBrowser *browser);
-void edit_metadata__gth_browser_file_list_popup_before_cb (GthBrowser *browser);
-void edit_metadata__gth_browser_file_popup_before_cb (GthBrowser *browser);
gpointer edit_metadata__gth_browser_file_list_key_press_cb (GthBrowser *browser,
GdkEventKey *event);
diff --git a/extensions/edit_metadata/data/ui/tag-chooser.ui b/extensions/edit_metadata/data/ui/tag-chooser.ui
index 8cb6897..7009c68 100644
--- a/extensions/edit_metadata/data/ui/tag-chooser.ui
+++ b/extensions/edit_metadata/data/ui/tag-chooser.ui
@@ -1,131 +1,46 @@
-<?xml version="1.0"?>
+<?xml version="1.0" encoding="UTF-8"?>
<interface>
<requires lib="gtk+" version="2.14"/>
- <!-- interface-naming-policy project-wide -->
- <object class="GtkListStore" id="tags_liststore">
- <columns>
- <!-- column-name name -->
- <column type="gchararray"/>
- <!-- column-name selected -->
- <column type="gboolean"/>
- </columns>
- </object>
<object class="GtkVBox" id="content">
<property name="visible">True</property>
- <property name="orientation">vertical</property>
+ <property name="can_focus">False</property>
<property name="spacing">6</property>
<child>
<object class="GtkLabel" id="tag_label">
<property name="visible">True</property>
+ <property name="can_focus">False</property>
<property name="xalign">0</property>
<property name="label" translatable="yes">T_ags:</property>
<property name="use_underline">True</property>
- <property name="mnemonic_widget">tags_treeview</property>
</object>
<packing>
<property name="expand">False</property>
+ <property name="fill">True</property>
<property name="position">0</property>
</packing>
</child>
<child>
- <object class="GtkHBox" id="hbox3">
+ <object class="GtkBox" id="tag_entry_box">
<property name="visible">True</property>
- <property name="spacing">12</property>
- <child>
- <object class="GtkScrolledWindow" id="tags_scrolledwindow">
- <property name="width_request">250</property>
- <property name="height_request">300</property>
- <property name="visible">True</property>
- <property name="can_focus">True</property>
- <property name="hscrollbar_policy">automatic</property>
- <property name="vscrollbar_policy">automatic</property>
- <property name="shadow_type">etched-in</property>
- <child>
- <object class="GtkTreeView" id="tags_treeview">
- <property name="visible">True</property>
- <property name="can_focus">True</property>
- <property name="model">tags_liststore</property>
- <property name="headers_visible">False</property>
- <child>
- <object class="GtkTreeViewColumn" id="treeviewcolumn1">
- <child>
- <object class="GtkCellRendererToggle" id="selected_cellrenderertoggle"/>
- <attributes>
- <attribute name="active">1</attribute>
- </attributes>
- </child>
- </object>
- </child>
- <child>
- <object class="GtkTreeViewColumn" id="treeviewcolumn2">
- <property name="title">column</property>
- <property name="sort_column_id">1</property>
- <child>
- <object class="GtkCellRendererPixbuf" id="cellrendererpixbuf2">
- <property name="icon_name">tag</property>
- </object>
- </child>
- <child>
- <object class="GtkCellRendererText" id="name_cellrenderertext">
- <property name="editable">True</property>
- </object>
- <attributes>
- <attribute name="text">0</attribute>
- </attributes>
- </child>
- </object>
- </child>
- </object>
- </child>
- </object>
- <packing>
- <property name="position">0</property>
- </packing>
- </child>
+ <property name="can_focus">False</property>
+ <property name="orientation">vertical</property>
<child>
- <object class="GtkVButtonBox" id="vbuttonbox3">
- <property name="visible">True</property>
- <property name="orientation">vertical</property>
- <property name="spacing">6</property>
- <property name="layout_style">start</property>
- <child>
- <object class="GtkButton" id="new_button">
- <property name="label">gtk-new</property>
- <property name="visible">True</property>
- <property name="can_focus">True</property>
- <property name="receives_default">True</property>
- <property name="use_stock">True</property>
- </object>
- <packing>
- <property name="expand">False</property>
- <property name="fill">False</property>
- <property name="position">0</property>
- </packing>
- </child>
- <child>
- <object class="GtkButton" id="delete_button">
- <property name="label">gtk-remove</property>
- <property name="visible">True</property>
- <property name="can_focus">True</property>
- <property name="receives_default">True</property>
- <property name="use_stock">True</property>
- </object>
- <packing>
- <property name="expand">False</property>
- <property name="fill">False</property>
- <property name="position">1</property>
- </packing>
- </child>
- </object>
- <packing>
- <property name="expand">False</property>
- <property name="position">1</property>
- </packing>
+ <placeholder/>
</child>
</object>
<packing>
+ <property name="expand">True</property>
+ <property name="fill">True</property>
<property name="position">1</property>
</packing>
</child>
</object>
+ <object class="GtkListStore" id="tags_liststore">
+ <columns>
+ <!-- column-name name -->
+ <column type="gchararray"/>
+ <!-- column-name selected -->
+ <column type="gboolean"/>
+ </columns>
+ </object>
</interface>
diff --git a/extensions/edit_metadata/dlg-edit-metadata.c b/extensions/edit_metadata/dlg-edit-metadata.c
index 42d1039..be378ca 100644
--- a/extensions/edit_metadata/dlg-edit-metadata.c
+++ b/extensions/edit_metadata/dlg-edit-metadata.c
@@ -26,14 +26,14 @@
#include "gth-edit-metadata-dialog.h"
-#define UPDATE_SELECTION_DELAY 300
-#define EDIT_METADATA_DIALOG_NAME "dlg-edit-metadata"
+#define UPDATE_SELECTION_DELAY 300
typedef struct {
int ref;
GthBrowser *browser;
GtkWidget *dialog;
+ char *dialog_name;
GList *file_list; /* GthFileData list */
GList *parents;
gboolean never_shown;
@@ -80,9 +80,10 @@ dialog_data_unref (DialogData *data)
}
cancel_file_list_loading (data);
- gth_browser_set_dialog (data->browser, EDIT_METADATA_DIALOG_NAME, NULL);
+ gth_browser_set_dialog (data->browser, data->dialog_name, NULL);
gtk_widget_destroy (data->dialog);
+ g_free (data->dialog_name);
_g_object_list_unref (data->file_list);
_g_object_list_unref (data->parents);
g_free (data);
@@ -149,6 +150,11 @@ edit_metadata_dialog__response_cb (GtkDialog *dialog,
GList *scan;
GthTask *task;
+ if (response == GTK_RESPONSE_HELP) {
+ show_help_dialog (GTK_WINDOW (dialog), data->dialog_name);
+ return;
+ }
+
if ((response != GTK_RESPONSE_OK) && (response != GTK_RESPONSE_APPLY)) {
cancel_file_list_loading (data);
close_dialog (data);
@@ -234,6 +240,7 @@ loader_completed_cb (GthTask *task,
_g_object_list_unref (data->file_list);
data->file_list = _g_object_list_ref (gth_load_file_data_task_get_result (GTH_LOAD_FILE_DATA_TASK (task)));
+
gth_edit_metadata_dialog_set_file_list (GTH_EDIT_METADATA_DIALOG (data->dialog), data->file_list);
gtk_window_set_transient_for (GTK_WINDOW (data->dialog), GTK_WINDOW (data->browser));
@@ -293,22 +300,25 @@ file_selection_changed_cb (GthFileSelection *self,
void
-dlg_edit_metadata (GthBrowser *browser)
+dlg_edit_metadata (GthBrowser *browser,
+ GType dialog_type,
+ const char *dialog_name)
{
DialogData *data;
- if (gth_browser_get_dialog (browser, EDIT_METADATA_DIALOG_NAME)) {
- gtk_window_present (GTK_WINDOW (gth_browser_get_dialog (browser, EDIT_METADATA_DIALOG_NAME)));
+ if (gth_browser_get_dialog (browser, dialog_name)) {
+ gtk_window_present (GTK_WINDOW (gth_browser_get_dialog (browser, dialog_name)));
return;
}
data = g_new0 (DialogData, 1);
data->ref = 1;
data->browser = browser;
- data->dialog = gth_edit_metadata_dialog_new ();
+ data->dialog = g_object_new (dialog_type, 0);
+ data->dialog_name = g_strdup (dialog_name);
data->never_shown = TRUE;
- gth_browser_set_dialog (browser, EDIT_METADATA_DIALOG_NAME, data->dialog);
+ gth_browser_set_dialog (browser, data->dialog_name, data->dialog);
g_signal_connect (G_OBJECT (data->dialog),
"delete-event",
diff --git a/extensions/edit_metadata/dlg-edit-metadata.h b/extensions/edit_metadata/dlg-edit-metadata.h
index fc5424b..697dd84 100644
--- a/extensions/edit_metadata/dlg-edit-metadata.h
+++ b/extensions/edit_metadata/dlg-edit-metadata.h
@@ -24,6 +24,8 @@
#include <gthumb.h>
-void dlg_edit_metadata (GthBrowser *browser);
+void dlg_edit_metadata (GthBrowser *browser,
+ GType dialog_type,
+ const char *dialog_name);
#endif /* DLG_EDIT_METADATA_H */
diff --git a/extensions/edit_metadata/gth-edit-comment-dialog.c b/extensions/edit_metadata/gth-edit-comment-dialog.c
new file mode 100644
index 0000000..00b1dbc
--- /dev/null
+++ b/extensions/edit_metadata/gth-edit-comment-dialog.c
@@ -0,0 +1,217 @@
+/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */
+
+/*
+ * GThumb
+ *
+ * Copyright (C) 2009 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, see <http://www.gnu.org/licenses/>.
+ */
+
+#include <config.h>
+#include <glib/gi18n.h>
+#include "gth-edit-comment-dialog.h"
+#include "gth-edit-metadata-dialog.h"
+
+
+struct _GthEditCommentDialogPrivate {
+ GtkWidget *notebook;
+ GtkWidget *save_changed_checkbutton;
+};
+
+
+static void gth_edit_comment_dialog_gth_edit_metadata_dialog_interface_init (GthEditMetadataDialogInterface *iface);
+
+
+G_DEFINE_TYPE_WITH_CODE (GthEditCommentDialog,
+ gth_edit_comment_dialog,
+ GTK_TYPE_DIALOG,
+ G_IMPLEMENT_INTERFACE (GTH_TYPE_EDIT_METADATA_DIALOG,
+ gth_edit_comment_dialog_gth_edit_metadata_dialog_interface_init))
+
+
+
+static void
+gth_edit_comment_dialog_set_file_list (GthEditMetadataDialog *base,
+ GList *file_list)
+{
+ GthEditCommentDialog *self = GTH_EDIT_COMMENT_DIALOG (base);
+ int n_files;
+ char *title;
+ GList *pages;
+ GList *scan;
+
+ n_files = g_list_length (file_list);
+
+ /* update the title */
+
+ if (n_files == 1) {
+ GthFileData *file_data = file_list->data;
+
+ /* Translators: the %s symbol in the string is a file name */
+ title = g_strdup_printf (_("%s Metadata"), g_file_info_get_display_name (file_data->info));
+ }
+ else
+ title = g_strdup_printf (g_dngettext (NULL, "%d file", "%d files", n_files), n_files);
+ gtk_window_set_title (GTK_WINDOW (self), title);
+ g_free (title);
+
+ /* update the widgets */
+
+ gtk_toggle_button_set_active (GTK_TOGGLE_BUTTON (self->priv->save_changed_checkbutton), n_files > 1);
+ gtk_widget_set_sensitive (self->priv->save_changed_checkbutton, n_files > 1);
+
+ pages = gtk_container_get_children (GTK_CONTAINER (self->priv->notebook));
+ for (scan = pages; scan; scan = scan->next)
+ gth_edit_comment_page_set_file_list (GTH_EDIT_COMMENT_PAGE (scan->data), file_list);
+
+ gtk_dialog_set_response_sensitive (GTK_DIALOG (self),
+ GTK_RESPONSE_APPLY,
+ n_files > 0);
+ gtk_dialog_set_response_sensitive (GTK_DIALOG (self),
+ GTK_RESPONSE_OK,
+ n_files > 0);
+
+ g_list_free (pages);
+}
+
+
+static void
+gth_edit_comment_dialog_update_info (GthEditMetadataDialog *base,
+ GList *file_list /* GthFileData list */)
+{
+ GthEditCommentDialog *self = GTH_EDIT_COMMENT_DIALOG (base);
+ gboolean only_modified_fields;
+ GList *pages;
+ GList *scan;
+
+ only_modified_fields = gtk_toggle_button_get_active (GTK_TOGGLE_BUTTON (self->priv->save_changed_checkbutton));
+ pages = gtk_container_get_children (GTK_CONTAINER (self->priv->notebook));
+ for (scan = pages; scan; scan = scan->next) {
+ GList *scan_file;
+
+ for (scan_file = file_list; scan_file; scan_file = scan_file->next) {
+ GthFileData *file_data = scan_file->data;
+ gth_edit_comment_page_update_info (GTH_EDIT_COMMENT_PAGE (scan->data), file_data->info, only_modified_fields);
+ }
+ }
+
+ g_list_free (pages);
+}
+
+
+static void
+gth_edit_comment_dialog_gth_edit_metadata_dialog_interface_init (GthEditMetadataDialogInterface *iface)
+{
+ iface->set_file_list = gth_edit_comment_dialog_set_file_list;
+ iface->update_info = gth_edit_comment_dialog_update_info;
+}
+
+
+static void
+gth_edit_comment_dialog_class_init (GthEditCommentDialogClass *klass)
+{
+ g_type_class_add_private (klass, sizeof (GthEditCommentDialogPrivate));
+}
+
+
+static void
+gth_edit_comment_dialog_init (GthEditCommentDialog *self)
+{
+ GtkWidget *vbox;
+ GArray *pages;
+ int i;
+
+ self->priv = G_TYPE_INSTANCE_GET_PRIVATE (self, GTH_TYPE_EDIT_COMMENT_DIALOG, GthEditCommentDialogPrivate);
+
+ gtk_window_set_resizable (GTK_WINDOW (self), TRUE);
+ gtk_box_set_spacing (GTK_BOX (gtk_dialog_get_content_area (GTK_DIALOG (self))), 5);
+ gtk_container_set_border_width (GTK_CONTAINER (self), 5);
+
+ gtk_dialog_add_button (GTK_DIALOG (self), GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL);
+ gtk_dialog_add_button (GTK_DIALOG (self), GTK_STOCK_SAVE, GTK_RESPONSE_APPLY);
+ gtk_dialog_add_button (GTK_DIALOG (self), _("Sa_ve and Close"), GTK_RESPONSE_OK);
+ gtk_dialog_add_button (GTK_DIALOG (self), GTK_STOCK_HELP, GTK_RESPONSE_HELP);
+
+ vbox = gtk_box_new (GTK_ORIENTATION_VERTICAL, 6);
+ gtk_container_set_border_width (GTK_CONTAINER (vbox), 5);
+ gtk_widget_show (vbox);
+ gtk_box_pack_start (GTK_BOX (gtk_dialog_get_content_area (GTK_DIALOG (self))), vbox, TRUE, TRUE, 0);
+
+ self->priv->notebook = gtk_notebook_new ();
+ gtk_widget_show (self->priv->notebook);
+ gtk_box_pack_start (GTK_BOX (vbox), self->priv->notebook, TRUE, TRUE, 0);
+
+ self->priv->save_changed_checkbutton = gtk_check_button_new_with_mnemonic (_("Save only cha_nged fields"));
+ gtk_widget_show (self->priv->save_changed_checkbutton);
+ gtk_box_pack_start (GTK_BOX (vbox), self->priv->save_changed_checkbutton, FALSE, FALSE, 0);
+
+ pages = gth_main_get_type_set ("edit-comment-dialog-page");
+ if (pages == NULL)
+ return;
+
+ for (i = 0; i < pages->len; i++) {
+ GType page_type;
+ GtkWidget *page;
+
+ page_type = g_array_index (pages, GType, i);
+ page = g_object_new (page_type, NULL);
+ if (! GTH_IS_EDIT_COMMENT_PAGE (page)) {
+ g_object_unref (page);
+ continue;
+ }
+
+ gtk_widget_show (page);
+ gtk_notebook_append_page (GTK_NOTEBOOK (self->priv->notebook),
+ page,
+ gtk_label_new (gth_edit_comment_page_get_name (GTH_EDIT_COMMENT_PAGE (page))));
+ }
+}
+
+
+/* -- gth_edit_comment_dialog_page -- */
+
+
+G_DEFINE_INTERFACE (GthEditCommentPage, gth_edit_comment_page, 0)
+
+
+static void
+gth_edit_comment_page_default_init (GthEditCommentPageInterface *iface)
+{
+ /* void */
+}
+
+
+void
+gth_edit_comment_page_set_file_list (GthEditCommentPage *self,
+ GList *file_list)
+{
+ GTH_EDIT_COMMENT_PAGE_GET_INTERFACE (self)->set_file_list (self, file_list);
+}
+
+
+void
+gth_edit_comment_page_update_info (GthEditCommentPage *self,
+ GFileInfo *info,
+ gboolean only_modified_fields)
+{
+ GTH_EDIT_COMMENT_PAGE_GET_INTERFACE (self)->update_info (self, info, only_modified_fields);
+}
+
+
+const char *
+gth_edit_comment_page_get_name (GthEditCommentPage *self)
+{
+ return GTH_EDIT_COMMENT_PAGE_GET_INTERFACE (self)->get_name (self);
+}
diff --git a/extensions/edit_metadata/gth-edit-comment-dialog.h b/extensions/edit_metadata/gth-edit-comment-dialog.h
new file mode 100644
index 0000000..ee40b28
--- /dev/null
+++ b/extensions/edit_metadata/gth-edit-comment-dialog.h
@@ -0,0 +1,84 @@
+/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */
+
+/*
+ * GThumb
+ *
+ * Copyright (C) 2009 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, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifndef GTH_EDIT_COMMENT_DIALOG_H
+#define GTH_EDIT_COMMENT_DIALOG_H
+
+#include <gtk/gtk.h>
+#include <gthumb.h>
+
+G_BEGIN_DECLS
+
+#define GTH_TYPE_EDIT_COMMENT_DIALOG (gth_edit_comment_dialog_get_type ())
+#define GTH_EDIT_COMMENT_DIALOG(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), GTH_TYPE_EDIT_COMMENT_DIALOG, GthEditCommentDialog))
+#define GTH_EDIT_COMMENT_DIALOG_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), GTH_TYPE_EDIT_COMMENT_DIALOG, GthEditCommentDialogClass))
+#define GTH_IS_EDIT_COMMENT_DIALOG(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), GTH_TYPE_EDIT_COMMENT_DIALOG))
+#define GTH_IS_EDIT_COMMENT_DIALOG_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), GTH_TYPE_EDIT_COMMENT_DIALOG))
+#define GTH_EDIT_COMMENT_DIALOG_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), GTH_TYPE_EDIT_COMMENT_DIALOG, GthEditCommentDialogClass))
+
+#define GTH_TYPE_EDIT_COMMENT_PAGE (gth_edit_comment_page_get_type ())
+#define GTH_EDIT_COMMENT_PAGE(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), GTH_TYPE_EDIT_COMMENT_PAGE, GthEditCommentPage))
+#define GTH_IS_EDIT_COMMENT_PAGE(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), GTH_TYPE_EDIT_COMMENT_PAGE))
+#define GTH_EDIT_COMMENT_PAGE_GET_INTERFACE(obj) (G_TYPE_INSTANCE_GET_INTERFACE ((obj), GTH_TYPE_EDIT_COMMENT_PAGE, GthEditCommentPageInterface))
+
+typedef struct _GthEditCommentDialog GthEditCommentDialog;
+typedef struct _GthEditCommentDialogClass GthEditCommentDialogClass;
+typedef struct _GthEditCommentDialogPrivate GthEditCommentDialogPrivate;
+
+struct _GthEditCommentDialog {
+ GtkDialog parent_instance;
+ GthEditCommentDialogPrivate *priv;
+};
+
+struct _GthEditCommentDialogClass {
+ GtkDialogClass parent_class;
+};
+
+typedef struct _GthEditCommentPage GthEditCommentPage;
+typedef struct _GthEditCommentPageInterface GthEditCommentPageInterface;
+
+struct _GthEditCommentPageInterface {
+ GTypeInterface parent_iface;
+ void (*set_file_list) (GthEditCommentPage *self,
+ GList *file_list /* GthFileData list */);
+ void (*update_info) (GthEditCommentPage *self,
+ GFileInfo *info,
+ gboolean only_modified_fields);
+ const char * (*get_name) (GthEditCommentPage *self);
+};
+
+/* GthEditCommentDialog */
+
+GType gth_edit_comment_dialog_get_type (void);
+
+/* GthEditCommentPage */
+
+GType gth_edit_comment_page_get_type (void);
+void gth_edit_comment_page_set_file_list (GthEditCommentPage *self,
+ GList *file_list /* GthFileData list */);
+void gth_edit_comment_page_update_info (GthEditCommentPage *self,
+ GFileInfo *info,
+ gboolean only_modified_fields);
+const char * gth_edit_comment_page_get_name (GthEditCommentPage *self);
+
+G_END_DECLS
+
+#endif /* GTH_EDIT_COMMENT_DIALOG_H */
diff --git a/extensions/edit_metadata/gth-edit-comment-page.c b/extensions/edit_metadata/gth-edit-general-page.c
similarity index 85%
rename from extensions/edit_metadata/gth-edit-comment-page.c
rename to extensions/edit_metadata/gth-edit-general-page.c
index eaee343..2468e1e 100644
--- a/extensions/edit_metadata/gth-edit-comment-page.c
+++ b/extensions/edit_metadata/gth-edit-general-page.c
@@ -22,11 +22,10 @@
#include <config.h>
#include <glib/gi18n.h>
#include <gio/gio.h>
-#include "gth-edit-comment-page.h"
-#include "gth-edit-metadata-dialog.h"
+#include "gth-edit-comment-dialog.h"
+#include "gth-edit-general-page.h"
-#define GTH_EDIT_COMMENT_PAGE_GET_PRIVATE(o) (G_TYPE_INSTANCE_GET_PRIVATE ((o), GTH_TYPE_EDIT_COMMENT_PAGE, GthEditCommentPagePrivate))
#define GET_WIDGET(name) _gtk_builder_get_widget (self->priv->builder, (name))
@@ -41,7 +40,7 @@ typedef enum {
} DateOption;
-struct _GthEditCommentPagePrivate {
+struct _GthEditGeneralPagePrivate {
GFileInfo *info;
GtkBuilder *builder;
GtkWidget *date_combobox;
@@ -51,21 +50,21 @@ struct _GthEditCommentPagePrivate {
};
-static void gth_edit_comment_page_gth_edit_comment_page_interface_init (GthEditMetadataPageInterface *iface);
+static void gth_edit_general_page_gth_edit_general_page_interface_init (GthEditCommentPageInterface *iface);
-G_DEFINE_TYPE_WITH_CODE (GthEditCommentPage,
- gth_edit_comment_page,
+G_DEFINE_TYPE_WITH_CODE (GthEditGeneralPage,
+ gth_edit_general_page,
GTK_TYPE_VBOX,
- G_IMPLEMENT_INTERFACE (GTH_TYPE_EDIT_METADATA_PAGE,
- gth_edit_comment_page_gth_edit_comment_page_interface_init))
+ G_IMPLEMENT_INTERFACE (GTH_TYPE_EDIT_COMMENT_PAGE,
+ gth_edit_general_page_gth_edit_general_page_interface_init))
void
-gth_edit_comment_page_real_set_file_list (GthEditMetadataPage *base,
- GList *file_list)
+gth_edit_general_page_real_set_file_list (GthEditCommentPage *base,
+ GList *file_list)
{
- GthEditCommentPage *self;
+ GthEditGeneralPage *self;
GtkTextBuffer *buffer;
GthMetadata *metadata;
GthStringList *tags;
@@ -74,7 +73,7 @@ gth_edit_comment_page_real_set_file_list (GthEditMetadataPage *base,
GthFileData *file_data;
const char *mime_type;
- self = GTH_EDIT_COMMENT_PAGE (base);
+ self = GTH_EDIT_GENERAL_PAGE (base);
_g_object_unref (self->priv->info);
self->priv->info = gth_file_data_list_get_common_info (file_list, "general::description,general::title,general::location,general::datetime,general::tags,general::rating");
@@ -123,12 +122,12 @@ gth_edit_comment_page_real_set_file_list (GthEditMetadataPage *base,
char *value;
value = gth_string_list_join (tags, ",");
- gth_tags_entry_set_text (GTH_TAGS_ENTRY (self->priv->tags_entry), value);
+ gth_tags_entry_set_tags_from_text (GTH_TAGS_ENTRY (self->priv->tags_entry), value);
g_free (value);
}
else
- gth_tags_entry_set_text (GTH_TAGS_ENTRY (self->priv->tags_entry), NULL);
+ gth_tags_entry_set_tags_from_text (GTH_TAGS_ENTRY (self->priv->tags_entry), NULL);
metadata = (GthMetadata *) g_file_info_get_attribute_object (self->priv->info, "general::rating");
if (metadata != NULL) {
@@ -198,7 +197,7 @@ gth_edit_comment_page_real_set_file_list (GthEditMetadataPage *base,
static char *
-get_date_from_option (GthEditCommentPage *self,
+get_date_from_option (GthEditGeneralPage *self,
DateOption option,
GFileInfo *info)
{
@@ -259,24 +258,24 @@ get_date_from_option (GthEditCommentPage *self,
void
-gth_edit_comment_page_real_update_info (GthEditMetadataPage *base,
- GFileInfo *info,
- gboolean only_modified_fields)
+gth_edit_general_page_real_update_info (GthEditCommentPage *base,
+ GFileInfo *info,
+ gboolean only_modified_fields)
{
- GthEditCommentPage *self;
- GthFileData *file_data;
- GtkTextBuffer *buffer;
- GtkTextIter start;
- GtkTextIter end;
- char *text;
- GthMetadata *metadata;
- int i;
- char **tagv;
- GList *tags;
- GthStringList *string_list;
- char *s;
-
- self = GTH_EDIT_COMMENT_PAGE (base);
+ GthEditGeneralPage *self;
+ GthFileData *file_data;
+ GtkTextBuffer *buffer;
+ GtkTextIter start;
+ GtkTextIter end;
+ char *text;
+ GthMetadata *metadata;
+ int i;
+ char **tagv;
+ GList *tags;
+ GthStringList *string_list;
+ char *s;
+
+ self = GTH_EDIT_GENERAL_PAGE (base);
file_data = gth_file_data_new (NULL, self->priv->info);
@@ -325,9 +324,11 @@ gth_edit_comment_page_real_update_info (GthEditMetadataPage *base,
switch (gtk_combo_box_get_active (GTK_COMBO_BOX (self->priv->date_combobox))) {
case NO_CHANGE:
break;
+
case NO_DATE:
g_file_info_remove_attribute (info, "general::datetime");
break;
+
default:
{
char *exif_date;
@@ -398,32 +399,32 @@ gth_edit_comment_page_real_update_info (GthEditMetadataPage *base,
const char *
-gth_edit_comment_page_real_get_name (GthEditMetadataPage *self)
+gth_edit_general_page_real_get_name (GthEditCommentPage *self)
{
return _("General");
}
static void
-gth_edit_comment_page_finalize (GObject *object)
+gth_edit_general_page_finalize (GObject *object)
{
- GthEditCommentPage *self;
+ GthEditGeneralPage *self;
- self = GTH_EDIT_COMMENT_PAGE (object);
+ self = GTH_EDIT_GENERAL_PAGE (object);
_g_object_unref (self->priv->info);
g_object_unref (self->priv->builder);
- G_OBJECT_CLASS (gth_edit_comment_page_parent_class)->finalize (object);
+ G_OBJECT_CLASS (gth_edit_general_page_parent_class)->finalize (object);
}
static void
-gth_edit_comment_page_class_init (GthEditCommentPageClass *klass)
+gth_edit_general_page_class_init (GthEditGeneralPageClass *klass)
{
- g_type_class_add_private (klass, sizeof (GthEditCommentPagePrivate));
+ g_type_class_add_private (klass, sizeof (GthEditGeneralPagePrivate));
- G_OBJECT_CLASS (klass)->finalize = gth_edit_comment_page_finalize;
+ G_OBJECT_CLASS (klass)->finalize = gth_edit_general_page_finalize;
}
@@ -431,7 +432,7 @@ static void
date_combobox_changed_cb (GtkComboBox *widget,
gpointer user_data)
{
- GthEditCommentPage *self = user_data;
+ GthEditGeneralPage *self = user_data;
char *value;
value = get_date_from_option (self, gtk_combo_box_get_active (widget), self->priv->info);
@@ -444,7 +445,7 @@ date_combobox_changed_cb (GtkComboBox *widget,
static void
tags_entry_list_collapsed_cb (GthTagsEntry *widget,
- gpointer user_data)
+ gpointer user_data)
{
GtkWidget *toplevel;
int width;
@@ -461,9 +462,9 @@ tags_entry_list_collapsed_cb (GthTagsEntry *widget,
static void
-gth_edit_comment_page_init (GthEditCommentPage *self)
+gth_edit_general_page_init (GthEditGeneralPage *self)
{
- self->priv = GTH_EDIT_COMMENT_PAGE_GET_PRIVATE (self);
+ self->priv = G_TYPE_INSTANCE_GET_PRIVATE (self, GTH_TYPE_EDIT_GENERAL_PAGE, GthEditGeneralPagePrivate);
self->priv->info = NULL;
gtk_container_set_border_width (GTK_CONTAINER (self), 12);
@@ -507,9 +508,9 @@ gth_edit_comment_page_init (GthEditCommentPage *self)
static void
-gth_edit_comment_page_gth_edit_comment_page_interface_init (GthEditMetadataPageInterface *iface)
+gth_edit_general_page_gth_edit_general_page_interface_init (GthEditCommentPageInterface *iface)
{
- iface->set_file_list = gth_edit_comment_page_real_set_file_list;
- iface->update_info = gth_edit_comment_page_real_update_info;
- iface->get_name = gth_edit_comment_page_real_get_name;
+ iface->set_file_list = gth_edit_general_page_real_set_file_list;
+ iface->update_info = gth_edit_general_page_real_update_info;
+ iface->get_name = gth_edit_general_page_real_get_name;
}
diff --git a/extensions/edit_metadata/gth-edit-general-page.h b/extensions/edit_metadata/gth-edit-general-page.h
new file mode 100644
index 0000000..0398daa
--- /dev/null
+++ b/extensions/edit_metadata/gth-edit-general-page.h
@@ -0,0 +1,53 @@
+/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */
+
+/*
+ * GThumb
+ *
+ * Copyright (C) 2009 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, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifndef GTH_EDIT_GENERAL_PAGE_H
+#define GTH_EDIT_GENERAL_PAGE_H
+
+#include <glib.h>
+#include <glib-object.h>
+#include <gthumb.h>
+
+#define GTH_TYPE_EDIT_GENERAL_PAGE (gth_edit_general_page_get_type ())
+#define GTH_EDIT_GENERAL_PAGE(o) (G_TYPE_CHECK_INSTANCE_CAST ((o), GTH_TYPE_EDIT_GENERAL_PAGE, GthEditGeneralPage))
+#define GTH_EDIT_GENERAL_PAGE_CLASS(k) (G_TYPE_CHECK_CLASS_CAST ((k), GTH_TYPE_EDIT_GENERAL_PAGE, GthEditGeneralPageClass))
+#define GTH_IS_EDIT_GENERAL_PAGE(o) (G_TYPE_CHECK_INSTANCE_TYPE ((o), GTH_TYPE_EDIT_GENERAL_PAGE))
+#define GTH_IS_EDIT_GENERAL_PAGE_CLASS(k) (G_TYPE_CHECK_CLASS_TYPE ((k), GTH_TYPE_EDIT_GENERAL_PAGE))
+#define GTH_EDIT_GENERAL_PAGE_GET_CLASS(o) (G_TYPE_INSTANCE_GET_CLASS((o), GTH_TYPE_EDIT_GENERAL_PAGE, GthEditGeneralPageClass))
+
+typedef struct _GthEditGeneralPage GthEditGeneralPage;
+typedef struct _GthEditGeneralPagePrivate GthEditGeneralPagePrivate;
+typedef struct _GthEditGeneralPageClass GthEditGeneralPageClass;
+
+struct _GthEditGeneralPage
+{
+ GtkVBox __parent;
+ GthEditGeneralPagePrivate *priv;
+};
+
+struct _GthEditGeneralPageClass
+{
+ GtkVBoxClass __parent_class;
+};
+
+GType gth_edit_general_page_get_type (void) G_GNUC_CONST;
+
+#endif /* GTH_EDIT_GENERAL_PAGE_H */
diff --git a/extensions/edit_metadata/gth-edit-metadata-dialog.c b/extensions/edit_metadata/gth-edit-metadata-dialog.c
index fcc5912..6621ec5 100644
--- a/extensions/edit_metadata/gth-edit-metadata-dialog.c
+++ b/extensions/edit_metadata/gth-edit-metadata-dialog.c
@@ -3,7 +3,7 @@
/*
* GThumb
*
- * Copyright (C) 2009 Free Software Foundation, Inc.
+ * Copyright (C) 2011 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
@@ -20,182 +20,30 @@
*/
#include <config.h>
-#include <glib/gi18n.h>
#include "gth-edit-metadata-dialog.h"
-G_DEFINE_TYPE (GthEditMetadataDialog, gth_edit_metadata_dialog, GTK_TYPE_DIALOG)
-
-
-struct _GthEditMetadataDialogPrivate {
- GtkWidget *notebook;
- GtkWidget *save_changed_checkbutton;
-};
-
-
-static void
-gth_edit_metadata_dialog_class_init (GthEditMetadataDialogClass *klass)
-{
- g_type_class_add_private (klass, sizeof (GthEditMetadataDialogPrivate));
-}
+G_DEFINE_INTERFACE (GthEditMetadataDialog, gth_edit_metadata_dialog, 0)
static void
-gth_edit_metadata_dialog_init (GthEditMetadataDialog *self)
-{
- GtkWidget *vbox;
- GArray *pages;
- int i;
-
- self->priv = G_TYPE_INSTANCE_GET_PRIVATE (self, GTH_TYPE_EDIT_METADATA_DIALOG, GthEditMetadataDialogPrivate);
-
- gtk_window_set_resizable (GTK_WINDOW (self), TRUE);
- gtk_box_set_spacing (GTK_BOX (gtk_dialog_get_content_area (GTK_DIALOG (self))), 5);
- gtk_container_set_border_width (GTK_CONTAINER (self), 5);
-
- gtk_dialog_add_button (GTK_DIALOG (self), GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL);
- gtk_dialog_add_button (GTK_DIALOG (self), GTK_STOCK_SAVE, GTK_RESPONSE_APPLY);
- gtk_dialog_add_button (GTK_DIALOG (self), _("Sa_ve and Close"), GTK_RESPONSE_OK);
-
- vbox = gtk_box_new (GTK_ORIENTATION_VERTICAL, 6);
- gtk_container_set_border_width (GTK_CONTAINER (vbox), 5);
- gtk_widget_show (vbox);
- gtk_box_pack_start (GTK_BOX (gtk_dialog_get_content_area (GTK_DIALOG (self))), vbox, TRUE, TRUE, 0);
-
- self->priv->notebook = gtk_notebook_new ();
- gtk_widget_show (self->priv->notebook);
- gtk_box_pack_start (GTK_BOX (vbox), self->priv->notebook, TRUE, TRUE, 0);
-
- self->priv->save_changed_checkbutton = gtk_check_button_new_with_mnemonic (_("Save only cha_nged fields"));
- gtk_widget_show (self->priv->save_changed_checkbutton);
- gtk_box_pack_start (GTK_BOX (vbox), self->priv->save_changed_checkbutton, FALSE, FALSE, 0);
-
- pages = gth_main_get_type_set ("edit-metadata-dialog-page");
- if (pages == NULL)
- return;
-
- for (i = 0; i < pages->len; i++) {
- GType page_type;
- GtkWidget *page;
-
- page_type = g_array_index (pages, GType, i);
- page = g_object_new (page_type, NULL);
- if (! GTH_IS_EDIT_METADATA_PAGE (page)) {
- g_object_unref (page);
- continue;
- }
-
- gtk_widget_show (page);
- gtk_notebook_append_page (GTK_NOTEBOOK (self->priv->notebook),
- page,
- gtk_label_new (gth_edit_metadata_page_get_name (GTH_EDIT_METADATA_PAGE (page))));
- }
-}
-
-
-GtkWidget *
-gth_edit_metadata_dialog_new (void)
-{
- return g_object_new (GTH_TYPE_EDIT_METADATA_DIALOG, NULL);
-}
-
-
-void
-gth_edit_metadata_dialog_set_file_list (GthEditMetadataDialog *dialog,
- GList *file_list)
-{
- int n_files;
- char *title;
- GList *pages;
- GList *scan;
-
- n_files = g_list_length (file_list);
- if (n_files == 1) {
- GthFileData *file_data = file_list->data;
-
- /* Translators: the %s symbol in the string is a file name */
- title = g_strdup_printf (_("%s Metadata"), g_file_info_get_display_name (file_data->info));
- gtk_window_set_title (GTK_WINDOW (dialog), title);
- }
- else {
- title = g_strdup_printf (g_dngettext (NULL, "%d file", "%d files", n_files), n_files);
- gtk_window_set_title (GTK_WINDOW (dialog), title);
- }
-
- gtk_toggle_button_set_active (GTK_TOGGLE_BUTTON (dialog->priv->save_changed_checkbutton), n_files > 1);
- gtk_widget_set_sensitive (dialog->priv->save_changed_checkbutton, n_files > 1);
-
- pages = gtk_container_get_children (GTK_CONTAINER (dialog->priv->notebook));
- for (scan = pages; scan; scan = scan->next)
- gth_edit_metadata_page_set_file_list (GTH_EDIT_METADATA_PAGE (scan->data), file_list);
-
- gtk_dialog_set_response_sensitive (GTK_DIALOG (dialog),
- GTK_RESPONSE_APPLY,
- n_files > 0);
- gtk_dialog_set_response_sensitive (GTK_DIALOG (dialog),
- GTK_RESPONSE_OK,
- n_files > 0);
-
- g_list_free (pages);
- g_free (title);
-}
-
-
-void
-gth_edit_metadata_dialog_update_info (GthEditMetadataDialog *dialog,
- GList *file_list /* GthFileData list */)
-{
- gboolean only_modified_fields;
- GList *pages;
- GList *scan;
-
- only_modified_fields = gtk_toggle_button_get_active (GTK_TOGGLE_BUTTON (dialog->priv->save_changed_checkbutton));
- pages = gtk_container_get_children (GTK_CONTAINER (dialog->priv->notebook));
- for (scan = pages; scan; scan = scan->next) {
- GList *scan_file;
-
- for (scan_file = file_list; scan_file; scan_file = scan_file->next) {
- GthFileData *file_data = scan_file->data;
- gth_edit_metadata_page_update_info (GTH_EDIT_METADATA_PAGE (scan->data), file_data->info, only_modified_fields);
- }
- }
-
- g_list_free (pages);
-}
-
-
-/* -- gth_edit_metadata_dialog_page -- */
-
-
-G_DEFINE_INTERFACE (GthEditMetadataPage, gth_edit_metadata_page, 0)
-
-
-static void
-gth_edit_metadata_page_default_init (GthEditMetadataPageInterface *iface)
+gth_edit_metadata_dialog_default_init (GthEditMetadataDialogInterface *iface)
{
/* void */
}
void
-gth_edit_metadata_page_set_file_list (GthEditMetadataPage *self,
- GList *file_list)
+gth_edit_metadata_dialog_set_file_list (GthEditMetadataDialog *self,
+ GList *file_list)
{
- GTH_EDIT_METADATA_PAGE_GET_INTERFACE (self)->set_file_list (self, file_list);
+ GTH_EDIT_METADATA_DIALOG_GET_INTERFACE (self)->set_file_list (self, file_list);
}
void
-gth_edit_metadata_page_update_info (GthEditMetadataPage *self,
- GFileInfo *info,
- gboolean only_modified_fields)
-{
- GTH_EDIT_METADATA_PAGE_GET_INTERFACE (self)->update_info (self, info, only_modified_fields);
-}
-
-
-const char *
-gth_edit_metadata_page_get_name (GthEditMetadataPage *self)
+gth_edit_metadata_dialog_update_info (GthEditMetadataDialog *self,
+ GList *file_list)
{
- return GTH_EDIT_METADATA_PAGE_GET_INTERFACE (self)->get_name (self);
+ GTH_EDIT_METADATA_DIALOG_GET_INTERFACE (self)->update_info (self, file_list);
}
diff --git a/extensions/edit_metadata/gth-edit-metadata-dialog.h b/extensions/edit_metadata/gth-edit-metadata-dialog.h
index 9ae14eb..b7ed3c6 100644
--- a/extensions/edit_metadata/gth-edit-metadata-dialog.h
+++ b/extensions/edit_metadata/gth-edit-metadata-dialog.h
@@ -3,7 +3,7 @@
/*
* GThumb
*
- * Copyright (C) 2009 Free Software Foundation, Inc.
+ * Copyright (C) 2011 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
@@ -18,72 +18,40 @@
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
-
+
#ifndef GTH_EDIT_METADATA_DIALOG_H
#define GTH_EDIT_METADATA_DIALOG_H
#include <gtk/gtk.h>
-#include <gthumb.h>
G_BEGIN_DECLS
-#define GTH_TYPE_EDIT_METADATA_DIALOG (gth_edit_metadata_dialog_get_type ())
-#define GTH_EDIT_METADATA_DIALOG(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), GTH_TYPE_EDIT_METADATA_DIALOG, GthEditMetadataDialog))
-#define GTH_EDIT_METADATA_DIALOG_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), GTH_TYPE_EDIT_METADATA_DIALOG, GthEditMetadataDialogClass))
-#define GTH_IS_EDIT_METADATA_DIALOG(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), GTH_TYPE_EDIT_METADATA_DIALOG))
-#define GTH_IS_EDIT_METADATA_DIALOG_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), GTH_TYPE_EDIT_METADATA_DIALOG))
-#define GTH_EDIT_METADATA_DIALOG_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), GTH_TYPE_EDIT_METADATA_DIALOG, GthEditMetadataDialogClass))
-
-#define GTH_TYPE_EDIT_METADATA_PAGE (gth_edit_metadata_page_get_type ())
-#define GTH_EDIT_METADATA_PAGE(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), GTH_TYPE_EDIT_METADATA_PAGE, GthEditMetadataPage))
-#define GTH_IS_EDIT_METADATA_PAGE(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), GTH_TYPE_EDIT_METADATA_PAGE))
-#define GTH_EDIT_METADATA_PAGE_GET_INTERFACE(obj) (G_TYPE_INSTANCE_GET_INTERFACE ((obj), GTH_TYPE_EDIT_METADATA_PAGE, GthEditMetadataPageInterface))
+#define GTH_TYPE_EDIT_METADATA_DIALOG (gth_edit_metadata_dialog_get_type ())
+#define GTH_EDIT_METADATA_DIALOG(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), GTH_TYPE_EDIT_METADATA_DIALOG, GthEditMetadataDialog))
+#define GTH_IS_EDIT_METADATA_DIALOG(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), GTH_TYPE_EDIT_METADATA_DIALOG))
+#define GTH_EDIT_METADATA_DIALOG_GET_INTERFACE(obj) (G_TYPE_INSTANCE_GET_INTERFACE ((obj), GTH_TYPE_EDIT_METADATA_DIALOG, GthEditMetadataDialogInterface))
typedef struct _GthEditMetadataDialog GthEditMetadataDialog;
-typedef struct _GthEditMetadataDialogClass GthEditMetadataDialogClass;
-typedef struct _GthEditMetadataDialogPrivate GthEditMetadataDialogPrivate;
-
-struct _GthEditMetadataDialog {
- GtkDialog parent_instance;
- GthEditMetadataDialogPrivate *priv;
-};
-
-struct _GthEditMetadataDialogClass {
- GtkDialogClass parent_class;
-};
+typedef struct _GthEditMetadataDialogInterface GthEditMetadataDialogInterface;
-typedef struct _GthEditMetadataPage GthEditMetadataPage;
-typedef struct _GthEditMetadataPageInterface GthEditMetadataPageInterface;
-
-struct _GthEditMetadataPageInterface {
+struct _GthEditMetadataDialogInterface {
GTypeInterface parent_iface;
- void (*set_file_list) (GthEditMetadataPage *self,
- GList *file_list /* GthFileData list */);
- void (*update_info) (GthEditMetadataPage *self,
- GFileInfo *info,
- gboolean only_modified_fields);
- const char * (*get_name) (GthEditMetadataPage *self);
+
+ void (*set_file_list) (GthEditMetadataDialog *dialog,
+ GList *file_list /* GthFileData list */);
+ void (*update_info) (GthEditMetadataDialog *dialog,
+ GList *file_list /* GthFileData list */);
};
/* GthEditMetadataDialog */
GType gth_edit_metadata_dialog_get_type (void);
-GtkWidget * gth_edit_metadata_dialog_new (void);
void gth_edit_metadata_dialog_set_file_list (GthEditMetadataDialog *dialog,
GList *file_list /* GthFileData list */);
void gth_edit_metadata_dialog_update_info (GthEditMetadataDialog *dialog,
- GList *file_list /* GthFileData list */);
-
-/* GthEditMetadataPage */
-
-GType gth_edit_metadata_page_get_type (void);
-void gth_edit_metadata_page_set_file_list (GthEditMetadataPage *self,
- GList *file_list /* GthFileData list */);
-void gth_edit_metadata_page_update_info (GthEditMetadataPage *self,
- GFileInfo *info,
- gboolean only_modified_fields);
-const char * gth_edit_metadata_page_get_name (GthEditMetadataPage *self);
+ GList *file_list /* GthFileData list */);
G_END_DECLS
+
#endif /* GTH_EDIT_METADATA_DIALOG_H */
diff --git a/extensions/edit_metadata/gth-edit-tags-dialog.c b/extensions/edit_metadata/gth-edit-tags-dialog.c
new file mode 100644
index 0000000..c5d559c
--- /dev/null
+++ b/extensions/edit_metadata/gth-edit-tags-dialog.c
@@ -0,0 +1,272 @@
+/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */
+
+/*
+ * GThumb
+ *
+ * Copyright (C) 2011 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, see <http://www.gnu.org/licenses/>.
+ */
+
+#include <config.h>
+#include <glib/gi18n.h>
+#include "gth-edit-metadata-dialog.h"
+#include "gth-edit-tags-dialog.h"
+
+
+#define GET_WIDGET(name) _gtk_builder_get_widget (self->priv->builder, (name))
+
+
+struct _GthEditTagsDialogPrivate {
+ GtkBuilder *builder;
+ GtkWidget *tags_entry;
+};
+
+
+static void gth_edit_tags_dialog_gth_edit_metadata_dialog_interface_init (GthEditMetadataDialogInterface *iface);
+
+
+G_DEFINE_TYPE_WITH_CODE (GthEditTagsDialog,
+ gth_edit_tags_dialog,
+ GTK_TYPE_DIALOG,
+ G_IMPLEMENT_INTERFACE (GTH_TYPE_EDIT_METADATA_DIALOG,
+ gth_edit_tags_dialog_gth_edit_metadata_dialog_interface_init))
+
+
+static void
+gth_edit_tags_dialog_finalize (GObject *object)
+{
+ GthEditTagsDialog *self;
+
+ self = GTH_EDIT_TAGS_DIALOG (object);
+ _g_object_unref (self->priv->builder);
+
+ G_OBJECT_CLASS (gth_edit_tags_dialog_parent_class)->finalize (object);
+}
+
+
+static gboolean
+remove_tag_if_not_present (gpointer key,
+ gpointer value,
+ gpointer user_data)
+{
+ GthStringList *file_tags = user_data;
+
+ return g_list_find_custom (gth_string_list_get_list (file_tags), key, (GCompareFunc) g_strcmp0) == NULL;
+}
+
+
+static void
+gth_edit_tags_dialog_set_file_list (GthEditMetadataDialog *base,
+ GList *file_list)
+{
+ GthEditTagsDialog *self = GTH_EDIT_TAGS_DIALOG (base);
+ int n_files;
+ char *title;
+ GList *scan;
+ GHashTable *all_tags;
+ GHashTable *common_tags;
+ GHashTable *no_common_tags;
+ GList *all_tags_list;
+ GList *scan_tags;
+ GList *common_tags_list;
+ GList *no_common_tags_list;
+
+ n_files = g_list_length (file_list);
+
+ /* update the title */
+
+ if (n_files == 1) {
+ GthFileData *file_data = file_list->data;
+
+ /* Translators: the %s symbol in the string is a file name */
+ title = g_strdup_printf (_("%s Tags"), g_file_info_get_display_name (file_data->info));
+ }
+ else
+ title = g_strdup_printf (g_dngettext (NULL, "%d file", "%d files", n_files), n_files);
+ gtk_window_set_title (GTK_WINDOW (self), title);
+
+ g_free (title);
+
+ /* update the tag entry */
+
+ all_tags = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, NULL);
+ common_tags = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, NULL);
+ for (scan = file_list; scan; scan = scan->next) {
+ GthFileData *file_data = scan->data;
+ GthStringList *file_tags;
+
+ file_tags = (GthStringList *) g_file_info_get_attribute_object (file_data->info, "general::tags");
+ if (file_tags != NULL) {
+ GList *scan_tags;
+
+ for (scan_tags = gth_string_list_get_list (file_tags);
+ scan_tags != NULL;
+ scan_tags = scan_tags->next)
+ {
+ char *tag = scan_tags->data;
+
+ /* update the all tags set */
+
+ if (g_hash_table_lookup (all_tags, tag) == NULL)
+ g_hash_table_insert (all_tags, g_strdup (tag), GINT_TO_POINTER (1));
+
+ /* update the common tags set */
+
+ if (scan == file_list)
+ g_hash_table_insert (common_tags, g_strdup (tag), GINT_TO_POINTER (1));
+ else
+ g_hash_table_foreach_remove (common_tags, remove_tag_if_not_present, file_tags);
+ }
+ }
+ else
+ g_hash_table_remove_all (common_tags);
+ }
+
+ no_common_tags = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, NULL);
+ all_tags_list = g_hash_table_get_keys (all_tags);
+ for (scan_tags = all_tags_list; scan_tags; scan_tags = scan_tags->next) {
+ char *tag = scan_tags->data;
+
+ if (g_hash_table_lookup (common_tags, tag) == NULL)
+ g_hash_table_insert (no_common_tags, g_strdup (tag), GINT_TO_POINTER (1));
+ }
+
+ common_tags_list = g_hash_table_get_keys (common_tags);
+ no_common_tags_list = g_hash_table_get_keys (no_common_tags);
+ gth_tags_entry_set_tag_list (GTH_TAGS_ENTRY (self->priv->tags_entry),
+ common_tags_list,
+ no_common_tags_list);
+
+ g_list_free (no_common_tags_list);
+ g_list_free (common_tags_list);
+ g_list_free (all_tags_list);
+ g_hash_table_unref (no_common_tags);
+ g_hash_table_unref (common_tags);
+ g_hash_table_unref (all_tags);
+}
+
+
+static GHashTable *
+_g_hash_table_from_string_list (GthStringList *list)
+{
+ GHashTable *h;
+ GList *scan;
+
+ h = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, NULL);
+ for (scan = gth_string_list_get_list (list); scan; scan = scan->next)
+ g_hash_table_insert (h, g_strdup (scan->data), GINT_TO_POINTER (1));
+
+ return h;
+}
+
+
+static void
+gth_edit_tags_dialog_update_info (GthEditMetadataDialog *base,
+ GList *file_list /* GthFileData list */)
+{
+ GthEditTagsDialog *self = GTH_EDIT_TAGS_DIALOG (base);
+ GList *checked_tags;
+ GList *inconsistent_tags;
+ GList *scan;
+
+ gth_tags_entry_get_tag_list (GTH_TAGS_ENTRY (self->priv->tags_entry),
+ TRUE,
+ &checked_tags,
+ &inconsistent_tags);
+
+ for (scan = file_list; scan; scan = scan->next) {
+ GthFileData *file_data = scan->data;
+ GList *new_tags;
+ GHashTable *old_tags;
+ GList *scan_tags;
+
+ new_tags = _g_string_list_dup (checked_tags);
+
+ /* keep the inconsistent tags */
+
+ old_tags = _g_hash_table_from_string_list ((GthStringList *) g_file_info_get_attribute_object (file_data->info, "general::tags"));
+ for (scan_tags = inconsistent_tags; scan_tags; scan_tags = scan_tags->next) {
+ char *inconsistent_tag = scan_tags->data;
+
+ if (g_hash_table_lookup (old_tags, inconsistent_tag) != NULL)
+ new_tags = g_list_prepend (new_tags, g_strdup (inconsistent_tag));
+ }
+ g_hash_table_unref (old_tags);
+
+ /* update the general::tags attribute */
+
+ if (new_tags != NULL) {
+ GthStringList *file_tags;
+
+ new_tags = g_list_sort (new_tags, (GCompareFunc) g_strcmp0);
+ file_tags = gth_string_list_new (new_tags);
+ g_file_info_set_attribute_object (file_data->info, "general::tags", G_OBJECT (file_tags));
+
+ _g_object_unref (file_tags);
+ _g_string_list_free (new_tags);
+ }
+ else
+ g_file_info_remove_attribute (file_data->info, "general::tags");
+ }
+
+ g_list_free (inconsistent_tags);
+ _g_string_list_free (checked_tags);
+}
+
+
+static void
+gth_edit_tags_dialog_gth_edit_metadata_dialog_interface_init (GthEditMetadataDialogInterface *iface)
+{
+ iface->set_file_list = gth_edit_tags_dialog_set_file_list;
+ iface->update_info = gth_edit_tags_dialog_update_info;
+}
+
+
+static void
+gth_edit_tags_dialog_class_init (GthEditTagsDialogClass *klass)
+{
+ GObjectClass *object_class;
+
+ g_type_class_add_private (klass, sizeof (GthEditTagsDialogPrivate));
+
+ object_class = (GObjectClass*) klass;
+ object_class->finalize = gth_edit_tags_dialog_finalize;
+}
+
+
+static void
+gth_edit_tags_dialog_init (GthEditTagsDialog *self)
+{
+ self->priv = G_TYPE_INSTANCE_GET_PRIVATE (self, GTH_TYPE_EDIT_TAGS_DIALOG, GthEditTagsDialogPrivate);
+ self->priv->builder = _gtk_builder_new_from_file ("tag-chooser.ui", "edit_metadata");
+
+ gtk_window_set_title (GTK_WINDOW (self), _("Assign Tags"));
+ gtk_window_set_resizable (GTK_WINDOW (self), TRUE);
+ gtk_window_set_default_size (GTK_WINDOW (self), -1, 500);
+ gtk_box_set_spacing (GTK_BOX (gtk_dialog_get_content_area (GTK_DIALOG (self))), 5);
+ gtk_container_set_border_width (GTK_CONTAINER (self), 5);
+
+ gtk_dialog_add_button (GTK_DIALOG (self), GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL);
+ gtk_dialog_add_button (GTK_DIALOG (self), GTK_STOCK_SAVE, GTK_RESPONSE_APPLY);
+ gtk_dialog_add_button (GTK_DIALOG (self), _("Sa_ve and Close"), GTK_RESPONSE_OK);
+
+ self->priv->tags_entry = gth_tags_entry_new ();
+ gth_tags_entry_set_expanded (GTH_TAGS_ENTRY (self->priv->tags_entry), TRUE);
+ gtk_widget_show (self->priv->tags_entry);
+ gtk_box_pack_start (GTK_BOX (GET_WIDGET ("tag_entry_box")), self->priv->tags_entry, TRUE, TRUE, 0);
+
+ gtk_container_set_border_width (GTK_CONTAINER (GET_WIDGET ("content")), 5);
+ gtk_box_pack_start (GTK_BOX (gtk_dialog_get_content_area (GTK_DIALOG (self))), GET_WIDGET ("content"), TRUE, TRUE, 0);
+}
diff --git a/extensions/edit_metadata/gth-edit-tags-dialog.h b/extensions/edit_metadata/gth-edit-tags-dialog.h
new file mode 100644
index 0000000..362ac0e
--- /dev/null
+++ b/extensions/edit_metadata/gth-edit-tags-dialog.h
@@ -0,0 +1,56 @@
+/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */
+
+/*
+ * GThumb
+ *
+ * Copyright (C) 2011 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, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifndef GTH_EDIT_TAGS_DIALOG_H
+#define GTH_EDIT_TAGS_DIALOG_H
+
+#include <gtk/gtk.h>
+#include <gthumb.h>
+
+G_BEGIN_DECLS
+
+#define GTH_TYPE_EDIT_TAGS_DIALOG (gth_edit_tags_dialog_get_type ())
+#define GTH_EDIT_TAGS_DIALOG(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), GTH_TYPE_EDIT_TAGS_DIALOG, GthEditTagsDialog))
+#define GTH_EDIT_TAGS_DIALOG_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), GTH_TYPE_EDIT_TAGS_DIALOG, GthEditTagsDialogClass))
+#define GTH_IS_EDIT_TAGS_DIALOG(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), GTH_TYPE_EDIT_TAGS_DIALOG))
+#define GTH_IS_EDIT_TAGS_DIALOG_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), GTH_TYPE_EDIT_TAGS_DIALOG))
+#define GTH_EDIT_TAGS_DIALOG_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), GTH_TYPE_EDIT_TAGS_DIALOG, GthEditTagsDialogClass))
+
+typedef struct _GthEditTagsDialog GthEditTagsDialog;
+typedef struct _GthEditTagsDialogClass GthEditTagsDialogClass;
+typedef struct _GthEditTagsDialogPrivate GthEditTagsDialogPrivate;
+
+struct _GthEditTagsDialog {
+ GtkDialog parent_instance;
+ GthEditTagsDialogPrivate *priv;
+};
+
+struct _GthEditTagsDialogClass {
+ GtkDialogClass parent_class;
+};
+
+GType gth_edit_tags_dialog_get_type (void);
+GtkWidget * gth_edit_tags_dialog_new (void);
+
+
+G_END_DECLS
+
+#endif /* GTH_EDIT_TAGS_DIALOG_H */
diff --git a/extensions/edit_metadata/main.c b/extensions/edit_metadata/main.c
index 7d91719..85b7df4 100644
--- a/extensions/edit_metadata/main.c
+++ b/extensions/edit_metadata/main.c
@@ -24,7 +24,7 @@
#include <gtk/gtk.h>
#include <gthumb.h>
#include "callbacks.h"
-#include "gth-edit-comment-page.h"
+#include "gth-edit-general-page.h"
G_MODULE_EXPORT void
@@ -39,12 +39,10 @@ gthumb_extension_activate (void)
**/
gth_hook_register ("delete-metadata", 3);
- gth_main_register_type ("edit-metadata-dialog-page", GTH_TYPE_EDIT_COMMENT_PAGE);
+ gth_main_register_type ("edit-comment-dialog-page", GTH_TYPE_EDIT_GENERAL_PAGE);
gth_hook_add_callback ("gth-browser-construct", 7, G_CALLBACK (edit_metadata__gth_browser_construct_cb), NULL);
gth_hook_add_callback ("gth-browser-set-current-page", 5, G_CALLBACK (edit_metadata__gth_browser_set_current_page_cb), NULL);
gth_hook_add_callback ("gth-browser-update-sensitivity", 10, G_CALLBACK (edit_metadata__gth_browser_update_sensitivity_cb), NULL);
- gth_hook_add_callback ("gth-browser-file-list-popup-before", 5, G_CALLBACK (edit_metadata__gth_browser_file_list_popup_before_cb), NULL);
- gth_hook_add_callback ("gth-browser-file-popup-before", 5, G_CALLBACK (edit_metadata__gth_browser_file_popup_before_cb), NULL);
gth_hook_add_callback ("gth-browser-file-list-key-press", 10, G_CALLBACK (edit_metadata__gth_browser_file_list_key_press_cb), NULL);
}
diff --git a/extensions/exiv2_tools/Makefile.am b/extensions/exiv2_tools/Makefile.am
index 26a127f..cb5f583 100644
--- a/extensions/exiv2_tools/Makefile.am
+++ b/extensions/exiv2_tools/Makefile.am
@@ -8,8 +8,8 @@ extension_LTLIBRARIES = libexiv2_tools.la
libexiv2_tools_la_SOURCES = \
exiv2-utils.h \
exiv2-utils.cpp \
- gth-edit-exiv2-page.c \
- gth-edit-exiv2-page.h \
+ gth-edit-iptc-page.c \
+ gth-edit-iptc-page.h \
gth-metadata-provider-exiv2.c \
gth-metadata-provider-exiv2.h \
main.c
diff --git a/extensions/exiv2_tools/gth-edit-exiv2-page.c b/extensions/exiv2_tools/gth-edit-iptc-page.c
similarity index 80%
rename from extensions/exiv2_tools/gth-edit-exiv2-page.c
rename to extensions/exiv2_tools/gth-edit-iptc-page.c
index d66ec9b..bc4fe7a 100644
--- a/extensions/exiv2_tools/gth-edit-exiv2-page.c
+++ b/extensions/exiv2_tools/gth-edit-iptc-page.c
@@ -22,25 +22,25 @@
#include <config.h>
#include <glib/gi18n.h>
#include <gio/gio.h>
-#include <extensions/edit_metadata/gth-edit-metadata-dialog.h>
+#include <extensions/edit_metadata/gth-edit-comment-dialog.h>
#include "exiv2-utils.h"
-#include "gth-edit-exiv2-page.h"
+#include "gth-edit-iptc-page.h"
#define GET_WIDGET(name) _gtk_builder_get_widget (self->priv->builder, (name))
-static void gth_edit_exiv2_page_gth_edit_exiv2_page_interface_init (GthEditMetadataPageInterface *iface);
+static void gth_edit_iptc_page_gth_edit_comment_page_interface_init (GthEditCommentPageInterface *iface);
-G_DEFINE_TYPE_WITH_CODE (GthEditExiv2Page,
- gth_edit_exiv2_page,
+G_DEFINE_TYPE_WITH_CODE (GthEditIptcPage,
+ gth_edit_iptc_page,
GTK_TYPE_VBOX,
- G_IMPLEMENT_INTERFACE (GTH_TYPE_EDIT_METADATA_PAGE,
- gth_edit_exiv2_page_gth_edit_exiv2_page_interface_init))
+ G_IMPLEMENT_INTERFACE (GTH_TYPE_EDIT_COMMENT_PAGE,
+ gth_edit_iptc_page_gth_edit_comment_page_interface_init))
-struct _GthEditExiv2PagePrivate {
+struct _GthEditIptcPagePrivate {
GtkBuilder *builder;
gboolean supported;
GFileInfo *info;
@@ -48,7 +48,7 @@ struct _GthEditExiv2PagePrivate {
static void
-set_entry_value (GthEditExiv2Page *self,
+set_entry_value (GthEditIptcPage *self,
GFileInfo *info,
const char *attribute,
const char *widget_id)
@@ -64,14 +64,14 @@ set_entry_value (GthEditExiv2Page *self,
void
-gth_edit_exiv2_page_real_set_file_list (GthEditMetadataPage *base,
- GList *file_data_list)
+gth_edit_iptc_page_real_set_file_list (GthEditCommentPage *base,
+ GList *file_data_list)
{
- GthEditExiv2Page *self;
+ GthEditIptcPage *self;
GList *scan;
GthMetadata *metadata;
- self = GTH_EDIT_EXIV2_PAGE (base);
+ self = GTH_EDIT_IPTC_PAGE (base);
self->priv->supported = TRUE;
for (scan = file_data_list; self->priv->supported && scan; scan = scan->next) {
@@ -117,7 +117,7 @@ gth_edit_exiv2_page_real_set_file_list (GthEditMetadataPage *base,
static void
-set_attribute_from_entry (GthEditExiv2Page *self,
+set_attribute_from_entry (GthEditIptcPage *self,
GFileInfo *info,
GthFileData *file_data,
gboolean only_modified_fields,
@@ -142,16 +142,16 @@ set_attribute_from_entry (GthEditExiv2Page *self,
void
-gth_edit_exiv2_page_real_update_info (GthEditMetadataPage *base,
- GFileInfo *info,
- gboolean only_modified_fields)
+gth_edit_iptc_page_real_update_info (GthEditCommentPage *base,
+ GFileInfo *info,
+ gboolean only_modified_fields)
{
- GthEditExiv2Page *self;
+ GthEditIptcPage *self;
GthFileData *file_data;
double v;
char *s;
- self = GTH_EDIT_EXIV2_PAGE (base);
+ self = GTH_EDIT_IPTC_PAGE (base);
if (! self->priv->supported)
return;
@@ -193,38 +193,38 @@ gth_edit_exiv2_page_real_update_info (GthEditMetadataPage *base,
const char *
-gth_edit_exiv2_page_real_get_name (GthEditMetadataPage *self)
+gth_edit_iptc_page_real_get_name (GthEditCommentPage *self)
{
return _("Other");
}
static void
-gth_edit_exiv2_page_finalize (GObject *object)
+gth_edit_iptc_page_finalize (GObject *object)
{
- GthEditExiv2Page *self;
+ GthEditIptcPage *self;
- self = GTH_EDIT_EXIV2_PAGE (object);
+ self = GTH_EDIT_IPTC_PAGE (object);
_g_object_unref (self->priv->info);
g_object_unref (self->priv->builder);
- G_OBJECT_CLASS (gth_edit_exiv2_page_parent_class)->finalize (object);
+ G_OBJECT_CLASS (gth_edit_iptc_page_parent_class)->finalize (object);
}
static void
-gth_edit_exiv2_page_class_init (GthEditExiv2PageClass *klass)
+gth_edit_iptc_page_class_init (GthEditIptcPageClass *klass)
{
- g_type_class_add_private (klass, sizeof (GthEditExiv2PagePrivate));
- G_OBJECT_CLASS (klass)->finalize = gth_edit_exiv2_page_finalize;
+ g_type_class_add_private (klass, sizeof (GthEditIptcPagePrivate));
+ G_OBJECT_CLASS (klass)->finalize = gth_edit_iptc_page_finalize;
}
static void
-gth_edit_exiv2_page_init (GthEditExiv2Page *self)
+gth_edit_iptc_page_init (GthEditIptcPage *self)
{
- self->priv = G_TYPE_INSTANCE_GET_PRIVATE (self, GTH_TYPE_EDIT_EXIV2_PAGE, GthEditExiv2PagePrivate);
+ self->priv = G_TYPE_INSTANCE_GET_PRIVATE (self, GTH_TYPE_EDIT_IPTC_PAGE, GthEditIptcPagePrivate);
self->priv->info = NULL;
gtk_container_set_border_width (GTK_CONTAINER (self), 12);
@@ -235,9 +235,9 @@ gth_edit_exiv2_page_init (GthEditExiv2Page *self)
static void
-gth_edit_exiv2_page_gth_edit_exiv2_page_interface_init (GthEditMetadataPageInterface *iface)
+gth_edit_iptc_page_gth_edit_comment_page_interface_init (GthEditCommentPageInterface *iface)
{
- iface->set_file_list = gth_edit_exiv2_page_real_set_file_list;
- iface->update_info = gth_edit_exiv2_page_real_update_info;
- iface->get_name = gth_edit_exiv2_page_real_get_name;
+ iface->set_file_list = gth_edit_iptc_page_real_set_file_list;
+ iface->update_info = gth_edit_iptc_page_real_update_info;
+ iface->get_name = gth_edit_iptc_page_real_get_name;
}
diff --git a/extensions/exiv2_tools/gth-edit-iptc-page.h b/extensions/exiv2_tools/gth-edit-iptc-page.h
new file mode 100644
index 0000000..d99fad1
--- /dev/null
+++ b/extensions/exiv2_tools/gth-edit-iptc-page.h
@@ -0,0 +1,53 @@
+/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */
+
+/*
+ * GThumb
+ *
+ * Copyright (C) 2009 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, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifndef GTH_EDIT_IPTC_PAGE_H
+#define GTH_EDIT_IPTC_PAGE_H
+
+#include <glib.h>
+#include <glib-object.h>
+#include <gthumb.h>
+
+#define GTH_TYPE_EDIT_IPTC_PAGE (gth_edit_iptc_page_get_type ())
+#define GTH_EDIT_IPTC_PAGE(o) (G_TYPE_CHECK_INSTANCE_CAST ((o), GTH_TYPE_EDIT_IPTC_PAGE, GthEditIptcPage))
+#define GTH_EDIT_IPTC_PAGE_CLASS(k) (G_TYPE_CHECK_CLASS_CAST ((k), GTH_TYPE_EDIT_IPTC_PAGE, GthEditIptcPageClass))
+#define GTH_IS_EDIT_IPTC_PAGE(o) (G_TYPE_CHECK_INSTANCE_TYPE ((o), GTH_TYPE_EDIT_IPTC_PAGE))
+#define GTH_IS_EDIT_IPTC_PAGE_CLASS(k) (G_TYPE_CHECK_CLASS_TYPE ((k), GTH_TYPE_EDIT_IPTC_PAGE))
+#define GTH_EDIT_IPTC_PAGE_GET_CLASS(o) (G_TYPE_INSTANCE_GET_CLASS((o), GTH_TYPE_EDIT_IPTC_PAGE, GthEditIptcPageClass))
+
+typedef struct _GthEditIptcPage GthEditIptcPage;
+typedef struct _GthEditIptcPagePrivate GthEditIptcPagePrivate;
+typedef struct _GthEditIptcPageClass GthEditIptcPageClass;
+
+struct _GthEditIptcPage
+{
+ GtkVBox __parent;
+ GthEditIptcPagePrivate *priv;
+};
+
+struct _GthEditIptcPageClass
+{
+ GtkVBoxClass __parent_class;
+};
+
+GType gth_edit_iptc_page_get_type (void) G_GNUC_CONST;
+
+#endif /* GTH_EDIT_IPTC_PAGE_H */
diff --git a/extensions/exiv2_tools/main.c b/extensions/exiv2_tools/main.c
index 21df433..6c8f748 100644
--- a/extensions/exiv2_tools/main.c
+++ b/extensions/exiv2_tools/main.c
@@ -24,7 +24,7 @@
#include <gtk/gtk.h>
#include <gthumb.h>
#include <extensions/jpeg_utils/jpegtran.h>
-#include "gth-edit-exiv2-page.h"
+#include "gth-edit-iptc-page.h"
#include "gth-metadata-provider-exiv2.h"
#include "exiv2-utils.h"
@@ -275,7 +275,7 @@ gthumb_extension_activate (void)
gth_main_register_metadata_info_v (exiv2_metadata_info);
gth_main_register_metadata_provider (GTH_TYPE_METADATA_PROVIDER_EXIV2);
if (gth_main_extension_is_active ("edit_metadata")) {
- gth_main_register_type ("edit-metadata-dialog-page", GTH_TYPE_EDIT_EXIV2_PAGE);
+ gth_main_register_type ("edit-comment-dialog-page", GTH_TYPE_EDIT_IPTC_PAGE);
gth_hook_add_callback ("delete-metadata", 10, G_CALLBACK (exiv2_delete_metadata_cb), NULL);
}
gth_hook_add_callback ("save-pixbuf", 10, G_CALLBACK (exiv2_write_metadata), NULL);
diff --git a/gthumb/dlg-preferences-extensions.c b/gthumb/dlg-preferences-extensions.c
index 30739b0..c71498f 100644
--- a/gthumb/dlg-preferences-extensions.c
+++ b/gthumb/dlg-preferences-extensions.c
@@ -786,7 +786,7 @@ extensions__dlg_preferences_apply (GtkWidget *dialog,
BrowserData *data;
GList *active_extensions;
GthExtensionManager *manager;
- GList *names;
+ GList *extension_names;
GList *scan;
data = g_object_get_data (G_OBJECT (dialog), BROWSER_DATA_KEY);
@@ -794,17 +794,17 @@ extensions__dlg_preferences_apply (GtkWidget *dialog,
active_extensions = NULL;
manager = gth_main_get_default_extension_manager ();
- names = gth_extension_manager_get_extensions (manager);
- for (scan = names; scan; scan = scan->next) {
- char *name = scan->data;
+ extension_names = gth_extension_manager_get_extensions (manager);
+ for (scan = extension_names; scan; scan = scan->next) {
+ char *extension_name = scan->data;
GthExtensionDescription *description;
- description = gth_extension_manager_get_description (manager, name);
+ description = gth_extension_manager_get_description (manager, extension_name);
if ((description == NULL) || description->mandatory || description->hidden)
continue;
if (gth_extension_description_is_active (description))
- active_extensions = g_list_prepend (active_extensions, g_strdup (name));
+ active_extensions = g_list_prepend (active_extensions, g_strdup (extension_name));
}
active_extensions = g_list_reverse (active_extensions);
_g_settings_set_string_list (data->settings, PREF_GENERAL_ACTIVE_EXTENSIONS, active_extensions);
@@ -830,4 +830,5 @@ extensions__dlg_preferences_apply (GtkWidget *dialog,
g_list_foreach (active_extensions, (GFunc) g_free, NULL);
g_list_free (active_extensions);
+ g_list_free (extension_names);
}
diff --git a/gthumb/gth-browser-actions-callbacks.h b/gthumb/gth-browser-actions-callbacks.h
index 5b61549..d2b7860 100644
--- a/gthumb/gth-browser-actions-callbacks.h
+++ b/gthumb/gth-browser-actions-callbacks.h
@@ -29,7 +29,7 @@
DEFINE_ACTION(gth_browser_activate_action_bookmarks_add)
DEFINE_ACTION(gth_browser_activate_action_bookmarks_edit)
DEFINE_ACTION(gth_browser_activate_action_browser_mode)
-DEFINE_ACTION(gth_browser_activate_action_edit_metadata)
+DEFINE_ACTION(gth_browser_activate_action_edit_comment)
DEFINE_ACTION(gth_browser_activate_action_edit_preferences)
DEFINE_ACTION(gth_browser_activate_action_edit_select_all)
DEFINE_ACTION(gth_browser_activate_action_file_open)
diff --git a/gthumb/gth-tags-entry.c b/gthumb/gth-tags-entry.c
index d571ec4..bb841b1 100644
--- a/gthumb/gth-tags-entry.c
+++ b/gthumb/gth-tags-entry.c
@@ -38,6 +38,7 @@ enum {
enum {
EXPANDED_LIST_USED_COLUMN,
+ EXPANDED_LIST_INCONSISTENT_COLUMN,
EXPANDED_LIST_SEPARATOR_COLUMN,
EXPANDED_LIST_NAME_COLUMN,
EXPANDED_LIST_N_COLUMNS
@@ -55,6 +56,7 @@ typedef struct {
char *name;
gboolean used;
gboolean suggested;
+ gboolean inconsistent;
} TagData;
@@ -70,12 +72,14 @@ struct _GthTagsEntryPrivate {
GtkWidget *entry;
GtkWidget *expand_button;
ExpandedList expanded_list;
+ gboolean expanded;
char **tags;
GtkEntryCompletion *completion;
GtkListStore *completion_store;
char *new_tag;
gboolean action_create;
gulong monitor_event;
+ GHashTable *inconsistent;
};
@@ -98,6 +102,7 @@ gth_tags_entry_finalize (GObject *obj)
g_object_unref (self->priv->completion);
g_strfreev (self->priv->tags);
g_strfreev (self->priv->expanded_list.last_used);
+ g_hash_table_unref (self->priv->inconsistent);
G_OBJECT_CLASS (gth_tags_entry_parent_class)->finalize (obj);
}
@@ -240,9 +245,12 @@ update_expanded_list_from_entry (GthTagsEntry *self)
tag_data[i]->name = g_strdup (all_tags[i]);
tag_data[i]->suggested = FALSE;
tag_data[i]->used = FALSE;
+ tag_data[i]->inconsistent = (g_hash_table_lookup (self->priv->inconsistent, tag_data[i]->name) != NULL);
for (j = 0; ! tag_data[i]->used && (used_tags[j] != NULL); j++)
- if (g_utf8_collate (tag_data[i]->name, used_tags[j]) == 0)
+ if (g_utf8_collate (tag_data[i]->name, used_tags[j]) == 0) {
tag_data[i]->used = TRUE;
+ tag_data[i]->inconsistent = FALSE;
+ }
if (! tag_data[i]->used)
for (j = 0; ! tag_data[i]->suggested && (self->priv->expanded_list.last_used[j] != NULL); j++)
@@ -273,6 +281,7 @@ update_expanded_list_from_entry (GthTagsEntry *self)
gtk_list_store_append (self->priv->expanded_list.store, &iter);
gtk_list_store_set (self->priv->expanded_list.store, &iter,
EXPANDED_LIST_USED_COLUMN, TRUE,
+ EXPANDED_LIST_INCONSISTENT_COLUMN, tag_data[i]->inconsistent,
EXPANDED_LIST_SEPARATOR_COLUMN, FALSE,
EXPANDED_LIST_NAME_COLUMN, tag_data[i]->name,
-1);
@@ -282,6 +291,7 @@ update_expanded_list_from_entry (GthTagsEntry *self)
gtk_list_store_append (self->priv->expanded_list.store, &iter);
gtk_list_store_set (self->priv->expanded_list.store, &iter,
EXPANDED_LIST_USED_COLUMN, FALSE,
+ EXPANDED_LIST_INCONSISTENT_COLUMN, FALSE,
EXPANDED_LIST_SEPARATOR_COLUMN, TRUE,
EXPANDED_LIST_NAME_COLUMN, "",
-1);
@@ -301,6 +311,7 @@ update_expanded_list_from_entry (GthTagsEntry *self)
gtk_list_store_append (self->priv->expanded_list.store, &iter);
gtk_list_store_set (self->priv->expanded_list.store, &iter,
EXPANDED_LIST_USED_COLUMN, FALSE,
+ EXPANDED_LIST_INCONSISTENT_COLUMN, tag_data[i]->inconsistent,
EXPANDED_LIST_SEPARATOR_COLUMN, FALSE,
EXPANDED_LIST_NAME_COLUMN, tag_data[i]->name,
-1);
@@ -310,6 +321,7 @@ update_expanded_list_from_entry (GthTagsEntry *self)
gtk_list_store_append (self->priv->expanded_list.store, &iter);
gtk_list_store_set (self->priv->expanded_list.store, &iter,
EXPANDED_LIST_USED_COLUMN, FALSE,
+ EXPANDED_LIST_INCONSISTENT_COLUMN, FALSE,
EXPANDED_LIST_SEPARATOR_COLUMN, TRUE,
EXPANDED_LIST_NAME_COLUMN, "",
-1);
@@ -326,6 +338,7 @@ update_expanded_list_from_entry (GthTagsEntry *self)
gtk_list_store_append (self->priv->expanded_list.store, &iter);
gtk_list_store_set (self->priv->expanded_list.store, &iter,
EXPANDED_LIST_USED_COLUMN, FALSE,
+ EXPANDED_LIST_INCONSISTENT_COLUMN, tag_data[i]->inconsistent,
EXPANDED_LIST_SEPARATOR_COLUMN, FALSE,
EXPANDED_LIST_NAME_COLUMN, tag_data[i]->name,
-1);
@@ -618,14 +631,21 @@ cell_renderer_toggle_toggled_cb (GtkCellRendererToggle *cell_renderer,
tree_model = gtk_tree_view_get_model (GTK_TREE_VIEW (self->priv->expanded_list.tree_view));
if (gtk_tree_model_get_iter (tree_model, &iter, tpath)) {
- gboolean used;
+ char *tag;
+ gboolean used;
gtk_tree_model_get (tree_model, &iter,
+ EXPANDED_LIST_NAME_COLUMN, &tag,
EXPANDED_LIST_USED_COLUMN, &used,
-1);
+
+ g_hash_table_remove (self->priv->inconsistent, tag);
gtk_list_store_set (GTK_LIST_STORE (tree_model), &iter,
EXPANDED_LIST_USED_COLUMN, ! used,
+ EXPANDED_LIST_INCONSISTENT_COLUMN, FALSE,
-1);
+
+ g_free (tag);
}
update_entry_from_expanded_list (self);
@@ -679,6 +699,8 @@ gth_tags_entry_init (GthTagsEntry *self)
self->priv = G_TYPE_INSTANCE_GET_PRIVATE (self, GTH_TYPE_TAGS_ENTRY, GthTagsEntryPrivate);
self->priv->expanded_list.last_used = g_new0 (char *, 1);
+ self->priv->expanded = FALSE;
+ self->priv->inconsistent = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, NULL);
gtk_box_set_spacing (GTK_BOX (self), 3);
@@ -729,7 +751,11 @@ gth_tags_entry_init (GthTagsEntry *self)
/* expanded list, the treeview */
- self->priv->expanded_list.store = gtk_list_store_new (EXPANDED_LIST_N_COLUMNS, G_TYPE_BOOLEAN, G_TYPE_BOOLEAN, G_TYPE_STRING);
+ self->priv->expanded_list.store = gtk_list_store_new (EXPANDED_LIST_N_COLUMNS,
+ G_TYPE_BOOLEAN,
+ G_TYPE_BOOLEAN,
+ G_TYPE_BOOLEAN,
+ G_TYPE_STRING);
self->priv->expanded_list.tree_view = gtk_tree_view_new_with_model (GTK_TREE_MODEL (self->priv->expanded_list.store));
gtk_tree_view_set_headers_visible (GTK_TREE_VIEW (self->priv->expanded_list.tree_view), FALSE);
gtk_tree_view_set_row_separator_func (GTK_TREE_VIEW (self->priv->expanded_list.tree_view),
@@ -749,6 +775,7 @@ gth_tags_entry_init (GthTagsEntry *self)
gtk_tree_view_column_pack_start (column, renderer, FALSE);
gtk_tree_view_column_set_attributes (column, renderer,
"active", EXPANDED_LIST_USED_COLUMN,
+ "inconsistent", EXPANDED_LIST_INCONSISTENT_COLUMN,
NULL);
/* the name column. */
@@ -804,38 +831,24 @@ gth_tags_entry_new (void)
}
-char **
-gth_tags_entry_get_tags (GthTagsEntry *self,
- gboolean update_globals)
+void
+gth_tags_entry_set_expanded (GthTagsEntry *self,
+ gboolean expanded)
{
- GthTagsFile *tags_file;
- char **all_tags;
- char **tags;
- int i;
- int j;
-
- tags_file = gth_main_get_default_tag_file ();
+ g_return_if_fail (GTH_IS_TAGS_ENTRY (self));
- all_tags = g_strsplit (gtk_entry_get_text (GTK_ENTRY (self->priv->entry)), ",", -1);
- tags = g_new0 (char *, g_strv_length (all_tags) + 1);
- for (i = 0, j = 0; all_tags[i] != NULL; i++) {
- all_tags[i] = g_strstrip (all_tags[i]);
- if (all_tags[i][0] != '\0') {
- tags[j] = g_strdup (g_strstrip (all_tags[i]));
- if (update_globals)
- gth_tags_file_add (tags_file, tags[j]);
- j++;
- }
- }
- g_strfreev (all_tags);
+ self->priv->expanded = expanded;
+ gtk_widget_set_size_request (self->priv->expanded_list.container, -1, self->priv->expanded ? -1 : EXPANDED_LIST_HEIGHT);
+ gtk_widget_set_visible (self->priv->expand_button, ! expanded);
+ gtk_widget_set_visible (self->priv->expanded_list.container, expanded || gtk_toggle_button_get_active (GTK_TOGGLE_BUTTON (self->priv->expand_button)));
+}
- if (update_globals) {
- for (i = 0; self->priv->tags[i] != NULL; i++)
- gth_tags_file_add (tags_file, self->priv->tags[i]);
- gth_main_tags_changed ();
- }
- return tags;
+gboolean
+gth_tags_entry_get_expanded (GthTagsEntry *self)
+{
+ g_return_val_if_fail (GTH_IS_TAGS_ENTRY (self), FALSE);
+ return self->priv->expanded;
}
@@ -867,8 +880,8 @@ gth_tags_entry_set_tags (GthTagsEntry *self,
void
-gth_tags_entry_set_text (GthTagsEntry *self,
- const char *text)
+gth_tags_entry_set_tags_from_text (GthTagsEntry *self,
+ const char *text)
{
char **tags;
@@ -882,3 +895,87 @@ gth_tags_entry_set_text (GthTagsEntry *self,
g_strfreev (tags);
}
+
+
+char **
+gth_tags_entry_get_tags (GthTagsEntry *self,
+ gboolean update_globals)
+{
+ GthTagsFile *tags_file;
+ char **all_tags;
+ char **tags;
+ int i;
+ int j;
+
+ tags_file = gth_main_get_default_tag_file ();
+
+ all_tags = g_strsplit (gtk_entry_get_text (GTK_ENTRY (self->priv->entry)), ",", -1);
+ tags = g_new0 (char *, g_strv_length (all_tags) + 1);
+ for (i = 0, j = 0; all_tags[i] != NULL; i++) {
+ all_tags[i] = g_strstrip (all_tags[i]);
+ if (all_tags[i][0] != '\0') {
+ tags[j] = g_strdup (g_strstrip (all_tags[i]));
+ if (update_globals)
+ gth_tags_file_add (tags_file, tags[j]);
+ j++;
+ }
+ }
+ g_strfreev (all_tags);
+
+ if (update_globals) {
+ for (i = 0; self->priv->tags[i] != NULL; i++)
+ gth_tags_file_add (tags_file, self->priv->tags[i]);
+ gth_main_tags_changed ();
+ }
+
+ return tags;
+}
+
+
+void
+gth_tags_entry_set_tag_list (GthTagsEntry *self,
+ GList *checked,
+ GList *inconsistent)
+{
+ GString *str;
+ GList *scan;
+
+ g_hash_table_remove_all (self->priv->inconsistent);
+ for (scan = inconsistent; scan; scan = scan->next)
+ g_hash_table_insert (self->priv->inconsistent, g_strdup (scan->data), GINT_TO_POINTER (1));
+
+ str = g_string_new ("");
+ for (scan = checked; scan; scan = scan->next) {
+ if (scan != checked)
+ g_string_append (str, ", ");
+ g_string_append (str, (char *) scan->data);
+ }
+ gth_tags_entry_set_tags_from_text (self, str->str);
+
+ if (checked == NULL)
+ update_expanded_list_from_entry (self);
+
+ g_string_free (str, TRUE);
+}
+
+
+void
+gth_tags_entry_get_tag_list (GthTagsEntry *self,
+ gboolean update_globals,
+ GList **checked,
+ GList **inconsistent)
+{
+ if (checked != NULL) {
+ char **tags_v;
+ int i;
+
+ tags_v = gth_tags_entry_get_tags (self, update_globals);
+ *checked = NULL;
+ for (i = 0; tags_v[i] != NULL; i++)
+ *checked = g_list_prepend (*checked, g_strdup (tags_v[i]));
+ *checked = g_list_reverse (*checked);
+ }
+
+ if (inconsistent != NULL)
+ *inconsistent = g_hash_table_get_keys (self->priv->inconsistent);
+}
diff --git a/gthumb/gth-tags-entry.h b/gthumb/gth-tags-entry.h
index 9f0e538..5773119 100644
--- a/gthumb/gth-tags-entry.h
+++ b/gthumb/gth-tags-entry.h
@@ -50,14 +50,24 @@ struct _GthTagsEntryClass {
void (*list_collapsed) (GthTagsEntry *self);
};
-GType gth_tags_entry_get_type (void);
-GtkWidget * gth_tags_entry_new (void);
-char ** gth_tags_entry_get_tags (GthTagsEntry *self,
- gboolean update_globals);
-void gth_tags_entry_set_tags (GthTagsEntry *self,
- char **tags);
-void gth_tags_entry_set_text (GthTagsEntry *self,
- const char *text);
+GType gth_tags_entry_get_type (void);
+GtkWidget * gth_tags_entry_new (void);
+void gth_tags_entry_set_expanded (GthTagsEntry *self,
+ gboolean expanded);
+gboolean gth_tags_entry_get_expanded (GthTagsEntry *self);
+void gth_tags_entry_set_tags (GthTagsEntry *self,
+ char **tags);
+void gth_tags_entry_set_tags_from_text (GthTagsEntry *self,
+ const char *text);
+char ** gth_tags_entry_get_tags (GthTagsEntry *self,
+ gboolean update_globals);
+void gth_tags_entry_set_tag_list (GthTagsEntry *self,
+ GList *checked,
+ GList *inconsistent);
+void gth_tags_entry_get_tag_list (GthTagsEntry *self,
+ gboolean update_globals,
+ GList **checked,
+ GList **inconsistent);
G_END_DECLS
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]