[rhythmbox] add a property to RBSource indicating the source loading status



commit f8f6321f96d99ad2cc33007bec7e75737d7b16f7
Author: Jonathan Matthew <jonathan d14n org>
Date:   Mon May 7 12:31:54 2012 +1000

    add a property to RBSource indicating the source loading status
    
    Media player sources in particular take some time to load their
    contents, during which some actions may not be available.
    
    In media player sources, disable the sync action and defer transfers
    until fully loaded.

 plugins/audiocd/rb-audiocd-source.c               |    9 ++++
 plugins/daap/rb-daap-source.c                     |    6 ++-
 plugins/generic-player/rb-generic-player-source.c |   27 ++++++++++--
 plugins/ipod/rb-ipod-source.c                     |   32 ++++++++++++---
 plugins/mtpdevice/rb-mtp-source.c                 |   36 ++++++++++++-----
 sources/rb-media-player-source.c                  |   15 ++++++-
 sources/rb-source.c                               |   45 ++++++++++++++++++++-
 sources/rb-source.h                               |   10 +++++
 sources/rb-transfer-target.c                      |   25 ++++++++---
 sources/rb-transfer-target.h                      |    2 +-
 10 files changed, 175 insertions(+), 32 deletions(-)
---
diff --git a/plugins/audiocd/rb-audiocd-source.c b/plugins/audiocd/rb-audiocd-source.c
index ff349c3..7b403a2 100644
--- a/plugins/audiocd/rb-audiocd-source.c
+++ b/plugins/audiocd/rb-audiocd-source.c
@@ -548,6 +548,7 @@ rb_audiocd_source_new (GObject *plugin,
 			       "volume", volume,
 			       "shell", shell,
 			       "plugin", plugin,
+			       "load-status", RB_SOURCE_LOAD_STATUS_LOADING,
 			       "show-browser", FALSE,
 			       "settings", g_settings_get_child (settings, "source"),
 			       "toolbar-path", "/AudioCdSourceToolBar",
@@ -786,6 +787,7 @@ apply_album_metadata (RBAudioCdSource *source, AlbumDetails *album)
 		g_object_unref (source->priv->metadata);
 		source->priv->metadata = NULL;
 		g_object_unref (db);
+		g_object_set (source, "load-status", RB_SOURCE_LOAD_STATUS_LOADED, NULL);
 		return;
 	}
 
@@ -891,6 +893,8 @@ apply_album_metadata (RBAudioCdSource *source, AlbumDetails *album)
 	source->priv->metadata = NULL;
 
 	g_object_unref (db);
+
+	g_object_set (source, "load-status", RB_SOURCE_LOAD_STATUS_LOADED, NULL);
 }
 
 
@@ -1048,12 +1052,14 @@ metadata_cb (SjMetadataGetter *metadata,
 		/* TODO display error to user? */
 		g_object_unref (metadata);
 		source->priv->metadata = NULL;
+		g_object_set (source, "load-status", RB_SOURCE_LOAD_STATUS_LOADED, NULL);
 		return;
 	}
 	if (albums == NULL) {
 		rb_debug ("Musicbrainz didn't return any CD metadata, but didn't give an error");
 		g_object_unref (metadata);
 		source->priv->metadata = NULL;
+		g_object_set (source, "load-status", RB_SOURCE_LOAD_STATUS_LOADED, NULL);
 		return;
 	}
 	if (source->priv->tracks == NULL) {
@@ -1061,6 +1067,7 @@ metadata_cb (SjMetadataGetter *metadata,
 		rb_debug ("no tracks on the CD?");
 		g_object_unref (metadata);
 		source->priv->metadata = NULL;
+		g_object_set (source, "load-status", RB_SOURCE_LOAD_STATUS_LOADED, NULL);
 		return;
 	}
 
@@ -1101,6 +1108,8 @@ rb_audiocd_load_metadata (RBAudioCdSource *source,
 	g_signal_connect (G_OBJECT (source->priv->metadata), "metadata",
 			  G_CALLBACK (metadata_cb), source);
 	sj_metadata_getter_list_albums (source->priv->metadata, NULL);
+#else
+	g_object_set (source, "load-status", RB_SOURCE_LOAD_STATUS_LOADED, NULL);
 #endif
 }
 
diff --git a/plugins/daap/rb-daap-source.c b/plugins/daap/rb-daap-source.c
index 351bdc0..82cb91e 100644
--- a/plugins/daap/rb-daap-source.c
+++ b/plugins/daap/rb-daap-source.c
@@ -338,6 +338,7 @@ rb_daap_source_new (RBShell *shell,
 					  "visibility", TRUE,
 					  "password-protected", password_protected,
 					  "plugin", G_OBJECT (plugin),
+					  "load-status", RB_SOURCE_LOAD_STATUS_NOT_LOADED,
 					  "settings", g_settings_get_child (settings, "source"),
 					  "toolbar-path", "/DAAPSourceToolBar",
 					  NULL));
@@ -425,6 +426,7 @@ ask_password (RBDAAPSource *source, const char *name, const char *keyring, SoupS
 	AuthData *auth_data;
 	char *message;
 
+	g_object_set (source, "load-status", RB_SOURCE_LOAD_STATUS_WAITING, NULL);
 	parent = GTK_WINDOW (gtk_widget_get_toplevel (GTK_WIDGET (source)));
 
 	mount_op = gtk_mount_operation_new (parent);
@@ -517,14 +519,16 @@ connection_connecting_cb (DMAPConnection       *connection,
 		source->priv->connection_status = _("Connecting to music share");
 		break;
 	case DMAP_GET_REVISION_NUMBER:
+		g_object_set (source, "load-status", RB_SOURCE_LOAD_STATUS_LOADING, NULL);
 	case DMAP_GET_DB_INFO:
 	case DMAP_GET_SONGS:
 	case DMAP_GET_PLAYLISTS:
 	case DMAP_GET_PLAYLIST_ENTRIES:
 		source->priv->connection_status = _("Retrieving songs from music share");
 		break;
-	case DMAP_LOGOUT:
 	case DMAP_DONE:
+		g_object_set (source, "load-status", RB_SOURCE_LOAD_STATUS_LOADED, NULL);
+	case DMAP_LOGOUT:
 		source->priv->connection_status = NULL;
 		break;
 	}
diff --git a/plugins/generic-player/rb-generic-player-source.c b/plugins/generic-player/rb-generic-player-source.c
index 6ae56d5..6a1aaef 100644
--- a/plugins/generic-player/rb-generic-player-source.c
+++ b/plugins/generic-player/rb-generic-player-source.c
@@ -475,6 +475,7 @@ rb_generic_player_source_new (GObject *plugin, RBShell *shell, GMount *mount, MP
 							 "mount", mount,
 							 "shell", shell,
 							 "device-info", device_info,
+							 "load-status", RB_SOURCE_LOAD_STATUS_LOADING,
 							 "settings", g_settings_get_child (settings, "source"),
 							 "toolbar-path", "/GenericPlayerSourceToolBar",
 							 NULL));
@@ -510,20 +511,30 @@ impl_delete_thyself (RBDisplayPage *page)
 	RB_DISPLAY_PAGE_CLASS (rb_generic_player_source_parent_class)->delete_thyself (page);
 }
 
-static void
-impl_selected (RBDisplayPage *page)
+static gboolean
+ensure_loaded (RBGenericPlayerSource *source)
 {
-	RBGenericPlayerSource *source = RB_GENERIC_PLAYER_SOURCE (page);
 	RBGenericPlayerSourcePrivate *priv = GET_PRIVATE (source);
+	RBSourceLoadStatus status;
 
-	if (priv->loaded == FALSE) {
+	if (priv->loaded) {
+		g_object_get (source, "load-status", &status, NULL);
+		return (status == RB_SOURCE_LOAD_STATUS_LOADED);
+	} else {
 		priv->loaded = TRUE;
 		rb_media_player_source_load (RB_MEDIA_PLAYER_SOURCE (source));
 		load_songs (source);
+		return FALSE;
 	}
 }
 
 static void
+impl_selected (RBDisplayPage *page)
+{
+	ensure_loaded (RB_GENERIC_PLAYER_SOURCE (page));
+}
+
+static void
 import_complete_cb (RhythmDBImportJob *job, int total, RBGenericPlayerSource *source)
 {
 	RBGenericPlayerSourceClass *klass = RB_GENERIC_PLAYER_SOURCE_GET_CLASS (source);
@@ -543,6 +554,9 @@ import_complete_cb (RhythmDBImportJob *job, int total, RBGenericPlayerSource *so
 	priv->import_job = NULL;
 
 	rb_display_page_notify_status_changed (RB_DISPLAY_PAGE (source));
+	g_object_set (source, "load-status", RB_SOURCE_LOAD_STATUS_LOADED, NULL);
+
+	rb_transfer_target_transfer (RB_TRANSFER_TARGET (source), NULL, FALSE);
 
 	GDK_THREADS_LEAVE ();
 }
@@ -899,7 +913,10 @@ impl_can_paste (RBSource *source)
 static RBTrackTransferBatch *
 impl_paste (RBSource *source, GList *entries)
 {
-	return rb_transfer_target_transfer (RB_TRANSFER_TARGET (source), entries);
+	gboolean defer;
+
+	defer = (ensure_loaded (RB_GENERIC_PLAYER_SOURCE (source)) == FALSE);
+	return rb_transfer_target_transfer (RB_TRANSFER_TARGET (source), entries, defer);
 }
 
 static gboolean
diff --git a/plugins/ipod/rb-ipod-source.c b/plugins/ipod/rb-ipod-source.c
index 194807c..73baca9 100644
--- a/plugins/ipod/rb-ipod-source.c
+++ b/plugins/ipod/rb-ipod-source.c
@@ -105,6 +105,7 @@ static void rb_ipod_source_get_property (GObject *object,
 					 guint prop_id,
 					 GValue *value,
 					 GParamSpec *pspec);
+static gboolean ensure_loaded (RBiPodSource *source);
 
 
 static RhythmDB *get_db_for_source (RBiPodSource *source);
@@ -544,6 +545,7 @@ rb_ipod_source_new (GObject *plugin,
 					       "mount", mount,
 					       "shell", shell,
 					       "device-info", device_info,
+					       "load-status", RB_SOURCE_LOAD_STATUS_LOADING,
 					       "settings", g_settings_get_child (settings, "source"),
 					       "toolbar-path", "/iPodSourceToolBar",
 					       NULL));
@@ -1166,6 +1168,10 @@ load_ipod_db_idle_cb (RBiPodSource *source)
 
 	g_object_unref (db);
 
+	g_object_set (source, "load-status", RB_SOURCE_LOAD_STATUS_LOADED, NULL);
+
+	rb_transfer_target_transfer (RB_TRANSFER_TARGET (source), NULL, FALSE);
+
 	GDK_THREADS_LEAVE ();
 	priv->load_idle_id = 0;
 	return FALSE;
@@ -1284,7 +1290,10 @@ impl_delete_entries (RBMediaPlayerSource *source, GList *entries, RBMediaPlayerS
 static RBTrackTransferBatch *
 impl_paste (RBSource *source, GList *entries)
 {
-	return rb_transfer_target_transfer (RB_TRANSFER_TARGET (source), entries);
+	gboolean defer;
+
+	defer = (ensure_loaded (RB_IPOD_SOURCE (source)) == FALSE);
+	return rb_transfer_target_transfer (RB_TRANSFER_TARGET (source), entries, defer);
 }
 
 static void
@@ -1809,18 +1818,29 @@ ipod_path_from_unix_path (const gchar *mount_point, const gchar *unix_path)
 	return ipod_path;
 }
 
-static void
-impl_selected (RBDisplayPage *page)
+static gboolean
+ensure_loaded (RBiPodSource *source)
 {
-	RBiPodSourcePrivate *priv = IPOD_SOURCE_GET_PRIVATE (page);
+	RBiPodSourcePrivate *priv = IPOD_SOURCE_GET_PRIVATE (source);
+	RBSourceLoadStatus status;
 	
 	if (priv->ipod_db == NULL) {
-		rb_ipod_load_songs (RB_IPOD_SOURCE (page));
-		rb_media_player_source_load (RB_MEDIA_PLAYER_SOURCE (page));
+		rb_ipod_load_songs (source);
+		rb_media_player_source_load (RB_MEDIA_PLAYER_SOURCE (source));
+		return FALSE;
+	} else {
+		g_object_get (source, "load-status", &status, NULL);
+		return (status == RB_SOURCE_LOAD_STATUS_LOADED);
 	}
 }
 
 static void
+impl_selected (RBDisplayPage *page)
+{
+	ensure_loaded (RB_IPOD_SOURCE (page));
+}
+
+static void
 impl_delete_thyself (RBDisplayPage *page)
 {
 	RBiPodSourcePrivate *priv = IPOD_SOURCE_GET_PRIVATE (page);
diff --git a/plugins/mtpdevice/rb-mtp-source.c b/plugins/mtpdevice/rb-mtp-source.c
index cbf640f..ac557ac 100644
--- a/plugins/mtpdevice/rb-mtp-source.c
+++ b/plugins/mtpdevice/rb-mtp-source.c
@@ -331,16 +331,18 @@ unmount_done_cb (GObject *object, GAsyncResult *result, gpointer psource)
 
 #endif
 
-static void
-impl_selected (RBDisplayPage *page)
+static gboolean
+ensure_loaded (RBMtpSource *source)
 {
-	RBMtpSourcePrivate *priv = MTP_SOURCE_GET_PRIVATE (page);
+	RBMtpSourcePrivate *priv = MTP_SOURCE_GET_PRIVATE (source);
 #if defined(HAVE_GUDEV)
 	GMount *mount;
 #endif
-
-	if (priv->tried_open)
-		return;
+	if (priv->tried_open) {
+		RBSourceLoadStatus status;
+		g_object_get (source, "load-status", &status, NULL);
+		return (status == RB_SOURCE_LOAD_STATUS_LOADED);
+	}
 	priv->tried_open = TRUE;
 
 	/* try to open the device.  if gvfs has mounted it, unmount it first */
@@ -353,15 +355,22 @@ impl_selected (RBDisplayPage *page)
 						NULL,
 						NULL,
 						unmount_done_cb,
-						g_object_ref (page));
+						g_object_ref (source));
 		/* mount gets unreffed in callback */
 	} else {
 		rb_debug ("device isn't mounted");
-		open_device (RB_MTP_SOURCE (page));
+		open_device (source);
 	}
 #else
