summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorGravatar Alexey Yakovenko <wakeroid@gmail.com>2009-08-04 22:29:26 +0200
committerGravatar Alexey Yakovenko <wakeroid@gmail.com>2009-08-04 22:29:26 +0200
commit8e2e95f37a8509c7cbc7b85a61ab7b53f9d7b9d3 (patch)
treeb31ddc98a4af3041e9c94737510adf419e8c5dcc
parentfbbbd7436a347595e925c5ba8b69e8875b5c73bc (diff)
fixed drag and drop from filemanagers
-rw-r--r--callbacks.c31
-rw-r--r--gtkplaylist.c59
-rw-r--r--gtkplaylist.h3
-rw-r--r--playlist.c87
4 files changed, 153 insertions, 27 deletions
diff --git a/callbacks.c b/callbacks.c
index 2a148fe4..c38e82b9 100644
--- a/callbacks.c
+++ b/callbacks.c
@@ -360,6 +360,9 @@ on_playlist_drag_drop (GtkWidget *widget,
{
if (drag_context->targets) {
GdkAtom target_type = GDK_POINTER_TO_ATOM (g_list_nth_data (drag_context->targets, TARGET_SAMEWIDGET));
+ if (!target_type) {
+ return FALSE;
+ }
gtk_drag_get_data (widget, drag_context, target_type, time);
return TRUE;
}
@@ -413,35 +416,9 @@ on_playlist_drag_data_received (GtkWidget *widget,
gpointer user_data)
{
gchar *ptr=(char*)data->data;
-// printf ("target type: %d\n", target_type);
if (target_type == 0) { // uris
if (!strncmp(ptr,"file:///",8)) {
- //printf ("data: %s\n", ptr);
- // this happens when dropped from file manager
- // parse, and try to add to playlist
- const gchar *p = ptr;
- while (*p) {
- const gchar *pe = p+1;
- while (*pe && *pe > ' ') {
- pe++;
- }
- if (pe - p < 4096 && pe - p > 7) {
- char fname[(int)(pe - p)];
- strncpy (fname, p, pe - p);
- fname[pe - p] = 0;
- if (ps_add_dir (fname+7)) {
- ps_add_file (fname+7);
- }
- }
- p = pe;
- // skip whitespace
- while (*p && *p <= ' ') {
- p++;
- }
- }
- gtkps_setup_scrollbar ();
- draw_playlist (widget, 0, 0, widget->allocation.width, widget->allocation.height);
- gtkps_expose (widget, 0, 0, widget->allocation.width, widget->allocation.height);
+ gtkps_handle_fm_drag_drop (y, ptr, data->length);
}
}
else if (target_type == 1) {
diff --git a/gtkplaylist.c b/gtkplaylist.c
index 497833e8..ead402ac 100644
--- a/gtkplaylist.c
+++ b/gtkplaylist.c
@@ -921,3 +921,62 @@ gtkps_handle_drag_drop (int drop_y, uint32_t *d, int length) {
playlist_tail = tail;
}
}
+
+void
+strcopy_special (char *dest, const char *src, int len) {
+ while (len > 0) {
+ if (len >= 3 && !strncmp (src, "\%20", 3)) {
+ *dest = ' ';
+ dest++;
+ src += 3;
+ len -= 3;
+ }
+ else {
+ *dest++ = *src++;
+ len--;
+ }
+ }
+ *dest = 0;
+}
+
+void
+gtkps_handle_fm_drag_drop (int drop_y, void *ptr, int length) {
+ int drop_row = drop_y / rowheight + scrollpos;
+ playItem_t *drop_before = ps_get_for_idx (drop_row);
+ playItem_t *after = NULL;
+ if (drop_before) {
+ after = drop_before->prev;
+ }
+ //printf ("data: %s\n", ptr);
+ // this happens when dropped from file manager
+ // parse, and try to add to playlist
+ const gchar *p = ptr;
+ while (*p) {
+ const gchar *pe = p+1;
+ while (*pe && *pe > ' ') {
+ pe++;
+ }
+ if (pe - p < 4096 && pe - p > 7) {
+ char fname[(int)(pe - p)];
+ strcopy_special (fname, p, pe-p);
+ //strncpy (fname, p, pe - p);
+ //fname[pe - p] = 0;
+ playItem_t *inserted = ps_insert_dir (after, fname + 7);
+ if (!inserted) {
+ inserted = ps_insert_file (after, fname + 7);
+ }
+ if (inserted) {
+ after = inserted;
+ }
+ }
+ p = pe;
+ // skip whitespace
+ while (*p && *p <= ' ') {
+ p++;
+ }
+ }
+ gtkps_setup_scrollbar ();
+ GtkWidget *widget = lookup_widget (mainwin, "playlist");
+ draw_playlist (widget, 0, 0, widget->allocation.width, widget->allocation.height);
+ gtkps_expose (widget, 0, 0, widget->allocation.width, widget->allocation.height);
+}
diff --git a/gtkplaylist.h b/gtkplaylist.h
index cd0b9938..12e0b23c 100644
--- a/gtkplaylist.h
+++ b/gtkplaylist.h
@@ -85,4 +85,7 @@ gtkps_track_dragdrop (int y);
void
gtkps_handle_drag_drop (int drop_y, uint32_t *d, int length);
+void
+gtkps_handle_fm_drag_drop (int drop_y, void *ptr, int length);
+
#endif
diff --git a/playlist.c b/playlist.c
index 0cb2c21e..5f55f807 100644
--- a/playlist.c
+++ b/playlist.c
@@ -352,14 +352,91 @@ ps_add_cue (const char *cuename) {
playItem_t *
ps_insert_file (playItem_t *after, const char *fname) {
+ if (!fname) {
+ return NULL;
+ }
+ // detect codec
+ codec_t *codec = NULL;
+ const char *eol = fname + strlen (fname) - 1;
+ while (eol > fname && *eol != '.') {
+ eol--;
+ }
+ eol++;
+
+ // match by codec
+ codec_t *codecs[] = {
+ &cdumb, &cvorbis, &cflac, &cgme, &cmp3, &csid, NULL
+ };
+ for (int i = 0; codecs[i]; i++) {
+ if (codecs[i]->getexts && codecs[i]->insert) {
+ const char **exts = codecs[i]->getexts ();
+ if (exts) {
+ for (int e = 0; exts[e]; e++) {
+ if (!strcasecmp (exts[e], eol)) {
+ playItem_t *inserted = NULL;
+ if ((inserted = codecs[i]->insert (after, fname)) != NULL) {
+ return inserted;
+ }
+ }
+ }
+ }
+ }
+ }
+ return NULL;
}
playItem_t *
ps_insert_dir (playItem_t *after, const char *dirname) {
+ struct stat buf;
+ lstat (dirname, &buf);
+ if (S_ISLNK(buf.st_mode)) {
+ return NULL;
+ }
+ struct dirent **namelist = NULL;
+ int n;
+
+ n = scandir (dirname, &namelist, NULL, alphasort);
+ if (n < 0)
+ {
+ if (namelist)
+ free (namelist);
+ return NULL; // not a dir or no read access
+ }
+ else
+ {
+ int i;
+ for (i = 0; i < n; i++)
+ {
+ // no hidden files
+ if (namelist[i]->d_name[0] != '.')
+ {
+ char fullname[1024];
+ strcpy (fullname, dirname);
+ strncat (fullname, "/", 1024);
+ strncat (fullname, namelist[i]->d_name, 1024);
+ playItem_t *inserted = ps_insert_dir (after, fullname);
+ if (!inserted) {
+ inserted = ps_insert_file (after, fullname);
+ }
+ if (inserted) {
+ after = inserted;
+ }
+ }
+ free (namelist[i]);
+ }
+ free (namelist);
+ }
+ return after;
}
int
ps_add_file (const char *fname) {
+ if (ps_insert_file (playlist_tail, fname)) {
+ return 0;
+ }
+ return -1;
+// {{{ original ps_add_file
+#if 0
if (!fname) {
return -1;
}
@@ -393,10 +470,18 @@ ps_add_file (const char *fname) {
}
return -1;
+#endif
+// }}}
}
int
ps_add_dir (const char *dirname) {
+ if (ps_insert_dir (playlist_tail, dirname)) {
+ return 0;
+ }
+ return -1;
+// {{{ original ps_add_dir code
+#if 0
struct stat buf;
lstat (dirname, &buf);
if (S_ISLNK(buf.st_mode)) {
@@ -433,6 +518,8 @@ ps_add_dir (const char *dirname) {
free (namelist);
}
return 0;
+#endif
+// }}}
}
int