[rhythmbox] source: add a completion callback to rb_source_add_uri



commit ea1fb03f57f705ac1d6cd199a3ca72bb3818e1dc
Author: Jonathan Matthew <jonathan d14n org>
Date:   Sat Aug 14 23:21:37 2010 +1000

    source: add a completion callback to rb_source_add_uri
    
    Currently the only interesting case here is the library, since
    its implementation of rb_source_add_uri is asynchronous.

 bindings/python/rb.defs                   |    6 +++
 plugins/audioscrobbler/rb-lastfm-source.c |   30 ++++++++++++----
 plugins/iradio/rb-iradio-source.c         |   18 +++++++++-
 shell/rb-shell.c                          |    4 +-
 sources/rb-library-source.c               |   53 +++++++++++++++++++++++++++-
 sources/rb-podcast-source.c               |   18 +++++++++-
 sources/rb-source.c                       |   13 ++++++-
 sources/rb-source.h                       |   17 ++++++++-
 8 files changed, 139 insertions(+), 20 deletions(-)
---
diff --git a/bindings/python/rb.defs b/bindings/python/rb.defs
index 6bd7028..103e91e 100644
--- a/bindings/python/rb.defs
+++ b/bindings/python/rb.defs
@@ -1205,6 +1205,9 @@
     '("const-char*" "uri")
     '("const-char*" "title")
     '("const-char*" "genre")
+    '("RBSourceAddCallback" "callback")
+    '("gpointer" "data")
+    '("GDestroyNotify" "destroy_data")
   )
 )
 
@@ -1410,6 +1413,9 @@
     '("const-char*" "uri")
     '("const-char*" "title" (null-ok))
     '("const-char*" "genre" (null-ok))
+    '("RBSourceAddCallback" "callback")
+    '("gpointer" "data")
+    '("GDestroyNotify" "destroy_data")
   )
 )
 
diff --git a/plugins/audioscrobbler/rb-lastfm-source.c b/plugins/audioscrobbler/rb-lastfm-source.c
index a71845a..4ad392c 100644
--- a/plugins/audioscrobbler/rb-lastfm-source.c
+++ b/plugins/audioscrobbler/rb-lastfm-source.c
@@ -159,7 +159,13 @@ static gboolean impl_receive_drag (RBSource *source, GtkSelectionData *data);
 static void impl_activate (RBSource *source);
 static gboolean impl_show_popup (RBSource *source);
 static guint impl_want_uri (RBSource *source, const char *uri);
-static gboolean impl_add_uri (RBSource *source, const char *uri, const char *title, const char *genre);
+static gboolean impl_add_uri (RBSource *source,
+			      const char *uri,
+			      const char *title,
+			      const char *genre,
+			      RBSourceAddCallback callback,
+			      gpointer data,
+			      GDestroyNotify destroy_data);
 static RBSourceEOFType impl_handle_eos (RBSource *asource);
 
 static void rb_lastfm_source_new_station (const char *uri, const char *title, RBLastfmSource *source);
@@ -1397,17 +1403,25 @@ impl_want_uri (RBSource *source, const char *uri)
 }
 
 static gboolean
-impl_add_uri (RBSource *source, const char *uri, const char *title, const char *genre)
+impl_add_uri (RBSource *source,
+	      const char *uri,
+	      const char *title,
+	      const char *genre,
+	      RBSourceAddCallback callback,
+	      gpointer data,
+	      GDestroyNotify destroy_data)
 {
 	char *name;
+	gboolean ret = FALSE;
 
-	if (strstr (uri, "lastfm://") == NULL)
-		return FALSE;
-
-	name = rb_lastfm_source_title_from_uri (uri);
+	if (strstr (uri, "lastfm://") != NULL) {
+		name = rb_lastfm_source_title_from_uri (uri);
+		rb_lastfm_source_new_station (uri, name, RB_LASTFM_SOURCE (source));
+	}
 
-	rb_lastfm_source_new_station (uri, name, RB_LASTFM_SOURCE (source));
-	return TRUE;
+	callback (source, uri, data);
+	destroy_data (data);
+	return ret;
 }
 
 static RBSourceEOFType
