[rygel] core: Allow plugins to provide thumbnails
- From: Zeeshan Ali Khattak <zeeshanak src gnome org>
- To: svn-commits-list gnome org
- Cc:
- Subject: [rygel] core: Allow plugins to provide thumbnails
- Date: Tue, 8 Sep 2009 16:23:17 +0000 (UTC)
commit 4d9b1428e8df65da170b895f3bd981f65caf09e7
Author: Zeeshan Ali (Khattak) <zeeshanak gnome org>
Date: Sun Sep 6 02:44:11 2009 +0300
core: Allow plugins to provide thumbnails
Plugins can now provide thumnails using a new easy-to-use API.
src/rygel/Makefile.am | 1 +
src/rygel/rygel-http-identity-handler.vala | 40 +++++++++++---
src/rygel/rygel-http-request.vala | 12 ++++
src/rygel/rygel-http-server.vala | 29 ++++++++++-
src/rygel/rygel-media-item.vala | 12 ++++
src/rygel/rygel-thumbnail.vala | 76 ++++++++++++++++++++++++++++
src/rygel/rygel-transcode-manager.vala | 1 +
src/rygel/rygel-transcoder.vala | 1 +
8 files changed, 160 insertions(+), 12 deletions(-)
---
diff --git a/src/rygel/Makefile.am b/src/rygel/Makefile.am
index e9e289e..85d42a3 100644
--- a/src/rygel/Makefile.am
+++ b/src/rygel/Makefile.am
@@ -66,6 +66,7 @@ VAPI_SOURCE_FILES = rygel-configuration.vala \
rygel-media-container.vala \
rygel-simple-async-result.vala \
rygel-media-item.vala \
+ rygel-thumbnail.vala \
rygel-browse.vala \
rygel-didl-lite-writer.vala \
rygel-transcoder.vala \
diff --git a/src/rygel/rygel-http-identity-handler.vala b/src/rygel/rygel-http-identity-handler.vala
index e473927..ec46794 100644
--- a/src/rygel/rygel-http-identity-handler.vala
+++ b/src/rygel/rygel-http-identity-handler.vala
@@ -30,20 +30,30 @@ internal class Rygel.HTTPIdentityHandler : Rygel.HTTPRequestHandler {
public override void add_response_headers (HTTPRequest request)
throws HTTPRequestError {
- var item = request.item;
+ long size;
+ string mime_type;
- request.msg.response_headers.append ("Content-Type", item.mime_type);
- if (item.size >= 0) {
- request.msg.response_headers.set_content_length (item.size);
+ if (request.thumbnail != null) {
+ size = request.thumbnail.size;
+ mime_type= request.thumbnail.mime_type;
+ } else {
+ size = request.item.size;
+ mime_type= request.item.mime_type;
}
- if (item.should_stream ()) {
+
+ request.msg.response_headers.append ("Content-Type", mime_type);
+ if (size >= 0) {
+ request.msg.response_headers.set_content_length (size);
+ }
+
+ if (request.thumbnail == null && request.item.should_stream ()) {
if (request.time_range != null) {
request.time_range.add_response_header (request.msg);
}
} else {
request.msg.response_headers.append ("Accept-Ranges", "bytes");
if (request.byte_range != null) {
- request.byte_range.add_response_header (request.msg, item.size);
+ request.byte_range.add_response_header (request.msg, size);
}
}
@@ -53,6 +63,14 @@ internal class Rygel.HTTPIdentityHandler : Rygel.HTTPRequestHandler {
public override HTTPResponse render_body (HTTPRequest request)
throws HTTPRequestError {
+ if (request.thumbnail != null) {
+ return new SeekableResponse (request.server,
+ request.msg,
+ request.thumbnail.uri,
+ request.byte_range,
+ request.thumbnail.size);
+ }
+
var item = request.item;
if (item.should_stream ()) {
@@ -84,8 +102,12 @@ internal class Rygel.HTTPIdentityHandler : Rygel.HTTPRequestHandler {
protected override DIDLLiteResource add_resource (DIDLLiteItem didl_item,
HTTPRequest request)
throws HTTPRequestError {
- return request.item.add_resource (didl_item,
- null,
- request.http_server.get_protocol ());
+ var protocol = request.http_server.get_protocol ();
+
+ if (request.thumbnail != null) {
+ return request.thumbnail.add_resource (didl_item, protocol);
+ } else {
+ return request.item.add_resource (didl_item, null, protocol);
+ }
}
}
diff --git a/src/rygel/rygel-http-request.vala b/src/rygel/rygel-http-request.vala
index 580d11c..2299d7f 100644
--- a/src/rygel/rygel-http-request.vala
+++ b/src/rygel/rygel-http-request.vala
@@ -44,7 +44,9 @@ internal class Rygel.HTTPRequest : GLib.Object, Rygel.StateMachine {
private HTTPResponse response;
private string item_id;
+ private int thumbnail_index;
public MediaItem item;
+ public Thumbnail thumbnail;
public HTTPSeek byte_range;
public HTTPSeek time_range;
@@ -61,6 +63,7 @@ internal class Rygel.HTTPRequest : GLib.Object, Rygel.StateMachine {
this.server = server;
this.msg = msg;
this.query = query;
+ this.thumbnail_index = -1;
}
public void run (Cancellable? cancellable) {
@@ -86,6 +89,11 @@ internal class Rygel.HTTPRequest : GLib.Object, Rygel.StateMachine {
var transcoder = this.http_server.get_transcoder (target);
this.request_handler = new HTTPTranscodeHandler (transcoder);
}
+
+ var index = this.query.lookup ("thumbnail");
+ if (index != null) {
+ this.thumbnail_index = index.to_int ();
+ }
}
if (this.item_id == null) {
@@ -151,6 +159,10 @@ internal class Rygel.HTTPRequest : GLib.Object, Rygel.StateMachine {
this.item = (MediaItem) media_object;
+ if (this.thumbnail_index >= 0) {
+ this.thumbnail = this.item.thumbnails.get (this.thumbnail_index);
+ }
+
this.handle_item_request ();
}
diff --git a/src/rygel/rygel-http-server.vala b/src/rygel/rygel-http-server.vala
index d583aac..0d06b7e 100644
--- a/src/rygel/rygel-http-server.vala
+++ b/src/rygel/rygel-http-server.vala
@@ -67,11 +67,29 @@ internal class Rygel.HTTPServer : Rygel.TranscodeManager, Rygel.StateMachine {
if (!this.http_uri_present (item)) {
// Create the HTTP proxy URI
string protocol;
- var uri = this.create_uri_for_item (item, null, out protocol);
+ var uri = this.create_uri_for_item (item, -1, null, out protocol);
item.add_resource (didl_item, uri, protocol);
}
base.add_resources (didl_item, item);
+
+ // Thumbnails comes in the end
+ foreach (var thumbnail in item.thumbnails) {
+ if (!is_http_uri (thumbnail.uri)) {
+ var uri = thumbnail.uri; // Save the original URI
+ var index = item.thumbnails.index_of (thumbnail);
+ string protocol;
+
+ thumbnail.uri = this.create_uri_for_item (item,
+ index,
+ null,
+ out protocol);
+ thumbnail.add_resource (didl_item, protocol);
+
+ // Now restore the original URI
+ thumbnail.uri = uri;
+ }
+ }
}
private bool http_uri_present (MediaItem item) {
@@ -104,11 +122,16 @@ internal class Rygel.HTTPServer : Rygel.TranscodeManager, Rygel.StateMachine {
path);
}
- internal override string create_uri_for_item (MediaItem item,
- string? transcode_target,
+ internal override string create_uri_for_item (MediaItem item,
+ int thumbnail_index,
+ string? transcode_target,
out string protocol) {
string escaped = Uri.escape_string (item.id, "", true);
string query = "?itemid=" + escaped;
+ if (thumbnail_index >= 0) {
+ query += "&thumbnail=" + thumbnail_index.to_string ();
+ }
+
if (transcode_target != null) {
escaped = Uri.escape_string (transcode_target, "", true);
query += "&transcode=" + escaped;
diff --git a/src/rygel/rygel-media-item.vala b/src/rygel/rygel-media-item.vala
index 1e2e2d1..40dcca7 100644
--- a/src/rygel/rygel-media-item.vala
+++ b/src/rygel/rygel-media-item.vala
@@ -63,6 +63,8 @@ public class Rygel.MediaItem : MediaObject {
public int pixel_height = -1;
public int color_depth = -1;
+ public ArrayList<Thumbnail> thumbnails;
+
public MediaItem (string id,
MediaContainer parent,
string title,
@@ -71,6 +73,8 @@ public class Rygel.MediaItem : MediaObject {
this.parent = parent;
this.title = title;
this.upnp_class = upnp_class;
+
+ this.thumbnails = new ArrayList<Thumbnail> ();
}
// Live media items need to provide a nice working implementation of this
@@ -117,6 +121,14 @@ public class Rygel.MediaItem : MediaObject {
this.add_resource (didl_item, uri, protocol);
}
}
+
+ foreach (var thumbnail in this.thumbnails) {
+ var protocol = this.get_protocol_for_uri (thumbnail.uri);
+
+ if (allow_internal || protocol != "internal") {
+ thumbnail.add_resource (didl_item, protocol);
+ }
+ }
}
internal DIDLLiteResource add_resource (DIDLLiteItem didl_item,
diff --git a/src/rygel/rygel-thumbnail.vala b/src/rygel/rygel-thumbnail.vala
new file mode 100644
index 0000000..63f5e7d
--- /dev/null
+++ b/src/rygel/rygel-thumbnail.vala
@@ -0,0 +1,76 @@
+/*
+ * Copyright (C) 2008 Zeeshan Ali <zeenix gmail com>.
+ *
+ * Author: Zeeshan Ali <zeenix gmail com>
+ *
+ * This file is part of Rygel.
+ *
+ * Rygel is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU Lesser General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * Rygel is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * along with this program; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ */
+
+using GUPnP;
+
+private errordomain Rygel.ThumbnailError {
+ BAD_URI
+}
+
+/**
+ * Represents a picture or video thumbnail.
+ */
+public class Rygel.Thumbnail : GLib.Object {
+ public string uri;
+ public string mime_type;
+ public string dlna_profile;
+
+ public long size = -1; // Size in bytes
+ public int width = -1; // Width in pixels
+ public int height = -1; // Height in pixels
+ public int color_depth = -1; // depth of pixels in bytes
+
+ public Thumbnail (string mime_type = "image/jpeg",
+ string dlna_profile = "JPEG_TN") {
+ this.mime_type = mime_type;
+ this.dlna_profile = dlna_profile;
+ }
+
+ internal DIDLLiteResource add_resource (DIDLLiteItem didl_item,
+ string protocol) {
+ var res = didl_item.add_resource ();
+
+ res.uri = this.uri;
+ res.size = this.size;
+
+ res.width = this.width;
+ res.height = this.height;
+ res.color_depth = this.color_depth;
+
+ /* Protocol info */
+ res.protocol_info = this.get_protocol_info (protocol);
+
+ return res;
+ }
+
+ private ProtocolInfo get_protocol_info (string protocol) {
+ var protocol_info = new ProtocolInfo ();
+
+ protocol_info.mime_type = this.mime_type;
+ protocol_info.dlna_profile = this.dlna_profile;
+ protocol_info.protocol = protocol;
+ protocol_info.dlna_flags |= DLNAFlags.INTERACTIVE_TRANSFER_MODE |
+ DLNAFlags.BACKGROUND_TRANSFER_MODE;
+
+ return protocol_info;
+ }
+}
diff --git a/src/rygel/rygel-transcode-manager.vala b/src/rygel/rygel-transcode-manager.vala
index fe15db8..5bb002e 100644
--- a/src/rygel/rygel-transcode-manager.vala
+++ b/src/rygel/rygel-transcode-manager.vala
@@ -53,6 +53,7 @@ internal abstract class Rygel.TranscodeManager : GLib.Object {
}
public abstract string create_uri_for_item (MediaItem item,
+ int thumbnail_index,
string? transcode_target,
out string protocol);
diff --git a/src/rygel/rygel-transcoder.vala b/src/rygel/rygel-transcoder.vala
index f13a313..d16d4ca 100644
--- a/src/rygel/rygel-transcoder.vala
+++ b/src/rygel/rygel-transcoder.vala
@@ -66,6 +66,7 @@ internal abstract class Rygel.Transcoder : GLib.Object {
string protocol;
var uri = manager.create_uri_for_item (item,
+ -1,
this.dlna_profile,
out protocol);
var res = item.add_resource (didl_item, uri, protocol);
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]