-	open_device (RB_MTP_SOURCE (page));
+	open_device (source);
 #endif
+	return FALSE;
+}
+
+static void
+impl_selected (RBDisplayPage *page)
+{
+	ensure_loaded (RB_MTP_SOURCE (page));
 }
 
 static void
@@ -599,6 +608,7 @@ rb_mtp_source_new (RBShell *shell,
 #else
 					      "udi", udi,
 #endif
+					      "load-status", RB_SOURCE_LOAD_STATUS_LOADING,
 					      "settings", g_settings_get_child (settings, "source"),
 					      "toolbar-path", "/MTPSourceToolBar",
 					      "name", _("Media Player"),
@@ -990,6 +1000,10 @@ mtp_tracklist_cb (LIBMTP_track_t *tracks, RBMtpSource *source)
 		add_mtp_track_to_db (source, db, track);
 	}
 	g_object_unref (db);
+
+	g_object_set (source, "load-status", RB_SOURCE_LOAD_STATUS_LOADED, NULL);
+
+	rb_transfer_target_transfer (RB_TRANSFER_TARGET (source), NULL, FALSE);
 }
 
 static char *
@@ -1066,7 +1080,9 @@ impl_uri_is_source (RBSource *source, const char *uri)
 static RBTrackTransferBatch *
 impl_paste (RBSource *source, GList *entries)
 {
-	return rb_transfer_target_transfer (RB_TRANSFER_TARGET (source), entries);
+	gboolean defer;
+	defer = (ensure_loaded (RB_MTP_SOURCE (source)) == FALSE);
+	return rb_transfer_target_transfer (RB_TRANSFER_TARGET (source), entries, defer);
 }
 
 static gboolean