diff --git a/plugins/iradio/rb-iradio-source.c b/plugins/iradio/rb-iradio-source.c
index d25501f..c73c585 100644
--- a/plugins/iradio/rb-iradio-source.c
+++ b/plugins/iradio/rb-iradio-source.c
@@ -106,7 +106,13 @@ static void impl_song_properties (RBSource *source);
 static gboolean impl_show_popup (RBSource *source);
 static GList *impl_get_ui_actions (RBSource *source);
 static guint impl_want_uri (RBSource *source, const char *uri);
-static gboolean impl_add_uri (RBSource *source, const char *uri, const char *title, const char *genre);
+static gboolean impl_add_uri (RBSource *source,
+			      const char *uri,
+			      const char *title,
+			      const char *genre,
+			      RBSourceAddCallback callback,
+			      gpointer data,
+			      GDestroyNotify destroy_data);
 
 static void rb_iradio_source_do_query (RBIRadioSource *source);
 
@@ -651,7 +657,13 @@ impl_want_uri (RBSource *source, const char *uri)
 }
 
 static gboolean
-impl_add_uri (RBSource *source, const char *uri, const char *title, const char *genre)
+impl_add_uri (RBSource *source,
+	      const char *uri,
+	      const char *title,
+	      const char *genre,
+	      RBSourceAddCallback callback,
+	      gpointer data,
+	      GDestroyNotify destroy_data)
 {
 	if (rb_uri_is_local (uri)) {
 		rb_iradio_source_add_from_playlist (RB_IRADIO_SOURCE (source), uri);
@@ -659,6 +671,8 @@ impl_add_uri (RBSource *source, const char *uri, const char *title, const char *
 		rb_iradio_source_add_station (RB_IRADIO_SOURCE (source),
 					      uri, title, genre);
 	}
+	callback (source, uri, data);
+	destroy_data (data);
 	return TRUE;
 }
 
diff --git a/shell/rb-shell.c b/shell/rb-shell.c
index b81d363..47e7cf6 100644
--- a/shell/rb-shell.c
+++ b/shell/rb-shell.c
@@ -3191,7 +3191,7 @@ rb_shell_add_uri (RBShell *shell,
 		return FALSE;
 	}
 
-	rb_source_add_uri (source, uri, title, genre);
+	rb_source_add_uri (source, uri, title, genre, NULL, NULL, NULL);
 	return TRUE;
 }
 
