Added Media page
authorveltr
Fri, 23 Nov 2012 19:13:50 +0100
changeset 49 a21b851538b2
parent 48 2774e46c3e9d
child 50 89e152523cb6
Added Media page
integration/css/hashcut.css
integration/edition.html
integration/hashcut.html
integration/js/contentapi-serializer.js
integration/js/editor.js
integration/js/i18n.js
integration/js/mashupplayer.js
integration/js/mediaplayer.js
integration/js/segmentapi-serializer.js
integration/js/social.js
--- a/integration/css/hashcut.css	Thu Nov 22 18:45:06 2012 +0100
+++ b/integration/css/hashcut.css	Fri Nov 23 19:13:50 2012 +0100
@@ -83,3 +83,6 @@
 .frise-segment {
     cursor: pointer;
 }
+.segment-info .pointer {
+    margin-left: -10px;
+}
--- a/integration/edition.html	Thu Nov 22 18:45:06 2012 +0100
+++ b/integration/edition.html	Fri Nov 23 19:13:50 2012 +0100
@@ -353,20 +353,32 @@
         <script type="text/javascript" src="lib/underscore-min.js"></script>
         <script type="text/javascript" src="lib/popcorn-complete.min.js"></script>
         <script type="text/javascript" src="js/init.js"></script>
+        <script type="text/javascript" src="js/i18n.js"></script>
         <script type="text/javascript" src="js/ldt-serializer.js"></script>
         <script type="text/javascript" src="js/medialist-serializer.js"></script>
+        <script type="text/javascript" src="js/contentapi-serializer.js"></script>
         <script type="text/javascript" src="js/segmentapi-serializer.js"></script>
         <script type="text/javascript" src="js/model.js"></script>
         <script type="text/javascript" src="js/mashupcore.js"></script>
         <script type="text/javascript" src="js/editor.js"></script>
         <script type="text/javascript" src="js/common.js"></script>
         <script type="text/javascript">
+        
+    IriSP.endpoints = {
+        content: "/pf/ldtplatform/api/ldt/1.0/contents/",
+        project: "/pf/ldtplatform/api/ldt/1.0/projects/",
+        segment: "/pf/ldtplatform/api/ldt/1.0/segments/",
+        ldt: "http://capsicum//pf/ldtplatform/ldt/cljson/id/",
+        hashcut_page: "hashcut.html?project="
+    };
+    
     $(function() {
         var hashcut = IriSP.editor({
            //url: "data/bpidata.json",
-           url: "data/moon-local.json",
-           segment_api_endpoint: "http://capsicum/pf/ldtplatform/api/ldt/1.0/segments/",
-           project_api_endpoint: "http://capsicum/pf/ldtplatform/api/ldt/1.0/projects/"
+           //url: "data/moon-local.json",
+           filter: {
+               tags__icontains: "Hashcut"
+           }
        });
     });
         </script>
--- a/integration/hashcut.html	Thu Nov 22 18:45:06 2012 +0100
+++ b/integration/hashcut.html	Fri Nov 23 19:13:50 2012 +0100
@@ -227,7 +227,7 @@
                                     </tr> -->
                                 </tbody>
                             </table>
-                            <a href="#" class="button cloner">Cloner le Hashcut</a>
+    <!--                        <a href="#" class="button cloner">Cloner le Hashcut</a> -->
                         </div>
                         <h2>Médias utilisés dans le Hashcut</h2>
                         <ul class="list-video">
@@ -257,20 +257,35 @@
         <script type="text/javascript" src="lib/jquery-ui.min.js"></script>
         <script type="text/javascript" src="lib/underscore-min.js"></script>
         <script type="text/javascript" src="lib/popcorn-complete.min.js"></script>
+        <script type="text/javascript" src="lib/ZeroClipboard.js"></script>
         <script type="text/javascript" src="js/init.js"></script>
         <script type="text/javascript" src="js/ldt-serializer.js"></script>
+        <script type="text/javascript" src="js/contentapi-serializer.js"></script>
         <script type="text/javascript" src="js/model.js"></script>
         <script type="text/javascript" src="js/mashupcore.js"></script>
         <script type="text/javascript" src="js/mashupplayer.js"></script>
         <script type="text/javascript" src="js/common.js"></script>
         <script type="text/javascript" src="js/social.js"></script>
         <script type="text/javascript">
-            $(function() {
-                IriSP.player({
-                    url: "data/moon-mashup.json"
-//                    url: "http://capsicum/pf/ldtplatform/ldt/cljson/id/d204aa58-2cf2-11e2-a234-08002791f1b7"
-                })
-            })
+        
+    IriSP.endpoints = {
+        content: "/pf/ldtplatform/api/ldt/1.0/contents/",
+        project: "/pf/ldtplatform/api/ldt/1.0/projects/",
+        segment: "/pf/ldtplatform/api/ldt/1.0/segments/",
+        ldt: "http://capsicum//pf/ldtplatform/ldt/cljson/id/",
+        media_page: "media.html?media="
+    };
+    
+    var projrx = /project=([^&#]+)/,
+        match = document.location.href.match(projrx),
+        projid = match ? match[1] : "d204aa58-2cf2-11e2-a234-08002791f1b7";
+    
+    $(function() {
+        IriSP.mashupplayer({
+            id: projid
+        });
+        IriSP.social();
+    });
         </script>
     </body>
 </html>
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/integration/js/contentapi-serializer.js	Fri Nov 23 19:13:50 2012 +0100
@@ -0,0 +1,26 @@
+IriSP.serializers.content = {
+    deSerialize : function(_data, _source) {
+        var colors = ["#1f77b4","#ff7f0e","#2ca02c","#d62728","#9467bd","#8c564b","#e377c2","#7f7f7f","#bcbd22","#17becf"];
+        var _medialist = new IriSP.Model.List(_source.directory);
+        
+        function deserializeObject(_m, i) {
+            var _media = new IriSP.Model.Media(_m.iri_id, _source);
+            _media.video = _m.media_url;
+            _media.title = _m.title;
+            _media.description = _m.description;
+            _media.setDuration(_m.duration);
+            _media.thumbnail = _m.image;
+            _media.color = colors[i % colors.length];
+            _media.keywords = _m.tags;
+            _medialist.push(_media);
+        }
+        
+        if (typeof _data.objects !== "undefined") {
+            IriSP._(_data.objects).each(deserializeObject);
+        } else {
+            deserializeObject(_data, 0);
+        }
+        
+        _source.addList("media", _medialist);
+    }
+}
\ No newline at end of file
--- a/integration/js/editor.js	Thu Nov 22 18:45:06 2012 +0100
+++ b/integration/js/editor.js	Fri Nov 23 19:13:50 2012 +0100
@@ -1,19 +1,3 @@
-
-IriSP.hc_messages = {
-    Duration_ : "Durée :",
-    duration_ : "durée :",
-    edit_segment: "Éditer le segment",
-    segment_down: "Descendre le segment",
-    segment_up: "Remonter le segment",
-    delete_segment: "Supprimer le segment",
-    clone_segment: "Cloner le segment",
-    From_: "De :",
-    to_: "à :",
-    segment_title_placeholder: "Segment sans titre",
-    mashup_title_placeholder: "Hashcut sans titre",
-    copy_of_: "Copie de ",
-}
-
 IriSP.editor = function(options) {
     
     /* Load Media List */
@@ -21,30 +5,36 @@
     var directory = new IriSP.Model.Directory(),
         apidirectory = new IriSP.Model.Directory(),
         project = directory.remoteSource({
+            url: IriSP.endpoints.content,
+            url_params: _({}).extend(options.filter),
+            serializer: IriSP.serializers.content
+        }),
+/*        project = directory.remoteSource({
             url: options.url,
             serializer: IriSP.serializers.medialist
         }),
+*/
         mashup = new IriSP.Model.Mashup(false, project),
         mediatemplate = _.template(
             '<li class="item-video media" data-media-id="<%= id %>"><div class="media-count-wrap"><span class="media-count"></span></div>'
             + '<img class="thumbnail" src="<%= thumbnail %>" alt="<%= title %>" />'
             + '<div class="video-info"><h3 class="title-video"><%= title %></h3><p class="description"><%= description %></p>'
-            + '<p class="time-length"><%= IriSP.hc_messages.Duration_ %> <span><%= duration.toString() %></span></p></div><div class="media-found-segments"></div></li>'
+            + '<p class="time-length"><%= IriSP.translate("Duration:") %> <span><%= duration.toString() %></span></p></div><div class="media-found-segments"></div></li>'
         ),
         segmenttemplate = _.template(
             '<li class="item-video annotation" data-segment-id="<%= annotation.id %>" data-media-id="<%= annotation.getMedia().id %>">'
             + '<img class="thumbnail" src="<%= annotation.thumbnail %>" alt="<%= annotation.getMedia().title %>" />'
             + '<div class="validate <%= annotation.status %>"><div class="validate-tooltip"><ul><li><%= annotation.status_messages.join("</li><li>") %></li></ul></div></div><div class="video-info"><h3 class="title-video"><%= annotation.getMedia().title %></h3>'
             + '<p class="subtitle"><%= annotation.title %></p><p class="duration"><%= annotation.begin.toString() %> - <%= annotation.end.toString() %> (<%= annotation.getDuration().toString() %>)</p>'
-            + '<ul class="tools"><li><a class="edit" href="#" title="<%= IriSP.hc_messages.edit_segment %>"></a></li><li><a class="bottom" href="#" title="<%= IriSP.hc_messages.segment_down %>"></a></li>'
-            + '<li><a class="top" href="#" title="<%= IriSP.hc_messages.segment_up %>"></a></li><li><a class="delete" href="#" title="<%= IriSP.hc_messages.delete_segment %>"></a></li></ul></div></li>'
+            + '<ul class="tools"><li><a class="edit" href="#" title="<%= IriSP.translate("Edit segment") %>"></a></li><li><a class="bottom" href="#" title="<%= IriSP.translate("Move segment down") %>"></a></li>'
+            + '<li><a class="top" href="#" title="<%= IriSP.translate("Move segment up") %>"></a></li><li><a class="delete" href="#" title="<%= IriSP.translate("Delete segment") %>"></a></li></ul></div></li>'
         ),
         mediasegmenttemplate = _.template(
             '<div class="media-segment">'
-            + '<div class="media-segment-section" style="left:<%= left %>px; width:<%= width %>px; background:<%= color %>; top: <%= top %>px;"></div>'
+            + '<div class="media-segment-section" style="left:<%= left %>px; width:<%= width %>px; background:<%= color %>; top: <%= top %>px;" data-segment-id="<%= annotation.id %>"></div>'
             + '<div class="popin media-segment-popin" style="left:<%= popleft %>px; top: <%= 5+top %>px;"><img style="left:<%= pointerpos %>px;" class="pointer" src="img/popin-triangle.png" alt="" /><div class="popin-content">'
-            + '<h3><%= annotation.title %></h3><a href="#" class="button reprendre-segment" data-segment-id="<%= annotation.id %>"><%= IriSP.hc_messages.clone_segment %></a>'
-            + '<p><%= IriSP.hc_messages.From_ %> <span><%= annotation.begin.toString() %></span> <%= IriSP.hc_messages.to_ %> <span><%= annotation.end.toString() %></span> (<%= IriSP.hc_messages.duration_ %> <span><%= annotation.getDuration().toString() %></span>)</p>'
+            + '<h3><%= annotation.title %></h3><a href="#" class="button reprendre-segment" data-segment-id="<%= annotation.id %>"><%= IriSP.translate("Clone segment") %></a>'
+            + '<p><%= IriSP.translate("From:") %> <span><%= annotation.begin.toString() %></span> <%= IriSP.translate("to:") %> <span><%= annotation.end.toString() %></span> (<%= IriSP.translate("duration:") %> <span><%= annotation.getDuration().toString() %></span>)</p>'
             + '</div></div></div>'
         ),
         mediasegmentlisttemplate = _.template(
@@ -53,7 +43,7 @@
         mediafoundtemplate = _.template(
             '<div class="media-segment"><div class="media-segment-section" style="left:<%= left %>px; width:<%= width %>px; background:<%= color %>; top: <%= top %>px;"></div>'
             + '<div class="popin media-found-popin" style="left:<%= popleft %>px; top: <%= 5+top %>px;"><img style="left:<%= pointerpos %>px;" class="pointer" src="img/popin-triangle.png" alt="" /><div class="popin-content">'
-            + '<h3><%= title %></h3><a href="#" class="button clone-segment" data-segment-id="<%= annotation.id %>"><%= IriSP.hc_messages.clone_segment %></a>'
+            + '<h3><%= title %></h3><a href="#" class="button clone-segment" data-segment-id="<%= annotation.id %>"><%= IriSP.translate("Clone segment") %></a>'
             + '</div></div></div>'
         ),
         mediafoundlisttemplate = _.template(
@@ -73,19 +63,19 @@
             validate: function(_s) {
                 return (_s.getDuration() >= 1000);
             },
-            message: "Le segment doit durer au moins une seconde"
+            message: "A segment must be at least one second long"
         },
         {
             validate: function(_s) {
                 return (_s.getDuration() < 180000);
             },
-            message: "Le segment doit durer moins de trois minutes"
+            message: "A segment must be at most three minutes long"
         },
         {
             validate: function(_s) {
-                return (!!_s.title && _s.title !== IriSP.hc_messages.segment_title_placeholder);
+                return (!!_s.title && _s.title !== IriSP.translate("Untitled segment"));
             },
-            message: "Le segment doit avoir un titre"
+            message: "A segment must have a title"
         }
     ];
     var segmentwarning = [
@@ -93,13 +83,13 @@
             validate: function(_s) {
                 return (!!_s.description);
             },
-            message: "Il est recommandé de donner une description au segment"
+            message: "A segment should have a description"
         },
         {
             validate: function(_s) {
                 return (!!_s.keywords.length);
             },
-            message: "Il est recommandé de tagguer le segment"
+            message: "A segment should have tags"
         }
     ];
     
@@ -108,13 +98,13 @@
             validate: function(_m) {
                 return _m.segments.length > 2;
             },
-            message: "Un hashcut doit être composé d'au moins trois segments"
+            message: "A hashcut must be made from at least three segments"
         },
         {
             validate: function(_m) {
-                return (!!_m.title && _m.title !== IriSP.hc_messages.mashup_title_placeholder);
+                return (!!_m.title && _m.title !== IriSP.translate("Untitled Hashcut"));
             },
-            message: "Un titre doit être donné au hashcut"
+            message: "A hashcut must have a title"
         }
     ];
     var mashupwarning = [
@@ -122,7 +112,7 @@
             validate: function(_m) {
                 return !!_m.description
             },
-            message: "Il est recommandé de donner une description au hashcut"
+            message: "A hashcut should have a description"
         }
     ];
 
@@ -136,7 +126,7 @@
         $(".col-left .list-video").html(html);
         project.getMedias().forEach(function(_m) {
             apidirectory.remoteSource({
-                url: options.segment_api_endpoint,
+                url: IriSP.endpoints.segment,
                 url_params: {
                     iri_id: _m.id,
                     limit: 0
@@ -238,7 +228,7 @@
             }
         });
         if (critical) {
-            messages.push("Certains segments ne sont pas valides");
+            messages.push("One or more segments are invalid");
         }
         
         _(mashupcritical).each(function(sc) {
@@ -255,9 +245,9 @@
         });
         mashup.status = critical ? "critical" : (warning ? "warning" : "valid");
         if (!messages.length) {
-            messages.push("Le hashcut est valide !");
+            messages.push("Your hashcut is valid!");
         }
-        mashupstatus = ' - ' + messages.join('\n - ');
+        mashupstatus = ' - ' + _(messages).map(IriSP.translate).join('\n - ');
         
         $(".publier-button").toggleClass("disable", critical);
         
@@ -360,9 +350,9 @@
             });
             currentSegment.status = critical ? "critical" : (warning ? "warning" : "valid");
             if (!messages.length) {
-                messages.push("Le segment est valide !")
+                messages.push("This segment is valid!")
             }
-            currentSegment.status_messages = messages;
+            currentSegment.status_messages = _(messages).map(IriSP.translate);
             
             $(".segmentation .validate").removeClass("critical warning valid").addClass(currentSegment.status);
             $(".segmentation .validate-tooltip").html("<ul><li>" + currentSegment.status_messages.join("</li><li>")+"</li></ul>");
@@ -388,7 +378,7 @@
                 currentSegment.setMedia(currentMedia.id);
                 currentSegment.setBegin(currentMedia.getCurrentTime());
                 currentSegment.setEnd(Math.min(currentMedia.getCurrentTime() +  180000, currentMedia.duration));
-                currentSegment.title = IriSP.hc_messages.segment_title_placeholder;
+                currentSegment.title = IriSP.translate("Untitled segment");
                 currentSegment.color = currentMedia.color;
                 currentSegment.thumbnail = currentMedia.thumbnail;
                 currentSegment.created = new Date();
@@ -410,8 +400,8 @@
             if (currentMedia.loaded) {
                 currentMedia.setCurrentTime(currentSegment.begin);
             }
-            $(".add-segment").val(addMode ? "Ajouter au Hashcut" : "Sauvegarder");
-            $(".create-or-edit").text(addMode ? "Créer un nouveau segment" : "Modifier le segment");
+            $(".add-segment").val(IriSP.translate(addMode ? "Add segment to hashcut" : "Save segment"));
+            $(".create-or-edit").text(IriSP.translate(addMode ? "Create new segment" : "Edit existing segment"));
             media.show();
             $("#segment-title").val(currentSegment.title);
             $("#segment-description").val(currentSegment.description);
@@ -514,7 +504,7 @@
         }
     });
     $("#segment-title").on("focus click", function() {
-        if ($(this).val() === IriSP.hc_messages.segment_title_placeholder) {
+        if ($(this).val() === IriSP.translate("Untitled segment")) {
             $(this).val("");
         }
     });
@@ -531,6 +521,7 @@
             setMedia(currentMedia);
         } else {
             mashup.trigger("change");
+            var segment = mashup.getAnnotation(currentSegment);
             currentSegment = undefined;
             setMedia(mashup);
             if (segment) {
@@ -735,7 +726,7 @@
         currentSegment.setMedia(media.id);
         currentSegment.setBegin(s.begin);
         currentSegment.setEnd(s.end);
-        currentSegment.title = IriSP.hc_messages.copy_of_ + s.title;
+        currentSegment.title = IriSP.translate("Copy of ") + s.title;
         currentSegment.description = s.description;
         currentSegment.keywords = s.keywords;
         currentSegment.color = media.color;
@@ -763,6 +754,12 @@
     }).on("click", ".reprendre-segment", function() {
         cloneSegment($(this).attr("data-segment-id"));
         return false;
+    }).on("click", ".media-segment-section", function() {
+        var sid = $(this).attr("data-segment-id"),
+            s = directory.getElement(sid) || apidirectory.getElement(sid);
+        if (s.media.id === currentMedia.id) {
+            currentMedia.setCurrentTime(s.begin);
+        }
     });
     
     $(".col-left").on("mouseover", ".media-segment", function() {
@@ -775,7 +772,7 @@
     });
     /* Changing Hashcut Title and description */
     
-    mashup.title = IriSP.hc_messages.mashup_title_placeholder;
+    mashup.title = IriSP.translate("Untitled Hashcut");
     $(".title-video-wrap a").text(mashup.title);
     $("#hashcut-title").val(mashup.title);
     