diff --git a/sources/rb-media-player-source.c b/sources/rb-media-player-source.c
index dd8b426..f313629 100644
--- a/sources/rb-media-player-source.c
+++ b/sources/rb-media-player-source.c
@@ -256,6 +256,17 @@ rb_media_player_source_get_property (GObject *object,
 }
 
 static void
+load_status_changed_cb (GObject *object, GParamSpec *pspec, gpointer whatever)
+{
+	RBMediaPlayerSourcePrivate *priv = MEDIA_PLAYER_SOURCE_GET_PRIVATE (object);
+	RBSourceLoadStatus status;
+
+	g_object_get (object, "load-status", &status, NULL);
+
+	gtk_action_set_sensitive (priv->sync_action, (status == RB_SOURCE_LOAD_STATUS_LOADED));
+}
+
+static void
 rb_media_player_source_constructed (GObject *object)
 {
 	RBMediaPlayerSourcePrivate *priv = MEDIA_PLAYER_SOURCE_GET_PRIVATE (object);
@@ -268,6 +279,8 @@ rb_media_player_source_constructed (GObject *object)
 	g_object_unref (shell);
 
 	priv->sync_action = gtk_action_group_get_action (action_group, "MediaPlayerSourceSync");
+	g_signal_connect (object, "notify::load-status", G_CALLBACK (load_status_changed_cb), NULL);
+	load_status_changed_cb (object, NULL, NULL);
 }
 
 /* must be called once device information is available via source properties */
@@ -886,7 +899,7 @@ impl_receive_drag (RBDisplayPage *page, GtkSelectionData *data)
 	if (entries) {
 		entries = g_list_reverse (entries);
 		if (rb_source_can_paste (RB_SOURCE (page))) {
-			rb_transfer_target_transfer (RB_TRANSFER_TARGET (page), entries);
+			rb_source_paste (RB_SOURCE (page), entries);
 		}
 		g_list_free (entries);
 	}
diff --git a/sources/rb-source.c b/sources/rb-source.c
index df6d7ac..7019aea 100644
--- a/sources/rb-source.c
+++ b/sources/rb-source.c
@@ -108,6 +108,7 @@ struct _RBSourcePrivate
 	guint update_visibility_id;
 	guint update_status_id;
 	RhythmDBEntryType *entry_type;
+	RBSourceLoadStatus load_status;
 
 	GSettings *settings;
 
@@ -124,6 +125,7 @@ enum
 	PROP_PLAY_ORDER,
 	PROP_SETTINGS,
 	PROP_SHOW_BROWSER,
+	PROP_LOAD_STATUS,
 	PROP_TOOLBAR_PATH
 };
 
@@ -235,6 +237,21 @@ rb_source_class_init (RBSourceClass *klass)
 							      G_PARAM_READABLE));
 
 	/**
+	 * RBSource:load-status:
+	 *
+	 * Indicates whether the source is not loaded, is currently loading data, or is
+	 * fully loaded.
+	 */
+	g_object_class_install_property (object_class,
+					 PROP_LOAD_STATUS,
+					 g_param_spec_enum ("load-status",
+							    "load-status",
+							    "load status",
+							    RB_TYPE_SOURCE_LOAD_STATUS,
+							    RB_SOURCE_LOAD_STATUS_LOADED,
+							    G_PARAM_READWRITE | G_PARAM_CONSTRUCT));
+
+	/**
 	 * RBSource:settings:
 	 *
 	 * The #GSettings instance storing settings for the source.  The instance must
@@ -451,6 +468,9 @@ rb_source_set_property (GObject *object,
 	case PROP_SHOW_BROWSER:
 		/* not connected to anything here */
 		break;