@@ -3300,7 +3300,7 @@ rb_shell_load_uri (RBShell *shell,
 		if (result == TOTEM_PL_PARSER_RESULT_SUCCESS) {
 			if (data.can_use_playlist && data.playlist_source) {
 				rb_debug ("adding playlist %s to source", uri);
-				rb_source_add_uri (data.playlist_source, uri, NULL, NULL);
+				rb_source_add_uri (data.playlist_source, uri, NULL, NULL, NULL, NULL, NULL);
 
 				/* FIXME: We need some way to determine whether the URI as
 				 * given will appear in the db, or whether something else will.
diff --git a/sources/rb-library-source.c b/sources/rb-library-source.c
index 24bc436..eb8bbd6 100644
--- a/sources/rb-library-source.c
+++ b/sources/rb-library-source.c
@@ -84,7 +84,13 @@ static gboolean impl_receive_drag (RBSource *source, GtkSelectionData *data);
 static gboolean impl_can_paste (RBSource *asource);
 static RBTrackTransferBatch *impl_paste (RBSource *source, GList *entries);
 static guint impl_want_uri (RBSource *source, const char *uri);
-static gboolean impl_add_uri (RBSource *source, const char *uri, const char *title, const char *genre);
+static gboolean impl_add_uri (RBSource *source,
+			      const char *uri,
+			      const char *title,
+			      const char *genre,
+			      RBSourceAddCallback callback,
+			      gpointer data,
+			      GDestroyNotify destroy_data);
 static void impl_get_status (RBSource *source, char **text, char **progress_text, float *progress);
 
 static void rb_library_source_ui_prefs_sync (RBLibrarySource *source);
@@ -1424,8 +1430,39 @@ maybe_create_import_job (RBLibrarySource *source)
 	return job;
 }
 
+struct ImportJobCallbackData {
+	char *uri;
+	RBSource *source;
+	RBSourceAddCallback callback;
+	gpointer data;
+	GDestroyNotify destroy_data;
+};
+
+static void
+import_job_callback_destroy (struct ImportJobCallbackData *data)
+{
+	if (data->destroy_data != NULL) {
+		data->destroy_data (data->data);
+	}
+	g_object_unref (data->source);
+	g_free (data->uri);
+	g_free (data);
+}
+
+static void
+import_job_callback_cb (RhythmDBImportJob *job, int total, struct ImportJobCallbackData *data)
+{
+	data->callback (data->source, data->uri, data->data);
+}
+
 static gboolean
-impl_add_uri (RBSource *asource, const char *uri, const char *title, const char *genre)
+impl_add_uri (RBSource *asource,
+	      const char *uri,
+	      const char *title,
+	      const char *genre,
+	      RBSourceAddCallback callback,
+	      gpointer data,
+	      GDestroyNotify destroy_data)
 {
 	RBLibrarySource *source = RB_LIBRARY_SOURCE (asource);
 	RhythmDBImportJob *job;
@@ -1434,6 +1471,18 @@ impl_add_uri (RBSource *asource, const char *uri, const char *title, const char
 
 	rb_debug ("adding uri %s to library", uri);
 	rhythmdb_import_job_add_uri (job, uri);
+
+	if (callback != NULL) {
+		struct ImportJobCallbackData *cbdata;
+
+		cbdata = g_new0 (struct ImportJobCallbackData, 1);
+		cbdata->uri = g_strdup (uri);
+		cbdata->source = g_object_ref (source);
+		cbdata->callback = callback;
+		cbdata->data = data;
+		cbdata->destroy_data = destroy_data;
+		g_signal_connect_data (job, "complete", G_CALLBACK (import_job_callback_cb), cbdata, (GClosureNotify) import_job_callback_destroy, 0);
+	}
 	return TRUE;
 }
 
diff --git a/sources/rb-podcast-source.c b/sources/rb-podcast-source.c
index 383a0e2..5bbda4e 100644
--- a/sources/rb-podcast-source.c
+++ b/sources/rb-podcast-source.c
@@ -255,7 +255,13 @@ static void impl_get_status				(RBSource *source,
 							 char **progress_text,
 							 float *progress);
 static guint impl_want_uri				(RBSource *source, const char *uri);
-static gboolean impl_add_uri				(RBSource *source, const char *uri, const char *title, const char *genre);
+static gboolean impl_add_uri				(RBSource *source,
+							 const char *uri,
+							 const char *title,
+							 const char *genre,
+							 RBSourceAddCallback callback,
+							 gpointer data,
+							 GDestroyNotify destroy_data);
 static char *impl_get_delete_action			(RBSource *source);
 
 #define CMD_PATH_SHOW_BROWSER "/commands/ShowBrowser"
@@ -2066,10 +2072,18 @@ impl_want_uri (RBSource *source, const char *uri)
 }
 
 static gboolean
-impl_add_uri (RBSource *asource, const char *uri, const char *title, const char *genre)
+impl_add_uri (RBSource *asource,
+	      const char *uri,
+	      const char *title,
+	      const char *genre,
+	      RBSourceAddCallback callback,
+	      gpointer data,
+	      GDestroyNotify destroy_data)
 {
 	RBPodcastSource *source = RB_PODCAST_SOURCE (asource);
 	rb_podcast_manager_subscribe_feed (source->priv->podcast_mgr, uri, FALSE);
+	callback (asource, uri, data);
+	destroy_data (data);
 	return TRUE;
 }
 
diff --git a/sources/rb-source.c b/sources/rb-source.c
index 04004e4..57d1ae0 100644
--- a/sources/rb-source.c
+++ b/sources/rb-source.c
@@ -1387,6 +1387,9 @@ rb_source_uri_is_source (RBSource *source, const char *uri)
  * @uri: a URI to add
  * @title: theoretically, the title of the entity the URI points to
  * @genre: theoretically, the genre of the entity the URI points to
+ * @callback: a callback function to call when complete
+ * @data: data to pass to the callback
+ * @destroy_data: function to call to destroy the callback data
  *
  * Adds an entry corresponding to the URI to the source.  The
  * @title and @genre parameters are not really used.
@@ -1394,11 +1397,17 @@ rb_source_uri_is_source (RBSource *source, const char *uri)
  * Return value: TRUE if the URI was successfully added to the source
  */
 gboolean
-rb_source_add_uri (RBSource *source, const char *uri, const char *title, const char *genre)
+rb_source_add_uri (RBSource *source,
+		   const char *uri,
+		   const char *title,
+		   const char *genre,
+		   RBSourceAddCallback callback,
+		   gpointer data,
+		   GDestroyNotify destroy_data)
 {
 	RBSourceClass *klass = RB_SOURCE_GET_CLASS (source);
 	if (klass->impl_add_uri)
-		return klass->impl_add_uri (source, uri, title, genre);
+		return klass->impl_add_uri (source, uri, title, genre, callback, data, destroy_data);
 	return FALSE;
 }
 
diff --git a/sources/rb-source.h b/sources/rb-source.h
index 4bc33ce..34b2a6f 100644
--- a/sources/rb-source.h
+++ b/sources/rb-source.h
@@ -76,6 +76,7 @@ GType rb_source_search_type_get_type (void);
 
 typedef gboolean (*RBSourceFeatureFunc) (RBSource *source);
 typedef const char * (*RBSourceStringFunc) (RBSource *source);
+typedef void (*RBSourceAddCallback) (RBSource *source, const char *uri, gpointer data);
 
 struct _RBSource
 {
@@ -126,7 +127,13 @@ struct _RBSourceClass
 
 	gboolean	(*impl_try_playlist)	(RBSource *source);
 	guint		(*impl_want_uri)	(RBSource *source, const char *uri);
-	gboolean	(*impl_add_uri)		(RBSource *source, const char *uri, const char *title, const char *genre);
+	gboolean	(*impl_add_uri)		(RBSource *source,
+						 const char *uri,
+						 const char *title,
+						 const char *genre,
+						 RBSourceAddCallback callback,
+						 gpointer data,
+						 GDestroyNotify destroy_data);
 	gboolean	(*impl_uri_is_source)	(RBSource *source, const char *uri);
 
 	gboolean	(*impl_can_pause)	(RBSource *source);
@@ -196,7 +203,13 @@ void		rb_source_song_properties	(RBSource *source);
 gboolean	rb_source_try_playlist		(RBSource *source);
 guint		rb_source_want_uri		(RBSource *source, const char *uri);
 gboolean	rb_source_uri_is_source		(RBSource *source, const char *uri);
-gboolean	rb_source_add_uri		(RBSource *source, const char *uri, const char *title, const char *genre);
+gboolean	rb_source_add_uri		(RBSource *source,
+						 const char *uri,
+						 const char *title,
+						 const char *genre,
+						 RBSourceAddCallback callback,
+						 gpointer data,
+						 GDestroyNotify destroy_data);
 
 gboolean	rb_source_can_pause		(RBSource *source);
 RBSourceEOFType	rb_source_handle_eos		(RBSource *source);



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