Revision: 1470
http://geeqie.svn.sourceforge.net/geeqie/?rev=1470&view=rev
Author: nadvornik
Date: 2009-03-03 23:17:07 +0000 (Tue, 03 Mar 2009)
Log Message:
-----------
reorder exif pane entries with drag and drop
Modified Paths:
--------------
trunk/src/bar_exif.c
trunk/src/dnd.h
Modified: trunk/src/bar_exif.c
===================================================================
--- trunk/src/bar_exif.c 2009-03-02 22:48:04 UTC (rev 1469)
+++ trunk/src/bar_exif.c 2009-03-03 23:17:07 UTC (rev 1470)
@@ -22,6 +22,7 @@
#include "ui_misc.h"
#include "bar.h"
#include "rcfile.h"
+#include "dnd.h"
#include <math.h>
@@ -36,6 +37,7 @@
typedef struct _ExifEntry ExifEntry;
struct _ExifEntry
{
+ GtkWidget *ebox;
GtkWidget *hbox;
GtkWidget *title_label;
GtkWidget *value_label;
@@ -60,6 +62,7 @@
FileData *fd;
};
+static void bar_pane_exif_entry_dnd_init(GtkWidget *entry);
static void bar_pane_exif_update_entry(PaneExifData *ped, GtkWidget *entry,
gboolean update_title);
static void bar_pane_exif_entry_destroy(GtkWidget *widget, gpointer data)
@@ -72,7 +75,7 @@
}
-static void bar_pane_exif_add_entry(PaneExifData *ped, const gchar *key, const
gchar *title, gint if_set)
+static GtkWidget *bar_pane_exif_add_entry(PaneExifData *ped, const gchar *key,
const gchar *title, gint if_set)
{
ExifEntry *ee = g_new0(ExifEntry, 1);
@@ -89,11 +92,15 @@
ee->if_set = if_set;
- ee->hbox = gtk_hbox_new(FALSE, 0);
- g_object_set_data(G_OBJECT(ee->hbox), "entry_data", ee);
- g_signal_connect_after(G_OBJECT(ee->hbox), "destroy",
+ ee->ebox = gtk_event_box_new();
+ g_object_set_data(G_OBJECT(ee->ebox), "entry_data", ee);
+ g_signal_connect_after(G_OBJECT(ee->ebox), "destroy",
G_CALLBACK(bar_pane_exif_entry_destroy), ee);
+ ee->hbox = gtk_hbox_new(FALSE, 0);
+ gtk_container_add(GTK_CONTAINER(ee->ebox), ee->hbox);
+ gtk_widget_show(ee->hbox);
+
ee->title_label = gtk_label_new(NULL);
gtk_misc_set_alignment(GTK_MISC(ee->title_label), 1.0, 0.5);
gtk_size_group_add_widget(ped->size_group, ee->title_label);
@@ -107,11 +114,31 @@
gtk_misc_set_alignment(GTK_MISC(ee->value_label), 0.0, 0.5);
gtk_box_pack_start(GTK_BOX(ee->hbox), ee->value_label, TRUE, TRUE, 1);
gtk_widget_show(ee->value_label);
+ gtk_box_pack_start(GTK_BOX(ped->vbox), ee->ebox, TRUE, TRUE, 0);
+
+ bar_pane_exif_entry_dnd_init(ee->ebox);
- gtk_box_pack_start(GTK_BOX(ped->vbox), ee->hbox, TRUE, TRUE, 0);
- bar_pane_exif_update_entry(ped, ee->hbox, TRUE);
+ bar_pane_exif_update_entry(ped, ee->ebox, TRUE);
+ return ee->ebox;
}
+
+static void bar_pane_exif_reparent_entry(GtkWidget *entry, GtkWidget *pane)
+{
+ GtkWidget *old_pane = entry->parent;
+ PaneExifData *ped = g_object_get_data(G_OBJECT(pane), "pane_data");
+ PaneExifData *old_ped = g_object_get_data(G_OBJECT(old_pane),
"pane_data");
+ ExifEntry *ee = g_object_get_data(G_OBJECT(entry), "entry_data");
+ if (!ped || !old_ped || !ee) return;
+ g_object_ref(entry);
+
+ gtk_size_group_remove_widget(old_ped->size_group, ee->title_label);
+ gtk_container_remove(GTK_CONTAINER(old_ped->vbox), entry);
+
+ gtk_size_group_add_widget(ped->size_group, ee->title_label);
+ gtk_box_pack_start(GTK_BOX(ped->vbox), entry, TRUE, TRUE, 0);
+}
+
static void bar_pane_exif_entry_update_title(ExifEntry *ee)
{
gchar *markup;
@@ -131,7 +158,7 @@
if (ee->if_set && (!text || !*text))
{
gtk_label_set_text(GTK_LABEL(ee->value_label), NULL);
- gtk_widget_hide(ee->hbox);
+ gtk_widget_hide(entry);
}
else
{
@@ -139,7 +166,7 @@
#if GTK_CHECK_VERSION(2,12,0)
gtk_widget_set_tooltip_text(ee->hbox, text);
#endif
- gtk_widget_show(ee->hbox);
+ gtk_widget_show(entry);
}
g_free(text);
@@ -177,6 +204,7 @@
{
GtkWidget *entry = work->data;
work = work->next;
+
bar_pane_exif_update_entry(ped, entry, FALSE);
}
@@ -196,6 +224,131 @@
bar_pane_exif_update(ped);
}
+/*
+ *-------------------------------------------------------------------
+ * dnd
+ *-------------------------------------------------------------------
+ */
+
+static GtkTargetEntry bar_pane_exif_drag_types[] = {
+ { TARGET_APP_EXIF_ENTRY_STRING, GTK_TARGET_SAME_APP,
TARGET_APP_EXIF_ENTRY },
+ { "text/plain", 0, TARGET_TEXT_PLAIN }
+};
+static gint n_exif_entry_drag_types = 2;
+
+static GtkTargetEntry bar_pane_exif_drop_types[] = {
+ { TARGET_APP_EXIF_ENTRY_STRING, GTK_TARGET_SAME_APP,
TARGET_APP_EXIF_ENTRY },
+ { "text/plain", 0, TARGET_TEXT_PLAIN }
+};
+static gint n_exif_entry_drop_types = 2;
+
+
+static void bar_pane_exif_entry_dnd_get(GtkWidget *entry, GdkDragContext
*context,
+ GtkSelectionData *selection_data, guint
info,
+ guint time, gpointer data)
+{
+ ExifEntry *ee = g_object_get_data(G_OBJECT(entry), "entry_data");
+
+ switch (info)
+ {
+
+ case TARGET_APP_EXIF_ENTRY:
+ gtk_selection_data_set(selection_data,
selection_data->target,
+ 8, (gpointer) &entry,
sizeof(entry));
+ break;
+
+ case TARGET_TEXT_PLAIN:
+ default:
+ gtk_selection_data_set_text(selection_data, ee->key,
-1);
+ break;
+ }
+
+}
+
+static void bar_pane_exif_dnd_receive(GtkWidget *pane, GdkDragContext *context,
+ gint x, gint y,
+ GtkSelectionData *selection_data,
guint info,
+ guint time, gpointer data)
+{
+ PaneExifData *ped;
+ GList *work, *list;
+ gint pos;
+ GtkWidget *new_entry = NULL;
+ ped = g_object_get_data(G_OBJECT(pane), "pane_data");
+ if (!ped) return;
+
+ switch (info)
+ {
+ case TARGET_APP_EXIF_ENTRY:
+ new_entry = *(gpointer *)selection_data->data;
+
+ if (new_entry->parent && new_entry->parent !=
ped->vbox) bar_pane_exif_reparent_entry(new_entry, pane);
+
+ break;
+ default:
+ /* FIXME: this needs a check for valid exif keys */
+ new_entry = bar_pane_exif_add_entry(ped, (gchar
*)selection_data->data, NULL, TRUE);
+ break;
+ }
+
+
+ list = gtk_container_get_children(GTK_CONTAINER(ped->vbox));
+ work = list;
+ pos = 0;
+ while (work)
+ {
+ gint nx, ny;
+ GtkWidget *entry = work->data;
+ work = work->next;
+
+ if (entry == new_entry) continue;
+
+ if (GTK_WIDGET_DRAWABLE(entry) &&
+ gtk_widget_translate_coordinates(pane, entry, x, y, &nx,
&ny) &&
+ ny < entry->allocation.height / 2) break;
+ pos++;
+ }
+ g_list_free(list);
+
+ gtk_box_reorder_child(GTK_BOX(ped->vbox), new_entry, pos);
+}
+
+static void bar_pane_exif_entry_dnd_begin(GtkWidget *widget, GdkDragContext
*context, gpointer data)
+{
+// gtk_drag_set_icon_default(context);
+}
+
+static void bar_pane_exif_entry_dnd_end(GtkWidget *widget, GdkDragContext
*context, gpointer data)
+{
+}
+
+static void bar_pane_exif_entry_dnd_init(GtkWidget *entry)
+{
+ ExifEntry *ee = g_object_get_data(G_OBJECT(entry), "entry_data");
+
+ gtk_drag_source_set(entry, GDK_BUTTON1_MASK | GDK_BUTTON2_MASK,
+ bar_pane_exif_drag_types, n_exif_entry_drag_types,
+ GDK_ACTION_COPY | GDK_ACTION_MOVE |
GDK_ACTION_LINK);
+ g_signal_connect(G_OBJECT(entry), "drag_data_get",
+ G_CALLBACK(bar_pane_exif_entry_dnd_get), ee);
+
+ g_signal_connect(G_OBJECT(entry), "drag_begin",
+ G_CALLBACK(bar_pane_exif_entry_dnd_begin), ee);
+ g_signal_connect(G_OBJECT(entry), "drag_end",
+ G_CALLBACK(bar_pane_exif_entry_dnd_end), ee);
+}
+
+static void bar_pane_exif_dnd_init(GtkWidget *pane)
+{
+ gtk_drag_dest_set(pane,
+ GTK_DEST_DEFAULT_MOTION | GTK_DEST_DEFAULT_HIGHLIGHT
| GTK_DEST_DEFAULT_DROP,
+ bar_pane_exif_drop_types, n_exif_entry_drop_types,
+ GDK_ACTION_COPY | GDK_ACTION_MOVE | GDK_ACTION_ASK);
+ g_signal_connect(G_OBJECT(pane), "drag_data_received",
+ G_CALLBACK(bar_pane_exif_dnd_receive), NULL);
+}
+
+
static void bar_pane_exif_entry_write_config(GtkWidget *entry, GString
*outstr, gint indent)
{
ExifEntry *ee = g_object_get_data(G_OBJECT(entry), "entry_data");
@@ -297,6 +450,8 @@
G_CALLBACK(bar_pane_exif_size_request), ped);
g_signal_connect(G_OBJECT(ped->widget), "size-allocate",
G_CALLBACK(bar_pane_exif_size_allocate), ped);
+
+ bar_pane_exif_dnd_init(ped->widget);
if (populate)
{
Modified: trunk/src/dnd.h
===================================================================
--- trunk/src/dnd.h 2009-03-02 22:48:04 UTC (rev 1469)
+++ trunk/src/dnd.h 2009-03-03 23:17:07 UTC (rev 1470)
@@ -15,9 +15,11 @@
#define DND_H
#define TARGET_APP_COLLECTION_MEMBER_STRING "application/x-" GQ_APPNAME_LC
"-collection-member"
+#define TARGET_APP_EXIF_ENTRY_STRING "application/x-" GQ_APPNAME_LC
"-exif-entry"
enum {
TARGET_APP_COLLECTION_MEMBER,
+ TARGET_APP_EXIF_ENTRY,
TARGET_URI_LIST,
TARGET_TEXT_PLAIN
};
This was sent by the SourceForge.net collaborative development platform, the
world's largest Open Source development site.
------------------------------------------------------------------------------
Open Source Business Conference (OSBC), March 24-25, 2009, San Francisco, CA
-OSBC tackles the biggest issue in open source: Open Sourcing the Enterprise
-Strategies to boost innovation and cut costs with open source participation
-Receive a $600 discount off the registration fee with the source code: SFAD
http://p.sf.net/sfu/XcvMzF8H
_______________________________________________
Geeqie-svn mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/geeqie-svn