+	case PROP_LOAD_STATUS:
+		source->priv->load_status = g_value_get_enum (value);
+		break;
 	case PROP_TOOLBAR_PATH:
 		source->priv->toolbar_path = g_value_dup_string (value);
 		break;
@@ -490,6 +510,9 @@ rb_source_get_property (GObject *object,
 	case PROP_SHOW_BROWSER:
 		g_value_set_boolean (value, FALSE);
 		break;
+	case PROP_LOAD_STATUS:
+		g_value_set_enum (value, source->priv->load_status);
+		break;
 	case PROP_TOOLBAR_PATH:
 		g_value_set_string (value, source->priv->toolbar_path);
 		break;
@@ -1443,6 +1466,27 @@ rb_source_eof_type_get_type (void)
 
 	return etype;
 }
+
+GType
+rb_source_load_status_get_type (void)
+{
+	static GType etype = 0;
+
+	if (etype == 0) {
+		static const GEnumValue values[] = {
+			ENUM_ENTRY (RB_SOURCE_LOAD_STATUS_NOT_LOADED, "not-loaded"),
+			ENUM_ENTRY (RB_SOURCE_LOAD_STATUS_WAITING, "waiting"),
+			ENUM_ENTRY (RB_SOURCE_LOAD_STATUS_LOADING, "loading"),
+			ENUM_ENTRY (RB_SOURCE_LOAD_STATUS_LOADED, "loaded"),
+			{ 0, 0, 0 }
+		};
+
+		etype = g_enum_register_static ("RBSourceLoadStatus", values);
+	}
+
+	return etype;
+}
+
 /* introspection annotations for vmethods */
 
 /**
@@ -1478,4 +1522,3 @@ rb_source_eof_type_get_type (void)
  * @source: a #RBSource
  * @entries: (element-type RB.RhythmDBEntry) (transfer none): list of entries to paste
  */
-
diff --git a/sources/rb-source.h b/sources/rb-source.h
index c38868d..d519495 100644
--- a/sources/rb-source.h
+++ b/sources/rb-source.h
@@ -48,6 +48,13 @@ typedef enum {
 	RB_SOURCE_EOF_NEXT,
 } RBSourceEOFType;
 
+typedef enum {
+	RB_SOURCE_LOAD_STATUS_NOT_LOADED,
+	RB_SOURCE_LOAD_STATUS_WAITING,
+	RB_SOURCE_LOAD_STATUS_LOADING,
+	RB_SOURCE_LOAD_STATUS_LOADED
+} RBSourceLoadStatus;
+
 typedef struct _RBSource	RBSource;
 typedef struct _RBSourceClass	RBSourceClass;
 typedef struct _RBSourcePrivate	RBSourcePrivate;
@@ -57,6 +64,9 @@ typedef void (*RBSourceActionCallback) (GtkAction *action, RBSource *source);
 GType rb_source_eof_type_get_type (void);
 #define RB_TYPE_SOURCE_EOF_TYPE	(rb_source_eof_type_get_type())
 
+GType rb_source_load_status_get_type (void);
+#define RB_TYPE_SOURCE_LOAD_STATUS (rb_source_load_status_get_type())
+
 #define RB_TYPE_SOURCE         (rb_source_get_type ())
 #define RB_SOURCE(o)           (G_TYPE_CHECK_INSTANCE_CAST ((o), RB_TYPE_SOURCE, RBSource))
 #define RB_SOURCE_CLASS(k)     (G_TYPE_CHECK_CLASS_CAST((k), RB_TYPE_SOURCE, RBSourceClass))
