Commit c7c18fac authored by Aaron Bockover's avatar Aaron Bockover

Support Amazon MP3 music previews/samples

Add mimetype propagation on the download callbacks in Ossifer so we know
what kind of content we are handling.

Support audio/x-mpegurl playback directly in the Banshee Player Engine.

Disable the default WebKit context menu, since it can invoke actions we
don't really support.
parent 0fe0aa1f
......@@ -32,9 +32,9 @@ namespace Banshee.WebBrowser
public class OssiferWebView : Gtk.Widget
{
private delegate OssiferNavigationResponse MimeTypePolicyDecisionRequestedCallback (IntPtr ossifer, IntPtr mimetype);
private delegate IntPtr DownloadRequestedCallback (IntPtr ossifer, IntPtr uri, IntPtr suggested_filename);
private delegate IntPtr DownloadRequestedCallback (IntPtr ossifer, IntPtr mimetype, IntPtr uri, IntPtr suggested_filename);
private delegate void DocumentLoadFinishedCallback (IntPtr ossifer, IntPtr uri);
private delegate void DownloadStatusChangedCallback (IntPtr ossifer, OssiferDownloadStatus status, IntPtr destnation_uri);
private delegate void DownloadStatusChangedCallback (IntPtr ossifer, OssiferDownloadStatus status, IntPtr mimetype, IntPtr destnation_uri);
[StructLayout (LayoutKind.Sequential)]
private struct Callbacks
......@@ -71,15 +71,15 @@ namespace Banshee.WebBrowser
Initialize ();
CreateNativeObject (new string[0], new GLib.Value[0]);
ossifer_web_view_set_callbacks (Handle, callbacks = new Callbacks () {
callbacks = new Callbacks () {
MimeTypePolicyDecisionRequested =
new MimeTypePolicyDecisionRequestedCallback (HandleMimeTypePolicyDecisionRequested),
DownloadRequested = new DownloadRequestedCallback (HandleDownloadRequested),
DocumentLoadFinished = new DocumentLoadFinishedCallback (HandleDocumentLoadFinished),
DownloadStatusChanged = new DownloadStatusChangedCallback (HandleDownloadStatusChanged)
});
};
GC.KeepAlive (callbacks);
ossifer_web_view_set_callbacks (Handle, callbacks);
}
#region Callback Implementations
......@@ -94,9 +94,10 @@ namespace Banshee.WebBrowser
return OssiferNavigationResponse.Unhandled;
}
private IntPtr HandleDownloadRequested (IntPtr ossifer, IntPtr uri, IntPtr suggested_filename)
private IntPtr HandleDownloadRequested (IntPtr ossifer, IntPtr mimetype, IntPtr uri, IntPtr suggested_filename)
{
var destination_uri = OnDownloadRequested (
GLib.Marshaller.Utf8PtrToString (mimetype),
GLib.Marshaller.Utf8PtrToString (uri),
GLib.Marshaller.Utf8PtrToString (suggested_filename));
return destination_uri == null
......@@ -104,7 +105,7 @@ namespace Banshee.WebBrowser
: GLib.Marshaller.StringToPtrGStrdup (destination_uri);
}
protected virtual string OnDownloadRequested (string uri, string suggestedFilename)
protected virtual string OnDownloadRequested (string mimetype, string uri, string suggestedFilename)
{
return null;
}
......@@ -122,12 +123,14 @@ namespace Banshee.WebBrowser
}
}
private void HandleDownloadStatusChanged (IntPtr ossifer, OssiferDownloadStatus status, IntPtr destinationUri)
private void HandleDownloadStatusChanged (IntPtr ossifer, OssiferDownloadStatus status, IntPtr mimetype, IntPtr destinationUri)
{
OnDownloadStatusChanged (status, GLib.Marshaller.Utf8PtrToString (destinationUri));
OnDownloadStatusChanged (status,
GLib.Marshaller.Utf8PtrToString (mimetype),
GLib.Marshaller.Utf8PtrToString (destinationUri));
}
protected virtual void OnDownloadStatusChanged (OssiferDownloadStatus status, string destinationUri)
protected virtual void OnDownloadStatusChanged (OssiferDownloadStatus status, string mimetype, string destinationUri)
{
}
......
......@@ -37,13 +37,13 @@ typedef WebKitNavigationResponse (* OssiferWebViewMimeTypePolicyDecisionRequeste
(OssiferWebView *ossifer, const gchar *mimetype);
typedef gchar * (* OssiferWebViewDownloadRequestedCallback)
(OssiferWebView *ossifer, const gchar *uri, const gchar *suggested_filename);
(OssiferWebView *ossifer, const gchar *mimetype, const gchar *uri, const gchar *suggested_filename);
typedef void (* OssiferWebViewDocumentLoadFinishedCallback)
(OssiferWebView *ossifer, const gchar *uri);
typedef void (* OssiferWebViewDownloadStatusChanged)
(OssiferWebView *ossifer, WebKitDownloadStatus status, const gchar *uri);
(OssiferWebView *ossifer, WebKitDownloadStatus status, const gchar *mimetype, const gchar *uri);
typedef struct {
OssiferWebViewMimeTypePolicyDecisionRequestedCallback mime_type_policy_decision_requested;
......@@ -60,6 +60,15 @@ struct OssiferWebViewPrivate {
// OssiferWebView Internal Implementation
// ---------------------------------------------------------------------------
static const gchar *
ossifer_web_view_download_get_mimetype (WebKitDownload *download)
{
return soup_message_headers_get_content_type (
webkit_network_response_get_message (
webkit_download_get_network_response (download)
)->response_headers, NULL);
}
static WebKitWebView *
ossifer_web_view_create_web_view (WebKitWebView *web_view, WebKitWebFrame *web_frame)
{
......@@ -103,6 +112,7 @@ ossifer_web_view_download_notify_status (GObject* object, GParamSpec* pspec, gpo
if (ossifer->priv->callbacks.download_status_changed != NULL) {
ossifer->priv->callbacks.download_status_changed (ossifer,
webkit_download_get_status (download),
ossifer_web_view_download_get_mimetype (download),
webkit_download_get_destination_uri (download));
}
}
......@@ -116,6 +126,7 @@ ossifer_web_view_download_requested (WebKitWebView *web_view, WebKitDownload *do
if (ossifer->priv->callbacks.download_requested == NULL ||
(destination_uri = ossifer->priv->callbacks.download_requested (
ossifer,
ossifer_web_view_download_get_mimetype (download),
webkit_download_get_uri (download),
webkit_download_get_suggested_filename (download))) == NULL) {
return FALSE;
......@@ -172,7 +183,10 @@ ossifer_web_view_init (OssiferWebView *ossifer)
ossifer->priv = G_TYPE_INSTANCE_GET_PRIVATE (ossifer, OSSIFER_TYPE_WEB_VIEW, OssiferWebViewPrivate);
g_object_get (ossifer, "settings", &settings, NULL);
g_object_set (settings, "enable-plugins", FALSE, NULL);
g_object_set (settings,
"enable-plugins", FALSE,
"enable-default-context-menu", FALSE,
NULL);
g_signal_connect (ossifer, "mime-type-policy-decision-requested",
G_CALLBACK (ossifer_web_view_mime_type_policy_decision_requested), NULL);
......
......@@ -55,25 +55,44 @@ namespace Banshee.AmazonMp3.Store
// download audio/x-amzxml - everything else is ignored.
switch (mimetype) {
case "text/html": return OssiferNavigationResponse.Accept;
case "audio/x-mpegurl":
case "audio/x-amzxml": return OssiferNavigationResponse.Download;
default: return OssiferNavigationResponse.Ignore;
default:
Log.Debug ("OssiferWebView: ignoring mime type", mimetype);
return OssiferNavigationResponse.Ignore;
}
}
protected override string OnDownloadRequested (string uri, string suggestedFilename)
protected override string OnDownloadRequested (string mimetype, string uri, string suggestedFilename)
{
var dest_uri_base = "file://" + Paths.Combine (Paths.TempDir, suggestedFilename);
var dest_uri = new SafeUri (dest_uri_base);
for (int i = 1; File.Exists (dest_uri);
dest_uri = new SafeUri (String.Format ("{0} ({1})", dest_uri_base, ++i)));
return dest_uri.AbsoluteUri;
switch (mimetype) {
case "audio/x-amzurl":
var dest_uri_base = "file://" + Paths.Combine (Paths.TempDir, suggestedFilename);
var dest_uri = new SafeUri (dest_uri_base);
for (int i = 1; File.Exists (dest_uri);
dest_uri = new SafeUri (String.Format ("{0} ({1})", dest_uri_base, ++i)));
return dest_uri.AbsoluteUri;
case "audio/x-mpegurl":
Banshee.Streaming.RadioTrackInfo.OpenPlay (uri);
return null;
}
return null;
}
protected override void OnDownloadStatusChanged (OssiferDownloadStatus status, string destinationUri)
protected override void OnDownloadStatusChanged (OssiferDownloadStatus status, string mimetype, string destinationUri)
{
if (status == OssiferDownloadStatus.Finished) {
Banshee.ServiceStack.ServiceManager.Get<AmazonMp3DownloaderService> ()
.DownloadAmz (new SafeUri (destinationUri).LocalPath);
// FIXME: handle the error case
if (status != OssiferDownloadStatus.Finished) {
return;
}
switch (mimetype) {
case "audio/x-amzurl":
Log.Debug ("OssiferWebView: downloaded purchase list", destinationUri);
Banshee.ServiceStack.ServiceManager.Get<AmazonMp3DownloaderService> ()
.DownloadAmz (new SafeUri (destinationUri).LocalPath);
break;
}
}
}
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment