Updated LatestAnnotation, CurrentSegmentInfobox, AnnotationController and AnnotationList widgets to use timerange to find the current segment when the corresponding option is used + CurrentSegmentInfobox now has an option for editing the current segment + LatestAnnotation now has a "Copy and edit" button that allows to use the text from the currently displayed annotation into the CreateAnnotation widget textarea
--- a/src/widgets/AnnotationsController.js Tue Sep 01 15:24:26 2015 +0200
+++ b/src/widgets/AnnotationsController.js Tue Sep 01 15:31:46 2015 +0200
@@ -15,7 +15,7 @@
display_or_write: false,
starts_hidden: false,
hide_without_segment: false,
- segments_annotation_type: "chap"
+ segments_annotation_type: "chap",
};
IriSP.Widgets.AnnotationsController.prototype.template =
@@ -57,7 +57,17 @@
_this.player.trigger("CreateAnnotation.hide");
}
})
- this.onMediaEvent("timeupdate", "onTimeUpdate")
+
+ if(this.hide_without_segment){
+ this.onMediaEvent("timeupdate", function(){
+ _this.refresh();
+ })
+ this.onMediaEvent("settimerange", function(_timeRange){
+ _this.refresh(_timeRange);
+ })
+ this.segments = this.source.getAnnotationsByTypeTitle(this.segments_annotation_type)
+ this.currentSegment = false
+ }
if (this.starts_hidden) {
this.visible = true
@@ -70,25 +80,53 @@
};
-IriSP.Widgets.AnnotationsController.prototype.onTimeUpdate = function(){
+IriSP.Widgets.AnnotationsController.prototype.refresh = function(_timeRange){
+ _timeRange = typeof _timeRange !== 'undefined' ? _timeRange : false ;
+
+ if(!_timeRange){
+ if (this.media.getTimeRange()){
+ _timeRange = this.media.getTimeRange();
+ }
+ }
+
if (this.hide_without_segment){
- _currentTime = this.media.getCurrentTime()
- _segmentsAnnotations = this.source.getAnnotationsByTypeTitle(this.segments_annotation_type)
- _currentSegments = _segmentsAnnotations.filter(function(_segment){
- return (_currentTime >= _segment.begin && _currentTime <= _segment.end)
- });
- if (_currentSegments.length == 0){
+ if (!_timeRange && !this.media.getTimeRange()){
+ _currentTime = this.media.getCurrentTime()
+ _currentSegments = this.segments.filter(function(_segment){
+ return (_currentTime >= _segment.begin && _currentTime <= _segment.end)
+ });
+ if(_currentSegments.length > 0){
+ currentSegment = true;
+ }
+ else {
+ currentSegment = false;
+ }
+ }
+ else {
+ var _timeRangeBegin = _timeRange[0],
+ _timeRangeEnd = _timeRange[1];
+ _currentSegments = this.segments.filter(function(_segment){
+ return (_timeRangeBegin == _segment.begin && _timeRangeEnd == _segment.end)
+ });
+ if(_currentSegments.length > 0){
+ currentSegment = true;
+ }
+ else {
+ currentSegment = false;
+ }
+ }
+ if (!currentSegment && _currentSegments.length == 0){
if (this.visible){
this.hide();
- _this.player.trigger("CreateAnnotation.hide");
- _this.player.trigger("AnnotationsList.hide");
+ this.player.trigger("CreateAnnotation.hide");
+ this.player.trigger("AnnotationsList.hide");
}
}
else {
if (!this.visible){
this.show();
- _this.player.trigger("CreateAnnotation.hide");
- _this.player.trigger("AnnotationsList.hide");
+ this.player.trigger("CreateAnnotation.hide");
+ this.player.trigger("AnnotationsList.hide");
}
}
}
--- a/src/widgets/AnnotationsList.css Tue Sep 01 15:24:26 2015 +0200
+++ b/src/widgets/AnnotationsList.css Tue Sep 01 15:31:46 2015 +0200
@@ -1,9 +1,14 @@
/* AnnotationsListWidget */
+#ui-datepicker-div
+{
+ display: none;
+}
+
.Ldt-AnnotationsListWidget {
border: none; margin: 0; padding: 0;
overflow: auto;
- max-height: 480px;
+ max-height: 380px;
}
.Ldt-AnnotationsListWidget a {
text-decoration: none;
--- a/src/widgets/AnnotationsList.js Tue Sep 01 15:24:26 2015 +0200
+++ b/src/widgets/AnnotationsList.js Tue Sep 01 15:31:46 2015 +0200
@@ -37,8 +37,10 @@
start_visible: true,
show_audio : true,
show_filters : false,
+ show_header : false,
+ custom_header : false,
show_creation_date : false,
- show_timecode : true,
+ show_timecode : true,
/*
* Only annotation in the current segment will be displayed. Designed to work with the Segments Widget.
*/
@@ -71,21 +73,30 @@
IriSP.Widgets.AnnotationsList.prototype.messages = {
en: {
voice_annotation: "Voice Annotation",
- now_playing: "Now playing..."
+ now_playing: "Now playing...",
+ everyone: "Everyone",
+ header: "Annotations for this content"
},
fr: {
voice_annotation: "Annotation Vocale",
- now_playing: "Lecture en cours..."
+ now_playing: "Lecture en cours...",
+ everyone: "Tous",
+ header: "Annotations sur ce contenu"
}
};
IriSP.Widgets.AnnotationsList.prototype.template =
- '<div class="Ldt-AnnotationsListWidget">'
+ '{{#show_header}}<p class="Ldt-AnnotationsList-header">'
+ + '{{#custom_header}}{{custom_header}}{{/custom_header}}'
+ + '{{^custom_header}}{{l10n.header}}{{/custom_header}}'
+ + '</p>{{/show_header}}'
+ + '<div class="Ldt-AnnotationsListWidget">'
+ '{{#show_filters}}'
+ '<div class="Ldt-AnnotationsList-Filters">'
- + '<input class="Ldt-AnnotationsList-filter-text" type="text" value="Mot-clés"></input>'
- + '<select class="Ldt-AnnotationsList-filter-dropdown"></select>'
- + '<label class="Ldt-AnnotationsList-filter-checkbox"><input type="checkbox">Toutes annotations</label>'
+ + '<input class="Ldt-AnnotationsList-filter-text" id="Ldt-AnnotationsList-keywordsFilter" type="text" value=""></input>'
+ + '<select class="Ldt-AnnotationsList-filter-dropdown" id="Ldt-AnnotationsList-userFilter"><option selected value="">{{l10n.everyone}}</option></select>'
+ + '<label class="Ldt-AnnotationsList-filter-date">Date: <input id="Ldt-AnnotationsList-dateFilter" type="text"></input></label>'
+ + '<label class="Ldt-AnnotationsList-filter-checkbox"><input type="checkbox" id="Ldt-AnnotationsList-ignoreSegmentsFilter">Toutes annotations</label>'
+ '</div>'
+ '{{/show_filters}}'
+ '{{#show_audio}}<div class="Ldt-AnnotationsList-Audio"></div>{{/show_audio}}'
@@ -177,15 +188,23 @@
_list = _list.filter(function(_annotation) {
return _annotation.found !== false;
});
- if (this.filter_by_segments) {
+
+ if ((this.filter_by_segments)&&(!(this.show_filters && this.ignoresegmentcheckbox_$[0].checked))) {
/*
* A given annotation is considered "in" segment if the middle of it is between the segment beginning and the segment end.
* Note this is meant to be used for "markings" annotations (not segments)
*/
_segmentsAnnotation = this.currentSource.getAnnotationsByTypeTitle(this.segments_annotation_type)
- _currentSegments = _segmentsAnnotation.filter(function(_segment){
- return (_currentTime >= _segment.begin && _currentTime <= _segment.end)
- });
+ if (this.media.getTimeRange()){
+ _currentSegments = _segmentsAnnotation.filter(function(_segment){
+ return (_this.media.getTimeRange()[0] == _segment.begin && _this.media.getTimeRange()[1] == _segment.end)
+ });
+ }
+ else {
+ _currentSegments = _segmentsAnnotation.filter(function(_segment){
+ return (_currentTime >= _segment.begin && _currentTime <= _segment.end)
+ });
+ }
if (_currentSegments.length == 0) {
_list = _list.filter(function(_annotation){
return false;
@@ -209,6 +228,7 @@
return Math.abs((_annotation.begin + _annotation.end) / 2 - _currentTime);
}).slice(0, this.limit_count);
}
+
if (this.newest_first) {
_list = _list.sortBy(function(_annotation) {
return -_annotation.created.valueOf();
@@ -219,6 +239,31 @@
});
}
+ if (this.show_filters){
+ _username = this.userselect_$[0].options[this.userselect_$[0].selectedIndex].value;
+ if (_username != "false")
+ {
+ _list = _list.filter(function(_annotation){
+ return _annotation.creator == _username
+ })
+ }
+ _keyword = this.keywordinput_$[0].value;
+ if (_keyword != ""){
+ _list = _list.filter(function(_annotation){
+ return _annotation.description.toLowerCase().match(_keyword.toLowerCase());
+ });
+ }
+
+
+ if(this.datefilterinput_$[0].value != ""){
+ _date = this.datefilterinput_$.datepicker("getDate");
+ _list = _list.filter(function(_annotation){
+ return ((_annotation.created.getDate() == _date.getDate())&&(_annotation.created.getMonth() == _date.getMonth())&&(_annotation.created.getFullYear() == _date.getFullYear()))
+ });
+ }
+
+ }
+
var _ids = _list.idIndex;
if (_forceRedraw || !IriSP._.isEqual(_ids, this.lastIds) || this.searchString !== this.lastSearch) {
@@ -246,7 +291,8 @@
);
var _title = "",
_description = _annotation.description,
- _thumbnail = (typeof _annotation.thumbnail !== "undefined" && _annotation.thumbnail ? _annotation.thumbnail : _this.default_thumbnail);
+ _thumbnail = (typeof _annotation.thumbnail !== "undefined" && _annotation.thumbnail ? _annotation.thumbnail : _this.default_thumbnail)
+
// Update : display creator
if (_annotation.creator) {
_title = _annotation.creator;
@@ -334,6 +380,9 @@
.mouseout(function() {
_annotation.trigger("unselect");
})
+ .click(function() {
+ _annotation.trigger("click");
+ })
.appendTo(_this.list_$);
IriSP.attachDndData(_el.find("[draggable]"), {
title: _title,
@@ -393,16 +442,20 @@
};
IriSP.Widgets.AnnotationsList.prototype.hide = function() {
+ var _this = this;
if (this.visible){
this.visible = false;
- this.widget_$.slideUp()
+ this.widget_$.slideUp(function(){
+ _this.$.find('.Ldt-AnnotationsList-header').hide();
+ });
}
}
IriSP.Widgets.AnnotationsList.prototype.show = function() {
if(!this.visible){
this.visible = true;
- this.widget_$.slideDown()
+ this.$.find('.Ldt-AnnotationsList-header').show();
+ this.widget_$.slideDown();
}
}
@@ -428,7 +481,23 @@
this.list_$ = this.$.find(".Ldt-AnnotationsList-ul");
this.widget_$ = this.$.find(".Ldt-AnnotationsListWidget");
-
+ this.userselect_$ = this.$.find("#Ldt-AnnotationsList-userFilter");
+ this.userselect_$.change(function(){
+ _this.player.trigger("AnnotationsList.refresh");
+ });
+ this.keywordinput_$ = this.$.find("#Ldt-AnnotationsList-keywordsFilter");
+ this.keywordinput_$.keyup(function(){
+ _this.player.trigger("AnnotationsList.refresh");
+ });
+ this.ignoresegmentcheckbox_$ = this.$.find("#Ldt-AnnotationsList-ignoreSegmentsFilter");
+ this.ignoresegmentcheckbox_$.click(function(){
+ _this.player.trigger("AnnotationsList.refresh");
+ });
+ this.datefilterinput_$ = this.$.find("#Ldt-AnnotationsList-dateFilter");
+ this.datefilterinput_$.datepicker({ dateFormat: 'dd/mm/yy' });
+ this.datefilterinput_$.change(function(){
+ _this.player.trigger("AnnotationsList.refresh")
+ })
this.source.getAnnotations().on("search", function(_text) {
_this.searchString = _text;
@@ -453,6 +522,20 @@
_this.throttledRefresh();
});
+ if (this.show_filters){
+ _usernames = Array();
+ _list = this.getWidgetAnnotations()
+ _list.forEach(function(_annotation){
+ if(_usernames.indexOf(_annotation.creator) == -1){
+ _usernames.push(_annotation.creator);
+ }
+ });
+ this.userselect_$.html("<option selected value='false'>"+this.l10n.everyone+"</option>");
+ _usernames.forEach(function(_user){
+ _this.userselect_$.append("<option value='"+_user+"'>"+_user+"</option>");
+ });
+ }
+
this.onMdpEvent("AnnotationsList.refresh", function() {
if (_this.ajax_url) {
if (_this.mashupMode) {
@@ -484,11 +567,12 @@
this.onMdpEvent("AnnotationsList.hide", "hide");
this.onMdpEvent("AnnotationsList.show", "show");
- this.onMdpEvent("createAnnotationWidget.addedAnnotation", "refresh");
+ this.onMdpEvent("createAnnotationWidget.addedAnnotation", this.throttledRefresh);
var _events = [
"timeupdate",
"seeked",
- "loadedmetadata"
+ "loadedmetadata",
+ "settimerange"
];
for (var _i = 0; _i < _events.length; _i++) {
this.onMediaEvent(_events[_i], this.throttledRefresh);
--- a/src/widgets/CurrentSegmentInfobox.css Tue Sep 01 15:24:26 2015 +0200
+++ b/src/widgets/CurrentSegmentInfobox.css Tue Sep 01 15:31:46 2015 +0200
@@ -39,10 +39,90 @@
font-weight: bold;
}
+textarea.Ldt-CurrentSegmentInfobox-DescriptionInput.Ldt-CurrentSegmentInfobox-Description{
+ display: inline-block;
+ width: 95%;
+}
+
.Ldt-CurrentSegmentInfobox-Tags{
}
.Ldt-CurrentSegmentInfobox-NoSegment{
font-size: 15px;
font-weight: bold;
+}
+
+.Ldt-CurrentSegmentInfobox-SubmitButton{
+ display: inline-block;
+ background-color: #d93c71;
+ color: #ffffff;
+ float: right;
+ cursor: pointer;
+ height: 14px;
+ width: 100px;
+ margin: 2px;
+ margin-top: 5px;
+ padding: 2px;
+ font-size: 11px;
+ border: 1px solid;
+ border-color: #eca3bc #631e34 #36101c #e16e93;
+ cursor: pointer;
+ text-align: center;
+ vertical-align: middle;
+}
+
+.Ldt-CurrentSegmentInfobox-CancelButton{
+ display: inline-block;
+ background-color: #d93c71;
+ color: #ffffff;
+ float: right;
+ cursor: pointer;
+ height: 14px;
+ width: 100px;
+ margin: 2px;
+ margin-top: 5px;
+ margin-right: 5px;
+ padding: 2px;
+ font-size: 11px;
+ border: 1px solid;
+ border-color: #eca3bc #631e34 #36101c #e16e93;
+ cursor: pointer;
+ text-align: center;
+ vertical-align: middle;
+}
+
+.Ldt-CurrentSegmentInfobox-CreateTagButton{
+ display: block;
+ background-color: #d93c71;
+ color: #ffffff;
+ cursor: pointer;
+ height: 14px;
+ width: 75px;
+ margin: 2px;
+ padding: 2px;
+ font-size: 11px;
+ border: 1px solid;
+ border-color: #eca3bc #631e34 #36101c #e16e93;
+ cursor: pointer;
+ text-align: center;
+ vertical-align: middle;
+}
+
+.Ldt-CurrentSegmentInfobox-Tags-Li-Input{
+ width: 80px;
+}
+
+.Ldt-CurrentSegmentInfobox-CreateTagButton:hover, .Ldt-CurrentSegmentInfobox-CancelButton:hover,
+.Ldt-CurrentSegmentInfobox-SubmitButton:hover{
+ background-color: #e15581;
+ border-color: #222222 #e87d9f #f0adc3 #68273c;
+}
+
+.Ldt-CurrentSegmentInfobox-Tags-Li-DeleteTagButton{
+ font-weight: bold;
+ color: #d93c71
+}
+
+.Ldt-CurrentSegmentInfobox-Tags-Li-DeleteTagButton:hover{
+ color: #e16e93
}
\ No newline at end of file
--- a/src/widgets/CurrentSegmentInfobox.js Tue Sep 01 15:24:26 2015 +0200
+++ b/src/widgets/CurrentSegmentInfobox.js Tue Sep 01 15:31:46 2015 +0200
@@ -8,69 +8,263 @@
IriSP.Widgets.CurrentSegmentInfobox.prototype.defaults = {
annotation_type: "chap",
- readonly: true,
- empty_message: false
+ editable_segments: false,
+ empty_message: false,
+ project_id: false,
+ api_serializer: "ldt_annotate",
+ api_method: "PUT",
+ api_endpoint_template: ""
};
IriSP.Widgets.CurrentSegmentInfobox.prototype.template =
- "<div class='Ldt-CurrentSegmentInfobox'>"
- + " <div class='Ldt-CurrentSegmentInfobox-Element Ldt-CurrentSegmentInfobox-Title'>{{title}}</div>"
- + " <div class='Ldt-CurrentSegmentInfobox-Element Ldt-CurrentSegmentInfobox-Description'>{{description}}</div>"
- + " <div class='Ldt-CurrentSegmentInfobox-Element Ldt-CurrentSegmentInfobox-Tags'>"
- + ' {{#tags.length}}'
- + ' <ul class="Ldt-CurrentSegmentInfobox-Tags-Ul">'
- + ' {{#tags}}'
- + ' {{#.}}'
- + ' <li class="Ldt-CurrentSegmentInfobox-Tags-Li">'
- + ' <span>{{.}}</span>'
- + ' </li>'
- + ' {{/.}}'
- + ' {{/tags}}'
- + ' </ul>'
- + ' {{/tags.length}}'
- + " </div>"
- + "</div>"
+ '<div class="Ldt-CurrentSegmentInfobox">'
+ + '<div class="Ldt-CurrentSegmentInfobox-Element Ldt-CurrentSegmentInfobox-Title">{{title}}</div>'
+ + '<div class="Ldt-CurrentSegmentInfobox-Element Ldt-CurrentSegmentInfobox-Description">{{description}}</div>'
+ + '<div class="Ldt-CurrentSegmentInfobox-Element Ldt-CurrentSegmentInfobox-Tags">'
+ + '{{#tags.length}}'
+ + '<ul class="Ldt-CurrentSegmentInfobox-Tags-Ul">'
+ + '{{#tags}}'
+ + '{{#.}}'
+ + '<li class="Ldt-CurrentSegmentInfobox-Tags-Li">'
+ + '<span>{{.}}</span>'
+ + '</li>'
+ + '{{/.}}'
+ + '{{/tags}}'
+ + '</ul>'
+ + '{{/tags.length}}'
+ + '</div>'
+ + '</div>'
+IriSP.Widgets.CurrentSegmentInfobox.prototype.editTemplate =
+ '<div class="Ldt-CurrentSegmentInfobox">'
+ + '<input type="text" class="Ldt-CurrentSegmentInfobox-Element Ldt-CurrentSegmentInfobox-TitleInput Ldt-CurrentSegmentInfobox-Title" value="{{title}}"></input>'
+ + '<div class="Ldt-CurrentSegmentInfobox-CancelButton">{{cancel}}</div>'
+ + '<div class="Ldt-CurrentSegmentInfobox-SubmitButton">{{submit}}</div>'
+ + '<textarea class="Ldt-CurrentSegmentInfobox-Element Ldt-CurrentSegmentInfobox-DescriptionInput Ldt-CurrentSegmentInfobox-Description">{{description}}</textarea>'
+ + '<div class="Ldt-CurrentSegmentInfobox-Element Ldt-CurrentSegmentInfobox-Tags">'
+ + '<div class="Ldt-CurrentSegmentInfobox-CreateTagButton">{{new_tag}}</div>'
+ + '{{#tags.length}}'
+ + '<ul class="Ldt-CurrentSegmentInfobox-Tags-Ul">'
+ + '{{#tags}}'
+ + '{{#.}}'
+ + '<li class="Ldt-CurrentSegmentInfobox-Tags-Li">'
+ + '<input type="text" class="Ldt-CurrentSegmentInfobox-Tags-Li-Input" value="{{.}}"></input>'
+ + '<div class="Ldt-CurrentSegmentInfobox-Tags-Li-DeleteTagButton">{{delete_tag}}</div>'
+ + '</li>'
+ + '{{/.}}'
+ + '{{/tags}}'
+ + '</ul>'
+ + '{{/tags.length}}'
+ + '</div>'
+ + '</div>'
+
IriSP.Widgets.CurrentSegmentInfobox.prototype.messages = {
fr : {
+ submit : "Soumettre",
+ cancel : "Annuler",
+ new_tag : "Nouveau tag",
+ delete_tag : "Supprimer",
empty : "Le player vidéo ne lit actuellement aucun segment"
},
en: {
- empty: "The player currently doesn't read any segment"
+ submit : "Submit",
+ cancel : "Cancel",
+ new_tag : "New tag",
+ delete_tag : "Delete tag",
+ empty : "The player currently doesn't read any segment"
}
}
IriSP.Widgets.CurrentSegmentInfobox.prototype.draw = function() {
var _this = this;
this.segments = this.getWidgetAnnotations();
-
this.renderTemplate();
+ this.currentSegment = false;
+ this.clearBox();
this.refresh();
+ this.onMediaEvent("timeupdate", "refresh");
+ this.onMediaEvent("settimerange", function(_timeRange){
+ var _segmentBegin = _timeRange[0],
+ _segmentEnd = _timeRange[1],
+ _list = _this.segments.filter(function(_segment){
+ return _segment.begin.milliseconds == _segmentBegin.milliseconds && _segment.end.milliseconds == _segmentEnd.milliseconds
+ });
+ if (_list.length >0){
+ if (_this.currentSegment.id != _list[0].id){
+ _this.currentSegment = _list[0];
+ _data = {
+ title: _this.currentSegment.title,
+ description : _this.currentSegment.description,
+ tags : _this.currentSegment.getTagTexts()
+ }
+ _this.$.html(Mustache.to_html(_this.template, _data))
+ if(_this.editable_segments&&_this.currentSegment){
+ _this.$.find(".Ldt-CurrentSegmentInfobox").click(_this.functionWrapper("enableEditMode"));
+ }
+ }
+ }
+ });
- this.onMediaEvent("timeupdate", "refresh");
+ if(this.editable_segments&&this.currentSegment){
+ this.$.find(".Ldt-CurrentSegmentInfobox").click(_this.functionWrapper("enableEditMode"));
+ }
+}
+
+IriSP.Widgets.CurrentSegmentInfobox.prototype.enableEditMode = function() {
+ if(this.currentSegment){
+ _data = {
+ title: this.currentSegment.title,
+ description : this.currentSegment.description,
+ tags : this.currentSegment.getTagTexts(),
+ submit : this.l10n.submit,
+ cancel : this.l10n.cancel,
+ new_tag : this.l10n.new_tag,
+ delete_tag : this.l10n.delete_tag
+ }
+ this.$.html(Mustache.to_html(this.editTemplate, _data));
+ this.$.find(".Ldt-CurrentSegmentInfobox-CancelButton").click(this.functionWrapper("disableEditMode"));
+ this.$.find(".Ldt-CurrentSegmentInfobox-CreateTagButton").click(this.functionWrapper("insertTagInput"));
+ this.$.find(".Ldt-CurrentSegmentInfobox-Tags-Li-DeleteTagButton").click(this.functionWrapper("deleteTagInput"));
+ this.$.find(".Ldt-CurrentSegmentInfobox-SubmitButton").click(this.functionWrapper("onSubmit"))
+ }
+}
+
+IriSP.Widgets.CurrentSegmentInfobox.prototype.disableEditMode = function() {
+ if(this.currentSegment){
+ data = {
+ title: this.currentSegment.title,
+ description : this.currentSegment.description,
+ tags : this.currentSegment.getTagTexts()
+ }
+ this.$.html(Mustache.to_html(this.template, _data));
+ this.$.find(".Ldt-CurrentSegmentInfobox").click(this.functionWrapper("enableEditMode"));
+ }
+}
+
+IriSP.Widgets.CurrentSegmentInfobox.prototype.insertTagInput = function() {
+ if((!this.currentSegment.getTagTexts().length)&&(!this.$.find(".Ldt-CurrentSegmentInfobox-Tags-Ul").length)){
+ this.$.find(".Ldt-CurrentSegmentInfobox-Tags").prepend('<ul class="Ldt-CurrentSegmentInfobox-Tags-Ul"></ul>')
+ }
+ this.$.find(".Ldt-CurrentSegmentInfobox-Tags-Ul").append(
+ '<li class="Ldt-CurrentSegmentInfobox-Tags-Li">'
+ +'<input type="text" class="Ldt-CurrentSegmentInfobox-Tags-Li-Input" value=""></input>'
+ +'<div class="Ldt-CurrentSegmentInfobox-Tags-Li-DeleteTagButton">'+this.l10n.delete_tag+'</div>'
+ +'</li>');
+ this.$.find(".Ldt-CurrentSegmentInfobox-Tags-Li-DeleteTagButton").click(this.functionWrapper("deleteTagInput"));
+}
+
+IriSP.Widgets.CurrentSegmentInfobox.prototype.deleteTagInput = function(clickEvent) {
+ $(clickEvent.currentTarget).parent().remove();
+}
+
+IriSP.Widgets.CurrentSegmentInfobox.prototype.onSubmit = function() {
+ new_tags_titles = this.$.find(".Ldt-CurrentSegmentInfobox-Tags-Li-Input").map(function(){
+ if($(this).val()){
+ return $(this).val()
+ }
+ });
+ new_title = this.$.find(".Ldt-CurrentSegmentInfobox-TitleInput").val()
+ new_description = this.$.find(".Ldt-CurrentSegmentInfobox-DescriptionInput").val()
+
+ var _this = this,
+ _exportedAnnotations = new IriSP.Model.List(this.player.sourceManager), /* Création d'une liste d'annotations contenant une annotation afin de l'envoyer au serveur */
+ _export = this.player.sourceManager.newLocalSource({serializer: IriSP.serializers[this.api_serializer]}),
+ _annotation = new IriSP.Model.Annotation(this.currentSegment.id, _export); /* Création d'une annotation dans cette source avec un ID généré à la volée (param. false) */
+
+ _annotation.setAnnotationType(this.currentSegment.getAnnotationType().id);
+ _annotation.setMedia(this.currentSegment.getMedia().id);
+ _annotation.setBegin(this.currentSegment.begin);
+ _annotation.setEnd(this.currentSegment.end);
+ _annotation.created = this.currentSegment.created;
+ _annotation.creator = this.currentSegment.creator;
+ _annotation.title = new_title /* Champ titre */
+ _annotation.description = new_description /* Champ description */
+ var _tagIds = IriSP._(new_tags_titles).map(function(_title) {
+ var _tags = _this.source.getTags(true).searchByTitle(_title, true);
+ if (_tags.length) {
+ var _tag = _tags[0];
+ }
+ else {
+ _tag = new IriSP.Model.Tag(_title.replace(/\W/g,'_'), _this.source);
+ _tag.title = _title;
+ _this.source.getTags().push(_tag);
+ }
+ return _tag.id;
+ });
+ _annotation.setTags(_tagIds);
+ _annotation.project_id = this.project_id;
+
+ _exportedAnnotations.push(_annotation); /* Ajout de l'annotation à la liste à exporter */
+ _export.addList("annotation",_exportedAnnotations); /* Ajout de la liste à exporter à l'objet Source */
+
+ _url = Mustache.to_html(this.api_endpoint_template, {annotation_id: this.currentSegment.id});
+
+ IriSP.jQuery.ajax({
+ url: _url,
+ type: this.api_method,
+ contentType: 'application/json',
+ data: _export.serialize(), /* L'objet Source est sérialisé */
+ success: function(_data) {
+ _export.getAnnotations().removeElement(_annotation, true); /* Pour éviter les doublons, on supprime l'annotation qui a été envoyée */
+ _export.deSerialize(_data); /* On désérialise les données reçues pour les réinjecter */
+ _this.source.merge(_export); /* On récupère les données réimportées dans l'espace global des données */
+ _this.segments.forEach(function(_segment){
+ if (_segment.id == _annotation.id){
+ _this.segments.removeElement(_segment)
+ }
+ })
+ _this.segments.push(_annotation)
+ _this.currentSegment = _annotation
+ _data = {
+ title: _this.currentSegment.title,
+ description : _this.currentSegment.description,
+ tags : _this.currentSegment.getTagTexts()
+ }
+ _this.$.html(Mustache.to_html(_this.template, _data))
+ if(_this.editable_segments&&_this.currentSegment){
+ _this.$.find(".Ldt-CurrentSegmentInfobox").click(_this.functionWrapper("enableEditMode"));
+ }
+ _this.player.trigger("AnnotationsList.refresh"); /* On force le rafraîchissement du widget AnnotationsList */
+ },
+ error: function(_xhr, _error, _thrown) {
+ IriSP.log("Error when sending annotation", _thrown);
+ _export.getAnnotations().removeElement(_annotation, true);
+ }
+ });
}
IriSP.Widgets.CurrentSegmentInfobox.prototype.refresh = function() {
- var _list = this.segments;
-
- _currentTime = this.media.getCurrentTime();
- _list = _list.filter(function(_segment){
- return (_segment.begin <= _currentTime && _segment.end >= _currentTime);
- })
- if (_list.length > 0){
- _currentSegment = _list[0];
- _data = {
- title: _currentSegment.title,
- description : _currentSegment.description,
- tags : _currentSegment.getTagTexts()
+ if(!this.media.getTimeRange()){
+ var _currentTime = this.media.getCurrentTime();
+ var _list = this.segments.filter(function(_segment){
+ return (_segment.begin <= _currentTime && _segment.end >= _currentTime);
+ })
+
+ if (_list.length > 0){
+ if (this.currentSegment.id != _list[0].id){
+ this.currentSegment = _list[0];
+ _data = {
+ title: this.currentSegment.title,
+ description : this.currentSegment.description,
+ tags : this.currentSegment.getTagTexts()
+ }
+ this.$.html(Mustache.to_html(this.template, _data))
+ if(this.editable_segments&&this.currentSegment){
+ this.$.find(".Ldt-CurrentSegmentInfobox").click(this.functionWrapper("enableEditMode"));
+ }
+ }
}
- this.$.html(Mustache.to_html(this.template, _data))
+ else {
+ this.currentSegment = false;
+ this.clearBox();
+ }
}
- else {
- var _empty_message = this.l10n.empty
- if (this.empty_message) {
- _empty_message = this.empty_message
- }
- this.$.find(".Ldt-CurrentSegmentInfobox").html("<div class='Ldt-CurrentSegmentInfobox-Element Ldt-CurrentSegmentInfobox-NoSegment'>"+_empty_message+"</div>");
+}
+
+IriSP.Widgets.CurrentSegmentInfobox.prototype.clearBox = function(){
+ var _empty_message = this.l10n.empty
+ if (this.empty_message) {
+ _empty_message = this.empty_message
}
+ this.$.find(".Ldt-CurrentSegmentInfobox").html("<div class='Ldt-CurrentSegmentInfobox-Element Ldt-CurrentSegmentInfobox-NoSegment'>"+_empty_message+"</div>");
}
\ No newline at end of file
--- a/src/widgets/LatestAnnotation.css Tue Sep 01 15:24:26 2015 +0200
+++ b/src/widgets/LatestAnnotation.css Tue Sep 01 15:31:46 2015 +0200
@@ -25,6 +25,8 @@
}
.Ldt-LatestAnnotation-Content{
+ max-width: 230px;
+ text-align: justify;
}
.Ldt-LatestAnnotation-Title{
@@ -37,3 +39,26 @@
font-size: 14px;
font-weight: bold;
}
+
+.Ldt-LatestAnnotation-CopyEditButton{
+ display: inline-block;
+ background-color: #d93c71;
+ color: #ffffff;
+ float: right;
+ cursor: pointer;
+ height: 14px;
+ width: 100px;
+ margin: 2px;
+ padding: 2px;
+ font-size: 11px;
+ border: 1px solid;
+ border-color: #eca3bc #631e34 #36101c #e16e93;
+ cursor: pointer;
+ text-align: center;
+ vertical-align: middle;
+}
+
+.Ldt-LatestAnnotation-CopyEditButton:hover{
+ background-color: #e15581;
+ border-color: #222222 #e87d9f #f0adc3 #68273c;
+}
\ No newline at end of file
--- a/src/widgets/LatestAnnotation.js Tue Sep 01 15:24:26 2015 +0200
+++ b/src/widgets/LatestAnnotation.js Tue Sep 01 15:31:46 2015 +0200
@@ -16,31 +16,94 @@
* Set to a username if you only want to display annotations from a given user
*/
show_only_annotation_from_user: false,
+ /*
+ * Displays a button that copy currently displayed annotation into CreateAnnotation input field
+ */
+ copy_and_edit_button: false,
+ /*
+ * Allows clicks on an annotation from Annotations to display the annotation content into this widget
+ */
+ selectable_annotations: false,
empty_message: false,
starts_hidden: false,
+ show_header: false,
+ custom_header: false,
};
+IriSP.Widgets.LatestAnnotation.prototype.messages = {
+ fr : {
+ copy_and_edit: "Copier et Editer",
+ empty : "Aucune annotation à afficher",
+ header: "Dernière annotation"
+ },
+ en: {
+ copy_and_edit: "Copy and Edit",
+ empty: "No annotation to display",
+ header: "Last annotation"
+ }
+}
+
IriSP.Widgets.LatestAnnotation.prototype.template =
- "<div class='Ldt-LatestAnnotation'>"
+ "{{#show_header}}"
+ + "<p class='Ldt-LatestAnnotation-header'>"
+ + "{{#custom_header}}{{custom_header}}{{/custom_header}}"
+ + "{{^custom_header}}{{l10n.header}}{{/custom_header}}"
+ + "</p>"
+ + "{{/show_header}}"
+ + "<div class='Ldt-LatestAnnotation'>"
+ "</div>";
IriSP.Widgets.LatestAnnotation.prototype.annotationTemplate =
"<div class='Ldt-LatestAnnotation-Box'>"
- + " <div class='Ldt-LatestAnnotation-Element Ldt-LatestAnnotation-CreationDate'>{{{annotation_created}}}</div>"
- + " <div class='Ldt-LatestAnnotation-Element Ldt-LatestAnnotation-Title'>{{{annotation_creator}}}{{#annotation_title}}: {{{annotation_title}}}{{/annotation_title}}</div>"
- + " <div class='Ldt-LatestAnnotation-Element Ldt-LatestAnnotation-Content'>"
+ + "<div class='Ldt-LatestAnnotation-Element Ldt-LatestAnnotation-CreationDate'>{{{annotation_created}}}</div>"
+ + "<div class='Ldt-LatestAnnotation-Element Ldt-LatestAnnotation-Title'>{{{annotation_creator}}}{{#annotation_title}}: {{{annotation_title}}}{{/annotation_title}}</div>"
+ + "<div class='Ldt-LatestAnnotation-Element Ldt-LatestAnnotation-Content'>"
+ "{{{annotation_content}}}"
- + " </div>"
+ + "</div>"
+ + "{{#copy_and_edit_button}}<div class='Ldt-LatestAnnotation-CopyEditButton'>{{button_text}}</div>{{/copy_and_edit_button}}"
+ "</div>"
+
IriSP.Widgets.LatestAnnotation.prototype.draw = function(){
var _this = this;
-
this.renderTemplate();
this.annotationContainer_$ = this.$.find('.Ldt-LatestAnnotation');
- this.onMediaEvent("timeupdate", "refresh");
+ if (this.selectable_annotations){
+ this.onMdpEvent("AnnotationsList.refresh", function(){
+ _this.getWidgetAnnotations().forEach(function(_annotation){
+ _annotation.off("click");
+ _annotation.on("click", function(){
+ _html = Mustache.to_html(_this.annotationTemplate, {
+ annotation_created: _annotation.created.toLocaleDateString()+", "+_annotation.created.toLocaleTimeString(),
+ annotation_creator: _annotation.creator,
+ annotation_title: _annotation.title,
+ annotation_content: _annotation.description,
+ copy_and_edit_button: _this.copy_and_edit_button,
+ button_text: _this.l10n.copy_and_edit,
+ });
+ _this.annotationContainer_$.html(_html);
+ _this.selectedAnnotation = true;
+ });
+ });
+ });
+
+ this.segments = _this.source.getAnnotationsByTypeTitle(this.segments_annotation_type)
+ this.segments.forEach(function(_segment){
+ _segment.on("click", function(){
+ _this.selectedAnnotation = false;
+ })
+ })
+ this.currentSegment = false;
+ }
+
+ this.onMediaEvent("timeupdate", function(){
+ _this.refresh();
+ });
+ this.onMediaEvent("settimerange", function(_timeRange){
+ _this.refresh(_timeRange);
+ })
if (this.starts_hidden){
this.visible = true;
@@ -51,40 +114,59 @@
this.show();
}
+ this.selectedAnnotation = false; // This flag tells the widget if it must display last annotation (false) or clicked annotation (true)
+ this.player.trigger("AnnotationsList.refresh");
this.refresh();
}
-IriSP.Widgets.LatestAnnotation.prototype.messages = {
- fr : {
- empty : "Aucune annotation à afficher"
- },
- en: {
- empty: "No annotation to display"
- }
-}
-IriSP.Widgets.LatestAnnotation.prototype.refresh = function(){
- var _currentTime = this.media.getCurrentTime()
- var _segmentsAnnotations = this.source.getAnnotationsByTypeTitle(this.segments_annotation_type)
- var _currentSegments = _segmentsAnnotations.filter(function(_segment){
- return (_currentTime >= _segment.begin && _currentTime <= _segment.end)
- });
+IriSP.Widgets.LatestAnnotation.prototype.refresh = function(_timeRange){
+ _timeRange = typeof _timeRange !== 'undefined' ? _timeRange : false ;
+ var _this = this;
if (this.hide_without_segment){
- if (_currentSegments.length == 0){
+ if (!_timeRange && !this.media.getTimeRange()){
+ var _currentTime = this.media.getCurrentTime();
+ var _currentSegments = this.segments.filter(function(_segment){
+ return (_currentTime >= _segment.begin && _currentTime <= _segment.end)
+ });
+ if (_currentSegments.length == 0){
+ this.currentSegment = false;
+ this.selectedAnnotation = false;
+ }
+ else {
+ this.currentSegment = _currentSegments[0]
+ }
+ }
+ else {
+ var _segmentBegin = _timeRange? _timeRange[0] : this.media.getTimeRange()[0],
+ _segmentEnd = _timeRange? _timeRange[1] : this.media.getTimeRange()[1];
+ if ((!this.currentSegment)||(this.currentSegment.begin != _segmentBegin || this.currentSegment.end != _segmentEnd)) {
+ var _currentSegments = this.segments.filter(function(_segment){
+ return _segment.begin == _segmentBegin && _segment.end == _segmentEnd
+ });
+ if (_currentSegments.length > 0){
+ this.selectedAnnotation = false;
+ this.currentSegment = _currentSegments[0];
+ }
+ }
+ }
+ if (!this.currentSegment){
if (this.visible){
- this.hide()
+ this.hide();
}
}
else {
if (!this.visible){
- this.show()
+ this.show();
}
}
}
- if (this.visible){
+
+ if (this.visible && !this.selectedAnnotation){
var _list = this.getWidgetAnnotations();
+
if(this.filter_by_segment){
- if (_currentSegments.length == 0) {
+ if (!this.currentSegment) {
_list = _list.filter(function(_annotation){
return false;
});
@@ -92,40 +174,56 @@
else {
_list = _list.filter(function(_annotation){
_annotationTime = (_annotation.begin+_annotation.end)/2;
- return (_currentSegments[0].begin <= _annotationTime && _currentSegments[0].end >= _annotationTime);
+ return (_this.currentSegment.begin <= _annotationTime && _this.currentSegment.end >= _annotationTime);
});
}
- _list.sortBy(function(_annotation){
- return _annotation.created;
+ }
+ _list = _list.sortBy(function(_annotation){
+ return _annotation.created;
+ });
+
+ var _latestAnnotation = false;
+ var _html="";
+ if (_list.length != 0){
+ _latestAnnotation = _list.pop();
+ _html = Mustache.to_html(this.annotationTemplate, {
+ annotation_created: _latestAnnotation.created.toLocaleDateString()+", "+_latestAnnotation.created.toLocaleTimeString(),
+ annotation_creator: _latestAnnotation.creator,
+ annotation_title: _latestAnnotation.title,
+ annotation_content: _latestAnnotation.description,
+ copy_and_edit_button: this.copy_and_edit_button,
+ button_text: this.l10n.copy_and_edit,
});
-
- var _latestAnnotation = false;
- var _html="";
- if (_list.length != 0){
- _latestAnnotation = _list.pop();
- _html = Mustache.to_html(this.annotationTemplate, {
- annotation_created: _latestAnnotation.created.toLocaleDateString()+", "+_latestAnnotation.created.toLocaleTimeString(),
- annotation_creator: _latestAnnotation.creator,
- annotation_title: _latestAnnotation.title,
- annotation_content: _latestAnnotation.description,
- });
+ }
+ else {
+ var _empty_message = this.l10n.empty
+ if (this.empty_message) {
+ _empty_message = this.empty_message
}
- else {
- var _empty_message = this.l10n.empty
- if (this.empty_message) {
- _empty_message = this.empty_message
- }
- _html = "<div class='Ldt-LatestAnnotation-Element Ldt-LatestAnnotation-NoAnnotation'>"+_empty_message+"</div>";
- }
- this.annotationContainer_$.html(_html);
-
+ _html = "<div class='Ldt-LatestAnnotation-Element Ldt-LatestAnnotation-NoAnnotation'>"+_empty_message+"</div>";
}
+ this.annotationContainer_$.html(_html);
}
+
+ if(this.copy_and_edit_button){
+ this.copyAndEditButton_$ = this.$.find('.Ldt-LatestAnnotation-CopyEditButton');
+ this.copyAndEditButton_$.click(this.functionWrapper("copy_and_edit"));
+ }
+}
+
+IriSP.Widgets.LatestAnnotation.prototype.copy_and_edit = function(){
+ this.player.trigger("CreateAnnotation.show");
+ this.player.trigger("AnnotationsList.hide");
+ annotationText = $('.Ldt-LatestAnnotation-Content').get(0).innerHTML;
+
+ $('.Ldt-CreateAnnotation-Description').removeClass('empty');
+ $('.Ldt-CreateAnnotation-Description').val(annotationText);
}
IriSP.Widgets.LatestAnnotation.prototype.hide = function() {
if (this.visible){
this.visible = false;
+ this.$.find('.Ldt-LatestAnnotation-header').hide();
this.annotationContainer_$.hide()
}
}
@@ -133,6 +231,7 @@
IriSP.Widgets.LatestAnnotation.prototype.show = function() {
if(!this.visible){
this.visible = true;
+ this.$.find('.Ldt-LatestAnnotation-header').show();
this.annotationContainer_$.show()
}
}
Binary file src/widgets/img/loader.gif has changed