diff --git a/sources/rb-transfer-target.c b/sources/rb-transfer-target.c
index e2631c8..dd53009 100644
--- a/sources/rb-transfer-target.c
+++ b/sources/rb-transfer-target.c
@@ -376,6 +376,7 @@ track_done_cb (RBTrackTransferBatch *batch,
  * rb_transfer_target_transfer:
  * @target: an #RBTransferTarget
  * @entries: a #GList of entries to transfer
+ * @defer: if %TRUE, don't start the transfer until
  *
  * Starts tranferring @entries to the target.  This returns the
  * #RBTrackTransferBatch that it starts, so the caller can track
@@ -385,7 +386,7 @@ track_done_cb (RBTrackTransferBatch *batch,
  * Return value: (transfer full): an #RBTrackTransferBatch, or NULL
  */
 RBTrackTransferBatch *
-rb_transfer_target_transfer (RBTransferTarget *target, GList *entries)
+rb_transfer_target_transfer (RBTransferTarget *target, GList *entries, gboolean defer)
 {
 	RBTrackTransferQueue *xferq;
 	RBShell *shell;
@@ -395,7 +396,7 @@ rb_transfer_target_transfer (RBTransferTarget *target, GList *entries)
 	GstEncodingTarget *encoding_target;
 	gboolean start_batch = FALSE;
 
-	g_object_get (target,		/* hrm */
+	g_object_get (target,
 		      "shell", &shell,
 		      "entry-type", &our_entry_type,
 		      "encoding-target", &encoding_target,
@@ -403,11 +404,17 @@ rb_transfer_target_transfer (RBTransferTarget *target, GList *entries)
 	g_object_get (shell, "track-transfer-queue", &xferq, NULL);
 	g_object_unref (shell);
 
-	batch = rb_track_transfer_batch_new (encoding_target, NULL, G_OBJECT (target));
-	gst_encoding_target_unref (encoding_target);
+	batch = g_object_steal_data (G_OBJECT (target), "transfer-target-batch");
 
-	g_signal_connect_object (batch, "get-dest-uri", G_CALLBACK (get_dest_uri_cb), target, 0);
-	g_signal_connect_object (batch, "track-done", G_CALLBACK (track_done_cb), target, 0);
+	if (batch == NULL) {
+		batch = rb_track_transfer_batch_new (encoding_target, NULL, G_OBJECT (target));
+
+		g_signal_connect_object (batch, "get-dest-uri", G_CALLBACK (get_dest_uri_cb), target, 0);
+		g_signal_connect_object (batch, "track-done", G_CALLBACK (track_done_cb), target, 0);
+	} else {
+		start_batch = TRUE;
+	}
+	gst_encoding_target_unref (encoding_target);
 
 	for (l = entries; l != NULL; l = l->next) {
 		RhythmDBEntry *entry;
@@ -433,7 +440,11 @@ rb_transfer_target_transfer (RBTransferTarget *target, GList *entries)
 	g_object_unref (our_entry_type);
 
 	if (start_batch) {
-		rb_track_transfer_queue_start_batch (xferq, batch);
+		if (defer) {
+			g_object_set_data_full (G_OBJECT (target), "transfer-target-batch", g_object_ref (batch), g_object_unref);
+		} else {
+			rb_track_transfer_queue_start_batch (xferq, batch);
+		}
 	} else {
 		g_object_unref (batch);
 		batch = NULL;
diff --git a/sources/rb-transfer-target.h b/sources/rb-transfer-target.h
index cb3df15..44ed100 100644
--- a/sources/rb-transfer-target.h
+++ b/sources/rb-transfer-target.h
@@ -86,7 +86,7 @@ gboolean        rb_transfer_target_check_category	(RBTransferTarget *target,
 gboolean        rb_transfer_target_check_duplicate	(RBTransferTarget *target,
 							 RhythmDBEntry *entry);
 
-RBTrackTransferBatch *rb_transfer_target_transfer	(RBTransferTarget *target, GList *entries);
+RBTrackTransferBatch *rb_transfer_target_transfer	(RBTransferTarget *target, GList *entries, gboolean defer);
 
 
 G_END_DECLS



[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]