@@ -785,7 +782,7 @@
         mashup.trigger("change");
     });
     $("#hashcut-title").on("focus click", function() {
-        if ($(this).val() === IriSP.hc_messages.mashup_title_placeholder) {
+        if ($(this).val() === IriSP.translate("Untitled Hashcut")) {
             $(this).val("");
         }
     });
@@ -802,9 +799,15 @@
     
     /* Publication */
    
+    function onLeave() {
+        return IriSP.translate("You haven't published your hashcut yet.\nIf you leave this page, it will be lost");
+    }
+    
+    $(window).on("beforeunload", onLeave);
+   
     $(".publier-button").click(function() {
         if ($(this).hasClass("disable")) {
-            alert("Le Mashup ne peut pas être publié pour les raisons suivantes :\n\n"+mashupstatus);
+            alert(IriSP.translate("The mashup can't be published because:")+"\n\n"+mashupstatus);
             return false;
         }
         var postproject = directory.newLocalSource(),
@@ -847,17 +850,24 @@
         postproject.description = mashup.description;
         $.ajax({
             type: "POST",
-            url: options.project_api_endpoint,
+            url: IriSP.endpoints.project,
             data: IriSP.serializers.ldt.serialize(postproject),
             contentType: "application/cinelab",
 //            headers: {"X-CSRFToken": "{{csrf_token}}"},
             success: function(data, status, request){
-                console.log(request.getResponseHeader("Location"));
+                var location = request.getResponseHeader("Location"),
+                    projid = location.match(/([^/]+)\/?$/)[1],
+                    destination = IriSP.endpoints.hashcut_page + projid;
+                $(window).off("beforeunload", onLeave);
+                document.location.href = destination;
             },
             error: function(jqXHR, textStatus, errorThrown){
-                alert(errorThrown);
+                console.log(arguments);
+                alert(IriSP.translate("Server error\nYour hashcut couldn't be published"));
             }
         });
+        //TODO: ADD WAITING SCREEN
+        
         return false;
     });
     
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/integration/js/i18n.js	Fri Nov 23 19:13:50 2012 +0100
@@ -0,0 +1,57 @@
+IriSP.messages = {
+    fr: {
+        "Duration:" : "Durée :",
+        "duration:" : "durée :",
+        "Edit segment": "Éditer le segment",
+        "Move segment down": "Descendre le segment",
+        "Move segment up": "Remonter le segment",
+        "Delete segment": "Supprimer le segment",
+        "Clone segment": "Cloner le segment",
+        "From:": "De :",
+        "to:": "à :",
+        "Untitled segment": "Segment sans titre",
+        "Untitled Hashcut": "Hashcut sans titre",
+        "Copy of ": "Copie de ",
+        "A segment must be at least one second long": "Le segment doit durer au moins une seconde",
+        "A segment must be at most three minutes long": "Le segment doit durer moins de trois minutes",
+        "A segment must have a title": "Le segment doit avoir un titre",
+        "A segment should have a description": "Il est recommandé de donner une description au segment",
+        "A segment should have tags": "Il est recommandé de taguer le segment",
+        "A hashcut must be made from at least three segments": "Un hashcut doit être composé d'au moins trois segments",
+        "A hashcut must have a title": "Un titre doit être donné au hashcut",
+        "A hashcut should have a description": "Il est recommandé de donner une description au hashcut",
+        "One or more segments are invalid": "Un ou plusieurs segments ne sont pas valides",
+        "Your hashcut is valid!": "Votre hashcut est valide !",
+        "This segment is valid!": "Ce segment est valide !",
+        "Add segment to hashcut": "Ajouter au Hashcut",
+        "Save segment": "Sauvegarder",
+        "Create new segment": "Créer un nouveau segment",
+        "Edit existing segment": "Modifier le segment",
+        "The hashcut can't be published because:": "Le Hashcut ne peut pas être publié pour les raisons suivantes :",
+        "Server error\nYour hashcut couldn't be published": "Erreur serveur\nVotre hashcut n'a pas pu être publié",
+        "You haven't published your hashcut yet.\nIf you leave this page, it will be lost": "Vous n'avez pas encore publié votre Hashcut.\nSi vous quittez cette page, il sera perdu."
+    }
+};
+
+((function() {
+    var lang = IriSP.language || navigator.language || navigator.userLanguage || "en",
+        srcs = [ ];
+    if (typeof IriSP.messages[lang] === "object") {
+        srcs.push(IriSP.messages[lang])
+    }
+    if (lang.substr(0,2) !== lang && typeof IriSP.messages[lang.substr(0,2)] === "object") {
+        srcs.push(IriSP.messages[lang.substr(0,2)])
+    }
+    srcs.push({});
+    var l = srcs.length;
+    
+    IriSP.translate = function(_str) {
+        for (var i = 0; i < l; i++) {
+            if (typeof srcs[i][_str] !== "undefined") {
+                return srcs[i][_str];
+            }
+        }
+        return _str;
+    }
+    
+}) ());
--- a/integration/js/mashupplayer.js	Thu Nov 22 18:45:06 2012 +0100
+++ b/integration/js/mashupplayer.js	Fri Nov 23 19:13:50 2012 +0100
@@ -1,13 +1,14 @@
-IriSP.player = function(options) {
+IriSP.mashupplayer = function(options) {
     
     var directory = new IriSP.Model.Directory(),
         project = directory.remoteSource({
-            url: options.url,
+            url: IriSP.endpoints.ldt + options.id,
             serializer: IriSP.serializers.ldt
         }),
+        apidirectory = new IriSP.Model.Directory(),
         mashup,
         mediatemplate = _.template('<li class="item-video media" data-media-id="<%= media.id %>">'
-            + '<a href="#"><img class="thumbnail" alt="<%= media.title %>" src="<%= media.thumbnail %>"></a><div class="video-info">'
+            + '<a href="<%= IriSP.endpoints.media_page + media.id %>"><img class="thumbnail" alt="<%= media.title %>" src="<%= media.thumbnail %>"></a><div class="video-info">'
             + '<h3 class="title-video"><a href="#"><%= media.title %></a></h3><p class="description"><%= media.description %></p>'
             + '<p class="time-length">Durée : <span><%= media.duration.toString() %></span></p><div class="frise">'
             + '<div class="frise-overflow"><div class="frise-segments"><%= segments %></div></div></div></div></li>');
@@ -20,32 +21,41 @@
         project.trigger("set-current",mashup);
         
         $(".info-title a").text(mashup.title);
+        $(".title-video-wrap .title-video").text(mashup.title);
         $(".info-duration td").text(mashup.duration.toString());
         $(".info-author a").text(mashup.creator);
         $(".info-description td").text(mashup.description);
         
-        var html = '';
         mashup.getMedias().forEach(function(media) {
-            var segments = mashup.segments.filter(function(segment) {
-                return segment.getMedia() === media;
+            apidirectory.remoteSource({
+                url: IriSP.endpoints.content + media.id,
+                serializer: IriSP.serializers.content
+            }).onLoad(function() {
+                var m = apidirectory.getElement(media.id);
+                if (m) {
+                    media.thumbnail = m.thumbnail;
+                }
+                var segments = mashup.segments.filter(function(segment) {
+                    return segment.getMedia() === media;
+                });
+                var segmentshtml = '', k = media.duration ? (100 / media.duration) : 0;
+                segments.forEach(function(segment) {
+                    var vizdata = {
+                        annotation: segment.annotation,
+                        left: k * segment.annotation.begin,
+                        width: k * segment.annotation.getDuration()
+                    }
+                    segmentshtml += segmenttemplate(vizdata);
+                });
+                var mediadata = {
+                    media: media,
+                    segments: segmentshtml
+                }
+                
+                $(".list-video").append(mediatemplate(mediadata));
             });
-            var segmentshtml = '', k = media.duration ? (100 / media.duration) : 0;
-            segments.forEach(function(segment) {
-                var vizdata = {
-                    annotation: segment.annotation,
-                    left: k * segment.annotation.begin,
-                    width: k * segment.annotation.getDuration()
-                }
-                segmentshtml += segmenttemplate(vizdata);
-            });
-            var mediadata = {
-                media: media,
-                segments: segmentshtml
-            }
-            html += mediatemplate(mediadata);
         });
         
-        $(".list-video").html(html);
         
         project.on("mouseover-annotation", function(annotation) {
             var mediaid = annotation.getMedia().id;
@@ -59,19 +69,17 @@
             $(".media[data-media-id='" + mediaid + "']").addClass("active");
         });
         
-        $(".list-video .frise-segment")
-        .mouseover(function() {
+        $(".list-video")
+        .on("mouseover", ".frise-segment", function() {
             project.trigger("mouseover-annotation", project.getElement($(this).attr("data-segment-id")));
         })
-        .click(function() {
+        .on("click", ".frise-segment", function() {
             project.trigger("click-annotation", project.getElement($(this).attr("data-segment-id")));
-        });
-        
-        $(".item-video")
-        .mouseover(function() {
+        })
+        .on("mouseover", ".item-video", function() {
             $(".media").removeClass("active");
         })
-        .mouseout(function() {
+        .on("mouseout", ".item-video", function() {
             project.trigger("mouseout-annotation");
         })
         
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/integration/js/mediaplayer.js	Fri Nov 23 19:13:50 2012 +0100
@@ -0,0 +1,25 @@
+IriSP.mediaplayer = function(options) {
+    
+    var directory = new IriSP.Model.Directory(),
+        content = directory.remoteSource({
+            url: IriSP.endpoints.content + options.id,
+            serializer: IriSP.serializers.content
+        }),
+        apidirectory = new IriSP.Model.Directory();
+    
+    content.onLoad(function() {
+        
+        IriSP.mashupcore(content, new IriSP.Model.Mashup(false, content));
+        
+        var media = content.getMedias()[0];
+        
+        content.trigger("set-current", media);
+        
+        $(".info-title a").text(media.title);
+        $(".title-video-wrap .title-video").text(media.title);
+        $(".info-duration td").text(media.duration.toString());
+        $(".info-description td").text(media.description);
+        $(".info-tags td").text(media.keywords);
+        
+    });
+}
--- a/integration/js/segmentapi-serializer.js	Thu Nov 22 18:45:06 2012 +0100
+++ b/integration/js/segmentapi-serializer.js	Fri Nov 23 19:13:50 2012 +0100
@@ -3,7 +3,8 @@
         var _annotationlist = new IriSP.Model.List(_source.directory),
             _medialist = new IriSP.Model.List(_source.directory);
         _source.addList("media", _medialist);
-        IriSP._(_data.objects).each(function(_s) {
+        
+        function deserializeObject(_s) {
             var _ann = new IriSP.Model.Annotation(_s.element_id, _source),
                 _media = _source.getElement(_s.iri_id);
             if (!_media) {
@@ -17,7 +18,13 @@
             _ann.end = new IriSP.Model.Time(_s.start_ts + _s.duration);
             _ann.keywords = _s.tags.split(",");
             _annotationlist.push(_ann);
-        });
+        }
+        
+        if (typeof _data.objects !== "undefined") {
+            IriSP._(_data.objects).each(deserializeObject);
+        } else {
+            deserializeObject(_data);
+        }
         _source.addList("annotation", _annotationlist);
     }
 }
\ No newline at end of file
--- a/integration/js/social.js	Thu Nov 22 18:45:06 2012 +0100
+++ b/integration/js/social.js	Fri Nov 23 19:13:50 2012 +0100
@@ -1,14 +1,15 @@
-$(function() {
+IriSP.social = function(sel, url) {
     
-    var url = document.location.href,
-        text = $("title").text(),
+    var sel = sel || $(".Ldt-Social"),
+        url = url || document.location.href,
+        text = sel.find("title").text(),
         clipId = IriSP.Model.getUID(),
         clip;
 
-    $(".Ldt-Social-CopyBtn").attr("id", this.clipId);
+    sel.find(".Ldt-Social-CopyBtn").attr("id", this.clipId);
 
-    $(".Ldt-Social-Url").click(function() {
-        var _pop = $(".Ldt-Social-UrlPop");
+    sel.find(".Ldt-Social-Url").click(function() {
+        var _pop = sel.find(".Ldt-Social-UrlPop");
         _pop.toggle();
         if (_pop.is(":visible")) {
             if (typeof clip == "undefined") {
@@ -23,25 +24,25 @@
             }
             clip.show();
             clip.setText( url );
-            $(".Ldt-Social-Input").val(url).focus();
+            sel.find(".Ldt-Social-Input").val(url).focus();
         } else {
             clip.hide();
         }
         return false;
     });
-    $(".Ldt-Social-Input").focus(function() {
+    sel.find(".Ldt-Social-Input").focus(function() {
         this.select();
     });
-    $(".Ldt-Social-Ext").click(function() {
+    sel.find(".Ldt-Social-Ext").click(function() {
         window.open(
-            $(this).attr("href"),
+            sel.find(this).attr("href"),
             "_blank",
             "height=300,width=450,left=100,top=100,toolbar=0,menubar=0,status=0,location=0");
         return false;
     });
     
-    $(".Ldt-Social-Fb").attr("href", "http://www.facebook.com/share.php?" + $.param({ u: url, t: text }));
-    $(".Ldt-Social-Twitter").attr("href", "https://twitter.com/intent/tweet?" + $.param({ url: url, text: text }));
-    $(".Ldt-Social-Gplus").attr("href", "https://plus.google.com/share?" + $.param({ url: url, title: text }));
-    $(".Ldt-Social-Mail").attr("href", "mailto:?" + $.param({ subject: text, body: text + ": " + url }));
-});
+    sel.find(".Ldt-Social-Fb").attr("href", "http://www.facebook.com/share.php?" + $.param({ u: url, t: text }));
+    sel.find(".Ldt-Social-Twitter").attr("href", "https://twitter.com/intent/tweet?" + $.param({ url: url, text: text }));
+    sel.find(".Ldt-Social-Gplus").attr("href", "https://plus.google.com/share?" + $.param({ url: url, title: text }));
+    sel.find(".Ldt-Social-Mail").attr("href", "mailto:?" + $.param({ subject: text, body: text + ": " + url }));
+}