diff --git a/dashboard-ui/bower_components/Sortable/Sortable.min.js b/dashboard-ui/bower_components/Sortable/Sortable.min.js index e95d2a301f..d5e2b5f37a 100644 --- a/dashboard-ui/bower_components/Sortable/Sortable.min.js +++ b/dashboard-ui/bower_components/Sortable/Sortable.min.js @@ -1,2 +1,393 @@ -/*! Sortable 1.4.2 - MIT | git://github.com/rubaxa/Sortable.git */ -!function(a){"use strict";"function"==typeof define&&define.amd?define(a):"undefined"!=typeof module&&"undefined"!=typeof module.exports?module.exports=a():"undefined"!=typeof Package?Sortable=a():window.Sortable=a()}(function(){"use strict";function a(a,b){if(!a||!a.nodeType||1!==a.nodeType)throw"Sortable: `el` must be HTMLElement, and not "+{}.toString.call(a);this.el=a,this.options=b=r({},b),a[L]=this;var c={group:Math.random(),sort:!0,disabled:!1,store:null,handle:null,scroll:!0,scrollSensitivity:30,scrollSpeed:10,draggable:/[uo]l/i.test(a.nodeName)?"li":">*",ghostClass:"sortable-ghost",chosenClass:"sortable-chosen",ignore:"a, img",filter:null,animation:0,setData:function(a,b){a.setData("Text",b.textContent)},dropBubble:!1,dragoverBubble:!1,dataIdAttr:"data-id",delay:0,forceFallback:!1,fallbackClass:"sortable-fallback",fallbackOnBody:!1};for(var d in c)!(d in b)&&(b[d]=c[d]);V(b);for(var f in this)"_"===f.charAt(0)&&(this[f]=this[f].bind(this));this.nativeDraggable=b.forceFallback?!1:P,e(a,"mousedown",this._onTapStart),e(a,"touchstart",this._onTapStart),this.nativeDraggable&&(e(a,"dragover",this),e(a,"dragenter",this)),T.push(this._onDragOver),b.store&&this.sort(b.store.get(this))}function b(a){v&&v.state!==a&&(h(v,"display",a?"none":""),!a&&v.state&&w.insertBefore(v,s),v.state=a)}function c(a,b,c){if(a){c=c||N,b=b.split(".");var d=b.shift().toUpperCase(),e=new RegExp("\\s("+b.join("|")+")(?=\\s)","g");do if(">*"===d&&a.parentNode===c||(""===d||a.nodeName.toUpperCase()==d)&&(!b.length||((" "+a.className+" ").match(e)||[]).length==b.length))return a;while(a!==c&&(a=a.parentNode))}return null}function d(a){a.dataTransfer&&(a.dataTransfer.dropEffect="move"),a.preventDefault()}function e(a,b,c){a.addEventListener(b,c,!1)}function f(a,b,c){a.removeEventListener(b,c,!1)}function g(a,b,c){if(a)if(a.classList)a.classList[c?"add":"remove"](b);else{var d=(" "+a.className+" ").replace(K," ").replace(" "+b+" "," ");a.className=(d+(c?" "+b:"")).replace(K," ")}}function h(a,b,c){var d=a&&a.style;if(d){if(void 0===c)return N.defaultView&&N.defaultView.getComputedStyle?c=N.defaultView.getComputedStyle(a,""):a.currentStyle&&(c=a.currentStyle),void 0===b?c:c[b];b in d||(b="-webkit-"+b),d[b]=c+("string"==typeof c?"":"px")}}function i(a,b,c){if(a){var d=a.getElementsByTagName(b),e=0,f=d.length;if(c)for(;f>e;e++)c(d[e],e);return d}return[]}function j(a,b,c,d,e,f,g){var h=N.createEvent("Event"),i=(a||b[L]).options,j="on"+c.charAt(0).toUpperCase()+c.substr(1);h.initEvent(c,!0,!0),h.to=b,h.from=e||b,h.item=d||b,h.clone=v,h.oldIndex=f,h.newIndex=g,b.dispatchEvent(h),i[j]&&i[j].call(a,h)}function k(a,b,c,d,e,f){var g,h,i=a[L],j=i.options.onMove;return g=N.createEvent("Event"),g.initEvent("move",!0,!0),g.to=b,g.from=a,g.dragged=c,g.draggedRect=d,g.related=e||b,g.relatedRect=f||b.getBoundingClientRect(),a.dispatchEvent(g),j&&(h=j.call(i,g)),h}function l(a){a.draggable=!1}function m(){R=!1}function n(a,b){var c=a.lastElementChild,d=c.getBoundingClientRect();return(b.clientY-(d.top+d.height)>5||b.clientX-(d.right+d.width)>5)&&c}function o(a){for(var b=a.tagName+a.className+a.src+a.href+a.textContent,c=b.length,d=0;c--;)d+=b.charCodeAt(c);return d.toString(36)}function p(a){var b=0;if(!a||!a.parentNode)return-1;for(;a&&(a=a.previousElementSibling);)"TEMPLATE"!==a.nodeName.toUpperCase()&&b++;return b}function q(a,b){var c,d;return function(){void 0===c&&(c=arguments,d=this,setTimeout(function(){1===c.length?a.call(d,c[0]):a.apply(d,c),c=void 0},b))}}function r(a,b){if(a&&b)for(var c in b)b.hasOwnProperty(c)&&(a[c]=b[c]);return a}var s,t,u,v,w,x,y,z,A,B,C,D,E,F,G,H,I,J={},K=/\s+/g,L="Sortable"+(new Date).getTime(),M=window,N=M.document,O=M.parseInt,P=!!("draggable"in N.createElement("div")),Q=function(a){return a=N.createElement("x"),a.style.cssText="pointer-events:auto","auto"===a.style.pointerEvents}(),R=!1,S=Math.abs,T=([].slice,[]),U=q(function(a,b,c){if(c&&b.scroll){var d,e,f,g,h=b.scrollSensitivity,i=b.scrollSpeed,j=a.clientX,k=a.clientY,l=window.innerWidth,m=window.innerHeight;if(z!==c&&(y=b.scroll,z=c,y===!0)){y=c;do if(y.offsetWidth=l-j)-(h>=j),g=(h>=m-k)-(h>=k),(f||g)&&(d=M)),(J.vx!==f||J.vy!==g||J.el!==d)&&(J.el=d,J.vx=f,J.vy=g,clearInterval(J.pid),d&&(J.pid=setInterval(function(){d===M?M.scrollTo(M.pageXOffset+f*i,M.pageYOffset+g*i):(g&&(d.scrollTop+=g*i),f&&(d.scrollLeft+=f*i))},24)))}},30),V=function(a){var b=a.group;b&&"object"==typeof b||(b=a.group={name:b}),["pull","put"].forEach(function(a){a in b||(b[a]=!0)}),a.groups=" "+b.name+(b.put.join?" "+b.put.join(" "):"")+" "};return a.prototype={constructor:a,_onTapStart:function(a){var b=this,d=this.el,e=this.options,f=a.type,g=a.touches&&a.touches[0],h=(g||a).target,i=h,k=e.filter;if(!("mousedown"===f&&0!==a.button||e.disabled)&&(h=c(h,e.draggable,d))){if(D=p(h),"function"==typeof k){if(k.call(this,a,h,this))return j(b,i,"filter",h,d,D),void a.preventDefault()}else if(k&&(k=k.split(",").some(function(a){return a=c(i,a.trim(),d),a?(j(b,a,"filter",h,d,D),!0):void 0})))return void a.preventDefault();(!e.handle||c(i,e.handle,d))&&this._prepareDragStart(a,g,h)}},_prepareDragStart:function(a,b,c){var d,f=this,h=f.el,j=f.options,k=h.ownerDocument;c&&!s&&c.parentNode===h&&(G=a,w=h,s=c,t=s.parentNode,x=s.nextSibling,F=j.group,d=function(){f._disableDelayedDrag(),s.draggable=!0,g(s,f.options.chosenClass,!0),f._triggerDragStart(b)},j.ignore.split(",").forEach(function(a){i(s,a.trim(),l)}),e(k,"mouseup",f._onDrop),e(k,"touchend",f._onDrop),e(k,"touchcancel",f._onDrop),j.delay?(e(k,"mouseup",f._disableDelayedDrag),e(k,"touchend",f._disableDelayedDrag),e(k,"touchcancel",f._disableDelayedDrag),e(k,"mousemove",f._disableDelayedDrag),e(k,"touchmove",f._disableDelayedDrag),f._dragStartTimer=setTimeout(d,j.delay)):d())},_disableDelayedDrag:function(){var a=this.el.ownerDocument;clearTimeout(this._dragStartTimer),f(a,"mouseup",this._disableDelayedDrag),f(a,"touchend",this._disableDelayedDrag),f(a,"touchcancel",this._disableDelayedDrag),f(a,"mousemove",this._disableDelayedDrag),f(a,"touchmove",this._disableDelayedDrag)},_triggerDragStart:function(a){a?(G={target:s,clientX:a.clientX,clientY:a.clientY},this._onDragStart(G,"touch")):this.nativeDraggable?(e(s,"dragend",this),e(w,"dragstart",this._onDragStart)):this._onDragStart(G,!0);try{N.selection?N.selection.empty():window.getSelection().removeAllRanges()}catch(b){}},_dragStarted:function(){w&&s&&(g(s,this.options.ghostClass,!0),a.active=this,j(this,w,"start",s,w,D))},_emulateDragOver:function(){if(H){if(this._lastX===H.clientX&&this._lastY===H.clientY)return;this._lastX=H.clientX,this._lastY=H.clientY,Q||h(u,"display","none");var a=N.elementFromPoint(H.clientX,H.clientY),b=a,c=" "+this.options.group.name,d=T.length;if(b)do{if(b[L]&&b[L].options.groups.indexOf(c)>-1){for(;d--;)T[d]({clientX:H.clientX,clientY:H.clientY,target:a,rootEl:b});break}a=b}while(b=b.parentNode);Q||h(u,"display","")}},_onTouchMove:function(b){if(G){a.active||this._dragStarted(),this._appendGhost();var c=b.touches?b.touches[0]:b,d=c.clientX-G.clientX,e=c.clientY-G.clientY,f=b.touches?"translate3d("+d+"px,"+e+"px,0)":"translate("+d+"px,"+e+"px)";I=!0,H=c,h(u,"webkitTransform",f),h(u,"mozTransform",f),h(u,"msTransform",f),h(u,"transform",f),b.preventDefault()}},_appendGhost:function(){if(!u){var a,b=s.getBoundingClientRect(),c=h(s),d=this.options;u=s.cloneNode(!0),g(u,d.ghostClass,!1),g(u,d.fallbackClass,!0),h(u,"top",b.top-O(c.marginTop,10)),h(u,"left",b.left-O(c.marginLeft,10)),h(u,"width",b.width),h(u,"height",b.height),h(u,"opacity","0.8"),h(u,"position","fixed"),h(u,"zIndex","100000"),h(u,"pointerEvents","none"),d.fallbackOnBody&&N.body.appendChild(u)||w.appendChild(u),a=u.getBoundingClientRect(),h(u,"width",2*b.width-a.width),h(u,"height",2*b.height-a.height)}},_onDragStart:function(a,b){var c=a.dataTransfer,d=this.options;this._offUpEvents(),"clone"==F.pull&&(v=s.cloneNode(!0),h(v,"display","none"),w.insertBefore(v,s)),b?("touch"===b?(e(N,"touchmove",this._onTouchMove),e(N,"touchend",this._onDrop),e(N,"touchcancel",this._onDrop)):(e(N,"mousemove",this._onTouchMove),e(N,"mouseup",this._onDrop)),this._loopId=setInterval(this._emulateDragOver,50)):(c&&(c.effectAllowed="move",d.setData&&d.setData.call(this,c,s)),e(N,"drop",this),setTimeout(this._dragStarted,0))},_onDragOver:function(a){var d,e,f,g=this.el,i=this.options,j=i.group,l=j.put,o=F===j,p=i.sort;if(void 0!==a.preventDefault&&(a.preventDefault(),!i.dragoverBubble&&a.stopPropagation()),I=!0,F&&!i.disabled&&(o?p||(f=!w.contains(s)):F.pull&&l&&(F.name===j.name||l.indexOf&&~l.indexOf(F.name)))&&(void 0===a.rootEl||a.rootEl===this.el)){if(U(a,i,this.el),R)return;if(d=c(a.target,i.draggable,g),e=s.getBoundingClientRect(),f)return b(!0),void(v||x?w.insertBefore(s,v||x):p||w.appendChild(s));if(0===g.children.length||g.children[0]===u||g===a.target&&(d=n(g,a))){if(d){if(d.animated)return;r=d.getBoundingClientRect()}b(o),k(w,g,s,e,d,r)!==!1&&(s.contains(g)||(g.appendChild(s),t=g),this._animate(e,s),d&&this._animate(r,d))}else if(d&&!d.animated&&d!==s&&void 0!==d.parentNode[L]){A!==d&&(A=d,B=h(d),C=h(d.parentNode));var q,r=d.getBoundingClientRect(),y=r.right-r.left,z=r.bottom-r.top,D=/left|right|inline/.test(B.cssFloat+B.display)||"flex"==C.display&&0===C["flex-direction"].indexOf("row"),E=d.offsetWidth>s.offsetWidth,G=d.offsetHeight>s.offsetHeight,H=(D?(a.clientX-r.left)/y:(a.clientY-r.top)/z)>.5,J=d.nextElementSibling,K=k(w,g,s,e,d,r);if(K!==!1){if(R=!0,setTimeout(m,30),b(o),1===K||-1===K)q=1===K;else if(D){var M=s.offsetTop,N=d.offsetTop;q=M===N?d.previousElementSibling===s&&!E||H&&E:N>M}else q=J!==s&&!G||H&&G;s.contains(g)||(q&&!J?g.appendChild(s):d.parentNode.insertBefore(s,q?J:d)),t=s.parentNode,this._animate(e,s),this._animate(r,d)}}}},_animate:function(a,b){var c=this.options.animation;if(c){var d=b.getBoundingClientRect();h(b,"transition","none"),h(b,"transform","translate3d("+(a.left-d.left)+"px,"+(a.top-d.top)+"px,0)"),b.offsetWidth,h(b,"transition","all "+c+"ms"),h(b,"transform","translate3d(0,0,0)"),clearTimeout(b.animated),b.animated=setTimeout(function(){h(b,"transition",""),h(b,"transform",""),b.animated=!1},c)}},_offUpEvents:function(){var a=this.el.ownerDocument;f(N,"touchmove",this._onTouchMove),f(a,"mouseup",this._onDrop),f(a,"touchend",this._onDrop),f(a,"touchcancel",this._onDrop)},_onDrop:function(b){var c=this.el,d=this.options;clearInterval(this._loopId),clearInterval(J.pid),clearTimeout(this._dragStartTimer),f(N,"mousemove",this._onTouchMove),this.nativeDraggable&&(f(N,"drop",this),f(c,"dragstart",this._onDragStart)),this._offUpEvents(),b&&(I&&(b.preventDefault(),!d.dropBubble&&b.stopPropagation()),u&&u.parentNode.removeChild(u),s&&(this.nativeDraggable&&f(s,"dragend",this),l(s),g(s,this.options.ghostClass,!1),g(s,this.options.chosenClass,!1),w!==t?(E=p(s),E>=0&&(j(null,t,"sort",s,w,D,E),j(this,w,"sort",s,w,D,E),j(null,t,"add",s,w,D,E),j(this,w,"remove",s,w,D,E))):(v&&v.parentNode.removeChild(v),s.nextSibling!==x&&(E=p(s),E>=0&&(j(this,w,"update",s,w,D,E),j(this,w,"sort",s,w,D,E)))),a.active&&((null===E||-1===E)&&(E=D),j(this,w,"end",s,w,D,E),this.save())),w=s=t=u=x=v=y=z=G=H=I=E=A=B=F=a.active=null)},handleEvent:function(a){var b=a.type;"dragover"===b||"dragenter"===b?s&&(this._onDragOver(a),d(a)):("drop"===b||"dragend"===b)&&this._onDrop(a)},toArray:function(){for(var a,b=[],d=this.el.children,e=0,f=d.length,g=this.options;f>e;e++)a=d[e],c(a,g.draggable,this.el)&&b.push(a.getAttribute(g.dataIdAttr)||o(a));return b},sort:function(a){var b={},d=this.el;this.toArray().forEach(function(a,e){var f=d.children[e];c(f,this.options.draggable,d)&&(b[a]=f)},this),a.forEach(function(a){b[a]&&(d.removeChild(b[a]),d.appendChild(b[a]))})},save:function(){var a=this.options.store;a&&a.set(this)},closest:function(a,b){return c(a,b||this.options.draggable,this.el)},option:function(a,b){var c=this.options;return void 0===b?c[a]:(c[a]=b,void("group"===a&&V(c)))},destroy:function(){var a=this.el;a[L]=null,f(a,"mousedown",this._onTapStart),f(a,"touchstart",this._onTapStart),this.nativeDraggable&&(f(a,"dragover",this),f(a,"dragenter",this)),Array.prototype.forEach.call(a.querySelectorAll("[draggable]"),function(a){a.removeAttribute("draggable")}),T.splice(T.indexOf(this._onDragOver),1),this._onDrop(),this.el=a=null}},a.utils={on:e,off:f,css:h,find:i,is:function(a,b){return!!c(a,b,a)},extend:r,throttle:q,closest:c,toggleClass:g,index:p},a.create=function(b,c){return new a(b,c)},a.version="1.4.2",a}); \ No newline at end of file +/*! Sortable 1.4.2 - MIT | git://github.com/rubaxa/Sortable.git */ ! function(a) { + "use strict"; + "function" == typeof define && define.amd ? define(a) : "undefined" != typeof module && "undefined" != typeof module.exports ? module.exports = a() : "undefined" != typeof Package ? Sortable = a() : window.Sortable = a() +}(function() { + "use strict"; + + function a(a, b) { + if (!a || !a.nodeType || 1 !== a.nodeType) throw "Sortable: `el` must be HTMLElement, and not " + {}.toString.call(a); + this.el = a, this.options = b = r({}, b), a[L] = this; + var c = { + group: Math.random(), + sort: !0, + disabled: !1, + store: null, + handle: null, + scroll: !0, + scrollSensitivity: 30, + scrollSpeed: 10, + draggable: /[uo]l/i.test(a.nodeName) ? "li" : ">*", + ghostClass: "sortable-ghost", + chosenClass: "sortable-chosen", + ignore: "a, img", + filter: null, + animation: 0, + setData: function(a, b) { + a.setData("Text", b.textContent) + }, + dropBubble: !1, + dragoverBubble: !1, + dataIdAttr: "data-id", + delay: 0, + forceFallback: !1, + fallbackClass: "sortable-fallback", + fallbackOnBody: !1 + }; + for (var d in c) !(d in b) && (b[d] = c[d]); + V(b); + for (var f in this) "_" === f.charAt(0) && (this[f] = this[f].bind(this)); + this.nativeDraggable = b.forceFallback ? !1 : P, e(a, "mousedown", this._onTapStart), e(a, "touchstart", this._onTapStart), this.nativeDraggable && (e(a, "dragover", this), e(a, "dragenter", this)), T.push(this._onDragOver), b.store && this.sort(b.store.get(this)) + } + + function b(a) { + v && v.state !== a && (h(v, "display", a ? "none" : ""), !a && v.state && w.insertBefore(v, s), v.state = a) + } + + function c(a, b, c) { + if (a) { + c = c || N, b = b.split("."); + var d = b.shift().toUpperCase(), + e = new RegExp("\\s(" + b.join("|") + ")(?=\\s)", "g"); + do + if (">*" === d && a.parentNode === c || ("" === d || a.nodeName.toUpperCase() == d) && (!b.length || ((" " + a.className + " ").match(e) || []).length == b.length)) return a; while (a !== c && (a = a.parentNode)) + } + return null + } + + function d(a) { + a.dataTransfer && (a.dataTransfer.dropEffect = "move"), a.preventDefault() + } + + function e(a, b, c) { + a.addEventListener(b, c, !1) + } + + function f(a, b, c) { + a.removeEventListener(b, c, !1) + } + + function g(a, b, c) { + if (a) + if (a.classList) a.classList[c ? "add" : "remove"](b); + else { + var d = (" " + a.className + " ").replace(K, " ").replace(" " + b + " ", " "); + a.className = (d + (c ? " " + b : "")).replace(K, " ") + } + } + + function h(a, b, c) { + var d = a && a.style; + if (d) { + if (void 0 === c) return N.defaultView && N.defaultView.getComputedStyle ? c = N.defaultView.getComputedStyle(a, "") : a.currentStyle && (c = a.currentStyle), void 0 === b ? c : c[b]; + b in d || (b = "-webkit-" + b), d[b] = c + ("string" == typeof c ? "" : "px") + } + } + + function i(a, b, c) { + if (a) { + var d = a.getElementsByTagName(b), + e = 0, + f = d.length; + if (c) + for (; f > e; e++) c(d[e], e); + return d + } + return [] + } + + function j(a, b, c, d, e, f, g) { + var h = N.createEvent("Event"), + i = (a || b[L]).options, + j = "on" + c.charAt(0).toUpperCase() + c.substr(1); + h.initEvent(c, !0, !0), h.to = b, h.from = e || b, h.item = d || b, h.clone = v, h.oldIndex = f, h.newIndex = g, b.dispatchEvent(h), i[j] && i[j].call(a, h) + } + + function k(a, b, c, d, e, f) { + var g, h, i = a[L], + j = i.options.onMove; + return g = N.createEvent("Event"), g.initEvent("move", !0, !0), g.to = b, g.from = a, g.dragged = c, g.draggedRect = d, g.related = e || b, g.relatedRect = f || b.getBoundingClientRect(), a.dispatchEvent(g), j && (h = j.call(i, g)), h + } + + function l(a) { + a.draggable = !1 + } + + function m() { + R = !1 + } + + function n(a, b) { + var c = a.lastElementChild, + d = c.getBoundingClientRect(); + return (b.clientY - (d.top + d.height) > 5 || b.clientX - (d.right + d.width) > 5) && c + } + + function o(a) { + for (var b = a.tagName + a.className + a.src + a.href + a.textContent, c = b.length, d = 0; c--;) d += b.charCodeAt(c); + return d.toString(36) + } + + function p(a) { + var b = 0; + if (!a || !a.parentNode) return -1; + for (; a && (a = a.previousElementSibling);) "TEMPLATE" !== a.nodeName.toUpperCase() && b++; + return b + } + + function q(a, b) { + var c, d; + return function() { + void 0 === c && (c = arguments, d = this, setTimeout(function() { + 1 === c.length ? a.call(d, c[0]) : a.apply(d, c), c = void 0 + }, b)) + } + } + + function r(a, b) { + if (a && b) + for (var c in b) b.hasOwnProperty(c) && (a[c] = b[c]); + return a + } + var s, t, u, v, w, x, y, z, A, B, C, D, E, F, G, H, I, J = {}, + K = /\s+/g, + L = "Sortable" + (new Date).getTime(), + M = window, + N = M.document, + O = M.parseInt, + P = !!("draggable" in N.createElement("div")), + Q = function(a) { + return a = N.createElement("x"), a.style.cssText = "pointer-events:auto", "auto" === a.style.pointerEvents + }(), + R = !1, + S = Math.abs, + T = ([].slice, []), + U = q(function(a, b, c) { + if (c && b.scroll) { + var d, e, f, g, h = b.scrollSensitivity, + i = b.scrollSpeed, + j = a.clientX, + k = a.clientY, + l = window.innerWidth, + m = window.innerHeight; + if (z !== c && (y = b.scroll, z = c, y === !0)) { + y = c; + do + if (y.offsetWidth < y.scrollWidth || y.offsetHeight < y.scrollHeight) break; while (y = y.parentNode) + } + y && (d = y, e = y.getBoundingClientRect(), f = (S(e.right - j) <= h) - (S(e.left - j) <= h), g = (S(e.bottom - k) <= h) - (S(e.top - k) <= h)), f || g || (f = (h >= l - j) - (h >= j), g = (h >= m - k) - (h >= k), (f || g) && (d = M)), (J.vx !== f || J.vy !== g || J.el !== d) && (J.el = d, J.vx = f, J.vy = g, clearInterval(J.pid), d && (J.pid = setInterval(function() { + d === M ? M.scrollTo(M.pageXOffset + f * i, M.pageYOffset + g * i) : (g && (d.scrollTop += g * i), f && (d.scrollLeft += f * i)) + }, 24))) + } + }, 30), + V = function(a) { + var b = a.group; + b && "object" == typeof b || (b = a.group = { + name: b + }), ["pull", "put"].forEach(function(a) { + a in b || (b[a] = !0) + }), a.groups = " " + b.name + (b.put.join ? " " + b.put.join(" ") : "") + " " + }; + return a.prototype = { + constructor: a, + _onTapStart: function(a) { + var b = this, + d = this.el, + e = this.options, + f = a.type, + g = a.touches && a.touches[0], + h = (g || a).target, + i = h, + k = e.filter; + if (!("mousedown" === f && 0 !== a.button || e.disabled) && (h = c(h, e.draggable, d))) { + if (D = p(h), "function" == typeof k) { + if (k.call(this, a, h, this)) return j(b, i, "filter", h, d, D), void a.preventDefault() + } else if (k && (k = k.split(",").some(function(a) { + return a = c(i, a.trim(), d), a ? (j(b, a, "filter", h, d, D), !0) : void 0 + }))) return void a.preventDefault(); + (!e.handle || c(i, e.handle, d)) && this._prepareDragStart(a, g, h) + } + }, + _prepareDragStart: function(a, b, c) { + var d, f = this, + h = f.el, + j = f.options, + k = h.ownerDocument; + c && !s && c.parentNode === h && (G = a, w = h, s = c, t = s.parentNode, x = s.nextSibling, F = j.group, d = function() { + f._disableDelayedDrag(), s.draggable = !0, g(s, f.options.chosenClass, !0), f._triggerDragStart(b) + }, j.ignore.split(",").forEach(function(a) { + i(s, a.trim(), l) + }), e(k, "mouseup", f._onDrop), e(k, "touchend", f._onDrop), e(k, "touchcancel", f._onDrop), j.delay ? (e(k, "mouseup", f._disableDelayedDrag), e(k, "touchend", f._disableDelayedDrag), e(k, "touchcancel", f._disableDelayedDrag), e(k, "mousemove", f._disableDelayedDrag), e(k, "touchmove", f._disableDelayedDrag), f._dragStartTimer = setTimeout(d, j.delay)) : d()) + }, + _disableDelayedDrag: function() { + var a = this.el.ownerDocument; + clearTimeout(this._dragStartTimer), f(a, "mouseup", this._disableDelayedDrag), f(a, "touchend", this._disableDelayedDrag), f(a, "touchcancel", this._disableDelayedDrag), f(a, "mousemove", this._disableDelayedDrag), f(a, "touchmove", this._disableDelayedDrag) + }, + _triggerDragStart: function(a) { + a ? (G = { + target: s, + clientX: a.clientX, + clientY: a.clientY + }, this._onDragStart(G, "touch")) : this.nativeDraggable ? (e(s, "dragend", this), e(w, "dragstart", this._onDragStart)) : this._onDragStart(G, !0); + try { + N.selection ? N.selection.empty() : window.getSelection().removeAllRanges() + } catch (b) {} + }, + _dragStarted: function() { + w && s && (g(s, this.options.ghostClass, !0), a.active = this, j(this, w, "start", s, w, D)) + }, + _emulateDragOver: function() { + if (H) { + if (this._lastX === H.clientX && this._lastY === H.clientY) return; + this._lastX = H.clientX, this._lastY = H.clientY, Q || h(u, "display", "none"); + var a = N.elementFromPoint(H.clientX, H.clientY), + b = a, + c = " " + this.options.group.name, + d = T.length; + if (b) + do { + if (b[L] && b[L].options.groups.indexOf(c) > -1) { + for (; d--;) T[d]({ + clientX: H.clientX, + clientY: H.clientY, + target: a, + rootEl: b + }); + break + } + a = b + } while (b = b.parentNode); + Q || h(u, "display", "") + } + }, + _onTouchMove: function(b) { + if (G) { + a.active || this._dragStarted(), this._appendGhost(); + var c = b.touches ? b.touches[0] : b, + d = c.clientX - G.clientX, + e = c.clientY - G.clientY, + f = b.touches ? "translate3d(" + d + "px," + e + "px,0)" : "translate(" + d + "px," + e + "px)"; + I = !0, H = c, h(u, "webkitTransform", f), h(u, "mozTransform", f), h(u, "msTransform", f), h(u, "transform", f), b.preventDefault() + } + }, + _appendGhost: function() { + if (!u) { + var a, b = s.getBoundingClientRect(), + c = h(s), + d = this.options; + u = s.cloneNode(!0), g(u, d.ghostClass, !1), g(u, d.fallbackClass, !0), h(u, "top", b.top - O(c.marginTop, 10)), h(u, "left", b.left - O(c.marginLeft, 10)), h(u, "width", b.width), h(u, "height", b.height), h(u, "opacity", "0.8"), h(u, "position", "fixed"), h(u, "zIndex", "100000"), h(u, "pointerEvents", "none"), d.fallbackOnBody && N.body.appendChild(u) || w.appendChild(u), a = u.getBoundingClientRect(), h(u, "width", 2 * b.width - a.width), h(u, "height", 2 * b.height - a.height) + } + }, + _onDragStart: function(a, b) { + var c = a.dataTransfer, + d = this.options; + this._offUpEvents(), "clone" == F.pull && (v = s.cloneNode(!0), h(v, "display", "none"), w.insertBefore(v, s)), b ? ("touch" === b ? (e(N, "touchmove", this._onTouchMove), e(N, "touchend", this._onDrop), e(N, "touchcancel", this._onDrop)) : (e(N, "mousemove", this._onTouchMove), e(N, "mouseup", this._onDrop)), this._loopId = setInterval(this._emulateDragOver, 50)) : (c && (c.effectAllowed = "move", d.setData && d.setData.call(this, c, s)), e(N, "drop", this), setTimeout(this._dragStarted, 0)) + }, + _onDragOver: function(a) { + var d, e, f, g = this.el, + i = this.options, + j = i.group, + l = j.put, + o = F === j, + p = i.sort; + if (void 0 !== a.preventDefault && (a.preventDefault(), !i.dragoverBubble && a.stopPropagation()), I = !0, F && !i.disabled && (o ? p || (f = !w.contains(s)) : F.pull && l && (F.name === j.name || l.indexOf && ~l.indexOf(F.name))) && (void 0 === a.rootEl || a.rootEl === this.el)) { + if (U(a, i, this.el), R) return; + if (d = c(a.target, i.draggable, g), e = s.getBoundingClientRect(), f) return b(!0), void(v || x ? w.insertBefore(s, v || x) : p || w.appendChild(s)); + if (0 === g.children.length || g.children[0] === u || g === a.target && (d = n(g, a))) { + if (d) { + if (d.animated) return; + r = d.getBoundingClientRect() + } + b(o), k(w, g, s, e, d, r) !== !1 && (s.contains(g) || (g.appendChild(s), t = g), this._animate(e, s), d && this._animate(r, d)) + } else if (d && !d.animated && d !== s && void 0 !== d.parentNode[L]) { + A !== d && (A = d, B = h(d), C = h(d.parentNode)); + var q, r = d.getBoundingClientRect(), + y = r.right - r.left, + z = r.bottom - r.top, + D = /left|right|inline/.test(B.cssFloat + B.display) || "flex" == C.display && 0 === C["flex-direction"].indexOf("row"), + E = d.offsetWidth > s.offsetWidth, + G = d.offsetHeight > s.offsetHeight, + H = (D ? (a.clientX - r.left) / y : (a.clientY - r.top) / z) > .5, + J = d.nextElementSibling, + K = k(w, g, s, e, d, r); + if (K !== !1) { + if (R = !0, setTimeout(m, 30), b(o), 1 === K || -1 === K) q = 1 === K; + else if (D) { + var M = s.offsetTop, + N = d.offsetTop; + q = M === N ? d.previousElementSibling === s && !E || H && E : N > M + } else q = J !== s && !G || H && G; + s.contains(g) || (q && !J ? g.appendChild(s) : d.parentNode.insertBefore(s, q ? J : d)), t = s.parentNode, this._animate(e, s), this._animate(r, d) + } + } + } + }, + _animate: function(a, b) { + var c = this.options.animation; + if (c) { + var d = b.getBoundingClientRect(); + h(b, "transition", "none"), h(b, "transform", "translate3d(" + (a.left - d.left) + "px," + (a.top - d.top) + "px,0)"), b.offsetWidth, h(b, "transition", "all " + c + "ms"), h(b, "transform", "translate3d(0,0,0)"), clearTimeout(b.animated), b.animated = setTimeout(function() { + h(b, "transition", ""), h(b, "transform", ""), b.animated = !1 + }, c) + } + }, + _offUpEvents: function() { + var a = this.el.ownerDocument; + f(N, "touchmove", this._onTouchMove), f(a, "mouseup", this._onDrop), f(a, "touchend", this._onDrop), f(a, "touchcancel", this._onDrop) + }, + _onDrop: function(b) { + var c = this.el, + d = this.options; + clearInterval(this._loopId), clearInterval(J.pid), clearTimeout(this._dragStartTimer), f(N, "mousemove", this._onTouchMove), this.nativeDraggable && (f(N, "drop", this), f(c, "dragstart", this._onDragStart)), this._offUpEvents(), b && (I && (b.preventDefault(), !d.dropBubble && b.stopPropagation()), u && u.parentNode.removeChild(u), s && (this.nativeDraggable && f(s, "dragend", this), l(s), g(s, this.options.ghostClass, !1), g(s, this.options.chosenClass, !1), w !== t ? (E = p(s), E >= 0 && (j(null, t, "sort", s, w, D, E), j(this, w, "sort", s, w, D, E), j(null, t, "add", s, w, D, E), j(this, w, "remove", s, w, D, E))) : (v && v.parentNode.removeChild(v), s.nextSibling !== x && (E = p(s), E >= 0 && (j(this, w, "update", s, w, D, E), j(this, w, "sort", s, w, D, E)))), a.active && ((null === E || -1 === E) && (E = D), j(this, w, "end", s, w, D, E), this.save())), w = s = t = u = x = v = y = z = G = H = I = E = A = B = F = a.active = null) + }, + handleEvent: function(a) { + var b = a.type; + "dragover" === b || "dragenter" === b ? s && (this._onDragOver(a), d(a)) : ("drop" === b || "dragend" === b) && this._onDrop(a) + }, + toArray: function() { + for (var a, b = [], d = this.el.children, e = 0, f = d.length, g = this.options; f > e; e++) a = d[e], c(a, g.draggable, this.el) && b.push(a.getAttribute(g.dataIdAttr) || o(a)); + return b + }, + sort: function(a) { + var b = {}, + d = this.el; + this.toArray().forEach(function(a, e) { + var f = d.children[e]; + c(f, this.options.draggable, d) && (b[a] = f) + }, this), a.forEach(function(a) { + b[a] && (d.removeChild(b[a]), d.appendChild(b[a])) + }) + }, + save: function() { + var a = this.options.store; + a && a.set(this) + }, + closest: function(a, b) { + return c(a, b || this.options.draggable, this.el) + }, + option: function(a, b) { + var c = this.options; + return void 0 === b ? c[a] : (c[a] = b, void("group" === a && V(c))) + }, + destroy: function() { + var a = this.el; + a[L] = null, f(a, "mousedown", this._onTapStart), f(a, "touchstart", this._onTapStart), this.nativeDraggable && (f(a, "dragover", this), f(a, "dragenter", this)), Array.prototype.forEach.call(a.querySelectorAll("[draggable]"), function(a) { + a.removeAttribute("draggable") + }), T.splice(T.indexOf(this._onDragOver), 1), this._onDrop(), this.el = a = null + } + }, a.utils = { + on: e, + off: f, + css: h, + find: i, + is: function(a, b) { + return !!c(a, b, a) + }, + extend: r, + throttle: q, + closest: c, + toggleClass: g, + index: p + }, a.create = function(b, c) { + return new a(b, c) + }, a.version = "1.4.2", a +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/Sortable/jquery.binding.js b/dashboard-ui/bower_components/Sortable/jquery.binding.js index b85cd4b2f1..95970ca2a3 100644 --- a/dashboard-ui/bower_components/Sortable/jquery.binding.js +++ b/dashboard-ui/bower_components/Sortable/jquery.binding.js @@ -1 +1,17 @@ -!function(factory){"use strict";"function"==typeof define&&define.amd?define(["jquery"],factory):factory(jQuery)}(function($){"use strict";$.fn.sortable=function(options){var retVal,args=arguments;return this.each(function(){var $el=$(this),sortable=$el.data("sortable");if(sortable||!(options instanceof Object)&&options||(sortable=new Sortable(this,options),$el.data("sortable",sortable)),sortable){if("widget"===options)return sortable;"destroy"===options?(sortable.destroy(),$el.removeData("sortable")):"function"==typeof sortable[options]?retVal=sortable[options].apply(sortable,[].slice.call(args,1)):options in sortable.options&&(retVal=sortable.option.apply(sortable,args))}}),void 0===retVal?this:retVal}}); \ No newline at end of file +! function(factory) { + "use strict"; + "function" == typeof define && define.amd ? define(["jquery"], factory) : factory(jQuery) +}(function($) { + "use strict"; + $.fn.sortable = function(options) { + var retVal, args = arguments; + return this.each(function() { + var $el = $(this), + sortable = $el.data("sortable"); + if (sortable || !(options instanceof Object) && options || (sortable = new Sortable(this, options), $el.data("sortable", sortable)), sortable) { + if ("widget" === options) return sortable; + "destroy" === options ? (sortable.destroy(), $el.removeData("sortable")) : "function" == typeof sortable[options] ? retVal = sortable[options].apply(sortable, [].slice.call(args, 1)) : options in sortable.options && (retVal = sortable.option.apply(sortable, args)) + } + }), void 0 === retVal ? this : retVal + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/Sortable/knockout-sortable.js b/dashboard-ui/bower_components/Sortable/knockout-sortable.js index 387aa64e67..75b23527f8 100644 --- a/dashboard-ui/bower_components/Sortable/knockout-sortable.js +++ b/dashboard-ui/bower_components/Sortable/knockout-sortable.js @@ -1 +1,97 @@ -!function(factory){"use strict";if("function"==typeof define&&define.amd)define(["knockout"],factory);else if("function"==typeof require&&"object"==typeof exports&&"object"==typeof module){var ko=require("knockout");factory(ko)}else factory(window.ko)}(function(ko){"use strict";var init=function(element,valueAccessor,allBindings,viewModel,bindingContext,sortableOptions){var options=buildOptions(valueAccessor,sortableOptions);["onStart","onEnd","onRemove","onAdd","onUpdate","onSort","onFilter"].forEach(function(e){(options[e]||eventHandlers[e])&&(options[e]=function(eventType,parentVM,parentBindings,handler,e){var itemVM=ko.dataFor(e.item),bindings=ko.utils.peekObservable(parentBindings()),bindingHandlerBinding=bindings.sortable||bindings.draggable,collection=bindingHandlerBinding.collection||bindingHandlerBinding.foreach;handler&&handler(e,itemVM,parentVM,collection,bindings),eventHandlers[eventType]&&eventHandlers[eventType](e,itemVM,parentVM,collection,bindings)}.bind(void 0,e,viewModel,allBindings,options[e]))});var sortableElement=Sortable.create(element,options);return ko.utils.domNodeDisposal.addDisposeCallback(element,function(){sortableElement.destroy()}),ko.bindingHandlers.template.init(element,valueAccessor)},update=function(element,valueAccessor,allBindings,viewModel,bindingContext,sortableOptions){return ko.bindingHandlers.template.update(element,valueAccessor,allBindings,viewModel,bindingContext)},eventHandlers=function(handlers){var moveOperations=[],tryMoveOperation=function(e,itemVM,parentVM,collection,parentBindings){var currentOperation={event:e,itemVM:itemVM,parentVM:parentVM,collection:collection,parentBindings:parentBindings},existingOperation=moveOperations.filter(function(op){return op.itemVM===currentOperation.itemVM})[0];if(existingOperation){moveOperations.splice(moveOperations.indexOf(existingOperation),1);var removeOperation="remove"===currentOperation.event.type?currentOperation:existingOperation,addOperation="add"===currentOperation.event.type?currentOperation:existingOperation;moveItem(itemVM,removeOperation.collection,addOperation.collection,addOperation.event.clone,addOperation.event)}else moveOperations.push(currentOperation)},moveItem=function(itemVM,from,to,clone,e){var fromArray=from(),originalIndex=fromArray.indexOf(itemVM),newIndex=e.newIndex;e.item.previousElementSibling&&(newIndex=fromArray.indexOf(ko.dataFor(e.item.previousElementSibling)),originalIndex>newIndex&&(newIndex+=1)),e.item.parentNode.removeChild(e.item),fromArray.splice(originalIndex,1),from.valueHasMutated(),clone&&from!==to&&(fromArray.splice(originalIndex,0,itemVM),from.valueHasMutated()),to().splice(newIndex,0,itemVM),to.valueHasMutated()};return handlers.onRemove=tryMoveOperation,handlers.onAdd=tryMoveOperation,handlers.onUpdate=function(e,itemVM,parentVM,collection,parentBindings){moveItem(itemVM,collection,collection,!1,e)},handlers}({}),buildOptions=function(bindingOptions,options){var merge=function(into,from){for(var prop in from)"[object Object]"===Object.prototype.toString.call(from[prop])?("[object Object]"!==Object.prototype.toString.call(into[prop])&&(into[prop]={}),into[prop]=merge(into[prop],from[prop])):into[prop]=from[prop];return into},unwrappedOptions=ko.utils.peekObservable(bindingOptions()).options||{};return options=merge({},options),unwrappedOptions.group&&"[object Object]"!==Object.prototype.toString.call(unwrappedOptions.group)&&(unwrappedOptions.group={name:unwrappedOptions.group}),merge(options,unwrappedOptions)};ko.bindingHandlers.draggable={sortableOptions:{group:{pull:"clone",put:!1},sort:!1},init:function(element,valueAccessor,allBindings,viewModel,bindingContext){return init(element,valueAccessor,allBindings,viewModel,0,ko.bindingHandlers.draggable.sortableOptions)},update:function(element,valueAccessor,allBindings,viewModel,bindingContext){return update(element,valueAccessor,allBindings,viewModel,bindingContext,ko.bindingHandlers.draggable.sortableOptions)}},ko.bindingHandlers.sortable={sortableOptions:{group:{pull:!0,put:!0}},init:function(element,valueAccessor,allBindings,viewModel,bindingContext){return init(element,valueAccessor,allBindings,viewModel,0,ko.bindingHandlers.sortable.sortableOptions)},update:function(element,valueAccessor,allBindings,viewModel,bindingContext){return update(element,valueAccessor,allBindings,viewModel,bindingContext,ko.bindingHandlers.sortable.sortableOptions)}}}); \ No newline at end of file +! function(factory) { + "use strict"; + if ("function" == typeof define && define.amd) define(["knockout"], factory); + else if ("function" == typeof require && "object" == typeof exports && "object" == typeof module) { + var ko = require("knockout"); + factory(ko) + } else factory(window.ko) +}(function(ko) { + "use strict"; + var init = function(element, valueAccessor, allBindings, viewModel, bindingContext, sortableOptions) { + var options = buildOptions(valueAccessor, sortableOptions); + ["onStart", "onEnd", "onRemove", "onAdd", "onUpdate", "onSort", "onFilter"].forEach(function(e) { + (options[e] || eventHandlers[e]) && (options[e] = function(eventType, parentVM, parentBindings, handler, e) { + var itemVM = ko.dataFor(e.item), + bindings = ko.utils.peekObservable(parentBindings()), + bindingHandlerBinding = bindings.sortable || bindings.draggable, + collection = bindingHandlerBinding.collection || bindingHandlerBinding.foreach; + handler && handler(e, itemVM, parentVM, collection, bindings), eventHandlers[eventType] && eventHandlers[eventType](e, itemVM, parentVM, collection, bindings) + }.bind(void 0, e, viewModel, allBindings, options[e])) + }); + var sortableElement = Sortable.create(element, options); + return ko.utils.domNodeDisposal.addDisposeCallback(element, function() { + sortableElement.destroy() + }), ko.bindingHandlers.template.init(element, valueAccessor) + }, + update = function(element, valueAccessor, allBindings, viewModel, bindingContext, sortableOptions) { + return ko.bindingHandlers.template.update(element, valueAccessor, allBindings, viewModel, bindingContext) + }, + eventHandlers = function(handlers) { + var moveOperations = [], + tryMoveOperation = function(e, itemVM, parentVM, collection, parentBindings) { + var currentOperation = { + event: e, + itemVM: itemVM, + parentVM: parentVM, + collection: collection, + parentBindings: parentBindings + }, + existingOperation = moveOperations.filter(function(op) { + return op.itemVM === currentOperation.itemVM + })[0]; + if (existingOperation) { + moveOperations.splice(moveOperations.indexOf(existingOperation), 1); + var removeOperation = "remove" === currentOperation.event.type ? currentOperation : existingOperation, + addOperation = "add" === currentOperation.event.type ? currentOperation : existingOperation; + moveItem(itemVM, removeOperation.collection, addOperation.collection, addOperation.event.clone, addOperation.event) + } else moveOperations.push(currentOperation) + }, + moveItem = function(itemVM, from, to, clone, e) { + var fromArray = from(), + originalIndex = fromArray.indexOf(itemVM), + newIndex = e.newIndex; + e.item.previousElementSibling && (newIndex = fromArray.indexOf(ko.dataFor(e.item.previousElementSibling)), originalIndex > newIndex && (newIndex += 1)), e.item.parentNode.removeChild(e.item), fromArray.splice(originalIndex, 1), from.valueHasMutated(), clone && from !== to && (fromArray.splice(originalIndex, 0, itemVM), from.valueHasMutated()), to().splice(newIndex, 0, itemVM), to.valueHasMutated() + }; + return handlers.onRemove = tryMoveOperation, handlers.onAdd = tryMoveOperation, handlers.onUpdate = function(e, itemVM, parentVM, collection, parentBindings) { + moveItem(itemVM, collection, collection, !1, e) + }, handlers + }({}), + buildOptions = function(bindingOptions, options) { + var merge = function(into, from) { + for (var prop in from) "[object Object]" === Object.prototype.toString.call(from[prop]) ? ("[object Object]" !== Object.prototype.toString.call(into[prop]) && (into[prop] = {}), into[prop] = merge(into[prop], from[prop])) : into[prop] = from[prop]; + return into + }, + unwrappedOptions = ko.utils.peekObservable(bindingOptions()).options || {}; + return options = merge({}, options), unwrappedOptions.group && "[object Object]" !== Object.prototype.toString.call(unwrappedOptions.group) && (unwrappedOptions.group = { + name: unwrappedOptions.group + }), merge(options, unwrappedOptions) + }; + ko.bindingHandlers.draggable = { + sortableOptions: { + group: { + pull: "clone", + put: !1 + }, + sort: !1 + }, + init: function(element, valueAccessor, allBindings, viewModel, bindingContext) { + return init(element, valueAccessor, allBindings, viewModel, 0, ko.bindingHandlers.draggable.sortableOptions) + }, + update: function(element, valueAccessor, allBindings, viewModel, bindingContext) { + return update(element, valueAccessor, allBindings, viewModel, bindingContext, ko.bindingHandlers.draggable.sortableOptions) + } + }, ko.bindingHandlers.sortable = { + sortableOptions: { + group: { + pull: !0, + put: !0 + } + }, + init: function(element, valueAccessor, allBindings, viewModel, bindingContext) { + return init(element, valueAccessor, allBindings, viewModel, 0, ko.bindingHandlers.sortable.sortableOptions) + }, + update: function(element, valueAccessor, allBindings, viewModel, bindingContext) { + return update(element, valueAccessor, allBindings, viewModel, bindingContext, ko.bindingHandlers.sortable.sortableOptions) + } + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/Sortable/ng-sortable.js b/dashboard-ui/bower_components/Sortable/ng-sortable.js index 47890a3b49..fe92b33453 100644 --- a/dashboard-ui/bower_components/Sortable/ng-sortable.js +++ b/dashboard-ui/bower_components/Sortable/ng-sortable.js @@ -1 +1,87 @@ -!function(factory){"use strict";"function"==typeof define&&define.amd?define(["angular","./Sortable"],factory):"function"==typeof require&&"object"==typeof exports&&"object"==typeof module?(require("angular"),factory(angular,require("./Sortable")),module.exports="ng-sortable"):window.angular&&window.Sortable&&factory(angular,Sortable)}(function(angular,Sortable){"use strict";var expando="Sortable:ng-sortable";angular.module("ng-sortable",[]).constant("ngSortableVersion","0.4.0").constant("ngSortableConfig",{}).directive("ngSortable",["$parse","ngSortableConfig",function($parse,ngSortableConfig){var removed,nextSibling,getSourceFactory=function(el,scope){var ngRepeat=[].filter.call(el.childNodes,function(node){return 8===node.nodeType&&-1!==node.nodeValue.indexOf("ngRepeat:")})[0];if(!ngRepeat)return function(){return null};ngRepeat=ngRepeat.nodeValue.match(/ngRepeat:\s*(?:\(.*?,\s*)?([^\s)]+)[\s)]+in\s+([^\s|]+)/);var itemsExpr=$parse(ngRepeat[2]);return function(){return itemsExpr(scope.$parent)||[]}};return{restrict:"AC",scope:{ngSortable:"=?"},link:function(scope,$el){function _emitEvent(evt,item){var name="on"+evt.type.charAt(0).toUpperCase()+evt.type.substr(1),source=getSource();options[name]&&options[name]({model:item||source[evt.newIndex],models:source,oldIndex:evt.oldIndex,newIndex:evt.newIndex})}function _sync(evt){var items=getSource();if(items){var oldIndex=evt.oldIndex,newIndex=evt.newIndex;if(el!==evt.from){var prevItems=evt.from[expando]();removed=prevItems[oldIndex],evt.clone?(removed=angular.copy(removed),prevItems.splice(Sortable.utils.index(evt.clone),0,prevItems.splice(oldIndex,1)[0]),evt.from.removeChild(evt.clone)):prevItems.splice(oldIndex,1),items.splice(newIndex,0,removed),evt.from.insertBefore(evt.item,nextSibling)}else items.splice(newIndex,0,items.splice(oldIndex,1)[0]);scope.$apply()}}var sortable,el=$el[0],options=angular.extend(scope.ngSortable||{},ngSortableConfig),watchers=[],getSource=getSourceFactory(el,scope);el[expando]=getSource,sortable=Sortable.create(el,Object.keys(options).reduce(function(opts,name){return opts[name]=opts[name]||options[name],opts},{onStart:function(evt){nextSibling=evt.item.nextSibling,_emitEvent(evt),scope.$apply()},onEnd:function(evt){_emitEvent(evt,removed),scope.$apply()},onAdd:function(evt){_sync(evt),_emitEvent(evt,removed),scope.$apply()},onUpdate:function(evt){_sync(evt),_emitEvent(evt)},onRemove:function(evt){_emitEvent(evt,removed)},onSort:function(evt){_emitEvent(evt)}})),$el.on("$destroy",function(){angular.forEach(watchers,function(unwatch){unwatch()}),sortable.destroy(),el[expando]=null,el=null,watchers=null,sortable=null,nextSibling=null}),angular.forEach(["sort","disabled","draggable","handle","animation","group","ghostClass","filter","onStart","onEnd","onAdd","onUpdate","onRemove","onSort"],function(name){watchers.push(scope.$watch("ngSortable."+name,function(value){void 0!==value&&(options[name]=value,/^on[A-Z]/.test(name)||sortable.option(name,value))}))})}}}])}); \ No newline at end of file +! function(factory) { + "use strict"; + "function" == typeof define && define.amd ? define(["angular", "./Sortable"], factory) : "function" == typeof require && "object" == typeof exports && "object" == typeof module ? (require("angular"), factory(angular, require("./Sortable")), module.exports = "ng-sortable") : window.angular && window.Sortable && factory(angular, Sortable) +}(function(angular, Sortable) { + "use strict"; + var expando = "Sortable:ng-sortable"; + angular.module("ng-sortable", []).constant("ngSortableVersion", "0.4.0").constant("ngSortableConfig", {}).directive("ngSortable", ["$parse", "ngSortableConfig", function($parse, ngSortableConfig) { + var removed, nextSibling, getSourceFactory = function(el, scope) { + var ngRepeat = [].filter.call(el.childNodes, function(node) { + return 8 === node.nodeType && -1 !== node.nodeValue.indexOf("ngRepeat:") + })[0]; + if (!ngRepeat) return function() { + return null + }; + ngRepeat = ngRepeat.nodeValue.match(/ngRepeat:\s*(?:\(.*?,\s*)?([^\s)]+)[\s)]+in\s+([^\s|]+)/); + var itemsExpr = $parse(ngRepeat[2]); + return function() { + return itemsExpr(scope.$parent) || [] + } + }; + return { + restrict: "AC", + scope: { + ngSortable: "=?" + }, + link: function(scope, $el) { + function _emitEvent(evt, item) { + var name = "on" + evt.type.charAt(0).toUpperCase() + evt.type.substr(1), + source = getSource(); + options[name] && options[name]({ + model: item || source[evt.newIndex], + models: source, + oldIndex: evt.oldIndex, + newIndex: evt.newIndex + }) + } + + function _sync(evt) { + var items = getSource(); + if (items) { + var oldIndex = evt.oldIndex, + newIndex = evt.newIndex; + if (el !== evt.from) { + var prevItems = evt.from[expando](); + removed = prevItems[oldIndex], evt.clone ? (removed = angular.copy(removed), prevItems.splice(Sortable.utils.index(evt.clone), 0, prevItems.splice(oldIndex, 1)[0]), evt.from.removeChild(evt.clone)) : prevItems.splice(oldIndex, 1), items.splice(newIndex, 0, removed), evt.from.insertBefore(evt.item, nextSibling) + } else items.splice(newIndex, 0, items.splice(oldIndex, 1)[0]); + scope.$apply() + } + } + var sortable, el = $el[0], + options = angular.extend(scope.ngSortable || {}, ngSortableConfig), + watchers = [], + getSource = getSourceFactory(el, scope); + el[expando] = getSource, sortable = Sortable.create(el, Object.keys(options).reduce(function(opts, name) { + return opts[name] = opts[name] || options[name], opts + }, { + onStart: function(evt) { + nextSibling = evt.item.nextSibling, _emitEvent(evt), scope.$apply() + }, + onEnd: function(evt) { + _emitEvent(evt, removed), scope.$apply() + }, + onAdd: function(evt) { + _sync(evt), _emitEvent(evt, removed), scope.$apply() + }, + onUpdate: function(evt) { + _sync(evt), _emitEvent(evt) + }, + onRemove: function(evt) { + _emitEvent(evt, removed) + }, + onSort: function(evt) { + _emitEvent(evt) + } + })), $el.on("$destroy", function() { + angular.forEach(watchers, function(unwatch) { + unwatch() + }), sortable.destroy(), el[expando] = null, el = null, watchers = null, sortable = null, nextSibling = null + }), angular.forEach(["sort", "disabled", "draggable", "handle", "animation", "group", "ghostClass", "filter", "onStart", "onEnd", "onAdd", "onUpdate", "onRemove", "onSort"], function(name) { + watchers.push(scope.$watch("ngSortable." + name, function(value) { + void 0 !== value && (options[name] = value, /^on[A-Z]/.test(name) || sortable.option(name, value)) + })) + }) + } + } + }]) +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/Sortable/react-sortable-mixin.js b/dashboard-ui/bower_components/Sortable/react-sortable-mixin.js index ec578ed833..27c20c1f05 100644 --- a/dashboard-ui/bower_components/Sortable/react-sortable-mixin.js +++ b/dashboard-ui/bower_components/Sortable/react-sortable-mixin.js @@ -1 +1,71 @@ -!function(factory){"use strict";"undefined"!=typeof module&&void 0!==module.exports?module.exports=factory(require("./Sortable")):"function"==typeof define&&define.amd?define(["./Sortable"],factory):window.SortableMixin=factory(Sortable)}(function(Sortable){"use strict";function _getModelName(component){return component.sortableOptions&&component.sortableOptions.model||_defaultOptions.model}function _getModelItems(component){var name=_getModelName(component);return(component.state&&component.state[name]||component.props[name]).slice()}function _extend(dst,src){for(var key in src)src.hasOwnProperty(key)&&(dst[key]=src[key]);return dst}var _nextSibling,_activeComponent,_defaultOptions={ref:"list",model:"items",animation:100,onStart:"handleStart",onEnd:"handleEnd",onAdd:"handleAdd",onUpdate:"handleUpdate",onRemove:"handleRemove",onSort:"handleSort",onFilter:"handleFilter",onMove:"handleMove"};return{sortableMixinVersion:"0.1.1",_sortableInstance:null,componentDidMount:function(){var DOMNode,options=_extend(_extend({},_defaultOptions),this.sortableOptions||{}),copyOptions=_extend({},options),emitEvent=function(type,evt){var method=this[options[type]];method&&method.call(this,evt,this._sortableInstance)}.bind(this);"onStart onEnd onAdd onSort onUpdate onRemove onFilter onMove".split(" ").forEach(function(name){copyOptions[name]=function(evt){if("onStart"===name)_nextSibling=evt.item.nextElementSibling,_activeComponent=this;else if("onAdd"===name||"onUpdate"===name){evt.from.insertBefore(evt.item,_nextSibling);var remoteItems,item,newState={},remoteState={},oldIndex=evt.oldIndex,newIndex=evt.newIndex,items=_getModelItems(this);"onAdd"===name?(remoteItems=_getModelItems(_activeComponent),item=remoteItems.splice(oldIndex,1)[0],items.splice(newIndex,0,item),remoteState[_getModelName(_activeComponent)]=remoteItems):items.splice(newIndex,0,items.splice(oldIndex,1)[0]),newState[_getModelName(this)]=items,copyOptions.stateHandler?this[copyOptions.stateHandler](newState):this.setState(newState),this!==_activeComponent&&_activeComponent.setState(remoteState)}setTimeout(function(){emitEvent(name,evt)},0)}.bind(this)},this),DOMNode=this.getDOMNode()?(this.refs[options.ref]||this).getDOMNode():this.refs[options.ref]||this,this._sortableInstance=Sortable.create(DOMNode,copyOptions)},componentWillReceiveProps:function(nextProps){var newState={},modelName=_getModelName(this),items=nextProps[modelName];items&&(newState[modelName]=items,this.setState(newState))},componentWillUnmount:function(){this._sortableInstance.destroy(),this._sortableInstance=null}}}); \ No newline at end of file +! function(factory) { + "use strict"; + "undefined" != typeof module && void 0 !== module.exports ? module.exports = factory(require("./Sortable")) : "function" == typeof define && define.amd ? define(["./Sortable"], factory) : window.SortableMixin = factory(Sortable) +}(function(Sortable) { + "use strict"; + + function _getModelName(component) { + return component.sortableOptions && component.sortableOptions.model || _defaultOptions.model + } + + function _getModelItems(component) { + var name = _getModelName(component); + return (component.state && component.state[name] || component.props[name]).slice() + } + + function _extend(dst, src) { + for (var key in src) src.hasOwnProperty(key) && (dst[key] = src[key]); + return dst + } + var _nextSibling, _activeComponent, _defaultOptions = { + ref: "list", + model: "items", + animation: 100, + onStart: "handleStart", + onEnd: "handleEnd", + onAdd: "handleAdd", + onUpdate: "handleUpdate", + onRemove: "handleRemove", + onSort: "handleSort", + onFilter: "handleFilter", + onMove: "handleMove" + }; + return { + sortableMixinVersion: "0.1.1", + _sortableInstance: null, + componentDidMount: function() { + var DOMNode, options = _extend(_extend({}, _defaultOptions), this.sortableOptions || {}), + copyOptions = _extend({}, options), + emitEvent = function(type, evt) { + var method = this[options[type]]; + method && method.call(this, evt, this._sortableInstance) + }.bind(this); + "onStart onEnd onAdd onSort onUpdate onRemove onFilter onMove".split(" ").forEach(function(name) { + copyOptions[name] = function(evt) { + if ("onStart" === name) _nextSibling = evt.item.nextElementSibling, _activeComponent = this; + else if ("onAdd" === name || "onUpdate" === name) { + evt.from.insertBefore(evt.item, _nextSibling); + var remoteItems, item, newState = {}, + remoteState = {}, + oldIndex = evt.oldIndex, + newIndex = evt.newIndex, + items = _getModelItems(this); + "onAdd" === name ? (remoteItems = _getModelItems(_activeComponent), item = remoteItems.splice(oldIndex, 1)[0], items.splice(newIndex, 0, item), remoteState[_getModelName(_activeComponent)] = remoteItems) : items.splice(newIndex, 0, items.splice(oldIndex, 1)[0]), newState[_getModelName(this)] = items, copyOptions.stateHandler ? this[copyOptions.stateHandler](newState) : this.setState(newState), this !== _activeComponent && _activeComponent.setState(remoteState) + } + setTimeout(function() { + emitEvent(name, evt) + }, 0) + }.bind(this) + }, this), DOMNode = this.getDOMNode() ? (this.refs[options.ref] || this).getDOMNode() : this.refs[options.ref] || this, this._sortableInstance = Sortable.create(DOMNode, copyOptions) + }, + componentWillReceiveProps: function(nextProps) { + var newState = {}, + modelName = _getModelName(this), + items = nextProps[modelName]; + items && (newState[modelName] = items, this.setState(newState)) + }, + componentWillUnmount: function() { + this._sortableInstance.destroy(), this._sortableInstance = null + } + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/Swiper/dist/js/swiper.min.js b/dashboard-ui/bower_components/Swiper/dist/js/swiper.min.js index 678fba43ad..7e1956e15a 100644 --- a/dashboard-ui/bower_components/Swiper/dist/js/swiper.min.js +++ b/dashboard-ui/bower_components/Swiper/dist/js/swiper.min.js @@ -12,7 +12,1595 @@ * * Released on: February 7, 2016 */ -!function(){"use strict";function e(e){e.fn.swiper=function(a){var r;return e(this).each(function(){var e=new t(this,a);r||(r=e)}),r}}var a,t=function(e,i){function s(e){return Math.floor(e)}function n(){b.autoplayTimeoutId=setTimeout(function(){b.params.loop?(b.fixLoop(),b._slideNext(),b.emit("onAutoplay",b)):b.isEnd?i.autoplayStopOnLast?b.stopAutoplay():(b._slideTo(0),b.emit("onAutoplay",b)):(b._slideNext(),b.emit("onAutoplay",b))},b.params.autoplay)}function o(e,t){var r=a(e.target);if(!r.is(t))if("string"==typeof t)r=r.parents(t);else if(t.nodeType){var i;return r.parents().each(function(e,a){a===t&&(i=t)}),i?t:void 0}if(0!==r.length)return r[0]}function l(e,a){a=a||{};var t=window.MutationObserver||window.WebkitMutationObserver,r=new t(function(e){e.forEach(function(e){b.onResize(!0),b.emit("onObserverUpdate",b,e)})});r.observe(e,{attributes:"undefined"==typeof a.attributes?!0:a.attributes,childList:"undefined"==typeof a.childList?!0:a.childList,characterData:"undefined"==typeof a.characterData?!0:a.characterData}),b.observers.push(r)}function p(e){e.originalEvent&&(e=e.originalEvent);var a=e.keyCode||e.charCode;if(!b.params.allowSwipeToNext&&(b.isHorizontal()&&39===a||!b.isHorizontal()&&40===a))return!1;if(!b.params.allowSwipeToPrev&&(b.isHorizontal()&&37===a||!b.isHorizontal()&&38===a))return!1;if(!(e.shiftKey||e.altKey||e.ctrlKey||e.metaKey||document.activeElement&&document.activeElement.nodeName&&("input"===document.activeElement.nodeName.toLowerCase()||"textarea"===document.activeElement.nodeName.toLowerCase()))){if(37===a||39===a||38===a||40===a){var t=!1;if(b.container.parents(".swiper-slide").length>0&&0===b.container.parents(".swiper-slide-active").length)return;var r={left:window.pageXOffset,top:window.pageYOffset},i=window.innerWidth,s=window.innerHeight,n=b.container.offset();b.rtl&&(n.left=n.left-b.container[0].scrollLeft);for(var o=[[n.left,n.top],[n.left+b.width,n.top],[n.left,n.top+b.height],[n.left+b.width,n.top+b.height]],l=0;l=r.left&&p[0]<=r.left+i&&p[1]>=r.top&&p[1]<=r.top+s&&(t=!0)}if(!t)return}b.isHorizontal()?((37===a||39===a)&&(e.preventDefault?e.preventDefault():e.returnValue=!1),(39===a&&!b.rtl||37===a&&b.rtl)&&b.slideNext(),(37===a&&!b.rtl||39===a&&b.rtl)&&b.slidePrev()):((38===a||40===a)&&(e.preventDefault?e.preventDefault():e.returnValue=!1),40===a&&b.slideNext(),38===a&&b.slidePrev())}}function d(e){e.originalEvent&&(e=e.originalEvent);var a=b.mousewheel.event,t=0,r=b.rtl?-1:1;if("mousewheel"===a)if(b.params.mousewheelForceToAxis)if(b.isHorizontal()){if(!(Math.abs(e.wheelDeltaX)>Math.abs(e.wheelDeltaY)))return;t=e.wheelDeltaX*r}else{if(!(Math.abs(e.wheelDeltaY)>Math.abs(e.wheelDeltaX)))return;t=e.wheelDeltaY}else t=Math.abs(e.wheelDeltaX)>Math.abs(e.wheelDeltaY)?-e.wheelDeltaX*r:-e.wheelDeltaY;else if("DOMMouseScroll"===a)t=-e.detail;else if("wheel"===a)if(b.params.mousewheelForceToAxis)if(b.isHorizontal()){if(!(Math.abs(e.deltaX)>Math.abs(e.deltaY)))return;t=-e.deltaX*r}else{if(!(Math.abs(e.deltaY)>Math.abs(e.deltaX)))return;t=-e.deltaY}else t=Math.abs(e.deltaX)>Math.abs(e.deltaY)?-e.deltaX*r:-e.deltaY;if(0!==t){if(b.params.mousewheelInvert&&(t=-t),b.params.freeMode){var i=b.getWrapperTranslate()+t*b.params.mousewheelSensitivity,s=b.isBeginning,n=b.isEnd;if(i>=b.minTranslate()&&(i=b.minTranslate()),i<=b.maxTranslate()&&(i=b.maxTranslate()),b.setWrapperTransition(0),b.setWrapperTranslate(i),b.updateProgress(),b.updateActiveIndex(),(!s&&b.isBeginning||!n&&b.isEnd)&&b.updateClasses(),b.params.freeModeSticky?(clearTimeout(b.mousewheel.timeout),b.mousewheel.timeout=setTimeout(function(){b.slideReset()},300)):b.params.lazyLoading&&b.lazy&&b.lazy.load(),0===i||i===b.maxTranslate())return}else{if((new window.Date).getTime()-b.mousewheel.lastScrollTime>60)if(0>t)if(b.isEnd&&!b.params.loop||b.animating){if(b.params.mousewheelReleaseOnEdges)return!0}else b.slideNext();else if(b.isBeginning&&!b.params.loop||b.animating){if(b.params.mousewheelReleaseOnEdges)return!0}else b.slidePrev();b.mousewheel.lastScrollTime=(new window.Date).getTime()}return b.params.autoplay&&b.stopAutoplay(),e.preventDefault?e.preventDefault():e.returnValue=!1,!1}}function u(e,t){e=a(e);var r,i,s,n=b.rtl?-1:1;r=e.attr("data-swiper-parallax")||"0",i=e.attr("data-swiper-parallax-x"),s=e.attr("data-swiper-parallax-y"),i||s?(i=i||"0",s=s||"0"):b.isHorizontal()?(i=r,s="0"):(s=r,i="0"),i=i.indexOf("%")>=0?parseInt(i,10)*t*n+"%":i*t*n+"px",s=s.indexOf("%")>=0?parseInt(s,10)*t+"%":s*t+"px",e.transform("translate3d("+i+", "+s+",0px)")}function c(e){return 0!==e.indexOf("on")&&(e=e[0]!==e[0].toUpperCase()?"on"+e[0].toUpperCase()+e.substring(1):"on"+e),e}if(!(this instanceof t))return new t(e,i);var m={direction:"horizontal",touchEventsTarget:"container",initialSlide:0,speed:300,autoplay:!1,autoplayDisableOnInteraction:!0,autoplayStopOnLast:!1,iOSEdgeSwipeDetection:!1,iOSEdgeSwipeThreshold:20,freeMode:!1,freeModeMomentum:!0,freeModeMomentumRatio:1,freeModeMomentumBounce:!0,freeModeMomentumBounceRatio:1,freeModeSticky:!1,freeModeMinimumVelocity:.02,autoHeight:!1,setWrapperSize:!1,virtualTranslate:!1,effect:"slide",coverflow:{rotate:50,stretch:0,depth:100,modifier:1,slideShadows:!0},flip:{slideShadows:!0,limitRotation:!0},cube:{slideShadows:!0,shadow:!0,shadowOffset:20,shadowScale:.94},fade:{crossFade:!1},parallax:!1,scrollbar:null,scrollbarHide:!0,scrollbarDraggable:!1,scrollbarSnapOnRelease:!1,keyboardControl:!1,mousewheelControl:!1,mousewheelReleaseOnEdges:!1,mousewheelInvert:!1,mousewheelForceToAxis:!1,mousewheelSensitivity:1,hashnav:!1,breakpoints:void 0,spaceBetween:0,slidesPerView:1,slidesPerColumn:1,slidesPerColumnFill:"column",slidesPerGroup:1,centeredSlides:!1,slidesOffsetBefore:0,slidesOffsetAfter:0,roundLengths:!1,touchRatio:1,touchAngle:45,simulateTouch:!0,shortSwipes:!0,longSwipes:!0,longSwipesRatio:.5,longSwipesMs:300,followFinger:!0,onlyExternal:!1,threshold:0,touchMoveStopPropagation:!0,uniqueNavElements:!0,pagination:null,paginationElement:"span",paginationClickable:!1,paginationHide:!1,paginationBulletRender:null,paginationProgressRender:null,paginationFractionRender:null,paginationCustomRender:null,paginationType:"bullets",resistance:!0,resistanceRatio:.85,nextButton:null,prevButton:null,watchSlidesProgress:!1,watchSlidesVisibility:!1,grabCursor:!1,preventClicks:!0,preventClicksPropagation:!0,slideToClickedSlide:!1,lazyLoading:!1,lazyLoadingInPrevNext:!1,lazyLoadingInPrevNextAmount:1,lazyLoadingOnTransitionStart:!1,preloadImages:!0,updateOnImagesReady:!0,loop:!1,loopAdditionalSlides:0,loopedSlides:null,control:void 0,controlInverse:!1,controlBy:"slide",allowSwipeToPrev:!0,allowSwipeToNext:!0,swipeHandler:null,noSwiping:!0,noSwipingClass:"swiper-no-swiping",slideClass:"swiper-slide",slideActiveClass:"swiper-slide-active",slideVisibleClass:"swiper-slide-visible",slideDuplicateClass:"swiper-slide-duplicate",slideNextClass:"swiper-slide-next",slidePrevClass:"swiper-slide-prev",wrapperClass:"swiper-wrapper",bulletClass:"swiper-pagination-bullet",bulletActiveClass:"swiper-pagination-bullet-active",buttonDisabledClass:"swiper-button-disabled",paginationCurrentClass:"swiper-pagination-current",paginationTotalClass:"swiper-pagination-total",paginationHiddenClass:"swiper-pagination-hidden",paginationProgressbarClass:"swiper-pagination-progressbar",observer:!1,observeParents:!1,a11y:!1,prevSlideMessage:"Previous slide",nextSlideMessage:"Next slide",firstSlideMessage:"This is the first slide",lastSlideMessage:"This is the last slide",paginationBulletMessage:"Go to slide {{index}}",runCallbacksOnInit:!0},h=i&&i.virtualTranslate;i=i||{};var f={};for(var g in i)if("object"!=typeof i[g]||null===i[g]||(i[g].nodeType||i[g]===window||i[g]===document||"undefined"!=typeof r&&i[g]instanceof r||"undefined"!=typeof jQuery&&i[g]instanceof jQuery))f[g]=i[g];else{f[g]={};for(var v in i[g])f[g][v]=i[g][v]}for(var w in m)if("undefined"==typeof i[w])i[w]=m[w];else if("object"==typeof i[w])for(var y in m[w])"undefined"==typeof i[w][y]&&(i[w][y]=m[w][y]);var b=this;if(b.params=i,b.originalParams=f,b.classNames=[],"undefined"!=typeof a&&"undefined"!=typeof r&&(a=r),("undefined"!=typeof a||(a="undefined"==typeof r?window.Dom7||window.Zepto||window.jQuery:r))&&(b.$=a,b.currentBreakpoint=void 0,b.getActiveBreakpoint=function(){if(!b.params.breakpoints)return!1;var e,a=!1,t=[];for(e in b.params.breakpoints)b.params.breakpoints.hasOwnProperty(e)&&t.push(e);t.sort(function(e,a){return parseInt(e,10)>parseInt(a,10)});for(var r=0;r=window.innerWidth&&!a&&(a=e);return a||"max"},b.setBreakpoint=function(){var e=b.getActiveBreakpoint();if(e&&b.currentBreakpoint!==e){var a=e in b.params.breakpoints?b.params.breakpoints[e]:b.originalParams,t=b.params.loop&&a.slidesPerView!==b.params.slidesPerView;for(var r in a)b.params[r]=a[r];b.currentBreakpoint=e,t&&b.destroyLoop&&b.reLoop(!0)}},b.params.breakpoints&&b.setBreakpoint(),b.container=a(e),0!==b.container.length)){if(b.container.length>1){var x=[];return b.container.each(function(){x.push(new t(this,i))}),x}b.container[0].swiper=b,b.container.data("swiper",b),b.classNames.push("swiper-container-"+b.params.direction),b.params.freeMode&&b.classNames.push("swiper-container-free-mode"),b.support.flexbox||(b.classNames.push("swiper-container-no-flexbox"),b.params.slidesPerColumn=1),b.params.autoHeight&&b.classNames.push("swiper-container-autoheight"),(b.params.parallax||b.params.watchSlidesVisibility)&&(b.params.watchSlidesProgress=!0),["cube","coverflow","flip"].indexOf(b.params.effect)>=0&&(b.support.transforms3d?(b.params.watchSlidesProgress=!0,b.classNames.push("swiper-container-3d")):b.params.effect="slide"),"slide"!==b.params.effect&&b.classNames.push("swiper-container-"+b.params.effect),"cube"===b.params.effect&&(b.params.resistanceRatio=0,b.params.slidesPerView=1,b.params.slidesPerColumn=1,b.params.slidesPerGroup=1,b.params.centeredSlides=!1,b.params.spaceBetween=0,b.params.virtualTranslate=!0,b.params.setWrapperSize=!1),("fade"===b.params.effect||"flip"===b.params.effect)&&(b.params.slidesPerView=1,b.params.slidesPerColumn=1,b.params.slidesPerGroup=1,b.params.watchSlidesProgress=!0,b.params.spaceBetween=0,b.params.setWrapperSize=!1,"undefined"==typeof h&&(b.params.virtualTranslate=!0)),b.params.grabCursor&&b.support.touch&&(b.params.grabCursor=!1),b.wrapper=b.container.children("."+b.params.wrapperClass),b.params.pagination&&(b.paginationContainer=a(b.params.pagination),b.params.uniqueNavElements&&"string"==typeof b.params.pagination&&b.paginationContainer.length>1&&1===b.container.find(b.params.pagination).length&&(b.paginationContainer=b.container.find(b.params.pagination)),"bullets"===b.params.paginationType&&b.params.paginationClickable?b.paginationContainer.addClass("swiper-pagination-clickable"):b.params.paginationClickable=!1,b.paginationContainer.addClass("swiper-pagination-"+b.params.paginationType)),(b.params.nextButton||b.params.prevButton)&&(b.params.nextButton&&(b.nextButton=a(b.params.nextButton),b.params.uniqueNavElements&&"string"==typeof b.params.nextButton&&b.nextButton.length>1&&1===b.container.find(b.params.nextButton).length&&(b.nextButton=b.container.find(b.params.nextButton))),b.params.prevButton&&(b.prevButton=a(b.params.prevButton),b.params.uniqueNavElements&&"string"==typeof b.params.prevButton&&b.prevButton.length>1&&1===b.container.find(b.params.prevButton).length&&(b.prevButton=b.container.find(b.params.prevButton)))),b.isHorizontal=function(){return"horizontal"===b.params.direction},b.rtl=b.isHorizontal()&&("rtl"===b.container[0].dir.toLowerCase()||"rtl"===b.container.css("direction")),b.rtl&&b.classNames.push("swiper-container-rtl"),b.rtl&&(b.wrongRTL="-webkit-box"===b.wrapper.css("display")),b.params.slidesPerColumn>1&&b.classNames.push("swiper-container-multirow"),b.device.android&&b.classNames.push("swiper-container-android"),b.container.addClass(b.classNames.join(" ")),b.translate=0,b.progress=0,b.velocity=0,b.lockSwipeToNext=function(){b.params.allowSwipeToNext=!1},b.lockSwipeToPrev=function(){b.params.allowSwipeToPrev=!1},b.lockSwipes=function(){b.params.allowSwipeToNext=b.params.allowSwipeToPrev=!1},b.unlockSwipeToNext=function(){b.params.allowSwipeToNext=!0},b.unlockSwipeToPrev=function(){b.params.allowSwipeToPrev=!0},b.unlockSwipes=function(){b.params.allowSwipeToNext=b.params.allowSwipeToPrev=!0},b.params.grabCursor&&(b.container[0].style.cursor="move",b.container[0].style.cursor="-webkit-grab",b.container[0].style.cursor="-moz-grab",b.container[0].style.cursor="grab"),b.imagesToLoad=[],b.imagesLoaded=0,b.loadImage=function(e,a,t,r,i){function s(){i&&i()}var n;e.complete&&r?s():a?(n=new window.Image,n.onload=s,n.onerror=s,t&&(n.srcset=t),a&&(n.src=a)):s()},b.preloadImages=function(){function e(){"undefined"!=typeof b&&null!==b&&(void 0!==b.imagesLoaded&&b.imagesLoaded++,b.imagesLoaded===b.imagesToLoad.length&&(b.params.updateOnImagesReady&&b.update(),b.emit("onImagesReady",b)))}b.imagesToLoad=b.container.find("img");for(var a=0;a=0&&(a=parseFloat(a.replace("%",""))/100*b.size),b.virtualSize=-a,b.rtl?b.slides.css({marginLeft:"",marginTop:""}):b.slides.css({marginRight:"",marginBottom:""});var n;b.params.slidesPerColumn>1&&(n=Math.floor(b.slides.length/b.params.slidesPerColumn)===b.slides.length/b.params.slidesPerColumn?b.slides.length:Math.ceil(b.slides.length/b.params.slidesPerColumn)*b.params.slidesPerColumn,"auto"!==b.params.slidesPerView&&"row"===b.params.slidesPerColumnFill&&(n=Math.max(n,b.params.slidesPerView*b.params.slidesPerColumn)));var o,l=b.params.slidesPerColumn,p=n/l,d=p-(b.params.slidesPerColumn*p-b.slides.length);for(e=0;e1){var c,m,h;"column"===b.params.slidesPerColumnFill?(m=Math.floor(e/l),h=e-m*l,(m>d||m===d&&h===l-1)&&++h>=l&&(h=0,m++),c=m+h*n/l,u.css({"-webkit-box-ordinal-group":c,"-moz-box-ordinal-group":c,"-ms-flex-order":c,"-webkit-order":c,order:c})):(h=Math.floor(e/p),m=e-h*p),u.css({"margin-top":0!==h&&b.params.spaceBetween&&b.params.spaceBetween+"px"}).attr("data-swiper-column",m).attr("data-swiper-row",h)}"none"!==u.css("display")&&("auto"===b.params.slidesPerView?(o=b.isHorizontal()?u.outerWidth(!0):u.outerHeight(!0),b.params.roundLengths&&(o=s(o))):(o=(b.size-(b.params.slidesPerView-1)*a)/b.params.slidesPerView,b.params.roundLengths&&(o=s(o)),b.isHorizontal()?b.slides[e].style.width=o+"px":b.slides[e].style.height=o+"px"),b.slides[e].swiperSlideSize=o,b.slidesSizesGrid.push(o),b.params.centeredSlides?(t=t+o/2+r/2+a,0===e&&(t=t-b.size/2-a),Math.abs(t)<.001&&(t=0),i%b.params.slidesPerGroup===0&&b.snapGrid.push(t),b.slidesGrid.push(t)):(i%b.params.slidesPerGroup===0&&b.snapGrid.push(t),b.slidesGrid.push(t),t=t+o+a),b.virtualSize+=o+a,r=o,i++)}b.virtualSize=Math.max(b.virtualSize,b.size)+b.params.slidesOffsetAfter;var f;if(b.rtl&&b.wrongRTL&&("slide"===b.params.effect||"coverflow"===b.params.effect)&&b.wrapper.css({width:b.virtualSize+b.params.spaceBetween+"px"}),(!b.support.flexbox||b.params.setWrapperSize)&&(b.isHorizontal()?b.wrapper.css({width:b.virtualSize+b.params.spaceBetween+"px"}):b.wrapper.css({height:b.virtualSize+b.params.spaceBetween+"px"})),b.params.slidesPerColumn>1&&(b.virtualSize=(o+b.params.spaceBetween)*n,b.virtualSize=Math.ceil(b.virtualSize/b.params.slidesPerColumn)-b.params.spaceBetween,b.wrapper.css({width:b.virtualSize+b.params.spaceBetween+"px"}),b.params.centeredSlides)){for(f=[],e=0;e1&&b.snapGrid.push(b.virtualSize-b.size)}0===b.snapGrid.length&&(b.snapGrid=[0]),0!==b.params.spaceBetween&&(b.isHorizontal()?b.rtl?b.slides.css({marginLeft:a+"px"}):b.slides.css({marginRight:a+"px"}):b.slides.css({marginBottom:a+"px"})),b.params.watchSlidesProgress&&b.updateSlidesOffset()}},b.updateSlidesOffset=function(){for(var e=0;e=0&&s0&&n<=b.size||0>=s&&n>=b.size;o&&b.slides.eq(t).addClass(b.params.slideVisibleClass)}r.progress=b.rtl?-i:i}}},b.updateProgress=function(e){"undefined"==typeof e&&(e=b.translate||0);var a=b.maxTranslate()-b.minTranslate(),t=b.isBeginning,r=b.isEnd;0===a?(b.progress=0,b.isBeginning=b.isEnd=!0):(b.progress=(e-b.minTranslate())/a,b.isBeginning=b.progress<=0,b.isEnd=b.progress>=1),b.isBeginning&&!t&&b.emit("onReachBeginning",b),b.isEnd&&!r&&b.emit("onReachEnd",b),b.params.watchSlidesProgress&&b.updateSlidesProgress(e),b.emit("onProgress",b,b.progress)},b.updateActiveIndex=function(){var e,a,t,r=b.rtl?b.translate:-b.translate;for(a=0;a=b.slidesGrid[a]&&r=b.slidesGrid[a]&&r=b.slidesGrid[a]&&(e=a);(0>e||"undefined"==typeof e)&&(e=0),t=Math.floor(e/b.params.slidesPerGroup),t>=b.snapGrid.length&&(t=b.snapGrid.length-1),e!==b.activeIndex&&(b.snapIndex=t,b.previousIndex=b.activeIndex,b.activeIndex=e,b.updateClasses())},b.updateClasses=function(){b.slides.removeClass(b.params.slideActiveClass+" "+b.params.slideNextClass+" "+b.params.slidePrevClass);var e=b.slides.eq(b.activeIndex);e.addClass(b.params.slideActiveClass);var t=e.next("."+b.params.slideClass).addClass(b.params.slideNextClass);b.params.loop&&0===t.length&&b.slides.eq(0).addClass(b.params.slideNextClass);var r=e.prev("."+b.params.slideClass).addClass(b.params.slidePrevClass);if(b.params.loop&&0===r.length&&b.slides.eq(-1).addClass(b.params.slidePrevClass),b.paginationContainer&&b.paginationContainer.length>0){var i,s=b.params.loop?Math.ceil((b.slides.length-2*b.loopedSlides)/b.params.slidesPerGroup):b.snapGrid.length;if(b.params.loop?(i=Math.ceil((b.activeIndex-b.loopedSlides)/b.params.slidesPerGroup),i>b.slides.length-1-2*b.loopedSlides&&(i-=b.slides.length-2*b.loopedSlides),i>s-1&&(i-=s),0>i&&"bullets"!==b.params.paginationType&&(i=s+i)):i="undefined"!=typeof b.snapIndex?b.snapIndex:b.activeIndex||0,"bullets"===b.params.paginationType&&b.bullets&&b.bullets.length>0&&(b.bullets.removeClass(b.params.bulletActiveClass),b.paginationContainer.length>1?b.bullets.each(function(){a(this).index()===i&&a(this).addClass(b.params.bulletActiveClass)}):b.bullets.eq(i).addClass(b.params.bulletActiveClass)),"fraction"===b.params.paginationType&&(b.paginationContainer.find("."+b.params.paginationCurrentClass).text(i+1),b.paginationContainer.find("."+b.params.paginationTotalClass).text(s)),"progress"===b.params.paginationType){var n=(i+1)/s,o=n,l=1;b.isHorizontal()||(l=n,o=1),b.paginationContainer.find("."+b.params.paginationProgressbarClass).transform("translate3d(0,0,0) scaleX("+o+") scaleY("+l+")").transition(b.params.speed)}"custom"===b.params.paginationType&&b.params.paginationCustomRender&&(b.paginationContainer.html(b.params.paginationCustomRender(b,i+1,s)),b.emit("onPaginationRendered",b,b.paginationContainer[0]))}b.params.loop||(b.params.prevButton&&b.prevButton&&b.prevButton.length>0&&(b.isBeginning?(b.prevButton.addClass(b.params.buttonDisabledClass),b.params.a11y&&b.a11y&&b.a11y.disable(b.prevButton)):(b.prevButton.removeClass(b.params.buttonDisabledClass),b.params.a11y&&b.a11y&&b.a11y.enable(b.prevButton))),b.params.nextButton&&b.nextButton&&b.nextButton.length>0&&(b.isEnd?(b.nextButton.addClass(b.params.buttonDisabledClass),b.params.a11y&&b.a11y&&b.a11y.disable(b.nextButton)):(b.nextButton.removeClass(b.params.buttonDisabledClass),b.params.a11y&&b.a11y&&b.a11y.enable(b.nextButton))))},b.updatePagination=function(){if(b.params.pagination&&b.paginationContainer&&b.paginationContainer.length>0){var e="";if("bullets"===b.params.paginationType){for(var a=b.params.loop?Math.ceil((b.slides.length-2*b.loopedSlides)/b.params.slidesPerGroup):b.snapGrid.length,t=0;a>t;t++)e+=b.params.paginationBulletRender?b.params.paginationBulletRender(t,b.params.bulletClass):"<"+b.params.paginationElement+' class="'+b.params.bulletClass+'">";b.paginationContainer.html(e),b.bullets=b.paginationContainer.find("."+b.params.bulletClass),b.params.paginationClickable&&b.params.a11y&&b.a11y&&b.a11y.initPagination()}"fraction"===b.params.paginationType&&(e=b.params.paginationFractionRender?b.params.paginationFractionRender(b,b.params.paginationCurrentClass,b.params.paginationTotalClass):' / ',b.paginationContainer.html(e)),"progress"===b.params.paginationType&&(e=b.params.paginationProgressRender?b.params.paginationProgressRender(b,b.params.paginationProgressbarClass):'',b.paginationContainer.html(e)),"custom"!==b.params.paginationType&&b.emit("onPaginationRendered",b,b.paginationContainer[0])}},b.update=function(e){function a(){r=Math.min(Math.max(b.translate,b.maxTranslate()),b.minTranslate()),b.setWrapperTranslate(r),b.updateActiveIndex(),b.updateClasses()}if(b.updateContainerSize(),b.updateSlidesSize(),b.updateProgress(),b.updatePagination(),b.updateClasses(),b.params.scrollbar&&b.scrollbar&&b.scrollbar.set(),e){var t,r;b.controller&&b.controller.spline&&(b.controller.spline=void 0),b.params.freeMode?(a(),b.params.autoHeight&&b.updateAutoHeight()):(t=("auto"===b.params.slidesPerView||b.params.slidesPerView>1)&&b.isEnd&&!b.params.centeredSlides?b.slideTo(b.slides.length-1,0,!1,!0):b.slideTo(b.activeIndex,0,!1,!0),t||a())}else b.params.autoHeight&&b.updateAutoHeight()},b.onResize=function(e){b.params.breakpoints&&b.setBreakpoint();var a=b.params.allowSwipeToPrev,t=b.params.allowSwipeToNext;b.params.allowSwipeToPrev=b.params.allowSwipeToNext=!0,b.updateContainerSize(),b.updateSlidesSize(),("auto"===b.params.slidesPerView||b.params.freeMode||e)&&b.updatePagination(),b.params.scrollbar&&b.scrollbar&&b.scrollbar.set(),b.controller&&b.controller.spline&&(b.controller.spline=void 0);var r=!1;if(b.params.freeMode){var i=Math.min(Math.max(b.translate,b.maxTranslate()),b.minTranslate());b.setWrapperTranslate(i),b.updateActiveIndex(),b.updateClasses(),b.params.autoHeight&&b.updateAutoHeight()}else b.updateClasses(),r=("auto"===b.params.slidesPerView||b.params.slidesPerView>1)&&b.isEnd&&!b.params.centeredSlides?b.slideTo(b.slides.length-1,0,!1,!0):b.slideTo(b.activeIndex,0,!1,!0);b.params.lazyLoading&&!r&&b.lazy&&b.lazy.load(),b.params.allowSwipeToPrev=a,b.params.allowSwipeToNext=t};var T=["mousedown","mousemove","mouseup"];window.navigator.pointerEnabled?T=["pointerdown","pointermove","pointerup"]:window.navigator.msPointerEnabled&&(T=["MSPointerDown","MSPointerMove","MSPointerUp"]),b.touchEvents={start:b.support.touch||!b.params.simulateTouch?"touchstart":T[0],move:b.support.touch||!b.params.simulateTouch?"touchmove":T[1],end:b.support.touch||!b.params.simulateTouch?"touchend":T[2]},(window.navigator.pointerEnabled||window.navigator.msPointerEnabled)&&("container"===b.params.touchEventsTarget?b.container:b.wrapper).addClass("swiper-wp8-"+b.params.direction),b.initEvents=function(e){var a=e?"off":"on",t=e?"removeEventListener":"addEventListener",r="container"===b.params.touchEventsTarget?b.container[0]:b.wrapper[0],s=b.support.touch?r:document,n=b.params.nested?!0:!1;b.browser.ie?(r[t](b.touchEvents.start,b.onTouchStart,!1),s[t](b.touchEvents.move,b.onTouchMove,n),s[t](b.touchEvents.end,b.onTouchEnd,!1)):(b.support.touch&&(r[t](b.touchEvents.start,b.onTouchStart,!1),r[t](b.touchEvents.move,b.onTouchMove,n),r[t](b.touchEvents.end,b.onTouchEnd,!1)),!i.simulateTouch||b.device.ios||b.device.android||(r[t]("mousedown",b.onTouchStart,!1),document[t]("mousemove",b.onTouchMove,n),document[t]("mouseup",b.onTouchEnd,!1))),window[t]("resize",b.onResize),b.params.nextButton&&b.nextButton&&b.nextButton.length>0&&(b.nextButton[a]("click",b.onClickNext),b.params.a11y&&b.a11y&&b.nextButton[a]("keydown",b.a11y.onEnterKey)),b.params.prevButton&&b.prevButton&&b.prevButton.length>0&&(b.prevButton[a]("click",b.onClickPrev),b.params.a11y&&b.a11y&&b.prevButton[a]("keydown",b.a11y.onEnterKey)),b.params.pagination&&b.params.paginationClickable&&(b.paginationContainer[a]("click","."+b.params.bulletClass,b.onClickIndex),b.params.a11y&&b.a11y&&b.paginationContainer[a]("keydown","."+b.params.bulletClass,b.a11y.onEnterKey)),(b.params.preventClicks||b.params.preventClicksPropagation)&&r[t]("click",b.preventClicks,!0)},b.attachEvents=function(){b.initEvents()},b.detachEvents=function(){b.initEvents(!0)},b.allowClick=!0,b.preventClicks=function(e){b.allowClick||(b.params.preventClicks&&e.preventDefault(),b.params.preventClicksPropagation&&b.animating&&(e.stopPropagation(),e.stopImmediatePropagation()))},b.onClickNext=function(e){e.preventDefault(),(!b.isEnd||b.params.loop)&&b.slideNext()},b.onClickPrev=function(e){e.preventDefault(),(!b.isBeginning||b.params.loop)&&b.slidePrev()},b.onClickIndex=function(e){e.preventDefault();var t=a(this).index()*b.params.slidesPerGroup;b.params.loop&&(t+=b.loopedSlides),b.slideTo(t)},b.updateClickedSlide=function(e){var t=o(e,"."+b.params.slideClass),r=!1;if(t)for(var i=0;ib.slides.length-b.loopedSlides+b.params.slidesPerView/2?(b.fixLoop(),n=b.wrapper.children("."+b.params.slideClass+'[data-swiper-slide-index="'+s+'"]:not(.swiper-slide-duplicate)').eq(0).index(),setTimeout(function(){b.slideTo(n)},0)):b.slideTo(n):n>b.slides.length-b.params.slidesPerView?(b.fixLoop(),n=b.wrapper.children("."+b.params.slideClass+'[data-swiper-slide-index="'+s+'"]:not(.swiper-slide-duplicate)').eq(0).index(),setTimeout(function(){b.slideTo(n)},0)):b.slideTo(n)}else b.slideTo(n)}};var S,C,z,M,E,P,k,I,L,B,D="input, select, textarea, button",H=Date.now(),A=[];b.animating=!1,b.touches={startX:0,startY:0,currentX:0,currentY:0,diff:0};var G,O;if(b.onTouchStart=function(e){if(e.originalEvent&&(e=e.originalEvent),G="touchstart"===e.type,G||!("which"in e)||3!==e.which){if(b.params.noSwiping&&o(e,"."+b.params.noSwipingClass))return void(b.allowClick=!0);if(!b.params.swipeHandler||o(e,b.params.swipeHandler)){var t=b.touches.currentX="touchstart"===e.type?e.targetTouches[0].pageX:e.pageX,r=b.touches.currentY="touchstart"===e.type?e.targetTouches[0].pageY:e.pageY;if(!(b.device.ios&&b.params.iOSEdgeSwipeDetection&&t<=b.params.iOSEdgeSwipeThreshold)){if(S=!0,C=!1,z=!0,E=void 0,O=void 0,b.touches.startX=t,b.touches.startY=r,M=Date.now(),b.allowClick=!0,b.updateContainerSize(),b.swipeDirection=void 0,b.params.threshold>0&&(I=!1),"touchstart"!==e.type){var i=!0;a(e.target).is(D)&&(i=!1),document.activeElement&&a(document.activeElement).is(D)&&document.activeElement.blur(),i&&e.preventDefault()}b.emit("onTouchStart",b,e)}}}},b.onTouchMove=function(e){if(e.originalEvent&&(e=e.originalEvent),!G||"mousemove"!==e.type){if(e.preventedByNestedSwiper)return b.touches.startX="touchmove"===e.type?e.targetTouches[0].pageX:e.pageX,void(b.touches.startY="touchmove"===e.type?e.targetTouches[0].pageY:e.pageY);if(b.params.onlyExternal)return b.allowClick=!1,void(S&&(b.touches.startX=b.touches.currentX="touchmove"===e.type?e.targetTouches[0].pageX:e.pageX,b.touches.startY=b.touches.currentY="touchmove"===e.type?e.targetTouches[0].pageY:e.pageY,M=Date.now()));if(G&&document.activeElement&&e.target===document.activeElement&&a(e.target).is(D))return C=!0,void(b.allowClick=!1);if(z&&b.emit("onTouchMove",b,e),!(e.targetTouches&&e.targetTouches.length>1)){if(b.touches.currentX="touchmove"===e.type?e.targetTouches[0].pageX:e.pageX,b.touches.currentY="touchmove"===e.type?e.targetTouches[0].pageY:e.pageY,"undefined"==typeof E){var t=180*Math.atan2(Math.abs(b.touches.currentY-b.touches.startY),Math.abs(b.touches.currentX-b.touches.startX))/Math.PI;E=b.isHorizontal()?t>b.params.touchAngle:90-t>b.params.touchAngle}if(E&&b.emit("onTouchMoveOpposite",b,e),"undefined"==typeof O&&b.browser.ieTouch&&(b.touches.currentX!==b.touches.startX||b.touches.currentY!==b.touches.startY)&&(O=!0),S){if(E)return void(S=!1);if(O||!b.browser.ieTouch){b.allowClick=!1,b.emit("onSliderMove",b,e),e.preventDefault(),b.params.touchMoveStopPropagation&&!b.params.nested&&e.stopPropagation(),C||(i.loop&&b.fixLoop(),k=b.getWrapperTranslate(),b.setWrapperTransition(0),b.animating&&b.wrapper.trigger("webkitTransitionEnd transitionend oTransitionEnd MSTransitionEnd msTransitionEnd"),b.params.autoplay&&b.autoplaying&&(b.params.autoplayDisableOnInteraction?b.stopAutoplay():b.pauseAutoplay()),B=!1,b.params.grabCursor&&(b.container[0].style.cursor="move",b.container[0].style.cursor="-webkit-grabbing",b.container[0].style.cursor="-moz-grabbin",b.container[0].style.cursor="grabbing")),C=!0;var r=b.touches.diff=b.isHorizontal()?b.touches.currentX-b.touches.startX:b.touches.currentY-b.touches.startY;r*=b.params.touchRatio,b.rtl&&(r=-r),b.swipeDirection=r>0?"prev":"next",P=r+k;var s=!0;if(r>0&&P>b.minTranslate()?(s=!1,b.params.resistance&&(P=b.minTranslate()-1+Math.pow(-b.minTranslate()+k+r,b.params.resistanceRatio))):0>r&&PP&&(P=k),!b.params.allowSwipeToPrev&&"prev"===b.swipeDirection&&P>k&&(P=k),b.params.followFinger){if(b.params.threshold>0){if(!(Math.abs(r)>b.params.threshold||I))return void(P=k);if(!I)return I=!0,b.touches.startX=b.touches.currentX,b.touches.startY=b.touches.currentY,P=k,void(b.touches.diff=b.isHorizontal()?b.touches.currentX-b.touches.startX:b.touches.currentY-b.touches.startY)}(b.params.freeMode||b.params.watchSlidesProgress)&&b.updateActiveIndex(),b.params.freeMode&&(0===A.length&&A.push({position:b.touches[b.isHorizontal()?"startX":"startY"],time:M}),A.push({position:b.touches[b.isHorizontal()?"currentX":"currentY"],time:(new window.Date).getTime()})),b.updateProgress(P),b.setWrapperTranslate(P)}}}}}},b.onTouchEnd=function(e){if(e.originalEvent&&(e=e.originalEvent),z&&b.emit("onTouchEnd",b,e),z=!1,S){b.params.grabCursor&&C&&S&&(b.container[0].style.cursor="move",b.container[0].style.cursor="-webkit-grab",b.container[0].style.cursor="-moz-grab",b.container[0].style.cursor="grab");var t=Date.now(),r=t-M;if(b.allowClick&&(b.updateClickedSlide(e),b.emit("onTap",b,e),300>r&&t-H>300&&(L&&clearTimeout(L),L=setTimeout(function(){b&&(b.params.paginationHide&&b.paginationContainer.length>0&&!a(e.target).hasClass(b.params.bulletClass)&&b.paginationContainer.toggleClass(b.params.paginationHiddenClass),b.emit("onClick",b,e))},300)),300>r&&300>t-H&&(L&&clearTimeout(L),b.emit("onDoubleTap",b,e))),H=Date.now(),setTimeout(function(){b&&(b.allowClick=!0)},0),!S||!C||!b.swipeDirection||0===b.touches.diff||P===k)return void(S=C=!1);S=C=!1;var i;if(i=b.params.followFinger?b.rtl?b.translate:-b.translate:-P,b.params.freeMode){if(i<-b.minTranslate())return void b.slideTo(b.activeIndex);if(i>-b.maxTranslate())return void(b.slides.length1){var s=A.pop(),n=A.pop(),o=s.position-n.position,l=s.time-n.time;b.velocity=o/l,b.velocity=b.velocity/2,Math.abs(b.velocity)150||(new window.Date).getTime()-s.time>300)&&(b.velocity=0)}else b.velocity=0;A.length=0;var p=1e3*b.params.freeModeMomentumRatio,d=b.velocity*p,u=b.translate+d;b.rtl&&(u=-u);var c,m=!1,h=20*Math.abs(b.velocity)*b.params.freeModeMomentumBounceRatio;if(ub.minTranslate())b.params.freeModeMomentumBounce?(u-b.minTranslate()>h&&(u=b.minTranslate()+h),c=b.minTranslate(),m=!0,B=!0):u=b.minTranslate();else if(b.params.freeModeSticky){var f,g=0;for(g=0;g-u){f=g;break}u=Math.abs(b.snapGrid[f]-u)=b.params.longSwipesMs)&&(b.updateProgress(),b.updateActiveIndex()))}var v,w=0,y=b.slidesSizesGrid[0];for(v=0;v=b.slidesGrid[v]&&i=b.slidesGrid[v]&&(w=v,y=b.slidesGrid[b.slidesGrid.length-1]-b.slidesGrid[b.slidesGrid.length-2]);var x=(i-b.slidesGrid[w])/y;if(r>b.params.longSwipesMs){if(!b.params.longSwipes)return void b.slideTo(b.activeIndex);"next"===b.swipeDirection&&(x>=b.params.longSwipesRatio?b.slideTo(w+b.params.slidesPerGroup):b.slideTo(w)),"prev"===b.swipeDirection&&(x>1-b.params.longSwipesRatio?b.slideTo(w+b.params.slidesPerGroup):b.slideTo(w))}else{if(!b.params.shortSwipes)return void b.slideTo(b.activeIndex);"next"===b.swipeDirection&&b.slideTo(w+b.params.slidesPerGroup),"prev"===b.swipeDirection&&b.slideTo(w)}}},b._slideTo=function(e,a){return b.slideTo(e,a,!0,!0)},b.slideTo=function(e,a,t,r){"undefined"==typeof t&&(t=!0),"undefined"==typeof e&&(e=0),0>e&&(e=0),b.snapIndex=Math.floor(e/b.params.slidesPerGroup),b.snapIndex>=b.snapGrid.length&&(b.snapIndex=b.snapGrid.length-1);var i=-b.snapGrid[b.snapIndex];b.params.autoplay&&b.autoplaying&&(r||!b.params.autoplayDisableOnInteraction?b.pauseAutoplay(a):b.stopAutoplay()),b.updateProgress(i);for(var s=0;s=Math.floor(100*b.slidesGrid[s])&&(e=s);return!b.params.allowSwipeToNext&&ib.translate&&i>b.maxTranslate()&&(b.activeIndex||0)!==e?!1:("undefined"==typeof a&&(a=b.params.speed),b.previousIndex=b.activeIndex||0,b.activeIndex=e,b.rtl&&-i===b.translate||!b.rtl&&i===b.translate?(b.params.autoHeight&&b.updateAutoHeight(),b.updateClasses(),"slide"!==b.params.effect&&b.setWrapperTranslate(i),!1):(b.updateClasses(),b.onTransitionStart(t),0===a?(b.setWrapperTranslate(i),b.setWrapperTransition(0),b.onTransitionEnd(t)):(b.setWrapperTranslate(i),b.setWrapperTransition(a),b.animating||(b.animating=!0,b.wrapper.transitionEnd(function(){b&&b.onTransitionEnd(t)}))),!0))},b.onTransitionStart=function(e){"undefined"==typeof e&&(e=!0),b.params.autoHeight&&b.updateAutoHeight(),b.lazy&&b.lazy.onTransitionStart(),e&&(b.emit("onTransitionStart",b),b.activeIndex!==b.previousIndex&&(b.emit("onSlideChangeStart",b),b.activeIndex>b.previousIndex?b.emit("onSlideNextStart",b):b.emit("onSlidePrevStart",b)))},b.onTransitionEnd=function(e){b.animating=!1,b.setWrapperTransition(0),"undefined"==typeof e&&(e=!0),b.lazy&&b.lazy.onTransitionEnd(),e&&(b.emit("onTransitionEnd",b),b.activeIndex!==b.previousIndex&&(b.emit("onSlideChangeEnd",b),b.activeIndex>b.previousIndex?b.emit("onSlideNextEnd",b):b.emit("onSlidePrevEnd",b))),b.params.hashnav&&b.hashnav&&b.hashnav.setHash()},b.slideNext=function(e,a,t){if(b.params.loop){if(b.animating)return!1;b.fixLoop();b.container[0].clientLeft;return b.slideTo(b.activeIndex+b.params.slidesPerGroup,a,e,t)}return b.slideTo(b.activeIndex+b.params.slidesPerGroup,a,e,t)},b._slideNext=function(e){return b.slideNext(!0,e,!0)},b.slidePrev=function(e,a,t){if(b.params.loop){if(b.animating)return!1;b.fixLoop();b.container[0].clientLeft;return b.slideTo(b.activeIndex-1,a,e,t)}return b.slideTo(b.activeIndex-1,a,e,t)},b._slidePrev=function(e){return b.slidePrev(!0,e,!0)},b.slideReset=function(e,a,t){return b.slideTo(b.activeIndex,a,e)},b.setWrapperTransition=function(e,a){b.wrapper.transition(e),"slide"!==b.params.effect&&b.effects[b.params.effect]&&b.effects[b.params.effect].setTransition(e),b.params.parallax&&b.parallax&&b.parallax.setTransition(e),b.params.scrollbar&&b.scrollbar&&b.scrollbar.setTransition(e),b.params.control&&b.controller&&b.controller.setTransition(e,a),b.emit("onSetTransition",b,e)},b.setWrapperTranslate=function(e,a,t){var r=0,i=0,n=0;b.isHorizontal()?r=b.rtl?-e:e:i=e,b.params.roundLengths&&(r=s(r),i=s(i)),b.params.virtualTranslate||(b.support.transforms3d?b.wrapper.transform("translate3d("+r+"px, "+i+"px, "+n+"px)"):b.wrapper.transform("translate("+r+"px, "+i+"px)")),b.translate=b.isHorizontal()?r:i;var o,l=b.maxTranslate()-b.minTranslate();o=0===l?0:(e-b.minTranslate())/l,o!==b.progress&&b.updateProgress(e),a&&b.updateActiveIndex(),"slide"!==b.params.effect&&b.effects[b.params.effect]&&b.effects[b.params.effect].setTranslate(b.translate),b.params.parallax&&b.parallax&&b.parallax.setTranslate(b.translate),b.params.scrollbar&&b.scrollbar&&b.scrollbar.setTranslate(b.translate),b.params.control&&b.controller&&b.controller.setTranslate(b.translate,t),b.emit("onSetTranslate",b,b.translate)},b.getTranslate=function(e,a){var t,r,i,s;return"undefined"==typeof a&&(a="x"),b.params.virtualTranslate?b.rtl?-b.translate:b.translate:(i=window.getComputedStyle(e,null),window.WebKitCSSMatrix?(r=i.transform||i.webkitTransform,r.split(",").length>6&&(r=r.split(", ").map(function(e){return e.replace(",",".")}).join(", ")),s=new window.WebKitCSSMatrix("none"===r?"":r)):(s=i.MozTransform||i.OTransform||i.MsTransform||i.msTransform||i.transform||i.getPropertyValue("transform").replace("translate(","matrix(1, 0, 0, 1,"),t=s.toString().split(",")),"x"===a&&(r=window.WebKitCSSMatrix?s.m41:16===t.length?parseFloat(t[12]):parseFloat(t[4])),"y"===a&&(r=window.WebKitCSSMatrix?s.m42:16===t.length?parseFloat(t[13]):parseFloat(t[5])),b.rtl&&r&&(r=-r),r||0)},b.getWrapperTranslate=function(e){return"undefined"==typeof e&&(e=b.isHorizontal()?"x":"y"),b.getTranslate(b.wrapper[0],e)},b.observers=[],b.initObservers=function(){if(b.params.observeParents)for(var e=b.container.parents(),a=0;ae.length&&(b.loopedSlides=e.length);var t,r=[],i=[];for(e.each(function(t,s){var n=a(this);t=e.length-b.loopedSlides&&r.push(s),n.attr("data-swiper-slide-index",t)}),t=0;t=0;t--)b.wrapper.prepend(a(r[t].cloneNode(!0)).addClass(b.params.slideDuplicateClass))},b.destroyLoop=function(){b.wrapper.children("."+b.params.slideClass+"."+b.params.slideDuplicateClass).remove(),b.slides.removeAttr("data-swiper-slide-index")},b.reLoop=function(e){var a=b.activeIndex-b.loopedSlides;b.destroyLoop(),b.createLoop(),b.updateSlidesSize(),e&&b.slideTo(a+b.loopedSlides,0,!1)},b.fixLoop=function(){var e;b.activeIndex=2*b.loopedSlides||b.activeIndex>b.slides.length-2*b.params.slidesPerView)&&(e=-b.slides.length+b.activeIndex+b.loopedSlides,e+=b.loopedSlides,b.slideTo(e,0,!1,!0))},b.appendSlide=function(e){if(b.params.loop&&b.destroyLoop(),"object"==typeof e&&e.length)for(var a=0;aa&&t--;t=Math.max(t,0)}else a=e,b.slides[a]&&b.slides.eq(a).remove(),t>a&&t--,t=Math.max(t,0);b.params.loop&&b.createLoop(),b.params.observer&&b.support.observer||b.update(!0),b.params.loop?b.slideTo(t+b.loopedSlides,0,!1):b.slideTo(t,0,!1)},b.removeAllSlides=function(){for(var e=[],a=0;a'),t.append(d)),0===u.length&&(u=a('
'),t.append(u)),d.length&&(d[0].style.opacity=Math.max(-r,0)),u.length&&(u[0].style.opacity=Math.max(r,0))}t.transform("translate3d("+l+"px, "+p+"px, 0px) rotateX("+o+"deg) rotateY("+n+"deg)")}},setTransition:function(e){if(b.slides.transition(e).find(".swiper-slide-shadow-top, .swiper-slide-shadow-right, .swiper-slide-shadow-bottom, .swiper-slide-shadow-left").transition(e),b.params.virtualTranslate&&0!==e){var t=!1;b.slides.eq(b.activeIndex).transitionEnd(function(){if(!t&&b&&a(this).hasClass(b.params.slideActiveClass)){t=!0,b.animating=!1;for(var e=["webkitTransitionEnd","transitionend","oTransitionEnd","MSTransitionEnd","msTransitionEnd"],r=0;r'),b.wrapper.append(e)),e.css({height:b.width+"px"})):(e=b.container.find(".swiper-cube-shadow"),0===e.length&&(e=a('
'),b.container.append(e))));for(var r=0;r=o&&o>-1&&(t=90*r+90*o,b.rtl&&(t=90*-r-90*o)),i.transform(u),b.params.cube.slideShadows){var c=b.isHorizontal()?i.find(".swiper-slide-shadow-left"):i.find(".swiper-slide-shadow-top"),m=b.isHorizontal()?i.find(".swiper-slide-shadow-right"):i.find(".swiper-slide-shadow-bottom");0===c.length&&(c=a('
'),i.append(c)),0===m.length&&(m=a('
'),i.append(m)),c.length&&(c[0].style.opacity=Math.max(-o,0)),m.length&&(m[0].style.opacity=Math.max(o,0))}}if(b.wrapper.css({"-webkit-transform-origin":"50% 50% -"+b.size/2+"px","-moz-transform-origin":"50% 50% -"+b.size/2+"px","-ms-transform-origin":"50% 50% -"+b.size/2+"px","transform-origin":"50% 50% -"+b.size/2+"px"}),b.params.cube.shadow)if(b.isHorizontal())e.transform("translate3d(0px, "+(b.width/2+b.params.cube.shadowOffset)+"px, "+-b.width/2+"px) rotateX(90deg) rotateZ(0deg) scale("+b.params.cube.shadowScale+")");else{var h=Math.abs(t)-90*Math.floor(Math.abs(t)/90),f=1.5-(Math.sin(2*h*Math.PI/360)/2+Math.cos(2*h*Math.PI/360)/2),g=b.params.cube.shadowScale,v=b.params.cube.shadowScale/f,w=b.params.cube.shadowOffset;e.transform("scale3d("+g+", 1, "+v+") translate3d(0px, "+(b.height/2+w)+"px, "+-b.height/2/v+"px) rotateX(-90deg)")}var y=b.isSafari||b.isUiWebView?-b.size/2:0;b.wrapper.transform("translate3d(0px,0,"+y+"px) rotateX("+(b.isHorizontal()?0:t)+"deg) rotateY("+(b.isHorizontal()?-t:0)+"deg)")},setTransition:function(e){b.slides.transition(e).find(".swiper-slide-shadow-top, .swiper-slide-shadow-right, .swiper-slide-shadow-bottom, .swiper-slide-shadow-left").transition(e),b.params.cube.shadow&&!b.isHorizontal()&&b.container.find(".swiper-cube-shadow").transition(e)}},coverflow:{setTranslate:function(){for(var e=b.translate,t=b.isHorizontal()?-e+b.width/2:-e+b.height/2,r=b.isHorizontal()?b.params.coverflow.rotate:-b.params.coverflow.rotate,i=b.params.coverflow.depth,s=0,n=b.slides.length;n>s;s++){var o=b.slides.eq(s),l=b.slidesSizesGrid[s],p=o[0].swiperSlideOffset,d=(t-p-l/2)/l*b.params.coverflow.modifier,u=b.isHorizontal()?r*d:0,c=b.isHorizontal()?0:r*d,m=-i*Math.abs(d),h=b.isHorizontal()?0:b.params.coverflow.stretch*d,f=b.isHorizontal()?b.params.coverflow.stretch*d:0;Math.abs(f)<.001&&(f=0),Math.abs(h)<.001&&(h=0),Math.abs(m)<.001&&(m=0),Math.abs(u)<.001&&(u=0),Math.abs(c)<.001&&(c=0);var g="translate3d("+f+"px,"+h+"px,"+m+"px) rotateX("+c+"deg) rotateY("+u+"deg)";if(o.transform(g),o[0].style.zIndex=-Math.abs(Math.round(d))+1,b.params.coverflow.slideShadows){var v=b.isHorizontal()?o.find(".swiper-slide-shadow-left"):o.find(".swiper-slide-shadow-top"),w=b.isHorizontal()?o.find(".swiper-slide-shadow-right"):o.find(".swiper-slide-shadow-bottom");0===v.length&&(v=a('
'),o.append(v)),0===w.length&&(w=a('
'),o.append(w)),v.length&&(v[0].style.opacity=d>0?d:0),w.length&&(w[0].style.opacity=-d>0?-d:0)}}if(b.browser.ie){var y=b.wrapper[0].style;y.perspectiveOrigin=t+"px 50%"}},setTransition:function(e){b.slides.transition(e).find(".swiper-slide-shadow-top, .swiper-slide-shadow-right, .swiper-slide-shadow-bottom, .swiper-slide-shadow-left").transition(e)}}},b.lazy={initialImageLoaded:!1,loadImageInSlide:function(e,t){if("undefined"!=typeof e&&("undefined"==typeof t&&(t=!0),0!==b.slides.length)){var r=b.slides.eq(e),i=r.find(".swiper-lazy:not(.swiper-lazy-loaded):not(.swiper-lazy-loading)");!r.hasClass("swiper-lazy")||r.hasClass("swiper-lazy-loaded")||r.hasClass("swiper-lazy-loading")||(i=i.add(r[0])),0!==i.length&&i.each(function(){var e=a(this);e.addClass("swiper-lazy-loading");var i=e.attr("data-background"),s=e.attr("data-src"),n=e.attr("data-srcset");b.loadImage(e[0],s||i,n,!1,function(){if(i?(e.css("background-image",'url("'+i+'")'),e.removeAttr("data-background")):(n&&(e.attr("srcset",n),e.removeAttr("data-srcset")),s&&(e.attr("src",s),e.removeAttr("data-src"))),e.addClass("swiper-lazy-loaded").removeClass("swiper-lazy-loading"),r.find(".swiper-lazy-preloader, .preloader").remove(),b.params.loop&&t){var a=r.attr("data-swiper-slide-index");if(r.hasClass(b.params.slideDuplicateClass)){var o=b.wrapper.children('[data-swiper-slide-index="'+a+'"]:not(.'+b.params.slideDuplicateClass+")");b.lazy.loadImageInSlide(o.index(),!1)}else{var l=b.wrapper.children("."+b.params.slideDuplicateClass+'[data-swiper-slide-index="'+a+'"]');b.lazy.loadImageInSlide(l.index(),!1)}}b.emit("onLazyImageReady",b,r[0],e[0])}),b.emit("onLazyImageLoad",b,r[0],e[0])})}},load:function(){var e;if(b.params.watchSlidesVisibility)b.wrapper.children("."+b.params.slideVisibleClass).each(function(){b.lazy.loadImageInSlide(a(this).index())});else if(b.params.slidesPerView>1)for(e=b.activeIndex;e1||b.params.lazyLoadingInPrevNextAmount&&b.params.lazyLoadingInPrevNextAmount>1){var t=b.params.lazyLoadingInPrevNextAmount,r=b.params.slidesPerView,i=Math.min(b.activeIndex+r+Math.max(t,r),b.slides.length),s=Math.max(b.activeIndex-Math.max(r,t),0);for(e=b.activeIndex+b.params.slidesPerView;i>e;e++)b.slides[e]&&b.lazy.loadImageInSlide(e);for(e=s;e0&&b.lazy.loadImageInSlide(n.index());var o=b.wrapper.children("."+b.params.slidePrevClass);o.length>0&&b.lazy.loadImageInSlide(o.index())}},onTransitionStart:function(){b.params.lazyLoading&&(b.params.lazyLoadingOnTransitionStart||!b.params.lazyLoadingOnTransitionStart&&!b.lazy.initialImageLoaded)&&b.lazy.load()},onTransitionEnd:function(){b.params.lazyLoading&&!b.params.lazyLoadingOnTransitionStart&&b.lazy.load()}},b.scrollbar={isTouched:!1,setDragPosition:function(e){var a=b.scrollbar,t=b.isHorizontal()?"touchstart"===e.type||"touchmove"===e.type?e.targetTouches[0].pageX:e.pageX||e.clientX:"touchstart"===e.type||"touchmove"===e.type?e.targetTouches[0].pageY:e.pageY||e.clientY,r=t-a.track.offset()[b.isHorizontal()?"left":"top"]-a.dragSize/2,i=-b.minTranslate()*a.moveDivider,s=-b.maxTranslate()*a.moveDivider;i>r?r=i:r>s&&(r=s),r=-r/a.moveDivider,b.updateProgress(r),b.setWrapperTranslate(r,!0)},dragStart:function(e){var a=b.scrollbar;a.isTouched=!0,e.preventDefault(),e.stopPropagation(),a.setDragPosition(e),clearTimeout(a.dragTimeout),a.track.transition(0),b.params.scrollbarHide&&a.track.css("opacity",1),b.wrapper.transition(100),a.drag.transition(100),b.emit("onScrollbarDragStart",b)},dragMove:function(e){var a=b.scrollbar;a.isTouched&&(e.preventDefault?e.preventDefault():e.returnValue=!1,a.setDragPosition(e),b.wrapper.transition(0),a.track.transition(0),a.drag.transition(0),b.emit("onScrollbarDragMove",b))},dragEnd:function(e){var a=b.scrollbar;a.isTouched&&(a.isTouched=!1,b.params.scrollbarHide&&(clearTimeout(a.dragTimeout),a.dragTimeout=setTimeout(function(){a.track.css("opacity",0),a.track.transition(400)},1e3)),b.emit("onScrollbarDragEnd",b),b.params.scrollbarSnapOnRelease&&b.slideReset())},enableDraggable:function(){var e=b.scrollbar,t=b.support.touch?e.track:document;a(e.track).on(b.touchEvents.start,e.dragStart),a(t).on(b.touchEvents.move,e.dragMove),a(t).on(b.touchEvents.end,e.dragEnd)},disableDraggable:function(){var e=b.scrollbar,t=b.support.touch?e.track:document;a(e.track).off(b.touchEvents.start,e.dragStart),a(t).off(b.touchEvents.move,e.dragMove),a(t).off(b.touchEvents.end,e.dragEnd)},set:function(){if(b.params.scrollbar){var e=b.scrollbar;e.track=a(b.params.scrollbar),b.params.uniqueNavElements&&"string"==typeof b.params.scrollbar&&e.track.length>1&&1===b.container.find(b.params.scrollbar).length&&(e.track=b.container.find(b.params.scrollbar)),e.drag=e.track.find(".swiper-scrollbar-drag"),0===e.drag.length&&(e.drag=a('
'),e.track.append(e.drag)),e.drag[0].style.width="",e.drag[0].style.height="",e.trackSize=b.isHorizontal()?e.track[0].offsetWidth:e.track[0].offsetHeight,e.divider=b.size/b.virtualSize,e.moveDivider=e.divider*(e.trackSize/b.size),e.dragSize=e.trackSize*e.divider,b.isHorizontal()?e.drag[0].style.width=e.dragSize+"px":e.drag[0].style.height=e.dragSize+"px",e.divider>=1?e.track[0].style.display="none":e.track[0].style.display="",b.params.scrollbarHide&&(e.track[0].style.opacity=0)}},setTranslate:function(){if(b.params.scrollbar){var e,a=b.scrollbar,t=(b.translate||0,a.dragSize);e=(a.trackSize-a.dragSize)*b.progress,b.rtl&&b.isHorizontal()?(e=-e,e>0?(t=a.dragSize-e,e=0):-e+a.dragSize>a.trackSize&&(t=a.trackSize+e)):0>e?(t=a.dragSize+e,e=0):e+a.dragSize>a.trackSize&&(t=a.trackSize-e),b.isHorizontal()?(b.support.transforms3d?a.drag.transform("translate3d("+e+"px, 0, 0)"):a.drag.transform("translateX("+e+"px)"),a.drag[0].style.width=t+"px"):(b.support.transforms3d?a.drag.transform("translate3d(0px, "+e+"px, 0)"):a.drag.transform("translateY("+e+"px)"),a.drag[0].style.height=t+"px"),b.params.scrollbarHide&&(clearTimeout(a.timeout),a.track[0].style.opacity=1,a.timeout=setTimeout(function(){a.track[0].style.opacity=0,a.track.transition(400)},1e3))}},setTransition:function(e){b.params.scrollbar&&b.scrollbar.drag.transition(e)}},b.controller={LinearSpline:function(e,a){this.x=e,this.y=a,this.lastIndex=e.length-1;var t,r;this.x.length;this.interpolate=function(e){return e?(r=i(this.x,e),t=r-1,(e-this.x[t])*(this.y[r]-this.y[t])/(this.x[r]-this.x[t])+this.y[t]):0};var i=function(){var e,a,t;return function(r,i){for(a=-1,e=r.length;e-a>1;)r[t=e+a>>1]<=i?a=t:e=t;return e}}()},getInterpolateFunction:function(e){b.controller.spline||(b.controller.spline=b.params.loop?new b.controller.LinearSpline(b.slidesGrid,e.slidesGrid):new b.controller.LinearSpline(b.snapGrid,e.snapGrid))},setTranslate:function(e,a){function r(a){e=a.rtl&&"horizontal"===a.params.direction?-b.translate:b.translate,"slide"===b.params.controlBy&&(b.controller.getInterpolateFunction(a),s=-b.controller.spline.interpolate(-e)),s&&"container"!==b.params.controlBy||(i=(a.maxTranslate()-a.minTranslate())/(b.maxTranslate()-b.minTranslate()),s=(e-b.minTranslate())*i+a.minTranslate()),b.params.controlInverse&&(s=a.maxTranslate()-s),a.updateProgress(s),a.setWrapperTranslate(s,!1,b),a.updateActiveIndex()}var i,s,n=b.params.control;if(b.isArray(n))for(var o=0;ot;t++){var i=b.slides.eq(t),s=i.attr("data-hash");if(s===e&&!i.hasClass(b.params.slideDuplicateClass)){var n=i.index();b.slideTo(n,a,b.params.runCallbacksOnInit,!0)}}}},setHash:function(){b.hashnav.initialized&&b.params.hashnav&&(document.location.hash=b.slides.eq(b.activeIndex).attr("data-hash")||"")}},b.disableKeyboardControl=function(){b.params.keyboardControl=!1,a(document).off("keydown",p)},b.enableKeyboardControl=function(){b.params.keyboardControl=!0,a(document).on("keydown",p)},b.mousewheel={event:!1,lastScrollTime:(new window.Date).getTime()},b.params.mousewheelControl){try{new window.WheelEvent("wheel"),b.mousewheel.event="wheel"}catch(N){(window.WheelEvent||b.container[0]&&"wheel"in b.container[0])&&(b.mousewheel.event="wheel")}!b.mousewheel.event&&window.WheelEvent,b.mousewheel.event||void 0===document.onmousewheel||(b.mousewheel.event="mousewheel"),b.mousewheel.event||(b.mousewheel.event="DOMMouseScroll")}b.disableMousewheelControl=function(){return b.mousewheel.event?(b.container.off(b.mousewheel.event,d),!0):!1},b.enableMousewheelControl=function(){return b.mousewheel.event?(b.container.on(b.mousewheel.event,d),!0):!1},b.parallax={setTranslate:function(){b.container.children("[data-swiper-parallax], [data-swiper-parallax-x], [data-swiper-parallax-y]").each(function(){u(this,b.progress)}),b.slides.each(function(){var e=a(this);e.find("[data-swiper-parallax], [data-swiper-parallax-x], [data-swiper-parallax-y]").each(function(){var a=Math.min(Math.max(e[0].progress,-1),1);u(this,a)})})},setTransition:function(e){"undefined"==typeof e&&(e=b.params.speed),b.container.find("[data-swiper-parallax], [data-swiper-parallax-x], [data-swiper-parallax-y]").each(function(){var t=a(this),r=parseInt(t.attr("data-swiper-parallax-duration"),10)||e;0===e&&(r=0),t.transition(r)})}},b._plugins=[];for(var R in b.plugins){var W=b.plugins[R](b,b.params[R]);W&&b._plugins.push(W)}return b.callPlugins=function(e){for(var a=0;a'),notify:function(e){var a=b.a11y.liveRegion;0!==a.length&&(a.html(""),a.html(e))},init:function(){b.params.nextButton&&b.nextButton&&b.nextButton.length>0&&(b.a11y.makeFocusable(b.nextButton),b.a11y.addRole(b.nextButton,"button"),b.a11y.addLabel(b.nextButton,b.params.nextSlideMessage)),b.params.prevButton&&b.prevButton&&b.prevButton.length>0&&(b.a11y.makeFocusable(b.prevButton),b.a11y.addRole(b.prevButton,"button"),b.a11y.addLabel(b.prevButton,b.params.prevSlideMessage)),a(b.container).append(b.a11y.liveRegion)},initPagination:function(){b.params.pagination&&b.params.paginationClickable&&b.bullets&&b.bullets.length&&b.bullets.each(function(){var e=a(this);b.a11y.makeFocusable(e),b.a11y.addRole(e,"button"),b.a11y.addLabel(e,b.params.paginationBulletMessage.replace(/{{index}}/,e.index()+1))})},destroy:function(){b.a11y.liveRegion&&b.a11y.liveRegion.length>0&&b.a11y.liveRegion.remove()}},b.init=function(){b.params.loop&&b.createLoop(),b.updateContainerSize(),b.updateSlidesSize(),b.updatePagination(),b.params.scrollbar&&b.scrollbar&&(b.scrollbar.set(),b.params.scrollbarDraggable&&b.scrollbar.enableDraggable()),"slide"!==b.params.effect&&b.effects[b.params.effect]&&(b.params.loop||b.updateProgress(),b.effects[b.params.effect].setTranslate()),b.params.loop?b.slideTo(b.params.initialSlide+b.loopedSlides,0,b.params.runCallbacksOnInit):(b.slideTo(b.params.initialSlide,0,b.params.runCallbacksOnInit),0===b.params.initialSlide&&(b.parallax&&b.params.parallax&&b.parallax.setTranslate(),b.lazy&&b.params.lazyLoading&&(b.lazy.load(),b.lazy.initialImageLoaded=!0))),b.attachEvents(),b.params.observer&&b.support.observer&&b.initObservers(),b.params.preloadImages&&!b.params.lazyLoading&&b.preloadImages(),b.params.autoplay&&b.startAutoplay(),b.params.keyboardControl&&b.enableKeyboardControl&&b.enableKeyboardControl(),b.params.mousewheelControl&&b.enableMousewheelControl&&b.enableMousewheelControl(), -b.params.hashnav&&b.hashnav&&b.hashnav.init(),b.params.a11y&&b.a11y&&b.a11y.init(),b.emit("onInit",b)},b.cleanupStyles=function(){b.container.removeClass(b.classNames.join(" ")).removeAttr("style"),b.wrapper.removeAttr("style"),b.slides&&b.slides.length&&b.slides.removeClass([b.params.slideVisibleClass,b.params.slideActiveClass,b.params.slideNextClass,b.params.slidePrevClass].join(" ")).removeAttr("style").removeAttr("data-swiper-column").removeAttr("data-swiper-row"),b.paginationContainer&&b.paginationContainer.length&&b.paginationContainer.removeClass(b.params.paginationHiddenClass),b.bullets&&b.bullets.length&&b.bullets.removeClass(b.params.bulletActiveClass),b.params.prevButton&&a(b.params.prevButton).removeClass(b.params.buttonDisabledClass),b.params.nextButton&&a(b.params.nextButton).removeClass(b.params.buttonDisabledClass),b.params.scrollbar&&b.scrollbar&&(b.scrollbar.track&&b.scrollbar.track.length&&b.scrollbar.track.removeAttr("style"),b.scrollbar.drag&&b.scrollbar.drag.length&&b.scrollbar.drag.removeAttr("style"))},b.destroy=function(e,a){b.detachEvents(),b.stopAutoplay(),b.params.scrollbar&&b.scrollbar&&b.params.scrollbarDraggable&&b.scrollbar.disableDraggable(),b.params.loop&&b.destroyLoop(),a&&b.cleanupStyles(),b.disconnectObservers(),b.params.keyboardControl&&b.disableKeyboardControl&&b.disableKeyboardControl(),b.params.mousewheelControl&&b.disableMousewheelControl&&b.disableMousewheelControl(),b.params.a11y&&b.a11y&&b.a11y.destroy(),b.emit("onDestroy"),e!==!1&&(b=null)},b.init(),b}};t.prototype={isSafari:function(){var e=navigator.userAgent.toLowerCase();return e.indexOf("safari")>=0&&e.indexOf("chrome")<0&&e.indexOf("android")<0}(),isUiWebView:/(iPhone|iPod|iPad).*AppleWebKit(?!.*Safari)/i.test(navigator.userAgent),isArray:function(e){return"[object Array]"===Object.prototype.toString.apply(e)},browser:{ie:window.navigator.pointerEnabled||window.navigator.msPointerEnabled,ieTouch:window.navigator.msPointerEnabled&&window.navigator.msMaxTouchPoints>1||window.navigator.pointerEnabled&&window.navigator.maxTouchPoints>1},device:function(){var e=navigator.userAgent,a=e.match(/(Android);?[\s\/]+([\d.]+)?/),t=e.match(/(iPad).*OS\s([\d_]+)/),r=e.match(/(iPod)(.*OS\s([\d_]+))?/),i=!t&&e.match(/(iPhone\sOS)\s([\d_]+)/);return{ios:t||i||r,android:a}}(),support:{touch:window.Modernizr&&Modernizr.touch===!0||function(){return!!("ontouchstart"in window||window.DocumentTouch&&document instanceof DocumentTouch)}(),transforms3d:window.Modernizr&&Modernizr.csstransforms3d===!0||function(){var e=document.createElement("div").style;return"webkitPerspective"in e||"MozPerspective"in e||"OPerspective"in e||"MsPerspective"in e||"perspective"in e}(),flexbox:function(){for(var e=document.createElement("div").style,a="alignItems webkitAlignItems webkitBoxAlign msFlexAlign mozBoxAlign webkitFlexDirection msFlexDirection mozBoxDirection mozBoxOrient webkitBoxDirection webkitBoxOrient".split(" "),t=0;t=0&&o.indexOf(">")>=0){var l="div";for(0===o.indexOf(":~]/)?(t||document).querySelectorAll(a):[document.getElementById(a.split("#")[1])],i=0;i0&&a[0].nodeType)for(i=0;i0?parseFloat(this.css("width")):null},outerWidth:function(e){return this.length>0?e?this[0].offsetWidth+parseFloat(this.css("margin-right"))+parseFloat(this.css("margin-left")):this[0].offsetWidth:null},height:function(){return this[0]===window?window.innerHeight:this.length>0?parseFloat(this.css("height")):null},outerHeight:function(e){return this.length>0?e?this[0].offsetHeight+parseFloat(this.css("margin-top"))+parseFloat(this.css("margin-bottom")):this[0].offsetHeight:null},offset:function(){if(this.length>0){var e=this[0],a=e.getBoundingClientRect(),t=document.body,r=e.clientTop||t.clientTop||0,i=e.clientLeft||t.clientLeft||0,s=window.pageYOffset||e.scrollTop,n=window.pageXOffset||e.scrollLeft;return{top:a.top+s-r,left:a.left+n-i}}return null},css:function(e,a){var t;if(1===arguments.length){if("string"!=typeof e){for(t=0;tr-1?new e([]):0>a?(t=r+a,new e(0>t?[]:[this[t]])):new e([this[a]])},append:function(a){var t,r;for(t=0;t=0;r--)this[t].insertBefore(i.childNodes[r],this[t].childNodes[0])}else if(a instanceof e)for(r=0;r1)for(var i=0;i1)for(var i=0;i0?t?this[0].nextElementSibling&&a(this[0].nextElementSibling).is(t)?[this[0].nextElementSibling]:[]:this[0].nextElementSibling?[this[0].nextElementSibling]:[]:[])},nextAll:function(t){var r=[],i=this[0];if(!i)return new e([]);for(;i.nextElementSibling;){var s=i.nextElementSibling;t?a(s).is(t)&&r.push(s):r.push(s),i=s}return new e(r)},prev:function(t){return new e(this.length>0?t?this[0].previousElementSibling&&a(this[0].previousElementSibling).is(t)?[this[0].previousElementSibling]:[]:this[0].previousElementSibling?[this[0].previousElementSibling]:[]:[])},prevAll:function(t){var r=[],i=this[0];if(!i)return new e([]);for(;i.previousElementSibling;){var s=i.previousElementSibling;t?a(s).is(t)&&r.push(s):r.push(s),i=s}return new e(r)},parent:function(e){for(var t=[],r=0;r 0 && 0 === b.container.parents(".swiper-slide-active").length) return; + var r = { + left: window.pageXOffset, + top: window.pageYOffset + }, + i = window.innerWidth, + s = window.innerHeight, + n = b.container.offset(); + b.rtl && (n.left = n.left - b.container[0].scrollLeft); + for (var o = [ + [n.left, n.top], + [n.left + b.width, n.top], + [n.left, n.top + b.height], + [n.left + b.width, n.top + b.height] + ], l = 0; l < o.length; l++) { + var p = o[l]; + p[0] >= r.left && p[0] <= r.left + i && p[1] >= r.top && p[1] <= r.top + s && (t = !0) + } + if (!t) return + } + b.isHorizontal() ? ((37 === a || 39 === a) && (e.preventDefault ? e.preventDefault() : e.returnValue = !1), (39 === a && !b.rtl || 37 === a && b.rtl) && b.slideNext(), (37 === a && !b.rtl || 39 === a && b.rtl) && b.slidePrev()) : ((38 === a || 40 === a) && (e.preventDefault ? e.preventDefault() : e.returnValue = !1), 40 === a && b.slideNext(), 38 === a && b.slidePrev()) + } + } + + function d(e) { + e.originalEvent && (e = e.originalEvent); + var a = b.mousewheel.event, + t = 0, + r = b.rtl ? -1 : 1; + if ("mousewheel" === a) + if (b.params.mousewheelForceToAxis) + if (b.isHorizontal()) { + if (!(Math.abs(e.wheelDeltaX) > Math.abs(e.wheelDeltaY))) return; + t = e.wheelDeltaX * r + } else { + if (!(Math.abs(e.wheelDeltaY) > Math.abs(e.wheelDeltaX))) return; + t = e.wheelDeltaY + } + else t = Math.abs(e.wheelDeltaX) > Math.abs(e.wheelDeltaY) ? -e.wheelDeltaX * r : -e.wheelDeltaY; + else if ("DOMMouseScroll" === a) t = -e.detail; + else if ("wheel" === a) + if (b.params.mousewheelForceToAxis) + if (b.isHorizontal()) { + if (!(Math.abs(e.deltaX) > Math.abs(e.deltaY))) return; + t = -e.deltaX * r + } else { + if (!(Math.abs(e.deltaY) > Math.abs(e.deltaX))) return; + t = -e.deltaY + } + else t = Math.abs(e.deltaX) > Math.abs(e.deltaY) ? -e.deltaX * r : -e.deltaY; + if (0 !== t) { + if (b.params.mousewheelInvert && (t = -t), b.params.freeMode) { + var i = b.getWrapperTranslate() + t * b.params.mousewheelSensitivity, + s = b.isBeginning, + n = b.isEnd; + if (i >= b.minTranslate() && (i = b.minTranslate()), i <= b.maxTranslate() && (i = b.maxTranslate()), b.setWrapperTransition(0), b.setWrapperTranslate(i), b.updateProgress(), b.updateActiveIndex(), (!s && b.isBeginning || !n && b.isEnd) && b.updateClasses(), b.params.freeModeSticky ? (clearTimeout(b.mousewheel.timeout), b.mousewheel.timeout = setTimeout(function() { + b.slideReset() + }, 300)) : b.params.lazyLoading && b.lazy && b.lazy.load(), 0 === i || i === b.maxTranslate()) return + } else { + if ((new window.Date).getTime() - b.mousewheel.lastScrollTime > 60) + if (0 > t) + if (b.isEnd && !b.params.loop || b.animating) { + if (b.params.mousewheelReleaseOnEdges) return !0 + } else b.slideNext(); + else if (b.isBeginning && !b.params.loop || b.animating) { + if (b.params.mousewheelReleaseOnEdges) return !0 + } else b.slidePrev(); + b.mousewheel.lastScrollTime = (new window.Date).getTime() + } + return b.params.autoplay && b.stopAutoplay(), e.preventDefault ? e.preventDefault() : e.returnValue = !1, !1 + } + } + + function u(e, t) { + e = a(e); + var r, i, s, n = b.rtl ? -1 : 1; + r = e.attr("data-swiper-parallax") || "0", i = e.attr("data-swiper-parallax-x"), s = e.attr("data-swiper-parallax-y"), i || s ? (i = i || "0", s = s || "0") : b.isHorizontal() ? (i = r, s = "0") : (s = r, i = "0"), i = i.indexOf("%") >= 0 ? parseInt(i, 10) * t * n + "%" : i * t * n + "px", s = s.indexOf("%") >= 0 ? parseInt(s, 10) * t + "%" : s * t + "px", e.transform("translate3d(" + i + ", " + s + ",0px)") + } + + function c(e) { + return 0 !== e.indexOf("on") && (e = e[0] !== e[0].toUpperCase() ? "on" + e[0].toUpperCase() + e.substring(1) : "on" + e), e + } + if (!(this instanceof t)) return new t(e, i); + var m = { + direction: "horizontal", + touchEventsTarget: "container", + initialSlide: 0, + speed: 300, + autoplay: !1, + autoplayDisableOnInteraction: !0, + autoplayStopOnLast: !1, + iOSEdgeSwipeDetection: !1, + iOSEdgeSwipeThreshold: 20, + freeMode: !1, + freeModeMomentum: !0, + freeModeMomentumRatio: 1, + freeModeMomentumBounce: !0, + freeModeMomentumBounceRatio: 1, + freeModeSticky: !1, + freeModeMinimumVelocity: .02, + autoHeight: !1, + setWrapperSize: !1, + virtualTranslate: !1, + effect: "slide", + coverflow: { + rotate: 50, + stretch: 0, + depth: 100, + modifier: 1, + slideShadows: !0 + }, + flip: { + slideShadows: !0, + limitRotation: !0 + }, + cube: { + slideShadows: !0, + shadow: !0, + shadowOffset: 20, + shadowScale: .94 + }, + fade: { + crossFade: !1 + }, + parallax: !1, + scrollbar: null, + scrollbarHide: !0, + scrollbarDraggable: !1, + scrollbarSnapOnRelease: !1, + keyboardControl: !1, + mousewheelControl: !1, + mousewheelReleaseOnEdges: !1, + mousewheelInvert: !1, + mousewheelForceToAxis: !1, + mousewheelSensitivity: 1, + hashnav: !1, + breakpoints: void 0, + spaceBetween: 0, + slidesPerView: 1, + slidesPerColumn: 1, + slidesPerColumnFill: "column", + slidesPerGroup: 1, + centeredSlides: !1, + slidesOffsetBefore: 0, + slidesOffsetAfter: 0, + roundLengths: !1, + touchRatio: 1, + touchAngle: 45, + simulateTouch: !0, + shortSwipes: !0, + longSwipes: !0, + longSwipesRatio: .5, + longSwipesMs: 300, + followFinger: !0, + onlyExternal: !1, + threshold: 0, + touchMoveStopPropagation: !0, + uniqueNavElements: !0, + pagination: null, + paginationElement: "span", + paginationClickable: !1, + paginationHide: !1, + paginationBulletRender: null, + paginationProgressRender: null, + paginationFractionRender: null, + paginationCustomRender: null, + paginationType: "bullets", + resistance: !0, + resistanceRatio: .85, + nextButton: null, + prevButton: null, + watchSlidesProgress: !1, + watchSlidesVisibility: !1, + grabCursor: !1, + preventClicks: !0, + preventClicksPropagation: !0, + slideToClickedSlide: !1, + lazyLoading: !1, + lazyLoadingInPrevNext: !1, + lazyLoadingInPrevNextAmount: 1, + lazyLoadingOnTransitionStart: !1, + preloadImages: !0, + updateOnImagesReady: !0, + loop: !1, + loopAdditionalSlides: 0, + loopedSlides: null, + control: void 0, + controlInverse: !1, + controlBy: "slide", + allowSwipeToPrev: !0, + allowSwipeToNext: !0, + swipeHandler: null, + noSwiping: !0, + noSwipingClass: "swiper-no-swiping", + slideClass: "swiper-slide", + slideActiveClass: "swiper-slide-active", + slideVisibleClass: "swiper-slide-visible", + slideDuplicateClass: "swiper-slide-duplicate", + slideNextClass: "swiper-slide-next", + slidePrevClass: "swiper-slide-prev", + wrapperClass: "swiper-wrapper", + bulletClass: "swiper-pagination-bullet", + bulletActiveClass: "swiper-pagination-bullet-active", + buttonDisabledClass: "swiper-button-disabled", + paginationCurrentClass: "swiper-pagination-current", + paginationTotalClass: "swiper-pagination-total", + paginationHiddenClass: "swiper-pagination-hidden", + paginationProgressbarClass: "swiper-pagination-progressbar", + observer: !1, + observeParents: !1, + a11y: !1, + prevSlideMessage: "Previous slide", + nextSlideMessage: "Next slide", + firstSlideMessage: "This is the first slide", + lastSlideMessage: "This is the last slide", + paginationBulletMessage: "Go to slide {{index}}", + runCallbacksOnInit: !0 + }, + h = i && i.virtualTranslate; + i = i || {}; + var f = {}; + for (var g in i) + if ("object" != typeof i[g] || null === i[g] || (i[g].nodeType || i[g] === window || i[g] === document || "undefined" != typeof r && i[g] instanceof r || "undefined" != typeof jQuery && i[g] instanceof jQuery)) f[g] = i[g]; + else { + f[g] = {}; + for (var v in i[g]) f[g][v] = i[g][v] + } for (var w in m) + if ("undefined" == typeof i[w]) i[w] = m[w]; + else if ("object" == typeof i[w]) + for (var y in m[w]) "undefined" == typeof i[w][y] && (i[w][y] = m[w][y]); + var b = this; + if (b.params = i, b.originalParams = f, b.classNames = [], "undefined" != typeof a && "undefined" != typeof r && (a = r), ("undefined" != typeof a || (a = "undefined" == typeof r ? window.Dom7 || window.Zepto || window.jQuery : r)) && (b.$ = a, b.currentBreakpoint = void 0, b.getActiveBreakpoint = function() { + if (!b.params.breakpoints) return !1; + var e, a = !1, + t = []; + for (e in b.params.breakpoints) b.params.breakpoints.hasOwnProperty(e) && t.push(e); + t.sort(function(e, a) { + return parseInt(e, 10) > parseInt(a, 10) + }); + for (var r = 0; r < t.length; r++) e = t[r], e >= window.innerWidth && !a && (a = e); + return a || "max" + }, b.setBreakpoint = function() { + var e = b.getActiveBreakpoint(); + if (e && b.currentBreakpoint !== e) { + var a = e in b.params.breakpoints ? b.params.breakpoints[e] : b.originalParams, + t = b.params.loop && a.slidesPerView !== b.params.slidesPerView; + for (var r in a) b.params[r] = a[r]; + b.currentBreakpoint = e, t && b.destroyLoop && b.reLoop(!0) + } + }, b.params.breakpoints && b.setBreakpoint(), b.container = a(e), 0 !== b.container.length)) { + if (b.container.length > 1) { + var x = []; + return b.container.each(function() { + x.push(new t(this, i)) + }), x + } + b.container[0].swiper = b, b.container.data("swiper", b), b.classNames.push("swiper-container-" + b.params.direction), b.params.freeMode && b.classNames.push("swiper-container-free-mode"), b.support.flexbox || (b.classNames.push("swiper-container-no-flexbox"), b.params.slidesPerColumn = 1), b.params.autoHeight && b.classNames.push("swiper-container-autoheight"), (b.params.parallax || b.params.watchSlidesVisibility) && (b.params.watchSlidesProgress = !0), ["cube", "coverflow", "flip"].indexOf(b.params.effect) >= 0 && (b.support.transforms3d ? (b.params.watchSlidesProgress = !0, b.classNames.push("swiper-container-3d")) : b.params.effect = "slide"), "slide" !== b.params.effect && b.classNames.push("swiper-container-" + b.params.effect), "cube" === b.params.effect && (b.params.resistanceRatio = 0, b.params.slidesPerView = 1, b.params.slidesPerColumn = 1, b.params.slidesPerGroup = 1, b.params.centeredSlides = !1, b.params.spaceBetween = 0, b.params.virtualTranslate = !0, b.params.setWrapperSize = !1), ("fade" === b.params.effect || "flip" === b.params.effect) && (b.params.slidesPerView = 1, b.params.slidesPerColumn = 1, b.params.slidesPerGroup = 1, b.params.watchSlidesProgress = !0, b.params.spaceBetween = 0, b.params.setWrapperSize = !1, "undefined" == typeof h && (b.params.virtualTranslate = !0)), b.params.grabCursor && b.support.touch && (b.params.grabCursor = !1), b.wrapper = b.container.children("." + b.params.wrapperClass), b.params.pagination && (b.paginationContainer = a(b.params.pagination), b.params.uniqueNavElements && "string" == typeof b.params.pagination && b.paginationContainer.length > 1 && 1 === b.container.find(b.params.pagination).length && (b.paginationContainer = b.container.find(b.params.pagination)), "bullets" === b.params.paginationType && b.params.paginationClickable ? b.paginationContainer.addClass("swiper-pagination-clickable") : b.params.paginationClickable = !1, b.paginationContainer.addClass("swiper-pagination-" + b.params.paginationType)), (b.params.nextButton || b.params.prevButton) && (b.params.nextButton && (b.nextButton = a(b.params.nextButton), b.params.uniqueNavElements && "string" == typeof b.params.nextButton && b.nextButton.length > 1 && 1 === b.container.find(b.params.nextButton).length && (b.nextButton = b.container.find(b.params.nextButton))), b.params.prevButton && (b.prevButton = a(b.params.prevButton), b.params.uniqueNavElements && "string" == typeof b.params.prevButton && b.prevButton.length > 1 && 1 === b.container.find(b.params.prevButton).length && (b.prevButton = b.container.find(b.params.prevButton)))), b.isHorizontal = function() { + return "horizontal" === b.params.direction + }, b.rtl = b.isHorizontal() && ("rtl" === b.container[0].dir.toLowerCase() || "rtl" === b.container.css("direction")), b.rtl && b.classNames.push("swiper-container-rtl"), b.rtl && (b.wrongRTL = "-webkit-box" === b.wrapper.css("display")), b.params.slidesPerColumn > 1 && b.classNames.push("swiper-container-multirow"), b.device.android && b.classNames.push("swiper-container-android"), b.container.addClass(b.classNames.join(" ")), b.translate = 0, b.progress = 0, b.velocity = 0, b.lockSwipeToNext = function() { + b.params.allowSwipeToNext = !1 + }, b.lockSwipeToPrev = function() { + b.params.allowSwipeToPrev = !1 + }, b.lockSwipes = function() { + b.params.allowSwipeToNext = b.params.allowSwipeToPrev = !1 + }, b.unlockSwipeToNext = function() { + b.params.allowSwipeToNext = !0 + }, b.unlockSwipeToPrev = function() { + b.params.allowSwipeToPrev = !0 + }, b.unlockSwipes = function() { + b.params.allowSwipeToNext = b.params.allowSwipeToPrev = !0 + }, b.params.grabCursor && (b.container[0].style.cursor = "move", b.container[0].style.cursor = "-webkit-grab", b.container[0].style.cursor = "-moz-grab", b.container[0].style.cursor = "grab"), b.imagesToLoad = [], b.imagesLoaded = 0, b.loadImage = function(e, a, t, r, i) { + function s() { + i && i() + } + var n; + e.complete && r ? s() : a ? (n = new window.Image, n.onload = s, n.onerror = s, t && (n.srcset = t), a && (n.src = a)) : s() + }, b.preloadImages = function() { + function e() { + "undefined" != typeof b && null !== b && (void 0 !== b.imagesLoaded && b.imagesLoaded++, b.imagesLoaded === b.imagesToLoad.length && (b.params.updateOnImagesReady && b.update(), b.emit("onImagesReady", b))) + } + b.imagesToLoad = b.container.find("img"); + for (var a = 0; a < b.imagesToLoad.length; a++) b.loadImage(b.imagesToLoad[a], b.imagesToLoad[a].currentSrc || b.imagesToLoad[a].getAttribute("src"), b.imagesToLoad[a].srcset || b.imagesToLoad[a].getAttribute("srcset"), !0, e) + }, b.autoplayTimeoutId = void 0, b.autoplaying = !1, b.autoplayPaused = !1, b.startAutoplay = function() { + return "undefined" != typeof b.autoplayTimeoutId ? !1 : b.params.autoplay ? b.autoplaying ? !1 : (b.autoplaying = !0, b.emit("onAutoplayStart", b), void n()) : !1 + }, b.stopAutoplay = function(e) { + b.autoplayTimeoutId && (b.autoplayTimeoutId && clearTimeout(b.autoplayTimeoutId), b.autoplaying = !1, b.autoplayTimeoutId = void 0, b.emit("onAutoplayStop", b)) + }, b.pauseAutoplay = function(e) { + b.autoplayPaused || (b.autoplayTimeoutId && clearTimeout(b.autoplayTimeoutId), b.autoplayPaused = !0, 0 === e ? (b.autoplayPaused = !1, n()) : b.wrapper.transitionEnd(function() { + b && (b.autoplayPaused = !1, b.autoplaying ? n() : b.stopAutoplay()) + })) + }, b.minTranslate = function() { + return -b.snapGrid[0] + }, b.maxTranslate = function() { + return -b.snapGrid[b.snapGrid.length - 1] + }, b.updateAutoHeight = function() { + var e = b.slides.eq(b.activeIndex)[0]; + if ("undefined" != typeof e) { + var a = e.offsetHeight; + a && b.wrapper.css("height", a + "px") + } + }, b.updateContainerSize = function() { + var e, a; + e = "undefined" != typeof b.params.width ? b.params.width : b.container[0].clientWidth, a = "undefined" != typeof b.params.height ? b.params.height : b.container[0].clientHeight, 0 === e && b.isHorizontal() || 0 === a && !b.isHorizontal() || (e = e - parseInt(b.container.css("padding-left"), 10) - parseInt(b.container.css("padding-right"), 10), a = a - parseInt(b.container.css("padding-top"), 10) - parseInt(b.container.css("padding-bottom"), 10), b.width = e, b.height = a, b.size = b.isHorizontal() ? b.width : b.height) + }, b.updateSlidesSize = function() { + b.slides = b.wrapper.children("." + b.params.slideClass), b.snapGrid = [], b.slidesGrid = [], b.slidesSizesGrid = []; + var e, a = b.params.spaceBetween, + t = -b.params.slidesOffsetBefore, + r = 0, + i = 0; + if ("undefined" != typeof b.size) { + "string" == typeof a && a.indexOf("%") >= 0 && (a = parseFloat(a.replace("%", "")) / 100 * b.size), b.virtualSize = -a, b.rtl ? b.slides.css({ + marginLeft: "", + marginTop: "" + }) : b.slides.css({ + marginRight: "", + marginBottom: "" + }); + var n; + b.params.slidesPerColumn > 1 && (n = Math.floor(b.slides.length / b.params.slidesPerColumn) === b.slides.length / b.params.slidesPerColumn ? b.slides.length : Math.ceil(b.slides.length / b.params.slidesPerColumn) * b.params.slidesPerColumn, "auto" !== b.params.slidesPerView && "row" === b.params.slidesPerColumnFill && (n = Math.max(n, b.params.slidesPerView * b.params.slidesPerColumn))); + var o, l = b.params.slidesPerColumn, + p = n / l, + d = p - (b.params.slidesPerColumn * p - b.slides.length); + for (e = 0; e < b.slides.length; e++) { + o = 0; + var u = b.slides.eq(e); + if (b.params.slidesPerColumn > 1) { + var c, m, h; + "column" === b.params.slidesPerColumnFill ? (m = Math.floor(e / l), h = e - m * l, (m > d || m === d && h === l - 1) && ++h >= l && (h = 0, m++), c = m + h * n / l, u.css({ + "-webkit-box-ordinal-group": c, + "-moz-box-ordinal-group": c, + "-ms-flex-order": c, + "-webkit-order": c, + order: c + })) : (h = Math.floor(e / p), m = e - h * p), u.css({ + "margin-top": 0 !== h && b.params.spaceBetween && b.params.spaceBetween + "px" + }).attr("data-swiper-column", m).attr("data-swiper-row", h) + } + "none" !== u.css("display") && ("auto" === b.params.slidesPerView ? (o = b.isHorizontal() ? u.outerWidth(!0) : u.outerHeight(!0), b.params.roundLengths && (o = s(o))) : (o = (b.size - (b.params.slidesPerView - 1) * a) / b.params.slidesPerView, b.params.roundLengths && (o = s(o)), b.isHorizontal() ? b.slides[e].style.width = o + "px" : b.slides[e].style.height = o + "px"), b.slides[e].swiperSlideSize = o, b.slidesSizesGrid.push(o), b.params.centeredSlides ? (t = t + o / 2 + r / 2 + a, 0 === e && (t = t - b.size / 2 - a), Math.abs(t) < .001 && (t = 0), i % b.params.slidesPerGroup === 0 && b.snapGrid.push(t), b.slidesGrid.push(t)) : (i % b.params.slidesPerGroup === 0 && b.snapGrid.push(t), b.slidesGrid.push(t), t = t + o + a), b.virtualSize += o + a, r = o, i++) + } + b.virtualSize = Math.max(b.virtualSize, b.size) + b.params.slidesOffsetAfter; + var f; + if (b.rtl && b.wrongRTL && ("slide" === b.params.effect || "coverflow" === b.params.effect) && b.wrapper.css({ + width: b.virtualSize + b.params.spaceBetween + "px" + }), (!b.support.flexbox || b.params.setWrapperSize) && (b.isHorizontal() ? b.wrapper.css({ + width: b.virtualSize + b.params.spaceBetween + "px" + }) : b.wrapper.css({ + height: b.virtualSize + b.params.spaceBetween + "px" + })), b.params.slidesPerColumn > 1 && (b.virtualSize = (o + b.params.spaceBetween) * n, b.virtualSize = Math.ceil(b.virtualSize / b.params.slidesPerColumn) - b.params.spaceBetween, b.wrapper.css({ + width: b.virtualSize + b.params.spaceBetween + "px" + }), b.params.centeredSlides)) { + for (f = [], e = 0; e < b.snapGrid.length; e++) b.snapGrid[e] < b.virtualSize + b.snapGrid[0] && f.push(b.snapGrid[e]); + b.snapGrid = f + } + if (!b.params.centeredSlides) { + for (f = [], e = 0; e < b.snapGrid.length; e++) b.snapGrid[e] <= b.virtualSize - b.size && f.push(b.snapGrid[e]); + b.snapGrid = f, Math.floor(b.virtualSize - b.size) - Math.floor(b.snapGrid[b.snapGrid.length - 1]) > 1 && b.snapGrid.push(b.virtualSize - b.size) + } + 0 === b.snapGrid.length && (b.snapGrid = [0]), 0 !== b.params.spaceBetween && (b.isHorizontal() ? b.rtl ? b.slides.css({ + marginLeft: a + "px" + }) : b.slides.css({ + marginRight: a + "px" + }) : b.slides.css({ + marginBottom: a + "px" + })), b.params.watchSlidesProgress && b.updateSlidesOffset() + } + }, b.updateSlidesOffset = function() { + for (var e = 0; e < b.slides.length; e++) b.slides[e].swiperSlideOffset = b.isHorizontal() ? b.slides[e].offsetLeft : b.slides[e].offsetTop + }, b.updateSlidesProgress = function(e) { + if ("undefined" == typeof e && (e = b.translate || 0), 0 !== b.slides.length) { + "undefined" == typeof b.slides[0].swiperSlideOffset && b.updateSlidesOffset(); + var a = -e; + b.rtl && (a = e), b.slides.removeClass(b.params.slideVisibleClass); + for (var t = 0; t < b.slides.length; t++) { + var r = b.slides[t], + i = (a - r.swiperSlideOffset) / (r.swiperSlideSize + b.params.spaceBetween); + if (b.params.watchSlidesVisibility) { + var s = -(a - r.swiperSlideOffset), + n = s + b.slidesSizesGrid[t], + o = s >= 0 && s < b.size || n > 0 && n <= b.size || 0 >= s && n >= b.size; + o && b.slides.eq(t).addClass(b.params.slideVisibleClass) + } + r.progress = b.rtl ? -i : i + } + } + }, b.updateProgress = function(e) { + "undefined" == typeof e && (e = b.translate || 0); + var a = b.maxTranslate() - b.minTranslate(), + t = b.isBeginning, + r = b.isEnd; + 0 === a ? (b.progress = 0, b.isBeginning = b.isEnd = !0) : (b.progress = (e - b.minTranslate()) / a, b.isBeginning = b.progress <= 0, b.isEnd = b.progress >= 1), b.isBeginning && !t && b.emit("onReachBeginning", b), b.isEnd && !r && b.emit("onReachEnd", b), b.params.watchSlidesProgress && b.updateSlidesProgress(e), b.emit("onProgress", b, b.progress) + }, b.updateActiveIndex = function() { + var e, a, t, r = b.rtl ? b.translate : -b.translate; + for (a = 0; a < b.slidesGrid.length; a++) "undefined" != typeof b.slidesGrid[a + 1] ? r >= b.slidesGrid[a] && r < b.slidesGrid[a + 1] - (b.slidesGrid[a + 1] - b.slidesGrid[a]) / 2 ? e = a : r >= b.slidesGrid[a] && r < b.slidesGrid[a + 1] && (e = a + 1) : r >= b.slidesGrid[a] && (e = a); + (0 > e || "undefined" == typeof e) && (e = 0), t = Math.floor(e / b.params.slidesPerGroup), t >= b.snapGrid.length && (t = b.snapGrid.length - 1), e !== b.activeIndex && (b.snapIndex = t, b.previousIndex = b.activeIndex, b.activeIndex = e, b.updateClasses()) + }, b.updateClasses = function() { + b.slides.removeClass(b.params.slideActiveClass + " " + b.params.slideNextClass + " " + b.params.slidePrevClass); + var e = b.slides.eq(b.activeIndex); + e.addClass(b.params.slideActiveClass); + var t = e.next("." + b.params.slideClass).addClass(b.params.slideNextClass); + b.params.loop && 0 === t.length && b.slides.eq(0).addClass(b.params.slideNextClass); + var r = e.prev("." + b.params.slideClass).addClass(b.params.slidePrevClass); + if (b.params.loop && 0 === r.length && b.slides.eq(-1).addClass(b.params.slidePrevClass), b.paginationContainer && b.paginationContainer.length > 0) { + var i, s = b.params.loop ? Math.ceil((b.slides.length - 2 * b.loopedSlides) / b.params.slidesPerGroup) : b.snapGrid.length; + if (b.params.loop ? (i = Math.ceil((b.activeIndex - b.loopedSlides) / b.params.slidesPerGroup), i > b.slides.length - 1 - 2 * b.loopedSlides && (i -= b.slides.length - 2 * b.loopedSlides), i > s - 1 && (i -= s), 0 > i && "bullets" !== b.params.paginationType && (i = s + i)) : i = "undefined" != typeof b.snapIndex ? b.snapIndex : b.activeIndex || 0, "bullets" === b.params.paginationType && b.bullets && b.bullets.length > 0 && (b.bullets.removeClass(b.params.bulletActiveClass), b.paginationContainer.length > 1 ? b.bullets.each(function() { + a(this).index() === i && a(this).addClass(b.params.bulletActiveClass) + }) : b.bullets.eq(i).addClass(b.params.bulletActiveClass)), "fraction" === b.params.paginationType && (b.paginationContainer.find("." + b.params.paginationCurrentClass).text(i + 1), b.paginationContainer.find("." + b.params.paginationTotalClass).text(s)), "progress" === b.params.paginationType) { + var n = (i + 1) / s, + o = n, + l = 1; + b.isHorizontal() || (l = n, o = 1), b.paginationContainer.find("." + b.params.paginationProgressbarClass).transform("translate3d(0,0,0) scaleX(" + o + ") scaleY(" + l + ")").transition(b.params.speed) + } + "custom" === b.params.paginationType && b.params.paginationCustomRender && (b.paginationContainer.html(b.params.paginationCustomRender(b, i + 1, s)), b.emit("onPaginationRendered", b, b.paginationContainer[0])) + } + b.params.loop || (b.params.prevButton && b.prevButton && b.prevButton.length > 0 && (b.isBeginning ? (b.prevButton.addClass(b.params.buttonDisabledClass), b.params.a11y && b.a11y && b.a11y.disable(b.prevButton)) : (b.prevButton.removeClass(b.params.buttonDisabledClass), b.params.a11y && b.a11y && b.a11y.enable(b.prevButton))), b.params.nextButton && b.nextButton && b.nextButton.length > 0 && (b.isEnd ? (b.nextButton.addClass(b.params.buttonDisabledClass), b.params.a11y && b.a11y && b.a11y.disable(b.nextButton)) : (b.nextButton.removeClass(b.params.buttonDisabledClass), b.params.a11y && b.a11y && b.a11y.enable(b.nextButton)))) + }, b.updatePagination = function() { + if (b.params.pagination && b.paginationContainer && b.paginationContainer.length > 0) { + var e = ""; + if ("bullets" === b.params.paginationType) { + for (var a = b.params.loop ? Math.ceil((b.slides.length - 2 * b.loopedSlides) / b.params.slidesPerGroup) : b.snapGrid.length, t = 0; a > t; t++) e += b.params.paginationBulletRender ? b.params.paginationBulletRender(t, b.params.bulletClass) : "<" + b.params.paginationElement + ' class="' + b.params.bulletClass + '">"; + b.paginationContainer.html(e), b.bullets = b.paginationContainer.find("." + b.params.bulletClass), b.params.paginationClickable && b.params.a11y && b.a11y && b.a11y.initPagination() + } + "fraction" === b.params.paginationType && (e = b.params.paginationFractionRender ? b.params.paginationFractionRender(b, b.params.paginationCurrentClass, b.params.paginationTotalClass) : ' / ', b.paginationContainer.html(e)), "progress" === b.params.paginationType && (e = b.params.paginationProgressRender ? b.params.paginationProgressRender(b, b.params.paginationProgressbarClass) : '', b.paginationContainer.html(e)), "custom" !== b.params.paginationType && b.emit("onPaginationRendered", b, b.paginationContainer[0]) + } + }, b.update = function(e) { + function a() { + r = Math.min(Math.max(b.translate, b.maxTranslate()), b.minTranslate()), b.setWrapperTranslate(r), b.updateActiveIndex(), b.updateClasses() + } + if (b.updateContainerSize(), b.updateSlidesSize(), b.updateProgress(), b.updatePagination(), b.updateClasses(), b.params.scrollbar && b.scrollbar && b.scrollbar.set(), e) { + var t, r; + b.controller && b.controller.spline && (b.controller.spline = void 0), b.params.freeMode ? (a(), b.params.autoHeight && b.updateAutoHeight()) : (t = ("auto" === b.params.slidesPerView || b.params.slidesPerView > 1) && b.isEnd && !b.params.centeredSlides ? b.slideTo(b.slides.length - 1, 0, !1, !0) : b.slideTo(b.activeIndex, 0, !1, !0), t || a()) + } else b.params.autoHeight && b.updateAutoHeight() + }, b.onResize = function(e) { + b.params.breakpoints && b.setBreakpoint(); + var a = b.params.allowSwipeToPrev, + t = b.params.allowSwipeToNext; + b.params.allowSwipeToPrev = b.params.allowSwipeToNext = !0, b.updateContainerSize(), b.updateSlidesSize(), ("auto" === b.params.slidesPerView || b.params.freeMode || e) && b.updatePagination(), b.params.scrollbar && b.scrollbar && b.scrollbar.set(), b.controller && b.controller.spline && (b.controller.spline = void 0); + var r = !1; + if (b.params.freeMode) { + var i = Math.min(Math.max(b.translate, b.maxTranslate()), b.minTranslate()); + b.setWrapperTranslate(i), b.updateActiveIndex(), b.updateClasses(), b.params.autoHeight && b.updateAutoHeight() + } else b.updateClasses(), r = ("auto" === b.params.slidesPerView || b.params.slidesPerView > 1) && b.isEnd && !b.params.centeredSlides ? b.slideTo(b.slides.length - 1, 0, !1, !0) : b.slideTo(b.activeIndex, 0, !1, !0); + b.params.lazyLoading && !r && b.lazy && b.lazy.load(), b.params.allowSwipeToPrev = a, b.params.allowSwipeToNext = t + }; + var T = ["mousedown", "mousemove", "mouseup"]; + window.navigator.pointerEnabled ? T = ["pointerdown", "pointermove", "pointerup"] : window.navigator.msPointerEnabled && (T = ["MSPointerDown", "MSPointerMove", "MSPointerUp"]), b.touchEvents = { + start: b.support.touch || !b.params.simulateTouch ? "touchstart" : T[0], + move: b.support.touch || !b.params.simulateTouch ? "touchmove" : T[1], + end: b.support.touch || !b.params.simulateTouch ? "touchend" : T[2] + }, (window.navigator.pointerEnabled || window.navigator.msPointerEnabled) && ("container" === b.params.touchEventsTarget ? b.container : b.wrapper).addClass("swiper-wp8-" + b.params.direction), b.initEvents = function(e) { + var a = e ? "off" : "on", + t = e ? "removeEventListener" : "addEventListener", + r = "container" === b.params.touchEventsTarget ? b.container[0] : b.wrapper[0], + s = b.support.touch ? r : document, + n = b.params.nested ? !0 : !1; + b.browser.ie ? (r[t](b.touchEvents.start, b.onTouchStart, !1), s[t](b.touchEvents.move, b.onTouchMove, n), s[t](b.touchEvents.end, b.onTouchEnd, !1)) : (b.support.touch && (r[t](b.touchEvents.start, b.onTouchStart, !1), r[t](b.touchEvents.move, b.onTouchMove, n), r[t](b.touchEvents.end, b.onTouchEnd, !1)), !i.simulateTouch || b.device.ios || b.device.android || (r[t]("mousedown", b.onTouchStart, !1), document[t]("mousemove", b.onTouchMove, n), document[t]("mouseup", b.onTouchEnd, !1))), window[t]("resize", b.onResize), b.params.nextButton && b.nextButton && b.nextButton.length > 0 && (b.nextButton[a]("click", b.onClickNext), b.params.a11y && b.a11y && b.nextButton[a]("keydown", b.a11y.onEnterKey)), b.params.prevButton && b.prevButton && b.prevButton.length > 0 && (b.prevButton[a]("click", b.onClickPrev), b.params.a11y && b.a11y && b.prevButton[a]("keydown", b.a11y.onEnterKey)), b.params.pagination && b.params.paginationClickable && (b.paginationContainer[a]("click", "." + b.params.bulletClass, b.onClickIndex), b.params.a11y && b.a11y && b.paginationContainer[a]("keydown", "." + b.params.bulletClass, b.a11y.onEnterKey)), (b.params.preventClicks || b.params.preventClicksPropagation) && r[t]("click", b.preventClicks, !0) + }, b.attachEvents = function() { + b.initEvents() + }, b.detachEvents = function() { + b.initEvents(!0) + }, b.allowClick = !0, b.preventClicks = function(e) { + b.allowClick || (b.params.preventClicks && e.preventDefault(), b.params.preventClicksPropagation && b.animating && (e.stopPropagation(), e.stopImmediatePropagation())) + }, b.onClickNext = function(e) { + e.preventDefault(), (!b.isEnd || b.params.loop) && b.slideNext() + }, b.onClickPrev = function(e) { + e.preventDefault(), (!b.isBeginning || b.params.loop) && b.slidePrev() + }, b.onClickIndex = function(e) { + e.preventDefault(); + var t = a(this).index() * b.params.slidesPerGroup; + b.params.loop && (t += b.loopedSlides), b.slideTo(t) + }, b.updateClickedSlide = function(e) { + var t = o(e, "." + b.params.slideClass), + r = !1; + if (t) + for (var i = 0; i < b.slides.length; i++) b.slides[i] === t && (r = !0); + if (!t || !r) return b.clickedSlide = void 0, void(b.clickedIndex = void 0); + if (b.clickedSlide = t, b.clickedIndex = a(t).index(), b.params.slideToClickedSlide && void 0 !== b.clickedIndex && b.clickedIndex !== b.activeIndex) { + var s, n = b.clickedIndex; + if (b.params.loop) { + if (b.animating) return; + s = a(b.clickedSlide).attr("data-swiper-slide-index"), b.params.centeredSlides ? n < b.loopedSlides - b.params.slidesPerView / 2 || n > b.slides.length - b.loopedSlides + b.params.slidesPerView / 2 ? (b.fixLoop(), n = b.wrapper.children("." + b.params.slideClass + '[data-swiper-slide-index="' + s + '"]:not(.swiper-slide-duplicate)').eq(0).index(), setTimeout(function() { + b.slideTo(n) + }, 0)) : b.slideTo(n) : n > b.slides.length - b.params.slidesPerView ? (b.fixLoop(), n = b.wrapper.children("." + b.params.slideClass + '[data-swiper-slide-index="' + s + '"]:not(.swiper-slide-duplicate)').eq(0).index(), setTimeout(function() { + b.slideTo(n) + }, 0)) : b.slideTo(n) + } else b.slideTo(n) + } + }; + var S, C, z, M, E, P, k, I, L, B, D = "input, select, textarea, button", + H = Date.now(), + A = []; + b.animating = !1, b.touches = { + startX: 0, + startY: 0, + currentX: 0, + currentY: 0, + diff: 0 + }; + var G, O; + if (b.onTouchStart = function(e) { + if (e.originalEvent && (e = e.originalEvent), G = "touchstart" === e.type, G || !("which" in e) || 3 !== e.which) { + if (b.params.noSwiping && o(e, "." + b.params.noSwipingClass)) return void(b.allowClick = !0); + if (!b.params.swipeHandler || o(e, b.params.swipeHandler)) { + var t = b.touches.currentX = "touchstart" === e.type ? e.targetTouches[0].pageX : e.pageX, + r = b.touches.currentY = "touchstart" === e.type ? e.targetTouches[0].pageY : e.pageY; + if (!(b.device.ios && b.params.iOSEdgeSwipeDetection && t <= b.params.iOSEdgeSwipeThreshold)) { + if (S = !0, C = !1, z = !0, E = void 0, O = void 0, b.touches.startX = t, b.touches.startY = r, M = Date.now(), b.allowClick = !0, b.updateContainerSize(), b.swipeDirection = void 0, b.params.threshold > 0 && (I = !1), "touchstart" !== e.type) { + var i = !0; + a(e.target).is(D) && (i = !1), document.activeElement && a(document.activeElement).is(D) && document.activeElement.blur(), i && e.preventDefault() + } + b.emit("onTouchStart", b, e) + } + } + } + }, b.onTouchMove = function(e) { + if (e.originalEvent && (e = e.originalEvent), !G || "mousemove" !== e.type) { + if (e.preventedByNestedSwiper) return b.touches.startX = "touchmove" === e.type ? e.targetTouches[0].pageX : e.pageX, void(b.touches.startY = "touchmove" === e.type ? e.targetTouches[0].pageY : e.pageY); + if (b.params.onlyExternal) return b.allowClick = !1, void(S && (b.touches.startX = b.touches.currentX = "touchmove" === e.type ? e.targetTouches[0].pageX : e.pageX, b.touches.startY = b.touches.currentY = "touchmove" === e.type ? e.targetTouches[0].pageY : e.pageY, M = Date.now())); + if (G && document.activeElement && e.target === document.activeElement && a(e.target).is(D)) return C = !0, void(b.allowClick = !1); + if (z && b.emit("onTouchMove", b, e), !(e.targetTouches && e.targetTouches.length > 1)) { + if (b.touches.currentX = "touchmove" === e.type ? e.targetTouches[0].pageX : e.pageX, b.touches.currentY = "touchmove" === e.type ? e.targetTouches[0].pageY : e.pageY, "undefined" == typeof E) { + var t = 180 * Math.atan2(Math.abs(b.touches.currentY - b.touches.startY), Math.abs(b.touches.currentX - b.touches.startX)) / Math.PI; + E = b.isHorizontal() ? t > b.params.touchAngle : 90 - t > b.params.touchAngle + } + if (E && b.emit("onTouchMoveOpposite", b, e), "undefined" == typeof O && b.browser.ieTouch && (b.touches.currentX !== b.touches.startX || b.touches.currentY !== b.touches.startY) && (O = !0), S) { + if (E) return void(S = !1); + if (O || !b.browser.ieTouch) { + b.allowClick = !1, b.emit("onSliderMove", b, e), e.preventDefault(), b.params.touchMoveStopPropagation && !b.params.nested && e.stopPropagation(), C || (i.loop && b.fixLoop(), k = b.getWrapperTranslate(), b.setWrapperTransition(0), b.animating && b.wrapper.trigger("webkitTransitionEnd transitionend oTransitionEnd MSTransitionEnd msTransitionEnd"), b.params.autoplay && b.autoplaying && (b.params.autoplayDisableOnInteraction ? b.stopAutoplay() : b.pauseAutoplay()), B = !1, b.params.grabCursor && (b.container[0].style.cursor = "move", b.container[0].style.cursor = "-webkit-grabbing", b.container[0].style.cursor = "-moz-grabbin", b.container[0].style.cursor = "grabbing")), C = !0; + var r = b.touches.diff = b.isHorizontal() ? b.touches.currentX - b.touches.startX : b.touches.currentY - b.touches.startY; + r *= b.params.touchRatio, b.rtl && (r = -r), b.swipeDirection = r > 0 ? "prev" : "next", P = r + k; + var s = !0; + if (r > 0 && P > b.minTranslate() ? (s = !1, b.params.resistance && (P = b.minTranslate() - 1 + Math.pow(-b.minTranslate() + k + r, b.params.resistanceRatio))) : 0 > r && P < b.maxTranslate() && (s = !1, b.params.resistance && (P = b.maxTranslate() + 1 - Math.pow(b.maxTranslate() - k - r, b.params.resistanceRatio))), + s && (e.preventedByNestedSwiper = !0), !b.params.allowSwipeToNext && "next" === b.swipeDirection && k > P && (P = k), !b.params.allowSwipeToPrev && "prev" === b.swipeDirection && P > k && (P = k), b.params.followFinger) { + if (b.params.threshold > 0) { + if (!(Math.abs(r) > b.params.threshold || I)) return void(P = k); + if (!I) return I = !0, b.touches.startX = b.touches.currentX, b.touches.startY = b.touches.currentY, P = k, void(b.touches.diff = b.isHorizontal() ? b.touches.currentX - b.touches.startX : b.touches.currentY - b.touches.startY) + }(b.params.freeMode || b.params.watchSlidesProgress) && b.updateActiveIndex(), b.params.freeMode && (0 === A.length && A.push({ + position: b.touches[b.isHorizontal() ? "startX" : "startY"], + time: M + }), A.push({ + position: b.touches[b.isHorizontal() ? "currentX" : "currentY"], + time: (new window.Date).getTime() + })), b.updateProgress(P), b.setWrapperTranslate(P) + } + } + } + } + } + }, b.onTouchEnd = function(e) { + if (e.originalEvent && (e = e.originalEvent), z && b.emit("onTouchEnd", b, e), z = !1, S) { + b.params.grabCursor && C && S && (b.container[0].style.cursor = "move", b.container[0].style.cursor = "-webkit-grab", b.container[0].style.cursor = "-moz-grab", b.container[0].style.cursor = "grab"); + var t = Date.now(), + r = t - M; + if (b.allowClick && (b.updateClickedSlide(e), b.emit("onTap", b, e), 300 > r && t - H > 300 && (L && clearTimeout(L), L = setTimeout(function() { + b && (b.params.paginationHide && b.paginationContainer.length > 0 && !a(e.target).hasClass(b.params.bulletClass) && b.paginationContainer.toggleClass(b.params.paginationHiddenClass), b.emit("onClick", b, e)) + }, 300)), 300 > r && 300 > t - H && (L && clearTimeout(L), b.emit("onDoubleTap", b, e))), H = Date.now(), setTimeout(function() { + b && (b.allowClick = !0) + }, 0), !S || !C || !b.swipeDirection || 0 === b.touches.diff || P === k) return void(S = C = !1); + S = C = !1; + var i; + if (i = b.params.followFinger ? b.rtl ? b.translate : -b.translate : -P, b.params.freeMode) { + if (i < -b.minTranslate()) return void b.slideTo(b.activeIndex); + if (i > -b.maxTranslate()) return void(b.slides.length < b.snapGrid.length ? b.slideTo(b.snapGrid.length - 1) : b.slideTo(b.slides.length - 1)); + if (b.params.freeModeMomentum) { + if (A.length > 1) { + var s = A.pop(), + n = A.pop(), + o = s.position - n.position, + l = s.time - n.time; + b.velocity = o / l, b.velocity = b.velocity / 2, Math.abs(b.velocity) < b.params.freeModeMinimumVelocity && (b.velocity = 0), (l > 150 || (new window.Date).getTime() - s.time > 300) && (b.velocity = 0) + } else b.velocity = 0; + A.length = 0; + var p = 1e3 * b.params.freeModeMomentumRatio, + d = b.velocity * p, + u = b.translate + d; + b.rtl && (u = -u); + var c, m = !1, + h = 20 * Math.abs(b.velocity) * b.params.freeModeMomentumBounceRatio; + if (u < b.maxTranslate()) b.params.freeModeMomentumBounce ? (u + b.maxTranslate() < -h && (u = b.maxTranslate() - h), c = b.maxTranslate(), m = !0, B = !0) : u = b.maxTranslate(); + else if (u > b.minTranslate()) b.params.freeModeMomentumBounce ? (u - b.minTranslate() > h && (u = b.minTranslate() + h), c = b.minTranslate(), m = !0, B = !0) : u = b.minTranslate(); + else if (b.params.freeModeSticky) { + var f, g = 0; + for (g = 0; g < b.snapGrid.length; g += 1) + if (b.snapGrid[g] > -u) { + f = g; + break + } u = Math.abs(b.snapGrid[f] - u) < Math.abs(b.snapGrid[f - 1] - u) || "next" === b.swipeDirection ? b.snapGrid[f] : b.snapGrid[f - 1], b.rtl || (u = -u) + } + if (0 !== b.velocity) p = b.rtl ? Math.abs((-u - b.translate) / b.velocity) : Math.abs((u - b.translate) / b.velocity); + else if (b.params.freeModeSticky) return void b.slideReset(); + b.params.freeModeMomentumBounce && m ? (b.updateProgress(c), b.setWrapperTransition(p), b.setWrapperTranslate(u), b.onTransitionStart(), b.animating = !0, b.wrapper.transitionEnd(function() { + b && B && (b.emit("onMomentumBounce", b), b.setWrapperTransition(b.params.speed), b.setWrapperTranslate(c), b.wrapper.transitionEnd(function() { + b && b.onTransitionEnd() + })) + })) : b.velocity ? (b.updateProgress(u), b.setWrapperTransition(p), b.setWrapperTranslate(u), b.onTransitionStart(), b.animating || (b.animating = !0, b.wrapper.transitionEnd(function() { + b && b.onTransitionEnd() + }))) : b.updateProgress(u), b.updateActiveIndex() + } + return void((!b.params.freeModeMomentum || r >= b.params.longSwipesMs) && (b.updateProgress(), b.updateActiveIndex())) + } + var v, w = 0, + y = b.slidesSizesGrid[0]; + for (v = 0; v < b.slidesGrid.length; v += b.params.slidesPerGroup) "undefined" != typeof b.slidesGrid[v + b.params.slidesPerGroup] ? i >= b.slidesGrid[v] && i < b.slidesGrid[v + b.params.slidesPerGroup] && (w = v, y = b.slidesGrid[v + b.params.slidesPerGroup] - b.slidesGrid[v]) : i >= b.slidesGrid[v] && (w = v, y = b.slidesGrid[b.slidesGrid.length - 1] - b.slidesGrid[b.slidesGrid.length - 2]); + var x = (i - b.slidesGrid[w]) / y; + if (r > b.params.longSwipesMs) { + if (!b.params.longSwipes) return void b.slideTo(b.activeIndex); + "next" === b.swipeDirection && (x >= b.params.longSwipesRatio ? b.slideTo(w + b.params.slidesPerGroup) : b.slideTo(w)), "prev" === b.swipeDirection && (x > 1 - b.params.longSwipesRatio ? b.slideTo(w + b.params.slidesPerGroup) : b.slideTo(w)) + } else { + if (!b.params.shortSwipes) return void b.slideTo(b.activeIndex); + "next" === b.swipeDirection && b.slideTo(w + b.params.slidesPerGroup), "prev" === b.swipeDirection && b.slideTo(w) + } + } + }, b._slideTo = function(e, a) { + return b.slideTo(e, a, !0, !0) + }, b.slideTo = function(e, a, t, r) { + "undefined" == typeof t && (t = !0), "undefined" == typeof e && (e = 0), 0 > e && (e = 0), b.snapIndex = Math.floor(e / b.params.slidesPerGroup), b.snapIndex >= b.snapGrid.length && (b.snapIndex = b.snapGrid.length - 1); + var i = -b.snapGrid[b.snapIndex]; + b.params.autoplay && b.autoplaying && (r || !b.params.autoplayDisableOnInteraction ? b.pauseAutoplay(a) : b.stopAutoplay()), b.updateProgress(i); + for (var s = 0; s < b.slidesGrid.length; s++) - Math.floor(100 * i) >= Math.floor(100 * b.slidesGrid[s]) && (e = s); + return !b.params.allowSwipeToNext && i < b.translate && i < b.minTranslate() ? !1 : !b.params.allowSwipeToPrev && i > b.translate && i > b.maxTranslate() && (b.activeIndex || 0) !== e ? !1 : ("undefined" == typeof a && (a = b.params.speed), b.previousIndex = b.activeIndex || 0, b.activeIndex = e, b.rtl && -i === b.translate || !b.rtl && i === b.translate ? (b.params.autoHeight && b.updateAutoHeight(), b.updateClasses(), "slide" !== b.params.effect && b.setWrapperTranslate(i), !1) : (b.updateClasses(), b.onTransitionStart(t), 0 === a ? (b.setWrapperTranslate(i), b.setWrapperTransition(0), b.onTransitionEnd(t)) : (b.setWrapperTranslate(i), b.setWrapperTransition(a), b.animating || (b.animating = !0, b.wrapper.transitionEnd(function() { + b && b.onTransitionEnd(t) + }))), !0)) + }, b.onTransitionStart = function(e) { + "undefined" == typeof e && (e = !0), b.params.autoHeight && b.updateAutoHeight(), b.lazy && b.lazy.onTransitionStart(), e && (b.emit("onTransitionStart", b), b.activeIndex !== b.previousIndex && (b.emit("onSlideChangeStart", b), b.activeIndex > b.previousIndex ? b.emit("onSlideNextStart", b) : b.emit("onSlidePrevStart", b))) + }, b.onTransitionEnd = function(e) { + b.animating = !1, b.setWrapperTransition(0), "undefined" == typeof e && (e = !0), b.lazy && b.lazy.onTransitionEnd(), e && (b.emit("onTransitionEnd", b), b.activeIndex !== b.previousIndex && (b.emit("onSlideChangeEnd", b), b.activeIndex > b.previousIndex ? b.emit("onSlideNextEnd", b) : b.emit("onSlidePrevEnd", b))), b.params.hashnav && b.hashnav && b.hashnav.setHash() + }, b.slideNext = function(e, a, t) { + if (b.params.loop) { + if (b.animating) return !1; + b.fixLoop(); + b.container[0].clientLeft; + return b.slideTo(b.activeIndex + b.params.slidesPerGroup, a, e, t) + } + return b.slideTo(b.activeIndex + b.params.slidesPerGroup, a, e, t) + }, b._slideNext = function(e) { + return b.slideNext(!0, e, !0) + }, b.slidePrev = function(e, a, t) { + if (b.params.loop) { + if (b.animating) return !1; + b.fixLoop(); + b.container[0].clientLeft; + return b.slideTo(b.activeIndex - 1, a, e, t) + } + return b.slideTo(b.activeIndex - 1, a, e, t) + }, b._slidePrev = function(e) { + return b.slidePrev(!0, e, !0) + }, b.slideReset = function(e, a, t) { + return b.slideTo(b.activeIndex, a, e) + }, b.setWrapperTransition = function(e, a) { + b.wrapper.transition(e), "slide" !== b.params.effect && b.effects[b.params.effect] && b.effects[b.params.effect].setTransition(e), b.params.parallax && b.parallax && b.parallax.setTransition(e), b.params.scrollbar && b.scrollbar && b.scrollbar.setTransition(e), b.params.control && b.controller && b.controller.setTransition(e, a), b.emit("onSetTransition", b, e) + }, b.setWrapperTranslate = function(e, a, t) { + var r = 0, + i = 0, + n = 0; + b.isHorizontal() ? r = b.rtl ? -e : e : i = e, b.params.roundLengths && (r = s(r), i = s(i)), b.params.virtualTranslate || (b.support.transforms3d ? b.wrapper.transform("translate3d(" + r + "px, " + i + "px, " + n + "px)") : b.wrapper.transform("translate(" + r + "px, " + i + "px)")), b.translate = b.isHorizontal() ? r : i; + var o, l = b.maxTranslate() - b.minTranslate(); + o = 0 === l ? 0 : (e - b.minTranslate()) / l, o !== b.progress && b.updateProgress(e), a && b.updateActiveIndex(), "slide" !== b.params.effect && b.effects[b.params.effect] && b.effects[b.params.effect].setTranslate(b.translate), b.params.parallax && b.parallax && b.parallax.setTranslate(b.translate), b.params.scrollbar && b.scrollbar && b.scrollbar.setTranslate(b.translate), b.params.control && b.controller && b.controller.setTranslate(b.translate, t), b.emit("onSetTranslate", b, b.translate) + }, b.getTranslate = function(e, a) { + var t, r, i, s; + return "undefined" == typeof a && (a = "x"), b.params.virtualTranslate ? b.rtl ? -b.translate : b.translate : (i = window.getComputedStyle(e, null), window.WebKitCSSMatrix ? (r = i.transform || i.webkitTransform, r.split(",").length > 6 && (r = r.split(", ").map(function(e) { + return e.replace(",", ".") + }).join(", ")), s = new window.WebKitCSSMatrix("none" === r ? "" : r)) : (s = i.MozTransform || i.OTransform || i.MsTransform || i.msTransform || i.transform || i.getPropertyValue("transform").replace("translate(", "matrix(1, 0, 0, 1,"), t = s.toString().split(",")), "x" === a && (r = window.WebKitCSSMatrix ? s.m41 : 16 === t.length ? parseFloat(t[12]) : parseFloat(t[4])), "y" === a && (r = window.WebKitCSSMatrix ? s.m42 : 16 === t.length ? parseFloat(t[13]) : parseFloat(t[5])), b.rtl && r && (r = -r), r || 0) + }, b.getWrapperTranslate = function(e) { + return "undefined" == typeof e && (e = b.isHorizontal() ? "x" : "y"), b.getTranslate(b.wrapper[0], e) + }, b.observers = [], b.initObservers = function() { + if (b.params.observeParents) + for (var e = b.container.parents(), a = 0; a < e.length; a++) l(e[a]); + l(b.container[0], { + childList: !1 + }), l(b.wrapper[0], { + attributes: !1 + }) + }, b.disconnectObservers = function() { + for (var e = 0; e < b.observers.length; e++) b.observers[e].disconnect(); + b.observers = [] + }, b.createLoop = function() { + b.wrapper.children("." + b.params.slideClass + "." + b.params.slideDuplicateClass).remove(); + var e = b.wrapper.children("." + b.params.slideClass); + "auto" !== b.params.slidesPerView || b.params.loopedSlides || (b.params.loopedSlides = e.length), b.loopedSlides = parseInt(b.params.loopedSlides || b.params.slidesPerView, 10), b.loopedSlides = b.loopedSlides + b.params.loopAdditionalSlides, b.loopedSlides > e.length && (b.loopedSlides = e.length); + var t, r = [], + i = []; + for (e.each(function(t, s) { + var n = a(this); + t < b.loopedSlides && i.push(s), t < e.length && t >= e.length - b.loopedSlides && r.push(s), n.attr("data-swiper-slide-index", t) + }), t = 0; t < i.length; t++) b.wrapper.append(a(i[t].cloneNode(!0)).addClass(b.params.slideDuplicateClass)); + for (t = r.length - 1; t >= 0; t--) b.wrapper.prepend(a(r[t].cloneNode(!0)).addClass(b.params.slideDuplicateClass)) + }, b.destroyLoop = function() { + b.wrapper.children("." + b.params.slideClass + "." + b.params.slideDuplicateClass).remove(), b.slides.removeAttr("data-swiper-slide-index") + }, b.reLoop = function(e) { + var a = b.activeIndex - b.loopedSlides; + b.destroyLoop(), b.createLoop(), b.updateSlidesSize(), e && b.slideTo(a + b.loopedSlides, 0, !1) + }, b.fixLoop = function() { + var e; + b.activeIndex < b.loopedSlides ? (e = b.slides.length - 3 * b.loopedSlides + b.activeIndex, e += b.loopedSlides, b.slideTo(e, 0, !1, !0)) : ("auto" === b.params.slidesPerView && b.activeIndex >= 2 * b.loopedSlides || b.activeIndex > b.slides.length - 2 * b.params.slidesPerView) && (e = -b.slides.length + b.activeIndex + b.loopedSlides, e += b.loopedSlides, b.slideTo(e, 0, !1, !0)) + }, b.appendSlide = function(e) { + if (b.params.loop && b.destroyLoop(), "object" == typeof e && e.length) + for (var a = 0; a < e.length; a++) e[a] && b.wrapper.append(e[a]); + else b.wrapper.append(e); + b.params.loop && b.createLoop(), b.params.observer && b.support.observer || b.update(!0) + }, b.prependSlide = function(e) { + b.params.loop && b.destroyLoop(); + var a = b.activeIndex + 1; + if ("object" == typeof e && e.length) { + for (var t = 0; t < e.length; t++) e[t] && b.wrapper.prepend(e[t]); + a = b.activeIndex + e.length + } else b.wrapper.prepend(e); + b.params.loop && b.createLoop(), b.params.observer && b.support.observer || b.update(!0), b.slideTo(a, 0, !1) + }, b.removeSlide = function(e) { + b.params.loop && (b.destroyLoop(), b.slides = b.wrapper.children("." + b.params.slideClass)); + var a, t = b.activeIndex; + if ("object" == typeof e && e.length) { + for (var r = 0; r < e.length; r++) a = e[r], b.slides[a] && b.slides.eq(a).remove(), t > a && t--; + t = Math.max(t, 0) + } else a = e, b.slides[a] && b.slides.eq(a).remove(), t > a && t--, t = Math.max(t, 0); + b.params.loop && b.createLoop(), b.params.observer && b.support.observer || b.update(!0), b.params.loop ? b.slideTo(t + b.loopedSlides, 0, !1) : b.slideTo(t, 0, !1) + }, b.removeAllSlides = function() { + for (var e = [], a = 0; a < b.slides.length; a++) e.push(a); + b.removeSlide(e) + }, b.effects = { + fade: { + setTranslate: function() { + for (var e = 0; e < b.slides.length; e++) { + var a = b.slides.eq(e), + t = a[0].swiperSlideOffset, + r = -t; + b.params.virtualTranslate || (r -= b.translate); + var i = 0; + b.isHorizontal() || (i = r, r = 0); + var s = b.params.fade.crossFade ? Math.max(1 - Math.abs(a[0].progress), 0) : 1 + Math.min(Math.max(a[0].progress, -1), 0); + a.css({ + opacity: s + }).transform("translate3d(" + r + "px, " + i + "px, 0px)") + } + }, + setTransition: function(e) { + if (b.slides.transition(e), b.params.virtualTranslate && 0 !== e) { + var a = !1; + b.slides.transitionEnd(function() { + if (!a && b) { + a = !0, b.animating = !1; + for (var e = ["webkitTransitionEnd", "transitionend", "oTransitionEnd", "MSTransitionEnd", "msTransitionEnd"], t = 0; t < e.length; t++) b.wrapper.trigger(e[t]) + } + }) + } + } + }, + flip: { + setTranslate: function() { + for (var e = 0; e < b.slides.length; e++) { + var t = b.slides.eq(e), + r = t[0].progress; + b.params.flip.limitRotation && (r = Math.max(Math.min(t[0].progress, 1), -1)); + var i = t[0].swiperSlideOffset, + s = -180 * r, + n = s, + o = 0, + l = -i, + p = 0; + if (b.isHorizontal() ? b.rtl && (n = -n) : (p = l, l = 0, o = -n, n = 0), t[0].style.zIndex = -Math.abs(Math.round(r)) + b.slides.length, b.params.flip.slideShadows) { + var d = b.isHorizontal() ? t.find(".swiper-slide-shadow-left") : t.find(".swiper-slide-shadow-top"), + u = b.isHorizontal() ? t.find(".swiper-slide-shadow-right") : t.find(".swiper-slide-shadow-bottom"); + 0 === d.length && (d = a('
'), t.append(d)), 0 === u.length && (u = a('
'), t.append(u)), d.length && (d[0].style.opacity = Math.max(-r, 0)), u.length && (u[0].style.opacity = Math.max(r, 0)) + } + t.transform("translate3d(" + l + "px, " + p + "px, 0px) rotateX(" + o + "deg) rotateY(" + n + "deg)") + } + }, + setTransition: function(e) { + if (b.slides.transition(e).find(".swiper-slide-shadow-top, .swiper-slide-shadow-right, .swiper-slide-shadow-bottom, .swiper-slide-shadow-left").transition(e), b.params.virtualTranslate && 0 !== e) { + var t = !1; + b.slides.eq(b.activeIndex).transitionEnd(function() { + if (!t && b && a(this).hasClass(b.params.slideActiveClass)) { + t = !0, b.animating = !1; + for (var e = ["webkitTransitionEnd", "transitionend", "oTransitionEnd", "MSTransitionEnd", "msTransitionEnd"], r = 0; r < e.length; r++) b.wrapper.trigger(e[r]) + } + }) + } + } + }, + cube: { + setTranslate: function() { + var e, t = 0; + b.params.cube.shadow && (b.isHorizontal() ? (e = b.wrapper.find(".swiper-cube-shadow"), 0 === e.length && (e = a('
'), b.wrapper.append(e)), e.css({ + height: b.width + "px" + })) : (e = b.container.find(".swiper-cube-shadow"), 0 === e.length && (e = a('
'), b.container.append(e)))); + for (var r = 0; r < b.slides.length; r++) { + var i = b.slides.eq(r), + s = 90 * r, + n = Math.floor(s / 360); + b.rtl && (s = -s, n = Math.floor(-s / 360)); + var o = Math.max(Math.min(i[0].progress, 1), -1), + l = 0, + p = 0, + d = 0; + r % 4 === 0 ? (l = 4 * -n * b.size, d = 0) : (r - 1) % 4 === 0 ? (l = 0, d = 4 * -n * b.size) : (r - 2) % 4 === 0 ? (l = b.size + 4 * n * b.size, d = b.size) : (r - 3) % 4 === 0 && (l = -b.size, d = 3 * b.size + 4 * b.size * n), b.rtl && (l = -l), b.isHorizontal() || (p = l, l = 0); + var u = "rotateX(" + (b.isHorizontal() ? 0 : -s) + "deg) rotateY(" + (b.isHorizontal() ? s : 0) + "deg) translate3d(" + l + "px, " + p + "px, " + d + "px)"; + if (1 >= o && o > -1 && (t = 90 * r + 90 * o, b.rtl && (t = 90 * -r - 90 * o)), i.transform(u), b.params.cube.slideShadows) { + var c = b.isHorizontal() ? i.find(".swiper-slide-shadow-left") : i.find(".swiper-slide-shadow-top"), + m = b.isHorizontal() ? i.find(".swiper-slide-shadow-right") : i.find(".swiper-slide-shadow-bottom"); + 0 === c.length && (c = a('
'), i.append(c)), 0 === m.length && (m = a('
'), i.append(m)), c.length && (c[0].style.opacity = Math.max(-o, 0)), m.length && (m[0].style.opacity = Math.max(o, 0)) + } + } + if (b.wrapper.css({ + "-webkit-transform-origin": "50% 50% -" + b.size / 2 + "px", + "-moz-transform-origin": "50% 50% -" + b.size / 2 + "px", + "-ms-transform-origin": "50% 50% -" + b.size / 2 + "px", + "transform-origin": "50% 50% -" + b.size / 2 + "px" + }), b.params.cube.shadow) + if (b.isHorizontal()) e.transform("translate3d(0px, " + (b.width / 2 + b.params.cube.shadowOffset) + "px, " + -b.width / 2 + "px) rotateX(90deg) rotateZ(0deg) scale(" + b.params.cube.shadowScale + ")"); + else { + var h = Math.abs(t) - 90 * Math.floor(Math.abs(t) / 90), + f = 1.5 - (Math.sin(2 * h * Math.PI / 360) / 2 + Math.cos(2 * h * Math.PI / 360) / 2), + g = b.params.cube.shadowScale, + v = b.params.cube.shadowScale / f, + w = b.params.cube.shadowOffset; + e.transform("scale3d(" + g + ", 1, " + v + ") translate3d(0px, " + (b.height / 2 + w) + "px, " + -b.height / 2 / v + "px) rotateX(-90deg)") + } var y = b.isSafari || b.isUiWebView ? -b.size / 2 : 0; + b.wrapper.transform("translate3d(0px,0," + y + "px) rotateX(" + (b.isHorizontal() ? 0 : t) + "deg) rotateY(" + (b.isHorizontal() ? -t : 0) + "deg)") + }, + setTransition: function(e) { + b.slides.transition(e).find(".swiper-slide-shadow-top, .swiper-slide-shadow-right, .swiper-slide-shadow-bottom, .swiper-slide-shadow-left").transition(e), b.params.cube.shadow && !b.isHorizontal() && b.container.find(".swiper-cube-shadow").transition(e) + } + }, + coverflow: { + setTranslate: function() { + for (var e = b.translate, t = b.isHorizontal() ? -e + b.width / 2 : -e + b.height / 2, r = b.isHorizontal() ? b.params.coverflow.rotate : -b.params.coverflow.rotate, i = b.params.coverflow.depth, s = 0, n = b.slides.length; n > s; s++) { + var o = b.slides.eq(s), + l = b.slidesSizesGrid[s], + p = o[0].swiperSlideOffset, + d = (t - p - l / 2) / l * b.params.coverflow.modifier, + u = b.isHorizontal() ? r * d : 0, + c = b.isHorizontal() ? 0 : r * d, + m = -i * Math.abs(d), + h = b.isHorizontal() ? 0 : b.params.coverflow.stretch * d, + f = b.isHorizontal() ? b.params.coverflow.stretch * d : 0; + Math.abs(f) < .001 && (f = 0), Math.abs(h) < .001 && (h = 0), Math.abs(m) < .001 && (m = 0), Math.abs(u) < .001 && (u = 0), Math.abs(c) < .001 && (c = 0); + var g = "translate3d(" + f + "px," + h + "px," + m + "px) rotateX(" + c + "deg) rotateY(" + u + "deg)"; + if (o.transform(g), o[0].style.zIndex = -Math.abs(Math.round(d)) + 1, b.params.coverflow.slideShadows) { + var v = b.isHorizontal() ? o.find(".swiper-slide-shadow-left") : o.find(".swiper-slide-shadow-top"), + w = b.isHorizontal() ? o.find(".swiper-slide-shadow-right") : o.find(".swiper-slide-shadow-bottom"); + 0 === v.length && (v = a('
'), o.append(v)), 0 === w.length && (w = a('
'), o.append(w)), v.length && (v[0].style.opacity = d > 0 ? d : 0), w.length && (w[0].style.opacity = -d > 0 ? -d : 0) + } + } + if (b.browser.ie) { + var y = b.wrapper[0].style; + y.perspectiveOrigin = t + "px 50%" + } + }, + setTransition: function(e) { + b.slides.transition(e).find(".swiper-slide-shadow-top, .swiper-slide-shadow-right, .swiper-slide-shadow-bottom, .swiper-slide-shadow-left").transition(e) + } + } + }, b.lazy = { + initialImageLoaded: !1, + loadImageInSlide: function(e, t) { + if ("undefined" != typeof e && ("undefined" == typeof t && (t = !0), 0 !== b.slides.length)) { + var r = b.slides.eq(e), + i = r.find(".swiper-lazy:not(.swiper-lazy-loaded):not(.swiper-lazy-loading)"); + !r.hasClass("swiper-lazy") || r.hasClass("swiper-lazy-loaded") || r.hasClass("swiper-lazy-loading") || (i = i.add(r[0])), 0 !== i.length && i.each(function() { + var e = a(this); + e.addClass("swiper-lazy-loading"); + var i = e.attr("data-background"), + s = e.attr("data-src"), + n = e.attr("data-srcset"); + b.loadImage(e[0], s || i, n, !1, function() { + if (i ? (e.css("background-image", 'url("' + i + '")'), e.removeAttr("data-background")) : (n && (e.attr("srcset", n), e.removeAttr("data-srcset")), s && (e.attr("src", s), e.removeAttr("data-src"))), e.addClass("swiper-lazy-loaded").removeClass("swiper-lazy-loading"), r.find(".swiper-lazy-preloader, .preloader").remove(), b.params.loop && t) { + var a = r.attr("data-swiper-slide-index"); + if (r.hasClass(b.params.slideDuplicateClass)) { + var o = b.wrapper.children('[data-swiper-slide-index="' + a + '"]:not(.' + b.params.slideDuplicateClass + ")"); + b.lazy.loadImageInSlide(o.index(), !1) + } else { + var l = b.wrapper.children("." + b.params.slideDuplicateClass + '[data-swiper-slide-index="' + a + '"]'); + b.lazy.loadImageInSlide(l.index(), !1) + } + } + b.emit("onLazyImageReady", b, r[0], e[0]) + }), b.emit("onLazyImageLoad", b, r[0], e[0]) + }) + } + }, + load: function() { + var e; + if (b.params.watchSlidesVisibility) b.wrapper.children("." + b.params.slideVisibleClass).each(function() { + b.lazy.loadImageInSlide(a(this).index()) + }); + else if (b.params.slidesPerView > 1) + for (e = b.activeIndex; e < b.activeIndex + b.params.slidesPerView; e++) b.slides[e] && b.lazy.loadImageInSlide(e); + else b.lazy.loadImageInSlide(b.activeIndex); + if (b.params.lazyLoadingInPrevNext) + if (b.params.slidesPerView > 1 || b.params.lazyLoadingInPrevNextAmount && b.params.lazyLoadingInPrevNextAmount > 1) { + var t = b.params.lazyLoadingInPrevNextAmount, + r = b.params.slidesPerView, + i = Math.min(b.activeIndex + r + Math.max(t, r), b.slides.length), + s = Math.max(b.activeIndex - Math.max(r, t), 0); + for (e = b.activeIndex + b.params.slidesPerView; i > e; e++) b.slides[e] && b.lazy.loadImageInSlide(e); + for (e = s; e < b.activeIndex; e++) b.slides[e] && b.lazy.loadImageInSlide(e) + } else { + var n = b.wrapper.children("." + b.params.slideNextClass); + n.length > 0 && b.lazy.loadImageInSlide(n.index()); + var o = b.wrapper.children("." + b.params.slidePrevClass); + o.length > 0 && b.lazy.loadImageInSlide(o.index()) + } + }, + onTransitionStart: function() { + b.params.lazyLoading && (b.params.lazyLoadingOnTransitionStart || !b.params.lazyLoadingOnTransitionStart && !b.lazy.initialImageLoaded) && b.lazy.load() + }, + onTransitionEnd: function() { + b.params.lazyLoading && !b.params.lazyLoadingOnTransitionStart && b.lazy.load() + } + }, b.scrollbar = { + isTouched: !1, + setDragPosition: function(e) { + var a = b.scrollbar, + t = b.isHorizontal() ? "touchstart" === e.type || "touchmove" === e.type ? e.targetTouches[0].pageX : e.pageX || e.clientX : "touchstart" === e.type || "touchmove" === e.type ? e.targetTouches[0].pageY : e.pageY || e.clientY, + r = t - a.track.offset()[b.isHorizontal() ? "left" : "top"] - a.dragSize / 2, + i = -b.minTranslate() * a.moveDivider, + s = -b.maxTranslate() * a.moveDivider; + i > r ? r = i : r > s && (r = s), r = -r / a.moveDivider, b.updateProgress(r), b.setWrapperTranslate(r, !0) + }, + dragStart: function(e) { + var a = b.scrollbar; + a.isTouched = !0, e.preventDefault(), e.stopPropagation(), a.setDragPosition(e), clearTimeout(a.dragTimeout), a.track.transition(0), b.params.scrollbarHide && a.track.css("opacity", 1), b.wrapper.transition(100), a.drag.transition(100), b.emit("onScrollbarDragStart", b) + }, + dragMove: function(e) { + var a = b.scrollbar; + a.isTouched && (e.preventDefault ? e.preventDefault() : e.returnValue = !1, a.setDragPosition(e), b.wrapper.transition(0), a.track.transition(0), a.drag.transition(0), b.emit("onScrollbarDragMove", b)) + }, + dragEnd: function(e) { + var a = b.scrollbar; + a.isTouched && (a.isTouched = !1, b.params.scrollbarHide && (clearTimeout(a.dragTimeout), a.dragTimeout = setTimeout(function() { + a.track.css("opacity", 0), a.track.transition(400) + }, 1e3)), b.emit("onScrollbarDragEnd", b), b.params.scrollbarSnapOnRelease && b.slideReset()) + }, + enableDraggable: function() { + var e = b.scrollbar, + t = b.support.touch ? e.track : document; + a(e.track).on(b.touchEvents.start, e.dragStart), a(t).on(b.touchEvents.move, e.dragMove), a(t).on(b.touchEvents.end, e.dragEnd) + }, + disableDraggable: function() { + var e = b.scrollbar, + t = b.support.touch ? e.track : document; + a(e.track).off(b.touchEvents.start, e.dragStart), a(t).off(b.touchEvents.move, e.dragMove), a(t).off(b.touchEvents.end, e.dragEnd) + }, + set: function() { + if (b.params.scrollbar) { + var e = b.scrollbar; + e.track = a(b.params.scrollbar), b.params.uniqueNavElements && "string" == typeof b.params.scrollbar && e.track.length > 1 && 1 === b.container.find(b.params.scrollbar).length && (e.track = b.container.find(b.params.scrollbar)), e.drag = e.track.find(".swiper-scrollbar-drag"), 0 === e.drag.length && (e.drag = a('
'), e.track.append(e.drag)), e.drag[0].style.width = "", e.drag[0].style.height = "", e.trackSize = b.isHorizontal() ? e.track[0].offsetWidth : e.track[0].offsetHeight, e.divider = b.size / b.virtualSize, e.moveDivider = e.divider * (e.trackSize / b.size), e.dragSize = e.trackSize * e.divider, b.isHorizontal() ? e.drag[0].style.width = e.dragSize + "px" : e.drag[0].style.height = e.dragSize + "px", e.divider >= 1 ? e.track[0].style.display = "none" : e.track[0].style.display = "", b.params.scrollbarHide && (e.track[0].style.opacity = 0) + } + }, + setTranslate: function() { + if (b.params.scrollbar) { + var e, a = b.scrollbar, + t = (b.translate || 0, a.dragSize); + e = (a.trackSize - a.dragSize) * b.progress, b.rtl && b.isHorizontal() ? (e = -e, e > 0 ? (t = a.dragSize - e, e = 0) : -e + a.dragSize > a.trackSize && (t = a.trackSize + e)) : 0 > e ? (t = a.dragSize + e, e = 0) : e + a.dragSize > a.trackSize && (t = a.trackSize - e), b.isHorizontal() ? (b.support.transforms3d ? a.drag.transform("translate3d(" + e + "px, 0, 0)") : a.drag.transform("translateX(" + e + "px)"), a.drag[0].style.width = t + "px") : (b.support.transforms3d ? a.drag.transform("translate3d(0px, " + e + "px, 0)") : a.drag.transform("translateY(" + e + "px)"), a.drag[0].style.height = t + "px"), b.params.scrollbarHide && (clearTimeout(a.timeout), a.track[0].style.opacity = 1, a.timeout = setTimeout(function() { + a.track[0].style.opacity = 0, a.track.transition(400) + }, 1e3)) + } + }, + setTransition: function(e) { + b.params.scrollbar && b.scrollbar.drag.transition(e) + } + }, b.controller = { + LinearSpline: function(e, a) { + this.x = e, this.y = a, this.lastIndex = e.length - 1; + var t, r; + this.x.length; + this.interpolate = function(e) { + return e ? (r = i(this.x, e), t = r - 1, (e - this.x[t]) * (this.y[r] - this.y[t]) / (this.x[r] - this.x[t]) + this.y[t]) : 0 + }; + var i = function() { + var e, a, t; + return function(r, i) { + for (a = -1, e = r.length; e - a > 1;) r[t = e + a >> 1] <= i ? a = t : e = t; + return e + } + }() + }, + getInterpolateFunction: function(e) { + b.controller.spline || (b.controller.spline = b.params.loop ? new b.controller.LinearSpline(b.slidesGrid, e.slidesGrid) : new b.controller.LinearSpline(b.snapGrid, e.snapGrid)) + }, + setTranslate: function(e, a) { + function r(a) { + e = a.rtl && "horizontal" === a.params.direction ? -b.translate : b.translate, "slide" === b.params.controlBy && (b.controller.getInterpolateFunction(a), s = -b.controller.spline.interpolate(-e)), s && "container" !== b.params.controlBy || (i = (a.maxTranslate() - a.minTranslate()) / (b.maxTranslate() - b.minTranslate()), s = (e - b.minTranslate()) * i + a.minTranslate()), b.params.controlInverse && (s = a.maxTranslate() - s), a.updateProgress(s), a.setWrapperTranslate(s, !1, b), a.updateActiveIndex() + } + var i, s, n = b.params.control; + if (b.isArray(n)) + for (var o = 0; o < n.length; o++) n[o] !== a && n[o] instanceof t && r(n[o]); + else n instanceof t && a !== n && r(n) + }, + setTransition: function(e, a) { + function r(a) { + a.setWrapperTransition(e, b), 0 !== e && (a.onTransitionStart(), a.wrapper.transitionEnd(function() { + s && (a.params.loop && "slide" === b.params.controlBy && a.fixLoop(), a.onTransitionEnd()) + })) + } + var i, s = b.params.control; + if (b.isArray(s)) + for (i = 0; i < s.length; i++) s[i] !== a && s[i] instanceof t && r(s[i]); + else s instanceof t && a !== s && r(s) + } + }, b.hashnav = { + init: function() { + if (b.params.hashnav) { + b.hashnav.initialized = !0; + var e = document.location.hash.replace("#", ""); + if (e) + for (var a = 0, t = 0, r = b.slides.length; r > t; t++) { + var i = b.slides.eq(t), + s = i.attr("data-hash"); + if (s === e && !i.hasClass(b.params.slideDuplicateClass)) { + var n = i.index(); + b.slideTo(n, a, b.params.runCallbacksOnInit, !0) + } + } + } + }, + setHash: function() { + b.hashnav.initialized && b.params.hashnav && (document.location.hash = b.slides.eq(b.activeIndex).attr("data-hash") || "") + } + }, b.disableKeyboardControl = function() { + b.params.keyboardControl = !1, a(document).off("keydown", p) + }, b.enableKeyboardControl = function() { + b.params.keyboardControl = !0, a(document).on("keydown", p) + }, b.mousewheel = { + event: !1, + lastScrollTime: (new window.Date).getTime() + }, b.params.mousewheelControl) { + try { + new window.WheelEvent("wheel"), b.mousewheel.event = "wheel" + } catch (N) { + (window.WheelEvent || b.container[0] && "wheel" in b.container[0]) && (b.mousewheel.event = "wheel") + }!b.mousewheel.event && window.WheelEvent, b.mousewheel.event || void 0 === document.onmousewheel || (b.mousewheel.event = "mousewheel"), b.mousewheel.event || (b.mousewheel.event = "DOMMouseScroll") + } + b.disableMousewheelControl = function() { + return b.mousewheel.event ? (b.container.off(b.mousewheel.event, d), !0) : !1 + }, b.enableMousewheelControl = function() { + return b.mousewheel.event ? (b.container.on(b.mousewheel.event, d), !0) : !1 + }, b.parallax = { + setTranslate: function() { + b.container.children("[data-swiper-parallax], [data-swiper-parallax-x], [data-swiper-parallax-y]").each(function() { + u(this, b.progress) + }), b.slides.each(function() { + var e = a(this); + e.find("[data-swiper-parallax], [data-swiper-parallax-x], [data-swiper-parallax-y]").each(function() { + var a = Math.min(Math.max(e[0].progress, -1), 1); + u(this, a) + }) + }) + }, + setTransition: function(e) { + "undefined" == typeof e && (e = b.params.speed), b.container.find("[data-swiper-parallax], [data-swiper-parallax-x], [data-swiper-parallax-y]").each(function() { + var t = a(this), + r = parseInt(t.attr("data-swiper-parallax-duration"), 10) || e; + 0 === e && (r = 0), t.transition(r) + }) + } + }, b._plugins = []; + for (var R in b.plugins) { + var W = b.plugins[R](b, b.params[R]); + W && b._plugins.push(W) + } + return b.callPlugins = function(e) { + for (var a = 0; a < b._plugins.length; a++) e in b._plugins[a] && b._plugins[a][e](arguments[1], arguments[2], arguments[3], arguments[4], arguments[5]) + }, b.emitterEventListeners = {}, b.emit = function(e) { + b.params[e] && b.params[e](arguments[1], arguments[2], arguments[3], arguments[4], arguments[5]); + var a; + if (b.emitterEventListeners[e]) + for (a = 0; a < b.emitterEventListeners[e].length; a++) b.emitterEventListeners[e][a](arguments[1], arguments[2], arguments[3], arguments[4], arguments[5]); + b.callPlugins && b.callPlugins(e, arguments[1], arguments[2], arguments[3], arguments[4], arguments[5]) + }, b.on = function(e, a) { + return e = c(e), b.emitterEventListeners[e] || (b.emitterEventListeners[e] = []), b.emitterEventListeners[e].push(a), b + }, b.off = function(e, a) { + var t; + if (e = c(e), "undefined" == typeof a) return b.emitterEventListeners[e] = [], b; + if (b.emitterEventListeners[e] && 0 !== b.emitterEventListeners[e].length) { + for (t = 0; t < b.emitterEventListeners[e].length; t++) b.emitterEventListeners[e][t] === a && b.emitterEventListeners[e].splice(t, 1); + return b + } + }, b.once = function(e, a) { + e = c(e); + var t = function() { + a(arguments[0], arguments[1], arguments[2], arguments[3], arguments[4]), b.off(e, t) + }; + return b.on(e, t), b + }, b.a11y = { + makeFocusable: function(e) { + return e.attr("tabIndex", "0"), e + }, + addRole: function(e, a) { + return e.attr("role", a), e + }, + addLabel: function(e, a) { + return e.attr("aria-label", a), e + }, + disable: function(e) { + return e.attr("aria-disabled", !0), e + }, + enable: function(e) { + return e.attr("aria-disabled", !1), e + }, + onEnterKey: function(e) { + 13 === e.keyCode && (a(e.target).is(b.params.nextButton) ? (b.onClickNext(e), b.isEnd ? b.a11y.notify(b.params.lastSlideMessage) : b.a11y.notify(b.params.nextSlideMessage)) : a(e.target).is(b.params.prevButton) && (b.onClickPrev(e), b.isBeginning ? b.a11y.notify(b.params.firstSlideMessage) : b.a11y.notify(b.params.prevSlideMessage)), a(e.target).is("." + b.params.bulletClass) && a(e.target)[0].click()) + }, + liveRegion: a(''), + notify: function(e) { + var a = b.a11y.liveRegion; + 0 !== a.length && (a.html(""), a.html(e)) + }, + init: function() { + b.params.nextButton && b.nextButton && b.nextButton.length > 0 && (b.a11y.makeFocusable(b.nextButton), b.a11y.addRole(b.nextButton, "button"), b.a11y.addLabel(b.nextButton, b.params.nextSlideMessage)), b.params.prevButton && b.prevButton && b.prevButton.length > 0 && (b.a11y.makeFocusable(b.prevButton), b.a11y.addRole(b.prevButton, "button"), b.a11y.addLabel(b.prevButton, b.params.prevSlideMessage)), a(b.container).append(b.a11y.liveRegion) + }, + initPagination: function() { + b.params.pagination && b.params.paginationClickable && b.bullets && b.bullets.length && b.bullets.each(function() { + var e = a(this); + b.a11y.makeFocusable(e), b.a11y.addRole(e, "button"), b.a11y.addLabel(e, b.params.paginationBulletMessage.replace(/{{index}}/, e.index() + 1)) + }) + }, + destroy: function() { + b.a11y.liveRegion && b.a11y.liveRegion.length > 0 && b.a11y.liveRegion.remove() + } + }, b.init = function() { + b.params.loop && b.createLoop(), b.updateContainerSize(), b.updateSlidesSize(), b.updatePagination(), b.params.scrollbar && b.scrollbar && (b.scrollbar.set(), b.params.scrollbarDraggable && b.scrollbar.enableDraggable()), "slide" !== b.params.effect && b.effects[b.params.effect] && (b.params.loop || b.updateProgress(), b.effects[b.params.effect].setTranslate()), b.params.loop ? b.slideTo(b.params.initialSlide + b.loopedSlides, 0, b.params.runCallbacksOnInit) : (b.slideTo(b.params.initialSlide, 0, b.params.runCallbacksOnInit), 0 === b.params.initialSlide && (b.parallax && b.params.parallax && b.parallax.setTranslate(), b.lazy && b.params.lazyLoading && (b.lazy.load(), b.lazy.initialImageLoaded = !0))), b.attachEvents(), b.params.observer && b.support.observer && b.initObservers(), b.params.preloadImages && !b.params.lazyLoading && b.preloadImages(), b.params.autoplay && b.startAutoplay(), b.params.keyboardControl && b.enableKeyboardControl && b.enableKeyboardControl(), b.params.mousewheelControl && b.enableMousewheelControl && b.enableMousewheelControl(), + b.params.hashnav && b.hashnav && b.hashnav.init(), b.params.a11y && b.a11y && b.a11y.init(), b.emit("onInit", b) + }, b.cleanupStyles = function() { + b.container.removeClass(b.classNames.join(" ")).removeAttr("style"), b.wrapper.removeAttr("style"), b.slides && b.slides.length && b.slides.removeClass([b.params.slideVisibleClass, b.params.slideActiveClass, b.params.slideNextClass, b.params.slidePrevClass].join(" ")).removeAttr("style").removeAttr("data-swiper-column").removeAttr("data-swiper-row"), b.paginationContainer && b.paginationContainer.length && b.paginationContainer.removeClass(b.params.paginationHiddenClass), b.bullets && b.bullets.length && b.bullets.removeClass(b.params.bulletActiveClass), b.params.prevButton && a(b.params.prevButton).removeClass(b.params.buttonDisabledClass), b.params.nextButton && a(b.params.nextButton).removeClass(b.params.buttonDisabledClass), b.params.scrollbar && b.scrollbar && (b.scrollbar.track && b.scrollbar.track.length && b.scrollbar.track.removeAttr("style"), b.scrollbar.drag && b.scrollbar.drag.length && b.scrollbar.drag.removeAttr("style")) + }, b.destroy = function(e, a) { + b.detachEvents(), b.stopAutoplay(), b.params.scrollbar && b.scrollbar && b.params.scrollbarDraggable && b.scrollbar.disableDraggable(), b.params.loop && b.destroyLoop(), a && b.cleanupStyles(), b.disconnectObservers(), b.params.keyboardControl && b.disableKeyboardControl && b.disableKeyboardControl(), b.params.mousewheelControl && b.disableMousewheelControl && b.disableMousewheelControl(), b.params.a11y && b.a11y && b.a11y.destroy(), b.emit("onDestroy"), e !== !1 && (b = null) + }, b.init(), b + } + }; + t.prototype = { + isSafari: function() { + var e = navigator.userAgent.toLowerCase(); + return e.indexOf("safari") >= 0 && e.indexOf("chrome") < 0 && e.indexOf("android") < 0 + }(), + isUiWebView: /(iPhone|iPod|iPad).*AppleWebKit(?!.*Safari)/i.test(navigator.userAgent), + isArray: function(e) { + return "[object Array]" === Object.prototype.toString.apply(e) + }, + browser: { + ie: window.navigator.pointerEnabled || window.navigator.msPointerEnabled, + ieTouch: window.navigator.msPointerEnabled && window.navigator.msMaxTouchPoints > 1 || window.navigator.pointerEnabled && window.navigator.maxTouchPoints > 1 + }, + device: function() { + var e = navigator.userAgent, + a = e.match(/(Android);?[\s\/]+([\d.]+)?/), + t = e.match(/(iPad).*OS\s([\d_]+)/), + r = e.match(/(iPod)(.*OS\s([\d_]+))?/), + i = !t && e.match(/(iPhone\sOS)\s([\d_]+)/); + return { + ios: t || i || r, + android: a + } + }(), + support: { + touch: window.Modernizr && Modernizr.touch === !0 || function() { + return !!("ontouchstart" in window || window.DocumentTouch && document instanceof DocumentTouch) + }(), + transforms3d: window.Modernizr && Modernizr.csstransforms3d === !0 || function() { + var e = document.createElement("div").style; + return "webkitPerspective" in e || "MozPerspective" in e || "OPerspective" in e || "MsPerspective" in e || "perspective" in e + }(), + flexbox: function() { + for (var e = document.createElement("div").style, a = "alignItems webkitAlignItems webkitBoxAlign msFlexAlign mozBoxAlign webkitFlexDirection msFlexDirection mozBoxDirection mozBoxOrient webkitBoxDirection webkitBoxOrient".split(" "), t = 0; t < a.length; t++) + if (a[t] in e) return !0 + }(), + observer: function() { + return "MutationObserver" in window || "WebkitMutationObserver" in window + }() + }, + plugins: {} + }; + for (var r = (function() { + var e = function(e) { + var a = this, + t = 0; + for (t = 0; t < e.length; t++) a[t] = e[t]; + return a.length = e.length, this + }, + a = function(a, t) { + var r = [], + i = 0; + if (a && !t && a instanceof e) return a; + if (a) + if ("string" == typeof a) { + var s, n, o = a.trim(); + if (o.indexOf("<") >= 0 && o.indexOf(">") >= 0) { + var l = "div"; + for (0 === o.indexOf(":~]/) ? (t || document).querySelectorAll(a) : [document.getElementById(a.split("#")[1])], i = 0; i < s.length; i++) s[i] && r.push(s[i]) + } else if (a.nodeType || a === window || a === document) r.push(a); + else if (a.length > 0 && a[0].nodeType) + for (i = 0; i < a.length; i++) r.push(a[i]); + return new e(r) + }; + return e.prototype = { + addClass: function(e) { + if ("undefined" == typeof e) return this; + for (var a = e.split(" "), t = 0; t < a.length; t++) + for (var r = 0; r < this.length; r++) this[r].classList.add(a[t]); + return this + }, + removeClass: function(e) { + for (var a = e.split(" "), t = 0; t < a.length; t++) + for (var r = 0; r < this.length; r++) this[r].classList.remove(a[t]); + return this + }, + hasClass: function(e) { + return this[0] ? this[0].classList.contains(e) : !1 + }, + toggleClass: function(e) { + for (var a = e.split(" "), t = 0; t < a.length; t++) + for (var r = 0; r < this.length; r++) this[r].classList.toggle(a[t]); + return this + }, + attr: function(e, a) { + if (1 === arguments.length && "string" == typeof e) return this[0] ? this[0].getAttribute(e) : void 0; + for (var t = 0; t < this.length; t++) + if (2 === arguments.length) this[t].setAttribute(e, a); + else + for (var r in e) this[t][r] = e[r], this[t].setAttribute(r, e[r]); + return this + }, + removeAttr: function(e) { + for (var a = 0; a < this.length; a++) this[a].removeAttribute(e); + return this + }, + data: function(e, a) { + if ("undefined" != typeof a) { + for (var t = 0; t < this.length; t++) { + var r = this[t]; + r.dom7ElementDataStorage || (r.dom7ElementDataStorage = {}), r.dom7ElementDataStorage[e] = a + } + return this + } + if (this[0]) { + var i = this[0].getAttribute("data-" + e); + return i ? i : this[0].dom7ElementDataStorage && e in this[0].dom7ElementDataStorage ? this[0].dom7ElementDataStorage[e] : void 0 + } + }, + transform: function(e) { + for (var a = 0; a < this.length; a++) { + var t = this[a].style; + t.webkitTransform = t.MsTransform = t.msTransform = t.MozTransform = t.OTransform = t.transform = e + } + return this + }, + transition: function(e) { + "string" != typeof e && (e += "ms"); + for (var a = 0; a < this.length; a++) { + var t = this[a].style; + t.webkitTransitionDuration = t.MsTransitionDuration = t.msTransitionDuration = t.MozTransitionDuration = t.OTransitionDuration = t.transitionDuration = e + } + return this + }, + on: function(e, t, r, i) { + function s(e) { + var i = e.target; + if (a(i).is(t)) r.call(i, e); + else + for (var s = a(i).parents(), n = 0; n < s.length; n++) a(s[n]).is(t) && r.call(s[n], e) + } + var n, o, l = e.split(" "); + for (n = 0; n < this.length; n++) + if ("function" == typeof t || t === !1) + for ("function" == typeof t && (r = arguments[1], i = arguments[2] || !1), o = 0; o < l.length; o++) this[n].addEventListener(l[o], r, i); + else + for (o = 0; o < l.length; o++) this[n].dom7LiveListeners || (this[n].dom7LiveListeners = []), this[n].dom7LiveListeners.push({ + listener: r, + liveListener: s + }), this[n].addEventListener(l[o], s, i); + return this + }, + off: function(e, a, t, r) { + for (var i = e.split(" "), s = 0; s < i.length; s++) + for (var n = 0; n < this.length; n++) + if ("function" == typeof a || a === !1) "function" == typeof a && (t = arguments[1], r = arguments[2] || !1), this[n].removeEventListener(i[s], t, r); + else if (this[n].dom7LiveListeners) + for (var o = 0; o < this[n].dom7LiveListeners.length; o++) this[n].dom7LiveListeners[o].listener === t && this[n].removeEventListener(i[s], this[n].dom7LiveListeners[o].liveListener, r); + return this + }, + once: function(e, a, t, r) { + function i(n) { + t(n), s.off(e, a, i, r) + } + var s = this; + "function" == typeof a && (a = !1, t = arguments[1], r = arguments[2]), s.on(e, a, i, r) + }, + trigger: function(e, a) { + for (var t = 0; t < this.length; t++) { + var r; + try { + r = new window.CustomEvent(e, { + detail: a, + bubbles: !0, + cancelable: !0 + }) + } catch (i) { + r = document.createEvent("Event"), r.initEvent(e, !0, !0), r.detail = a + } + this[t].dispatchEvent(r) + } + return this + }, + transitionEnd: function(e) { + function a(s) { + if (s.target === this) + for (e.call(this, s), t = 0; t < r.length; t++) i.off(r[t], a) + } + var t, r = ["webkitTransitionEnd", "transitionend", "oTransitionEnd", "MSTransitionEnd", "msTransitionEnd"], + i = this; + if (e) + for (t = 0; t < r.length; t++) i.on(r[t], a); + return this + }, + width: function() { + return this[0] === window ? window.innerWidth : this.length > 0 ? parseFloat(this.css("width")) : null + }, + outerWidth: function(e) { + return this.length > 0 ? e ? this[0].offsetWidth + parseFloat(this.css("margin-right")) + parseFloat(this.css("margin-left")) : this[0].offsetWidth : null + }, + height: function() { + return this[0] === window ? window.innerHeight : this.length > 0 ? parseFloat(this.css("height")) : null + }, + outerHeight: function(e) { + return this.length > 0 ? e ? this[0].offsetHeight + parseFloat(this.css("margin-top")) + parseFloat(this.css("margin-bottom")) : this[0].offsetHeight : null + }, + offset: function() { + if (this.length > 0) { + var e = this[0], + a = e.getBoundingClientRect(), + t = document.body, + r = e.clientTop || t.clientTop || 0, + i = e.clientLeft || t.clientLeft || 0, + s = window.pageYOffset || e.scrollTop, + n = window.pageXOffset || e.scrollLeft; + return { + top: a.top + s - r, + left: a.left + n - i + } + } + return null + }, + css: function(e, a) { + var t; + if (1 === arguments.length) { + if ("string" != typeof e) { + for (t = 0; t < this.length; t++) + for (var r in e) this[t].style[r] = e[r]; + return this + } + if (this[0]) return window.getComputedStyle(this[0], null).getPropertyValue(e) + } + if (2 === arguments.length && "string" == typeof e) { + for (t = 0; t < this.length; t++) this[t].style[e] = a; + return this + } + return this + }, + each: function(e) { + for (var a = 0; a < this.length; a++) e.call(this[a], a, this[a]); + return this + }, + html: function(e) { + if ("undefined" == typeof e) return this[0] ? this[0].innerHTML : void 0; + for (var a = 0; a < this.length; a++) this[a].innerHTML = e; + return this + }, + text: function(e) { + if ("undefined" == typeof e) return this[0] ? this[0].textContent.trim() : null; + for (var a = 0; a < this.length; a++) this[a].textContent = e; + return this + }, + is: function(t) { + if (!this[0]) return !1; + var r, i; + if ("string" == typeof t) { + var s = this[0]; + if (s === document) return t === document; + if (s === window) return t === window; + if (s.matches) return s.matches(t); + if (s.webkitMatchesSelector) return s.webkitMatchesSelector(t); + if (s.mozMatchesSelector) return s.mozMatchesSelector(t); + if (s.msMatchesSelector) return s.msMatchesSelector(t); + for (r = a(t), i = 0; i < r.length; i++) + if (r[i] === this[0]) return !0; + return !1 + } + if (t === document) return this[0] === document; + if (t === window) return this[0] === window; + if (t.nodeType || t instanceof e) { + for (r = t.nodeType ? [t] : t, i = 0; i < r.length; i++) + if (r[i] === this[0]) return !0; + return !1 + } + return !1 + }, + index: function() { + if (this[0]) { + for (var e = this[0], a = 0; null !== (e = e.previousSibling);) 1 === e.nodeType && a++; + return a + } + }, + eq: function(a) { + if ("undefined" == typeof a) return this; + var t, r = this.length; + return a > r - 1 ? new e([]) : 0 > a ? (t = r + a, new e(0 > t ? [] : [this[t]])) : new e([this[a]]) + }, + append: function(a) { + var t, r; + for (t = 0; t < this.length; t++) + if ("string" == typeof a) { + var i = document.createElement("div"); + for (i.innerHTML = a; i.firstChild;) this[t].appendChild(i.firstChild) + } else if (a instanceof e) + for (r = 0; r < a.length; r++) this[t].appendChild(a[r]); + else this[t].appendChild(a); + return this + }, + prepend: function(a) { + var t, r; + for (t = 0; t < this.length; t++) + if ("string" == typeof a) { + var i = document.createElement("div"); + for (i.innerHTML = a, r = i.childNodes.length - 1; r >= 0; r--) this[t].insertBefore(i.childNodes[r], this[t].childNodes[0]) + } else if (a instanceof e) + for (r = 0; r < a.length; r++) this[t].insertBefore(a[r], this[t].childNodes[0]); + else this[t].insertBefore(a, this[t].childNodes[0]); + return this + }, + insertBefore: function(e) { + for (var t = a(e), r = 0; r < this.length; r++) + if (1 === t.length) t[0].parentNode.insertBefore(this[r], t[0]); + else if (t.length > 1) + for (var i = 0; i < t.length; i++) t[i].parentNode.insertBefore(this[r].cloneNode(!0), t[i]) + }, + insertAfter: function(e) { + for (var t = a(e), r = 0; r < this.length; r++) + if (1 === t.length) t[0].parentNode.insertBefore(this[r], t[0].nextSibling); + else if (t.length > 1) + for (var i = 0; i < t.length; i++) t[i].parentNode.insertBefore(this[r].cloneNode(!0), t[i].nextSibling) + }, + next: function(t) { + return new e(this.length > 0 ? t ? this[0].nextElementSibling && a(this[0].nextElementSibling).is(t) ? [this[0].nextElementSibling] : [] : this[0].nextElementSibling ? [this[0].nextElementSibling] : [] : []) + }, + nextAll: function(t) { + var r = [], + i = this[0]; + if (!i) return new e([]); + for (; i.nextElementSibling;) { + var s = i.nextElementSibling; + t ? a(s).is(t) && r.push(s) : r.push(s), i = s + } + return new e(r) + }, + prev: function(t) { + return new e(this.length > 0 ? t ? this[0].previousElementSibling && a(this[0].previousElementSibling).is(t) ? [this[0].previousElementSibling] : [] : this[0].previousElementSibling ? [this[0].previousElementSibling] : [] : []) + }, + prevAll: function(t) { + var r = [], + i = this[0]; + if (!i) return new e([]); + for (; i.previousElementSibling;) { + var s = i.previousElementSibling; + t ? a(s).is(t) && r.push(s) : r.push(s), i = s + } + return new e(r) + }, + parent: function(e) { + for (var t = [], r = 0; r < this.length; r++) e ? a(this[r].parentNode).is(e) && t.push(this[r].parentNode) : t.push(this[r].parentNode); + return a(a.unique(t)) + }, + parents: function(e) { + for (var t = [], r = 0; r < this.length; r++) + for (var i = this[r].parentNode; i;) e ? a(i).is(e) && t.push(i) : t.push(i), i = i.parentNode; + return a(a.unique(t)) + }, + find: function(a) { + for (var t = [], r = 0; r < this.length; r++) + for (var i = this[r].querySelectorAll(a), s = 0; s < i.length; s++) t.push(i[s]); + return new e(t) + }, + children: function(t) { + for (var r = [], i = 0; i < this.length; i++) + for (var s = this[i].childNodes, n = 0; n < s.length; n++) t ? 1 === s[n].nodeType && a(s[n]).is(t) && r.push(s[n]) : 1 === s[n].nodeType && r.push(s[n]); + return new e(a.unique(r)) + }, + remove: function() { + for (var e = 0; e < this.length; e++) this[e].parentNode && this[e].parentNode.removeChild(this[e]); + return this + }, + add: function() { + var e, t, r = this; + for (e = 0; e < arguments.length; e++) { + var i = a(arguments[e]); + for (t = 0; t < i.length; t++) r[r.length] = i[t], r.length++ + } + return r + } + }, a.fn = e.prototype, a.unique = function(e) { + for (var a = [], t = 0; t < e.length; t++) - 1 === a.indexOf(e[t]) && a.push(e[t]); + return a + }, a + }()), i = ["jQuery", "Zepto", "Dom7"], s = 0; s < i.length; s++) window[i[s]] && e(window[i[s]]); + var n; + n = "undefined" == typeof r ? window.Dom7 || window.Zepto || window.jQuery : r, n && ("transitionEnd" in n.fn || (n.fn.transitionEnd = function(e) { + function a(s) { + if (s.target === this) + for (e.call(this, s), t = 0; t < r.length; t++) i.off(r[t], a) + } + var t, r = ["webkitTransitionEnd", "transitionend", "oTransitionEnd", "MSTransitionEnd", "msTransitionEnd"], + i = this; + if (e) + for (t = 0; t < r.length; t++) i.on(r[t], a); + return this + }), "transform" in n.fn || (n.fn.transform = function(e) { + for (var a = 0; a < this.length; a++) { + var t = this[a].style; + t.webkitTransform = t.MsTransform = t.msTransform = t.MozTransform = t.OTransform = t.transform = e + } + return this + }), "transition" in n.fn || (n.fn.transition = function(e) { + "string" != typeof e && (e += "ms"); + for (var a = 0; a < this.length; a++) { + var t = this[a].style; + t.webkitTransitionDuration = t.MsTransitionDuration = t.msTransitionDuration = t.MozTransitionDuration = t.OTransitionDuration = t.transitionDuration = e + } + return this + })), window.Swiper = t +}(), "undefined" != typeof module ? module.exports = window.Swiper : "function" == typeof define && define.amd && define([], function() { + "use strict"; + return window.Swiper +}); +//# sourceMappingURL=maps/swiper.min.js.map \ No newline at end of file diff --git a/dashboard-ui/bower_components/Swiper/package.js b/dashboard-ui/bower_components/Swiper/package.js index f0d32ef541..75fb0ca24d 100644 --- a/dashboard-ui/bower_components/Swiper/package.js +++ b/dashboard-ui/bower_components/Swiper/package.js @@ -1 +1,9 @@ -var version="3.3.1";Package.describe({name:"nolimits4web:swiper",summary:"iDangero.us Swiper - mobile touch slider with hardware accelerated transitions and native behavior",version:version,git:"https://github.com/nolimits4web/Swiper"}),Package.onUse(function(api){api.versionsFrom("1.1.0.2"),api.addFiles(["dist/css/swiper.min.css","dist/js/swiper.js"],["client"])}),Package.onTest(function(api){}); \ No newline at end of file +var version = "3.3.1"; +Package.describe({ + name: "nolimits4web:swiper", + summary: "iDangero.us Swiper - mobile touch slider with hardware accelerated transitions and native behavior", + version: version, + git: "https://github.com/nolimits4web/Swiper" +}), Package.onUse(function(api) { + api.versionsFrom("1.1.0.2"), api.addFiles(["dist/css/swiper.min.css", "dist/js/swiper.js"], ["client"]) +}), Package.onTest(function(api) {}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/alameda/alameda.js b/dashboard-ui/bower_components/alameda/alameda.js index 8f8d95207a..4f2a805250 100644 --- a/dashboard-ui/bower_components/alameda/alameda.js +++ b/dashboard-ui/bower_components/alameda/alameda.js @@ -1 +1,418 @@ -var requirejs,require,define;!function(global,Promise,undef){function commentReplace(match,singlePrefix){return singlePrefix||""}function hasProp(obj,prop){return hasOwn.call(obj,prop)}function getOwn(obj,prop){return obj&&hasProp(obj,prop)&&obj[prop]}function obj(){return Object.create(null)}function eachProp(obj,func){var prop;for(prop in obj)if(hasProp(obj,prop)&&func(obj[prop],prop))break}function mixin(target,source,force,deepStringMixin){return source&&eachProp(source,function(value,prop){!force&&hasProp(target,prop)||(!deepStringMixin||"object"!=typeof value||!value||Array.isArray(value)||"function"==typeof value||value instanceof RegExp?target[prop]=value:(target[prop]||(target[prop]={}),mixin(target[prop],value,force,deepStringMixin)))}),target}function getGlobal(value){if(!value)return value;var g=global;return value.split(".").forEach(function(part){g=g[part]}),g}function newContext(contextName){function trimDots(ary){var i,part,length=ary.length;for(i=0;i0&&(ary.splice(i-1,2),i-=2)}}function normalize(name,baseName,applyMap){var mapValue,nameParts,i,j,nameSegment,lastIndex,foundMap,foundI,foundStarMap,starI,baseParts=baseName&&baseName.split("/"),normalizedBaseParts=baseParts,map=config.map,starMap=map&&map["*"];if(name&&(name=name.split("/"),lastIndex=name.length-1,config.nodeIdCompat&&jsSuffixRegExp.test(name[lastIndex])&&(name[lastIndex]=name[lastIndex].replace(jsSuffixRegExp,"")),"."===name[0].charAt(0)&&baseParts&&(normalizedBaseParts=baseParts.slice(0,baseParts.length-1),name=normalizedBaseParts.concat(name)),trimDots(name),name=name.join("/")),applyMap&&map&&(baseParts||starMap)){nameParts=name.split("/");outerLoop:for(i=nameParts.length;i>0;i-=1){if(nameSegment=nameParts.slice(0,i).join("/"),baseParts)for(j=baseParts.length;j>0;j-=1)if((mapValue=getOwn(map,baseParts.slice(0,j).join("/")))&&(mapValue=getOwn(mapValue,nameSegment))){foundMap=mapValue,foundI=i;break outerLoop}!foundStarMap&&starMap&&getOwn(starMap,nameSegment)&&(foundStarMap=getOwn(starMap,nameSegment),starI=i)}!foundMap&&foundStarMap&&(foundMap=foundStarMap,foundI=starI),foundMap&&(nameParts.splice(0,foundI,foundMap),name=nameParts.join("/"))}return getOwn(config.pkgs,name)||name}function makeShimExports(value){function fn(){var ret;return value.init&&(ret=value.init.apply(global,arguments)),ret||value.exports&&getGlobal(value.exports)}return fn}function takeQueue(anonId){var i,id,args,shim;for(i=0;i0;i-=1)if(parentModule=syms.slice(0,i).join("/"),parentPath=getOwn(paths,parentModule)){Array.isArray(parentPath)&&(parentPath=parentPath[0]),syms.splice(0,i,parentPath);break}url=syms.join("/"),url+=ext||(/^data\:|^blob\:|\?/.test(url)||skipExt?"":".js"),url=("/"===url.charAt(0)||url.match(/^[\w\+\.\-]+:/)?"":config.baseUrl)+url}return config.urlArgs&&!/^blob\:/.test(url)?url+config.urlArgs(moduleName,url):url},req.toUrl=function(moduleNamePlusExt){var ext,index=moduleNamePlusExt.lastIndexOf("."),segment=moduleNamePlusExt.split("/")[0],isRelative="."===segment||".."===segment;return-1!==index&&(!isRelative||index>1)&&(ext=moduleNamePlusExt.substring(index,moduleNamePlusExt.length),moduleNamePlusExt=moduleNamePlusExt.substring(0,index)),req.nameToUrl(normalize(moduleNamePlusExt,relName),ext,!0)},req.defined=function(id){return makeMap(id,relName,!0).id in defined},req.specified=function(id){return(id=makeMap(id,relName,!0).id)in defined||id in deferreds},req}function resolve(name,d,value){name&&(defined[name]=value,requirejs.onResourceLoad&&requirejs.onResourceLoad(context,d.map,d.deps)),d.finished=!0,d.resolve(value)}function reject(d,err){d.finished=!0,d.rejected=!0,d.reject(err)}function makeNormalize(relName){return function(name){return normalize(name,relName,!0)}}function defineModule(d){d.factoryCalled=!0;var ret,name=d.map.id;try{ret=context.execCb(name,d.factory,d.values,defined[name])}catch(err){return reject(d,err)}name?ret===undef&&(d.cjsModule?ret=d.cjsModule.exports:d.usingExports&&(ret=defined[name])):requireDeferreds.splice(requireDeferreds.indexOf(d),1),resolve(name,d,ret)}function depFinished(val,i){this.rejected||this.depDefined[i]||(this.depDefined[i]=!0,this.depCount+=1,this.values[i]=val,this.depending||this.depCount!==this.depMax||defineModule(this))}function makeDefer(name,calculatedMap){var d={};return d.promise=new Promise(function(resolve,reject){d.resolve=resolve,d.reject=function(err){name||requireDeferreds.splice(requireDeferreds.indexOf(d),1),reject(err)}}),d.map=name?calculatedMap||makeMap(name):{},d.depCount=0,d.depMax=0,d.values=[],d.depDefined=[],d.depFinished=depFinished,d.map.pr&&(d.deps=[makeMap(d.map.pr)]),d}function getDefer(name,calculatedMap){var d;return name?(d=name in deferreds&&deferreds[name])||(d=deferreds[name]=makeDefer(name,calculatedMap)):(d=makeDefer(),requireDeferreds.push(d)),d}function makeErrback(d,name){return function(err){d.rejected||(err.dynaId||(err.dynaId="id"+(errCount+=1),err.requireModules=[name]),reject(d,err))}}function waitForDep(depMap,relName,d,i){d.depMax+=1,callDep(depMap,relName).then(function(val){d.depFinished(val,i)},makeErrback(d,depMap.id)).catch(makeErrback(d,d.map.id))}function makeLoad(id){function load(value){fromTextCalled||resolve(id,getDefer(id),value)}var fromTextCalled;return load.error=function(err){reject(getDefer(id),err)},load.fromText=function(text,textAlt){var execError,d=getDefer(id),map=makeMap(makeMap(id).n),plainId=map.id;fromTextCalled=!0,d.factory=function(p,val){return val},textAlt&&(text=textAlt),hasProp(config.config,id)&&(config.config[plainId]=config.config[id]);try{req.exec(text)}catch(e){execError=new Error("fromText eval for "+plainId+" failed: "+e),execError.requireType="fromtexteval",reject(d,execError)}takeQueue(plainId),d.deps=[map],waitForDep(map,null,d,d.deps.length)},load}function callPlugin(plugin,map,relName){plugin.load(map.n,makeRequire(relName),makeLoad(map.id),config)}function splitPrefix(name){var prefix,index=name?name.indexOf("!"):-1;return index>-1&&(prefix=name.substring(0,index),name=name.substring(index+1,name.length)),[prefix,name]}function breakCycle(d,traced,processed){var id=d.map.id;traced[id]=!0,!d.finished&&d.deps&&d.deps.forEach(function(depMap){var depId=depMap.id,dep=!hasProp(handlers,depId)&&getDefer(depId,depMap);!dep||dep.finished||processed[depId]||(hasProp(traced,depId)?d.deps.forEach(function(depMap,i){depMap.id===depId&&d.depFinished(defined[depId],i)}):breakCycle(dep,traced,processed))}),processed[id]=!0}function check(d){var err,mid,dfd,notFinished=[],waitInterval=1e3*config.waitSeconds,expired=waitInterval&&startTime+waitInterval<(new Date).getTime();if(0===loadCount&&(d?d.finished||breakCycle(d,{},{}):requireDeferreds.length&&requireDeferreds.forEach(function(d){breakCycle(d,{},{})})),expired){for(mid in deferreds)dfd=deferreds[mid],dfd.finished||notFinished.push(dfd.map.id);err=new Error("Timeout for modules: "+notFinished),err.requireModules=notFinished,err.requireType="timeout",notFinished.forEach(function(id){reject(getDefer(id),err)})}else(loadCount||requireDeferreds.length)&&(checkingLater||(checkingLater=!0,setTimeout(function(){checkingLater=!1,check()},70)))}function delayedError(e){return setTimeout(function(){e.dynaId&&trackedErrors[e.dynaId]||(trackedErrors[e.dynaId]=!0,req.onError(e))}),e}var req,main,makeMap,callDep,handlers,checkingLater,load,context,defined=obj(),waiting=obj(),config={waitSeconds:7,baseUrl:"./",paths:{},bundles:{},pkgs:{},shim:{},config:{}},mapCache=obj(),requireDeferreds=[],deferreds=obj(),calledDefine=obj(),calledPlugin=obj(),loadCount=0,startTime=(new Date).getTime(),errCount=0,trackedErrors=obj(),urlFetched=obj(),bundlesMap=obj(),asyncResolve=Promise.resolve();return load="function"==typeof importScripts?function(map){var url=map.url;urlFetched[url]||(urlFetched[url]=!0,getDefer(map.id),importScripts(url),takeQueue(map.id))}:function(map){var script,id=map.id,url=map.url;urlFetched[url]||(urlFetched[url]=!0,script=document.createElement("script"),script.setAttribute("data-requiremodule",id),script.type=config.scriptType||"text/javascript",script.charset="utf-8",script.async=!0,loadCount+=1,script.addEventListener("load",function(){loadCount-=1,takeQueue(id)},!1),script.addEventListener("error",function(){loadCount-=1;var err,pathConfig=getOwn(config.paths,id);if(pathConfig&&Array.isArray(pathConfig)&&pathConfig.length>1){script.parentNode.removeChild(script),pathConfig.shift();var d=getDefer(id);d.map=makeMap(id),d.map.url=req.nameToUrl(id),load(d.map)}else err=new Error("Load failed: "+id+": "+script.src),err.requireModules=[id],err.requireType="scripterror",reject(getDefer(id),err)},!1),script.src=url,10===document.documentMode?asap.then(function(){document.head.appendChild(script)}):document.head.appendChild(script))},callDep=function(map,relName){var args,bundleId,name=map.id,shim=config.shim[name];if(name in waiting)args=waiting[name],delete waiting[name],main.apply(undef,args);else if(!(name in deferreds))if(map.pr){if(!(bundleId=getOwn(bundlesMap,name)))return callDep(makeMap(map.pr)).then(function(plugin){var newMap=map.prn?map:makeMap(name,relName,!0),newId=newMap.id,shim=getOwn(config.shim,newId);return newId in calledPlugin||(calledPlugin[newId]=!0,shim&&shim.deps?req(shim.deps,function(){callPlugin(plugin,newMap,relName)}):callPlugin(plugin,newMap,relName)),getDefer(newId).promise});map.url=req.nameToUrl(bundleId),load(map)}else shim&&shim.deps?req(shim.deps,function(){load(map)}):load(map);return getDefer(name).promise},makeMap=function(name,relName,applyMap){if("string"!=typeof name)return name;var plugin,url,parts,prefix,result,prefixNormalized,cacheKey=name+" & "+(relName||"")+" & "+!!applyMap;return parts=splitPrefix(name),prefix=parts[0],name=parts[1],!prefix&&cacheKey in mapCache?mapCache[cacheKey]:(prefix&&(prefix=normalize(prefix,relName,applyMap),plugin=prefix in defined&&defined[prefix]),prefix?plugin&&plugin.normalize?(name=plugin.normalize(name,makeNormalize(relName)),prefixNormalized=!0):name=-1===name.indexOf("!")?normalize(name,relName,applyMap):name:(name=normalize(name,relName,applyMap),parts=splitPrefix(name),prefix=parts[0],name=parts[1],url=req.nameToUrl(name)),result={id:prefix?prefix+"!"+name:name,n:name,pr:prefix,url:url,prn:prefix&&prefixNormalized},prefix||(mapCache[cacheKey]=result),result)},handlers={require:function(name){return makeRequire(name)},exports:function(name){var e=defined[name];return void 0!==e?e:defined[name]={}},module:function(name){return{id:name,uri:"",exports:handlers.exports(name),config:function(){return getOwn(config.config,name)||{}}}}},main=function(name,deps,factory,errback,relName){if(name){if(name in calledDefine)return;calledDefine[name]=!0}var d=getDefer(name);return deps&&!Array.isArray(deps)&&(factory=deps,deps=[]),deps=deps?slice.call(deps,0):null,errback||(hasProp(config,"defaultErrback")?config.defaultErrback&&(errback=config.defaultErrback):errback=delayedError),errback&&d.promise.catch(errback),relName=relName||name,"function"==typeof factory?(!deps.length&&factory.length&&(factory.toString().replace(commentRegExp,commentReplace).replace(cjsRequireRegExp,function(match,dep){deps.push(dep)}),deps=(1===factory.length?["require"]:["require","exports","module"]).concat(deps)),d.factory=factory,d.deps=deps,d.depending=!0,deps.forEach(function(depName,i){var depMap;deps[i]=depMap=makeMap(depName,relName,!0),depName=depMap.id,"require"===depName?d.values[i]=handlers.require(name):"exports"===depName?(d.values[i]=handlers.exports(name),d.usingExports=!0):"module"===depName?d.values[i]=d.cjsModule=handlers.module(name):void 0===depName?d.values[i]=void 0:waitForDep(depMap,relName,d,i)}),d.depending=!1,d.depCount===d.depMax&&defineModule(d)):name&&resolve(name,d,factory),startTime=(new Date).getTime(),name||check(d),d.promise},req=makeRequire(null,!0),req.config=function(cfg){if(cfg.context&&cfg.context!==contextName){var existingContext=getOwn(contexts,cfg.context);return existingContext?existingContext.req.config(cfg):newContext(cfg.context).config(cfg)}if(mapCache=obj(),cfg.baseUrl&&"/"!==cfg.baseUrl.charAt(cfg.baseUrl.length-1)&&(cfg.baseUrl+="/"),"string"==typeof cfg.urlArgs){var urlArgs=cfg.urlArgs;cfg.urlArgs=function(id,url){return(-1===url.indexOf("?")?"?":"&")+urlArgs}}var shim=config.shim,objs={paths:!0,bundles:!0,config:!0,map:!0};return eachProp(cfg,function(value,prop){objs[prop]?(config[prop]||(config[prop]={}),mixin(config[prop],value,!0,!0)):config[prop]=value}),cfg.bundles&&eachProp(cfg.bundles,function(value,prop){value.forEach(function(v){v!==prop&&(bundlesMap[v]=prop)})}),cfg.shim&&(eachProp(cfg.shim,function(value,id){Array.isArray(value)&&(value={deps:value}),!value.exports&&!value.init||value.exportsFn||(value.exportsFn=makeShimExports(value)),shim[id]=value}),config.shim=shim),cfg.packages&&cfg.packages.forEach(function(pkgObj){var location,name;pkgObj="string"==typeof pkgObj?{name:pkgObj}:pkgObj,name=pkgObj.name,location=pkgObj.location,location&&(config.paths[name]=pkgObj.location),config.pkgs[name]=pkgObj.name+"/"+(pkgObj.main||"main").replace(currDirRegExp,"").replace(jsSuffixRegExp,"")}),(cfg.deps||cfg.callback)&&req(cfg.deps,cfg.callback),req},req.onError=function(err){throw err},context={id:contextName,defined:defined,waiting:waiting,config:config,deferreds:deferreds,req:req,execCb:function(name,callback,args,exports){return callback.apply(exports,args)}},contexts[contextName]=context,req}if(!Promise)throw new Error("No Promise implementation available");var topReq,dataMain,src,subPath,bootstrapConfig=requirejs||require,hasOwn=Object.prototype.hasOwnProperty,contexts={},queue=[],currDirRegExp=/^\.\//,urlRegExp=/^\/|\:|\?|\.js$/,commentRegExp=/\/\*[\s\S]*?\*\/|([^:"'=]|^)\/\/.*$/gm,cjsRequireRegExp=/[^.]\s*require\s*\(\s*["']([^'"\s]+)["']\s*\)/g,jsSuffixRegExp=/\.js$/,slice=Array.prototype.slice;if("function"!=typeof requirejs){var asap=Promise.resolve(void 0);requirejs=topReq=newContext("_"),"function"!=typeof require&&(require=topReq),topReq.exec=function(text){return eval(text)},topReq.contexts=contexts,define=function(){queue.push(slice.call(arguments,0))},define.amd={jQuery:!0},bootstrapConfig&&topReq.config(bootstrapConfig),topReq.isBrowser&&!contexts._.config.skipDataMain&&(dataMain=document.querySelectorAll("script[data-main]")[0],(dataMain=dataMain&&dataMain.getAttribute("data-main"))&&(dataMain=dataMain.replace(jsSuffixRegExp,""),bootstrapConfig&&bootstrapConfig.baseUrl||-1!==dataMain.indexOf("!")||(src=dataMain.split("/"),dataMain=src.pop(),subPath=src.length?src.join("/")+"/":"./",topReq.config({baseUrl:subPath})),topReq([dataMain])))}}(this,"undefined"!=typeof Promise?Promise:void 0); \ No newline at end of file +var requirejs, require, define; +! function(global, Promise, undef) { + function commentReplace(match, singlePrefix) { + return singlePrefix || "" + } + + function hasProp(obj, prop) { + return hasOwn.call(obj, prop) + } + + function getOwn(obj, prop) { + return obj && hasProp(obj, prop) && obj[prop] + } + + function obj() { + return Object.create(null) + } + + function eachProp(obj, func) { + var prop; + for (prop in obj) + if (hasProp(obj, prop) && func(obj[prop], prop)) break + } + + function mixin(target, source, force, deepStringMixin) { + return source && eachProp(source, function(value, prop) { + !force && hasProp(target, prop) || (!deepStringMixin || "object" != typeof value || !value || Array.isArray(value) || "function" == typeof value || value instanceof RegExp ? target[prop] = value : (target[prop] || (target[prop] = {}), mixin(target[prop], value, force, deepStringMixin))) + }), target + } + + function getGlobal(value) { + if (!value) return value; + var g = global; + return value.split(".").forEach(function(part) { + g = g[part] + }), g + } + + function newContext(contextName) { + function trimDots(ary) { + var i, part, length = ary.length; + for (i = 0; i < length; i++) + if ("." === (part = ary[i])) ary.splice(i, 1), i -= 1; + else if (".." === part) { + if (0 === i || 1 === i && ".." === ary[2] || ".." === ary[i - 1]) continue; + i > 0 && (ary.splice(i - 1, 2), i -= 2) + } + } + + function normalize(name, baseName, applyMap) { + var mapValue, nameParts, i, j, nameSegment, lastIndex, foundMap, foundI, foundStarMap, starI, baseParts = baseName && baseName.split("/"), + normalizedBaseParts = baseParts, + map = config.map, + starMap = map && map["*"]; + if (name && (name = name.split("/"), lastIndex = name.length - 1, config.nodeIdCompat && jsSuffixRegExp.test(name[lastIndex]) && (name[lastIndex] = name[lastIndex].replace(jsSuffixRegExp, "")), "." === name[0].charAt(0) && baseParts && (normalizedBaseParts = baseParts.slice(0, baseParts.length - 1), name = normalizedBaseParts.concat(name)), trimDots(name), name = name.join("/")), applyMap && map && (baseParts || starMap)) { + nameParts = name.split("/"); + outerLoop: for (i = nameParts.length; i > 0; i -= 1) { + if (nameSegment = nameParts.slice(0, i).join("/"), baseParts) + for (j = baseParts.length; j > 0; j -= 1) + if ((mapValue = getOwn(map, baseParts.slice(0, j).join("/"))) && (mapValue = getOwn(mapValue, nameSegment))) { + foundMap = mapValue, foundI = i; + break outerLoop + }! foundStarMap && starMap && getOwn(starMap, nameSegment) && (foundStarMap = getOwn(starMap, nameSegment), starI = i) + }!foundMap && foundStarMap && (foundMap = foundStarMap, foundI = starI), foundMap && (nameParts.splice(0, foundI, foundMap), name = nameParts.join("/")) + } + return getOwn(config.pkgs, name) || name + } + + function makeShimExports(value) { + function fn() { + var ret; + return value.init && (ret = value.init.apply(global, arguments)), ret || value.exports && getGlobal(value.exports) + } + return fn + } + + function takeQueue(anonId) { + var i, id, args, shim; + for (i = 0; i < queue.length; i += 1) { + if ("string" != typeof queue[i][0]) { + if (!anonId) break; + queue[i].unshift(anonId), anonId = undef + } + args = queue.shift(), id = args[0], i -= 1, id in defined || id in waiting || (id in deferreds ? main.apply(undef, args) : waiting[id] = args) + } + anonId && (shim = getOwn(config.shim, anonId) || {}, main(anonId, shim.deps || [], shim.exportsFn)) + } + + function makeRequire(relName, topLevel) { + var req = function(deps, callback, errback, alt) { + var name, cfg; + if (topLevel && takeQueue(), "string" == typeof deps) { + if (handlers[deps]) return handlers[deps](relName); + if (!((name = makeMap(deps, relName, !0).id) in defined)) throw new Error("Not loaded: " + name); + return defined[name] + } + return deps && !Array.isArray(deps) && (cfg = deps, deps = undef, Array.isArray(callback) && (deps = callback, callback = errback, errback = alt), topLevel) ? req.config(cfg)(deps, callback, errback) : (callback = callback || function() { + return slice.call(arguments, 0) + }, asyncResolve.then(function() { + return takeQueue(), main(undef, deps || [], callback, errback, relName) + })) + }; + return req.isBrowser = "undefined" != typeof document && "undefined" != typeof navigator, req.nameToUrl = function(moduleName, ext, skipExt) { + var paths, syms, i, parentModule, url, parentPath, bundleId, pkgMain = getOwn(config.pkgs, moduleName); + if (pkgMain && (moduleName = pkgMain), bundleId = getOwn(bundlesMap, moduleName)) return req.nameToUrl(bundleId, ext, skipExt); + if (urlRegExp.test(moduleName)) url = moduleName + (ext || ""); + else { + for (paths = config.paths, syms = moduleName.split("/"), i = syms.length; i > 0; i -= 1) + if (parentModule = syms.slice(0, i).join("/"), parentPath = getOwn(paths, parentModule)) { + Array.isArray(parentPath) && (parentPath = parentPath[0]), syms.splice(0, i, parentPath); + break + } url = syms.join("/"), url += ext || (/^data\:|^blob\:|\?/.test(url) || skipExt ? "" : ".js"), url = ("/" === url.charAt(0) || url.match(/^[\w\+\.\-]+:/) ? "" : config.baseUrl) + url + } + return config.urlArgs && !/^blob\:/.test(url) ? url + config.urlArgs(moduleName, url) : url + }, req.toUrl = function(moduleNamePlusExt) { + var ext, index = moduleNamePlusExt.lastIndexOf("."), + segment = moduleNamePlusExt.split("/")[0], + isRelative = "." === segment || ".." === segment; + return -1 !== index && (!isRelative || index > 1) && (ext = moduleNamePlusExt.substring(index, moduleNamePlusExt.length), moduleNamePlusExt = moduleNamePlusExt.substring(0, index)), req.nameToUrl(normalize(moduleNamePlusExt, relName), ext, !0) + }, req.defined = function(id) { + return makeMap(id, relName, !0).id in defined + }, req.specified = function(id) { + return (id = makeMap(id, relName, !0).id) in defined || id in deferreds + }, req + } + + function resolve(name, d, value) { + name && (defined[name] = value, requirejs.onResourceLoad && requirejs.onResourceLoad(context, d.map, d.deps)), d.finished = !0, d.resolve(value) + } + + function reject(d, err) { + d.finished = !0, d.rejected = !0, d.reject(err) + } + + function makeNormalize(relName) { + return function(name) { + return normalize(name, relName, !0) + } + } + + function defineModule(d) { + d.factoryCalled = !0; + var ret, name = d.map.id; + try { + ret = context.execCb(name, d.factory, d.values, defined[name]) + } catch (err) { + return reject(d, err) + } + name ? ret === undef && (d.cjsModule ? ret = d.cjsModule.exports : d.usingExports && (ret = defined[name])) : requireDeferreds.splice(requireDeferreds.indexOf(d), 1), resolve(name, d, ret) + } + + function depFinished(val, i) { + this.rejected || this.depDefined[i] || (this.depDefined[i] = !0, this.depCount += 1, this.values[i] = val, this.depending || this.depCount !== this.depMax || defineModule(this)) + } + + function makeDefer(name, calculatedMap) { + var d = {}; + return d.promise = new Promise(function(resolve, reject) { + d.resolve = resolve, d.reject = function(err) { + name || requireDeferreds.splice(requireDeferreds.indexOf(d), 1), reject(err) + } + }), d.map = name ? calculatedMap || makeMap(name) : {}, d.depCount = 0, d.depMax = 0, d.values = [], d.depDefined = [], d.depFinished = depFinished, d.map.pr && (d.deps = [makeMap(d.map.pr)]), d + } + + function getDefer(name, calculatedMap) { + var d; + return name ? (d = name in deferreds && deferreds[name]) || (d = deferreds[name] = makeDefer(name, calculatedMap)) : (d = makeDefer(), requireDeferreds.push(d)), d + } + + function makeErrback(d, name) { + return function(err) { + d.rejected || (err.dynaId || (err.dynaId = "id" + (errCount += 1), err.requireModules = [name]), reject(d, err)) + } + } + + function waitForDep(depMap, relName, d, i) { + d.depMax += 1, callDep(depMap, relName).then(function(val) { + d.depFinished(val, i) + }, makeErrback(d, depMap.id)).catch(makeErrback(d, d.map.id)) + } + + function makeLoad(id) { + function load(value) { + fromTextCalled || resolve(id, getDefer(id), value) + } + var fromTextCalled; + return load.error = function(err) { + reject(getDefer(id), err) + }, load.fromText = function(text, textAlt) { + var execError, d = getDefer(id), + map = makeMap(makeMap(id).n), + plainId = map.id; + fromTextCalled = !0, d.factory = function(p, val) { + return val + }, textAlt && (text = textAlt), hasProp(config.config, id) && (config.config[plainId] = config.config[id]); + try { + req.exec(text) + } catch (e) { + execError = new Error("fromText eval for " + plainId + " failed: " + e), execError.requireType = "fromtexteval", reject(d, execError) + } + takeQueue(plainId), d.deps = [map], waitForDep(map, null, d, d.deps.length) + }, load + } + + function callPlugin(plugin, map, relName) { + plugin.load(map.n, makeRequire(relName), makeLoad(map.id), config) + } + + function splitPrefix(name) { + var prefix, index = name ? name.indexOf("!") : -1; + return index > -1 && (prefix = name.substring(0, index), name = name.substring(index + 1, name.length)), [prefix, name] + } + + function breakCycle(d, traced, processed) { + var id = d.map.id; + traced[id] = !0, !d.finished && d.deps && d.deps.forEach(function(depMap) { + var depId = depMap.id, + dep = !hasProp(handlers, depId) && getDefer(depId, depMap); + !dep || dep.finished || processed[depId] || (hasProp(traced, depId) ? d.deps.forEach(function(depMap, i) { + depMap.id === depId && d.depFinished(defined[depId], i) + }) : breakCycle(dep, traced, processed)) + }), processed[id] = !0 + } + + function check(d) { + var err, mid, dfd, notFinished = [], + waitInterval = 1e3 * config.waitSeconds, + expired = waitInterval && startTime + waitInterval < (new Date).getTime(); + if (0 === loadCount && (d ? d.finished || breakCycle(d, {}, {}) : requireDeferreds.length && requireDeferreds.forEach(function(d) { + breakCycle(d, {}, {}) + })), expired) { + for (mid in deferreds) dfd = deferreds[mid], dfd.finished || notFinished.push(dfd.map.id); + err = new Error("Timeout for modules: " + notFinished), err.requireModules = notFinished, err.requireType = "timeout", notFinished.forEach(function(id) { + reject(getDefer(id), err) + }) + } else(loadCount || requireDeferreds.length) && (checkingLater || (checkingLater = !0, setTimeout(function() { + checkingLater = !1, check() + }, 70))) + } + + function delayedError(e) { + return setTimeout(function() { + e.dynaId && trackedErrors[e.dynaId] || (trackedErrors[e.dynaId] = !0, req.onError(e)) + }), e + } + var req, main, makeMap, callDep, handlers, checkingLater, load, context, defined = obj(), + waiting = obj(), + config = { + waitSeconds: 7, + baseUrl: "./", + paths: {}, + bundles: {}, + pkgs: {}, + shim: {}, + config: {} + }, + mapCache = obj(), + requireDeferreds = [], + deferreds = obj(), + calledDefine = obj(), + calledPlugin = obj(), + loadCount = 0, + startTime = (new Date).getTime(), + errCount = 0, + trackedErrors = obj(), + urlFetched = obj(), + bundlesMap = obj(), + asyncResolve = Promise.resolve(); + return load = "function" == typeof importScripts ? function(map) { + var url = map.url; + urlFetched[url] || (urlFetched[url] = !0, getDefer(map.id), importScripts(url), takeQueue(map.id)) + } : function(map) { + var script, id = map.id, + url = map.url; + urlFetched[url] || (urlFetched[url] = !0, script = document.createElement("script"), script.setAttribute("data-requiremodule", id), script.type = config.scriptType || "text/javascript", script.charset = "utf-8", script.async = !0, loadCount += 1, script.addEventListener("load", function() { + loadCount -= 1, takeQueue(id) + }, !1), script.addEventListener("error", function() { + loadCount -= 1; + var err, pathConfig = getOwn(config.paths, id); + if (pathConfig && Array.isArray(pathConfig) && pathConfig.length > 1) { + script.parentNode.removeChild(script), pathConfig.shift(); + var d = getDefer(id); + d.map = makeMap(id), d.map.url = req.nameToUrl(id), load(d.map) + } else err = new Error("Load failed: " + id + ": " + script.src), err.requireModules = [id], err.requireType = "scripterror", reject(getDefer(id), err) + }, !1), script.src = url, 10 === document.documentMode ? asap.then(function() { + document.head.appendChild(script) + }) : document.head.appendChild(script)) + }, callDep = function(map, relName) { + var args, bundleId, name = map.id, + shim = config.shim[name]; + if (name in waiting) args = waiting[name], delete waiting[name], main.apply(undef, args); + else if (!(name in deferreds)) + if (map.pr) { + if (!(bundleId = getOwn(bundlesMap, name))) return callDep(makeMap(map.pr)).then(function(plugin) { + var newMap = map.prn ? map : makeMap(name, relName, !0), + newId = newMap.id, + shim = getOwn(config.shim, newId); + return newId in calledPlugin || (calledPlugin[newId] = !0, shim && shim.deps ? req(shim.deps, function() { + callPlugin(plugin, newMap, relName) + }) : callPlugin(plugin, newMap, relName)), getDefer(newId).promise + }); + map.url = req.nameToUrl(bundleId), load(map) + } else shim && shim.deps ? req(shim.deps, function() { + load(map) + }) : load(map); + return getDefer(name).promise + }, makeMap = function(name, relName, applyMap) { + if ("string" != typeof name) return name; + var plugin, url, parts, prefix, result, prefixNormalized, cacheKey = name + " & " + (relName || "") + " & " + !!applyMap; + return parts = splitPrefix(name), prefix = parts[0], name = parts[1], !prefix && cacheKey in mapCache ? mapCache[cacheKey] : (prefix && (prefix = normalize(prefix, relName, applyMap), plugin = prefix in defined && defined[prefix]), prefix ? plugin && plugin.normalize ? (name = plugin.normalize(name, makeNormalize(relName)), prefixNormalized = !0) : name = -1 === name.indexOf("!") ? normalize(name, relName, applyMap) : name : (name = normalize(name, relName, applyMap), parts = splitPrefix(name), prefix = parts[0], name = parts[1], url = req.nameToUrl(name)), result = { + id: prefix ? prefix + "!" + name : name, + n: name, + pr: prefix, + url: url, + prn: prefix && prefixNormalized + }, prefix || (mapCache[cacheKey] = result), result) + }, handlers = { + require: function(name) { + return makeRequire(name) + }, + exports: function(name) { + var e = defined[name]; + return void 0 !== e ? e : defined[name] = {} + }, + module: function(name) { + return { + id: name, + uri: "", + exports: handlers.exports(name), + config: function() { + return getOwn(config.config, name) || {} + } + } + } + }, main = function(name, deps, factory, errback, relName) { + if (name) { + if (name in calledDefine) return; + calledDefine[name] = !0 + } + var d = getDefer(name); + return deps && !Array.isArray(deps) && (factory = deps, deps = []), deps = deps ? slice.call(deps, 0) : null, errback || (hasProp(config, "defaultErrback") ? config.defaultErrback && (errback = config.defaultErrback) : errback = delayedError), errback && d.promise.catch(errback), relName = relName || name, "function" == typeof factory ? (!deps.length && factory.length && (factory.toString().replace(commentRegExp, commentReplace).replace(cjsRequireRegExp, function(match, dep) { + deps.push(dep) + }), deps = (1 === factory.length ? ["require"] : ["require", "exports", "module"]).concat(deps)), d.factory = factory, d.deps = deps, d.depending = !0, deps.forEach(function(depName, i) { + var depMap; + deps[i] = depMap = makeMap(depName, relName, !0), depName = depMap.id, "require" === depName ? d.values[i] = handlers.require(name) : "exports" === depName ? (d.values[i] = handlers.exports(name), d.usingExports = !0) : "module" === depName ? d.values[i] = d.cjsModule = handlers.module(name) : void 0 === depName ? d.values[i] = void 0 : waitForDep(depMap, relName, d, i) + }), d.depending = !1, d.depCount === d.depMax && defineModule(d)) : name && resolve(name, d, factory), startTime = (new Date).getTime(), name || check(d), d.promise + }, req = makeRequire(null, !0), req.config = function(cfg) { + if (cfg.context && cfg.context !== contextName) { + var existingContext = getOwn(contexts, cfg.context); + return existingContext ? existingContext.req.config(cfg) : newContext(cfg.context).config(cfg) + } + if (mapCache = obj(), cfg.baseUrl && "/" !== cfg.baseUrl.charAt(cfg.baseUrl.length - 1) && (cfg.baseUrl += "/"), "string" == typeof cfg.urlArgs) { + var urlArgs = cfg.urlArgs; + cfg.urlArgs = function(id, url) { + return (-1 === url.indexOf("?") ? "?" : "&") + urlArgs + } + } + var shim = config.shim, + objs = { + paths: !0, + bundles: !0, + config: !0, + map: !0 + }; + return eachProp(cfg, function(value, prop) { + objs[prop] ? (config[prop] || (config[prop] = {}), mixin(config[prop], value, !0, !0)) : config[prop] = value + }), cfg.bundles && eachProp(cfg.bundles, function(value, prop) { + value.forEach(function(v) { + v !== prop && (bundlesMap[v] = prop) + }) + }), cfg.shim && (eachProp(cfg.shim, function(value, id) { + Array.isArray(value) && (value = { + deps: value + }), !value.exports && !value.init || value.exportsFn || (value.exportsFn = makeShimExports(value)), shim[id] = value + }), config.shim = shim), cfg.packages && cfg.packages.forEach(function(pkgObj) { + var location, name; + pkgObj = "string" == typeof pkgObj ? { + name: pkgObj + } : pkgObj, name = pkgObj.name, location = pkgObj.location, location && (config.paths[name] = pkgObj.location), config.pkgs[name] = pkgObj.name + "/" + (pkgObj.main || "main").replace(currDirRegExp, "").replace(jsSuffixRegExp, "") + }), (cfg.deps || cfg.callback) && req(cfg.deps, cfg.callback), req + }, req.onError = function(err) { + throw err + }, context = { + id: contextName, + defined: defined, + waiting: waiting, + config: config, + deferreds: deferreds, + req: req, + execCb: function(name, callback, args, exports) { + return callback.apply(exports, args) + } + }, contexts[contextName] = context, req + } + if (!Promise) throw new Error("No Promise implementation available"); + var topReq, dataMain, src, subPath, bootstrapConfig = requirejs || require, + hasOwn = Object.prototype.hasOwnProperty, + contexts = {}, + queue = [], + currDirRegExp = /^\.\//, + urlRegExp = /^\/|\:|\?|\.js$/, + commentRegExp = /\/\*[\s\S]*?\*\/|([^:"'=]|^)\/\/.*$/gm, + cjsRequireRegExp = /[^.]\s*require\s*\(\s*["']([^'"\s]+)["']\s*\)/g, + jsSuffixRegExp = /\.js$/, + slice = Array.prototype.slice; + if ("function" != typeof requirejs) { + var asap = Promise.resolve(void 0); + requirejs = topReq = newContext("_"), "function" != typeof require && (require = topReq), topReq.exec = function(text) { + return eval(text) + }, topReq.contexts = contexts, define = function() { + queue.push(slice.call(arguments, 0)) + }, define.amd = { + jQuery: !0 + }, bootstrapConfig && topReq.config(bootstrapConfig), topReq.isBrowser && !contexts._.config.skipDataMain && (dataMain = document.querySelectorAll("script[data-main]")[0], (dataMain = dataMain && dataMain.getAttribute("data-main")) && (dataMain = dataMain.replace(jsSuffixRegExp, ""), bootstrapConfig && bootstrapConfig.baseUrl || -1 !== dataMain.indexOf("!") || (src = dataMain.split("/"), dataMain = src.pop(), subPath = src.length ? src.join("/") + "/" : "./", topReq.config({ + baseUrl: subPath + })), topReq([dataMain]))) + } +}(this, "undefined" != typeof Promise ? Promise : void 0); \ No newline at end of file diff --git a/dashboard-ui/bower_components/document-register-element/build/document-register-element.js b/dashboard-ui/bower_components/document-register-element/build/document-register-element.js index 02fbeaf06c..57fe40a366 100644 --- a/dashboard-ui/bower_components/document-register-element/build/document-register-element.js +++ b/dashboard-ui/bower_components/document-register-element/build/document-register-element.js @@ -1,2 +1,246 @@ /*! (C) WebReflection Mit Style License */ -(function(e,t,n,r){"use strict";function rt(e,t){for(var n=0,r=e.length;n>0),s="attached",o="detached",u="extends",a="ADDITION",f="MODIFICATION",l="REMOVAL",c="DOMAttrModified",h="DOMContentLoaded",p="DOMSubtreeModified",d="<",v="=",m=/^[A-Z][A-Z0-9]*(?:-[A-Z0-9]+)+$/,g=["ANNOTATION-XML","COLOR-PROFILE","FONT-FACE","FONT-FACE-SRC","FONT-FACE-URI","FONT-FACE-FORMAT","FONT-FACE-NAME","MISSING-GLYPH"],y=[],b=[],w="",E=t.documentElement,S=y.indexOf||function(e){for(var t=this.length;t--&&this[t]!==e;);return t},x=n.prototype,T=x.hasOwnProperty,N=x.isPrototypeOf,C=n.defineProperty,k=n.getOwnPropertyDescriptor,L=n.getOwnPropertyNames,A=n.getPrototypeOf,O=n.setPrototypeOf,M=!!n.__proto__,_=n.create||function mt(e){return e?(mt.prototype=e,new mt):this},D=O||(M?function(e,t){return e.__proto__=t,e}:L&&k?function(){function e(e,t){for(var n,r=L(t),i=0,s=r.length;i> 0), + s = "attached", + o = "detached", + u = "extends", + a = "ADDITION", + f = "MODIFICATION", + l = "REMOVAL", + c = "DOMAttrModified", + h = "DOMContentLoaded", + p = "DOMSubtreeModified", + d = "<", + v = "=", + m = /^[A-Z][A-Z0-9]*(?:-[A-Z0-9]+)+$/, + g = ["ANNOTATION-XML", "COLOR-PROFILE", "FONT-FACE", "FONT-FACE-SRC", "FONT-FACE-URI", "FONT-FACE-FORMAT", "FONT-FACE-NAME", "MISSING-GLYPH"], + y = [], + b = [], + w = "", + E = t.documentElement, + S = y.indexOf || function(e) { + for (var t = this.length; t-- && this[t] !== e;); + return t + }, + x = n.prototype, + T = x.hasOwnProperty, + N = x.isPrototypeOf, + C = n.defineProperty, + k = n.getOwnPropertyDescriptor, + L = n.getOwnPropertyNames, + A = n.getPrototypeOf, + O = n.setPrototypeOf, + M = !!n.__proto__, + _ = n.create || function mt(e) { + return e ? (mt.prototype = e, new mt) : this + }, + D = O || (M ? function(e, t) { + return e.__proto__ = t, e + } : L && k ? function() { + function e(e, t) { + for (var n, r = L(t), i = 0, s = r.length; i < s; i++) n = r[i], T.call(e, n) || C(e, n, k(t, n)) + } + return function(t, n) { + do e(t, n); while ((n = A(n)) && !N.call(n, t)); + return t + } + }() : function(e, t) { + for (var n in t) e[n] = t[n]; + return e + }), + P = e.MutationObserver || e.WebKitMutationObserver, + H = (e.HTMLElement || e.Element || e.Node).prototype, + B = !N.call(H, E), + j = B ? function(e) { + return e.nodeType === 1 + } : function(e) { + return N.call(H, e) + }, + F = B && [], + I = H.cloneNode, + q = H.setAttribute, + R = H.removeAttribute, + U = t.createElement, + z = P && { + attributes: !0, + characterData: !0, + attributeOldValue: !0 + }, + W = P || function(e) { + J = !1, E.removeEventListener(c, W) + }, + X, V = e.requestAnimationFrame || e.webkitRequestAnimationFrame || e.mozRequestAnimationFrame || e.msRequestAnimationFrame || function(e) { + setTimeout(e, 10) + }, + $ = !1, + J = !0, + K = !0, + Q = !0, + G, Y, Z, et, tt, nt; + O || M ? (tt = function(e, t) { + N.call(t, e) || ht(e, t) + }, nt = ht) : (tt = function(e, t) { + e[i] || (e[i] = n(!0), ht(e, t)) + }, nt = tt), B ? (J = !1, function() { + var e = k(H, "addEventListener"), + t = e.value, + n = function(e) { + var t = new CustomEvent(c, { + bubbles: !0 + }); + t.attrName = e, t.prevValue = this.getAttribute(e), t.newValue = null, t[l] = t.attrChange = 2, R.call(this, e), this.dispatchEvent(t) + }, + r = function(e, t) { + var n = this.hasAttribute(e), + r = n && this.getAttribute(e), + i = new CustomEvent(c, { + bubbles: !0 + }); + q.call(this, e, t), i.attrName = e, i.prevValue = n ? r : null, i.newValue = t, n ? i[f] = i.attrChange = 1 : i[a] = i.attrChange = 0, this.dispatchEvent(i) + }, + s = function(e) { + var t = e.currentTarget, + n = t[i], + r = e.propertyName, + s; + n.hasOwnProperty(r) && (n = n[r], s = new CustomEvent(c, { + bubbles: !0 + }), s.attrName = n.name, s.prevValue = n.value || null, s.newValue = n.value = t[r] || null, s.prevValue == null ? s[a] = s.attrChange = 0 : s[f] = s.attrChange = 1, t.dispatchEvent(s)) + }; + e.value = function(e, o, u) { + e === c && this.attributeChangedCallback && this.setAttribute !== r && (this[i] = { + className: { + name: "class", + value: this.className + } + }, this.setAttribute = r, this.removeAttribute = n, t.call(this, "propertychange", s)), t.call(this, e, o, u) + }, C(H, "addEventListener", e) + }()) : P || (E.addEventListener(c, W), E.setAttribute(i, 1), E.removeAttribute(i), J && (G = function(e) { + var t = this, + n, r, s; + if (t === e.target) { + n = t[i], t[i] = r = Z(t); + for (s in r) { + if (!(s in n)) return Y(0, t, s, n[s], r[s], a); + if (r[s] !== n[s]) return Y(1, t, s, n[s], r[s], f) + } + for (s in n) + if (!(s in r)) return Y(2, t, s, n[s], r[s], l) + } + }, Y = function(e, t, n, r, i, s) { + var o = { + attrChange: e, + currentTarget: t, + attrName: n, + prevValue: r, + newValue: i + }; + o[s] = e, at(o) + }, Z = function(e) { + for (var t, n, r = {}, i = e.attributes, s = 0, o = i.length; s < o; s++) t = i[s], n = t.name, n !== "setAttribute" && (r[n] = t.value); + return r + })), t[r] = function(n, r) { + c = n.toUpperCase(), $ || ($ = !0, P ? (et = function(e, t) { + function n(e, t) { + for (var n = 0, r = e.length; n < r; t(e[n++])); + } + return new P(function(r) { + for (var i, s, o, u = 0, a = r.length; u < a; u++) i = r[u], i.type === "childList" ? (n(i.addedNodes, e), n(i.removedNodes, t)) : (s = i.target, Q && s.attributeChangedCallback && i.attributeName !== "style" && (o = s.getAttribute(i.attributeName), o !== i.oldValue && s.attributeChangedCallback(i.attributeName, i.oldValue, o))) + }) + }(st(s), st(o)), et.observe(t, { + childList: !0, + subtree: !0 + })) : (X = [], V(function E() { + while (X.length) X.shift().call(null, X.shift()); + V(E) + }), t.addEventListener("DOMNodeInserted", ft(s)), t.addEventListener("DOMNodeRemoved", ft(o))), t.addEventListener(h, lt), t.addEventListener("readystatechange", lt), t.createElement = function(e, n) { + var r = U.apply(t, arguments), + i = "" + e, + s = S.call(y, (n ? v : d) + (n || i).toUpperCase()), + o = -1 < s; + return n && (r.setAttribute("is", n = n.toLowerCase()), o && (o = ut(i.toUpperCase(), n))), Q = !t.createElement.innerHTMLHelper, o && nt(r, b[s]), r + }, H.cloneNode = function(e) { + var t = I.call(this, !!e), + n = ot(t); + return -1 < n && nt(t, b[n]), e && it(t.querySelectorAll(w)), t + }), -2 < S.call(y, v + c) + S.call(y, d + c) && dt(n); + if (!m.test(c) || -1 < S.call(g, c)) throw new Error("The type " + n + " is invalid"); + var i = function() { + return f ? t.createElement(l, c) : t.createElement(l) + }, + a = r || x, + f = T.call(a, u), + l = f ? r[u].toUpperCase() : c, + c, p; + return f && -1 < S.call(y, d + l) && dt(l), p = y.push((f ? v : d) + c) - 1, w = w.concat(w.length ? "," : "", f ? l + '[is="' + n.toLowerCase() + '"]' : l), i.prototype = b[p] = T.call(a, "prototype") ? a.prototype : _(H), rt(t.querySelectorAll(w), s), i + } +})(window, document, Object, "registerElement"); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-apiclient/apiclient.js b/dashboard-ui/bower_components/emby-apiclient/apiclient.js index 1a4a1aff5f..e86ff09bff 100644 --- a/dashboard-ui/bower_components/emby-apiclient/apiclient.js +++ b/dashboard-ui/bower_components/emby-apiclient/apiclient.js @@ -1,2 +1,1619 @@ -define(["events","appStorage","wakeOnLan"],function(events,appStorage,wakeOnLan){"use strict";function redetectBitrate(instance){stopBitrateDetection(instance),instance.accessToken()&&!1!==instance.enableAutomaticBitrateDetection&&setTimeout(redetectBitrateInternal.bind(instance),6e3)}function redetectBitrateInternal(){this.accessToken()&&this.detectBitrate()}function stopBitrateDetection(instance){instance.detectTimeout&&clearTimeout(instance.detectTimeout)}function replaceAll(originalString,strReplace,strWith){var reg=new RegExp(strReplace,"ig");return originalString.replace(reg,strWith)}function onFetchFail(instance,url,response){events.trigger(instance,"requestfail",[{url:url,status:response.status,errorCode:response.headers?response.headers.get("X-Application-Error-Code"):null}])}function paramsToString(params){var values=[];for(var key in params){var value=params[key];null!==value&&void 0!==value&&""!==value&&values.push(encodeURIComponent(key)+"="+encodeURIComponent(value))}return values.join("&")}function fetchWithTimeout(url,options,timeoutMs){return new Promise(function(resolve,reject){var timeout=setTimeout(reject,timeoutMs);options=options||{},options.credentials="same-origin",fetch(url,options).then(function(response){clearTimeout(timeout),resolve(response)},function(error){clearTimeout(timeout),reject(error)})})}function getFetchPromise(request){var headers=request.headers||{};"json"===request.dataType&&(headers.accept="application/json");var fetchRequest={headers:headers,method:request.type,credentials:"same-origin"},contentType=request.contentType;return request.data&&("string"==typeof request.data?fetchRequest.body=request.data:(fetchRequest.body=paramsToString(request.data),contentType=contentType||"application/x-www-form-urlencoded; charset=UTF-8")),contentType&&(headers["Content-Type"]=contentType),request.timeout?fetchWithTimeout(request.url,fetchRequest,request.timeout):fetch(request.url,fetchRequest)}function ApiClient(serverAddress,appName,appVersion,deviceName,deviceId,devicePixelRatio){if(!serverAddress)throw new Error("Must supply a serverAddress");console.log("ApiClient serverAddress: "+serverAddress),console.log("ApiClient appName: "+appName),console.log("ApiClient appVersion: "+appVersion),console.log("ApiClient deviceName: "+deviceName),console.log("ApiClient deviceId: "+deviceId),this._serverInfo={},this._serverAddress=serverAddress,this._deviceId=deviceId,this._deviceName=deviceName,this._appName=appName,this._appVersion=appVersion,this._devicePixelRatio=devicePixelRatio}function setSavedEndpointInfo(instance,info){instance._endPointInfo=info}function getTryConnectPromise(instance,url,state,resolve,reject){console.log("getTryConnectPromise "+url),fetchWithTimeout(instance.getUrl("system/info/public",null,url),{method:"GET",accept:"application/json"},15e3).then(function(){state.resolved||(state.resolved=!0,console.log("Reconnect succeeded to "+url),instance.serverAddress(url),resolve())},function(){state.resolved||(console.log("Reconnect failed to "+url),++state.rejects>=state.numAddresses&&reject())})}function tryReconnectInternal(instance){var addresses=[],addressesStrings=[],serverInfo=instance.serverInfo();return serverInfo.LocalAddress&&-1===addressesStrings.indexOf(serverInfo.LocalAddress)&&(addresses.push({url:serverInfo.LocalAddress,timeout:0}),addressesStrings.push(addresses[addresses.length-1].url)),serverInfo.ManualAddress&&-1===addressesStrings.indexOf(serverInfo.ManualAddress)&&(addresses.push({url:serverInfo.ManualAddress,timeout:100}),addressesStrings.push(addresses[addresses.length-1].url)),serverInfo.RemoteAddress&&-1===addressesStrings.indexOf(serverInfo.RemoteAddress)&&(addresses.push({url:serverInfo.RemoteAddress,timeout:200}),addressesStrings.push(addresses[addresses.length-1].url)),console.log("tryReconnect: "+addressesStrings.join("|")),new Promise(function(resolve,reject){var state={};state.numAddresses=addresses.length,state.rejects=0,addresses.map(function(url){setTimeout(function(){state.resolved||getTryConnectPromise(instance,url.url,state,resolve,reject)},url.timeout)})})}function tryReconnect(instance,retryCount){return retryCount=retryCount||0,retryCount>=20?Promise.reject():tryReconnectInternal(instance).catch(function(err){return console.log("error in tryReconnectInternal: "+(err||"")),new Promise(function(resolve,reject){setTimeout(function(){tryReconnect(instance,retryCount+1).then(resolve,reject)},500)})})}function getCachedUser(instance,userId){var serverId=instance.serverId();if(!serverId)return null;var json=appStorage.getItem("user-"+userId+"-"+serverId);return json?JSON.parse(json):null}function onWebSocketMessage(msg){var instance=this;msg=JSON.parse(msg.data),onMessageReceivedInternal(instance,msg)}function onMessageReceivedInternal(instance,msg){var messageId=msg.MessageId;if(messageId){if(messageIdsReceived[messageId])return;messageIdsReceived[messageId]=!0}if("UserDeleted"===msg.MessageType)instance._currentUser=null;else if("UserUpdated"===msg.MessageType||"UserConfigurationUpdated"===msg.MessageType){var user=msg.Data;user.Id===instance.getCurrentUserId()&&(instance._currentUser=null)}events.trigger(instance,"message",[msg])}function onWebSocketOpen(){var instance=this;console.log("web socket connection opened"),events.trigger(instance,"websocketopen")}function onWebSocketError(){var instance=this;events.trigger(instance,"websocketerror")}function setSocketOnClose(apiClient,socket){socket.onclose=function(){console.log("web socket closed"),apiClient._webSocket===socket&&(console.log("nulling out web socket"),apiClient._webSocket=null),setTimeout(function(){events.trigger(apiClient,"websocketclose")},0)}}function normalizeReturnBitrate(instance,bitrate){if(!bitrate)return instance.lastDetectedBitrate?instance.lastDetectedBitrate:Promise.reject();var result=Math.round(.7*bitrate);if(instance.getMaxBandwidth){var maxRate=instance.getMaxBandwidth();maxRate&&(result=Math.min(result,maxRate))}return instance.lastDetectedBitrate=result,instance.lastDetectedBitrateTime=(new Date).getTime(),result}function detectBitrateInternal(instance,tests,index,currentBitrate){if(index>=tests.length)return normalizeReturnBitrate(instance,currentBitrate);var test=tests[index];return instance.getDownloadSpeed(test.bytes).then(function(bitrate){return bitrate=infos.length)return void resolve();var info=infos[index];console.log("sending wakeonlan to "+info.MacAddress),wakeOnLan.send(info).then(function(result){sendNextWakeOnLan(infos,index+1,resolve)},function(){sendNextWakeOnLan(infos,index+1,resolve)})}function compareVersions(a,b){a=a.split("."),b=b.split(".");for(var i=0,length=Math.max(a.length,b.length);ibVal)return 1}return 0}ApiClient.prototype.appName=function(){return this._appName},ApiClient.prototype.setRequestHeaders=function(headers){var currentServerInfo=this.serverInfo(),appName=this._appName,accessToken=currentServerInfo.AccessToken,values=[];if(appName&&values.push('Client="'+appName+'"'),this._deviceName&&values.push('Device="'+this._deviceName+'"'),this._deviceId&&values.push('DeviceId="'+this._deviceId+'"'),this._appVersion&&values.push('Version="'+this._appVersion+'"'),accessToken&&values.push('Token="'+accessToken+'"'),values.length){var auth="MediaBrowser "+values.join(", ");headers["X-Emby-Authorization"]=auth}},ApiClient.prototype.appVersion=function(){return this._appVersion},ApiClient.prototype.deviceName=function(){return this._deviceName},ApiClient.prototype.deviceId=function(){return this._deviceId},ApiClient.prototype.serverAddress=function(val){if(null!=val){if(0!==val.toLowerCase().indexOf("http"))throw new Error("Invalid url: "+val);var changed=val!==this._serverAddress;this._serverAddress=val,this.onNetworkChange(),changed&&events.trigger(this,"serveraddresschanged")}return this._serverAddress},ApiClient.prototype.onNetworkChange=function(){this.lastDetectedBitrate=0,this.lastDetectedBitrateTime=0,setSavedEndpointInfo(this,null),redetectBitrate(this),refreshWakeOnLanInfoIfNeeded(this)},ApiClient.prototype.getUrl=function(name,params,serverAddress){if(!name)throw new Error("Url name cannot be empty");var url=serverAddress||this._serverAddress;if(!url)throw new Error("serverAddress is yet not set");var lowered=url.toLowerCase();return-1===lowered.indexOf("/emby")&&-1===lowered.indexOf("/mediabrowser")&&(url+="/emby"),"/"!==name.charAt(0)&&(url+="/"),url+=name,params&&(params=paramsToString(params))&&(url+="?"+params),url},ApiClient.prototype.fetchWithFailover=function(request,enableReconnection){console.log("Requesting "+request.url),request.timeout=3e4;var instance=this;return getFetchPromise(request).then(function(response){return instance.lastFetch=(new Date).getTime(),response.status<400?"json"===request.dataType||"application/json"===request.headers.accept?response.json():"text"===request.dataType||0===(response.headers.get("Content-Type")||"").toLowerCase().indexOf("text/")?response.text():response:(onFetchFail(instance,request.url,response),Promise.reject(response))},function(error){if(error?console.log("Request failed to "+request.url+" "+(error.status||"")+" "+error.toString()):console.log("Request timed out to "+request.url),error&&error.status||!enableReconnection)throw console.log("Reporting request failure"),onFetchFail(instance,request.url,{}),error;console.log("Attempting reconnection");var previousServerAddress=instance.serverAddress();return tryReconnect(instance).then(function(){return console.log("Reconnect succeesed"),request.url=request.url.replace(previousServerAddress,instance.serverAddress()),instance.fetchWithFailover(request,!1)},function(innerError){throw console.log("Reconnect failed"),onFetchFail(instance,request.url,{}),innerError})})},ApiClient.prototype.fetch=function(request,includeAuthorization){if(!request)throw new Error("Request cannot be null");if(request.headers=request.headers||{},!1!==includeAuthorization&&this.setRequestHeaders(request.headers),!1===this.enableAutomaticNetworking||"GET"!==request.type){console.log("Requesting url without automatic networking: "+request.url);var instance=this;return getFetchPromise(request).then(function(response){return instance.lastFetch=(new Date).getTime(),response.status<400?"json"===request.dataType||"application/json"===request.headers.accept?response.json():"text"===request.dataType||0===(response.headers.get("Content-Type")||"").toLowerCase().indexOf("text/")?response.text():response:(onFetchFail(instance,request.url,response),Promise.reject(response))},function(error){throw onFetchFail(instance,request.url,{}),error})}return this.fetchWithFailover(request,!0)},ApiClient.prototype.setAuthenticationInfo=function(accessKey,userId){this._currentUser=null,this._serverInfo.AccessToken=accessKey,this._serverInfo.UserId=userId,redetectBitrate(this),refreshWakeOnLanInfoIfNeeded(this)},ApiClient.prototype.serverInfo=function(info){return info&&(this._serverInfo=info),this._serverInfo},ApiClient.prototype.getCurrentUserId=function(){return this._serverInfo.UserId},ApiClient.prototype.accessToken=function(){return this._serverInfo.AccessToken},ApiClient.prototype.serverId=function(){return this.serverInfo().Id},ApiClient.prototype.serverName=function(){return this.serverInfo().Name},ApiClient.prototype.ajax=function(request,includeAuthorization){if(!request)throw new Error("Request cannot be null");return this.fetch(request,includeAuthorization)},ApiClient.prototype.getCurrentUser=function(enableCache){if(this._currentUser)return Promise.resolve(this._currentUser);var userId=this.getCurrentUserId();if(!userId)return Promise.reject();var user,instance=this,serverPromise=this.getUser(userId).then(function(user){return appStorage.setItem("user-"+user.Id+"-"+user.ServerId,JSON.stringify(user)),instance._currentUser=user,user},function(response){if(!response.status&&userId&&instance.accessToken()&&(user=getCachedUser(instance,userId)))return Promise.resolve(user);throw response});return!this.lastFetch&&!1!==enableCache&&(user=getCachedUser(instance,userId))?Promise.resolve(user):serverPromise},ApiClient.prototype.isLoggedIn=function(){var info=this.serverInfo();return!!(info&&info.UserId&&info.AccessToken)},ApiClient.prototype.logout=function(){stopBitrateDetection(this),this.closeWebSocket();var done=function(){this.setAuthenticationInfo(null,null)}.bind(this);if(this.accessToken()){var url=this.getUrl("Sessions/Logout");return this.ajax({type:"POST",url:url}).then(done,done)}return done(),Promise.resolve()},ApiClient.prototype.authenticateUserByName=function(name,password){if(!name)return Promise.reject();var url=this.getUrl("Users/authenticatebyname"),instance=this;return new Promise(function(resolve,reject){var postData={Username:name,Pw:password||""};instance.ajax({type:"POST",url:url,data:JSON.stringify(postData),dataType:"json",contentType:"application/json"}).then(function(result){var afterOnAuthenticated=function(){redetectBitrate(instance),refreshWakeOnLanInfoIfNeeded(instance),resolve(result)};instance.onAuthenticated?instance.onAuthenticated(instance,result).then(afterOnAuthenticated):afterOnAuthenticated()},reject)})},ApiClient.prototype.ensureWebSocket=function(){if(!this.isWebSocketOpenOrConnecting()&&this.isWebSocketSupported())try{this.openWebSocket()}catch(err){console.log("Error opening web socket: "+err)}};var messageIdsReceived={};return ApiClient.prototype.openWebSocket=function(){var accessToken=this.accessToken();if(!accessToken)throw new Error("Cannot open web socket without access token.");var url=this.getUrl("socket");url=replaceAll(url,"emby/socket","embywebsocket"),url=replaceAll(url,"https:","wss:"),url=replaceAll(url,"http:","ws:"),url+="?api_key="+accessToken,url+="&deviceId="+this.deviceId(),console.log("opening web socket with url: "+url);var webSocket=new WebSocket(url);webSocket.onmessage=onWebSocketMessage.bind(this),webSocket.onopen=onWebSocketOpen.bind(this),webSocket.onerror=onWebSocketError.bind(this),setSocketOnClose(this,webSocket),this._webSocket=webSocket},ApiClient.prototype.closeWebSocket=function(){var socket=this._webSocket;socket&&socket.readyState===WebSocket.OPEN&&socket.close()},ApiClient.prototype.sendWebSocketMessage=function(name,data){console.log("Sending web socket message: "+name);var msg={MessageType:name};data&&(msg.Data=data),msg=JSON.stringify(msg),this._webSocket.send(msg)},ApiClient.prototype.sendMessage=function(name,data){this.isWebSocketOpen()&&this.sendWebSocketMessage(name,data)},ApiClient.prototype.isMessageChannelOpen=function(){return this.isWebSocketOpen()},ApiClient.prototype.isWebSocketOpen=function(){var socket=this._webSocket;return!!socket&&socket.readyState===WebSocket.OPEN},ApiClient.prototype.isWebSocketOpenOrConnecting=function(){var socket=this._webSocket;return!!socket&&(socket.readyState===WebSocket.OPEN||socket.readyState===WebSocket.CONNECTING)},ApiClient.prototype.get=function(url){return this.ajax({type:"GET",url:url})},ApiClient.prototype.getJSON=function(url,includeAuthorization){return this.fetch({url:url,type:"GET",dataType:"json",headers:{accept:"application/json"}},includeAuthorization)},ApiClient.prototype.updateServerInfo=function(server,serverUrl){if(null==server)throw new Error("server cannot be null");if(this.serverInfo(server),!serverUrl)throw new Error("serverUrl cannot be null. serverInfo: "+JSON.stringify(server));console.log("Setting server address to "+serverUrl),this.serverAddress(serverUrl)},ApiClient.prototype.isWebSocketSupported=function(){try{return null!=WebSocket}catch(err){return!1}},ApiClient.prototype.clearAuthenticationInfo=function(){this.setAuthenticationInfo(null,null)},ApiClient.prototype.encodeName=function(name){name=name.split("/").join("-"),name=name.split("&").join("-"),name=name.split("?").join("-");var val=paramsToString({name:name});return val.substring(val.indexOf("=")+1).replace("'","%27")},ApiClient.prototype.getProductNews=function(options){options=options||{};var url=this.getUrl("News/Product",options);return this.getJSON(url)},ApiClient.prototype.getDownloadSpeed=function(byteSize){var url=this.getUrl("Playback/BitrateTest",{Size:byteSize}),now=(new Date).getTime();return this.ajax({type:"GET",url:url,timeout:5e3}).then(function(){var responseTimeSeconds=((new Date).getTime()-now)/1e3,bytesPerSecond=byteSize/responseTimeSeconds;return Math.round(8*bytesPerSecond)})},ApiClient.prototype.detectBitrate=function(force){if(!force&&this.lastDetectedBitrate&&(new Date).getTime()-(this.lastDetectedBitrateTime||0)<=36e5)return Promise.resolve(this.lastDetectedBitrate);var instance=this;return this.getEndpointInfo().then(function(info){return detectBitrateWithEndpointInfo(instance,info)},function(info){return detectBitrateWithEndpointInfo(instance,{})})},ApiClient.prototype.getItem=function(userId,itemId){if(!itemId)throw new Error("null itemId");var url=userId?this.getUrl("Users/"+userId+"/Items/"+itemId):this.getUrl("Items/"+itemId);return this.getJSON(url)},ApiClient.prototype.getRootFolder=function(userId){if(!userId)throw new Error("null userId");var url=this.getUrl("Users/"+userId+"/Items/Root");return this.getJSON(url)},ApiClient.prototype.getNotificationSummary=function(userId){if(!userId)throw new Error("null userId");var url=this.getUrl("Notifications/"+userId+"/Summary");return this.getJSON(url)},ApiClient.prototype.getNotifications=function(userId,options){if(!userId)throw new Error("null userId");var url=this.getUrl("Notifications/"+userId,options||{});return this.getJSON(url)},ApiClient.prototype.markNotificationsRead=function(userId,idList,isRead){if(!userId)throw new Error("null userId");if(!idList)throw new Error("null idList");var suffix=isRead?"Read":"Unread",params={UserId:userId,Ids:idList.join(",")},url=this.getUrl("Notifications/"+userId+"/"+suffix,params);return this.ajax({type:"POST",url:url})},ApiClient.prototype.getRemoteImageProviders=function(options){if(!options)throw new Error("null options");var urlPrefix=getRemoteImagePrefix(this,options),url=this.getUrl(urlPrefix+"/RemoteImages/Providers",options);return this.getJSON(url)},ApiClient.prototype.getAvailableRemoteImages=function(options){if(!options)throw new Error("null options");var urlPrefix=getRemoteImagePrefix(this,options),url=this.getUrl(urlPrefix+"/RemoteImages",options);return this.getJSON(url)},ApiClient.prototype.downloadRemoteImage=function(options){if(!options)throw new Error("null options");var urlPrefix=getRemoteImagePrefix(this,options),url=this.getUrl(urlPrefix+"/RemoteImages/Download",options);return this.ajax({type:"POST",url:url})},ApiClient.prototype.getRecordingFolders=function(userId){var url=this.getUrl("LiveTv/Recordings/Folders",{userId:userId});return this.getJSON(url)},ApiClient.prototype.getLiveTvInfo=function(options){var url=this.getUrl("LiveTv/Info",options||{});return this.getJSON(url)},ApiClient.prototype.getLiveTvGuideInfo=function(options){var url=this.getUrl("LiveTv/GuideInfo",options||{});return this.getJSON(url)},ApiClient.prototype.getLiveTvChannel=function(id,userId){if(!id)throw new Error("null id");var options={};userId&&(options.userId=userId);var url=this.getUrl("LiveTv/Channels/"+id,options);return this.getJSON(url)},ApiClient.prototype.getLiveTvChannels=function(options){var url=this.getUrl("LiveTv/Channels",options||{});return this.getJSON(url)},ApiClient.prototype.getLiveTvPrograms=function(options){return options=options||{},options.channelIds&&options.channelIds.length>1800?this.ajax({type:"POST",url:this.getUrl("LiveTv/Programs"),data:JSON.stringify(options),contentType:"application/json",dataType:"json"}):this.ajax({type:"GET",url:this.getUrl("LiveTv/Programs",options),dataType:"json"})},ApiClient.prototype.getLiveTvRecommendedPrograms=function(options){return options=options||{},this.ajax({type:"GET",url:this.getUrl("LiveTv/Programs/Recommended",options),dataType:"json"})},ApiClient.prototype.getLiveTvRecordings=function(options){var url=this.getUrl("LiveTv/Recordings",options||{});return this.getJSON(url)},ApiClient.prototype.getLiveTvRecordingSeries=function(options){var url=this.getUrl("LiveTv/Recordings/Series",options||{});return this.getJSON(url)},ApiClient.prototype.getLiveTvRecordingGroups=function(options){var url=this.getUrl("LiveTv/Recordings/Groups",options||{});return this.getJSON(url)},ApiClient.prototype.getLiveTvRecordingGroup=function(id){if(!id)throw new Error("null id");var url=this.getUrl("LiveTv/Recordings/Groups/"+id);return this.getJSON(url)},ApiClient.prototype.getLiveTvRecording=function(id,userId){if(!id)throw new Error("null id");var options={};userId&&(options.userId=userId);var url=this.getUrl("LiveTv/Recordings/"+id,options);return this.getJSON(url)},ApiClient.prototype.getLiveTvProgram=function(id,userId){if(!id)throw new Error("null id");var options={};userId&&(options.userId=userId);var url=this.getUrl("LiveTv/Programs/"+id,options);return this.getJSON(url)},ApiClient.prototype.deleteLiveTvRecording=function(id){if(!id)throw new Error("null id");var url=this.getUrl("LiveTv/Recordings/"+id);return this.ajax({type:"DELETE",url:url})},ApiClient.prototype.cancelLiveTvTimer=function(id){if(!id)throw new Error("null id");var url=this.getUrl("LiveTv/Timers/"+id);return this.ajax({type:"DELETE",url:url})},ApiClient.prototype.getLiveTvTimers=function(options){var url=this.getUrl("LiveTv/Timers",options||{});return this.getJSON(url)},ApiClient.prototype.getLiveTvTimer=function(id){if(!id)throw new Error("null id");var url=this.getUrl("LiveTv/Timers/"+id);return this.getJSON(url)},ApiClient.prototype.getNewLiveTvTimerDefaults=function(options){options=options||{};var url=this.getUrl("LiveTv/Timers/Defaults",options);return this.getJSON(url)},ApiClient.prototype.createLiveTvTimer=function(item){if(!item)throw new Error("null item");var url=this.getUrl("LiveTv/Timers");return this.ajax({type:"POST",url:url,data:JSON.stringify(item),contentType:"application/json"})},ApiClient.prototype.updateLiveTvTimer=function(item){if(!item)throw new Error("null item");var url=this.getUrl("LiveTv/Timers/"+item.Id);return this.ajax({type:"POST",url:url,data:JSON.stringify(item),contentType:"application/json"})},ApiClient.prototype.resetLiveTvTuner=function(id){if(!id)throw new Error("null id");var url=this.getUrl("LiveTv/Tuners/"+id+"/Reset");return this.ajax({type:"POST",url:url})},ApiClient.prototype.getLiveTvSeriesTimers=function(options){var url=this.getUrl("LiveTv/SeriesTimers",options||{});return this.getJSON(url)},ApiClient.prototype.getLiveTvSeriesTimer=function(id){if(!id)throw new Error("null id");var url=this.getUrl("LiveTv/SeriesTimers/"+id);return this.getJSON(url)},ApiClient.prototype.cancelLiveTvSeriesTimer=function(id){if(!id)throw new Error("null id");var url=this.getUrl("LiveTv/SeriesTimers/"+id);return this.ajax({type:"DELETE",url:url})},ApiClient.prototype.createLiveTvSeriesTimer=function(item){if(!item)throw new Error("null item");var url=this.getUrl("LiveTv/SeriesTimers");return this.ajax({type:"POST",url:url,data:JSON.stringify(item),contentType:"application/json"})},ApiClient.prototype.updateLiveTvSeriesTimer=function(item){if(!item)throw new Error("null item");var url=this.getUrl("LiveTv/SeriesTimers/"+item.Id);return this.ajax({type:"POST",url:url,data:JSON.stringify(item),contentType:"application/json"})},ApiClient.prototype.getRegistrationInfo=function(feature){var url=this.getUrl("Registrations/"+feature);return this.getJSON(url)},ApiClient.prototype.getSystemInfo=function(){var url=this.getUrl("System/Info"),instance=this;return this.getJSON(url).then(function(info){return instance.setSystemInfo(info),Promise.resolve(info)})},ApiClient.prototype.getSyncStatus=function(itemId){var url=this.getUrl("Sync/"+itemId+"/Status");return this.ajax({url:url,type:"POST",dataType:"json",contentType:"application/json",data:JSON.stringify({TargetId:this.deviceId()})})},ApiClient.prototype.getPublicSystemInfo=function(){var url=this.getUrl("System/Info/Public"),instance=this;return this.getJSON(url).then(function(info){return instance.setSystemInfo(info),Promise.resolve(info)})},ApiClient.prototype.getInstantMixFromItem=function(itemId,options){var url=this.getUrl("Items/"+itemId+"/InstantMix",options);return this.getJSON(url)},ApiClient.prototype.getEpisodes=function(itemId,options){var url=this.getUrl("Shows/"+itemId+"/Episodes",options);return this.getJSON(url)},ApiClient.prototype.getDisplayPreferences=function(id,userId,app){var url=this.getUrl("DisplayPreferences/"+id,{userId:userId,client:app});return this.getJSON(url)},ApiClient.prototype.updateDisplayPreferences=function(id,obj,userId,app){var url=this.getUrl("DisplayPreferences/"+id,{userId:userId,client:app});return this.ajax({type:"POST",url:url,data:JSON.stringify(obj),contentType:"application/json"})},ApiClient.prototype.getSeasons=function(itemId,options){var url=this.getUrl("Shows/"+itemId+"/Seasons",options);return this.getJSON(url)},ApiClient.prototype.getSimilarItems=function(itemId,options){var url=this.getUrl("Items/"+itemId+"/Similar",options);return this.getJSON(url)},ApiClient.prototype.getCultures=function(){var url=this.getUrl("Localization/cultures");return this.getJSON(url)},ApiClient.prototype.getCountries=function(){var url=this.getUrl("Localization/countries");return this.getJSON(url)},ApiClient.prototype.getPlaybackInfo=function(itemId,options,deviceProfile){var postData={DeviceProfile:deviceProfile};return this.ajax({url:this.getUrl("Items/"+itemId+"/PlaybackInfo",options),type:"POST",data:JSON.stringify(postData),contentType:"application/json",dataType:"json"})},ApiClient.prototype.getLiveStreamMediaInfo=function(liveStreamId){var postData={LiveStreamId:liveStreamId};return this.ajax({url:this.getUrl("LiveStreams/MediaInfo"),type:"POST",data:JSON.stringify(postData),contentType:"application/json",dataType:"json"})},ApiClient.prototype.getIntros=function(itemId){return this.getJSON(this.getUrl("Users/"+this.getCurrentUserId()+"/Items/"+itemId+"/Intros"))},ApiClient.prototype.getDirectoryContents=function(path,options){if(!path)throw new Error("null path");if("string"!=typeof path)throw new Error("invalid path");options=options||{},options.path=path;var url=this.getUrl("Environment/DirectoryContents",options);return this.getJSON(url)},ApiClient.prototype.getNetworkShares=function(path){if(!path)throw new Error("null path");var options={};options.path=path;var url=this.getUrl("Environment/NetworkShares",options);return this.getJSON(url)},ApiClient.prototype.getParentPath=function(path){if(!path)throw new Error("null path");var options={};options.path=path;var url=this.getUrl("Environment/ParentPath",options);return this.ajax({type:"GET",url:url,dataType:"text"})},ApiClient.prototype.getDrives=function(){var url=this.getUrl("Environment/Drives");return this.getJSON(url)},ApiClient.prototype.getNetworkDevices=function(){var url=this.getUrl("Environment/NetworkDevices");return this.getJSON(url)},ApiClient.prototype.cancelPackageInstallation=function(installationId){if(!installationId)throw new Error("null installationId");var url=this.getUrl("Packages/Installing/"+installationId);return this.ajax({type:"DELETE",url:url})},ApiClient.prototype.refreshItem=function(itemId,options){if(!itemId)throw new Error("null itemId");var url=this.getUrl("Items/"+itemId+"/Refresh",options||{});return this.ajax({type:"POST",url:url})},ApiClient.prototype.installPlugin=function(name,guid,updateClass,version){if(!name)throw new Error("null name");if(!updateClass)throw new Error("null updateClass");var options={updateClass:updateClass,AssemblyGuid:guid};version&&(options.version=version);var url=this.getUrl("Packages/Installed/"+name,options);return this.ajax({type:"POST",url:url})},ApiClient.prototype.restartServer=function(){var url=this.getUrl("System/Restart");return this.ajax({type:"POST",url:url})},ApiClient.prototype.shutdownServer=function(){var url=this.getUrl("System/Shutdown");return this.ajax({type:"POST",url:url})},ApiClient.prototype.getPackageInfo=function(name,guid){if(!name)throw new Error("null name");var options={AssemblyGuid:guid},url=this.getUrl("Packages/"+name,options);return this.getJSON(url)},ApiClient.prototype.getAvailableApplicationUpdate=function(){var url=this.getUrl("Packages/Updates",{PackageType:"System"});return this.getJSON(url)},ApiClient.prototype.getAvailablePluginUpdates=function(){var url=this.getUrl("Packages/Updates",{PackageType:"UserInstalled"});return this.getJSON(url)},ApiClient.prototype.getVirtualFolders=function(){var url="Library/VirtualFolders";return url=this.getUrl(url),this.getJSON(url)},ApiClient.prototype.getPhysicalPaths=function(){var url=this.getUrl("Library/PhysicalPaths");return this.getJSON(url)},ApiClient.prototype.getServerConfiguration=function(){var url=this.getUrl("System/Configuration");return this.getJSON(url)},ApiClient.prototype.getDevicesOptions=function(){var url=this.getUrl("System/Configuration/devices");return this.getJSON(url)},ApiClient.prototype.getContentUploadHistory=function(){var url=this.getUrl("Devices/CameraUploads",{DeviceId:this.deviceId()});return this.getJSON(url)},ApiClient.prototype.getNamedConfiguration=function(name){var url=this.getUrl("System/Configuration/"+name);return this.getJSON(url)},ApiClient.prototype.getScheduledTasks=function(options){options=options||{} -;var url=this.getUrl("ScheduledTasks",options);return this.getJSON(url)},ApiClient.prototype.startScheduledTask=function(id){if(!id)throw new Error("null id");var url=this.getUrl("ScheduledTasks/Running/"+id);return this.ajax({type:"POST",url:url})},ApiClient.prototype.getScheduledTask=function(id){if(!id)throw new Error("null id");var url=this.getUrl("ScheduledTasks/"+id);return this.getJSON(url)},ApiClient.prototype.getNextUpEpisodes=function(options){var url=this.getUrl("Shows/NextUp",options);return this.getJSON(url)},ApiClient.prototype.stopScheduledTask=function(id){if(!id)throw new Error("null id");var url=this.getUrl("ScheduledTasks/Running/"+id);return this.ajax({type:"DELETE",url:url})},ApiClient.prototype.getPluginConfiguration=function(id){if(!id)throw new Error("null Id");var url=this.getUrl("Plugins/"+id+"/Configuration");return this.getJSON(url)},ApiClient.prototype.getAvailablePlugins=function(options){options=options||{},options.PackageType="UserInstalled";var url=this.getUrl("Packages",options);return this.getJSON(url)},ApiClient.prototype.uninstallPlugin=function(id){if(!id)throw new Error("null Id");var url=this.getUrl("Plugins/"+id);return this.ajax({type:"DELETE",url:url})},ApiClient.prototype.removeVirtualFolder=function(name,refreshLibrary){if(!name)throw new Error("null name");var url="Library/VirtualFolders";return url=this.getUrl(url,{refreshLibrary:!!refreshLibrary,name:name}),this.ajax({type:"DELETE",url:url})},ApiClient.prototype.addVirtualFolder=function(name,type,refreshLibrary,libraryOptions){if(!name)throw new Error("null name");var options={};type&&(options.collectionType=type),options.refreshLibrary=!!refreshLibrary,options.name=name;var url="Library/VirtualFolders";return url=this.getUrl(url,options),this.ajax({type:"POST",url:url,data:JSON.stringify({LibraryOptions:libraryOptions}),contentType:"application/json"})},ApiClient.prototype.updateVirtualFolderOptions=function(id,libraryOptions){if(!id)throw new Error("null name");var url="Library/VirtualFolders/LibraryOptions";return url=this.getUrl(url),this.ajax({type:"POST",url:url,data:JSON.stringify({Id:id,LibraryOptions:libraryOptions}),contentType:"application/json"})},ApiClient.prototype.renameVirtualFolder=function(name,newName,refreshLibrary){if(!name)throw new Error("null name");var url="Library/VirtualFolders/Name";return url=this.getUrl(url,{refreshLibrary:!!refreshLibrary,newName:newName,name:name}),this.ajax({type:"POST",url:url})},ApiClient.prototype.addMediaPath=function(virtualFolderName,mediaPath,networkSharePath,refreshLibrary){if(!virtualFolderName)throw new Error("null virtualFolderName");if(!mediaPath)throw new Error("null mediaPath");var url="Library/VirtualFolders/Paths",pathInfo={Path:mediaPath};return networkSharePath&&(pathInfo.NetworkPath=networkSharePath),url=this.getUrl(url,{refreshLibrary:!!refreshLibrary}),this.ajax({type:"POST",url:url,data:JSON.stringify({Name:virtualFolderName,PathInfo:pathInfo}),contentType:"application/json"})},ApiClient.prototype.updateMediaPath=function(virtualFolderName,pathInfo){if(!virtualFolderName)throw new Error("null virtualFolderName");if(!pathInfo)throw new Error("null pathInfo");var url="Library/VirtualFolders/Paths/Update";return url=this.getUrl(url),this.ajax({type:"POST",url:url,data:JSON.stringify({Name:virtualFolderName,PathInfo:pathInfo}),contentType:"application/json"})},ApiClient.prototype.removeMediaPath=function(virtualFolderName,mediaPath,refreshLibrary){if(!virtualFolderName)throw new Error("null virtualFolderName");if(!mediaPath)throw new Error("null mediaPath");var url="Library/VirtualFolders/Paths";return url=this.getUrl(url,{refreshLibrary:!!refreshLibrary,path:mediaPath,name:virtualFolderName}),this.ajax({type:"DELETE",url:url})},ApiClient.prototype.deleteUser=function(id){if(!id)throw new Error("null id");var url=this.getUrl("Users/"+id);return this.ajax({type:"DELETE",url:url})},ApiClient.prototype.deleteUserImage=function(userId,imageType,imageIndex){if(!userId)throw new Error("null userId");if(!imageType)throw new Error("null imageType");var url=this.getUrl("Users/"+userId+"/Images/"+imageType);return null!=imageIndex&&(url+="/"+imageIndex),this.ajax({type:"DELETE",url:url})},ApiClient.prototype.deleteItemImage=function(itemId,imageType,imageIndex){if(!imageType)throw new Error("null imageType");var url=this.getUrl("Items/"+itemId+"/Images");return url+="/"+imageType,null!=imageIndex&&(url+="/"+imageIndex),this.ajax({type:"DELETE",url:url})},ApiClient.prototype.deleteItem=function(itemId){if(!itemId)throw new Error("null itemId");var url=this.getUrl("Items/"+itemId);return this.ajax({type:"DELETE",url:url})},ApiClient.prototype.stopActiveEncodings=function(playSessionId){var options={deviceId:this.deviceId()};playSessionId&&(options.PlaySessionId=playSessionId);var url=this.getUrl("Videos/ActiveEncodings",options);return this.ajax({type:"DELETE",url:url})},ApiClient.prototype.reportCapabilities=function(options){var url=this.getUrl("Sessions/Capabilities/Full");return this.ajax({type:"POST",url:url,data:JSON.stringify(options),contentType:"application/json"})},ApiClient.prototype.updateItemImageIndex=function(itemId,imageType,imageIndex,newIndex){if(!imageType)throw new Error("null imageType");var options={newIndex:newIndex},url=this.getUrl("Items/"+itemId+"/Images/"+imageType+"/"+imageIndex+"/Index",options);return this.ajax({type:"POST",url:url})},ApiClient.prototype.getItemImageInfos=function(itemId){var url=this.getUrl("Items/"+itemId+"/Images");return this.getJSON(url)},ApiClient.prototype.getCriticReviews=function(itemId,options){if(!itemId)throw new Error("null itemId");var url=this.getUrl("Items/"+itemId+"/CriticReviews",options);return this.getJSON(url)},ApiClient.prototype.getItemDownloadUrl=function(itemId){if(!itemId)throw new Error("itemId cannot be empty");var url="Items/"+itemId+"/Download";return this.getUrl(url,{api_key:this.accessToken()})},ApiClient.prototype.getSessions=function(options){var url=this.getUrl("Sessions",options);return this.getJSON(url)},ApiClient.prototype.uploadUserImage=function(userId,imageType,file){if(!userId)throw new Error("null userId");if(!imageType)throw new Error("null imageType");if(!file)throw new Error("File must be an image.");if("image/png"!==file.type&&"image/jpeg"!==file.type&&"image/jpeg"!==file.type)throw new Error("File must be an image.");var instance=this;return new Promise(function(resolve,reject){var reader=new FileReader;reader.onerror=function(){reject()},reader.onabort=function(){reject()},reader.onload=function(e){var data=e.target.result.split(",")[1],url=instance.getUrl("Users/"+userId+"/Images/"+imageType);instance.ajax({type:"POST",url:url,data:data,contentType:"image/"+file.name.substring(file.name.lastIndexOf(".")+1)}).then(resolve,reject)},reader.readAsDataURL(file)})},ApiClient.prototype.uploadItemImage=function(itemId,imageType,file){if(!itemId)throw new Error("null itemId");if(!imageType)throw new Error("null imageType");if(!file)throw new Error("File must be an image.");if("image/png"!==file.type&&"image/jpeg"!==file.type&&"image/jpeg"!==file.type)throw new Error("File must be an image.");var url=this.getUrl("Items/"+itemId+"/Images");url+="/"+imageType;var instance=this;return new Promise(function(resolve,reject){var reader=new FileReader;reader.onerror=function(){reject()},reader.onabort=function(){reject()},reader.onload=function(e){var data=e.target.result.split(",")[1];instance.ajax({type:"POST",url:url,data:data,contentType:"image/"+file.name.substring(file.name.lastIndexOf(".")+1)}).then(resolve,reject)},reader.readAsDataURL(file)})},ApiClient.prototype.getInstalledPlugins=function(){var options={},url=this.getUrl("Plugins",options);return this.getJSON(url)},ApiClient.prototype.getUser=function(id){if(!id)throw new Error("Must supply a userId");var url=this.getUrl("Users/"+id);return this.getJSON(url)},ApiClient.prototype.getStudio=function(name,userId){if(!name)throw new Error("null name");var options={};userId&&(options.userId=userId);var url=this.getUrl("Studios/"+this.encodeName(name),options);return this.getJSON(url)},ApiClient.prototype.getGenre=function(name,userId){if(!name)throw new Error("null name");var options={};userId&&(options.userId=userId);var url=this.getUrl("Genres/"+this.encodeName(name),options);return this.getJSON(url)},ApiClient.prototype.getMusicGenre=function(name,userId){if(!name)throw new Error("null name");var options={};userId&&(options.userId=userId);var url=this.getUrl("MusicGenres/"+this.encodeName(name),options);return this.getJSON(url)},ApiClient.prototype.getGameGenre=function(name,userId){if(!name)throw new Error("null name");var options={};userId&&(options.userId=userId);var url=this.getUrl("GameGenres/"+this.encodeName(name),options);return this.getJSON(url)},ApiClient.prototype.getArtist=function(name,userId){if(!name)throw new Error("null name");var options={};userId&&(options.userId=userId);var url=this.getUrl("Artists/"+this.encodeName(name),options);return this.getJSON(url)},ApiClient.prototype.getPerson=function(name,userId){if(!name)throw new Error("null name");var options={};userId&&(options.userId=userId);var url=this.getUrl("Persons/"+this.encodeName(name),options);return this.getJSON(url)},ApiClient.prototype.getPublicUsers=function(){var url=this.getUrl("users/public");return this.ajax({type:"GET",url:url,dataType:"json"},!1)},ApiClient.prototype.getUsers=function(options){var url=this.getUrl("users",options||{});return this.getJSON(url)},ApiClient.prototype.getParentalRatings=function(){var url=this.getUrl("Localization/ParentalRatings");return this.getJSON(url)},ApiClient.prototype.getDefaultImageQuality=function(imageType){return"backdrop"===imageType.toLowerCase()?80:90},ApiClient.prototype.getUserImageUrl=function(userId,options){if(!userId)throw new Error("null userId");options=options||{};var url="Users/"+userId+"/Images/"+options.type;return null!=options.index&&(url+="/"+options.index),normalizeImageOptions(this,options),delete options.type,delete options.index,this.getUrl(url,options)},ApiClient.prototype.getImageUrl=function(itemId,options){if(!itemId)throw new Error("itemId cannot be empty");options=options||{};var url="Items/"+itemId+"/Images/"+options.type;return null!=options.index&&(url+="/"+options.index),options.quality=options.quality||this.getDefaultImageQuality(options.type),this.normalizeImageOptions&&this.normalizeImageOptions(options),delete options.type,delete options.index,this.getUrl(url,options)},ApiClient.prototype.getScaledImageUrl=function(itemId,options){if(!itemId)throw new Error("itemId cannot be empty");options=options||{};var url="Items/"+itemId+"/Images/"+options.type;return null!=options.index&&(url+="/"+options.index),normalizeImageOptions(this,options),delete options.type,delete options.index,delete options.minScale,this.getUrl(url,options)},ApiClient.prototype.getThumbImageUrl=function(item,options){if(!item)throw new Error("null item");return options=options||{},options.imageType="thumb",item.ImageTags&&item.ImageTags.Thumb?(options.tag=item.ImageTags.Thumb,this.getImageUrl(item.Id,options)):item.ParentThumbItemId?(options.tag=item.ImageTags.ParentThumbImageTag,this.getImageUrl(item.ParentThumbItemId,options)):null},ApiClient.prototype.updateUserPassword=function(userId,currentPassword,newPassword){if(!userId)return Promise.reject();var url=this.getUrl("Users/"+userId+"/Password");return this.ajax({type:"POST",url:url,data:JSON.stringify({CurrentPw:currentPassword||"",NewPw:newPassword}),contentType:"application/json"})},ApiClient.prototype.updateEasyPassword=function(userId,newPassword){if(!userId)return void Promise.reject();var url=this.getUrl("Users/"+userId+"/EasyPassword");return this.ajax({type:"POST",url:url,data:{NewPw:newPassword}})},ApiClient.prototype.resetUserPassword=function(userId){if(!userId)throw new Error("null userId");var url=this.getUrl("Users/"+userId+"/Password"),postData={};return postData.resetPassword=!0,this.ajax({type:"POST",url:url,data:postData})},ApiClient.prototype.resetEasyPassword=function(userId){if(!userId)throw new Error("null userId");var url=this.getUrl("Users/"+userId+"/EasyPassword"),postData={};return postData.resetPassword=!0,this.ajax({type:"POST",url:url,data:postData})},ApiClient.prototype.updateServerConfiguration=function(configuration){if(!configuration)throw new Error("null configuration");var url=this.getUrl("System/Configuration");return this.ajax({type:"POST",url:url,data:JSON.stringify(configuration),contentType:"application/json"})},ApiClient.prototype.updateNamedConfiguration=function(name,configuration){if(!configuration)throw new Error("null configuration");var url=this.getUrl("System/Configuration/"+name);return this.ajax({type:"POST",url:url,data:JSON.stringify(configuration),contentType:"application/json"})},ApiClient.prototype.updateItem=function(item){if(!item)throw new Error("null item");var url=this.getUrl("Items/"+item.Id);return this.ajax({type:"POST",url:url,data:JSON.stringify(item),contentType:"application/json"})},ApiClient.prototype.updatePluginSecurityInfo=function(info){var url=this.getUrl("Plugins/SecurityInfo");return this.ajax({type:"POST",url:url,data:JSON.stringify(info),contentType:"application/json"})},ApiClient.prototype.createUser=function(name){var url=this.getUrl("Users/New");return this.ajax({type:"POST",url:url,data:{Name:name},dataType:"json"})},ApiClient.prototype.updateUser=function(user){if(!user)throw new Error("null user");var url=this.getUrl("Users/"+user.Id);return this.ajax({type:"POST",url:url,data:JSON.stringify(user),contentType:"application/json"})},ApiClient.prototype.updateUserPolicy=function(userId,policy){if(!userId)throw new Error("null userId");if(!policy)throw new Error("null policy");var url=this.getUrl("Users/"+userId+"/Policy");return this.ajax({type:"POST",url:url,data:JSON.stringify(policy),contentType:"application/json"})},ApiClient.prototype.updateUserConfiguration=function(userId,configuration){if(!userId)throw new Error("null userId");if(!configuration)throw new Error("null configuration");var url=this.getUrl("Users/"+userId+"/Configuration");return this.ajax({type:"POST",url:url,data:JSON.stringify(configuration),contentType:"application/json"})},ApiClient.prototype.updateScheduledTaskTriggers=function(id,triggers){if(!id)throw new Error("null id");if(!triggers)throw new Error("null triggers");var url=this.getUrl("ScheduledTasks/"+id+"/Triggers");return this.ajax({type:"POST",url:url,data:JSON.stringify(triggers),contentType:"application/json"})},ApiClient.prototype.updatePluginConfiguration=function(id,configuration){if(!id)throw new Error("null Id");if(!configuration)throw new Error("null configuration");var url=this.getUrl("Plugins/"+id+"/Configuration");return this.ajax({type:"POST",url:url,data:JSON.stringify(configuration),contentType:"application/json"})},ApiClient.prototype.getAncestorItems=function(itemId,userId){if(!itemId)throw new Error("null itemId");var options={};userId&&(options.userId=userId);var url=this.getUrl("Items/"+itemId+"/Ancestors",options);return this.getJSON(url)},ApiClient.prototype.getItems=function(userId,options){var url;return url="string"===(typeof userId).toString().toLowerCase()?this.getUrl("Users/"+userId+"/Items",options):this.getUrl("Items",options),this.getJSON(url)},ApiClient.prototype.getResumableItems=function(userId,options){return this.isMinServerVersion("3.2.33")?this.getJSON(this.getUrl("Users/"+userId+"/Items/Resume",options)):this.getItems(userId,Object.assign({SortBy:"DatePlayed",SortOrder:"Descending",Filters:"IsResumable",Recursive:!0,CollapseBoxSetItems:!1,ExcludeLocationTypes:"Virtual"},options))},ApiClient.prototype.getMovieRecommendations=function(options){return this.getJSON(this.getUrl("Movies/Recommendations",options))},ApiClient.prototype.getUpcomingEpisodes=function(options){return this.getJSON(this.getUrl("Shows/Upcoming",options))},ApiClient.prototype.getUserViews=function(options,userId){options=options||{};var url=this.getUrl("Users/"+(userId||this.getCurrentUserId())+"/Views",options);return this.getJSON(url)},ApiClient.prototype.getArtists=function(userId,options){if(!userId)throw new Error("null userId");options=options||{},options.userId=userId;var url=this.getUrl("Artists",options);return this.getJSON(url)},ApiClient.prototype.getAlbumArtists=function(userId,options){if(!userId)throw new Error("null userId");options=options||{},options.userId=userId;var url=this.getUrl("Artists/AlbumArtists",options);return this.getJSON(url)},ApiClient.prototype.getGenres=function(userId,options){if(!userId)throw new Error("null userId");options=options||{},options.userId=userId;var url=this.getUrl("Genres",options);return this.getJSON(url)},ApiClient.prototype.getMusicGenres=function(userId,options){if(!userId)throw new Error("null userId");options=options||{},options.userId=userId;var url=this.getUrl("MusicGenres",options);return this.getJSON(url)},ApiClient.prototype.getGameGenres=function(userId,options){if(!userId)throw new Error("null userId");options=options||{},options.userId=userId;var url=this.getUrl("GameGenres",options);return this.getJSON(url)},ApiClient.prototype.getPeople=function(userId,options){if(!userId)throw new Error("null userId");options=options||{},options.userId=userId;var url=this.getUrl("Persons",options);return this.getJSON(url)},ApiClient.prototype.getStudios=function(userId,options){if(!userId)throw new Error("null userId");options=options||{},options.userId=userId;var url=this.getUrl("Studios",options);return this.getJSON(url)},ApiClient.prototype.getLocalTrailers=function(userId,itemId){if(!userId)throw new Error("null userId");if(!itemId)throw new Error("null itemId");var url=this.getUrl("Users/"+userId+"/Items/"+itemId+"/LocalTrailers");return this.getJSON(url)},ApiClient.prototype.getGameSystems=function(){var options={},userId=this.getCurrentUserId();userId&&(options.userId=userId);var url=this.getUrl("Games/SystemSummaries",options);return this.getJSON(url)},ApiClient.prototype.getAdditionalVideoParts=function(userId,itemId){if(!itemId)throw new Error("null itemId");var options={};userId&&(options.userId=userId);var url=this.getUrl("Videos/"+itemId+"/AdditionalParts",options);return this.getJSON(url)},ApiClient.prototype.getThemeMedia=function(userId,itemId,inherit){if(!itemId)throw new Error("null itemId");var options={};userId&&(options.userId=userId),options.InheritFromParent=inherit||!1;var url=this.getUrl("Items/"+itemId+"/ThemeMedia",options);return this.getJSON(url)},ApiClient.prototype.getSearchHints=function(options){var url=this.getUrl("Search/Hints",options),serverId=this.serverId();return this.getJSON(url).then(function(result){return result.SearchHints.forEach(function(i){i.ServerId=serverId}),result})},ApiClient.prototype.getSpecialFeatures=function(userId,itemId){if(!userId)throw new Error("null userId");if(!itemId)throw new Error("null itemId");var url=this.getUrl("Users/"+userId+"/Items/"+itemId+"/SpecialFeatures");return this.getJSON(url)},ApiClient.prototype.getDateParamValue=function(date){function formatDigit(i){return i<10?"0"+i:i}var d=date;return""+d.getFullYear()+formatDigit(d.getMonth()+1)+formatDigit(d.getDate())+formatDigit(d.getHours())+formatDigit(d.getMinutes())+formatDigit(d.getSeconds())},ApiClient.prototype.markPlayed=function(userId,itemId,date){if(!userId)throw new Error("null userId");if(!itemId)throw new Error("null itemId");var options={};date&&(options.DatePlayed=this.getDateParamValue(date));var url=this.getUrl("Users/"+userId+"/PlayedItems/"+itemId,options);return this.ajax({type:"POST",url:url,dataType:"json"})},ApiClient.prototype.markUnplayed=function(userId,itemId){if(!userId)throw new Error("null userId");if(!itemId)throw new Error("null itemId");var url=this.getUrl("Users/"+userId+"/PlayedItems/"+itemId);return this.ajax({type:"DELETE",url:url,dataType:"json"})},ApiClient.prototype.updateFavoriteStatus=function(userId,itemId,isFavorite){if(!userId)throw new Error("null userId");if(!itemId)throw new Error("null itemId");var url=this.getUrl("Users/"+userId+"/FavoriteItems/"+itemId),method=isFavorite?"POST":"DELETE";return this.ajax({type:method,url:url,dataType:"json"})},ApiClient.prototype.updateUserItemRating=function(userId,itemId,likes){if(!userId)throw new Error("null userId");if(!itemId)throw new Error("null itemId");var url=this.getUrl("Users/"+userId+"/Items/"+itemId+"/Rating",{likes:likes});return this.ajax({type:"POST",url:url,dataType:"json"})},ApiClient.prototype.getItemCounts=function(userId){var options={};userId&&(options.userId=userId);var url=this.getUrl("Items/Counts",options);return this.getJSON(url)},ApiClient.prototype.clearUserItemRating=function(userId,itemId){if(!userId)throw new Error("null userId");if(!itemId)throw new Error("null itemId");var url=this.getUrl("Users/"+userId+"/Items/"+itemId+"/Rating");return this.ajax({type:"DELETE",url:url,dataType:"json"})},ApiClient.prototype.reportPlaybackStart=function(options){if(!options)throw new Error("null options");this.lastPlaybackProgressReport=0,this.lastPlaybackProgressReportTicks=null,stopBitrateDetection(this);var url=this.getUrl("Sessions/Playing");return this.ajax({type:"POST",data:JSON.stringify(options),contentType:"application/json",url:url})},ApiClient.prototype.reportPlaybackProgress=function(options){if(!options)throw new Error("null options");var newPositionTicks=options.PositionTicks;if("timeupdate"===(options.EventName||"timeupdate")){var now=(new Date).getTime(),msSinceLastReport=now-(this.lastPlaybackProgressReport||0);if(msSinceLastReport<=1e4){if(!newPositionTicks)return Promise.resolve();var expectedReportTicks=1e4*msSinceLastReport+(this.lastPlaybackProgressReportTicks||0);if(Math.abs((newPositionTicks||0)-expectedReportTicks)<5e7)return Promise.resolve()}this.lastPlaybackProgressReport=now}else this.lastPlaybackProgressReport=0;this.lastPlaybackProgressReportTicks=newPositionTicks;var url=this.getUrl("Sessions/Playing/Progress");return this.ajax({type:"POST",data:JSON.stringify(options),contentType:"application/json",url:url})},ApiClient.prototype.reportOfflineActions=function(actions){if(!actions)throw new Error("null actions");var url=this.getUrl("Sync/OfflineActions");return this.ajax({type:"POST",data:JSON.stringify(actions),contentType:"application/json",url:url})},ApiClient.prototype.syncData=function(data){if(!data)throw new Error("null data");var url=this.getUrl("Sync/Data");return this.ajax({type:"POST",data:JSON.stringify(data),contentType:"application/json",url:url,dataType:"json"})},ApiClient.prototype.getReadySyncItems=function(deviceId){if(!deviceId)throw new Error("null deviceId");var url=this.getUrl("Sync/Items/Ready",{TargetId:deviceId});return this.getJSON(url)},ApiClient.prototype.reportSyncJobItemTransferred=function(syncJobItemId){if(!syncJobItemId)throw new Error("null syncJobItemId");var url=this.getUrl("Sync/JobItems/"+syncJobItemId+"/Transferred");return this.ajax({type:"POST",url:url})},ApiClient.prototype.cancelSyncItems=function(itemIds,targetId){if(!itemIds)throw new Error("null itemIds");var url=this.getUrl("Sync/"+(targetId||this.deviceId())+"/Items",{ItemIds:itemIds.join(",")});return this.ajax({type:"DELETE",url:url})},ApiClient.prototype.reportPlaybackStopped=function(options){if(!options)throw new Error("null options");this.lastPlaybackProgressReport=0,this.lastPlaybackProgressReportTicks=null,redetectBitrate(this);var url=this.getUrl("Sessions/Playing/Stopped");return this.ajax({type:"POST",data:JSON.stringify(options),contentType:"application/json",url:url})},ApiClient.prototype.sendPlayCommand=function(sessionId,options){if(!sessionId)throw new Error("null sessionId");if(!options)throw new Error("null options");var url=this.getUrl("Sessions/"+sessionId+"/Playing",options);return this.ajax({type:"POST",url:url})},ApiClient.prototype.sendCommand=function(sessionId,command){if(!sessionId)throw new Error("null sessionId");if(!command)throw new Error("null command");var url=this.getUrl("Sessions/"+sessionId+"/Command"),ajaxOptions={type:"POST",url:url};return ajaxOptions.data=JSON.stringify(command),ajaxOptions.contentType="application/json",this.ajax(ajaxOptions)},ApiClient.prototype.sendMessageCommand=function(sessionId,options){if(!sessionId)throw new Error("null sessionId");if(!options)throw new Error("null options");var url=this.getUrl("Sessions/"+sessionId+"/Message"),ajaxOptions={type:"POST",url:url};return ajaxOptions.data=JSON.stringify(options),ajaxOptions.contentType="application/json",this.ajax(ajaxOptions)},ApiClient.prototype.sendPlayStateCommand=function(sessionId,command,options){if(!sessionId)throw new Error("null sessionId");if(!command)throw new Error("null command");var url=this.getUrl("Sessions/"+sessionId+"/Playing/"+command,options||{});return this.ajax({type:"POST",url:url})},ApiClient.prototype.createPackageReview=function(review){var url=this.getUrl("Packages/Reviews/"+review.id,review);return this.ajax({type:"POST",url:url})},ApiClient.prototype.getPackageReviews=function(packageId,minRating,maxRating,limit){if(!packageId)throw new Error("null packageId");var options={};minRating&&(options.MinRating=minRating),maxRating&&(options.MaxRating=maxRating),limit&&(options.Limit=limit);var url=this.getUrl("Packages/"+packageId+"/Reviews",options);return this.getJSON(url)},ApiClient.prototype.getSavedEndpointInfo=function(){return this._endPointInfo},ApiClient.prototype.getEndpointInfo=function(){var savedValue=this._endPointInfo;if(savedValue)return Promise.resolve(savedValue);var instance=this;return this.getJSON(this.getUrl("System/Endpoint")).then(function(endPointInfo){return setSavedEndpointInfo(instance,endPointInfo),endPointInfo})},ApiClient.prototype.getWakeOnLanInfo=function(){return this.getJSON(this.getUrl("System/WakeOnLanInfo"))},ApiClient.prototype.getLatestItems=function(options){return options=options||{},this.getJSON(this.getUrl("Users/"+this.getCurrentUserId()+"/Items/Latest",options))},ApiClient.prototype.getFilters=function(options){return this.getJSON(this.getUrl("Items/Filters2",options))},ApiClient.prototype.supportsWakeOnLan=function(){return!!wakeOnLan.isSupported()&&getCachedWakeOnLanInfo(this).length>0},ApiClient.prototype.wakeOnLan=function(){var infos=getCachedWakeOnLanInfo(this);return new Promise(function(resolve,reject){sendNextWakeOnLan(infos,0,resolve)})},ApiClient.prototype.setSystemInfo=function(info){this._serverVersion=info.Version},ApiClient.prototype.serverVersion=function(){return this._serverVersion},ApiClient.prototype.isMinServerVersion=function(version){var serverVersion=this.serverVersion();return!!serverVersion&&compareVersions(serverVersion,version)>=0},ApiClient.prototype.handleMessageReceived=function(msg){onMessageReceivedInternal(this,msg)},ApiClient}); \ No newline at end of file +define(["events", "appStorage", "wakeOnLan"], function(events, appStorage, wakeOnLan) { + "use strict"; + + function redetectBitrate(instance) { + stopBitrateDetection(instance), instance.accessToken() && !1 !== instance.enableAutomaticBitrateDetection && setTimeout(redetectBitrateInternal.bind(instance), 6e3) + } + + function redetectBitrateInternal() { + this.accessToken() && this.detectBitrate() + } + + function stopBitrateDetection(instance) { + instance.detectTimeout && clearTimeout(instance.detectTimeout) + } + + function replaceAll(originalString, strReplace, strWith) { + var reg = new RegExp(strReplace, "ig"); + return originalString.replace(reg, strWith) + } + + function onFetchFail(instance, url, response) { + events.trigger(instance, "requestfail", [{ + url: url, + status: response.status, + errorCode: response.headers ? response.headers.get("X-Application-Error-Code") : null + }]) + } + + function paramsToString(params) { + var values = []; + for (var key in params) { + var value = params[key]; + null !== value && void 0 !== value && "" !== value && values.push(encodeURIComponent(key) + "=" + encodeURIComponent(value)) + } + return values.join("&") + } + + function fetchWithTimeout(url, options, timeoutMs) { + return new Promise(function(resolve, reject) { + var timeout = setTimeout(reject, timeoutMs); + options = options || {}, options.credentials = "same-origin", fetch(url, options).then(function(response) { + clearTimeout(timeout), resolve(response) + }, function(error) { + clearTimeout(timeout), reject(error) + }) + }) + } + + function getFetchPromise(request) { + var headers = request.headers || {}; + "json" === request.dataType && (headers.accept = "application/json"); + var fetchRequest = { + headers: headers, + method: request.type, + credentials: "same-origin" + }, + contentType = request.contentType; + return request.data && ("string" == typeof request.data ? fetchRequest.body = request.data : (fetchRequest.body = paramsToString(request.data), contentType = contentType || "application/x-www-form-urlencoded; charset=UTF-8")), contentType && (headers["Content-Type"] = contentType), request.timeout ? fetchWithTimeout(request.url, fetchRequest, request.timeout) : fetch(request.url, fetchRequest) + } + + function ApiClient(serverAddress, appName, appVersion, deviceName, deviceId, devicePixelRatio) { + if (!serverAddress) throw new Error("Must supply a serverAddress"); + console.log("ApiClient serverAddress: " + serverAddress), console.log("ApiClient appName: " + appName), console.log("ApiClient appVersion: " + appVersion), console.log("ApiClient deviceName: " + deviceName), console.log("ApiClient deviceId: " + deviceId), this._serverInfo = {}, this._serverAddress = serverAddress, this._deviceId = deviceId, this._deviceName = deviceName, this._appName = appName, this._appVersion = appVersion, this._devicePixelRatio = devicePixelRatio + } + + function setSavedEndpointInfo(instance, info) { + instance._endPointInfo = info + } + + function getTryConnectPromise(instance, url, state, resolve, reject) { + console.log("getTryConnectPromise " + url), fetchWithTimeout(instance.getUrl("system/info/public", null, url), { + method: "GET", + accept: "application/json" + }, 15e3).then(function() { + state.resolved || (state.resolved = !0, console.log("Reconnect succeeded to " + url), instance.serverAddress(url), resolve()) + }, function() { + state.resolved || (console.log("Reconnect failed to " + url), ++state.rejects >= state.numAddresses && reject()) + }) + } + + function tryReconnectInternal(instance) { + var addresses = [], + addressesStrings = [], + serverInfo = instance.serverInfo(); + return serverInfo.LocalAddress && -1 === addressesStrings.indexOf(serverInfo.LocalAddress) && (addresses.push({ + url: serverInfo.LocalAddress, + timeout: 0 + }), addressesStrings.push(addresses[addresses.length - 1].url)), serverInfo.ManualAddress && -1 === addressesStrings.indexOf(serverInfo.ManualAddress) && (addresses.push({ + url: serverInfo.ManualAddress, + timeout: 100 + }), addressesStrings.push(addresses[addresses.length - 1].url)), serverInfo.RemoteAddress && -1 === addressesStrings.indexOf(serverInfo.RemoteAddress) && (addresses.push({ + url: serverInfo.RemoteAddress, + timeout: 200 + }), addressesStrings.push(addresses[addresses.length - 1].url)), console.log("tryReconnect: " + addressesStrings.join("|")), new Promise(function(resolve, reject) { + var state = {}; + state.numAddresses = addresses.length, state.rejects = 0, addresses.map(function(url) { + setTimeout(function() { + state.resolved || getTryConnectPromise(instance, url.url, state, resolve, reject) + }, url.timeout) + }) + }) + } + + function tryReconnect(instance, retryCount) { + return retryCount = retryCount || 0, retryCount >= 20 ? Promise.reject() : tryReconnectInternal(instance).catch(function(err) { + return console.log("error in tryReconnectInternal: " + (err || "")), new Promise(function(resolve, reject) { + setTimeout(function() { + tryReconnect(instance, retryCount + 1).then(resolve, reject) + }, 500) + }) + }) + } + + function getCachedUser(instance, userId) { + var serverId = instance.serverId(); + if (!serverId) return null; + var json = appStorage.getItem("user-" + userId + "-" + serverId); + return json ? JSON.parse(json) : null + } + + function onWebSocketMessage(msg) { + var instance = this; + msg = JSON.parse(msg.data), onMessageReceivedInternal(instance, msg) + } + + function onMessageReceivedInternal(instance, msg) { + var messageId = msg.MessageId; + if (messageId) { + if (messageIdsReceived[messageId]) return; + messageIdsReceived[messageId] = !0 + } + if ("UserDeleted" === msg.MessageType) instance._currentUser = null; + else if ("UserUpdated" === msg.MessageType || "UserConfigurationUpdated" === msg.MessageType) { + var user = msg.Data; + user.Id === instance.getCurrentUserId() && (instance._currentUser = null) + } + events.trigger(instance, "message", [msg]) + } + + function onWebSocketOpen() { + var instance = this; + console.log("web socket connection opened"), events.trigger(instance, "websocketopen") + } + + function onWebSocketError() { + var instance = this; + events.trigger(instance, "websocketerror") + } + + function setSocketOnClose(apiClient, socket) { + socket.onclose = function() { + console.log("web socket closed"), apiClient._webSocket === socket && (console.log("nulling out web socket"), apiClient._webSocket = null), setTimeout(function() { + events.trigger(apiClient, "websocketclose") + }, 0) + } + } + + function normalizeReturnBitrate(instance, bitrate) { + if (!bitrate) return instance.lastDetectedBitrate ? instance.lastDetectedBitrate : Promise.reject(); + var result = Math.round(.7 * bitrate); + if (instance.getMaxBandwidth) { + var maxRate = instance.getMaxBandwidth(); + maxRate && (result = Math.min(result, maxRate)) + } + return instance.lastDetectedBitrate = result, instance.lastDetectedBitrateTime = (new Date).getTime(), result + } + + function detectBitrateInternal(instance, tests, index, currentBitrate) { + if (index >= tests.length) return normalizeReturnBitrate(instance, currentBitrate); + var test = tests[index]; + return instance.getDownloadSpeed(test.bytes).then(function(bitrate) { + return bitrate < test.threshold ? normalizeReturnBitrate(instance, bitrate) : detectBitrateInternal(instance, tests, index + 1, bitrate) + }, function() { + return normalizeReturnBitrate(instance, currentBitrate) + }) + } + + function detectBitrateWithEndpointInfo(instance, endpointInfo) { + if (endpointInfo.IsInNetwork) { + return instance.lastDetectedBitrate = 14e7, instance.lastDetectedBitrateTime = (new Date).getTime(), 14e7 + } + return detectBitrateInternal(instance, [{ + bytes: 5e5, + threshold: 5e5 + }, { + bytes: 1e6, + threshold: 2e7 + }, { + bytes: 3e6, + threshold: 5e7 + }], 0) + } + + function getRemoteImagePrefix(instance, options) { + var urlPrefix; + return options.artist ? (urlPrefix = "Artists/" + instance.encodeName(options.artist), delete options.artist) : options.person ? (urlPrefix = "Persons/" + instance.encodeName(options.person), delete options.person) : options.genre ? (urlPrefix = "Genres/" + instance.encodeName(options.genre), delete options.genre) : options.musicGenre ? (urlPrefix = "MusicGenres/" + instance.encodeName(options.musicGenre), delete options.musicGenre) : options.gameGenre ? (urlPrefix = "GameGenres/" + instance.encodeName(options.gameGenre), delete options.gameGenre) : options.studio ? (urlPrefix = "Studios/" + instance.encodeName(options.studio), delete options.studio) : (urlPrefix = "Items/" + options.itemId, delete options.itemId), urlPrefix + } + + function normalizeImageOptions(instance, options) { + var ratio = instance._devicePixelRatio || 1; + ratio && (options.minScale && (ratio = Math.max(options.minScale, ratio)), options.width && (options.width = Math.round(options.width * ratio)), options.height && (options.height = Math.round(options.height * ratio)), options.maxWidth && (options.maxWidth = Math.round(options.maxWidth * ratio)), options.maxHeight && (options.maxHeight = Math.round(options.maxHeight * ratio))), options.quality = options.quality || instance.getDefaultImageQuality(options.type), instance.normalizeImageOptions && instance.normalizeImageOptions(options) + } + + function getCachedWakeOnLanInfo(instance) { + var serverId = instance.serverId(), + json = appStorage.getItem("server-" + serverId + "-wakeonlaninfo"); + return json ? JSON.parse(json) : [] + } + + function refreshWakeOnLanInfoIfNeeded(instance) { + wakeOnLan.isSupported() && instance.accessToken() && !1 !== instance.enableAutomaticBitrateDetection && (console.log("refreshWakeOnLanInfoIfNeeded"), setTimeout(refreshWakeOnLanInfo.bind(instance), 1e4)) + } + + function refreshWakeOnLanInfo() { + var instance = this; + console.log("refreshWakeOnLanInfo"), instance.getWakeOnLanInfo().then(function(info) { + var serverId = instance.serverId(); + return appStorage.setItem("server-" + serverId + "-wakeonlaninfo", JSON.stringify(info)), info + }, function(err) { + return [] + }) + } + + function sendNextWakeOnLan(infos, index, resolve) { + if (index >= infos.length) return void resolve(); + var info = infos[index]; + console.log("sending wakeonlan to " + info.MacAddress), wakeOnLan.send(info).then(function(result) { + sendNextWakeOnLan(infos, index + 1, resolve) + }, function() { + sendNextWakeOnLan(infos, index + 1, resolve) + }) + } + + function compareVersions(a, b) { + a = a.split("."), b = b.split("."); + for (var i = 0, length = Math.max(a.length, b.length); i < length; i++) { + var aVal = parseInt(a[i] || "0"), + bVal = parseInt(b[i] || "0"); + if (aVal < bVal) return -1; + if (aVal > bVal) return 1 + } + return 0 + } + ApiClient.prototype.appName = function() { + return this._appName + }, ApiClient.prototype.setRequestHeaders = function(headers) { + var currentServerInfo = this.serverInfo(), + appName = this._appName, + accessToken = currentServerInfo.AccessToken, + values = []; + if (appName && values.push('Client="' + appName + '"'), this._deviceName && values.push('Device="' + this._deviceName + '"'), this._deviceId && values.push('DeviceId="' + this._deviceId + '"'), this._appVersion && values.push('Version="' + this._appVersion + '"'), accessToken && values.push('Token="' + accessToken + '"'), values.length) { + var auth = "MediaBrowser " + values.join(", "); + headers["X-Emby-Authorization"] = auth + } + }, ApiClient.prototype.appVersion = function() { + return this._appVersion + }, ApiClient.prototype.deviceName = function() { + return this._deviceName + }, ApiClient.prototype.deviceId = function() { + return this._deviceId + }, ApiClient.prototype.serverAddress = function(val) { + if (null != val) { + if (0 !== val.toLowerCase().indexOf("http")) throw new Error("Invalid url: " + val); + var changed = val !== this._serverAddress; + this._serverAddress = val, this.onNetworkChange(), changed && events.trigger(this, "serveraddresschanged") + } + return this._serverAddress + }, ApiClient.prototype.onNetworkChange = function() { + this.lastDetectedBitrate = 0, this.lastDetectedBitrateTime = 0, setSavedEndpointInfo(this, null), redetectBitrate(this), refreshWakeOnLanInfoIfNeeded(this) + }, ApiClient.prototype.getUrl = function(name, params, serverAddress) { + if (!name) throw new Error("Url name cannot be empty"); + var url = serverAddress || this._serverAddress; + if (!url) throw new Error("serverAddress is yet not set"); + var lowered = url.toLowerCase(); + return -1 === lowered.indexOf("/emby") && -1 === lowered.indexOf("/mediabrowser") && (url += "/emby"), "/" !== name.charAt(0) && (url += "/"), url += name, params && (params = paramsToString(params)) && (url += "?" + params), url + }, ApiClient.prototype.fetchWithFailover = function(request, enableReconnection) { + console.log("Requesting " + request.url), request.timeout = 3e4; + var instance = this; + return getFetchPromise(request).then(function(response) { + return instance.lastFetch = (new Date).getTime(), response.status < 400 ? "json" === request.dataType || "application/json" === request.headers.accept ? response.json() : "text" === request.dataType || 0 === (response.headers.get("Content-Type") || "").toLowerCase().indexOf("text/") ? response.text() : response : (onFetchFail(instance, request.url, response), Promise.reject(response)) + }, function(error) { + if (error ? console.log("Request failed to " + request.url + " " + (error.status || "") + " " + error.toString()) : console.log("Request timed out to " + request.url), error && error.status || !enableReconnection) throw console.log("Reporting request failure"), onFetchFail(instance, request.url, {}), error; + console.log("Attempting reconnection"); + var previousServerAddress = instance.serverAddress(); + return tryReconnect(instance).then(function() { + return console.log("Reconnect succeesed"), request.url = request.url.replace(previousServerAddress, instance.serverAddress()), instance.fetchWithFailover(request, !1) + }, function(innerError) { + throw console.log("Reconnect failed"), onFetchFail(instance, request.url, {}), innerError + }) + }) + }, ApiClient.prototype.fetch = function(request, includeAuthorization) { + if (!request) throw new Error("Request cannot be null"); + if (request.headers = request.headers || {}, !1 !== includeAuthorization && this.setRequestHeaders(request.headers), !1 === this.enableAutomaticNetworking || "GET" !== request.type) { + console.log("Requesting url without automatic networking: " + request.url); + var instance = this; + return getFetchPromise(request).then(function(response) { + return instance.lastFetch = (new Date).getTime(), response.status < 400 ? "json" === request.dataType || "application/json" === request.headers.accept ? response.json() : "text" === request.dataType || 0 === (response.headers.get("Content-Type") || "").toLowerCase().indexOf("text/") ? response.text() : response : (onFetchFail(instance, request.url, response), Promise.reject(response)) + }, function(error) { + throw onFetchFail(instance, request.url, {}), error + }) + } + return this.fetchWithFailover(request, !0) + }, ApiClient.prototype.setAuthenticationInfo = function(accessKey, userId) { + this._currentUser = null, this._serverInfo.AccessToken = accessKey, this._serverInfo.UserId = userId, redetectBitrate(this), refreshWakeOnLanInfoIfNeeded(this) + }, ApiClient.prototype.serverInfo = function(info) { + return info && (this._serverInfo = info), this._serverInfo + }, ApiClient.prototype.getCurrentUserId = function() { + return this._serverInfo.UserId + }, ApiClient.prototype.accessToken = function() { + return this._serverInfo.AccessToken + }, ApiClient.prototype.serverId = function() { + return this.serverInfo().Id + }, ApiClient.prototype.serverName = function() { + return this.serverInfo().Name + }, ApiClient.prototype.ajax = function(request, includeAuthorization) { + if (!request) throw new Error("Request cannot be null"); + return this.fetch(request, includeAuthorization) + }, ApiClient.prototype.getCurrentUser = function(enableCache) { + if (this._currentUser) return Promise.resolve(this._currentUser); + var userId = this.getCurrentUserId(); + if (!userId) return Promise.reject(); + var user, instance = this, + serverPromise = this.getUser(userId).then(function(user) { + return appStorage.setItem("user-" + user.Id + "-" + user.ServerId, JSON.stringify(user)), instance._currentUser = user, user + }, function(response) { + if (!response.status && userId && instance.accessToken() && (user = getCachedUser(instance, userId))) return Promise.resolve(user); + throw response + }); + return !this.lastFetch && !1 !== enableCache && (user = getCachedUser(instance, userId)) ? Promise.resolve(user) : serverPromise + }, ApiClient.prototype.isLoggedIn = function() { + var info = this.serverInfo(); + return !!(info && info.UserId && info.AccessToken) + }, ApiClient.prototype.logout = function() { + stopBitrateDetection(this), this.closeWebSocket(); + var done = function() { + this.setAuthenticationInfo(null, null) + }.bind(this); + if (this.accessToken()) { + var url = this.getUrl("Sessions/Logout"); + return this.ajax({ + type: "POST", + url: url + }).then(done, done) + } + return done(), Promise.resolve() + }, ApiClient.prototype.authenticateUserByName = function(name, password) { + if (!name) return Promise.reject(); + var url = this.getUrl("Users/authenticatebyname"), + instance = this; + return new Promise(function(resolve, reject) { + var postData = { + Username: name, + Pw: password || "" + }; + instance.ajax({ + type: "POST", + url: url, + data: JSON.stringify(postData), + dataType: "json", + contentType: "application/json" + }).then(function(result) { + var afterOnAuthenticated = function() { + redetectBitrate(instance), refreshWakeOnLanInfoIfNeeded(instance), resolve(result) + }; + instance.onAuthenticated ? instance.onAuthenticated(instance, result).then(afterOnAuthenticated) : afterOnAuthenticated() + }, reject) + }) + }, ApiClient.prototype.ensureWebSocket = function() { + if (!this.isWebSocketOpenOrConnecting() && this.isWebSocketSupported()) try { + this.openWebSocket() + } catch (err) { + console.log("Error opening web socket: " + err) + } + }; + var messageIdsReceived = {}; + return ApiClient.prototype.openWebSocket = function() { + var accessToken = this.accessToken(); + if (!accessToken) throw new Error("Cannot open web socket without access token."); + var url = this.getUrl("socket"); + url = replaceAll(url, "emby/socket", "embywebsocket"), url = replaceAll(url, "https:", "wss:"), url = replaceAll(url, "http:", "ws:"), url += "?api_key=" + accessToken, url += "&deviceId=" + this.deviceId(), console.log("opening web socket with url: " + url); + var webSocket = new WebSocket(url); + webSocket.onmessage = onWebSocketMessage.bind(this), webSocket.onopen = onWebSocketOpen.bind(this), webSocket.onerror = onWebSocketError.bind(this), setSocketOnClose(this, webSocket), this._webSocket = webSocket + }, ApiClient.prototype.closeWebSocket = function() { + var socket = this._webSocket; + socket && socket.readyState === WebSocket.OPEN && socket.close() + }, ApiClient.prototype.sendWebSocketMessage = function(name, data) { + console.log("Sending web socket message: " + name); + var msg = { + MessageType: name + }; + data && (msg.Data = data), msg = JSON.stringify(msg), this._webSocket.send(msg) + }, ApiClient.prototype.sendMessage = function(name, data) { + this.isWebSocketOpen() && this.sendWebSocketMessage(name, data) + }, ApiClient.prototype.isMessageChannelOpen = function() { + return this.isWebSocketOpen() + }, ApiClient.prototype.isWebSocketOpen = function() { + var socket = this._webSocket; + return !!socket && socket.readyState === WebSocket.OPEN + }, ApiClient.prototype.isWebSocketOpenOrConnecting = function() { + var socket = this._webSocket; + return !!socket && (socket.readyState === WebSocket.OPEN || socket.readyState === WebSocket.CONNECTING) + }, ApiClient.prototype.get = function(url) { + return this.ajax({ + type: "GET", + url: url + }) + }, ApiClient.prototype.getJSON = function(url, includeAuthorization) { + return this.fetch({ + url: url, + type: "GET", + dataType: "json", + headers: { + accept: "application/json" + } + }, includeAuthorization) + }, ApiClient.prototype.updateServerInfo = function(server, serverUrl) { + if (null == server) throw new Error("server cannot be null"); + if (this.serverInfo(server), !serverUrl) throw new Error("serverUrl cannot be null. serverInfo: " + JSON.stringify(server)); + console.log("Setting server address to " + serverUrl), this.serverAddress(serverUrl) + }, ApiClient.prototype.isWebSocketSupported = function() { + try { + return null != WebSocket + } catch (err) { + return !1 + } + }, ApiClient.prototype.clearAuthenticationInfo = function() { + this.setAuthenticationInfo(null, null) + }, ApiClient.prototype.encodeName = function(name) { + name = name.split("/").join("-"), name = name.split("&").join("-"), name = name.split("?").join("-"); + var val = paramsToString({ + name: name + }); + return val.substring(val.indexOf("=") + 1).replace("'", "%27") + }, ApiClient.prototype.getProductNews = function(options) { + options = options || {}; + var url = this.getUrl("News/Product", options); + return this.getJSON(url) + }, ApiClient.prototype.getDownloadSpeed = function(byteSize) { + var url = this.getUrl("Playback/BitrateTest", { + Size: byteSize + }), + now = (new Date).getTime(); + return this.ajax({ + type: "GET", + url: url, + timeout: 5e3 + }).then(function() { + var responseTimeSeconds = ((new Date).getTime() - now) / 1e3, + bytesPerSecond = byteSize / responseTimeSeconds; + return Math.round(8 * bytesPerSecond) + }) + }, ApiClient.prototype.detectBitrate = function(force) { + if (!force && this.lastDetectedBitrate && (new Date).getTime() - (this.lastDetectedBitrateTime || 0) <= 36e5) return Promise.resolve(this.lastDetectedBitrate); + var instance = this; + return this.getEndpointInfo().then(function(info) { + return detectBitrateWithEndpointInfo(instance, info) + }, function(info) { + return detectBitrateWithEndpointInfo(instance, {}) + }) + }, ApiClient.prototype.getItem = function(userId, itemId) { + if (!itemId) throw new Error("null itemId"); + var url = userId ? this.getUrl("Users/" + userId + "/Items/" + itemId) : this.getUrl("Items/" + itemId); + return this.getJSON(url) + }, ApiClient.prototype.getRootFolder = function(userId) { + if (!userId) throw new Error("null userId"); + var url = this.getUrl("Users/" + userId + "/Items/Root"); + return this.getJSON(url) + }, ApiClient.prototype.getNotificationSummary = function(userId) { + if (!userId) throw new Error("null userId"); + var url = this.getUrl("Notifications/" + userId + "/Summary"); + return this.getJSON(url) + }, ApiClient.prototype.getNotifications = function(userId, options) { + if (!userId) throw new Error("null userId"); + var url = this.getUrl("Notifications/" + userId, options || {}); + return this.getJSON(url) + }, ApiClient.prototype.markNotificationsRead = function(userId, idList, isRead) { + if (!userId) throw new Error("null userId"); + if (!idList) throw new Error("null idList"); + var suffix = isRead ? "Read" : "Unread", + params = { + UserId: userId, + Ids: idList.join(",") + }, + url = this.getUrl("Notifications/" + userId + "/" + suffix, params); + return this.ajax({ + type: "POST", + url: url + }) + }, ApiClient.prototype.getRemoteImageProviders = function(options) { + if (!options) throw new Error("null options"); + var urlPrefix = getRemoteImagePrefix(this, options), + url = this.getUrl(urlPrefix + "/RemoteImages/Providers", options); + return this.getJSON(url) + }, ApiClient.prototype.getAvailableRemoteImages = function(options) { + if (!options) throw new Error("null options"); + var urlPrefix = getRemoteImagePrefix(this, options), + url = this.getUrl(urlPrefix + "/RemoteImages", options); + return this.getJSON(url) + }, ApiClient.prototype.downloadRemoteImage = function(options) { + if (!options) throw new Error("null options"); + var urlPrefix = getRemoteImagePrefix(this, options), + url = this.getUrl(urlPrefix + "/RemoteImages/Download", options); + return this.ajax({ + type: "POST", + url: url + }) + }, ApiClient.prototype.getRecordingFolders = function(userId) { + var url = this.getUrl("LiveTv/Recordings/Folders", { + userId: userId + }); + return this.getJSON(url) + }, ApiClient.prototype.getLiveTvInfo = function(options) { + var url = this.getUrl("LiveTv/Info", options || {}); + return this.getJSON(url) + }, ApiClient.prototype.getLiveTvGuideInfo = function(options) { + var url = this.getUrl("LiveTv/GuideInfo", options || {}); + return this.getJSON(url) + }, ApiClient.prototype.getLiveTvChannel = function(id, userId) { + if (!id) throw new Error("null id"); + var options = {}; + userId && (options.userId = userId); + var url = this.getUrl("LiveTv/Channels/" + id, options); + return this.getJSON(url) + }, ApiClient.prototype.getLiveTvChannels = function(options) { + var url = this.getUrl("LiveTv/Channels", options || {}); + return this.getJSON(url) + }, ApiClient.prototype.getLiveTvPrograms = function(options) { + return options = options || {}, options.channelIds && options.channelIds.length > 1800 ? this.ajax({ + type: "POST", + url: this.getUrl("LiveTv/Programs"), + data: JSON.stringify(options), + contentType: "application/json", + dataType: "json" + }) : this.ajax({ + type: "GET", + url: this.getUrl("LiveTv/Programs", options), + dataType: "json" + }) + }, ApiClient.prototype.getLiveTvRecommendedPrograms = function(options) { + return options = options || {}, this.ajax({ + type: "GET", + url: this.getUrl("LiveTv/Programs/Recommended", options), + dataType: "json" + }) + }, ApiClient.prototype.getLiveTvRecordings = function(options) { + var url = this.getUrl("LiveTv/Recordings", options || {}); + return this.getJSON(url) + }, ApiClient.prototype.getLiveTvRecordingSeries = function(options) { + var url = this.getUrl("LiveTv/Recordings/Series", options || {}); + return this.getJSON(url) + }, ApiClient.prototype.getLiveTvRecordingGroups = function(options) { + var url = this.getUrl("LiveTv/Recordings/Groups", options || {}); + return this.getJSON(url) + }, ApiClient.prototype.getLiveTvRecordingGroup = function(id) { + if (!id) throw new Error("null id"); + var url = this.getUrl("LiveTv/Recordings/Groups/" + id); + return this.getJSON(url) + }, ApiClient.prototype.getLiveTvRecording = function(id, userId) { + if (!id) throw new Error("null id"); + var options = {}; + userId && (options.userId = userId); + var url = this.getUrl("LiveTv/Recordings/" + id, options); + return this.getJSON(url) + }, ApiClient.prototype.getLiveTvProgram = function(id, userId) { + if (!id) throw new Error("null id"); + var options = {}; + userId && (options.userId = userId); + var url = this.getUrl("LiveTv/Programs/" + id, options); + return this.getJSON(url) + }, ApiClient.prototype.deleteLiveTvRecording = function(id) { + if (!id) throw new Error("null id"); + var url = this.getUrl("LiveTv/Recordings/" + id); + return this.ajax({ + type: "DELETE", + url: url + }) + }, ApiClient.prototype.cancelLiveTvTimer = function(id) { + if (!id) throw new Error("null id"); + var url = this.getUrl("LiveTv/Timers/" + id); + return this.ajax({ + type: "DELETE", + url: url + }) + }, ApiClient.prototype.getLiveTvTimers = function(options) { + var url = this.getUrl("LiveTv/Timers", options || {}); + return this.getJSON(url) + }, ApiClient.prototype.getLiveTvTimer = function(id) { + if (!id) throw new Error("null id"); + var url = this.getUrl("LiveTv/Timers/" + id); + return this.getJSON(url) + }, ApiClient.prototype.getNewLiveTvTimerDefaults = function(options) { + options = options || {}; + var url = this.getUrl("LiveTv/Timers/Defaults", options); + return this.getJSON(url) + }, ApiClient.prototype.createLiveTvTimer = function(item) { + if (!item) throw new Error("null item"); + var url = this.getUrl("LiveTv/Timers"); + return this.ajax({ + type: "POST", + url: url, + data: JSON.stringify(item), + contentType: "application/json" + }) + }, ApiClient.prototype.updateLiveTvTimer = function(item) { + if (!item) throw new Error("null item"); + var url = this.getUrl("LiveTv/Timers/" + item.Id); + return this.ajax({ + type: "POST", + url: url, + data: JSON.stringify(item), + contentType: "application/json" + }) + }, ApiClient.prototype.resetLiveTvTuner = function(id) { + if (!id) throw new Error("null id"); + var url = this.getUrl("LiveTv/Tuners/" + id + "/Reset"); + return this.ajax({ + type: "POST", + url: url + }) + }, ApiClient.prototype.getLiveTvSeriesTimers = function(options) { + var url = this.getUrl("LiveTv/SeriesTimers", options || {}); + return this.getJSON(url) + }, ApiClient.prototype.getLiveTvSeriesTimer = function(id) { + if (!id) throw new Error("null id"); + var url = this.getUrl("LiveTv/SeriesTimers/" + id); + return this.getJSON(url) + }, ApiClient.prototype.cancelLiveTvSeriesTimer = function(id) { + if (!id) throw new Error("null id"); + var url = this.getUrl("LiveTv/SeriesTimers/" + id); + return this.ajax({ + type: "DELETE", + url: url + }) + }, ApiClient.prototype.createLiveTvSeriesTimer = function(item) { + if (!item) throw new Error("null item"); + var url = this.getUrl("LiveTv/SeriesTimers"); + return this.ajax({ + type: "POST", + url: url, + data: JSON.stringify(item), + contentType: "application/json" + }) + }, ApiClient.prototype.updateLiveTvSeriesTimer = function(item) { + if (!item) throw new Error("null item"); + var url = this.getUrl("LiveTv/SeriesTimers/" + item.Id); + return this.ajax({ + type: "POST", + url: url, + data: JSON.stringify(item), + contentType: "application/json" + }) + }, ApiClient.prototype.getRegistrationInfo = function(feature) { + var url = this.getUrl("Registrations/" + feature); + return this.getJSON(url) + }, ApiClient.prototype.getSystemInfo = function() { + var url = this.getUrl("System/Info"), + instance = this; + return this.getJSON(url).then(function(info) { + return instance.setSystemInfo(info), Promise.resolve(info) + }) + }, ApiClient.prototype.getSyncStatus = function(itemId) { + var url = this.getUrl("Sync/" + itemId + "/Status"); + return this.ajax({ + url: url, + type: "POST", + dataType: "json", + contentType: "application/json", + data: JSON.stringify({ + TargetId: this.deviceId() + }) + }) + }, ApiClient.prototype.getPublicSystemInfo = function() { + var url = this.getUrl("System/Info/Public"), + instance = this; + return this.getJSON(url).then(function(info) { + return instance.setSystemInfo(info), Promise.resolve(info) + }) + }, ApiClient.prototype.getInstantMixFromItem = function(itemId, options) { + var url = this.getUrl("Items/" + itemId + "/InstantMix", options); + return this.getJSON(url) + }, ApiClient.prototype.getEpisodes = function(itemId, options) { + var url = this.getUrl("Shows/" + itemId + "/Episodes", options); + return this.getJSON(url) + }, ApiClient.prototype.getDisplayPreferences = function(id, userId, app) { + var url = this.getUrl("DisplayPreferences/" + id, { + userId: userId, + client: app + }); + return this.getJSON(url) + }, ApiClient.prototype.updateDisplayPreferences = function(id, obj, userId, app) { + var url = this.getUrl("DisplayPreferences/" + id, { + userId: userId, + client: app + }); + return this.ajax({ + type: "POST", + url: url, + data: JSON.stringify(obj), + contentType: "application/json" + }) + }, ApiClient.prototype.getSeasons = function(itemId, options) { + var url = this.getUrl("Shows/" + itemId + "/Seasons", options); + return this.getJSON(url) + }, ApiClient.prototype.getSimilarItems = function(itemId, options) { + var url = this.getUrl("Items/" + itemId + "/Similar", options); + return this.getJSON(url) + }, ApiClient.prototype.getCultures = function() { + var url = this.getUrl("Localization/cultures"); + return this.getJSON(url) + }, ApiClient.prototype.getCountries = function() { + var url = this.getUrl("Localization/countries"); + return this.getJSON(url) + }, ApiClient.prototype.getPlaybackInfo = function(itemId, options, deviceProfile) { + var postData = { + DeviceProfile: deviceProfile + }; + return this.ajax({ + url: this.getUrl("Items/" + itemId + "/PlaybackInfo", options), + type: "POST", + data: JSON.stringify(postData), + contentType: "application/json", + dataType: "json" + }) + }, ApiClient.prototype.getLiveStreamMediaInfo = function(liveStreamId) { + var postData = { + LiveStreamId: liveStreamId + }; + return this.ajax({ + url: this.getUrl("LiveStreams/MediaInfo"), + type: "POST", + data: JSON.stringify(postData), + contentType: "application/json", + dataType: "json" + }) + }, ApiClient.prototype.getIntros = function(itemId) { + return this.getJSON(this.getUrl("Users/" + this.getCurrentUserId() + "/Items/" + itemId + "/Intros")) + }, ApiClient.prototype.getDirectoryContents = function(path, options) { + if (!path) throw new Error("null path"); + if ("string" != typeof path) throw new Error("invalid path"); + options = options || {}, options.path = path; + var url = this.getUrl("Environment/DirectoryContents", options); + return this.getJSON(url) + }, ApiClient.prototype.getNetworkShares = function(path) { + if (!path) throw new Error("null path"); + var options = {}; + options.path = path; + var url = this.getUrl("Environment/NetworkShares", options); + return this.getJSON(url) + }, ApiClient.prototype.getParentPath = function(path) { + if (!path) throw new Error("null path"); + var options = {}; + options.path = path; + var url = this.getUrl("Environment/ParentPath", options); + return this.ajax({ + type: "GET", + url: url, + dataType: "text" + }) + }, ApiClient.prototype.getDrives = function() { + var url = this.getUrl("Environment/Drives"); + return this.getJSON(url) + }, ApiClient.prototype.getNetworkDevices = function() { + var url = this.getUrl("Environment/NetworkDevices"); + return this.getJSON(url) + }, ApiClient.prototype.cancelPackageInstallation = function(installationId) { + if (!installationId) throw new Error("null installationId"); + var url = this.getUrl("Packages/Installing/" + installationId); + return this.ajax({ + type: "DELETE", + url: url + }) + }, ApiClient.prototype.refreshItem = function(itemId, options) { + if (!itemId) throw new Error("null itemId"); + var url = this.getUrl("Items/" + itemId + "/Refresh", options || {}); + return this.ajax({ + type: "POST", + url: url + }) + }, ApiClient.prototype.installPlugin = function(name, guid, updateClass, version) { + if (!name) throw new Error("null name"); + if (!updateClass) throw new Error("null updateClass"); + var options = { + updateClass: updateClass, + AssemblyGuid: guid + }; + version && (options.version = version); + var url = this.getUrl("Packages/Installed/" + name, options); + return this.ajax({ + type: "POST", + url: url + }) + }, ApiClient.prototype.restartServer = function() { + var url = this.getUrl("System/Restart"); + return this.ajax({ + type: "POST", + url: url + }) + }, ApiClient.prototype.shutdownServer = function() { + var url = this.getUrl("System/Shutdown"); + return this.ajax({ + type: "POST", + url: url + }) + }, ApiClient.prototype.getPackageInfo = function(name, guid) { + if (!name) throw new Error("null name"); + var options = { + AssemblyGuid: guid + }, + url = this.getUrl("Packages/" + name, options); + return this.getJSON(url) + }, ApiClient.prototype.getAvailableApplicationUpdate = function() { + var url = this.getUrl("Packages/Updates", { + PackageType: "System" + }); + return this.getJSON(url) + }, ApiClient.prototype.getAvailablePluginUpdates = function() { + var url = this.getUrl("Packages/Updates", { + PackageType: "UserInstalled" + }); + return this.getJSON(url) + }, ApiClient.prototype.getVirtualFolders = function() { + var url = "Library/VirtualFolders"; + return url = this.getUrl(url), this.getJSON(url) + }, ApiClient.prototype.getPhysicalPaths = function() { + var url = this.getUrl("Library/PhysicalPaths"); + return this.getJSON(url) + }, ApiClient.prototype.getServerConfiguration = function() { + var url = this.getUrl("System/Configuration"); + return this.getJSON(url) + }, ApiClient.prototype.getDevicesOptions = function() { + var url = this.getUrl("System/Configuration/devices"); + return this.getJSON(url) + }, ApiClient.prototype.getContentUploadHistory = function() { + var url = this.getUrl("Devices/CameraUploads", { + DeviceId: this.deviceId() + }); + return this.getJSON(url) + }, ApiClient.prototype.getNamedConfiguration = function(name) { + var url = this.getUrl("System/Configuration/" + name); + return this.getJSON(url) + }, ApiClient.prototype.getScheduledTasks = function(options) { + options = options || {}; + var url = this.getUrl("ScheduledTasks", options); + return this.getJSON(url) + }, ApiClient.prototype.startScheduledTask = function(id) { + if (!id) throw new Error("null id"); + var url = this.getUrl("ScheduledTasks/Running/" + id); + return this.ajax({ + type: "POST", + url: url + }) + }, ApiClient.prototype.getScheduledTask = function(id) { + if (!id) throw new Error("null id"); + var url = this.getUrl("ScheduledTasks/" + id); + return this.getJSON(url) + }, ApiClient.prototype.getNextUpEpisodes = function(options) { + var url = this.getUrl("Shows/NextUp", options); + return this.getJSON(url) + }, ApiClient.prototype.stopScheduledTask = function(id) { + if (!id) throw new Error("null id"); + var url = this.getUrl("ScheduledTasks/Running/" + id); + return this.ajax({ + type: "DELETE", + url: url + }) + }, ApiClient.prototype.getPluginConfiguration = function(id) { + if (!id) throw new Error("null Id"); + var url = this.getUrl("Plugins/" + id + "/Configuration"); + return this.getJSON(url) + }, ApiClient.prototype.getAvailablePlugins = function(options) { + options = options || {}, options.PackageType = "UserInstalled"; + var url = this.getUrl("Packages", options); + return this.getJSON(url) + }, ApiClient.prototype.uninstallPlugin = function(id) { + if (!id) throw new Error("null Id"); + var url = this.getUrl("Plugins/" + id); + return this.ajax({ + type: "DELETE", + url: url + }) + }, ApiClient.prototype.removeVirtualFolder = function(name, refreshLibrary) { + if (!name) throw new Error("null name"); + var url = "Library/VirtualFolders"; + return url = this.getUrl(url, { + refreshLibrary: !!refreshLibrary, + name: name + }), this.ajax({ + type: "DELETE", + url: url + }) + }, ApiClient.prototype.addVirtualFolder = function(name, type, refreshLibrary, libraryOptions) { + if (!name) throw new Error("null name"); + var options = {}; + type && (options.collectionType = type), options.refreshLibrary = !!refreshLibrary, options.name = name; + var url = "Library/VirtualFolders"; + return url = this.getUrl(url, options), this.ajax({ + type: "POST", + url: url, + data: JSON.stringify({ + LibraryOptions: libraryOptions + }), + contentType: "application/json" + }) + }, ApiClient.prototype.updateVirtualFolderOptions = function(id, libraryOptions) { + if (!id) throw new Error("null name"); + var url = "Library/VirtualFolders/LibraryOptions"; + return url = this.getUrl(url), this.ajax({ + type: "POST", + url: url, + data: JSON.stringify({ + Id: id, + LibraryOptions: libraryOptions + }), + contentType: "application/json" + }) + }, ApiClient.prototype.renameVirtualFolder = function(name, newName, refreshLibrary) { + if (!name) throw new Error("null name"); + var url = "Library/VirtualFolders/Name"; + return url = this.getUrl(url, { + refreshLibrary: !!refreshLibrary, + newName: newName, + name: name + }), this.ajax({ + type: "POST", + url: url + }) + }, ApiClient.prototype.addMediaPath = function(virtualFolderName, mediaPath, networkSharePath, refreshLibrary) { + if (!virtualFolderName) throw new Error("null virtualFolderName"); + if (!mediaPath) throw new Error("null mediaPath"); + var url = "Library/VirtualFolders/Paths", + pathInfo = { + Path: mediaPath + }; + return networkSharePath && (pathInfo.NetworkPath = networkSharePath), url = this.getUrl(url, { + refreshLibrary: !!refreshLibrary + }), this.ajax({ + type: "POST", + url: url, + data: JSON.stringify({ + Name: virtualFolderName, + PathInfo: pathInfo + }), + contentType: "application/json" + }) + }, ApiClient.prototype.updateMediaPath = function(virtualFolderName, pathInfo) { + if (!virtualFolderName) throw new Error("null virtualFolderName"); + if (!pathInfo) throw new Error("null pathInfo"); + var url = "Library/VirtualFolders/Paths/Update"; + return url = this.getUrl(url), this.ajax({ + type: "POST", + url: url, + data: JSON.stringify({ + Name: virtualFolderName, + PathInfo: pathInfo + }), + contentType: "application/json" + }) + }, ApiClient.prototype.removeMediaPath = function(virtualFolderName, mediaPath, refreshLibrary) { + if (!virtualFolderName) throw new Error("null virtualFolderName"); + if (!mediaPath) throw new Error("null mediaPath"); + var url = "Library/VirtualFolders/Paths"; + return url = this.getUrl(url, { + refreshLibrary: !!refreshLibrary, + path: mediaPath, + name: virtualFolderName + }), this.ajax({ + type: "DELETE", + url: url + }) + }, ApiClient.prototype.deleteUser = function(id) { + if (!id) throw new Error("null id"); + var url = this.getUrl("Users/" + id); + return this.ajax({ + type: "DELETE", + url: url + }) + }, ApiClient.prototype.deleteUserImage = function(userId, imageType, imageIndex) { + if (!userId) throw new Error("null userId"); + if (!imageType) throw new Error("null imageType"); + var url = this.getUrl("Users/" + userId + "/Images/" + imageType); + return null != imageIndex && (url += "/" + imageIndex), this.ajax({ + type: "DELETE", + url: url + }) + }, ApiClient.prototype.deleteItemImage = function(itemId, imageType, imageIndex) { + if (!imageType) throw new Error("null imageType"); + var url = this.getUrl("Items/" + itemId + "/Images"); + return url += "/" + imageType, null != imageIndex && (url += "/" + imageIndex), this.ajax({ + type: "DELETE", + url: url + }) + }, ApiClient.prototype.deleteItem = function(itemId) { + if (!itemId) throw new Error("null itemId"); + var url = this.getUrl("Items/" + itemId); + return this.ajax({ + type: "DELETE", + url: url + }) + }, ApiClient.prototype.stopActiveEncodings = function(playSessionId) { + var options = { + deviceId: this.deviceId() + }; + playSessionId && (options.PlaySessionId = playSessionId); + var url = this.getUrl("Videos/ActiveEncodings", options); + return this.ajax({ + type: "DELETE", + url: url + }) + }, ApiClient.prototype.reportCapabilities = function(options) { + var url = this.getUrl("Sessions/Capabilities/Full"); + return this.ajax({ + type: "POST", + url: url, + data: JSON.stringify(options), + contentType: "application/json" + }) + }, ApiClient.prototype.updateItemImageIndex = function(itemId, imageType, imageIndex, newIndex) { + if (!imageType) throw new Error("null imageType"); + var options = { + newIndex: newIndex + }, + url = this.getUrl("Items/" + itemId + "/Images/" + imageType + "/" + imageIndex + "/Index", options); + return this.ajax({ + type: "POST", + url: url + }) + }, ApiClient.prototype.getItemImageInfos = function(itemId) { + var url = this.getUrl("Items/" + itemId + "/Images"); + return this.getJSON(url) + }, ApiClient.prototype.getCriticReviews = function(itemId, options) { + if (!itemId) throw new Error("null itemId"); + var url = this.getUrl("Items/" + itemId + "/CriticReviews", options); + return this.getJSON(url) + }, ApiClient.prototype.getItemDownloadUrl = function(itemId) { + if (!itemId) throw new Error("itemId cannot be empty"); + var url = "Items/" + itemId + "/Download"; + return this.getUrl(url, { + api_key: this.accessToken() + }) + }, ApiClient.prototype.getSessions = function(options) { + var url = this.getUrl("Sessions", options); + return this.getJSON(url) + }, ApiClient.prototype.uploadUserImage = function(userId, imageType, file) { + if (!userId) throw new Error("null userId"); + if (!imageType) throw new Error("null imageType"); + if (!file) throw new Error("File must be an image."); + if ("image/png" !== file.type && "image/jpeg" !== file.type && "image/jpeg" !== file.type) throw new Error("File must be an image."); + var instance = this; + return new Promise(function(resolve, reject) { + var reader = new FileReader; + reader.onerror = function() { + reject() + }, reader.onabort = function() { + reject() + }, reader.onload = function(e) { + var data = e.target.result.split(",")[1], + url = instance.getUrl("Users/" + userId + "/Images/" + imageType); + instance.ajax({ + type: "POST", + url: url, + data: data, + contentType: "image/" + file.name.substring(file.name.lastIndexOf(".") + 1) + }).then(resolve, reject) + }, reader.readAsDataURL(file) + }) + }, ApiClient.prototype.uploadItemImage = function(itemId, imageType, file) { + if (!itemId) throw new Error("null itemId"); + if (!imageType) throw new Error("null imageType"); + if (!file) throw new Error("File must be an image."); + if ("image/png" !== file.type && "image/jpeg" !== file.type && "image/jpeg" !== file.type) throw new Error("File must be an image."); + var url = this.getUrl("Items/" + itemId + "/Images"); + url += "/" + imageType; + var instance = this; + return new Promise(function(resolve, reject) { + var reader = new FileReader; + reader.onerror = function() { + reject() + }, reader.onabort = function() { + reject() + }, reader.onload = function(e) { + var data = e.target.result.split(",")[1]; + instance.ajax({ + type: "POST", + url: url, + data: data, + contentType: "image/" + file.name.substring(file.name.lastIndexOf(".") + 1) + }).then(resolve, reject) + }, reader.readAsDataURL(file) + }) + }, ApiClient.prototype.getInstalledPlugins = function() { + var options = {}, + url = this.getUrl("Plugins", options); + return this.getJSON(url) + }, ApiClient.prototype.getUser = function(id) { + if (!id) throw new Error("Must supply a userId"); + var url = this.getUrl("Users/" + id); + return this.getJSON(url) + }, ApiClient.prototype.getStudio = function(name, userId) { + if (!name) throw new Error("null name"); + var options = {}; + userId && (options.userId = userId); + var url = this.getUrl("Studios/" + this.encodeName(name), options); + return this.getJSON(url) + }, ApiClient.prototype.getGenre = function(name, userId) { + if (!name) throw new Error("null name"); + var options = {}; + userId && (options.userId = userId); + var url = this.getUrl("Genres/" + this.encodeName(name), options); + return this.getJSON(url) + }, ApiClient.prototype.getMusicGenre = function(name, userId) { + if (!name) throw new Error("null name"); + var options = {}; + userId && (options.userId = userId); + var url = this.getUrl("MusicGenres/" + this.encodeName(name), options); + return this.getJSON(url) + }, ApiClient.prototype.getGameGenre = function(name, userId) { + if (!name) throw new Error("null name"); + var options = {}; + userId && (options.userId = userId); + var url = this.getUrl("GameGenres/" + this.encodeName(name), options); + return this.getJSON(url) + }, ApiClient.prototype.getArtist = function(name, userId) { + if (!name) throw new Error("null name"); + var options = {}; + userId && (options.userId = userId); + var url = this.getUrl("Artists/" + this.encodeName(name), options); + return this.getJSON(url) + }, ApiClient.prototype.getPerson = function(name, userId) { + if (!name) throw new Error("null name"); + var options = {}; + userId && (options.userId = userId); + var url = this.getUrl("Persons/" + this.encodeName(name), options); + return this.getJSON(url) + }, ApiClient.prototype.getPublicUsers = function() { + var url = this.getUrl("users/public"); + return this.ajax({ + type: "GET", + url: url, + dataType: "json" + }, !1) + }, ApiClient.prototype.getUsers = function(options) { + var url = this.getUrl("users", options || {}); + return this.getJSON(url) + }, ApiClient.prototype.getParentalRatings = function() { + var url = this.getUrl("Localization/ParentalRatings"); + return this.getJSON(url) + }, ApiClient.prototype.getDefaultImageQuality = function(imageType) { + return "backdrop" === imageType.toLowerCase() ? 80 : 90 + }, ApiClient.prototype.getUserImageUrl = function(userId, options) { + if (!userId) throw new Error("null userId"); + options = options || {}; + var url = "Users/" + userId + "/Images/" + options.type; + return null != options.index && (url += "/" + options.index), normalizeImageOptions(this, options), delete options.type, delete options.index, this.getUrl(url, options) + }, ApiClient.prototype.getImageUrl = function(itemId, options) { + if (!itemId) throw new Error("itemId cannot be empty"); + options = options || {}; + var url = "Items/" + itemId + "/Images/" + options.type; + return null != options.index && (url += "/" + options.index), options.quality = options.quality || this.getDefaultImageQuality(options.type), this.normalizeImageOptions && this.normalizeImageOptions(options), delete options.type, delete options.index, this.getUrl(url, options) + }, ApiClient.prototype.getScaledImageUrl = function(itemId, options) { + if (!itemId) throw new Error("itemId cannot be empty"); + options = options || {}; + var url = "Items/" + itemId + "/Images/" + options.type; + return null != options.index && (url += "/" + options.index), normalizeImageOptions(this, options), delete options.type, delete options.index, delete options.minScale, this.getUrl(url, options) + }, ApiClient.prototype.getThumbImageUrl = function(item, options) { + if (!item) throw new Error("null item"); + return options = options || {}, options.imageType = "thumb", item.ImageTags && item.ImageTags.Thumb ? (options.tag = item.ImageTags.Thumb, this.getImageUrl(item.Id, options)) : item.ParentThumbItemId ? (options.tag = item.ImageTags.ParentThumbImageTag, this.getImageUrl(item.ParentThumbItemId, options)) : null + }, ApiClient.prototype.updateUserPassword = function(userId, currentPassword, newPassword) { + if (!userId) return Promise.reject(); + var url = this.getUrl("Users/" + userId + "/Password"); + return this.ajax({ + type: "POST", + url: url, + data: JSON.stringify({ + CurrentPw: currentPassword || "", + NewPw: newPassword + }), + contentType: "application/json" + }) + }, ApiClient.prototype.updateEasyPassword = function(userId, newPassword) { + if (!userId) return void Promise.reject(); + var url = this.getUrl("Users/" + userId + "/EasyPassword"); + return this.ajax({ + type: "POST", + url: url, + data: { + NewPw: newPassword + } + }) + }, ApiClient.prototype.resetUserPassword = function(userId) { + if (!userId) throw new Error("null userId"); + var url = this.getUrl("Users/" + userId + "/Password"), + postData = {}; + return postData.resetPassword = !0, this.ajax({ + type: "POST", + url: url, + data: postData + }) + }, ApiClient.prototype.resetEasyPassword = function(userId) { + if (!userId) throw new Error("null userId"); + var url = this.getUrl("Users/" + userId + "/EasyPassword"), + postData = {}; + return postData.resetPassword = !0, this.ajax({ + type: "POST", + url: url, + data: postData + }) + }, ApiClient.prototype.updateServerConfiguration = function(configuration) { + if (!configuration) throw new Error("null configuration"); + var url = this.getUrl("System/Configuration"); + return this.ajax({ + type: "POST", + url: url, + data: JSON.stringify(configuration), + contentType: "application/json" + }) + }, ApiClient.prototype.updateNamedConfiguration = function(name, configuration) { + if (!configuration) throw new Error("null configuration"); + var url = this.getUrl("System/Configuration/" + name); + return this.ajax({ + type: "POST", + url: url, + data: JSON.stringify(configuration), + contentType: "application/json" + }) + }, ApiClient.prototype.updateItem = function(item) { + if (!item) throw new Error("null item"); + var url = this.getUrl("Items/" + item.Id); + return this.ajax({ + type: "POST", + url: url, + data: JSON.stringify(item), + contentType: "application/json" + }) + }, ApiClient.prototype.updatePluginSecurityInfo = function(info) { + var url = this.getUrl("Plugins/SecurityInfo"); + return this.ajax({ + type: "POST", + url: url, + data: JSON.stringify(info), + contentType: "application/json" + }) + }, ApiClient.prototype.createUser = function(name) { + var url = this.getUrl("Users/New"); + return this.ajax({ + type: "POST", + url: url, + data: { + Name: name + }, + dataType: "json" + }) + }, ApiClient.prototype.updateUser = function(user) { + if (!user) throw new Error("null user"); + var url = this.getUrl("Users/" + user.Id); + return this.ajax({ + type: "POST", + url: url, + data: JSON.stringify(user), + contentType: "application/json" + }) + }, ApiClient.prototype.updateUserPolicy = function(userId, policy) { + if (!userId) throw new Error("null userId"); + if (!policy) throw new Error("null policy"); + var url = this.getUrl("Users/" + userId + "/Policy"); + return this.ajax({ + type: "POST", + url: url, + data: JSON.stringify(policy), + contentType: "application/json" + }) + }, ApiClient.prototype.updateUserConfiguration = function(userId, configuration) { + if (!userId) throw new Error("null userId"); + if (!configuration) throw new Error("null configuration"); + var url = this.getUrl("Users/" + userId + "/Configuration"); + return this.ajax({ + type: "POST", + url: url, + data: JSON.stringify(configuration), + contentType: "application/json" + }) + }, ApiClient.prototype.updateScheduledTaskTriggers = function(id, triggers) { + if (!id) throw new Error("null id"); + if (!triggers) throw new Error("null triggers"); + var url = this.getUrl("ScheduledTasks/" + id + "/Triggers"); + return this.ajax({ + type: "POST", + url: url, + data: JSON.stringify(triggers), + contentType: "application/json" + }) + }, ApiClient.prototype.updatePluginConfiguration = function(id, configuration) { + if (!id) throw new Error("null Id"); + if (!configuration) throw new Error("null configuration"); + var url = this.getUrl("Plugins/" + id + "/Configuration"); + return this.ajax({ + type: "POST", + url: url, + data: JSON.stringify(configuration), + contentType: "application/json" + }) + }, ApiClient.prototype.getAncestorItems = function(itemId, userId) { + if (!itemId) throw new Error("null itemId"); + var options = {}; + userId && (options.userId = userId); + var url = this.getUrl("Items/" + itemId + "/Ancestors", options); + return this.getJSON(url) + }, ApiClient.prototype.getItems = function(userId, options) { + var url; + return url = "string" === (typeof userId).toString().toLowerCase() ? this.getUrl("Users/" + userId + "/Items", options) : this.getUrl("Items", options), this.getJSON(url) + }, ApiClient.prototype.getResumableItems = function(userId, options) { + return this.isMinServerVersion("3.2.33") ? this.getJSON(this.getUrl("Users/" + userId + "/Items/Resume", options)) : this.getItems(userId, Object.assign({ + SortBy: "DatePlayed", + SortOrder: "Descending", + Filters: "IsResumable", + Recursive: !0, + CollapseBoxSetItems: !1, + ExcludeLocationTypes: "Virtual" + }, options)) + }, ApiClient.prototype.getMovieRecommendations = function(options) { + return this.getJSON(this.getUrl("Movies/Recommendations", options)) + }, ApiClient.prototype.getUpcomingEpisodes = function(options) { + return this.getJSON(this.getUrl("Shows/Upcoming", options)) + }, ApiClient.prototype.getUserViews = function(options, userId) { + options = options || {}; + var url = this.getUrl("Users/" + (userId || this.getCurrentUserId()) + "/Views", options); + return this.getJSON(url) + }, ApiClient.prototype.getArtists = function(userId, options) { + if (!userId) throw new Error("null userId"); + options = options || {}, options.userId = userId; + var url = this.getUrl("Artists", options); + return this.getJSON(url) + }, ApiClient.prototype.getAlbumArtists = function(userId, options) { + if (!userId) throw new Error("null userId"); + options = options || {}, options.userId = userId; + var url = this.getUrl("Artists/AlbumArtists", options); + return this.getJSON(url) + }, ApiClient.prototype.getGenres = function(userId, options) { + if (!userId) throw new Error("null userId"); + options = options || {}, options.userId = userId; + var url = this.getUrl("Genres", options); + return this.getJSON(url) + }, ApiClient.prototype.getMusicGenres = function(userId, options) { + if (!userId) throw new Error("null userId"); + options = options || {}, options.userId = userId; + var url = this.getUrl("MusicGenres", options); + return this.getJSON(url) + }, ApiClient.prototype.getGameGenres = function(userId, options) { + if (!userId) throw new Error("null userId"); + options = options || {}, options.userId = userId; + var url = this.getUrl("GameGenres", options); + return this.getJSON(url) + }, ApiClient.prototype.getPeople = function(userId, options) { + if (!userId) throw new Error("null userId"); + options = options || {}, options.userId = userId; + var url = this.getUrl("Persons", options); + return this.getJSON(url) + }, ApiClient.prototype.getStudios = function(userId, options) { + if (!userId) throw new Error("null userId"); + options = options || {}, options.userId = userId; + var url = this.getUrl("Studios", options); + return this.getJSON(url) + }, ApiClient.prototype.getLocalTrailers = function(userId, itemId) { + if (!userId) throw new Error("null userId"); + if (!itemId) throw new Error("null itemId"); + var url = this.getUrl("Users/" + userId + "/Items/" + itemId + "/LocalTrailers"); + return this.getJSON(url) + }, ApiClient.prototype.getGameSystems = function() { + var options = {}, + userId = this.getCurrentUserId(); + userId && (options.userId = userId); + var url = this.getUrl("Games/SystemSummaries", options); + return this.getJSON(url) + }, ApiClient.prototype.getAdditionalVideoParts = function(userId, itemId) { + if (!itemId) throw new Error("null itemId"); + var options = {}; + userId && (options.userId = userId); + var url = this.getUrl("Videos/" + itemId + "/AdditionalParts", options); + return this.getJSON(url) + }, ApiClient.prototype.getThemeMedia = function(userId, itemId, inherit) { + if (!itemId) throw new Error("null itemId"); + var options = {}; + userId && (options.userId = userId), options.InheritFromParent = inherit || !1; + var url = this.getUrl("Items/" + itemId + "/ThemeMedia", options); + return this.getJSON(url) + }, ApiClient.prototype.getSearchHints = function(options) { + var url = this.getUrl("Search/Hints", options), + serverId = this.serverId(); + return this.getJSON(url).then(function(result) { + return result.SearchHints.forEach(function(i) { + i.ServerId = serverId + }), result + }) + }, ApiClient.prototype.getSpecialFeatures = function(userId, itemId) { + if (!userId) throw new Error("null userId"); + if (!itemId) throw new Error("null itemId"); + var url = this.getUrl("Users/" + userId + "/Items/" + itemId + "/SpecialFeatures"); + return this.getJSON(url) + }, ApiClient.prototype.getDateParamValue = function(date) { + function formatDigit(i) { + return i < 10 ? "0" + i : i + } + var d = date; + return "" + d.getFullYear() + formatDigit(d.getMonth() + 1) + formatDigit(d.getDate()) + formatDigit(d.getHours()) + formatDigit(d.getMinutes()) + formatDigit(d.getSeconds()) + }, ApiClient.prototype.markPlayed = function(userId, itemId, date) { + if (!userId) throw new Error("null userId"); + if (!itemId) throw new Error("null itemId"); + var options = {}; + date && (options.DatePlayed = this.getDateParamValue(date)); + var url = this.getUrl("Users/" + userId + "/PlayedItems/" + itemId, options); + return this.ajax({ + type: "POST", + url: url, + dataType: "json" + }) + }, ApiClient.prototype.markUnplayed = function(userId, itemId) { + if (!userId) throw new Error("null userId"); + if (!itemId) throw new Error("null itemId"); + var url = this.getUrl("Users/" + userId + "/PlayedItems/" + itemId); + return this.ajax({ + type: "DELETE", + url: url, + dataType: "json" + }) + }, ApiClient.prototype.updateFavoriteStatus = function(userId, itemId, isFavorite) { + if (!userId) throw new Error("null userId"); + if (!itemId) throw new Error("null itemId"); + var url = this.getUrl("Users/" + userId + "/FavoriteItems/" + itemId), + method = isFavorite ? "POST" : "DELETE"; + return this.ajax({ + type: method, + url: url, + dataType: "json" + }) + }, ApiClient.prototype.updateUserItemRating = function(userId, itemId, likes) { + if (!userId) throw new Error("null userId"); + if (!itemId) throw new Error("null itemId"); + var url = this.getUrl("Users/" + userId + "/Items/" + itemId + "/Rating", { + likes: likes + }); + return this.ajax({ + type: "POST", + url: url, + dataType: "json" + }) + }, ApiClient.prototype.getItemCounts = function(userId) { + var options = {}; + userId && (options.userId = userId); + var url = this.getUrl("Items/Counts", options); + return this.getJSON(url) + }, ApiClient.prototype.clearUserItemRating = function(userId, itemId) { + if (!userId) throw new Error("null userId"); + if (!itemId) throw new Error("null itemId"); + var url = this.getUrl("Users/" + userId + "/Items/" + itemId + "/Rating"); + return this.ajax({ + type: "DELETE", + url: url, + dataType: "json" + }) + }, ApiClient.prototype.reportPlaybackStart = function(options) { + if (!options) throw new Error("null options"); + this.lastPlaybackProgressReport = 0, this.lastPlaybackProgressReportTicks = null, stopBitrateDetection(this); + var url = this.getUrl("Sessions/Playing"); + return this.ajax({ + type: "POST", + data: JSON.stringify(options), + contentType: "application/json", + url: url + }) + }, ApiClient.prototype.reportPlaybackProgress = function(options) { + if (!options) throw new Error("null options"); + var newPositionTicks = options.PositionTicks; + if ("timeupdate" === (options.EventName || "timeupdate")) { + var now = (new Date).getTime(), + msSinceLastReport = now - (this.lastPlaybackProgressReport || 0); + if (msSinceLastReport <= 1e4) { + if (!newPositionTicks) return Promise.resolve(); + var expectedReportTicks = 1e4 * msSinceLastReport + (this.lastPlaybackProgressReportTicks || 0); + if (Math.abs((newPositionTicks || 0) - expectedReportTicks) < 5e7) return Promise.resolve() + } + this.lastPlaybackProgressReport = now + } else this.lastPlaybackProgressReport = 0; + this.lastPlaybackProgressReportTicks = newPositionTicks; + var url = this.getUrl("Sessions/Playing/Progress"); + return this.ajax({ + type: "POST", + data: JSON.stringify(options), + contentType: "application/json", + url: url + }) + }, ApiClient.prototype.reportOfflineActions = function(actions) { + if (!actions) throw new Error("null actions"); + var url = this.getUrl("Sync/OfflineActions"); + return this.ajax({ + type: "POST", + data: JSON.stringify(actions), + contentType: "application/json", + url: url + }) + }, ApiClient.prototype.syncData = function(data) { + if (!data) throw new Error("null data"); + var url = this.getUrl("Sync/Data"); + return this.ajax({ + type: "POST", + data: JSON.stringify(data), + contentType: "application/json", + url: url, + dataType: "json" + }) + }, ApiClient.prototype.getReadySyncItems = function(deviceId) { + if (!deviceId) throw new Error("null deviceId"); + var url = this.getUrl("Sync/Items/Ready", { + TargetId: deviceId + }); + return this.getJSON(url) + }, ApiClient.prototype.reportSyncJobItemTransferred = function(syncJobItemId) { + if (!syncJobItemId) throw new Error("null syncJobItemId"); + var url = this.getUrl("Sync/JobItems/" + syncJobItemId + "/Transferred"); + return this.ajax({ + type: "POST", + url: url + }) + }, ApiClient.prototype.cancelSyncItems = function(itemIds, targetId) { + if (!itemIds) throw new Error("null itemIds"); + var url = this.getUrl("Sync/" + (targetId || this.deviceId()) + "/Items", { + ItemIds: itemIds.join(",") + }); + return this.ajax({ + type: "DELETE", + url: url + }) + }, ApiClient.prototype.reportPlaybackStopped = function(options) { + if (!options) throw new Error("null options"); + this.lastPlaybackProgressReport = 0, this.lastPlaybackProgressReportTicks = null, redetectBitrate(this); + var url = this.getUrl("Sessions/Playing/Stopped"); + return this.ajax({ + type: "POST", + data: JSON.stringify(options), + contentType: "application/json", + url: url + }) + }, ApiClient.prototype.sendPlayCommand = function(sessionId, options) { + if (!sessionId) throw new Error("null sessionId"); + if (!options) throw new Error("null options"); + var url = this.getUrl("Sessions/" + sessionId + "/Playing", options); + return this.ajax({ + type: "POST", + url: url + }) + }, ApiClient.prototype.sendCommand = function(sessionId, command) { + if (!sessionId) throw new Error("null sessionId"); + if (!command) throw new Error("null command"); + var url = this.getUrl("Sessions/" + sessionId + "/Command"), + ajaxOptions = { + type: "POST", + url: url + }; + return ajaxOptions.data = JSON.stringify(command), ajaxOptions.contentType = "application/json", this.ajax(ajaxOptions) + }, ApiClient.prototype.sendMessageCommand = function(sessionId, options) { + if (!sessionId) throw new Error("null sessionId"); + if (!options) throw new Error("null options"); + var url = this.getUrl("Sessions/" + sessionId + "/Message"), + ajaxOptions = { + type: "POST", + url: url + }; + return ajaxOptions.data = JSON.stringify(options), ajaxOptions.contentType = "application/json", this.ajax(ajaxOptions) + }, ApiClient.prototype.sendPlayStateCommand = function(sessionId, command, options) { + if (!sessionId) throw new Error("null sessionId"); + if (!command) throw new Error("null command"); + var url = this.getUrl("Sessions/" + sessionId + "/Playing/" + command, options || {}); + return this.ajax({ + type: "POST", + url: url + }) + }, ApiClient.prototype.createPackageReview = function(review) { + var url = this.getUrl("Packages/Reviews/" + review.id, review); + return this.ajax({ + type: "POST", + url: url + }) + }, ApiClient.prototype.getPackageReviews = function(packageId, minRating, maxRating, limit) { + if (!packageId) throw new Error("null packageId"); + var options = {}; + minRating && (options.MinRating = minRating), maxRating && (options.MaxRating = maxRating), limit && (options.Limit = limit); + var url = this.getUrl("Packages/" + packageId + "/Reviews", options); + return this.getJSON(url) + }, ApiClient.prototype.getSavedEndpointInfo = function() { + return this._endPointInfo + }, ApiClient.prototype.getEndpointInfo = function() { + var savedValue = this._endPointInfo; + if (savedValue) return Promise.resolve(savedValue); + var instance = this; + return this.getJSON(this.getUrl("System/Endpoint")).then(function(endPointInfo) { + return setSavedEndpointInfo(instance, endPointInfo), endPointInfo + }) + }, ApiClient.prototype.getWakeOnLanInfo = function() { + return this.getJSON(this.getUrl("System/WakeOnLanInfo")) + }, ApiClient.prototype.getLatestItems = function(options) { + return options = options || {}, this.getJSON(this.getUrl("Users/" + this.getCurrentUserId() + "/Items/Latest", options)) + }, ApiClient.prototype.getFilters = function(options) { + return this.getJSON(this.getUrl("Items/Filters2", options)) + }, ApiClient.prototype.supportsWakeOnLan = function() { + return !!wakeOnLan.isSupported() && getCachedWakeOnLanInfo(this).length > 0 + }, ApiClient.prototype.wakeOnLan = function() { + var infos = getCachedWakeOnLanInfo(this); + return new Promise(function(resolve, reject) { + sendNextWakeOnLan(infos, 0, resolve) + }) + }, ApiClient.prototype.setSystemInfo = function(info) { + this._serverVersion = info.Version + }, ApiClient.prototype.serverVersion = function() { + return this._serverVersion + }, ApiClient.prototype.isMinServerVersion = function(version) { + var serverVersion = this.serverVersion(); + return !!serverVersion && compareVersions(serverVersion, version) >= 0 + }, ApiClient.prototype.handleMessageReceived = function(msg) { + onMessageReceivedInternal(this, msg) + }, ApiClient +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-apiclient/apiclientex.js b/dashboard-ui/bower_components/emby-apiclient/apiclientex.js index 1bab61b0b9..b6a0c1bb14 100644 --- a/dashboard-ui/bower_components/emby-apiclient/apiclientex.js +++ b/dashboard-ui/bower_components/emby-apiclient/apiclientex.js @@ -1 +1,231 @@ -define(["apiclientcore","localassetmanager"],function(ApiClient,localassetmanager){"use strict";function isLocalId(str){return startsWith(str,localPrefix)}function isLocalViewId(str){return startsWith(str,localViewPrefix)}function isTopLevelLocalViewId(str){return"localview"===str}function stripLocalPrefix(str){var res=stripStart(str,localPrefix);return res=stripStart(res,localViewPrefix)}function startsWith(str,find){return!!(str&&find&&str.length>find.length&&0===str.indexOf(find))}function stripStart(str,find){return startsWith(str,find)?str.substr(find.length):str}function createEmptyList(){return{Items:[],TotalRecordCount:0}}function convertGuidToLocal(guid){return guid?isLocalId(guid)?guid:"local:"+guid:null}function adjustGuidProperties(downloadedItem){downloadedItem.Id=convertGuidToLocal(downloadedItem.Id),downloadedItem.SeriesId=convertGuidToLocal(downloadedItem.SeriesId),downloadedItem.SeasonId=convertGuidToLocal(downloadedItem.SeasonId),downloadedItem.AlbumId=convertGuidToLocal(downloadedItem.AlbumId),downloadedItem.ParentId=convertGuidToLocal(downloadedItem.ParentId),downloadedItem.ParentThumbItemId=convertGuidToLocal(downloadedItem.ParentThumbItemId),downloadedItem.ParentPrimaryImageItemId=convertGuidToLocal(downloadedItem.ParentPrimaryImageItemId),downloadedItem.PrimaryImageItemId=convertGuidToLocal(downloadedItem.PrimaryImageItemId),downloadedItem.ParentLogoItemId=convertGuidToLocal(downloadedItem.ParentLogoItemId),downloadedItem.ParentBackdropItemId=convertGuidToLocal(downloadedItem.ParentBackdropItemId),downloadedItem.ParentBackdropImageTags=null}function getLocalView(instance,serverId,userId){return instance.getLocalFolders(serverId,userId).then(function(views){var localView=null;return views.length>0&&(localView={Name:instance.downloadsTitleText||"Downloads",ServerId:serverId,Id:"localview",Type:"localview",IsFolder:!0}),Promise.resolve(localView)})}function ApiClientEx(serverAddress,clientName,applicationVersion,deviceName,deviceId,devicePixelRatio){ApiClient.call(this,serverAddress,clientName,applicationVersion,deviceName,deviceId,devicePixelRatio)}var localPrefix="local:",localViewPrefix="localview:";return Object.assign(ApiClientEx.prototype,ApiClient.prototype),ApiClientEx.prototype.getPlaybackInfo=function(itemId,options,deviceProfile){var onFailure=function(){return ApiClient.prototype.getPlaybackInfo.call(instance,itemId,options,deviceProfile)};if(isLocalId(itemId))return localassetmanager.getLocalItem(this.serverId(),stripLocalPrefix(itemId)).then(function(item){return{MediaSources:item.Item.MediaSources.map(function(m){return m.SupportsDirectPlay=!0,m.SupportsDirectStream=!1,m.SupportsTranscoding=!1,m.IsLocal=!0,m})}},onFailure);var instance=this;return localassetmanager.getLocalItem(this.serverId(),itemId).then(function(item){if(item){var mediaSources=item.Item.MediaSources.map(function(m){return m.SupportsDirectPlay=!0,m.SupportsDirectStream=!1,m.SupportsTranscoding=!1,m.IsLocal=!0,m});return localassetmanager.fileExists(item.LocalPath).then(function(exists){if(exists){var res={MediaSources:mediaSources};return Promise.resolve(res)}return ApiClient.prototype.getPlaybackInfo.call(instance,itemId,options,deviceProfile)},onFailure)}return ApiClient.prototype.getPlaybackInfo.call(instance,itemId,options,deviceProfile)},onFailure)},ApiClientEx.prototype.getItems=function(userId,options){var i,serverInfo=this.serverInfo();if(serverInfo&&"localview"===options.ParentId)return this.getLocalFolders(serverInfo.Id,userId).then(function(items){var result={Items:items,TotalRecordCount:items.length};return Promise.resolve(result)});if(serverInfo&&options&&(isLocalId(options.ParentId)||isLocalId(options.SeriesId)||isLocalId(options.SeasonId)||isLocalViewId(options.ParentId)||isLocalId(options.AlbumIds)))return localassetmanager.getViewItems(serverInfo.Id,userId,options).then(function(items){items.forEach(function(item){adjustGuidProperties(item)});var result={Items:items,TotalRecordCount:items.length};return Promise.resolve(result)});if(options&&options.ExcludeItemIds&&options.ExcludeItemIds.length){var exItems=options.ExcludeItemIds.split(",");for(i=0;i0?Promise.resolve(views[0]):Promise.reject()}):isLocalId(itemId)&&(serverInfo=this.serverInfo())?localassetmanager.getLocalItem(serverInfo.Id,stripLocalPrefix(itemId)).then(function(item){return adjustGuidProperties(item.Item),Promise.resolve(item.Item)}):ApiClient.prototype.getItem.call(this,userId,itemId)},ApiClientEx.prototype.getLocalFolders=function(userId){var serverInfo=this.serverInfo();return userId=userId||serverInfo.UserId,localassetmanager.getViews(serverInfo.Id,userId)},ApiClientEx.prototype.getNextUpEpisodes=function(options){return options.SeriesId&&isLocalId(options.SeriesId)?Promise.resolve(createEmptyList()):ApiClient.prototype.getNextUpEpisodes.call(this,options)},ApiClientEx.prototype.getSeasons=function(itemId,options){return isLocalId(itemId)?(options.SeriesId=itemId,options.IncludeItemTypes="Season",options.SortBy="SortName",this.getItems(this.getCurrentUserId(),options)):ApiClient.prototype.getSeasons.call(this,itemId,options)},ApiClientEx.prototype.getEpisodes=function(itemId,options){return isLocalId(options.SeasonId)||isLocalId(options.seasonId)?(options.SeriesId=itemId,options.IncludeItemTypes="Episode",options.SortBy="SortName",this.getItems(this.getCurrentUserId(),options)):isLocalId(itemId)?(options.SeriesId=itemId,options.IncludeItemTypes="Episode",options.SortBy="SortName",this.getItems(this.getCurrentUserId(),options)):ApiClient.prototype.getEpisodes.call(this,itemId,options)},ApiClientEx.prototype.getLatestOfflineItems=function(options){options.SortBy="DateCreated",options.SortOrder="Descending";var serverInfo=this.serverInfo();return serverInfo?localassetmanager.getViewItems(serverInfo.Id,null,options).then(function(items){return items.forEach(function(item){adjustGuidProperties(item)}),Promise.resolve(items)}):Promise.resolve([])},ApiClientEx.prototype.getThemeMedia=function(userId,itemId,inherit){return isLocalViewId(itemId)||isLocalId(itemId)||isTopLevelLocalViewId(itemId)?Promise.reject():ApiClient.prototype.getThemeMedia.call(this,userId,itemId,inherit)},ApiClientEx.prototype.getSpecialFeatures=function(userId,itemId){return isLocalId(itemId)?Promise.resolve([]):ApiClient.prototype.getSpecialFeatures.call(this,userId,itemId)},ApiClientEx.prototype.getSimilarItems=function(itemId,options){return isLocalId(itemId)?Promise.resolve(createEmptyList()):ApiClient.prototype.getSimilarItems.call(this,itemId,options)},ApiClientEx.prototype.updateFavoriteStatus=function(userId,itemId,isFavorite){return isLocalId(itemId)?Promise.resolve():ApiClient.prototype.updateFavoriteStatus.call(this,userId,itemId,isFavorite)},ApiClientEx.prototype.getScaledImageUrl=function(itemId,options){if(isLocalId(itemId)||options&&options.itemid&&isLocalId(options.itemid)){var serverInfo=this.serverInfo(),id=stripLocalPrefix(itemId);return localassetmanager.getImageUrl(serverInfo.Id,id,options)}return ApiClient.prototype.getScaledImageUrl.call(this,itemId,options)},ApiClientEx.prototype.reportPlaybackStart=function(options){if(!options)throw new Error("null options");return isLocalId(options.ItemId)?Promise.resolve():ApiClient.prototype.reportPlaybackStart.call(this,options)},ApiClientEx.prototype.reportPlaybackProgress=function(options){if(!options)throw new Error("null options");if(isLocalId(options.ItemId)){var serverInfo=this.serverInfo();return serverInfo?localassetmanager.getLocalItem(serverInfo.Id,stripLocalPrefix(options.ItemId)).then(function(item){var libraryItem=item.Item;return"Video"===libraryItem.MediaType||"AudioBook"===libraryItem.Type?(libraryItem.UserData=libraryItem.UserData||{},libraryItem.UserData.PlaybackPositionTicks=options.PositionTicks,libraryItem.UserData.PlayedPercentage=Math.min(libraryItem.RunTimeTicks?(options.PositionTicks||0)/libraryItem.RunTimeTicks*100:0,100),localassetmanager.addOrUpdateLocalItem(item)):Promise.resolve()}):Promise.resolve()}return ApiClient.prototype.reportPlaybackProgress.call(this,options)},ApiClientEx.prototype.reportPlaybackStopped=function(options){if(!options)throw new Error("null options");if(isLocalId(options.ItemId)){var serverInfo=this.serverInfo(),action={Date:(new Date).getTime(),ItemId:stripLocalPrefix(options.ItemId),PositionTicks:options.PositionTicks,ServerId:serverInfo.Id,Type:0,UserId:this.getCurrentUserId()};return localassetmanager.recordUserAction(action)}return ApiClient.prototype.reportPlaybackStopped.call(this,options)},ApiClientEx.prototype.getIntros=function(itemId){return isLocalId(itemId)?Promise.resolve({Items:[],TotalRecordCount:0}):ApiClient.prototype.getIntros.call(this,itemId)},ApiClientEx.prototype.getInstantMixFromItem=function(itemId,options){return isLocalId(itemId)?Promise.resolve({Items:[],TotalRecordCount:0}):ApiClient.prototype.getInstantMixFromItem.call(this,itemId,options)},ApiClientEx.prototype.getItemDownloadUrl=function(itemId){if(isLocalId(itemId)){var serverInfo=this.serverInfo();if(serverInfo)return localassetmanager.getLocalItem(serverInfo.Id,stripLocalPrefix(itemId)).then(function(item){return Promise.resolve(item.LocalPath)})}return ApiClient.prototype.getItemDownloadUrl.call(this,itemId)},ApiClientEx}); \ No newline at end of file +define(["apiclientcore", "localassetmanager"], function(ApiClient, localassetmanager) { + "use strict"; + + function isLocalId(str) { + return startsWith(str, localPrefix) + } + + function isLocalViewId(str) { + return startsWith(str, localViewPrefix) + } + + function isTopLevelLocalViewId(str) { + return "localview" === str + } + + function stripLocalPrefix(str) { + var res = stripStart(str, localPrefix); + return res = stripStart(res, localViewPrefix) + } + + function startsWith(str, find) { + return !!(str && find && str.length > find.length && 0 === str.indexOf(find)) + } + + function stripStart(str, find) { + return startsWith(str, find) ? str.substr(find.length) : str + } + + function createEmptyList() { + return { + Items: [], + TotalRecordCount: 0 + } + } + + function convertGuidToLocal(guid) { + return guid ? isLocalId(guid) ? guid : "local:" + guid : null + } + + function adjustGuidProperties(downloadedItem) { + downloadedItem.Id = convertGuidToLocal(downloadedItem.Id), downloadedItem.SeriesId = convertGuidToLocal(downloadedItem.SeriesId), downloadedItem.SeasonId = convertGuidToLocal(downloadedItem.SeasonId), downloadedItem.AlbumId = convertGuidToLocal(downloadedItem.AlbumId), downloadedItem.ParentId = convertGuidToLocal(downloadedItem.ParentId), downloadedItem.ParentThumbItemId = convertGuidToLocal(downloadedItem.ParentThumbItemId), downloadedItem.ParentPrimaryImageItemId = convertGuidToLocal(downloadedItem.ParentPrimaryImageItemId), downloadedItem.PrimaryImageItemId = convertGuidToLocal(downloadedItem.PrimaryImageItemId), downloadedItem.ParentLogoItemId = convertGuidToLocal(downloadedItem.ParentLogoItemId), downloadedItem.ParentBackdropItemId = convertGuidToLocal(downloadedItem.ParentBackdropItemId), downloadedItem.ParentBackdropImageTags = null + } + + function getLocalView(instance, serverId, userId) { + return instance.getLocalFolders(serverId, userId).then(function(views) { + var localView = null; + return views.length > 0 && (localView = { + Name: instance.downloadsTitleText || "Downloads", + ServerId: serverId, + Id: "localview", + Type: "localview", + IsFolder: !0 + }), Promise.resolve(localView) + }) + } + + function ApiClientEx(serverAddress, clientName, applicationVersion, deviceName, deviceId, devicePixelRatio) { + ApiClient.call(this, serverAddress, clientName, applicationVersion, deviceName, deviceId, devicePixelRatio) + } + var localPrefix = "local:", + localViewPrefix = "localview:"; + return Object.assign(ApiClientEx.prototype, ApiClient.prototype), ApiClientEx.prototype.getPlaybackInfo = function(itemId, options, deviceProfile) { + var onFailure = function() { + return ApiClient.prototype.getPlaybackInfo.call(instance, itemId, options, deviceProfile) + }; + if (isLocalId(itemId)) return localassetmanager.getLocalItem(this.serverId(), stripLocalPrefix(itemId)).then(function(item) { + return { + MediaSources: item.Item.MediaSources.map(function(m) { + return m.SupportsDirectPlay = !0, m.SupportsDirectStream = !1, m.SupportsTranscoding = !1, m.IsLocal = !0, m + }) + } + }, onFailure); + var instance = this; + return localassetmanager.getLocalItem(this.serverId(), itemId).then(function(item) { + if (item) { + var mediaSources = item.Item.MediaSources.map(function(m) { + return m.SupportsDirectPlay = !0, m.SupportsDirectStream = !1, m.SupportsTranscoding = !1, m.IsLocal = !0, m + }); + return localassetmanager.fileExists(item.LocalPath).then(function(exists) { + if (exists) { + var res = { + MediaSources: mediaSources + }; + return Promise.resolve(res) + } + return ApiClient.prototype.getPlaybackInfo.call(instance, itemId, options, deviceProfile) + }, onFailure) + } + return ApiClient.prototype.getPlaybackInfo.call(instance, itemId, options, deviceProfile) + }, onFailure) + }, ApiClientEx.prototype.getItems = function(userId, options) { + var i, serverInfo = this.serverInfo(); + if (serverInfo && "localview" === options.ParentId) return this.getLocalFolders(serverInfo.Id, userId).then(function(items) { + var result = { + Items: items, + TotalRecordCount: items.length + }; + return Promise.resolve(result) + }); + if (serverInfo && options && (isLocalId(options.ParentId) || isLocalId(options.SeriesId) || isLocalId(options.SeasonId) || isLocalViewId(options.ParentId) || isLocalId(options.AlbumIds))) return localassetmanager.getViewItems(serverInfo.Id, userId, options).then(function(items) { + items.forEach(function(item) { + adjustGuidProperties(item) + }); + var result = { + Items: items, + TotalRecordCount: items.length + }; + return Promise.resolve(result) + }); + if (options && options.ExcludeItemIds && options.ExcludeItemIds.length) { + var exItems = options.ExcludeItemIds.split(","); + for (i = 0; i < exItems.length; i++) + if (isLocalId(exItems[i])) return Promise.resolve(createEmptyList()) + } else if (options && options.Ids && options.Ids.length) { + var ids = options.Ids.split(","), + hasLocal = !1; + for (i = 0; i < ids.length; i++) isLocalId(ids[i]) && (hasLocal = !0); + if (hasLocal) return localassetmanager.getItemsFromIds(serverInfo.Id, ids).then(function(items) { + items.forEach(function(item) { + adjustGuidProperties(item) + }); + var result = { + Items: items, + TotalRecordCount: items.length + }; + return Promise.resolve(result) + }) + } + return ApiClient.prototype.getItems.call(this, userId, options) + }, ApiClientEx.prototype.getUserViews = function(options, userId) { + var instance = this; + options = options || {}; + var basePromise = ApiClient.prototype.getUserViews.call(instance, options, userId); + return options.enableLocalView ? basePromise.then(function(result) { + var serverInfo = instance.serverInfo(); + return serverInfo ? getLocalView(instance, serverInfo.Id, userId).then(function(localView) { + return localView && (result.Items.push(localView), result.TotalRecordCount++), Promise.resolve(result) + }) : Promise.resolve(result) + }) : basePromise + }, ApiClientEx.prototype.getItem = function(userId, itemId) { + if (!itemId) throw new Error("null itemId"); + itemId && (itemId = itemId.toString()); + var serverInfo; + return isTopLevelLocalViewId(itemId) && (serverInfo = this.serverInfo()) ? getLocalView(this, serverInfo.Id, userId) : isLocalViewId(itemId) && (serverInfo = this.serverInfo()) ? this.getLocalFolders(serverInfo.Id, userId).then(function(items) { + var views = items.filter(function(item) { + return item.Id === itemId + }); + return views.length > 0 ? Promise.resolve(views[0]) : Promise.reject() + }) : isLocalId(itemId) && (serverInfo = this.serverInfo()) ? localassetmanager.getLocalItem(serverInfo.Id, stripLocalPrefix(itemId)).then(function(item) { + return adjustGuidProperties(item.Item), Promise.resolve(item.Item) + }) : ApiClient.prototype.getItem.call(this, userId, itemId) + }, ApiClientEx.prototype.getLocalFolders = function(userId) { + var serverInfo = this.serverInfo(); + return userId = userId || serverInfo.UserId, localassetmanager.getViews(serverInfo.Id, userId) + }, ApiClientEx.prototype.getNextUpEpisodes = function(options) { + return options.SeriesId && isLocalId(options.SeriesId) ? Promise.resolve(createEmptyList()) : ApiClient.prototype.getNextUpEpisodes.call(this, options) + }, ApiClientEx.prototype.getSeasons = function(itemId, options) { + return isLocalId(itemId) ? (options.SeriesId = itemId, options.IncludeItemTypes = "Season", options.SortBy = "SortName", this.getItems(this.getCurrentUserId(), options)) : ApiClient.prototype.getSeasons.call(this, itemId, options) + }, ApiClientEx.prototype.getEpisodes = function(itemId, options) { + return isLocalId(options.SeasonId) || isLocalId(options.seasonId) ? (options.SeriesId = itemId, options.IncludeItemTypes = "Episode", options.SortBy = "SortName", this.getItems(this.getCurrentUserId(), options)) : isLocalId(itemId) ? (options.SeriesId = itemId, options.IncludeItemTypes = "Episode", options.SortBy = "SortName", this.getItems(this.getCurrentUserId(), options)) : ApiClient.prototype.getEpisodes.call(this, itemId, options) + }, ApiClientEx.prototype.getLatestOfflineItems = function(options) { + options.SortBy = "DateCreated", options.SortOrder = "Descending"; + var serverInfo = this.serverInfo(); + return serverInfo ? localassetmanager.getViewItems(serverInfo.Id, null, options).then(function(items) { + return items.forEach(function(item) { + adjustGuidProperties(item) + }), Promise.resolve(items) + }) : Promise.resolve([]) + }, ApiClientEx.prototype.getThemeMedia = function(userId, itemId, inherit) { + return isLocalViewId(itemId) || isLocalId(itemId) || isTopLevelLocalViewId(itemId) ? Promise.reject() : ApiClient.prototype.getThemeMedia.call(this, userId, itemId, inherit) + }, ApiClientEx.prototype.getSpecialFeatures = function(userId, itemId) { + return isLocalId(itemId) ? Promise.resolve([]) : ApiClient.prototype.getSpecialFeatures.call(this, userId, itemId) + }, ApiClientEx.prototype.getSimilarItems = function(itemId, options) { + return isLocalId(itemId) ? Promise.resolve(createEmptyList()) : ApiClient.prototype.getSimilarItems.call(this, itemId, options) + }, ApiClientEx.prototype.updateFavoriteStatus = function(userId, itemId, isFavorite) { + return isLocalId(itemId) ? Promise.resolve() : ApiClient.prototype.updateFavoriteStatus.call(this, userId, itemId, isFavorite) + }, ApiClientEx.prototype.getScaledImageUrl = function(itemId, options) { + if (isLocalId(itemId) || options && options.itemid && isLocalId(options.itemid)) { + var serverInfo = this.serverInfo(), + id = stripLocalPrefix(itemId); + return localassetmanager.getImageUrl(serverInfo.Id, id, options) + } + return ApiClient.prototype.getScaledImageUrl.call(this, itemId, options) + }, ApiClientEx.prototype.reportPlaybackStart = function(options) { + if (!options) throw new Error("null options"); + return isLocalId(options.ItemId) ? Promise.resolve() : ApiClient.prototype.reportPlaybackStart.call(this, options) + }, ApiClientEx.prototype.reportPlaybackProgress = function(options) { + if (!options) throw new Error("null options"); + if (isLocalId(options.ItemId)) { + var serverInfo = this.serverInfo(); + return serverInfo ? localassetmanager.getLocalItem(serverInfo.Id, stripLocalPrefix(options.ItemId)).then(function(item) { + var libraryItem = item.Item; + return "Video" === libraryItem.MediaType || "AudioBook" === libraryItem.Type ? (libraryItem.UserData = libraryItem.UserData || {}, libraryItem.UserData.PlaybackPositionTicks = options.PositionTicks, libraryItem.UserData.PlayedPercentage = Math.min(libraryItem.RunTimeTicks ? (options.PositionTicks || 0) / libraryItem.RunTimeTicks * 100 : 0, 100), localassetmanager.addOrUpdateLocalItem(item)) : Promise.resolve() + }) : Promise.resolve() + } + return ApiClient.prototype.reportPlaybackProgress.call(this, options) + }, ApiClientEx.prototype.reportPlaybackStopped = function(options) { + if (!options) throw new Error("null options"); + if (isLocalId(options.ItemId)) { + var serverInfo = this.serverInfo(), + action = { + Date: (new Date).getTime(), + ItemId: stripLocalPrefix(options.ItemId), + PositionTicks: options.PositionTicks, + ServerId: serverInfo.Id, + Type: 0, + UserId: this.getCurrentUserId() + }; + return localassetmanager.recordUserAction(action) + } + return ApiClient.prototype.reportPlaybackStopped.call(this, options) + }, ApiClientEx.prototype.getIntros = function(itemId) { + return isLocalId(itemId) ? Promise.resolve({ + Items: [], + TotalRecordCount: 0 + }) : ApiClient.prototype.getIntros.call(this, itemId) + }, ApiClientEx.prototype.getInstantMixFromItem = function(itemId, options) { + return isLocalId(itemId) ? Promise.resolve({ + Items: [], + TotalRecordCount: 0 + }) : ApiClient.prototype.getInstantMixFromItem.call(this, itemId, options) + }, ApiClientEx.prototype.getItemDownloadUrl = function(itemId) { + if (isLocalId(itemId)) { + var serverInfo = this.serverInfo(); + if (serverInfo) return localassetmanager.getLocalItem(serverInfo.Id, stripLocalPrefix(itemId)).then(function(item) { + return Promise.resolve(item.LocalPath) + }) + } + return ApiClient.prototype.getItemDownloadUrl.call(this, itemId) + }, ApiClientEx +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-apiclient/appstorage-cache.js b/dashboard-ui/bower_components/emby-apiclient/appstorage-cache.js index bbad4e1ffe..1f584f2a2b 100644 --- a/dashboard-ui/bower_components/emby-apiclient/appstorage-cache.js +++ b/dashboard-ui/bower_components/emby-apiclient/appstorage-cache.js @@ -1 +1,23 @@ -define([],function(){"use strict";function MyStore(){}function updateCache(instance){instance.cache.put("data",new Response(JSON.stringify(instance.localData)))}return MyStore.prototype.init=function(){var instance=this;return caches.open("embydata").then(function(result){instance.cache=result,instance.localData={}})},MyStore.prototype.setItem=function(name,value){if(this.localData){this.localData[name]!==value&&(this.localData[name]=value,updateCache(this))}},MyStore.prototype.getItem=function(name){if(this.localData)return this.localData[name]},MyStore.prototype.removeItem=function(name){this.localData&&(this.localData[name]=null,delete this.localData[name],updateCache(this))},new MyStore}); \ No newline at end of file +define([], function() { + "use strict"; + + function MyStore() {} + + function updateCache(instance) { + instance.cache.put("data", new Response(JSON.stringify(instance.localData))) + } + return MyStore.prototype.init = function() { + var instance = this; + return caches.open("embydata").then(function(result) { + instance.cache = result, instance.localData = {} + }) + }, MyStore.prototype.setItem = function(name, value) { + if (this.localData) { + this.localData[name] !== value && (this.localData[name] = value, updateCache(this)) + } + }, MyStore.prototype.getItem = function(name) { + if (this.localData) return this.localData[name] + }, MyStore.prototype.removeItem = function(name) { + this.localData && (this.localData[name] = null, delete this.localData[name], updateCache(this)) + }, new MyStore +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-apiclient/appstorage-localstorage.js b/dashboard-ui/bower_components/emby-apiclient/appstorage-localstorage.js index 5f23b2bb6e..4baa82618e 100644 --- a/dashboard-ui/bower_components/emby-apiclient/appstorage-localstorage.js +++ b/dashboard-ui/bower_components/emby-apiclient/appstorage-localstorage.js @@ -1 +1,37 @@ -define([],function(){"use strict";function onCachePutFail(e){console.log(e)}function updateCache(instance){var cache=instance.cache;cache&&cache.put("data",new Response(JSON.stringify(instance.localData))).catch(onCachePutFail)}function onCacheOpened(result){this.cache=result,this.localData={}}function MyStore(){try{self.caches&&caches.open("embydata").then(onCacheOpened.bind(this))}catch(err){console.log("Error opening cache: "+err)}}return MyStore.prototype.setItem=function(name,value){localStorage.setItem(name,value);var localData=this.localData;if(localData){localData[name]!==value&&(localData[name]=value,updateCache(this))}},MyStore.prototype.getItem=function(name){return localStorage.getItem(name)},MyStore.prototype.removeItem=function(name){localStorage.removeItem(name);var localData=this.localData;localData&&(localData[name]=null,delete localData[name],updateCache(this))},new MyStore}); \ No newline at end of file +define([], function() { + "use strict"; + + function onCachePutFail(e) { + console.log(e) + } + + function updateCache(instance) { + var cache = instance.cache; + cache && cache.put("data", new Response(JSON.stringify(instance.localData))).catch(onCachePutFail) + } + + function onCacheOpened(result) { + this.cache = result, this.localData = {} + } + + function MyStore() { + try { + self.caches && caches.open("embydata").then(onCacheOpened.bind(this)) + } catch (err) { + console.log("Error opening cache: " + err) + } + } + return MyStore.prototype.setItem = function(name, value) { + localStorage.setItem(name, value); + var localData = this.localData; + if (localData) { + localData[name] !== value && (localData[name] = value, updateCache(this)) + } + }, MyStore.prototype.getItem = function(name) { + return localStorage.getItem(name) + }, MyStore.prototype.removeItem = function(name) { + localStorage.removeItem(name); + var localData = this.localData; + localData && (localData[name] = null, delete localData[name], updateCache(this)) + }, new MyStore +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-apiclient/appstorage-memory.js b/dashboard-ui/bower_components/emby-apiclient/appstorage-memory.js index 370934de37..75aab19923 100644 --- a/dashboard-ui/bower_components/emby-apiclient/appstorage-memory.js +++ b/dashboard-ui/bower_components/emby-apiclient/appstorage-memory.js @@ -1 +1,14 @@ -define([],function(){"use strict";function MyStore(){this.localData={}}return MyStore.prototype.setItem=function(name,value){this.localData[name]=value},MyStore.prototype.getItem=function(name){return this.localData[name]},MyStore.prototype.removeItem=function(name){this.localData[name]=null},new MyStore}); \ No newline at end of file +define([], function() { + "use strict"; + + function MyStore() { + this.localData = {} + } + return MyStore.prototype.setItem = function(name, value) { + this.localData[name] = value + }, MyStore.prototype.getItem = function(name) { + return this.localData[name] + }, MyStore.prototype.removeItem = function(name) { + this.localData[name] = null + }, new MyStore +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-apiclient/cameraroll.js b/dashboard-ui/bower_components/emby-apiclient/cameraroll.js index 36c80a995f..fddd1a1850 100644 --- a/dashboard-ui/bower_components/emby-apiclient/cameraroll.js +++ b/dashboard-ui/bower_components/emby-apiclient/cameraroll.js @@ -1 +1,8 @@ -define([],function(){"use strict";function CameraRoll(){}return CameraRoll.prototype.getFiles=function(){return Promise.resolve([])},new CameraRoll}); \ No newline at end of file +define([], function() { + "use strict"; + + function CameraRoll() {} + return CameraRoll.prototype.getFiles = function() { + return Promise.resolve([]) + }, new CameraRoll +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-apiclient/connectionmanager.js b/dashboard-ui/bower_components/emby-apiclient/connectionmanager.js index 9aeddd5358..39824d31f7 100644 --- a/dashboard-ui/bower_components/emby-apiclient/connectionmanager.js +++ b/dashboard-ui/bower_components/emby-apiclient/connectionmanager.js @@ -741,4 +741,4 @@ define(["events", "apiclient", "appStorage"], function(events, apiClientFactory, } } }, ConnectionManager -}); +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-apiclient/credentials.js b/dashboard-ui/bower_components/emby-apiclient/credentials.js index 1c15bce01b..51a9cb55c6 100644 --- a/dashboard-ui/bower_components/emby-apiclient/credentials.js +++ b/dashboard-ui/bower_components/emby-apiclient/credentials.js @@ -1 +1,29 @@ -define(["events","appStorage"],function(events,appStorage){"use strict";function ensure(instance,data){if(!instance._credentials){var json=appStorage.getItem(instance.key)||"{}";console.log("credentials initialized with: "+json),instance._credentials=JSON.parse(json),instance._credentials.Servers=instance._credentials.Servers||[]}}function set(instance,data){data?(instance._credentials=data,appStorage.setItem(instance.key,JSON.stringify(data))):instance.clear(),events.trigger(instance,"credentialsupdated")}function Credentials(key){this.key=key||"servercredentials3"}return Credentials.prototype.clear=function(){this._credentials=null,appStorage.removeItem(this.key)},Credentials.prototype.credentials=function(data){return data&&set(this,data),ensure(this),this._credentials},Credentials.prototype.addOrUpdateServer=function(list,server){if(!server.Id)throw new Error("Server.Id cannot be null or empty");var existing=list.filter(function(s){return s.Id===server.Id})[0];return existing?(existing.DateLastAccessed=Math.max(existing.DateLastAccessed||0,server.DateLastAccessed||0),existing.UserLinkType=server.UserLinkType,server.AccessToken&&(existing.AccessToken=server.AccessToken,existing.UserId=server.UserId),server.ExchangeToken&&(existing.ExchangeToken=server.ExchangeToken),server.RemoteAddress&&(existing.RemoteAddress=server.RemoteAddress),server.ManualAddress&&(existing.ManualAddress=server.ManualAddress),server.LocalAddress&&(existing.LocalAddress=server.LocalAddress),server.Name&&(existing.Name=server.Name),server.WakeOnLanInfos&&server.WakeOnLanInfos.length&&(existing.WakeOnLanInfos=server.WakeOnLanInfos),null!=server.LastConnectionMode&&(existing.LastConnectionMode=server.LastConnectionMode),server.ConnectServerId&&(existing.ConnectServerId=server.ConnectServerId),existing):(list.push(server),server)},Credentials}); \ No newline at end of file +define(["events", "appStorage"], function(events, appStorage) { + "use strict"; + + function ensure(instance, data) { + if (!instance._credentials) { + var json = appStorage.getItem(instance.key) || "{}"; + console.log("credentials initialized with: " + json), instance._credentials = JSON.parse(json), instance._credentials.Servers = instance._credentials.Servers || [] + } + } + + function set(instance, data) { + data ? (instance._credentials = data, appStorage.setItem(instance.key, JSON.stringify(data))) : instance.clear(), events.trigger(instance, "credentialsupdated") + } + + function Credentials(key) { + this.key = key || "servercredentials3" + } + return Credentials.prototype.clear = function() { + this._credentials = null, appStorage.removeItem(this.key) + }, Credentials.prototype.credentials = function(data) { + return data && set(this, data), ensure(this), this._credentials + }, Credentials.prototype.addOrUpdateServer = function(list, server) { + if (!server.Id) throw new Error("Server.Id cannot be null or empty"); + var existing = list.filter(function(s) { + return s.Id === server.Id + })[0]; + return existing ? (existing.DateLastAccessed = Math.max(existing.DateLastAccessed || 0, server.DateLastAccessed || 0), existing.UserLinkType = server.UserLinkType, server.AccessToken && (existing.AccessToken = server.AccessToken, existing.UserId = server.UserId), server.ExchangeToken && (existing.ExchangeToken = server.ExchangeToken), server.RemoteAddress && (existing.RemoteAddress = server.RemoteAddress), server.ManualAddress && (existing.ManualAddress = server.ManualAddress), server.LocalAddress && (existing.LocalAddress = server.LocalAddress), server.Name && (existing.Name = server.Name), server.WakeOnLanInfos && server.WakeOnLanInfos.length && (existing.WakeOnLanInfos = server.WakeOnLanInfos), null != server.LastConnectionMode && (existing.LastConnectionMode = server.LastConnectionMode), server.ConnectServerId && (existing.ConnectServerId = server.ConnectServerId), existing) : (list.push(server), server) + }, Credentials +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-apiclient/events.js b/dashboard-ui/bower_components/emby-apiclient/events.js index 7ac4956539..6204dc4d4f 100644 --- a/dashboard-ui/bower_components/emby-apiclient/events.js +++ b/dashboard-ui/bower_components/emby-apiclient/events.js @@ -1 +1,30 @@ -define([],function(){"use strict";function getCallbacks(obj,name){if(!obj)throw new Error("obj cannot be null!");obj._callbacks=obj._callbacks||{};var list=obj._callbacks[name];return list||(obj._callbacks[name]=[],list=obj._callbacks[name]),list}return{on:function(obj,eventName,fn){getCallbacks(obj,eventName).push(fn)},off:function(obj,eventName,fn){var list=getCallbacks(obj,eventName),i=list.indexOf(fn);-1!==i&&list.splice(i,1)},trigger:function(obj,eventName){var eventObject={type:eventName},eventArgs=[];eventArgs.push(eventObject);for(var additionalArgs=arguments[2]||[],i=0,length=additionalArgs.length;i-1&&(item={Name:"Music",ServerId:serverId,Id:"localview:MusicView",Type:"MusicView",CollectionType:"music",IsFolder:!0},list.push(item)),types.indexOf("Photo")>-1&&(item={Name:"Photos",ServerId:serverId,Id:"localview:PhotosView",Type:"PhotosView",CollectionType:"photos",IsFolder:!0},list.push(item)),types.indexOf("Episode")>-1&&(item={Name:"TV",ServerId:serverId,Id:"localview:TVView",Type:"TVView",CollectionType:"tvshows",IsFolder:!0},list.push(item)),types.indexOf("Movie")>-1&&(item={Name:"Movies",ServerId:serverId,Id:"localview:MoviesView",Type:"MoviesView",CollectionType:"movies",IsFolder:!0},list.push(item)),types.indexOf("Video")>-1&&(item={Name:"Videos",ServerId:serverId,Id:"localview:VideosView",Type:"VideosView",CollectionType:"videos",IsFolder:!0},list.push(item)),types.indexOf("MusicVideo")>-1&&(item={Name:"Music Videos",ServerId:serverId,Id:"localview:MusicVideosView",Type:"MusicVideosView",CollectionType:"videos",IsFolder:!0},list.push(item)),Promise.resolve(list)})}function updateFiltersForTopLevelView(parentId,mediaTypes,includeItemTypes,query){switch(parentId){case"MusicView":return query.Recursive?includeItemTypes.push("Audio"):includeItemTypes.push("MusicAlbum"),!0;case"PhotosView":return query.Recursive?includeItemTypes.push("Photo"):includeItemTypes.push("PhotoAlbum"),!0;case"TVView":return query.Recursive?includeItemTypes.push("Episode"):includeItemTypes.push("Series"),!0;case"VideosView":return query.Recursive,includeItemTypes.push("Video"),!0;case"MoviesView":return query.Recursive,includeItemTypes.push("Movie"),!0;case"MusicVideosView":return query.Recursive,includeItemTypes.push("MusicVideo"),!0}return!1}function normalizeId(id){return id?(id=stripStart(id,"localview:"),id=stripStart(id,"local:")):null}function normalizeIdList(val){return val?val.split(",").map(normalizeId):[]}function shuffle(array){for(var temporaryValue,randomIndex,currentIndex=array.length;0!==currentIndex;)randomIndex=Math.floor(Math.random()*currentIndex),currentIndex-=1,temporaryValue=array[currentIndex],array[currentIndex]=array[randomIndex],array[randomIndex]=temporaryValue;return array}function sortItems(items,query){if(!query.SortBy||0===query.SortBy.length)return items;if("Random"===query.SortBy)return shuffle(items);var sortSpec=getSortSpec(query);return items.sort(function(a,b){for(var i=0;ivalB?result=1:valA0&&mediaSource.MediaStreams.forEach(function(mediaStream){mediaStream.Path&&(p=p.then(function(){return filerepository.deleteFile(mediaStream.Path)}))})}),p.then(onFileDeletedSuccessOrFail,onFileDeletedSuccessOrFail)},function(item){return Promise.resolve()})}function addOrUpdateLocalItem(localItem){return itemrepository.set(localItem.ServerId,localItem.Id,localItem)}function getSubtitleSaveFileName(localItem,mediaPath,language,isForced,format){var name=getNameWithoutExtension(mediaPath);name=filerepository.getValidFileName(name),language&&(name+="."+language.toLowerCase()),isForced&&(name+=".foreign"),name=name+"."+format.toLowerCase();var mediaFolder=filerepository.getParentPath(localItem.LocalPath);return filerepository.combinePath(mediaFolder,name)}function getItemFileSize(path){return filerepository.getItemFileSize(path)}function getNameWithoutExtension(path){var fileName=path,pos=fileName.lastIndexOf(".");return pos>0&&(fileName=fileName.substring(0,pos)),fileName}function downloadFile(url,localItem){var imageUrl=getImageUrl(localItem.Item.ServerId,localItem.Item.Id,{type:"Primary",index:0});return transfermanager.downloadFile(url,localItem,imageUrl)}function downloadSubtitles(url,fileName){return transfermanager.downloadSubtitles(url,fileName)}function getImageUrl(serverId,itemId,imageOptions){var imageType=imageOptions.type,index=imageOptions.index,pathArray=getImagePath(serverId,itemId,imageType,index);return filerepository.getImageUrl(pathArray)}function hasImage(serverId,itemId,imageType,index){var pathArray=getImagePath(serverId,itemId,imageType,index),localFilePath=filerepository.getFullMetadataPath(pathArray);return filerepository.fileExists(localFilePath).then(function(exists){return Promise.resolve(exists)},function(err){return Promise.resolve(!1)})}function fileExists(localFilePath){return filerepository.fileExists(localFilePath)}function downloadImage(localItem,url,serverId,itemId,imageType,index){var localPathParts=getImagePath(serverId,itemId,imageType,index);return transfermanager.downloadImage(url,localPathParts)}function isDownloadFileInQueue(path){return transfermanager.isDownloadFileInQueue(path)}function getDownloadItemCount(){return transfermanager.getDownloadItemCount()}function getDirectoryPath(item){var parts=[],itemtype=item.Type.toLowerCase(),mediaType=(item.MediaType||"").toLowerCase();"episode"===itemtype||"series"===itemtype||"season"===itemtype?parts.push("TV"):"video"===mediaType?parts.push("Videos"):"audio"===itemtype||"musicalbum"===itemtype||"musicartist"===itemtype?parts.push("Music"):"photo"===itemtype||"photoalbum"===itemtype?parts.push("Photos"):"game"!==itemtype&&"gamesystem"!==itemtype||parts.push("Games");var albumArtist=item.AlbumArtist;albumArtist&&parts.push(albumArtist);var seriesName=item.SeriesName;seriesName&&parts.push(seriesName);var seasonName=item.SeasonName;seasonName&&parts.push(seasonName),item.Album&&parts.push(item.Album),("video"===mediaType&&"episode"!==itemtype||"game"===itemtype||item.IsFolder)&&parts.push(item.Name);for(var finalParts=[],i=0;ifind.length&&0===str.indexOf(find))}function stripStart(str,find){return startsWith(str,find)?str.substr(find.length):str}function filterDistinct(value,index,self){return self.indexOf(value)===index}function enableBackgroundCompletion(){return transfermanager.enableBackgroundCompletion}return{getLocalItem:getLocalItem,getDirectoryPath:getDirectoryPath,getLocalFileName:getLocalFileName,recordUserAction:recordUserAction,getUserActions:getUserActions,deleteUserAction:deleteUserAction,deleteUserActions:deleteUserActions,removeLocalItem:removeLocalItem,addOrUpdateLocalItem:addOrUpdateLocalItem,downloadFile:downloadFile,downloadSubtitles:downloadSubtitles,hasImage:hasImage,downloadImage:downloadImage,getImageUrl:getImageUrl,getSubtitleSaveFileName:getSubtitleSaveFileName,getServerItems:getServerItems,getItemFileSize:getItemFileSize,isDownloadFileInQueue:isDownloadFileInQueue,getDownloadItemCount:getDownloadItemCount,getViews:getViews,getViewItems:getViewItems,resyncTransfers:resyncTransfers,getItemsFromIds:getItemsFromIds,removeObsoleteContainerItems:removeObsoleteContainerItems,fileExists:fileExists,enableBackgroundCompletion:enableBackgroundCompletion}}); \ No newline at end of file +define(["filerepository", "itemrepository", "useractionrepository", "transfermanager"], function(filerepository, itemrepository, useractionrepository, transfermanager) { + "use strict"; + + function getLocalItem(serverId, itemId) { + return console.log("[lcoalassetmanager] Begin getLocalItem"), itemrepository.get(serverId, itemId) + } + + function recordUserAction(action) { + return action.Id = createGuid(), useractionrepository.set(action.Id, action) + } + + function getUserActions(serverId) { + return useractionrepository.getByServerId(serverId) + } + + function deleteUserAction(action) { + return useractionrepository.remove(action.Id) + } + + function deleteUserActions(actions) { + var results = []; + return actions.forEach(function(action) { + results.push(deleteUserAction(action)) + }), Promise.all(results) + } + + function getServerItems(serverId) { + return console.log("[localassetmanager] Begin getServerItems"), itemrepository.getAll(serverId) + } + + function getItemsFromIds(serverId, ids) { + var actions = ids.map(function(id) { + var strippedId = stripStart(id, "local:"); + return getLocalItem(serverId, strippedId) + }); + return Promise.all(actions).then(function(items) { + var libItems = items.map(function(locItem) { + return locItem.Item + }); + return Promise.resolve(libItems) + }) + } + + function getViews(serverId, userId) { + return itemrepository.getServerItemTypes(serverId, userId).then(function(types) { + var item, list = []; + return types.indexOf("Audio") > -1 && (item = { + Name: "Music", + ServerId: serverId, + Id: "localview:MusicView", + Type: "MusicView", + CollectionType: "music", + IsFolder: !0 + }, list.push(item)), types.indexOf("Photo") > -1 && (item = { + Name: "Photos", + ServerId: serverId, + Id: "localview:PhotosView", + Type: "PhotosView", + CollectionType: "photos", + IsFolder: !0 + }, list.push(item)), types.indexOf("Episode") > -1 && (item = { + Name: "TV", + ServerId: serverId, + Id: "localview:TVView", + Type: "TVView", + CollectionType: "tvshows", + IsFolder: !0 + }, list.push(item)), types.indexOf("Movie") > -1 && (item = { + Name: "Movies", + ServerId: serverId, + Id: "localview:MoviesView", + Type: "MoviesView", + CollectionType: "movies", + IsFolder: !0 + }, list.push(item)), types.indexOf("Video") > -1 && (item = { + Name: "Videos", + ServerId: serverId, + Id: "localview:VideosView", + Type: "VideosView", + CollectionType: "videos", + IsFolder: !0 + }, list.push(item)), types.indexOf("MusicVideo") > -1 && (item = { + Name: "Music Videos", + ServerId: serverId, + Id: "localview:MusicVideosView", + Type: "MusicVideosView", + CollectionType: "videos", + IsFolder: !0 + }, list.push(item)), Promise.resolve(list) + }) + } + + function updateFiltersForTopLevelView(parentId, mediaTypes, includeItemTypes, query) { + switch (parentId) { + case "MusicView": + return query.Recursive ? includeItemTypes.push("Audio") : includeItemTypes.push("MusicAlbum"), !0; + case "PhotosView": + return query.Recursive ? includeItemTypes.push("Photo") : includeItemTypes.push("PhotoAlbum"), !0; + case "TVView": + return query.Recursive ? includeItemTypes.push("Episode") : includeItemTypes.push("Series"), !0; + case "VideosView": + return query.Recursive, includeItemTypes.push("Video"), !0; + case "MoviesView": + return query.Recursive, includeItemTypes.push("Movie"), !0; + case "MusicVideosView": + return query.Recursive, includeItemTypes.push("MusicVideo"), !0 + } + return !1 + } + + function normalizeId(id) { + return id ? (id = stripStart(id, "localview:"), id = stripStart(id, "local:")) : null + } + + function normalizeIdList(val) { + return val ? val.split(",").map(normalizeId) : [] + } + + function shuffle(array) { + for (var temporaryValue, randomIndex, currentIndex = array.length; 0 !== currentIndex;) randomIndex = Math.floor(Math.random() * currentIndex), currentIndex -= 1, temporaryValue = array[currentIndex], array[currentIndex] = array[randomIndex], array[randomIndex] = temporaryValue; + return array + } + + function sortItems(items, query) { + if (!query.SortBy || 0 === query.SortBy.length) return items; + if ("Random" === query.SortBy) return shuffle(items); + var sortSpec = getSortSpec(query); + return items.sort(function(a, b) { + for (var i = 0; i < sortSpec.length; i++) { + var result = compareValues(a, b, sortSpec[i].Field, sortSpec[i].OrderDescending); + if (0 !== result) return result + } + return 0 + }), items + } + + function compareValues(a, b, field, orderDesc) { + if (!a.hasOwnProperty(field) || !b.hasOwnProperty(field)) return 0; + var valA = a[field], + valB = b[field], + result = 0; + return "string" == typeof valA || "string" == typeof valB ? (valA = valA || "", valB = valB || "", result = valA.toLowerCase().localeCompare(valB.toLowerCase())) : valA > valB ? result = 1 : valA < valB && (result = -1), orderDesc && (result *= -1), result + } + + function getSortSpec(query) { + for (var sortFields = (query.SortBy || "").split(","), sortOrders = (query.SortOrder || "").split(","), sortSpec = [], i = 0; i < sortFields.length; i++) { + var orderDesc = !1; + i < sortOrders.length && -1 !== sortOrders[i].toLowerCase().indexOf("desc") && (orderDesc = !0), sortSpec.push({ + Field: sortFields[i], + OrderDescending: orderDesc + }) + } + return sortSpec + } + + function getViewItems(serverId, userId, options) { + var searchParentId = options.ParentId; + searchParentId = normalizeId(searchParentId); + var seasonId = normalizeId(options.SeasonId || options.seasonId), + seriesId = normalizeId(options.SeriesId || options.seriesId), + albumIds = normalizeIdList(options.AlbumIds || options.albumIds), + includeItemTypes = options.IncludeItemTypes ? options.IncludeItemTypes.split(",") : [], + filters = options.Filters ? options.Filters.split(",") : [], + mediaTypes = options.MediaTypes ? options.MediaTypes.split(",") : []; + return updateFiltersForTopLevelView(searchParentId, mediaTypes, includeItemTypes, options) && (searchParentId = null), getServerItems(serverId).then(function(items) { + var itemsMap = new Map, + subtreeIdSet = new Set; + if (items.forEach(function(item) { + item.Item.LocalChildren = [], itemsMap.set(item.Item.Id, item.Item) + }), itemsMap.forEach(function(item, ignored, ignored2) { + if (item.ParentId && itemsMap.has(item.ParentId)) { + itemsMap.get(item.ParentId).LocalChildren.push(item) + } + }), options.Recursive && searchParentId && itemsMap.has(searchParentId)) { + var addSubtreeIds = function(recurseItem) { + subtreeIdSet.has(recurseItem.Id) || subtreeIdSet.add(recurseItem.Id), recurseItem.LocalChildren.forEach(function(childItem) { + addSubtreeIds(childItem) + }) + }, + searchParentItem = itemsMap.get(searchParentId); + addSubtreeIds(searchParentItem) + } + var resultItems = items.filter(function(item) { + return (!item.SyncStatus || "synced" === item.SyncStatus) && ((!mediaTypes.length || -1 !== mediaTypes.indexOf(item.Item.MediaType || "")) && ((!seriesId || item.Item.SeriesId === seriesId) && ((!seasonId || item.Item.SeasonId === seasonId) && ((!albumIds.length || -1 !== albumIds.indexOf(item.Item.AlbumId || "")) && ((!item.Item.IsFolder || -1 === filters.indexOf("IsNotFolder")) && (!(!item.Item.IsFolder && -1 !== filters.indexOf("IsFolder")) && ((!includeItemTypes.length || -1 !== includeItemTypes.indexOf(item.Item.Type || "")) && (!searchParentId || (options.Recursive ? subtreeIdSet.has(item.Item.Id) : item.Item.ParentId === searchParentId))))))))) + }).map(function(item2) { + return item2.Item + }); + return resultItems = sortItems(resultItems, options), options.Limit && (resultItems = resultItems.slice(0, options.Limit)), Promise.resolve(resultItems) + }) + } + + function removeObsoleteContainerItems(serverId) { + return getServerItems(serverId).then(function(items) { + var seriesItems = items.filter(function(item) { + return "series" === (item.Item.Type || "").toLowerCase() + }), + seasonItems = items.filter(function(item) { + return "season" === (item.Item.Type || "").toLowerCase() + }), + albumItems = items.filter(function(item) { + var type = (item.Item.Type || "").toLowerCase(); + return "musicalbum" === type || "photoalbum" === type + }), + requiredSeriesIds = items.filter(function(item) { + return "episode" === (item.Item.Type || "").toLowerCase() + }).map(function(item2) { + return item2.Item.SeriesId + }).filter(filterDistinct), + requiredSeasonIds = items.filter(function(item) { + return "episode" === (item.Item.Type || "").toLowerCase() + }).map(function(item2) { + return item2.Item.SeasonId + }).filter(filterDistinct), + requiredAlbumIds = items.filter(function(item) { + var type = (item.Item.Type || "").toLowerCase(); + return "audio" === type || "photo" === type + }).map(function(item2) { + return item2.Item.AlbumId + }).filter(filterDistinct), + obsoleteItems = []; + seriesItems.forEach(function(item) { + requiredSeriesIds.indexOf(item.Item.Id) < 0 && obsoleteItems.push(item) + }), seasonItems.forEach(function(item) { + requiredSeasonIds.indexOf(item.Item.Id) < 0 && obsoleteItems.push(item) + }), albumItems.forEach(function(item) { + requiredAlbumIds.indexOf(item.Item.Id) < 0 && obsoleteItems.push(item) + }); + var p = Promise.resolve(); + return obsoleteItems.forEach(function(item) { + p = p.then(function() { + return itemrepository.remove(item.ServerId, item.Id) + }) + }), p + }) + } + + function removeLocalItem(localItem) { + return itemrepository.get(localItem.ServerId, localItem.Id).then(function(item) { + var onFileDeletedSuccessOrFail = function() { + return itemrepository.remove(localItem.ServerId, localItem.Id) + }, + p = Promise.resolve(); + return item.LocalPath && (p = p.then(function() { + return filerepository.deleteFile(item.LocalPath) + })), item && item.Item && item.Item.MediaSources && item.Item.MediaSources.forEach(function(mediaSource) { + mediaSource.MediaStreams && mediaSource.MediaStreams.length > 0 && mediaSource.MediaStreams.forEach(function(mediaStream) { + mediaStream.Path && (p = p.then(function() { + return filerepository.deleteFile(mediaStream.Path) + })) + }) + }), p.then(onFileDeletedSuccessOrFail, onFileDeletedSuccessOrFail) + }, function(item) { + return Promise.resolve() + }) + } + + function addOrUpdateLocalItem(localItem) { + return itemrepository.set(localItem.ServerId, localItem.Id, localItem) + } + + function getSubtitleSaveFileName(localItem, mediaPath, language, isForced, format) { + var name = getNameWithoutExtension(mediaPath); + name = filerepository.getValidFileName(name), language && (name += "." + language.toLowerCase()), isForced && (name += ".foreign"), name = name + "." + format.toLowerCase(); + var mediaFolder = filerepository.getParentPath(localItem.LocalPath); + return filerepository.combinePath(mediaFolder, name) + } + + function getItemFileSize(path) { + return filerepository.getItemFileSize(path) + } + + function getNameWithoutExtension(path) { + var fileName = path, + pos = fileName.lastIndexOf("."); + return pos > 0 && (fileName = fileName.substring(0, pos)), fileName + } + + function downloadFile(url, localItem) { + var imageUrl = getImageUrl(localItem.Item.ServerId, localItem.Item.Id, { + type: "Primary", + index: 0 + }); + return transfermanager.downloadFile(url, localItem, imageUrl) + } + + function downloadSubtitles(url, fileName) { + return transfermanager.downloadSubtitles(url, fileName) + } + + function getImageUrl(serverId, itemId, imageOptions) { + var imageType = imageOptions.type, + index = imageOptions.index, + pathArray = getImagePath(serverId, itemId, imageType, index); + return filerepository.getImageUrl(pathArray) + } + + function hasImage(serverId, itemId, imageType, index) { + var pathArray = getImagePath(serverId, itemId, imageType, index), + localFilePath = filerepository.getFullMetadataPath(pathArray); + return filerepository.fileExists(localFilePath).then(function(exists) { + return Promise.resolve(exists) + }, function(err) { + return Promise.resolve(!1) + }) + } + + function fileExists(localFilePath) { + return filerepository.fileExists(localFilePath) + } + + function downloadImage(localItem, url, serverId, itemId, imageType, index) { + var localPathParts = getImagePath(serverId, itemId, imageType, index); + return transfermanager.downloadImage(url, localPathParts) + } + + function isDownloadFileInQueue(path) { + return transfermanager.isDownloadFileInQueue(path) + } + + function getDownloadItemCount() { + return transfermanager.getDownloadItemCount() + } + + function getDirectoryPath(item) { + var parts = [], + itemtype = item.Type.toLowerCase(), + mediaType = (item.MediaType || "").toLowerCase(); + "episode" === itemtype || "series" === itemtype || "season" === itemtype ? parts.push("TV") : "video" === mediaType ? parts.push("Videos") : "audio" === itemtype || "musicalbum" === itemtype || "musicartist" === itemtype ? parts.push("Music") : "photo" === itemtype || "photoalbum" === itemtype ? parts.push("Photos") : "game" !== itemtype && "gamesystem" !== itemtype || parts.push("Games"); + var albumArtist = item.AlbumArtist; + albumArtist && parts.push(albumArtist); + var seriesName = item.SeriesName; + seriesName && parts.push(seriesName); + var seasonName = item.SeasonName; + seasonName && parts.push(seasonName), item.Album && parts.push(item.Album), ("video" === mediaType && "episode" !== itemtype || "game" === itemtype || item.IsFolder) && parts.push(item.Name); + for (var finalParts = [], i = 0; i < parts.length; i++) finalParts.push(filerepository.getValidFileName(parts[i])); + return finalParts + } + + function getImagePath(serverId, itemId, imageType, index) { + var parts = []; + parts.push("images"), index = index || 0, parts.push(itemId + "_" + imageType + "_" + index.toString()); + for (var finalParts = [], i = 0; i < parts.length; i++) finalParts.push(parts[i]); + return finalParts + } + + function getLocalFileName(item, originalFileName) { + var filename = originalFileName || item.Name; + return filerepository.getValidFileName(filename) + } + + function resyncTransfers() { + return transfermanager.resyncTransfers() + } + + function createGuid() { + var d = (new Date).getTime(); + return window.performance && "function" == typeof window.performance.now && (d += performance.now()), "xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx".replace(/[xy]/g, function(c) { + var r = (d + 16 * Math.random()) % 16 | 0; + return d = Math.floor(d / 16), ("x" === c ? r : 3 & r | 8).toString(16) + }) + } + + function startsWith(str, find) { + return !!(str && find && str.length > find.length && 0 === str.indexOf(find)) + } + + function stripStart(str, find) { + return startsWith(str, find) ? str.substr(find.length) : str + } + + function filterDistinct(value, index, self) { + return self.indexOf(value) === index + } + + function enableBackgroundCompletion() { + return transfermanager.enableBackgroundCompletion + } + return { + getLocalItem: getLocalItem, + getDirectoryPath: getDirectoryPath, + getLocalFileName: getLocalFileName, + recordUserAction: recordUserAction, + getUserActions: getUserActions, + deleteUserAction: deleteUserAction, + deleteUserActions: deleteUserActions, + removeLocalItem: removeLocalItem, + addOrUpdateLocalItem: addOrUpdateLocalItem, + downloadFile: downloadFile, + downloadSubtitles: downloadSubtitles, + hasImage: hasImage, + downloadImage: downloadImage, + getImageUrl: getImageUrl, + getSubtitleSaveFileName: getSubtitleSaveFileName, + getServerItems: getServerItems, + getItemFileSize: getItemFileSize, + isDownloadFileInQueue: isDownloadFileInQueue, + getDownloadItemCount: getDownloadItemCount, + getViews: getViews, + getViewItems: getViewItems, + resyncTransfers: resyncTransfers, + getItemsFromIds: getItemsFromIds, + removeObsoleteContainerItems: removeObsoleteContainerItems, + fileExists: fileExists, + enableBackgroundCompletion: enableBackgroundCompletion + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-apiclient/serverdiscovery.js b/dashboard-ui/bower_components/emby-apiclient/serverdiscovery.js index 7cecdbcd49..4f18505ecc 100644 --- a/dashboard-ui/bower_components/emby-apiclient/serverdiscovery.js +++ b/dashboard-ui/bower_components/emby-apiclient/serverdiscovery.js @@ -1 +1,8 @@ -define([],function(){"use strict";return{findServers:function(timeoutMs){return Promise.resolve([])}}}); \ No newline at end of file +define([], function() { + "use strict"; + return { + findServers: function(timeoutMs) { + return Promise.resolve([]) + } + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-apiclient/sync/contentuploader.js b/dashboard-ui/bower_components/emby-apiclient/sync/contentuploader.js index eaf70fb777..e08dbe4dd2 100644 --- a/dashboard-ui/bower_components/emby-apiclient/sync/contentuploader.js +++ b/dashboard-ui/bower_components/emby-apiclient/sync/contentuploader.js @@ -1 +1,57 @@ -define(["localassetmanager","cameraRoll"],function(localAssetManager,cameraRoll){"use strict";function getFilesToUpload(files,uploadHistory){return files.filter(function(file){if(!file)return!1;var uploadId=getUploadId(file);return 0===uploadHistory.FilesUploaded.filter(function(u){return uploadId===u.Id}).length})}function getUploadId(file){return btoa(file.Id+"1")}function uploadNext(files,index,server,apiClient,resolve,reject){var length=files.length;if(index>=length)return void resolve();uploadFile(files[index],apiClient).then(function(){uploadNext(files,index+1,server,apiClient,resolve,reject)},function(){uploadNext(files,index+1,server,apiClient,resolve,reject)})}function uploadFile(file,apiClient){return new Promise(function(resolve,reject){require(["fileupload"],function(FileUpload){var url=apiClient.getUrl("Devices/CameraUploads",{DeviceId:apiClient.deviceId(),Name:file.Name,Album:"Camera Roll",Id:getUploadId(file),api_key:apiClient.accessToken()});console.log("Uploading file to "+url),(new FileUpload).upload(file,url).then(resolve,reject)})})}function ContentUploader(){}return ContentUploader.prototype.uploadImages=function(connectionManager,server){return cameraRoll.getFiles().then(function(photos){if(!photos.length)return Promise.resolve();var apiClient=connectionManager.getApiClient(server.Id);return apiClient.getContentUploadHistory().then(function(uploadHistory){return photos=getFilesToUpload(photos,uploadHistory),console.log("Found "+photos.length+" files to upload"),new Promise(function(resolve,reject){uploadNext(photos,0,server,apiClient,resolve,reject)})},function(){return Promise.resolve()})})},ContentUploader}); \ No newline at end of file +define(["localassetmanager", "cameraRoll"], function(localAssetManager, cameraRoll) { + "use strict"; + + function getFilesToUpload(files, uploadHistory) { + return files.filter(function(file) { + if (!file) return !1; + var uploadId = getUploadId(file); + return 0 === uploadHistory.FilesUploaded.filter(function(u) { + return uploadId === u.Id + }).length + }) + } + + function getUploadId(file) { + return btoa(file.Id + "1") + } + + function uploadNext(files, index, server, apiClient, resolve, reject) { + var length = files.length; + if (index >= length) return void resolve(); + uploadFile(files[index], apiClient).then(function() { + uploadNext(files, index + 1, server, apiClient, resolve, reject) + }, function() { + uploadNext(files, index + 1, server, apiClient, resolve, reject) + }) + } + + function uploadFile(file, apiClient) { + return new Promise(function(resolve, reject) { + require(["fileupload"], function(FileUpload) { + var url = apiClient.getUrl("Devices/CameraUploads", { + DeviceId: apiClient.deviceId(), + Name: file.Name, + Album: "Camera Roll", + Id: getUploadId(file), + api_key: apiClient.accessToken() + }); + console.log("Uploading file to " + url), (new FileUpload).upload(file, url).then(resolve, reject) + }) + }) + } + + function ContentUploader() {} + return ContentUploader.prototype.uploadImages = function(connectionManager, server) { + return cameraRoll.getFiles().then(function(photos) { + if (!photos.length) return Promise.resolve(); + var apiClient = connectionManager.getApiClient(server.Id); + return apiClient.getContentUploadHistory().then(function(uploadHistory) { + return photos = getFilesToUpload(photos, uploadHistory), console.log("Found " + photos.length + " files to upload"), new Promise(function(resolve, reject) { + uploadNext(photos, 0, server, apiClient, resolve, reject) + }) + }, function() { + return Promise.resolve() + }) + }) + }, ContentUploader +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-apiclient/sync/filerepository.js b/dashboard-ui/bower_components/emby-apiclient/sync/filerepository.js index 38ea0b6a71..198967469d 100644 --- a/dashboard-ui/bower_components/emby-apiclient/sync/filerepository.js +++ b/dashboard-ui/bower_components/emby-apiclient/sync/filerepository.js @@ -1 +1,45 @@ -define([],function(){"use strict";function getValidFileName(path){return path}function getFullLocalPath(pathArray){return pathArray.join("/")}function getPathFromArray(pathArray){return pathArray.join("/")}function deleteFile(path){return Promise.resolve()}function deleteDirectory(path){return Promise.resolve()}function fileExists(path){return Promise.resolve()}function getItemFileSize(path){return Promise.resolve(0)}function getImageUrl(pathParts){return pathParts.join("/")}return{getValidFileName:getValidFileName,getFullLocalPath:getFullLocalPath,getPathFromArray:getPathFromArray,deleteFile:deleteFile,deleteDirectory:deleteDirectory,fileExists:fileExists,getItemFileSize:getItemFileSize,getImageUrl:getImageUrl}}); \ No newline at end of file +define([], function() { + "use strict"; + + function getValidFileName(path) { + return path + } + + function getFullLocalPath(pathArray) { + return pathArray.join("/") + } + + function getPathFromArray(pathArray) { + return pathArray.join("/") + } + + function deleteFile(path) { + return Promise.resolve() + } + + function deleteDirectory(path) { + return Promise.resolve() + } + + function fileExists(path) { + return Promise.resolve() + } + + function getItemFileSize(path) { + return Promise.resolve(0) + } + + function getImageUrl(pathParts) { + return pathParts.join("/") + } + return { + getValidFileName: getValidFileName, + getFullLocalPath: getFullLocalPath, + getPathFromArray: getPathFromArray, + deleteFile: deleteFile, + deleteDirectory: deleteDirectory, + fileExists: fileExists, + getItemFileSize: getItemFileSize, + getImageUrl: getImageUrl + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-apiclient/sync/itemrepository.js b/dashboard-ui/bower_components/emby-apiclient/sync/itemrepository.js index 1685367fe0..5330d5d1a2 100644 --- a/dashboard-ui/bower_components/emby-apiclient/sync/itemrepository.js +++ b/dashboard-ui/bower_components/emby-apiclient/sync/itemrepository.js @@ -1 +1,123 @@ -define([],function(){"use strict";function ServerDatabase(dbName,readyCallback){var request=indexedDB.open(dbName,dbVersion);request.onerror=function(event){},request.onupgradeneeded=function(event){var db=event.target.result;db.createObjectStore(dbName).transaction.oncomplete=function(event){readyCallback(db)}},request.onsuccess=function(event){var db=event.target.result;readyCallback(db)}}function getDbName(serverId){return"items_"+serverId}function getDb(serverId,callback){var dbName=getDbName(serverId),db=databases[dbName];if(db)return void callback(db);new ServerDatabase(dbName,function(db){databases[dbName]=db,callback(db)})}function getServerItemTypes(serverId,userId){return getAll(serverId,userId).then(function(all){return all.map(function(item2){return item2.Item.Type||""}).filter(filterDistinct)})}function getAll(serverId,userId){return new Promise(function(resolve,reject){getDb(serverId,function(db){var request,storeName=getDbName(serverId),transaction=db.transaction([storeName],"readonly"),objectStore=transaction.objectStore(storeName);if("getAll"in objectStore)request=objectStore.getAll(null,1e4),request.onsuccess=function(event){resolve(event.target.result)};else{var results=[];request=objectStore.openCursor(),request.onsuccess=function(event){var cursor=event.target.result;cursor?(results.push(cursor.value),cursor.continue()):resolve(results)}}request.onerror=reject})})}function get(serverId,key){return new Promise(function(resolve,reject){getDb(serverId,function(db){var storeName=getDbName(serverId),transaction=db.transaction([storeName],"readonly"),objectStore=transaction.objectStore(storeName),request=objectStore.get(key);request.onerror=reject,request.onsuccess=function(event){resolve(request.result)}})})}function set(serverId,key,val){return new Promise(function(resolve,reject){getDb(serverId,function(db){var storeName=getDbName(serverId),transaction=db.transaction([storeName],"readwrite"),objectStore=transaction.objectStore(storeName),request=objectStore.put(val,key);request.onerror=reject,request.onsuccess=resolve})})}function remove(serverId,key){return new Promise(function(resolve,reject){getDb(serverId,function(db){var storeName=getDbName(serverId),transaction=db.transaction([storeName],"readwrite"),objectStore=transaction.objectStore(storeName),request=objectStore.delete(key);request.onerror=reject,request.onsuccess=resolve})})}function clear(serverId){return new Promise(function(resolve,reject){getDb(serverId,function(db){var storeName=getDbName(serverId),transaction=db.transaction([storeName],"readwrite"),objectStore=transaction.objectStore(storeName),request=objectStore.clear();request.onerror=reject,request.onsuccess=resolve})})}function filterDistinct(value,index,self){return self.indexOf(value)===index}var indexedDB=self.indexedDB||self.mozIndexedDB||self.webkitIndexedDB||self.msIndexedDB,dbVersion=(self.IDBTransaction||self.webkitIDBTransaction||self.msIDBTransaction,self.IDBKeyRange||self.webkitIDBKeyRange||self.msIDBKeyRange,1),databases={};return{get:get,set:set,remove:remove,clear:clear,getAll:getAll,getServerItemTypes:getServerItemTypes}}); \ No newline at end of file +define([], function() { + "use strict"; + + function ServerDatabase(dbName, readyCallback) { + var request = indexedDB.open(dbName, dbVersion); + request.onerror = function(event) {}, request.onupgradeneeded = function(event) { + var db = event.target.result; + db.createObjectStore(dbName).transaction.oncomplete = function(event) { + readyCallback(db) + } + }, request.onsuccess = function(event) { + var db = event.target.result; + readyCallback(db) + } + } + + function getDbName(serverId) { + return "items_" + serverId + } + + function getDb(serverId, callback) { + var dbName = getDbName(serverId), + db = databases[dbName]; + if (db) return void callback(db); + new ServerDatabase(dbName, function(db) { + databases[dbName] = db, callback(db) + }) + } + + function getServerItemTypes(serverId, userId) { + return getAll(serverId, userId).then(function(all) { + return all.map(function(item2) { + return item2.Item.Type || "" + }).filter(filterDistinct) + }) + } + + function getAll(serverId, userId) { + return new Promise(function(resolve, reject) { + getDb(serverId, function(db) { + var request, storeName = getDbName(serverId), + transaction = db.transaction([storeName], "readonly"), + objectStore = transaction.objectStore(storeName); + if ("getAll" in objectStore) request = objectStore.getAll(null, 1e4), request.onsuccess = function(event) { + resolve(event.target.result) + }; + else { + var results = []; + request = objectStore.openCursor(), request.onsuccess = function(event) { + var cursor = event.target.result; + cursor ? (results.push(cursor.value), cursor.continue()) : resolve(results) + } + } + request.onerror = reject + }) + }) + } + + function get(serverId, key) { + return new Promise(function(resolve, reject) { + getDb(serverId, function(db) { + var storeName = getDbName(serverId), + transaction = db.transaction([storeName], "readonly"), + objectStore = transaction.objectStore(storeName), + request = objectStore.get(key); + request.onerror = reject, request.onsuccess = function(event) { + resolve(request.result) + } + }) + }) + } + + function set(serverId, key, val) { + return new Promise(function(resolve, reject) { + getDb(serverId, function(db) { + var storeName = getDbName(serverId), + transaction = db.transaction([storeName], "readwrite"), + objectStore = transaction.objectStore(storeName), + request = objectStore.put(val, key); + request.onerror = reject, request.onsuccess = resolve + }) + }) + } + + function remove(serverId, key) { + return new Promise(function(resolve, reject) { + getDb(serverId, function(db) { + var storeName = getDbName(serverId), + transaction = db.transaction([storeName], "readwrite"), + objectStore = transaction.objectStore(storeName), + request = objectStore.delete(key); + request.onerror = reject, request.onsuccess = resolve + }) + }) + } + + function clear(serverId) { + return new Promise(function(resolve, reject) { + getDb(serverId, function(db) { + var storeName = getDbName(serverId), + transaction = db.transaction([storeName], "readwrite"), + objectStore = transaction.objectStore(storeName), + request = objectStore.clear(); + request.onerror = reject, request.onsuccess = resolve + }) + }) + } + + function filterDistinct(value, index, self) { + return self.indexOf(value) === index + } + var indexedDB = self.indexedDB || self.mozIndexedDB || self.webkitIndexedDB || self.msIndexedDB, + dbVersion = (self.IDBTransaction || self.webkitIDBTransaction || self.msIDBTransaction, self.IDBKeyRange || self.webkitIDBKeyRange || self.msIDBKeyRange, 1), + databases = {}; + return { + get: get, + set: set, + remove: remove, + clear: clear, + getAll: getAll, + getServerItemTypes: getServerItemTypes + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-apiclient/sync/localsync.js b/dashboard-ui/bower_components/emby-apiclient/sync/localsync.js index 2f855bfc39..cea244de08 100644 --- a/dashboard-ui/bower_components/emby-apiclient/sync/localsync.js +++ b/dashboard-ui/bower_components/emby-apiclient/sync/localsync.js @@ -1 +1,17 @@ -define(["connectionManager"],function(connectionManager){"use strict";var isSyncing;return{sync:function(options){return console.log("localSync.sync starting..."),isSyncing?Promise.resolve():(isSyncing=!0,new Promise(function(resolve,reject){require(["multiserversync","appSettings"],function(MultiServerSync,appSettings){options=options||{},options.cameraUploadServers=appSettings.cameraUploadServers(),(new MultiServerSync).sync(connectionManager,options).then(function(){isSyncing=null,resolve()},function(err){isSyncing=null,reject(err)})})}))}}}); \ No newline at end of file +define(["connectionManager"], function(connectionManager) { + "use strict"; + var isSyncing; + return { + sync: function(options) { + return console.log("localSync.sync starting..."), isSyncing ? Promise.resolve() : (isSyncing = !0, new Promise(function(resolve, reject) { + require(["multiserversync", "appSettings"], function(MultiServerSync, appSettings) { + options = options || {}, options.cameraUploadServers = appSettings.cameraUploadServers(), (new MultiServerSync).sync(connectionManager, options).then(function() { + isSyncing = null, resolve() + }, function(err) { + isSyncing = null, reject(err) + }) + }) + })) + } + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-apiclient/sync/mediasync.js b/dashboard-ui/bower_components/emby-apiclient/sync/mediasync.js index cc09ffe5f0..24220561ad 100644 --- a/dashboard-ui/bower_components/emby-apiclient/sync/mediasync.js +++ b/dashboard-ui/bower_components/emby-apiclient/sync/mediasync.js @@ -1 +1,368 @@ -define(["localassetmanager"],function(localassetmanager){"use strict";function processDownloadStatus(apiClient,serverInfo,options){return console.log("[mediasync] Begin processDownloadStatus"),localassetmanager.resyncTransfers().then(function(){return localassetmanager.getServerItems(serverInfo.Id).then(function(items){console.log("[mediasync] Begin processDownloadStatus getServerItems completed");var p=Promise.resolve(),cnt=0;return items.filter(function(item){return"transferring"===item.SyncStatus||"queued"===item.SyncStatus}).forEach(function(item){p=p.then(function(){return reportTransfer(apiClient,item)}),cnt++}),p.then(function(){return console.log("[mediasync] Exit processDownloadStatus. Items reported: "+cnt.toString()),Promise.resolve()})})})}function reportTransfer(apiClient,item){return localassetmanager.getItemFileSize(item.LocalPath).then(function(size){return size>0?apiClient.reportSyncJobItemTransferred(item.SyncJobItemId).then(function(){return item.SyncStatus="synced",console.log("[mediasync] reportSyncJobItemTransferred called for "+item.LocalPath),localassetmanager.addOrUpdateLocalItem(item)},function(error){return console.error("[mediasync] Mediasync error on reportSyncJobItemTransferred",error),item.SyncStatus="error",localassetmanager.addOrUpdateLocalItem(item)}):localassetmanager.isDownloadFileInQueue(item.LocalPath).then(function(result){return result?Promise.resolve():(console.log("[mediasync] reportTransfer: Size is 0 and download no longer in queue. Deleting item."),localassetmanager.removeLocalItem(item).then(function(){return console.log("[mediasync] reportTransfer: Item deleted."),Promise.resolve()},function(err2){return console.log("[mediasync] reportTransfer: Failed to delete item.",err2),Promise.resolve()}))})},function(error){return console.error("[mediasync] reportTransfer: error on getItemFileSize. Deleting item.",error),localassetmanager.removeLocalItem(item).then(function(){return console.log("[mediasync] reportTransfer: Item deleted."),Promise.resolve()},function(err2){return console.log("[mediasync] reportTransfer: Failed to delete item.",err2),Promise.resolve()})})}function reportOfflineActions(apiClient,serverInfo){return console.log("[mediasync] Begin reportOfflineActions"),localassetmanager.getUserActions(serverInfo.Id).then(function(actions){return actions.length?apiClient.reportOfflineActions(actions).then(function(){return localassetmanager.deleteUserActions(actions).then(function(){return console.log("[mediasync] Exit reportOfflineActions (actions reported and deleted.)"),Promise.resolve()})},function(err){return console.error("[mediasync] error on apiClient.reportOfflineActions: "+err.toString()),localassetmanager.deleteUserActions(actions)}):(console.log("[mediasync] Exit reportOfflineActions (no actions)"),Promise.resolve())})}function syncData(apiClient,serverInfo){return console.log("[mediasync] Begin syncData"),localassetmanager.getServerItems(serverInfo.Id).then(function(items){var completedItems=items.filter(function(item){return item&&("synced"===item.SyncStatus||"error"===item.SyncStatus)}),request={TargetId:apiClient.deviceId(),LocalItemIds:completedItems.map(function(xitem){return xitem.ItemId})};return apiClient.syncData(request).then(function(result){return afterSyncData(apiClient,serverInfo,result).then(function(){return console.log("[mediasync] Exit syncData"),Promise.resolve()},function(err){return console.error("[mediasync] Error in syncData: "+err.toString()),Promise.resolve()})})})}function afterSyncData(apiClient,serverInfo,syncDataResult){console.log("[mediasync] Begin afterSyncData");var p=Promise.resolve();return syncDataResult.ItemIdsToRemove&&syncDataResult.ItemIdsToRemove.length>0&&syncDataResult.ItemIdsToRemove.forEach(function(itemId){p=p.then(function(){return removeLocalItem(itemId,serverInfo.Id)})}),p=p.then(function(){return removeObsoleteContainerItems(serverInfo.Id)}),p.then(function(){return console.log("[mediasync] Exit afterSyncData"),Promise.resolve()})}function removeObsoleteContainerItems(serverId){return console.log("[mediasync] Begin removeObsoleteContainerItems"),localassetmanager.removeObsoleteContainerItems(serverId)}function removeLocalItem(itemId,serverId){return console.log("[mediasync] Begin removeLocalItem"),localassetmanager.getLocalItem(serverId,itemId).then(function(item){return item?localassetmanager.removeLocalItem(item):Promise.resolve()},function(err2){return console.error("[mediasync] removeLocalItem: Failed: ",err2),Promise.resolve()})}function getNewMedia(apiClient,downloadCount){return console.log("[mediasync] Begin getNewMedia"),apiClient.getReadySyncItems(apiClient.deviceId()).then(function(jobItems){console.log("[mediasync] getReadySyncItems returned "+jobItems.length+" items");var p=Promise.resolve(),currentCount=downloadCount;return jobItems.forEach(function(jobItem){currentCount++<=10&&(p=p.then(function(){return getNewItem(jobItem,apiClient)}))}),p.then(function(){return console.log("[mediasync] Exit getNewMedia"),Promise.resolve()})},function(err){return console.error("[mediasync] getReadySyncItems: Failed: ",err),Promise.resolve()})}function afterMediaDownloaded(apiClient,jobItem,localItem){return console.log("[mediasync] Begin afterMediaDownloaded"),getImages(apiClient,jobItem,localItem).then(function(){var libraryItem=jobItem.Item;return downloadParentItems(apiClient,jobItem,libraryItem).then(function(){return getSubtitles(apiClient,jobItem,localItem)})})}function createLocalItem(libraryItem,jobItem){console.log("[localassetmanager] Begin createLocalItem");var item={Item:libraryItem,ItemId:libraryItem.Id,ServerId:libraryItem.ServerId,Id:libraryItem.Id};return jobItem&&(item.SyncJobItemId=jobItem.SyncJobItemId),console.log("[localassetmanager] End createLocalItem"),item}function getNewItem(jobItem,apiClient){console.log("[mediasync] Begin getNewItem");var libraryItem=jobItem.Item;return localassetmanager.getLocalItem(libraryItem.ServerId,libraryItem.Id).then(function(existingItem){if(existingItem&&("queued"===existingItem.SyncStatus||"transferring"===existingItem.SyncStatus||"synced"===existingItem.SyncStatus)&&(console.log("[mediasync] getNewItem: getLocalItem found existing item"),localassetmanager.enableBackgroundCompletion()))return Promise.resolve();libraryItem.CanDelete=!1,libraryItem.CanDownload=!1,libraryItem.SupportsSync=!1,libraryItem.People=[],libraryItem.Chapters=[],libraryItem.Studios=[],libraryItem.SpecialFeatureCount=null,libraryItem.LocalTrailerCount=null,libraryItem.RemoteTrailers=[];var localItem=createLocalItem(libraryItem,jobItem);return localItem.SyncStatus="queued",downloadMedia(apiClient,jobItem,localItem)})}function downloadParentItems(apiClient,jobItem,libraryItem){var p=Promise.resolve();return libraryItem.SeriesId&&(p=p.then(function(){return downloadItem(apiClient,libraryItem.SeriesId)})),libraryItem.SeasonId&&(p=p.then(function(){return downloadItem(apiClient,libraryItem.SeasonId).then(function(seasonItem){return libraryItem.SeasonPrimaryImageTag=(seasonItem.Item.ImageTags||{}).Primary,Promise.resolve()})})),libraryItem.AlbumId&&(p=p.then(function(){return downloadItem(apiClient,libraryItem.AlbumId)})),p}function downloadItem(apiClient,itemId){return apiClient.getItem(apiClient.getCurrentUserId(),itemId).then(function(downloadedItem){downloadedItem.CanDelete=!1,downloadedItem.CanDownload=!1,downloadedItem.SupportsSync=!1,downloadedItem.People=[],downloadedItem.SpecialFeatureCount=null,downloadedItem.BackdropImageTags=null,downloadedItem.ParentBackdropImageTags=null,downloadedItem.ParentArtImageTag=null,downloadedItem.ParentLogoImageTag=null;var localItem=createLocalItem(downloadedItem,null);return localassetmanager.addOrUpdateLocalItem(localItem).then(function(){return Promise.resolve(localItem)},function(err){return console.error("[mediasync] downloadItem failed: "+err.toString()),Promise.resolve(null)})})}function ensureLocalPathParts(localItem,jobItem){if(!localItem.LocalPathParts){var libraryItem=localItem.Item,parts=localassetmanager.getDirectoryPath(libraryItem);parts.push(localassetmanager.getLocalFileName(libraryItem,jobItem.OriginalFileName)),localItem.LocalPathParts=parts}}function downloadMedia(apiClient,jobItem,localItem){console.log("[mediasync] downloadMedia: start.");var url=apiClient.getUrl("Sync/JobItems/"+jobItem.SyncJobItemId+"/File",{api_key:apiClient.accessToken()});return ensureLocalPathParts(localItem,jobItem),localassetmanager.downloadFile(url,localItem).then(function(result){console.log("[mediasync] downloadMedia-downloadFile returned path: "+result.path);var localPath=result.path,libraryItem=localItem.Item;if(localPath&&libraryItem.MediaSources)for(var i=0;i2?Promise.resolve():reportOfflineActions(apiClient,serverInfo).then(function(){return getNewMedia(apiClient,downloadCount).then(function(){return syncData(apiClient,serverInfo).then(function(){return console.log("[mediasync]************************************* Exit sync"),Promise.resolve()})})})})})},function(err){console.error(err.toString())})}:self.sync=function(apiClient,serverInfo,options){return console.log("[mediasync]************************************* Start sync"),checkLocalFileExistence(apiClient,serverInfo,options).then(function(){return syncData(apiClient,serverInfo).then(function(){return processDownloadStatus(apiClient,serverInfo,options).then(function(){return localassetmanager.getDownloadItemCount().then(function(downloadCount){return!0===options.syncCheckProgressOnly&&downloadCount>2?Promise.resolve():reportOfflineActions(apiClient,serverInfo).then(function(){return getNewMedia(apiClient,downloadCount).then(function(){return syncData(apiClient,serverInfo)})})})})})},function(err){console.error(err.toString())})}}}); \ No newline at end of file +define(["localassetmanager"], function(localassetmanager) { + "use strict"; + + function processDownloadStatus(apiClient, serverInfo, options) { + return console.log("[mediasync] Begin processDownloadStatus"), localassetmanager.resyncTransfers().then(function() { + return localassetmanager.getServerItems(serverInfo.Id).then(function(items) { + console.log("[mediasync] Begin processDownloadStatus getServerItems completed"); + var p = Promise.resolve(), + cnt = 0; + return items.filter(function(item) { + return "transferring" === item.SyncStatus || "queued" === item.SyncStatus + }).forEach(function(item) { + p = p.then(function() { + return reportTransfer(apiClient, item) + }), cnt++ + }), p.then(function() { + return console.log("[mediasync] Exit processDownloadStatus. Items reported: " + cnt.toString()), Promise.resolve() + }) + }) + }) + } + + function reportTransfer(apiClient, item) { + return localassetmanager.getItemFileSize(item.LocalPath).then(function(size) { + return size > 0 ? apiClient.reportSyncJobItemTransferred(item.SyncJobItemId).then(function() { + return item.SyncStatus = "synced", console.log("[mediasync] reportSyncJobItemTransferred called for " + item.LocalPath), localassetmanager.addOrUpdateLocalItem(item) + }, function(error) { + return console.error("[mediasync] Mediasync error on reportSyncJobItemTransferred", error), item.SyncStatus = "error", localassetmanager.addOrUpdateLocalItem(item) + }) : localassetmanager.isDownloadFileInQueue(item.LocalPath).then(function(result) { + return result ? Promise.resolve() : (console.log("[mediasync] reportTransfer: Size is 0 and download no longer in queue. Deleting item."), localassetmanager.removeLocalItem(item).then(function() { + return console.log("[mediasync] reportTransfer: Item deleted."), Promise.resolve() + }, function(err2) { + return console.log("[mediasync] reportTransfer: Failed to delete item.", err2), Promise.resolve() + })) + }) + }, function(error) { + return console.error("[mediasync] reportTransfer: error on getItemFileSize. Deleting item.", error), localassetmanager.removeLocalItem(item).then(function() { + return console.log("[mediasync] reportTransfer: Item deleted."), Promise.resolve() + }, function(err2) { + return console.log("[mediasync] reportTransfer: Failed to delete item.", err2), Promise.resolve() + }) + }) + } + + function reportOfflineActions(apiClient, serverInfo) { + return console.log("[mediasync] Begin reportOfflineActions"), localassetmanager.getUserActions(serverInfo.Id).then(function(actions) { + return actions.length ? apiClient.reportOfflineActions(actions).then(function() { + return localassetmanager.deleteUserActions(actions).then(function() { + return console.log("[mediasync] Exit reportOfflineActions (actions reported and deleted.)"), Promise.resolve() + }) + }, function(err) { + return console.error("[mediasync] error on apiClient.reportOfflineActions: " + err.toString()), localassetmanager.deleteUserActions(actions) + }) : (console.log("[mediasync] Exit reportOfflineActions (no actions)"), Promise.resolve()) + }) + } + + function syncData(apiClient, serverInfo) { + return console.log("[mediasync] Begin syncData"), localassetmanager.getServerItems(serverInfo.Id).then(function(items) { + var completedItems = items.filter(function(item) { + return item && ("synced" === item.SyncStatus || "error" === item.SyncStatus) + }), + request = { + TargetId: apiClient.deviceId(), + LocalItemIds: completedItems.map(function(xitem) { + return xitem.ItemId + }) + }; + return apiClient.syncData(request).then(function(result) { + return afterSyncData(apiClient, serverInfo, result).then(function() { + return console.log("[mediasync] Exit syncData"), Promise.resolve() + }, function(err) { + return console.error("[mediasync] Error in syncData: " + err.toString()), Promise.resolve() + }) + }) + }) + } + + function afterSyncData(apiClient, serverInfo, syncDataResult) { + console.log("[mediasync] Begin afterSyncData"); + var p = Promise.resolve(); + return syncDataResult.ItemIdsToRemove && syncDataResult.ItemIdsToRemove.length > 0 && syncDataResult.ItemIdsToRemove.forEach(function(itemId) { + p = p.then(function() { + return removeLocalItem(itemId, serverInfo.Id) + }) + }), p = p.then(function() { + return removeObsoleteContainerItems(serverInfo.Id) + }), p.then(function() { + return console.log("[mediasync] Exit afterSyncData"), Promise.resolve() + }) + } + + function removeObsoleteContainerItems(serverId) { + return console.log("[mediasync] Begin removeObsoleteContainerItems"), localassetmanager.removeObsoleteContainerItems(serverId) + } + + function removeLocalItem(itemId, serverId) { + return console.log("[mediasync] Begin removeLocalItem"), localassetmanager.getLocalItem(serverId, itemId).then(function(item) { + return item ? localassetmanager.removeLocalItem(item) : Promise.resolve() + }, function(err2) { + return console.error("[mediasync] removeLocalItem: Failed: ", err2), Promise.resolve() + }) + } + + function getNewMedia(apiClient, downloadCount) { + return console.log("[mediasync] Begin getNewMedia"), apiClient.getReadySyncItems(apiClient.deviceId()).then(function(jobItems) { + console.log("[mediasync] getReadySyncItems returned " + jobItems.length + " items"); + var p = Promise.resolve(), + currentCount = downloadCount; + return jobItems.forEach(function(jobItem) { + currentCount++ <= 10 && (p = p.then(function() { + return getNewItem(jobItem, apiClient) + })) + }), p.then(function() { + return console.log("[mediasync] Exit getNewMedia"), Promise.resolve() + }) + }, function(err) { + return console.error("[mediasync] getReadySyncItems: Failed: ", err), Promise.resolve() + }) + } + + function afterMediaDownloaded(apiClient, jobItem, localItem) { + return console.log("[mediasync] Begin afterMediaDownloaded"), getImages(apiClient, jobItem, localItem).then(function() { + var libraryItem = jobItem.Item; + return downloadParentItems(apiClient, jobItem, libraryItem).then(function() { + return getSubtitles(apiClient, jobItem, localItem) + }) + }) + } + + function createLocalItem(libraryItem, jobItem) { + console.log("[localassetmanager] Begin createLocalItem"); + var item = { + Item: libraryItem, + ItemId: libraryItem.Id, + ServerId: libraryItem.ServerId, + Id: libraryItem.Id + }; + return jobItem && (item.SyncJobItemId = jobItem.SyncJobItemId), console.log("[localassetmanager] End createLocalItem"), item + } + + function getNewItem(jobItem, apiClient) { + console.log("[mediasync] Begin getNewItem"); + var libraryItem = jobItem.Item; + return localassetmanager.getLocalItem(libraryItem.ServerId, libraryItem.Id).then(function(existingItem) { + if (existingItem && ("queued" === existingItem.SyncStatus || "transferring" === existingItem.SyncStatus || "synced" === existingItem.SyncStatus) && (console.log("[mediasync] getNewItem: getLocalItem found existing item"), localassetmanager.enableBackgroundCompletion())) return Promise.resolve(); + libraryItem.CanDelete = !1, libraryItem.CanDownload = !1, libraryItem.SupportsSync = !1, libraryItem.People = [], libraryItem.Chapters = [], libraryItem.Studios = [], libraryItem.SpecialFeatureCount = null, libraryItem.LocalTrailerCount = null, libraryItem.RemoteTrailers = []; + var localItem = createLocalItem(libraryItem, jobItem); + return localItem.SyncStatus = "queued", downloadMedia(apiClient, jobItem, localItem) + }) + } + + function downloadParentItems(apiClient, jobItem, libraryItem) { + var p = Promise.resolve(); + return libraryItem.SeriesId && (p = p.then(function() { + return downloadItem(apiClient, libraryItem.SeriesId) + })), libraryItem.SeasonId && (p = p.then(function() { + return downloadItem(apiClient, libraryItem.SeasonId).then(function(seasonItem) { + return libraryItem.SeasonPrimaryImageTag = (seasonItem.Item.ImageTags || {}).Primary, Promise.resolve() + }) + })), libraryItem.AlbumId && (p = p.then(function() { + return downloadItem(apiClient, libraryItem.AlbumId) + })), p + } + + function downloadItem(apiClient, itemId) { + return apiClient.getItem(apiClient.getCurrentUserId(), itemId).then(function(downloadedItem) { + downloadedItem.CanDelete = !1, downloadedItem.CanDownload = !1, downloadedItem.SupportsSync = !1, downloadedItem.People = [], downloadedItem.SpecialFeatureCount = null, downloadedItem.BackdropImageTags = null, downloadedItem.ParentBackdropImageTags = null, downloadedItem.ParentArtImageTag = null, downloadedItem.ParentLogoImageTag = null; + var localItem = createLocalItem(downloadedItem, null); + return localassetmanager.addOrUpdateLocalItem(localItem).then(function() { + return Promise.resolve(localItem) + }, function(err) { + return console.error("[mediasync] downloadItem failed: " + err.toString()), Promise.resolve(null) + }) + }) + } + + function ensureLocalPathParts(localItem, jobItem) { + if (!localItem.LocalPathParts) { + var libraryItem = localItem.Item, + parts = localassetmanager.getDirectoryPath(libraryItem); + parts.push(localassetmanager.getLocalFileName(libraryItem, jobItem.OriginalFileName)), localItem.LocalPathParts = parts + } + } + + function downloadMedia(apiClient, jobItem, localItem) { + console.log("[mediasync] downloadMedia: start."); + var url = apiClient.getUrl("Sync/JobItems/" + jobItem.SyncJobItemId + "/File", { + api_key: apiClient.accessToken() + }); + return ensureLocalPathParts(localItem, jobItem), localassetmanager.downloadFile(url, localItem).then(function(result) { + console.log("[mediasync] downloadMedia-downloadFile returned path: " + result.path); + var localPath = result.path, + libraryItem = localItem.Item; + if (localPath && libraryItem.MediaSources) + for (var i = 0; i < libraryItem.MediaSources.length; i++) { + var mediaSource = libraryItem.MediaSources[i]; + mediaSource.Path = localPath, mediaSource.Protocol = "File" + } + return localItem.LocalPath = localPath, localItem.SyncStatus = "transferring", localassetmanager.addOrUpdateLocalItem(localItem).then(function() { + return afterMediaDownloaded(apiClient, jobItem, localItem).then(function() { + return result.isComplete ? (localItem.SyncStatus = "synced", reportTransfer(apiClient, localItem)) : Promise.resolve() + }, function(err) { + return console.log("[mediasync] downloadMedia: afterMediaDownloaded failed: " + err), Promise.reject(err) + }) + }, function(err) { + return console.log("[mediasync] downloadMedia: addOrUpdateLocalItem failed: " + err), Promise.reject(err) + }) + }, function(err) { + return console.log("[mediasync] downloadMedia: localassetmanager.downloadFile failed: " + err), Promise.reject(err) + }) + } + + function getImages(apiClient, jobItem, localItem) { + console.log("[mediasync] Begin getImages"); + var p = Promise.resolve(), + libraryItem = localItem.Item, + serverId = libraryItem.ServerId, + mainImageTag = (libraryItem.ImageTags || {}).Primary; + libraryItem.Id && mainImageTag && (p = p.then(function() { + return downloadImage(localItem, apiClient, serverId, libraryItem.Id, mainImageTag, "Primary") + })); + var logoImageTag = (libraryItem.ImageTags || {}).Logo; + libraryItem.Id && logoImageTag && (p = p.then(function() { + return downloadImage(localItem, apiClient, serverId, libraryItem.Id, logoImageTag, "Logo") + })); + var artImageTag = (libraryItem.ImageTags || {}).Art; + libraryItem.Id && artImageTag && (p = p.then(function() { + return downloadImage(localItem, apiClient, serverId, libraryItem.Id, artImageTag, "Art") + })); + var bannerImageTag = (libraryItem.ImageTags || {}).Banner; + libraryItem.Id && bannerImageTag && (p = p.then(function() { + return downloadImage(localItem, apiClient, serverId, libraryItem.Id, bannerImageTag, "Banner") + })); + var thumbImageTag = (libraryItem.ImageTags || {}).Thumb; + if (libraryItem.Id && thumbImageTag && (p = p.then(function() { + return downloadImage(localItem, apiClient, serverId, libraryItem.Id, thumbImageTag, "Thumb") + })), libraryItem.Id && libraryItem.BackdropImageTags) + for (var i = 0; i < libraryItem.BackdropImageTags.length; i++); + return libraryItem.SeriesId && libraryItem.SeriesPrimaryImageTag && (p = p.then(function() { + return downloadImage(localItem, apiClient, serverId, libraryItem.SeriesId, libraryItem.SeriesPrimaryImageTag, "Primary") + })), libraryItem.SeriesId && libraryItem.SeriesThumbImageTag && (p = p.then(function() { + return downloadImage(localItem, apiClient, serverId, libraryItem.SeriesId, libraryItem.SeriesThumbImageTag, "Thumb") + })), libraryItem.SeasonId && libraryItem.SeasonPrimaryImageTag && (p = p.then(function() { + return downloadImage(localItem, apiClient, serverId, libraryItem.SeasonId, libraryItem.SeasonPrimaryImageTag, "Primary") + })), libraryItem.AlbumId && libraryItem.AlbumPrimaryImageTag && (p = p.then(function() { + return downloadImage(localItem, apiClient, serverId, libraryItem.AlbumId, libraryItem.AlbumPrimaryImageTag, "Primary") + })), libraryItem.ParentThumbItemId && libraryItem.ParentThumbImageTag && (p = p.then(function() { + return downloadImage(localItem, apiClient, serverId, libraryItem.ParentThumbItemId, libraryItem.ParentThumbImageTag, "Thumb") + })), libraryItem.ParentPrimaryImageItemId && libraryItem.ParentPrimaryImageTag && (p = p.then(function() { + return downloadImage(localItem, apiClient, serverId, libraryItem.ParentPrimaryImageItemId, libraryItem.ParentPrimaryImageTag, "Primary") + })), p.then(function() { + return console.log("[mediasync] Finished getImages"), localassetmanager.addOrUpdateLocalItem(localItem) + }, function(err) { + return console.log("[mediasync] Error getImages: " + err.toString()), Promise.resolve() + }) + } + + function downloadImage(localItem, apiClient, serverId, itemId, imageTag, imageType, index) { + return index = index || 0, localassetmanager.hasImage(serverId, itemId, imageType, index).then(function(hasImage) { + if (hasImage) return console.log("[mediasync] downloadImage - skip existing: " + itemId + " " + imageType + "_" + index.toString()), Promise.resolve(); + var maxWidth = 400; + "backdrop" === imageType && (maxWidth = null); + var imageUrl = apiClient.getScaledImageUrl(itemId, { + tag: imageTag, + type: imageType, + maxWidth: maxWidth, + api_key: apiClient.accessToken() + }); + return console.log("[mediasync] downloadImage " + itemId + " " + imageType + "_" + index.toString()), localassetmanager.downloadImage(localItem, imageUrl, serverId, itemId, imageType, index).then(function(result) { + return Promise.resolve(result) + }, function(err) { + return console.log("[mediasync] Error downloadImage: " + err.toString()), Promise.resolve() + }) + }, function(err) { + return console.log("[mediasync] Error downloadImage: " + err.toString()), Promise.resolve() + }) + } + + function getSubtitles(apiClient, jobItem, localItem) { + if (console.log("[mediasync] Begin getSubtitles"), !jobItem.Item.MediaSources.length) return console.log("[mediasync] Cannot download subtitles because video has no media source info."), Promise.resolve(); + var files = jobItem.AdditionalFiles.filter(function(f) { + return "Subtitles" === f.Type + }), + mediaSource = jobItem.Item.MediaSources[0], + p = Promise.resolve(); + return files.forEach(function(file) { + p = p.then(function() { + return getItemSubtitle(file, apiClient, jobItem, localItem, mediaSource) + }) + }), p.then(function() { + return console.log("[mediasync] Exit getSubtitles"), Promise.resolve() + }) + } + + function getItemSubtitle(file, apiClient, jobItem, localItem, mediaSource) { + console.log("[mediasync] Begin getItemSubtitle"); + var subtitleStream = mediaSource.MediaStreams.filter(function(m) { + return "Subtitle" === m.Type && m.Index === file.Index + })[0]; + if (!subtitleStream) return console.log("[mediasync] Cannot download subtitles because matching stream info was not found."), Promise.resolve(); + var url = apiClient.getUrl("Sync/JobItems/" + jobItem.SyncJobItemId + "/AdditionalFiles", { + Name: file.Name, + api_key: apiClient.accessToken() + }), + fileName = localassetmanager.getSubtitleSaveFileName(localItem, jobItem.OriginalFileName, subtitleStream.Language, subtitleStream.IsForced, subtitleStream.Codec); + return localassetmanager.downloadSubtitles(url, fileName).then(function(subtitleResult) { + return localItem.AdditionalFiles && localItem.AdditionalFiles.forEach(function(item) { + item.Name === file.Name && (item.Path = subtitleResult.path) + }), subtitleStream.Path = subtitleResult.path, subtitleStream.DeliveryMethod = "External", localassetmanager.addOrUpdateLocalItem(localItem) + }) + } + + function checkLocalFileExistence(apiClient, serverInfo, options) { + return options.checkFileExistence ? (console.log("[mediasync] Begin checkLocalFileExistence"), localassetmanager.getServerItems(serverInfo.Id).then(function(items) { + var completedItems = items.filter(function(item) { + return item && ("synced" === item.SyncStatus || "error" === item.SyncStatus) + }), + p = Promise.resolve(); + return completedItems.forEach(function(completedItem) { + p = p.then(function() { + return localassetmanager.fileExists(completedItem.LocalPath).then(function(exists) { + return exists ? Promise.resolve() : localassetmanager.removeLocalItem(completedItem).then(function() { + return Promise.resolve() + }, function() { + return Promise.resolve() + }) + }) + }) + }), p + })) : Promise.resolve() + } + return function() { + var self = this; + "string" == typeof webWorkerBaseUrl && -1 !== webWorkerBaseUrl.indexOf("ms-appx://") ? self.sync = function(apiClient, serverInfo, options) { + return console.log("[mediasync]************************************* Start sync"), checkLocalFileExistence(apiClient, serverInfo, options).then(function() { + return processDownloadStatus(apiClient, serverInfo, options).then(function() { + return localassetmanager.getDownloadItemCount().then(function(downloadCount) { + return !0 === options.syncCheckProgressOnly && downloadCount > 2 ? Promise.resolve() : reportOfflineActions(apiClient, serverInfo).then(function() { + return getNewMedia(apiClient, downloadCount).then(function() { + return syncData(apiClient, serverInfo).then(function() { + return console.log("[mediasync]************************************* Exit sync"), Promise.resolve() + }) + }) + }) + }) + }) + }, function(err) { + console.error(err.toString()) + }) + } : self.sync = function(apiClient, serverInfo, options) { + return console.log("[mediasync]************************************* Start sync"), checkLocalFileExistence(apiClient, serverInfo, options).then(function() { + return syncData(apiClient, serverInfo).then(function() { + return processDownloadStatus(apiClient, serverInfo, options).then(function() { + return localassetmanager.getDownloadItemCount().then(function(downloadCount) { + return !0 === options.syncCheckProgressOnly && downloadCount > 2 ? Promise.resolve() : reportOfflineActions(apiClient, serverInfo).then(function() { + return getNewMedia(apiClient, downloadCount).then(function() { + return syncData(apiClient, serverInfo) + }) + }) + }) + }) + }) + }, function(err) { + console.error(err.toString()) + }) + } + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-apiclient/sync/multiserversync.js b/dashboard-ui/bower_components/emby-apiclient/sync/multiserversync.js index 204431130b..0654b5615d 100644 --- a/dashboard-ui/bower_components/emby-apiclient/sync/multiserversync.js +++ b/dashboard-ui/bower_components/emby-apiclient/sync/multiserversync.js @@ -1 +1,22 @@ -define(["serversync"],function(ServerSync){"use strict";function syncNext(connectionManager,servers,index,options,resolve,reject){var length=servers.length;if(index>=length)return console.log("MultiServerSync.sync complete"),void resolve();var server=servers[index];console.log("Creating ServerSync to server: "+server.Id),(new ServerSync).sync(connectionManager,server,options).then(function(){console.log("ServerSync succeeded to server: "+server.Id),syncNext(connectionManager,servers,index+1,options,resolve,reject)},function(err){console.log("ServerSync failed to server: "+server.Id+". "+err),syncNext(connectionManager,servers,index+1,options,resolve,reject)})}function MultiServerSync(){}return MultiServerSync.prototype.sync=function(connectionManager,options){return console.log("MultiServerSync.sync starting..."),new Promise(function(resolve,reject){var servers=connectionManager.getSavedServers();syncNext(connectionManager,servers,0,options,resolve,reject)})},MultiServerSync}); \ No newline at end of file +define(["serversync"], function(ServerSync) { + "use strict"; + + function syncNext(connectionManager, servers, index, options, resolve, reject) { + var length = servers.length; + if (index >= length) return console.log("MultiServerSync.sync complete"), void resolve(); + var server = servers[index]; + console.log("Creating ServerSync to server: " + server.Id), (new ServerSync).sync(connectionManager, server, options).then(function() { + console.log("ServerSync succeeded to server: " + server.Id), syncNext(connectionManager, servers, index + 1, options, resolve, reject) + }, function(err) { + console.log("ServerSync failed to server: " + server.Id + ". " + err), syncNext(connectionManager, servers, index + 1, options, resolve, reject) + }) + } + + function MultiServerSync() {} + return MultiServerSync.prototype.sync = function(connectionManager, options) { + return console.log("MultiServerSync.sync starting..."), new Promise(function(resolve, reject) { + var servers = connectionManager.getSavedServers(); + syncNext(connectionManager, servers, 0, options, resolve, reject) + }) + }, MultiServerSync +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-apiclient/sync/serversync.js b/dashboard-ui/bower_components/emby-apiclient/sync/serversync.js index 870d21fc06..4299091c27 100644 --- a/dashboard-ui/bower_components/emby-apiclient/sync/serversync.js +++ b/dashboard-ui/bower_components/emby-apiclient/sync/serversync.js @@ -1 +1,46 @@ -define([],function(){"use strict";function performSync(connectionManager,server,options){console.log("ServerSync.performSync to server: "+server.Id),options=options||{};var cameraUploadServers=options.cameraUploadServers||[];console.log("ServerSync cameraUploadServers: "+JSON.stringify(cameraUploadServers));var uploadPhotos=-1!==cameraUploadServers.indexOf(server.Id);return console.log("ServerSync uploadPhotos: "+uploadPhotos),(uploadPhotos?uploadContent(connectionManager,server,options):Promise.resolve()).then(function(){return syncMedia(connectionManager,server,options)})}function uploadContent(connectionManager,server,options){return new Promise(function(resolve,reject){require(["contentuploader"],function(ContentUploader){(new ContentUploader).uploadImages(connectionManager,server).then(resolve,reject)})})}function syncMedia(connectionManager,server,options){return new Promise(function(resolve,reject){require(["mediasync"],function(MediaSync){var apiClient=connectionManager.getApiClient(server.Id);(new MediaSync).sync(apiClient,server,options).then(resolve,reject)})})}function ServerSync(){}return ServerSync.prototype.sync=function(connectionManager,server,options){if(!server.AccessToken&&!server.ExchangeToken)return console.log("Skipping sync to server "+server.Id+" because there is no saved authentication information."),Promise.resolve();var connectionOptions={updateDateLastAccessed:!1,enableWebSocket:!1,reportCapabilities:!1,enableAutomaticBitrateDetection:!1};return connectionManager.connectToServer(server,connectionOptions).then(function(result){return"SignedIn"===result.State?performSync(connectionManager,server,options):(console.log("Unable to connect to server id: "+server.Id),Promise.reject())},function(err){throw console.log("Unable to connect to server id: "+server.Id),err})},ServerSync}); \ No newline at end of file +define([], function() { + "use strict"; + + function performSync(connectionManager, server, options) { + console.log("ServerSync.performSync to server: " + server.Id), options = options || {}; + var cameraUploadServers = options.cameraUploadServers || []; + console.log("ServerSync cameraUploadServers: " + JSON.stringify(cameraUploadServers)); + var uploadPhotos = -1 !== cameraUploadServers.indexOf(server.Id); + return console.log("ServerSync uploadPhotos: " + uploadPhotos), (uploadPhotos ? uploadContent(connectionManager, server, options) : Promise.resolve()).then(function() { + return syncMedia(connectionManager, server, options) + }) + } + + function uploadContent(connectionManager, server, options) { + return new Promise(function(resolve, reject) { + require(["contentuploader"], function(ContentUploader) { + (new ContentUploader).uploadImages(connectionManager, server).then(resolve, reject) + }) + }) + } + + function syncMedia(connectionManager, server, options) { + return new Promise(function(resolve, reject) { + require(["mediasync"], function(MediaSync) { + var apiClient = connectionManager.getApiClient(server.Id); + (new MediaSync).sync(apiClient, server, options).then(resolve, reject) + }) + }) + } + + function ServerSync() {} + return ServerSync.prototype.sync = function(connectionManager, server, options) { + if (!server.AccessToken && !server.ExchangeToken) return console.log("Skipping sync to server " + server.Id + " because there is no saved authentication information."), Promise.resolve(); + var connectionOptions = { + updateDateLastAccessed: !1, + enableWebSocket: !1, + reportCapabilities: !1, + enableAutomaticBitrateDetection: !1 + }; + return connectionManager.connectToServer(server, connectionOptions).then(function(result) { + return "SignedIn" === result.State ? performSync(connectionManager, server, options) : (console.log("Unable to connect to server id: " + server.Id), Promise.reject()) + }, function(err) { + throw console.log("Unable to connect to server id: " + server.Id), err + }) + }, ServerSync +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-apiclient/sync/transfermanager.js b/dashboard-ui/bower_components/emby-apiclient/sync/transfermanager.js index 3c4d24b681..162a6a1226 100644 --- a/dashboard-ui/bower_components/emby-apiclient/sync/transfermanager.js +++ b/dashboard-ui/bower_components/emby-apiclient/sync/transfermanager.js @@ -1 +1,30 @@ -define([],function(){"use strict";function downloadFile(url,folder,localItem,imageUrl){return Promise.reject()}function downloadSubtitles(url,folder,fileName){return Promise.reject()}function downloadImage(url,folder,fileName){return Promise.reject()}function resyncTransfers(){return Promise.resolve()}function getDownloadItemCount(){return Promise.resolve(0)}return{downloadFile:downloadFile,downloadSubtitles:downloadSubtitles,downloadImage:downloadImage,resyncTransfers:resyncTransfers,getDownloadItemCount:getDownloadItemCount}}); \ No newline at end of file +define([], function() { + "use strict"; + + function downloadFile(url, folder, localItem, imageUrl) { + return Promise.reject() + } + + function downloadSubtitles(url, folder, fileName) { + return Promise.reject() + } + + function downloadImage(url, folder, fileName) { + return Promise.reject() + } + + function resyncTransfers() { + return Promise.resolve() + } + + function getDownloadItemCount() { + return Promise.resolve(0) + } + return { + downloadFile: downloadFile, + downloadSubtitles: downloadSubtitles, + downloadImage: downloadImage, + resyncTransfers: resyncTransfers, + getDownloadItemCount: getDownloadItemCount + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-apiclient/sync/useractionrepository.js b/dashboard-ui/bower_components/emby-apiclient/sync/useractionrepository.js index 106d0b3925..8612b05bea 100644 --- a/dashboard-ui/bower_components/emby-apiclient/sync/useractionrepository.js +++ b/dashboard-ui/bower_components/emby-apiclient/sync/useractionrepository.js @@ -1 +1,108 @@ -define([],function(){"use strict";function getDb(callback){var db=databaseInstance;if(db)return void callback(db);var request=indexedDB.open(dbName,dbVersion);request.onerror=function(event){},request.onupgradeneeded=function(event){var db=event.target.result;db.createObjectStore(dbName).transaction.oncomplete=function(event){callback(db)}},request.onsuccess=function(event){var db=event.target.result;callback(db)}}function getByServerId(serverId){return getAll().then(function(items){return items.filter(function(item){return item.ServerId===serverId})})}function getAll(){return new Promise(function(resolve,reject){getDb(function(db){var request,storeName=dbName,transaction=db.transaction([storeName],"readonly"),objectStore=transaction.objectStore(storeName);if("getAll"in objectStore)request=objectStore.getAll(null,1e4),request.onsuccess=function(event){resolve(event.target.result)};else{var results=[];request=objectStore.openCursor(),request.onsuccess=function(event){var cursor=event.target.result;cursor?(results.push(cursor.value),cursor.continue()):resolve(results)}}request.onerror=reject})})}function get(key){return new Promise(function(resolve,reject){getDb(function(db){var storeName=dbName,transaction=db.transaction([storeName],"readonly"),objectStore=transaction.objectStore(storeName),request=objectStore.get(key);request.onerror=reject,request.onsuccess=function(event){resolve(request.result)}})})}function set(key,val){return new Promise(function(resolve,reject){getDb(function(db){var storeName=dbName,transaction=db.transaction([storeName],"readwrite"),objectStore=transaction.objectStore(storeName),request=objectStore.put(val,key);request.onerror=reject,request.onsuccess=resolve})})}function remove(key){return new Promise(function(resolve,reject){getDb(function(db){var storeName=dbName,transaction=db.transaction([storeName],"readwrite"),objectStore=transaction.objectStore(storeName),request=objectStore.delete(key);request.onerror=reject,request.onsuccess=resolve})})}function clear(){return new Promise(function(resolve,reject){getDb(function(db){var storeName=dbName,transaction=db.transaction([storeName],"readwrite"),objectStore=transaction.objectStore(storeName),request=objectStore.clear();request.onerror=reject,request.onsuccess=resolve})})}var databaseInstance,indexedDB=self.indexedDB||self.mozIndexedDB||self.webkitIndexedDB||self.msIndexedDB,dbName=(self.IDBTransaction||self.webkitIDBTransaction||self.msIDBTransaction,self.IDBKeyRange||self.webkitIDBKeyRange||self.msIDBKeyRange,"useractions"),dbVersion=1;return{get:get,set:set,remove:remove,clear:clear,getAll:getAll,getByServerId:getByServerId}}); \ No newline at end of file +define([], function() { + "use strict"; + + function getDb(callback) { + var db = databaseInstance; + if (db) return void callback(db); + var request = indexedDB.open(dbName, dbVersion); + request.onerror = function(event) {}, request.onupgradeneeded = function(event) { + var db = event.target.result; + db.createObjectStore(dbName).transaction.oncomplete = function(event) { + callback(db) + } + }, request.onsuccess = function(event) { + var db = event.target.result; + callback(db) + } + } + + function getByServerId(serverId) { + return getAll().then(function(items) { + return items.filter(function(item) { + return item.ServerId === serverId + }) + }) + } + + function getAll() { + return new Promise(function(resolve, reject) { + getDb(function(db) { + var request, storeName = dbName, + transaction = db.transaction([storeName], "readonly"), + objectStore = transaction.objectStore(storeName); + if ("getAll" in objectStore) request = objectStore.getAll(null, 1e4), request.onsuccess = function(event) { + resolve(event.target.result) + }; + else { + var results = []; + request = objectStore.openCursor(), request.onsuccess = function(event) { + var cursor = event.target.result; + cursor ? (results.push(cursor.value), cursor.continue()) : resolve(results) + } + } + request.onerror = reject + }) + }) + } + + function get(key) { + return new Promise(function(resolve, reject) { + getDb(function(db) { + var storeName = dbName, + transaction = db.transaction([storeName], "readonly"), + objectStore = transaction.objectStore(storeName), + request = objectStore.get(key); + request.onerror = reject, request.onsuccess = function(event) { + resolve(request.result) + } + }) + }) + } + + function set(key, val) { + return new Promise(function(resolve, reject) { + getDb(function(db) { + var storeName = dbName, + transaction = db.transaction([storeName], "readwrite"), + objectStore = transaction.objectStore(storeName), + request = objectStore.put(val, key); + request.onerror = reject, request.onsuccess = resolve + }) + }) + } + + function remove(key) { + return new Promise(function(resolve, reject) { + getDb(function(db) { + var storeName = dbName, + transaction = db.transaction([storeName], "readwrite"), + objectStore = transaction.objectStore(storeName), + request = objectStore.delete(key); + request.onerror = reject, request.onsuccess = resolve + }) + }) + } + + function clear() { + return new Promise(function(resolve, reject) { + getDb(function(db) { + var storeName = dbName, + transaction = db.transaction([storeName], "readwrite"), + objectStore = transaction.objectStore(storeName), + request = objectStore.clear(); + request.onerror = reject, request.onsuccess = resolve + }) + }) + } + var databaseInstance, indexedDB = self.indexedDB || self.mozIndexedDB || self.webkitIndexedDB || self.msIndexedDB, + dbName = (self.IDBTransaction || self.webkitIDBTransaction || self.msIDBTransaction, self.IDBKeyRange || self.webkitIDBKeyRange || self.msIDBKeyRange, "useractions"), + dbVersion = 1; + return { + get: get, + set: set, + remove: remove, + clear: clear, + getAll: getAll, + getByServerId: getByServerId + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-apiclient/wakeonlan.js b/dashboard-ui/bower_components/emby-apiclient/wakeonlan.js index ac74370479..58c01e61a5 100644 --- a/dashboard-ui/bower_components/emby-apiclient/wakeonlan.js +++ b/dashboard-ui/bower_components/emby-apiclient/wakeonlan.js @@ -1 +1,15 @@ -define([],function(){"use strict";function send(info){return Promise.reject()}function isSupported(){return!1}return{send:send,isSupported:isSupported}}); \ No newline at end of file +define([], function() { + "use strict"; + + function send(info) { + return Promise.reject() + } + + function isSupported() { + return !1 + } + return { + send: send, + isSupported: isSupported + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/actionsheet/actionsheet.js b/dashboard-ui/bower_components/emby-webcomponents/actionsheet/actionsheet.js index deff4b9903..6c93bb2507 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/actionsheet/actionsheet.js +++ b/dashboard-ui/bower_components/emby-webcomponents/actionsheet/actionsheet.js @@ -1 +1,93 @@ -define(["dialogHelper","layoutManager","globalize","browser","dom","emby-button","css!./actionsheet","material-icons","scrollStyles","listViewStyle"],function(dialogHelper,layoutManager,globalize,browser,dom){"use strict";function getOffsets(elems){var doc=document,results=[];if(!doc)return results;for(var box,elem,i=0,length=elems.length;i0&&(pos.left-=overflowX+20),overflowY>0&&(pos.top-=overflowY+20),pos.top+=options.offsetTop||0,pos.left+=options.offsetLeft||0,pos.top=Math.max(pos.top,10),pos.left=Math.max(pos.left,10),pos}function centerFocus(elem,horiz,on){require(["scrollHelper"],function(scrollHelper){var fn=on?"on":"off";scrollHelper.centerFocus[fn](elem,horiz)})}function show(options){var isFullscreen,dialogOptions={removeOnClose:!0,enableHistory:options.enableHistory,scrollY:!1};layoutManager.tv?(dialogOptions.size="fullscreen",isFullscreen=!0,!0,dialogOptions.autoFocus=!0):(dialogOptions.modal=!1,dialogOptions.entryAnimation=options.entryAnimation,dialogOptions.exitAnimation=options.exitAnimation,dialogOptions.entryAnimationDuration=options.entryAnimationDuration||140,dialogOptions.exitAnimationDuration=options.exitAnimationDuration||100,dialogOptions.autoFocus=!1);var dlg=dialogHelper.createDialog(dialogOptions);isFullscreen?dlg.classList.add("actionsheet-fullscreen"):dlg.classList.add("actionsheet-not-fullscreen"),dlg.classList.add("actionSheet"),options.dialogClass&&dlg.classList.add(options.dialogClass);var html="",scrollClassName=layoutManager.tv?"scrollY smoothScrollY hiddenScrollY":"scrollY",style="";if(options.items.length>20){style+="min-width:"+(dom.getWindowSize().innerWidth>=300?240:200)+"px;"}var i,length,option,itemIcon,renderIcon=!1,icons=[];for(i=0,length=options.items.length;i');var center=options.title&&!renderIcon;center||layoutManager.tv?html+='
':html+='
',options.title&&(html+='

',html+=options.title,html+="

"),options.text&&(html+='

',html+=options.text,html+="

");var scrollerClassName="actionSheetScroller";layoutManager.tv&&(scrollerClassName+=" actionSheetScroller-tv focuscontainer-x focuscontainer-y"),html+='
';var menuItemClass="listItem listItem-button actionSheetMenuItem";for((options.border||options.shaded)&&(menuItemClass+=" listItem-border"),options.menuItemClass&&(menuItemClass+=" "+options.menuItemClass),layoutManager.tv&&(menuItemClass+=" listItem-focusscale"),layoutManager.mobile&&(menuItemClass+=" actionsheet-xlargeFont"),i=0,length=options.items.length;i
';else{var autoFocus=option.selected&&layoutManager.tv?" autoFocus":"",optionId=null==option.id||""===option.id?option.value:option.id;html+="',itemIcon=icons[i],itemIcon?html+=''+itemIcon+"":renderIcon&&!center&&(html+=''),html+='
',html+='
',html+=option.name||option.textContent||option.innerText,html+="
",option.secondaryText&&(html+='
',html+=option.secondaryText,html+="
"),html+="
",option.asideText&&(html+='
',html+=option.asideText,html+="
"),html+=""}options.showCancel&&(html+='
',html+='",html+="
"),html+="
",dlg.innerHTML=html,layoutManager.tv&¢erFocus(dlg.querySelector(".actionSheetScroller"),!1,!0),dlg.querySelector(".btnCloseActionSheet")&&dlg.querySelector(".btnCloseActionSheet").addEventListener("click",function(){dialogHelper.close(dlg)});var selectedId,timeout;return options.timeout&&(timeout=setTimeout(function(){dialogHelper.close(dlg)},options.timeout)),new Promise(function(resolve,reject){var isResolved;dlg.addEventListener("click",function(e){var actionSheetMenuItem=dom.parentWithClass(e.target,"actionSheetMenuItem");actionSheetMenuItem&&(selectedId=actionSheetMenuItem.getAttribute("data-id"),options.resolveOnClick&&(options.resolveOnClick.indexOf?-1!==options.resolveOnClick.indexOf(selectedId)&&(resolve(selectedId),isResolved=!0):(resolve(selectedId),isResolved=!0)),dialogHelper.close(dlg))}),dlg.addEventListener("close",function(){layoutManager.tv&¢erFocus(dlg.querySelector(".actionSheetScroller"),!1,!1),timeout&&(clearTimeout(timeout),timeout=null),isResolved||(null!=selectedId?(options.callback&&options.callback(selectedId),resolve(selectedId)):reject())}),dialogHelper.open(dlg);var pos=options.positionTo&&"fullscreen"!==dialogOptions.size?getPosition(options,dlg):null;pos&&(dlg.style.position="fixed",dlg.style.margin=0,dlg.style.left=pos.left+"px",dlg.style.top=pos.top+"px")})}return{show:show}}); \ No newline at end of file +define(["dialogHelper", "layoutManager", "globalize", "browser", "dom", "emby-button", "css!./actionsheet", "material-icons", "scrollStyles", "listViewStyle"], function(dialogHelper, layoutManager, globalize, browser, dom) { + "use strict"; + + function getOffsets(elems) { + var doc = document, + results = []; + if (!doc) return results; + for (var box, elem, i = 0, length = elems.length; i < length; i++) elem = elems[i], box = elem.getBoundingClientRect ? elem.getBoundingClientRect() : { + top: 0, + left: 0 + }, results[i] = { + top: box.top, + left: box.left, + width: box.width, + height: box.height + }; + return results + } + + function getPosition(options, dlg) { + var windowSize = dom.getWindowSize(), + windowHeight = windowSize.innerHeight, + windowWidth = windowSize.innerWidth; + if (windowWidth < 600 || windowHeight < 600) return null; + var pos = getOffsets([options.positionTo])[0]; + "top" !== options.positionY && (pos.top += (pos.height || 0) / 2), pos.left += (pos.width || 0) / 2; + var height = dlg.offsetHeight || 300, + width = dlg.offsetWidth || 160; + pos.top -= height / 2, pos.left -= width / 2; + var overflowX = pos.left + width - windowWidth, + overflowY = pos.top + height - windowHeight; + return overflowX > 0 && (pos.left -= overflowX + 20), overflowY > 0 && (pos.top -= overflowY + 20), pos.top += options.offsetTop || 0, pos.left += options.offsetLeft || 0, pos.top = Math.max(pos.top, 10), pos.left = Math.max(pos.left, 10), pos + } + + function centerFocus(elem, horiz, on) { + require(["scrollHelper"], function(scrollHelper) { + var fn = on ? "on" : "off"; + scrollHelper.centerFocus[fn](elem, horiz) + }) + } + + function show(options) { + var isFullscreen, dialogOptions = { + removeOnClose: !0, + enableHistory: options.enableHistory, + scrollY: !1 + }; + layoutManager.tv ? (dialogOptions.size = "fullscreen", isFullscreen = !0, !0, dialogOptions.autoFocus = !0) : (dialogOptions.modal = !1, dialogOptions.entryAnimation = options.entryAnimation, dialogOptions.exitAnimation = options.exitAnimation, dialogOptions.entryAnimationDuration = options.entryAnimationDuration || 140, dialogOptions.exitAnimationDuration = options.exitAnimationDuration || 100, dialogOptions.autoFocus = !1); + var dlg = dialogHelper.createDialog(dialogOptions); + isFullscreen ? dlg.classList.add("actionsheet-fullscreen") : dlg.classList.add("actionsheet-not-fullscreen"), dlg.classList.add("actionSheet"), options.dialogClass && dlg.classList.add(options.dialogClass); + var html = "", + scrollClassName = layoutManager.tv ? "scrollY smoothScrollY hiddenScrollY" : "scrollY", + style = ""; + if (options.items.length > 20) { + style += "min-width:" + (dom.getWindowSize().innerWidth >= 300 ? 240 : 200) + "px;" + } + var i, length, option, itemIcon, renderIcon = !1, + icons = []; + for (i = 0, length = options.items.length; i < length; i++) option = options.items[i], itemIcon = option.icon || (option.selected ? "check" : null), itemIcon && (renderIcon = !0), icons.push(itemIcon || ""); + layoutManager.tv && (html += ''); + var center = options.title && !renderIcon; + center || layoutManager.tv ? html += '
' : html += '
', options.title && (html += '

', html += options.title, html += "

"), options.text && (html += '

', html += options.text, html += "

"); + var scrollerClassName = "actionSheetScroller"; + layoutManager.tv && (scrollerClassName += " actionSheetScroller-tv focuscontainer-x focuscontainer-y"), html += '
'; + var menuItemClass = "listItem listItem-button actionSheetMenuItem"; + for ((options.border || options.shaded) && (menuItemClass += " listItem-border"), options.menuItemClass && (menuItemClass += " " + options.menuItemClass), layoutManager.tv && (menuItemClass += " listItem-focusscale"), layoutManager.mobile && (menuItemClass += " actionsheet-xlargeFont"), i = 0, length = options.items.length; i < length; i++) + if (option = options.items[i], option.divider) html += '
'; + else { + var autoFocus = option.selected && layoutManager.tv ? " autoFocus" : "", + optionId = null == option.id || "" === option.id ? option.value : option.id; + html += "', itemIcon = icons[i], itemIcon ? html += '' + itemIcon + "" : renderIcon && !center && (html += ''), html += '
', html += '
', html += option.name || option.textContent || option.innerText, html += "
", option.secondaryText && (html += '
', html += option.secondaryText, html += "
"), html += "
", option.asideText && (html += '
', html += option.asideText, html += "
"), html += "" + } options.showCancel && (html += '
', html += '", html += "
"), html += "
", dlg.innerHTML = html, layoutManager.tv && centerFocus(dlg.querySelector(".actionSheetScroller"), !1, !0), dlg.querySelector(".btnCloseActionSheet") && dlg.querySelector(".btnCloseActionSheet").addEventListener("click", function() { + dialogHelper.close(dlg) + }); + var selectedId, timeout; + return options.timeout && (timeout = setTimeout(function() { + dialogHelper.close(dlg) + }, options.timeout)), new Promise(function(resolve, reject) { + var isResolved; + dlg.addEventListener("click", function(e) { + var actionSheetMenuItem = dom.parentWithClass(e.target, "actionSheetMenuItem"); + actionSheetMenuItem && (selectedId = actionSheetMenuItem.getAttribute("data-id"), options.resolveOnClick && (options.resolveOnClick.indexOf ? -1 !== options.resolveOnClick.indexOf(selectedId) && (resolve(selectedId), isResolved = !0) : (resolve(selectedId), isResolved = !0)), dialogHelper.close(dlg)) + }), dlg.addEventListener("close", function() { + layoutManager.tv && centerFocus(dlg.querySelector(".actionSheetScroller"), !1, !1), timeout && (clearTimeout(timeout), timeout = null), isResolved || (null != selectedId ? (options.callback && options.callback(selectedId), resolve(selectedId)) : reject()) + }), dialogHelper.open(dlg); + var pos = options.positionTo && "fullscreen" !== dialogOptions.size ? getPosition(options, dlg) : null; + pos && (dlg.style.position = "fixed", dlg.style.margin = 0, dlg.style.left = pos.left + "px", dlg.style.top = pos.top + "px") + }) + } + return { + show: show + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/alert/alert.js b/dashboard-ui/bower_components/emby-webcomponents/alert/alert.js index feb5ee2c5f..c9df6c23a3 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/alert/alert.js +++ b/dashboard-ui/bower_components/emby-webcomponents/alert/alert.js @@ -1 +1,18 @@ -define(["dialog","globalize"],function(dialog,globalize){"use strict";return function(text,title){var options;options="string"==typeof text?{title:title,text:text}:text;var items=[];return items.push({name:globalize.translate("sharedcomponents#ButtonGotIt"),id:"ok",type:"submit"}),options.buttons=items,dialog(options).then(function(result){return"ok"===result?Promise.resolve():Promise.reject()})}}); \ No newline at end of file +define(["dialog", "globalize"], function(dialog, globalize) { + "use strict"; + return function(text, title) { + var options; + options = "string" == typeof text ? { + title: title, + text: text + } : text; + var items = []; + return items.push({ + name: globalize.translate("sharedcomponents#ButtonGotIt"), + id: "ok", + type: "submit" + }), options.buttons = items, dialog(options).then(function(result) { + return "ok" === result ? Promise.resolve() : Promise.reject() + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/alert/nativealert.js b/dashboard-ui/bower_components/emby-webcomponents/alert/nativealert.js index f8cc5a9f6e..3d06cf10fe 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/alert/nativealert.js +++ b/dashboard-ui/bower_components/emby-webcomponents/alert/nativealert.js @@ -1 +1,14 @@ -define([],function(){"use strict";function replaceAll(str,find,replace){return str.split(find).join(replace)}return function(options){"string"==typeof options&&(options={text:options});var text=replaceAll(options.text||"","
","\n");return alert(text),Promise.resolve()}}); \ No newline at end of file +define([], function() { + "use strict"; + + function replaceAll(str, find, replace) { + return str.split(find).join(replace) + } + return function(options) { + "string" == typeof options && (options = { + text: options + }); + var text = replaceAll(options.text || "", "
", "\n"); + return alert(text), Promise.resolve() + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/alphanumericshortcuts/alphanumericshortcuts.js b/dashboard-ui/bower_components/emby-webcomponents/alphanumericshortcuts/alphanumericshortcuts.js index 679de11bbb..2b4abe9e92 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/alphanumericshortcuts/alphanumericshortcuts.js +++ b/dashboard-ui/bower_components/emby-webcomponents/alphanumericshortcuts/alphanumericshortcuts.js @@ -1 +1,59 @@ -define(["dom","focusManager"],function(dom,focusManager){"use strict";function onKeyDown(e){if(!e.ctrlKey&&!e.shiftKey&&!e.altKey){var key=e.key,chr=key?alphanumeric(key):null;chr&&(chr=chr.toString().toUpperCase(),1===chr.length&&(currentDisplayTextContainer=this.options.itemsContainer,onAlphanumericKeyPress(e,chr)))}}function alphanumeric(value){var letterNumber=/^[0-9a-zA-Z]+$/;return value.match(letterNumber)}function ensureInputDisplayElement(){inputDisplayElement||(inputDisplayElement=document.createElement("div"),inputDisplayElement.classList.add("alphanumeric-shortcut"),inputDisplayElement.classList.add("hide"),document.body.appendChild(inputDisplayElement))}function clearAlphaNumericShortcutTimeout(){alpanumericShortcutTimeout&&(clearTimeout(alpanumericShortcutTimeout),alpanumericShortcutTimeout=null)}function resetAlphaNumericShortcutTimeout(){clearAlphaNumericShortcutTimeout(),alpanumericShortcutTimeout=setTimeout(onAlphanumericShortcutTimeout,2e3)}function onAlphanumericKeyPress(e,chr){currentDisplayText.length>=3||(ensureInputDisplayElement(),currentDisplayText+=chr,inputDisplayElement.innerHTML=currentDisplayText,inputDisplayElement.classList.remove("hide"),resetAlphaNumericShortcutTimeout())}function onAlphanumericShortcutTimeout(){var value=currentDisplayText,container=currentDisplayTextContainer;currentDisplayText="",currentDisplayTextContainer=null,inputDisplayElement.innerHTML="",inputDisplayElement.classList.add("hide"),clearAlphaNumericShortcutTimeout(),selectByShortcutValue(container,value)}function selectByShortcutValue(container,value){value=value.toUpperCase();var focusElem;"#"===value&&(focusElem=container.querySelector("*[data-prefix]")),focusElem||(focusElem=container.querySelector("*[data-prefix^='"+value+"']")),focusElem&&focusManager.focus(focusElem)}function AlphaNumericShortcuts(options){this.options=options;var keyDownHandler=onKeyDown.bind(this);dom.addEventListener(window,"keydown",keyDownHandler,{passive:!0}),this.keyDownHandler=keyDownHandler}var inputDisplayElement,currentDisplayTextContainer,alpanumericShortcutTimeout,currentDisplayText="";return AlphaNumericShortcuts.prototype.destroy=function(){var keyDownHandler=this.keyDownHandler;keyDownHandler&&(dom.removeEventListener(window,"keydown",keyDownHandler,{passive:!0}),this.keyDownHandler=null),this.options=null},AlphaNumericShortcuts}); \ No newline at end of file +define(["dom", "focusManager"], function(dom, focusManager) { + "use strict"; + + function onKeyDown(e) { + if (!e.ctrlKey && !e.shiftKey && !e.altKey) { + var key = e.key, + chr = key ? alphanumeric(key) : null; + chr && (chr = chr.toString().toUpperCase(), 1 === chr.length && (currentDisplayTextContainer = this.options.itemsContainer, onAlphanumericKeyPress(e, chr))) + } + } + + function alphanumeric(value) { + var letterNumber = /^[0-9a-zA-Z]+$/; + return value.match(letterNumber) + } + + function ensureInputDisplayElement() { + inputDisplayElement || (inputDisplayElement = document.createElement("div"), inputDisplayElement.classList.add("alphanumeric-shortcut"), inputDisplayElement.classList.add("hide"), document.body.appendChild(inputDisplayElement)) + } + + function clearAlphaNumericShortcutTimeout() { + alpanumericShortcutTimeout && (clearTimeout(alpanumericShortcutTimeout), alpanumericShortcutTimeout = null) + } + + function resetAlphaNumericShortcutTimeout() { + clearAlphaNumericShortcutTimeout(), alpanumericShortcutTimeout = setTimeout(onAlphanumericShortcutTimeout, 2e3) + } + + function onAlphanumericKeyPress(e, chr) { + currentDisplayText.length >= 3 || (ensureInputDisplayElement(), currentDisplayText += chr, inputDisplayElement.innerHTML = currentDisplayText, inputDisplayElement.classList.remove("hide"), resetAlphaNumericShortcutTimeout()) + } + + function onAlphanumericShortcutTimeout() { + var value = currentDisplayText, + container = currentDisplayTextContainer; + currentDisplayText = "", currentDisplayTextContainer = null, inputDisplayElement.innerHTML = "", inputDisplayElement.classList.add("hide"), clearAlphaNumericShortcutTimeout(), selectByShortcutValue(container, value) + } + + function selectByShortcutValue(container, value) { + value = value.toUpperCase(); + var focusElem; + "#" === value && (focusElem = container.querySelector("*[data-prefix]")), focusElem || (focusElem = container.querySelector("*[data-prefix^='" + value + "']")), focusElem && focusManager.focus(focusElem) + } + + function AlphaNumericShortcuts(options) { + this.options = options; + var keyDownHandler = onKeyDown.bind(this); + dom.addEventListener(window, "keydown", keyDownHandler, { + passive: !0 + }), this.keyDownHandler = keyDownHandler + } + var inputDisplayElement, currentDisplayTextContainer, alpanumericShortcutTimeout, currentDisplayText = ""; + return AlphaNumericShortcuts.prototype.destroy = function() { + var keyDownHandler = this.keyDownHandler; + keyDownHandler && (dom.removeEventListener(window, "keydown", keyDownHandler, { + passive: !0 + }), this.keyDownHandler = null), this.options = null + }, AlphaNumericShortcuts +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/alphapicker/alphapicker.js b/dashboard-ui/bower_components/emby-webcomponents/alphapicker/alphapicker.js index 34980ad8cc..1d7fabb6f8 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/alphapicker/alphapicker.js +++ b/dashboard-ui/bower_components/emby-webcomponents/alphapicker/alphapicker.js @@ -1 +1,127 @@ -define(["focusManager","layoutManager","dom","css!./style.css","paper-icon-button-light","material-icons"],function(focusManager,layoutManager,dom){"use strict";function focus(){var scope=this,selected=scope.querySelector("."+selectedButtonClass);selected?focusManager.focus(selected):focusManager.autoFocus(scope,!0)}function getAlphaPickerButtonClassName(vertical){var alphaPickerButtonClassName="alphaPickerButton";return layoutManager.tv&&(alphaPickerButtonClassName+=" alphaPickerButton-tv"),vertical&&(alphaPickerButtonClassName+=" alphaPickerButton-vertical"),alphaPickerButtonClassName}function getLetterButton(l,vertical){return'"}function mapLetters(letters,vertical){return letters.map(function(l){return getLetterButton(l,vertical)})}function render(element,options){element.classList.add("alphaPicker"),layoutManager.tv&&element.classList.add("alphaPicker-tv");var vertical=element.classList.contains("alphaPicker-vertical");vertical||element.classList.add("focuscontainer-x");var letters,html="",alphaPickerButtonClassName=getAlphaPickerButtonClassName(vertical),rowClassName="alphaPickerRow";vertical&&(rowClassName+=" alphaPickerRow-vertical"),html+='
',"keyboard"===options.mode?html+='':(letters=["#"],html+=mapLetters(letters,vertical).join("")),letters=["A","B","C","D","E","F","G","H","I","J","K","L","M","N","O","P","Q","R","S","T","U","V","W","X","Y","Z"],html+=mapLetters(letters,vertical).join(""),"keyboard"===options.mode?(html+='',html+="
",letters=["0","1","2","3","4","5","6","7","8","9"],html+='
',html+="
",html+=mapLetters(letters,vertical).join(""),html+="
"):html+="
",element.innerHTML=html,element.classList.add("focusable"),element.focus=focus}function AlphaPicker(options){function onItemFocusTimeout(){itemFocusTimeout=null,self.value(itemFocusValue)}function onAlphaFocusTimeout(){if(alphaFocusTimeout=null,document.activeElement===alphaFocusedElement){var value=alphaFocusedElement.getAttribute("data-value");self.value(value,!0)}}function onAlphaPickerInKeyboardModeClick(e){var alphaPickerButton=dom.parentWithClass(e.target,"alphaPickerButton");if(alphaPickerButton){var value=alphaPickerButton.getAttribute("data-value");element.dispatchEvent(new CustomEvent("alphavalueclicked",{cancelable:!1,detail:{value:value}}))}}function onAlphaPickerClick(e){var alphaPickerButton=dom.parentWithClass(e.target,"alphaPickerButton");if(alphaPickerButton){var value=alphaPickerButton.getAttribute("data-value");(this._currentValue||"").toUpperCase()===value.toUpperCase()?self.value(null,!0):self.value(value,!0)}}function onAlphaPickerFocusIn(e){alphaFocusTimeout&&(clearTimeout(alphaFocusTimeout),alphaFocusTimeout=null);var alphaPickerButton=dom.parentWithClass(e.target,"alphaPickerButton");alphaPickerButton&&(alphaFocusedElement=alphaPickerButton,alphaFocusTimeout=setTimeout(onAlphaFocusTimeout,600))}function onItemsFocusIn(e){var item=dom.parentWithClass(e.target,itemClass);if(item){var prefix=item.getAttribute("data-prefix");prefix&&prefix.length&&(itemFocusValue=prefix[0],itemFocusTimeout&&clearTimeout(itemFocusTimeout),itemFocusTimeout=setTimeout(onItemFocusTimeout,100))}}var self=this;this.options=options;var itemFocusValue,itemFocusTimeout,alphaFocusedElement,alphaFocusTimeout,element=options.element,itemsContainer=options.itemsContainer,itemClass=options.itemClass;self.enabled=function(enabled){enabled?(itemsContainer&&itemsContainer.addEventListener("focus",onItemsFocusIn,!0),"keyboard"===options.mode&&element.addEventListener("click",onAlphaPickerInKeyboardModeClick),"click"!==options.valueChangeEvent?element.addEventListener("focus",onAlphaPickerFocusIn,!0):element.addEventListener("click",onAlphaPickerClick.bind(this))):(itemsContainer&&itemsContainer.removeEventListener("focus",onItemsFocusIn,!0),element.removeEventListener("click",onAlphaPickerInKeyboardModeClick),element.removeEventListener("focus",onAlphaPickerFocusIn,!0),element.removeEventListener("click",onAlphaPickerClick.bind(this)))},render(element,options),this.enabled(!0),this.visible(!0)}var selectedButtonClass="alphaPickerButton-selected";return AlphaPicker.prototype.value=function(value,applyValue){var btn,selected,element=this.options.element;if(void 0!==value)if(null!=value){if(value=value.toUpperCase(),this._currentValue=value,"keyboard"!==this.options.mode){selected=element.querySelector("."+selectedButtonClass);try{btn=element.querySelector(".alphaPickerButton[data-value='"+value+"']")}catch(err){console.log("Error in querySelector: "+err)}btn&&btn!==selected&&btn.classList.add(selectedButtonClass),selected&&selected!==btn&&selected.classList.remove(selectedButtonClass)}}else this._currentValue=value,(selected=element.querySelector("."+selectedButtonClass))&&selected.classList.remove(selectedButtonClass);return applyValue&&element.dispatchEvent(new CustomEvent("alphavaluechanged",{cancelable:!1,detail:{value:value}})),this._currentValue},AlphaPicker.prototype.on=function(name,fn){this.options.element.addEventListener(name,fn)},AlphaPicker.prototype.off=function(name,fn){this.options.element.removeEventListener(name,fn)},AlphaPicker.prototype.visible=function(visible){this.options.element.style.visibility=visible?"visible":"hidden"},AlphaPicker.prototype.values=function(){for(var element=this.options.element,elems=element.querySelectorAll(".alphaPickerButton"),values=[],i=0,length=elems.length;i' + l + "" + } + + function mapLetters(letters, vertical) { + return letters.map(function(l) { + return getLetterButton(l, vertical) + }) + } + + function render(element, options) { + element.classList.add("alphaPicker"), layoutManager.tv && element.classList.add("alphaPicker-tv"); + var vertical = element.classList.contains("alphaPicker-vertical"); + vertical || element.classList.add("focuscontainer-x"); + var letters, html = "", + alphaPickerButtonClassName = getAlphaPickerButtonClassName(vertical), + rowClassName = "alphaPickerRow"; + vertical && (rowClassName += " alphaPickerRow-vertical"), html += '
', "keyboard" === options.mode ? html += '' : (letters = ["#"], html += mapLetters(letters, vertical).join("")), letters = ["A", "B", "C", "D", "E", "F", "G", "H", "I", "J", "K", "L", "M", "N", "O", "P", "Q", "R", "S", "T", "U", "V", "W", "X", "Y", "Z"], html += mapLetters(letters, vertical).join(""), "keyboard" === options.mode ? (html += '', html += "
", letters = ["0", "1", "2", "3", "4", "5", "6", "7", "8", "9"], html += '
', html += "
", html += mapLetters(letters, vertical).join(""), html += "
") : html += "
", element.innerHTML = html, element.classList.add("focusable"), element.focus = focus + } + + function AlphaPicker(options) { + function onItemFocusTimeout() { + itemFocusTimeout = null, self.value(itemFocusValue) + } + + function onAlphaFocusTimeout() { + if (alphaFocusTimeout = null, document.activeElement === alphaFocusedElement) { + var value = alphaFocusedElement.getAttribute("data-value"); + self.value(value, !0) + } + } + + function onAlphaPickerInKeyboardModeClick(e) { + var alphaPickerButton = dom.parentWithClass(e.target, "alphaPickerButton"); + if (alphaPickerButton) { + var value = alphaPickerButton.getAttribute("data-value"); + element.dispatchEvent(new CustomEvent("alphavalueclicked", { + cancelable: !1, + detail: { + value: value + } + })) + } + } + + function onAlphaPickerClick(e) { + var alphaPickerButton = dom.parentWithClass(e.target, "alphaPickerButton"); + if (alphaPickerButton) { + var value = alphaPickerButton.getAttribute("data-value"); + (this._currentValue || "").toUpperCase() === value.toUpperCase() ? self.value(null, !0) : self.value(value, !0) + } + } + + function onAlphaPickerFocusIn(e) { + alphaFocusTimeout && (clearTimeout(alphaFocusTimeout), alphaFocusTimeout = null); + var alphaPickerButton = dom.parentWithClass(e.target, "alphaPickerButton"); + alphaPickerButton && (alphaFocusedElement = alphaPickerButton, alphaFocusTimeout = setTimeout(onAlphaFocusTimeout, 600)) + } + + function onItemsFocusIn(e) { + var item = dom.parentWithClass(e.target, itemClass); + if (item) { + var prefix = item.getAttribute("data-prefix"); + prefix && prefix.length && (itemFocusValue = prefix[0], itemFocusTimeout && clearTimeout(itemFocusTimeout), itemFocusTimeout = setTimeout(onItemFocusTimeout, 100)) + } + } + var self = this; + this.options = options; + var itemFocusValue, itemFocusTimeout, alphaFocusedElement, alphaFocusTimeout, element = options.element, + itemsContainer = options.itemsContainer, + itemClass = options.itemClass; + self.enabled = function(enabled) { + enabled ? (itemsContainer && itemsContainer.addEventListener("focus", onItemsFocusIn, !0), "keyboard" === options.mode && element.addEventListener("click", onAlphaPickerInKeyboardModeClick), "click" !== options.valueChangeEvent ? element.addEventListener("focus", onAlphaPickerFocusIn, !0) : element.addEventListener("click", onAlphaPickerClick.bind(this))) : (itemsContainer && itemsContainer.removeEventListener("focus", onItemsFocusIn, !0), element.removeEventListener("click", onAlphaPickerInKeyboardModeClick), element.removeEventListener("focus", onAlphaPickerFocusIn, !0), element.removeEventListener("click", onAlphaPickerClick.bind(this))) + }, render(element, options), this.enabled(!0), this.visible(!0) + } + var selectedButtonClass = "alphaPickerButton-selected"; + return AlphaPicker.prototype.value = function(value, applyValue) { + var btn, selected, element = this.options.element; + if (void 0 !== value) + if (null != value) { + if (value = value.toUpperCase(), this._currentValue = value, "keyboard" !== this.options.mode) { + selected = element.querySelector("." + selectedButtonClass); + try { + btn = element.querySelector(".alphaPickerButton[data-value='" + value + "']") + } catch (err) { + console.log("Error in querySelector: " + err) + } + btn && btn !== selected && btn.classList.add(selectedButtonClass), selected && selected !== btn && selected.classList.remove(selectedButtonClass) + } + } else this._currentValue = value, (selected = element.querySelector("." + selectedButtonClass)) && selected.classList.remove(selectedButtonClass); + return applyValue && element.dispatchEvent(new CustomEvent("alphavaluechanged", { + cancelable: !1, + detail: { + value: value + } + })), this._currentValue + }, AlphaPicker.prototype.on = function(name, fn) { + this.options.element.addEventListener(name, fn) + }, AlphaPicker.prototype.off = function(name, fn) { + this.options.element.removeEventListener(name, fn) + }, AlphaPicker.prototype.visible = function(visible) { + this.options.element.style.visibility = visible ? "visible" : "hidden" + }, AlphaPicker.prototype.values = function() { + for (var element = this.options.element, elems = element.querySelectorAll(".alphaPickerButton"), values = [], i = 0, length = elems.length; i < length; i++) values.push(elems[i].getAttribute("data-value")); + return values + }, AlphaPicker.prototype.focus = function() { + var element = this.options.element; + focusManager.autoFocus(element, !0) + }, AlphaPicker.prototype.destroy = function() { + var element = this.options.element; + this.enabled(!1), element.classList.remove("focuscontainer-x"), this.options = null + }, AlphaPicker +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/appfooter/appfooter.js b/dashboard-ui/bower_components/emby-webcomponents/appfooter/appfooter.js index 2f0191a5b1..e9dbffe0bb 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/appfooter/appfooter.js +++ b/dashboard-ui/bower_components/emby-webcomponents/appfooter/appfooter.js @@ -1 +1,20 @@ -define(["browser","css!./appfooter"],function(browser){"use strict";function render(options){var elem=document.createElement("div");return elem.classList.add("appfooter"),browser.chrome||elem.classList.add("appfooter-blurred"),document.body.appendChild(elem),elem}function appFooter(options){var self=this;self.element=render(options),self.add=function(elem){self.element.appendChild(elem)},self.insert=function(elem){"string"==typeof elem?self.element.insertAdjacentHTML("afterbegin",elem):self.element.insertBefore(elem,self.element.firstChild)}}return appFooter.prototype.destroy=function(){this.element=null},appFooter}); \ No newline at end of file +define(["browser", "css!./appfooter"], function(browser) { + "use strict"; + + function render(options) { + var elem = document.createElement("div"); + return elem.classList.add("appfooter"), browser.chrome || elem.classList.add("appfooter-blurred"), document.body.appendChild(elem), elem + } + + function appFooter(options) { + var self = this; + self.element = render(options), self.add = function(elem) { + self.element.appendChild(elem) + }, self.insert = function(elem) { + "string" == typeof elem ? self.element.insertAdjacentHTML("afterbegin", elem) : self.element.insertBefore(elem, self.element.firstChild) + } + } + return appFooter.prototype.destroy = function() { + this.element = null + }, appFooter +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/appsettings.js b/dashboard-ui/bower_components/emby-webcomponents/appsettings.js index ba92bded08..722bdf2aec 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/appsettings.js +++ b/dashboard-ui/bower_components/emby-webcomponents/appsettings.js @@ -1 +1,39 @@ -define(["appStorage","events"],function(appStorage,events){"use strict";function getKey(name,userId){return userId&&(name=userId+"-"+name),name}function AppSettings(){}return AppSettings.prototype.enableAutoLogin=function(val){return null!=val&&this.set("enableAutoLogin",val.toString()),"false"!==this.get("enableAutoLogin")},AppSettings.prototype.enableAutomaticBitrateDetection=function(isInNetwork,mediaType,val){var key="enableautobitratebitrate-"+mediaType+"-"+isInNetwork;return null!=val&&(isInNetwork&&"Audio"===mediaType&&(val=!0),this.set(key,val.toString())),!(!isInNetwork||"Audio"!==mediaType)||"false"!==this.get(key)},AppSettings.prototype.maxStreamingBitrate=function(isInNetwork,mediaType,val){var key="maxbitrate-"+mediaType+"-"+isInNetwork;return null!=val&&(isInNetwork&&"Audio"===mediaType||this.set(key,val)),isInNetwork&&"Audio"===mediaType?15e7:parseInt(this.get(key)||"0")||15e5},AppSettings.prototype.maxStaticMusicBitrate=function(val){void 0!==val&&this.set("maxStaticMusicBitrate",val);var defaultValue=32e4;return parseInt(this.get("maxStaticMusicBitrate")||defaultValue.toString())||defaultValue},AppSettings.prototype.maxChromecastBitrate=function(val){return null!=val&&this.set("chromecastBitrate1",val),val=this.get("chromecastBitrate1"),val?parseInt(val):null},AppSettings.prototype.syncOnlyOnWifi=function(val){return null!=val&&this.set("syncOnlyOnWifi",val.toString()),"false"!==this.get("syncOnlyOnWifi")},AppSettings.prototype.syncPath=function(val){return null!=val&&this.set("syncPath",val),this.get("syncPath")},AppSettings.prototype.cameraUploadServers=function(val){return null!=val&&this.set("cameraUploadServers",val.join(",")),val=this.get("cameraUploadServers"),val?val.split(","):[]},AppSettings.prototype.runAtStartup=function(val){return null!=val&&this.set("runatstartup",val.toString()),"true"===this.get("runatstartup")},AppSettings.prototype.set=function(name,value,userId){var currentValue=this.get(name,userId);appStorage.setItem(getKey(name,userId),value),currentValue!==value&&events.trigger(this,"change",[name])},AppSettings.prototype.get=function(name,userId){return appStorage.getItem(getKey(name,userId))},AppSettings.prototype.enableSystemExternalPlayers=function(val){return null!=val&&this.set("enableSystemExternalPlayers",val.toString()),"true"===this.get("enableSystemExternalPlayers")},new AppSettings}); \ No newline at end of file +define(["appStorage", "events"], function(appStorage, events) { + "use strict"; + + function getKey(name, userId) { + return userId && (name = userId + "-" + name), name + } + + function AppSettings() {} + return AppSettings.prototype.enableAutoLogin = function(val) { + return null != val && this.set("enableAutoLogin", val.toString()), "false" !== this.get("enableAutoLogin") + }, AppSettings.prototype.enableAutomaticBitrateDetection = function(isInNetwork, mediaType, val) { + var key = "enableautobitratebitrate-" + mediaType + "-" + isInNetwork; + return null != val && (isInNetwork && "Audio" === mediaType && (val = !0), this.set(key, val.toString())), !(!isInNetwork || "Audio" !== mediaType) || "false" !== this.get(key) + }, AppSettings.prototype.maxStreamingBitrate = function(isInNetwork, mediaType, val) { + var key = "maxbitrate-" + mediaType + "-" + isInNetwork; + return null != val && (isInNetwork && "Audio" === mediaType || this.set(key, val)), isInNetwork && "Audio" === mediaType ? 15e7 : parseInt(this.get(key) || "0") || 15e5 + }, AppSettings.prototype.maxStaticMusicBitrate = function(val) { + void 0 !== val && this.set("maxStaticMusicBitrate", val); + var defaultValue = 32e4; + return parseInt(this.get("maxStaticMusicBitrate") || defaultValue.toString()) || defaultValue + }, AppSettings.prototype.maxChromecastBitrate = function(val) { + return null != val && this.set("chromecastBitrate1", val), val = this.get("chromecastBitrate1"), val ? parseInt(val) : null + }, AppSettings.prototype.syncOnlyOnWifi = function(val) { + return null != val && this.set("syncOnlyOnWifi", val.toString()), "false" !== this.get("syncOnlyOnWifi") + }, AppSettings.prototype.syncPath = function(val) { + return null != val && this.set("syncPath", val), this.get("syncPath") + }, AppSettings.prototype.cameraUploadServers = function(val) { + return null != val && this.set("cameraUploadServers", val.join(",")), val = this.get("cameraUploadServers"), val ? val.split(",") : [] + }, AppSettings.prototype.runAtStartup = function(val) { + return null != val && this.set("runatstartup", val.toString()), "true" === this.get("runatstartup") + }, AppSettings.prototype.set = function(name, value, userId) { + var currentValue = this.get(name, userId); + appStorage.setItem(getKey(name, userId), value), currentValue !== value && events.trigger(this, "change", [name]) + }, AppSettings.prototype.get = function(name, userId) { + return appStorage.getItem(getKey(name, userId)) + }, AppSettings.prototype.enableSystemExternalPlayers = function(val) { + return null != val && this.set("enableSystemExternalPlayers", val.toString()), "true" === this.get("enableSystemExternalPlayers") + }, new AppSettings +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/backdrop/backdrop.js b/dashboard-ui/bower_components/emby-webcomponents/backdrop/backdrop.js index 8f79dc5aab..2f42ccd347 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/backdrop/backdrop.js +++ b/dashboard-ui/bower_components/emby-webcomponents/backdrop/backdrop.js @@ -1 +1,150 @@ -define(["browser","connectionManager","playbackManager","dom","css!./style"],function(browser,connectionManager,playbackManager,dom){"use strict";function enableAnimation(elem){return!browser.slow}function enableRotation(){return!browser.tv&&!browser.firefox}function Backdrop(){}function getBackdropContainer(){return backdropContainer||(backdropContainer=document.querySelector(".backdropContainer")),backdropContainer||(backdropContainer=document.createElement("div"),backdropContainer.classList.add("backdropContainer"),document.body.insertBefore(backdropContainer,document.body.firstChild)),backdropContainer}function clearBackdrop(clearAll){clearRotation(),currentLoadingBackdrop&&(currentLoadingBackdrop.destroy(),currentLoadingBackdrop=null),getBackdropContainer().innerHTML="",clearAll&&(hasExternalBackdrop=!1),internalBackdrop(!1)}function getBackgroundContainer(){return backgroundContainer||(backgroundContainer=document.querySelector(".backgroundContainer")),backgroundContainer}function setBackgroundContainerBackgroundEnabled(){hasInternalBackdrop||hasExternalBackdrop?getBackgroundContainer().classList.add("withBackdrop"):getBackgroundContainer().classList.remove("withBackdrop")}function internalBackdrop(enabled){hasInternalBackdrop=enabled,setBackgroundContainerBackgroundEnabled()}function externalBackdrop(enabled){hasExternalBackdrop=enabled,setBackgroundContainerBackgroundEnabled()}function setBackdropImage(url){currentLoadingBackdrop&&(currentLoadingBackdrop.destroy(),currentLoadingBackdrop=null);var elem=getBackdropContainer(),existingBackdropImage=elem.querySelector(".displayingBackdropImage");if(existingBackdropImage&&existingBackdropImage.getAttribute("data-url")===url){if(existingBackdropImage.getAttribute("data-url")===url)return;existingBackdropImage.classList.remove("displayingBackdropImage")}var instance=new Backdrop;instance.load(url,elem,existingBackdropImage),currentLoadingBackdrop=instance}function getBackdropMaxWidth(){var width=dom.getWindowSize().innerWidth;if(-1!==standardWidths.indexOf(width))return width;return width=100*Math.floor(width/100),Math.min(width,1920)}function getItemImageUrls(item,imageOptions){imageOptions=imageOptions||{};var apiClient=connectionManager.getApiClient(item.ServerId);return item.BackdropImageTags&&item.BackdropImageTags.length>0?item.BackdropImageTags.map(function(imgTag,index){return apiClient.getScaledImageUrl(item.BackdropItemId||item.Id,Object.assign(imageOptions,{type:"Backdrop",tag:imgTag,maxWidth:getBackdropMaxWidth(),index:index}))}):item.ParentBackdropItemId&&item.ParentBackdropImageTags&&item.ParentBackdropImageTags.length?item.ParentBackdropImageTags.map(function(imgTag,index){return apiClient.getScaledImageUrl(item.ParentBackdropItemId,Object.assign(imageOptions,{type:"Backdrop",tag:imgTag,maxWidth:getBackdropMaxWidth(),index:index}))}):[]}function getImageUrls(items,imageOptions){for(var list=[],onImg=function(img){list.push(img)},i=0,length=items.length;i1&&!1!==enableImageRotation&&enableRotation()&&(rotationInterval=setInterval(onRotationInterval,24e3)),onRotationInterval())}function onRotationInterval(){if(!playbackManager.isPlayingLocally(["Video"])){var newIndex=currentRotationIndex+1;newIndex>=currentRotatingImages.length&&(newIndex=0),currentRotationIndex=newIndex,setBackdropImage(currentRotatingImages[newIndex])}}function clearRotation(){var interval=rotationInterval;interval&&clearInterval(interval),rotationInterval=null,currentRotatingImages=[],currentRotationIndex=-1}function setBackdrop(url,imageOptions){url&&"string"!=typeof url&&(url=getImageUrls([url],imageOptions)[0]),url?(clearRotation(),setBackdropImage(url)):clearBackdrop()}Backdrop.prototype.load=function(url,parent,existingBackdropImage){var img=new Image,self=this;img.onload=function(){if(!self.isDestroyed){var backdropImage=document.createElement("div");if(backdropImage.classList.add("backdropImage"),backdropImage.classList.add("displayingBackdropImage"),backdropImage.style.backgroundImage="url('"+url+"')",backdropImage.setAttribute("data-url",url),backdropImage.classList.add("backdropImageFadeIn"),parent.appendChild(backdropImage),!enableAnimation(backdropImage))return existingBackdropImage&&existingBackdropImage.parentNode&&existingBackdropImage.parentNode.removeChild(existingBackdropImage),void internalBackdrop(!0);var onAnimationComplete=function(){dom.removeEventListener(backdropImage,dom.whichAnimationEvent(),onAnimationComplete,{once:!0}),backdropImage===self.currentAnimatingElement&&(self.currentAnimatingElement=null),existingBackdropImage&&existingBackdropImage.parentNode&&existingBackdropImage.parentNode.removeChild(existingBackdropImage)};dom.addEventListener(backdropImage,dom.whichAnimationEvent(),onAnimationComplete,{once:!0}),internalBackdrop(!0)}},img.src=url},Backdrop.prototype.cancelAnimation=function(){var elem=this.currentAnimatingElement;elem&&(elem.classList.remove("backdropImageFadeIn"),this.currentAnimatingElement=null)},Backdrop.prototype.destroy=function(){this.isDestroyed=!0,this.cancelAnimation()};var backdropContainer,backgroundContainer,hasInternalBackdrop,hasExternalBackdrop,currentLoadingBackdrop,rotationInterval,standardWidths=[480,720,1280,1440,1920],currentRotatingImages=[],currentRotationIndex=-1;return{setBackdrops:setBackdrops,setBackdrop:setBackdrop,clear:clearBackdrop,externalBackdrop:externalBackdrop}}); \ No newline at end of file +define(["browser", "connectionManager", "playbackManager", "dom", "css!./style"], function(browser, connectionManager, playbackManager, dom) { + "use strict"; + + function enableAnimation(elem) { + return !browser.slow + } + + function enableRotation() { + return !browser.tv && !browser.firefox + } + + function Backdrop() {} + + function getBackdropContainer() { + return backdropContainer || (backdropContainer = document.querySelector(".backdropContainer")), backdropContainer || (backdropContainer = document.createElement("div"), backdropContainer.classList.add("backdropContainer"), document.body.insertBefore(backdropContainer, document.body.firstChild)), backdropContainer + } + + function clearBackdrop(clearAll) { + clearRotation(), currentLoadingBackdrop && (currentLoadingBackdrop.destroy(), currentLoadingBackdrop = null), getBackdropContainer().innerHTML = "", clearAll && (hasExternalBackdrop = !1), internalBackdrop(!1) + } + + function getBackgroundContainer() { + return backgroundContainer || (backgroundContainer = document.querySelector(".backgroundContainer")), backgroundContainer + } + + function setBackgroundContainerBackgroundEnabled() { + hasInternalBackdrop || hasExternalBackdrop ? getBackgroundContainer().classList.add("withBackdrop") : getBackgroundContainer().classList.remove("withBackdrop") + } + + function internalBackdrop(enabled) { + hasInternalBackdrop = enabled, setBackgroundContainerBackgroundEnabled() + } + + function externalBackdrop(enabled) { + hasExternalBackdrop = enabled, setBackgroundContainerBackgroundEnabled() + } + + function setBackdropImage(url) { + currentLoadingBackdrop && (currentLoadingBackdrop.destroy(), currentLoadingBackdrop = null); + var elem = getBackdropContainer(), + existingBackdropImage = elem.querySelector(".displayingBackdropImage"); + if (existingBackdropImage && existingBackdropImage.getAttribute("data-url") === url) { + if (existingBackdropImage.getAttribute("data-url") === url) return; + existingBackdropImage.classList.remove("displayingBackdropImage") + } + var instance = new Backdrop; + instance.load(url, elem, existingBackdropImage), currentLoadingBackdrop = instance + } + + function getBackdropMaxWidth() { + var width = dom.getWindowSize().innerWidth; + if (-1 !== standardWidths.indexOf(width)) return width; + return width = 100 * Math.floor(width / 100), Math.min(width, 1920) + } + + function getItemImageUrls(item, imageOptions) { + imageOptions = imageOptions || {}; + var apiClient = connectionManager.getApiClient(item.ServerId); + return item.BackdropImageTags && item.BackdropImageTags.length > 0 ? item.BackdropImageTags.map(function(imgTag, index) { + return apiClient.getScaledImageUrl(item.BackdropItemId || item.Id, Object.assign(imageOptions, { + type: "Backdrop", + tag: imgTag, + maxWidth: getBackdropMaxWidth(), + index: index + })) + }) : item.ParentBackdropItemId && item.ParentBackdropImageTags && item.ParentBackdropImageTags.length ? item.ParentBackdropImageTags.map(function(imgTag, index) { + return apiClient.getScaledImageUrl(item.ParentBackdropItemId, Object.assign(imageOptions, { + type: "Backdrop", + tag: imgTag, + maxWidth: getBackdropMaxWidth(), + index: index + })) + }) : [] + } + + function getImageUrls(items, imageOptions) { + for (var list = [], onImg = function(img) { + list.push(img) + }, i = 0, length = items.length; i < length; i++) { + getItemImageUrls(items[i], imageOptions).forEach(onImg) + } + return list + } + + function arraysEqual(a, b) { + if (a === b) return !0; + if (null == a || null == b) return !1; + if (a.length !== b.length) return !1; + for (var i = 0; i < a.length; ++i) + if (a[i] !== b[i]) return !1; + return !0 + } + + function setBackdrops(items, imageOptions, enableImageRotation) { + var images = getImageUrls(items, imageOptions); + images.length ? startRotation(images, enableImageRotation) : clearBackdrop() + } + + function startRotation(images, enableImageRotation) { + arraysEqual(images, currentRotatingImages) || (clearRotation(), currentRotatingImages = images, currentRotationIndex = -1, images.length > 1 && !1 !== enableImageRotation && enableRotation() && (rotationInterval = setInterval(onRotationInterval, 24e3)), onRotationInterval()) + } + + function onRotationInterval() { + if (!playbackManager.isPlayingLocally(["Video"])) { + var newIndex = currentRotationIndex + 1; + newIndex >= currentRotatingImages.length && (newIndex = 0), currentRotationIndex = newIndex, setBackdropImage(currentRotatingImages[newIndex]) + } + } + + function clearRotation() { + var interval = rotationInterval; + interval && clearInterval(interval), rotationInterval = null, currentRotatingImages = [], currentRotationIndex = -1 + } + + function setBackdrop(url, imageOptions) { + url && "string" != typeof url && (url = getImageUrls([url], imageOptions)[0]), url ? (clearRotation(), setBackdropImage(url)) : clearBackdrop() + } + Backdrop.prototype.load = function(url, parent, existingBackdropImage) { + var img = new Image, + self = this; + img.onload = function() { + if (!self.isDestroyed) { + var backdropImage = document.createElement("div"); + if (backdropImage.classList.add("backdropImage"), backdropImage.classList.add("displayingBackdropImage"), backdropImage.style.backgroundImage = "url('" + url + "')", backdropImage.setAttribute("data-url", url), backdropImage.classList.add("backdropImageFadeIn"), parent.appendChild(backdropImage), !enableAnimation(backdropImage)) return existingBackdropImage && existingBackdropImage.parentNode && existingBackdropImage.parentNode.removeChild(existingBackdropImage), void internalBackdrop(!0); + var onAnimationComplete = function() { + dom.removeEventListener(backdropImage, dom.whichAnimationEvent(), onAnimationComplete, { + once: !0 + }), backdropImage === self.currentAnimatingElement && (self.currentAnimatingElement = null), existingBackdropImage && existingBackdropImage.parentNode && existingBackdropImage.parentNode.removeChild(existingBackdropImage) + }; + dom.addEventListener(backdropImage, dom.whichAnimationEvent(), onAnimationComplete, { + once: !0 + }), internalBackdrop(!0) + } + }, img.src = url + }, Backdrop.prototype.cancelAnimation = function() { + var elem = this.currentAnimatingElement; + elem && (elem.classList.remove("backdropImageFadeIn"), this.currentAnimatingElement = null) + }, Backdrop.prototype.destroy = function() { + this.isDestroyed = !0, this.cancelAnimation() + }; + var backdropContainer, backgroundContainer, hasInternalBackdrop, hasExternalBackdrop, currentLoadingBackdrop, rotationInterval, standardWidths = [480, 720, 1280, 1440, 1920], + currentRotatingImages = [], + currentRotationIndex = -1; + return { + setBackdrops: setBackdrops, + setBackdrop: setBackdrop, + clear: clearBackdrop, + externalBackdrop: externalBackdrop + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/browser.js b/dashboard-ui/bower_components/emby-webcomponents/browser.js index 6df8da22e6..c718dfb6d0 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/browser.js +++ b/dashboard-ui/bower_components/emby-webcomponents/browser.js @@ -1 +1,69 @@ -define([],function(){"use strict";function supportsCssAnimation(allowPrefix){if(allowPrefix){if(!0===_supportsCssAnimationWithPrefix||!1===_supportsCssAnimationWithPrefix)return _supportsCssAnimationWithPrefix}else if(!0===_supportsCssAnimation||!1===_supportsCssAnimation)return _supportsCssAnimation;var animation=!1,domPrefixes=["Webkit","O","Moz"],pfx="",elm=document.createElement("div");if(void 0!==elm.style.animationName&&(animation=!0),!1===animation&&allowPrefix)for(var i=0;i2&&(version=versionMatch[2]),version=version||match[2]||"0";var versionMajor=parseInt(version.split(".")[0]);return isNaN(versionMajor)&&(versionMajor=0),{browser:browser,version:version,platform:platform_match[0]||"",versionMajor:versionMajor}}(userAgent),browser={};return matched.browser&&(browser[matched.browser]=!0,browser.version=matched.version,browser.versionMajor=matched.versionMajor),matched.platform&&(browser[matched.platform]=!0),browser.chrome||browser.msie||browser.edge||browser.opera||-1===userAgent.toLowerCase().indexOf("webkit")||(browser.safari=!0),-1!==userAgent.toLowerCase().indexOf("playstation 4")&&(browser.ps4=!0,browser.tv=!0),function(userAgent){for(var terms=["mobi","ipad","iphone","ipod","silk","gt-p1000","nexus 7","kindle fire","opera mini"],lower=userAgent.toLowerCase(),i=0,length=terms.length;i 2 && (version = versionMatch[2]), version = version || match[2] || "0"; + var versionMajor = parseInt(version.split(".")[0]); + return isNaN(versionMajor) && (versionMajor = 0), { + browser: browser, + version: version, + platform: platform_match[0] || "", + versionMajor: versionMajor + } + }(userAgent), + browser = {}; + return matched.browser && (browser[matched.browser] = !0, browser.version = matched.version, browser.versionMajor = matched.versionMajor), matched.platform && (browser[matched.platform] = !0), browser.chrome || browser.msie || browser.edge || browser.opera || -1 === userAgent.toLowerCase().indexOf("webkit") || (browser.safari = !0), -1 !== userAgent.toLowerCase().indexOf("playstation 4") && (browser.ps4 = !0, browser.tv = !0), + function(userAgent) { + for (var terms = ["mobi", "ipad", "iphone", "ipod", "silk", "gt-p1000", "nexus 7", "kindle fire", "opera mini"], lower = userAgent.toLowerCase(), i = 0, length = terms.length; i < length; i++) + if (-1 !== lower.indexOf(terms[i])) return !0; + return !1 + }(userAgent) && (browser.mobile = !0), browser.xboxOne = -1 !== userAgent.toLowerCase().indexOf("xbox"), browser.animate = "undefined" != typeof document && null != document.documentElement.animate, browser.tizen = -1 !== userAgent.toLowerCase().indexOf("tizen") || null != self.tizen, browser.web0s = -1 !== userAgent.toLowerCase().indexOf("Web0S".toLowerCase()), browser.edgeUwp = browser.edge && (-1 !== userAgent.toLowerCase().indexOf("msapphost") || -1 !== userAgent.toLowerCase().indexOf("webview")), browser.tizen || (browser.orsay = -1 !== userAgent.toLowerCase().indexOf("smarthub")), browser.edgeUwp && (browser.edge = !0), browser.tv = function() { + var userAgent = navigator.userAgent.toLowerCase(); + return -1 !== userAgent.indexOf("tv") || (-1 !== userAgent.indexOf("samsungbrowser") || (-1 !== userAgent.indexOf("nintendo") || (-1 !== userAgent.indexOf("viera") || -1 !== userAgent.indexOf("webos")))) + }(), browser.operaTv = browser.tv && -1 !== userAgent.toLowerCase().indexOf("opr/"), + function(prop, value) { + if ("undefined" == typeof window) return !1; + if (value = 2 === arguments.length ? value : "inherit", "CSS" in window && "supports" in window.CSS) return window.CSS.supports(prop, value); + if ("supportsCSS" in window) return window.supportsCSS(prop, value); + try { + var camel = prop.replace(/-([a-z]|[0-9])/gi, function(all, letter) { + return (letter + "").toUpperCase() + }), + support = camel in el.style, + el = document.createElement("div"); + return el.style.cssText = prop + ":" + value, support && "" !== el.style[camel] + } catch (err) { + return !1 + } + }("display", "flex") || (browser.noFlex = !0), (browser.mobile || browser.tv) && (browser.slow = !0), "undefined" != typeof document && ("ontouchstart" in window || window.DocumentTouch && document instanceof DocumentTouch) && (browser.touch = !0), browser.keyboard = function(browser) { + return !!browser.touch || (!!browser.xboxOne || (!!browser.ps4 || (!!browser.edgeUwp || !!browser.tv))) + }(browser), browser.supportsCssAnimation = supportsCssAnimation, browser.osx = -1 !== userAgent.toLowerCase().indexOf("os x"), browser.iOS = browser.ipad || browser.iphone || browser.ipod, browser.iOS && (browser.iOSVersion = function() { + if (/iP(hone|od|ad)/.test(navigator.platform)) { + var v = navigator.appVersion.match(/OS (\d+)_(\d+)_?(\d+)?/); + return [parseInt(v[1], 10), parseInt(v[2], 10), parseInt(v[3] || 0, 10)] + } + }(), browser.iOSVersion = browser.iOSVersion[0] + browser.iOSVersion[1] / 10), browser.chromecast = browser.chrome && -1 !== userAgent.toLowerCase().indexOf("crkey"), browser +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/browserdeviceprofile.js b/dashboard-ui/bower_components/emby-webcomponents/browserdeviceprofile.js index 8381066c21..f4178a750a 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/browserdeviceprofile.js +++ b/dashboard-ui/bower_components/emby-webcomponents/browserdeviceprofile.js @@ -1 +1,384 @@ -define(["browser"],function(browser){"use strict";function canPlayH264(videoTestElement){return!(!videoTestElement.canPlayType||!videoTestElement.canPlayType('video/mp4; codecs="avc1.42E01E, mp4a.40.2"').replace(/no/,""))}function canPlayH265(videoTestElement,options){if(browser.tizen||browser.orsay||browser.xboxOne||browser.web0s||options.supportsHevc)return!0;var userAgent=navigator.userAgent.toLowerCase();if(browser.chromecast){if(-1!==userAgent.indexOf("aarch64"))return!0}return!!(browser.iOS&&(browser.iOSVersion||0)>=11)||!(!videoTestElement.canPlayType||!videoTestElement.canPlayType('video/hevc; codecs="hevc, aac"').replace(/no/,""))}function supportsTextTracks(){return!(!browser.tizen&&!browser.orsay)||(null==_supportsTextTracks&&(_supportsTextTracks=null!=document.createElement("video").textTracks),_supportsTextTracks)}function canPlayHls(src){return null==_canPlayHls&&(_canPlayHls=canPlayNativeHls()||canPlayHlsWithMSE()),_canPlayHls}function canPlayNativeHls(){if(browser.tizen||browser.orsay)return!0;var media=document.createElement("video");return!(!media.canPlayType("application/x-mpegURL").replace(/no/,"")&&!media.canPlayType("application/vnd.apple.mpegURL").replace(/no/,""))}function canPlayHlsWithMSE(){return null!=window.MediaSource}function canPlayAudioFormat(format){var typeString;if("flac"===format){if(browser.tizen||browser.orsay||browser.web0s)return!0;if(browser.edgeUwp)return!0}else if("wma"===format){if(browser.tizen||browser.orsay)return!0;if(browser.edgeUwp)return!0}else{if("opus"===format)return typeString='audio/ogg; codecs="opus"',!!document.createElement("audio").canPlayType(typeString).replace(/no/,"");if("mp2"===format)return!1}if("webma"===format)typeString="audio/webm";else if("mp2"===format)typeString="audio/mpeg";else if("ogg"===format||"oga"===format){if(browser.chrome)return!1;typeString="audio/"+format}else typeString="audio/"+format;return!!document.createElement("audio").canPlayType(typeString).replace(/no/,"")}function testCanPlayMkv(videoTestElement){if(browser.tizen||browser.orsay||browser.web0s)return!0;if(videoTestElement.canPlayType("video/x-matroska").replace(/no/,"")||videoTestElement.canPlayType("video/mkv").replace(/no/,""))return!0;var userAgent=navigator.userAgent.toLowerCase();return browser.chrome?!browser.operaTv&&(-1===userAgent.indexOf("vivaldi")&&-1===userAgent.indexOf("opera")):!!browser.edgeUwp}function testCanPlayTs(){return browser.tizen||browser.orsay||browser.web0s||browser.edgeUwp}function supportsMpeg2Video(){return browser.orsay||browser.tizen||browser.edgeUwp||browser.web0s}function supportsVc1(){return browser.orsay||browser.tizen||browser.edgeUwp||browser.web0s}function getDirectPlayProfileForVideoContainer(container,videoAudioCodecs,videoTestElement,options){var supported=!1,profileContainer=container,videoCodecs=[];switch(container){case"asf":supported=browser.tizen||browser.orsay||browser.edgeUwp,videoAudioCodecs=[];break;case"avi":supported=browser.tizen||browser.orsay||browser.edgeUwp;break;case"mpg":case"mpeg":supported=browser.edgeUwp||browser.tizen||browser.orsay;break;case"flv":supported=browser.tizen||browser.orsay;break;case"3gp":case"mts":case"trp":case"vob":case"vro":supported=browser.tizen||browser.orsay;break;case"mov":supported=browser.tizen||browser.orsay||browser.chrome||browser.edgeUwp,videoCodecs.push("h264");break;case"m2ts":supported=browser.tizen||browser.orsay||browser.web0s||browser.edgeUwp,videoCodecs.push("h264"),supportsVc1()&&videoCodecs.push("vc1"),supportsMpeg2Video()&&videoCodecs.push("mpeg2video");break;case"wmv":supported=browser.tizen||browser.orsay||browser.web0s||browser.edgeUwp,videoAudioCodecs=[];break;case"ts":supported=testCanPlayTs(),videoCodecs.push("h264"),canPlayH265(videoTestElement,options)&&(videoCodecs.push("h265"),videoCodecs.push("hevc")),supportsVc1()&&videoCodecs.push("vc1"),supportsMpeg2Video()&&videoCodecs.push("mpeg2video"),profileContainer="ts,mpegts"}return supported?{Container:profileContainer,Type:"Video",VideoCodec:videoCodecs.join(","),AudioCodec:videoAudioCodecs.join(",")}:null}function getGlobalMaxVideoBitrate(){var userAgent=navigator.userAgent.toLowerCase();if(browser.chromecast){return-1!==userAgent.indexOf("aarch64")?null:self.screen&&self.screen.width>=3800?null:3e7}var isTizenFhd=!1;if(browser.tizen)try{isTizenFhd=!webapis.productinfo.isUdPanelSupported(),console.log("isTizenFhd = "+isTizenFhd)}catch(error){console.log("isUdPanelSupported() error code = "+error.code)}return browser.ps4?8e6:browser.xboxOne?12e6:browser.edgeUwp?null:browser.tizen&&isTizenFhd?2e7:null}function supportsAc3(videoTestElement){return!!(browser.edgeUwp||browser.tizen||browser.orsay||browser.web0s)||videoTestElement.canPlayType('audio/mp4; codecs="ac-3"').replace(/no/,"")&&!browser.osx&&!browser.iOS}function supportsEac3(videoTestElement){return!!(browser.tizen||browser.orsay||browser.web0s)||videoTestElement.canPlayType('audio/mp4; codecs="ec-3"').replace(/no/,"")}var _supportsTextTracks,_canPlayHls;return function(options){options=options||{};var physicalAudioChannels=options.audioChannels||(browser.tv||browser.ps4||browser.xboxOne?6:2),videoTestElement=document.createElement("video"),canPlayVp8=videoTestElement.canPlayType('video/webm; codecs="vp8"').replace(/no/,""),canPlayVp9=videoTestElement.canPlayType('video/webm; codecs="vp9"').replace(/no/,""),webmAudioCodecs=["vorbis"],canPlayMkv=testCanPlayMkv(videoTestElement),profile={};profile.MaxStreamingBitrate=12e7,profile.MaxStaticBitrate=1e8,profile.MusicStreamingTranscodingBitrate=Math.min(12e7,192e3),profile.DirectPlayProfiles=[];var videoAudioCodecs=[],hlsVideoAudioCodecs=[],supportsMp3VideoAudio=videoTestElement.canPlayType('video/mp4; codecs="avc1.640029, mp4a.69"').replace(/no/,"")||videoTestElement.canPlayType('video/mp4; codecs="avc1.640029, mp4a.6B"').replace(/no/,""),supportsMp2VideoAudio=browser.edgeUwp||browser.tizen||browser.orsay||browser.web0s,maxVideoWidth=browser.xboxOne&&self.screen?self.screen.width:null;options.maxVideoWidth&&(maxVideoWidth=options.maxVideoWidth);var canPlayAacVideoAudio=videoTestElement.canPlayType('video/mp4; codecs="avc1.640029, mp4a.40.2"').replace(/no/,"");if(canPlayAacVideoAudio&&browser.chromecast&&physicalAudioChannels<=2&&videoAudioCodecs.push("aac"),supportsAc3(videoTestElement)){videoAudioCodecs.push("ac3");var eAc3=supportsEac3(videoTestElement);eAc3&&videoAudioCodecs.push("eac3");(!browser.edge||!browser.touch||browser.edgeUwp)&&(hlsVideoAudioCodecs.push("ac3"),eAc3&&hlsVideoAudioCodecs.push("eac3"))}canPlayAacVideoAudio&&browser.chromecast&&-1===videoAudioCodecs.indexOf("aac")&&videoAudioCodecs.push("aac"),supportsMp3VideoAudio&&(videoAudioCodecs.push("mp3"),browser.ps4||physicalAudioChannels<=2&&hlsVideoAudioCodecs.push("mp3")),canPlayAacVideoAudio&&(-1===videoAudioCodecs.indexOf("aac")&&videoAudioCodecs.push("aac"),hlsVideoAudioCodecs.push("aac")),supportsMp3VideoAudio&&(browser.ps4||-1===hlsVideoAudioCodecs.indexOf("mp3")&&hlsVideoAudioCodecs.push("mp3")),supportsMp2VideoAudio&&videoAudioCodecs.push("mp2");var supportsDts=browser.tizen||browser.orsay||browser.web0s||options.supportsDts;if(self.tizen&&self.tizen.systeminfo){var v=tizen.systeminfo.getCapability("http://tizen.org/feature/platform.version");v&&parseFloat(v)>=parseFloat("4.0")&&(supportsDts=!1)}supportsDts&&(videoAudioCodecs.push("dca"),videoAudioCodecs.push("dts")),(browser.tizen||browser.orsay||browser.web0s)&&(videoAudioCodecs.push("pcm_s16le"),videoAudioCodecs.push("pcm_s24le")),options.supportsTrueHd&&videoAudioCodecs.push("truehd"),(browser.tizen||browser.orsay)&&videoAudioCodecs.push("aac_latm"),canPlayAudioFormat("opus")&&(videoAudioCodecs.push("opus"),hlsVideoAudioCodecs.push("opus"),webmAudioCodecs.push("opus")),canPlayAudioFormat("flac")&&videoAudioCodecs.push("flac"),videoAudioCodecs=videoAudioCodecs.filter(function(c){return-1===(options.disableVideoAudioCodecs||[]).indexOf(c)}),hlsVideoAudioCodecs=hlsVideoAudioCodecs.filter(function(c){return-1===(options.disableHlsVideoAudioCodecs||[]).indexOf(c)});var mp4VideoCodecs=[],hlsVideoCodecs=[];canPlayH264(videoTestElement)&&(mp4VideoCodecs.push("h264"),hlsVideoCodecs.push("h264")),canPlayH265(videoTestElement,options)&&(mp4VideoCodecs.push("h265"),mp4VideoCodecs.push("hevc"),(browser.tizen||browser.web0s)&&(hlsVideoCodecs.push("h265"),hlsVideoCodecs.push("hevc"))),supportsMpeg2Video()&&mp4VideoCodecs.push("mpeg2video"),supportsVc1()&&mp4VideoCodecs.push("vc1"),(browser.tizen||browser.orsay)&&mp4VideoCodecs.push("msmpeg4v2"),canPlayVp8&&mp4VideoCodecs.push("vp8"),canPlayVp9&&mp4VideoCodecs.push("vp9"),(canPlayVp8||browser.tizen||browser.orsay)&&videoAudioCodecs.push("vorbis"),mp4VideoCodecs.length&&profile.DirectPlayProfiles.push({Container:"mp4,m4v",Type:"Video",VideoCodec:mp4VideoCodecs.join(","),AudioCodec:videoAudioCodecs.join(",")}),canPlayMkv&&mp4VideoCodecs.length&&profile.DirectPlayProfiles.push({Container:"mkv",Type:"Video",VideoCodec:mp4VideoCodecs.join(","),AudioCodec:videoAudioCodecs.join(",")}),["m2ts","wmv","ts","asf","avi","mpg","mpeg","flv","3gp","mts","trp","vob","vro","mov"].map(function(container){return getDirectPlayProfileForVideoContainer(container,videoAudioCodecs,videoTestElement,options)}).filter(function(i){return null!=i}).forEach(function(i){profile.DirectPlayProfiles.push(i)}),["opus","mp3","mp2","aac","flac","alac","webma","wma","wav","ogg","oga"].filter(canPlayAudioFormat).forEach(function(audioFormat){"mp2"===audioFormat?profile.DirectPlayProfiles.push({Container:"mp2,mp3",Type:"Audio",AudioCodec:audioFormat}):"mp3"===audioFormat?profile.DirectPlayProfiles.push({Container:audioFormat,Type:"Audio",AudioCodec:audioFormat}):profile.DirectPlayProfiles.push({Container:"webma"===audioFormat?"webma,webm":audioFormat,Type:"Audio"}),"aac"!==audioFormat&&"alac"!==audioFormat||profile.DirectPlayProfiles.push({Container:"m4a",AudioCodec:audioFormat,Type:"Audio"})}),canPlayVp8&&profile.DirectPlayProfiles.push({Container:"webm",Type:"Video",AudioCodec:webmAudioCodecs.join(","),VideoCodec:"VP8"}),canPlayVp9&&profile.DirectPlayProfiles.push({Container:"webm",Type:"Video",AudioCodec:webmAudioCodecs.join(","),VideoCodec:"VP9"}),profile.TranscodingProfiles=[];var hlsBreakOnNonKeyFrames=!(!(browser.iOS||browser.osx||browser.edge)&&canPlayNativeHls());canPlayHls()&&!1!==browser.enableHlsAudio&&profile.TranscodingProfiles.push({Container:!canPlayNativeHls()||browser.edge||browser.android?"ts":"aac",Type:"Audio",AudioCodec:"aac",Context:"Streaming",Protocol:"hls",MaxAudioChannels:physicalAudioChannels.toString(),MinSegments:browser.iOS||browser.osx?"2":"1",BreakOnNonKeyFrames:hlsBreakOnNonKeyFrames}),["aac","mp3","opus","wav"].filter(canPlayAudioFormat).forEach(function(audioFormat){profile.TranscodingProfiles.push({Container:audioFormat,Type:"Audio",AudioCodec:audioFormat,Context:"Streaming",Protocol:"http",MaxAudioChannels:physicalAudioChannels.toString()})}),["opus","mp3","aac","wav"].filter(canPlayAudioFormat).forEach(function(audioFormat){profile.TranscodingProfiles.push({Container:audioFormat,Type:"Audio",AudioCodec:audioFormat,Context:"Static",Protocol:"http",MaxAudioChannels:physicalAudioChannels.toString()})}),!canPlayMkv||browser.tizen||browser.orsay||!1===options.enableMkvProgressive||profile.TranscodingProfiles.push({Container:"mkv",Type:"Video",AudioCodec:videoAudioCodecs.join(","),VideoCodec:mp4VideoCodecs.join(","),Context:"Streaming",MaxAudioChannels:physicalAudioChannels.toString(),CopyTimestamps:!0}),canPlayMkv&&profile.TranscodingProfiles.push({Container:"mkv",Type:"Video",AudioCodec:videoAudioCodecs.join(","),VideoCodec:mp4VideoCodecs.join(","),Context:"Static",MaxAudioChannels:physicalAudioChannels.toString(),CopyTimestamps:!0}),canPlayHls()&&!1!==options.enableHls&&profile.TranscodingProfiles.push({Container:"ts",Type:"Video",AudioCodec:hlsVideoAudioCodecs.join(","),VideoCodec:hlsVideoCodecs.join(","),Context:"Streaming",Protocol:"hls",MaxAudioChannels:physicalAudioChannels.toString(),MinSegments:browser.iOS||browser.osx?"2":"1",BreakOnNonKeyFrames:hlsBreakOnNonKeyFrames}),canPlayVp8&&profile.TranscodingProfiles.push({Container:"webm",Type:"Video",AudioCodec:"vorbis",VideoCodec:"vpx",Context:"Streaming",Protocol:"http",MaxAudioChannels:physicalAudioChannels.toString()}),profile.TranscodingProfiles.push({Container:"mp4",Type:"Video",AudioCodec:videoAudioCodecs.join(","),VideoCodec:"h264",Context:"Static",Protocol:"http"}),profile.ContainerProfiles=[],profile.CodecProfiles=[];var supportsSecondaryAudio=browser.tizen||browser.orsay||videoTestElement.audioTracks,aacCodecProfileConditions=[];videoTestElement.canPlayType('video/mp4; codecs="avc1.640029, mp4a.40.5"').replace(/no/,"")||aacCodecProfileConditions.push({Condition:"NotEquals",Property:"AudioProfile",Value:"HE-AAC"}),supportsSecondaryAudio||aacCodecProfileConditions.push({Condition:"Equals",Property:"IsSecondaryAudio",Value:"false",IsRequired:"false"}),browser.chromecast&&aacCodecProfileConditions.push({Condition:"LessThanEqual",Property:"AudioChannels",Value:"2",IsRequired:!0}),aacCodecProfileConditions.length&&profile.CodecProfiles.push({Type:"VideoAudio",Codec:"aac",Conditions:aacCodecProfileConditions}),supportsSecondaryAudio||profile.CodecProfiles.push({Type:"VideoAudio",Conditions:[{Condition:"Equals",Property:"IsSecondaryAudio",Value:"false",IsRequired:"false"}]});var maxH264Level=browser.chromecast?42:51,h264Profiles="high|main|baseline|constrained baseline";maxH264Level>=51&&browser.chrome&&!browser.osx&&(h264Profiles+="|high 10"),profile.CodecProfiles.push({Type:"Video",Codec:"h264",Conditions:[{Condition:"NotEquals",Property:"IsAnamorphic",Value:"true",IsRequired:!1},{Condition:"EqualsAny",Property:"VideoProfile",Value:h264Profiles},{Condition:"LessThanEqual",Property:"VideoLevel",Value:maxH264Level.toString()}]}),browser.edgeUwp||browser.tizen||browser.orsay||browser.web0s,maxVideoWidth&&profile.CodecProfiles[profile.CodecProfiles.length-1].Conditions.push({Condition:"LessThanEqual",Property:"Width",Value:maxVideoWidth.toString(),IsRequired:!1});var globalMaxVideoBitrate=(getGlobalMaxVideoBitrate()||"").toString(),h264MaxVideoBitrate=globalMaxVideoBitrate;h264MaxVideoBitrate&&profile.CodecProfiles[profile.CodecProfiles.length-1].Conditions.push({Condition:"LessThanEqual",Property:"VideoBitrate",Value:h264MaxVideoBitrate,IsRequired:!0});var globalVideoConditions=[];return globalMaxVideoBitrate&&globalVideoConditions.push({Condition:"LessThanEqual",Property:"VideoBitrate",Value:globalMaxVideoBitrate}),maxVideoWidth&&globalVideoConditions.push({Condition:"LessThanEqual",Property:"Width",Value:maxVideoWidth.toString(),IsRequired:!1}),globalVideoConditions.length&&profile.CodecProfiles.push({Type:"Video",Conditions:globalVideoConditions}),browser.chromecast&&profile.CodecProfiles.push({Type:"Audio",Codec:"flac",Conditions:[{Condition:"LessThanEqual",Property:"AudioSampleRate",Value:"96000"}]}),profile.SubtitleProfiles=[],supportsTextTracks()&&profile.SubtitleProfiles.push({Format:"vtt",Method:"External"}),profile.ResponseProfiles=[],profile.ResponseProfiles.push({Type:"Video",Container:"m4v",MimeType:"video/mp4"}),profile}}); \ No newline at end of file +define(["browser"], function(browser) { + "use strict"; + + function canPlayH264(videoTestElement) { + return !(!videoTestElement.canPlayType || !videoTestElement.canPlayType('video/mp4; codecs="avc1.42E01E, mp4a.40.2"').replace(/no/, "")) + } + + function canPlayH265(videoTestElement, options) { + if (browser.tizen || browser.orsay || browser.xboxOne || browser.web0s || options.supportsHevc) return !0; + var userAgent = navigator.userAgent.toLowerCase(); + if (browser.chromecast) { + if (-1 !== userAgent.indexOf("aarch64")) return !0 + } + return !!(browser.iOS && (browser.iOSVersion || 0) >= 11) || !(!videoTestElement.canPlayType || !videoTestElement.canPlayType('video/hevc; codecs="hevc, aac"').replace(/no/, "")) + } + + function supportsTextTracks() { + return !(!browser.tizen && !browser.orsay) || (null == _supportsTextTracks && (_supportsTextTracks = null != document.createElement("video").textTracks), _supportsTextTracks) + } + + function canPlayHls(src) { + return null == _canPlayHls && (_canPlayHls = canPlayNativeHls() || canPlayHlsWithMSE()), _canPlayHls + } + + function canPlayNativeHls() { + if (browser.tizen || browser.orsay) return !0; + var media = document.createElement("video"); + return !(!media.canPlayType("application/x-mpegURL").replace(/no/, "") && !media.canPlayType("application/vnd.apple.mpegURL").replace(/no/, "")) + } + + function canPlayHlsWithMSE() { + return null != window.MediaSource + } + + function canPlayAudioFormat(format) { + var typeString; + if ("flac" === format) { + if (browser.tizen || browser.orsay || browser.web0s) return !0; + if (browser.edgeUwp) return !0 + } else if ("wma" === format) { + if (browser.tizen || browser.orsay) return !0; + if (browser.edgeUwp) return !0 + } else { + if ("opus" === format) return typeString = 'audio/ogg; codecs="opus"', !!document.createElement("audio").canPlayType(typeString).replace(/no/, ""); + if ("mp2" === format) return !1 + } + if ("webma" === format) typeString = "audio/webm"; + else if ("mp2" === format) typeString = "audio/mpeg"; + else if ("ogg" === format || "oga" === format) { + if (browser.chrome) return !1; + typeString = "audio/" + format + } else typeString = "audio/" + format; + return !!document.createElement("audio").canPlayType(typeString).replace(/no/, "") + } + + function testCanPlayMkv(videoTestElement) { + if (browser.tizen || browser.orsay || browser.web0s) return !0; + if (videoTestElement.canPlayType("video/x-matroska").replace(/no/, "") || videoTestElement.canPlayType("video/mkv").replace(/no/, "")) return !0; + var userAgent = navigator.userAgent.toLowerCase(); + return browser.chrome ? !browser.operaTv && (-1 === userAgent.indexOf("vivaldi") && -1 === userAgent.indexOf("opera")) : !!browser.edgeUwp + } + + function testCanPlayTs() { + return browser.tizen || browser.orsay || browser.web0s || browser.edgeUwp + } + + function supportsMpeg2Video() { + return browser.orsay || browser.tizen || browser.edgeUwp || browser.web0s + } + + function supportsVc1() { + return browser.orsay || browser.tizen || browser.edgeUwp || browser.web0s + } + + function getDirectPlayProfileForVideoContainer(container, videoAudioCodecs, videoTestElement, options) { + var supported = !1, + profileContainer = container, + videoCodecs = []; + switch (container) { + case "asf": + supported = browser.tizen || browser.orsay || browser.edgeUwp, videoAudioCodecs = []; + break; + case "avi": + supported = browser.tizen || browser.orsay || browser.edgeUwp; + break; + case "mpg": + case "mpeg": + supported = browser.edgeUwp || browser.tizen || browser.orsay; + break; + case "flv": + supported = browser.tizen || browser.orsay; + break; + case "3gp": + case "mts": + case "trp": + case "vob": + case "vro": + supported = browser.tizen || browser.orsay; + break; + case "mov": + supported = browser.tizen || browser.orsay || browser.chrome || browser.edgeUwp, videoCodecs.push("h264"); + break; + case "m2ts": + supported = browser.tizen || browser.orsay || browser.web0s || browser.edgeUwp, videoCodecs.push("h264"), supportsVc1() && videoCodecs.push("vc1"), supportsMpeg2Video() && videoCodecs.push("mpeg2video"); + break; + case "wmv": + supported = browser.tizen || browser.orsay || browser.web0s || browser.edgeUwp, videoAudioCodecs = []; + break; + case "ts": + supported = testCanPlayTs(), videoCodecs.push("h264"), canPlayH265(videoTestElement, options) && (videoCodecs.push("h265"), videoCodecs.push("hevc")), supportsVc1() && videoCodecs.push("vc1"), supportsMpeg2Video() && videoCodecs.push("mpeg2video"), profileContainer = "ts,mpegts" + } + return supported ? { + Container: profileContainer, + Type: "Video", + VideoCodec: videoCodecs.join(","), + AudioCodec: videoAudioCodecs.join(",") + } : null + } + + function getGlobalMaxVideoBitrate() { + var userAgent = navigator.userAgent.toLowerCase(); + if (browser.chromecast) { + return -1 !== userAgent.indexOf("aarch64") ? null : self.screen && self.screen.width >= 3800 ? null : 3e7 + } + var isTizenFhd = !1; + if (browser.tizen) try { + isTizenFhd = !webapis.productinfo.isUdPanelSupported(), console.log("isTizenFhd = " + isTizenFhd) + } catch (error) { + console.log("isUdPanelSupported() error code = " + error.code) + } + return browser.ps4 ? 8e6 : browser.xboxOne ? 12e6 : browser.edgeUwp ? null : browser.tizen && isTizenFhd ? 2e7 : null + } + + function supportsAc3(videoTestElement) { + return !!(browser.edgeUwp || browser.tizen || browser.orsay || browser.web0s) || videoTestElement.canPlayType('audio/mp4; codecs="ac-3"').replace(/no/, "") && !browser.osx && !browser.iOS + } + + function supportsEac3(videoTestElement) { + return !!(browser.tizen || browser.orsay || browser.web0s) || videoTestElement.canPlayType('audio/mp4; codecs="ec-3"').replace(/no/, "") + } + var _supportsTextTracks, _canPlayHls; + return function(options) { + options = options || {}; + var physicalAudioChannels = options.audioChannels || (browser.tv || browser.ps4 || browser.xboxOne ? 6 : 2), + videoTestElement = document.createElement("video"), + canPlayVp8 = videoTestElement.canPlayType('video/webm; codecs="vp8"').replace(/no/, ""), + canPlayVp9 = videoTestElement.canPlayType('video/webm; codecs="vp9"').replace(/no/, ""), + webmAudioCodecs = ["vorbis"], + canPlayMkv = testCanPlayMkv(videoTestElement), + profile = {}; + profile.MaxStreamingBitrate = 12e7, profile.MaxStaticBitrate = 1e8, profile.MusicStreamingTranscodingBitrate = Math.min(12e7, 192e3), profile.DirectPlayProfiles = []; + var videoAudioCodecs = [], + hlsVideoAudioCodecs = [], + supportsMp3VideoAudio = videoTestElement.canPlayType('video/mp4; codecs="avc1.640029, mp4a.69"').replace(/no/, "") || videoTestElement.canPlayType('video/mp4; codecs="avc1.640029, mp4a.6B"').replace(/no/, ""), + supportsMp2VideoAudio = browser.edgeUwp || browser.tizen || browser.orsay || browser.web0s, + maxVideoWidth = browser.xboxOne && self.screen ? self.screen.width : null; + options.maxVideoWidth && (maxVideoWidth = options.maxVideoWidth); + var canPlayAacVideoAudio = videoTestElement.canPlayType('video/mp4; codecs="avc1.640029, mp4a.40.2"').replace(/no/, ""); + if (canPlayAacVideoAudio && browser.chromecast && physicalAudioChannels <= 2 && videoAudioCodecs.push("aac"), supportsAc3(videoTestElement)) { + videoAudioCodecs.push("ac3"); + var eAc3 = supportsEac3(videoTestElement); + eAc3 && videoAudioCodecs.push("eac3"); + (!browser.edge || !browser.touch || browser.edgeUwp) && (hlsVideoAudioCodecs.push("ac3"), eAc3 && hlsVideoAudioCodecs.push("eac3")) + } + canPlayAacVideoAudio && browser.chromecast && -1 === videoAudioCodecs.indexOf("aac") && videoAudioCodecs.push("aac"), supportsMp3VideoAudio && (videoAudioCodecs.push("mp3"), browser.ps4 || physicalAudioChannels <= 2 && hlsVideoAudioCodecs.push("mp3")), canPlayAacVideoAudio && (-1 === videoAudioCodecs.indexOf("aac") && videoAudioCodecs.push("aac"), hlsVideoAudioCodecs.push("aac")), supportsMp3VideoAudio && (browser.ps4 || -1 === hlsVideoAudioCodecs.indexOf("mp3") && hlsVideoAudioCodecs.push("mp3")), supportsMp2VideoAudio && videoAudioCodecs.push("mp2"); + var supportsDts = browser.tizen || browser.orsay || browser.web0s || options.supportsDts; + if (self.tizen && self.tizen.systeminfo) { + var v = tizen.systeminfo.getCapability("http://tizen.org/feature/platform.version"); + v && parseFloat(v) >= parseFloat("4.0") && (supportsDts = !1) + } + supportsDts && (videoAudioCodecs.push("dca"), videoAudioCodecs.push("dts")), (browser.tizen || browser.orsay || browser.web0s) && (videoAudioCodecs.push("pcm_s16le"), videoAudioCodecs.push("pcm_s24le")), options.supportsTrueHd && videoAudioCodecs.push("truehd"), (browser.tizen || browser.orsay) && videoAudioCodecs.push("aac_latm"), canPlayAudioFormat("opus") && (videoAudioCodecs.push("opus"), hlsVideoAudioCodecs.push("opus"), webmAudioCodecs.push("opus")), canPlayAudioFormat("flac") && videoAudioCodecs.push("flac"), videoAudioCodecs = videoAudioCodecs.filter(function(c) { + return -1 === (options.disableVideoAudioCodecs || []).indexOf(c) + }), hlsVideoAudioCodecs = hlsVideoAudioCodecs.filter(function(c) { + return -1 === (options.disableHlsVideoAudioCodecs || []).indexOf(c) + }); + var mp4VideoCodecs = [], + hlsVideoCodecs = []; + canPlayH264(videoTestElement) && (mp4VideoCodecs.push("h264"), hlsVideoCodecs.push("h264")), canPlayH265(videoTestElement, options) && (mp4VideoCodecs.push("h265"), mp4VideoCodecs.push("hevc"), (browser.tizen || browser.web0s) && (hlsVideoCodecs.push("h265"), hlsVideoCodecs.push("hevc"))), supportsMpeg2Video() && mp4VideoCodecs.push("mpeg2video"), supportsVc1() && mp4VideoCodecs.push("vc1"), (browser.tizen || browser.orsay) && mp4VideoCodecs.push("msmpeg4v2"), canPlayVp8 && mp4VideoCodecs.push("vp8"), canPlayVp9 && mp4VideoCodecs.push("vp9"), (canPlayVp8 || browser.tizen || browser.orsay) && videoAudioCodecs.push("vorbis"), mp4VideoCodecs.length && profile.DirectPlayProfiles.push({ + Container: "mp4,m4v", + Type: "Video", + VideoCodec: mp4VideoCodecs.join(","), + AudioCodec: videoAudioCodecs.join(",") + }), canPlayMkv && mp4VideoCodecs.length && profile.DirectPlayProfiles.push({ + Container: "mkv", + Type: "Video", + VideoCodec: mp4VideoCodecs.join(","), + AudioCodec: videoAudioCodecs.join(",") + }), ["m2ts", "wmv", "ts", "asf", "avi", "mpg", "mpeg", "flv", "3gp", "mts", "trp", "vob", "vro", "mov"].map(function(container) { + return getDirectPlayProfileForVideoContainer(container, videoAudioCodecs, videoTestElement, options) + }).filter(function(i) { + return null != i + }).forEach(function(i) { + profile.DirectPlayProfiles.push(i) + }), ["opus", "mp3", "mp2", "aac", "flac", "alac", "webma", "wma", "wav", "ogg", "oga"].filter(canPlayAudioFormat).forEach(function(audioFormat) { + "mp2" === audioFormat ? profile.DirectPlayProfiles.push({ + Container: "mp2,mp3", + Type: "Audio", + AudioCodec: audioFormat + }) : "mp3" === audioFormat ? profile.DirectPlayProfiles.push({ + Container: audioFormat, + Type: "Audio", + AudioCodec: audioFormat + }) : profile.DirectPlayProfiles.push({ + Container: "webma" === audioFormat ? "webma,webm" : audioFormat, + Type: "Audio" + }), "aac" !== audioFormat && "alac" !== audioFormat || profile.DirectPlayProfiles.push({ + Container: "m4a", + AudioCodec: audioFormat, + Type: "Audio" + }) + }), canPlayVp8 && profile.DirectPlayProfiles.push({ + Container: "webm", + Type: "Video", + AudioCodec: webmAudioCodecs.join(","), + VideoCodec: "VP8" + }), canPlayVp9 && profile.DirectPlayProfiles.push({ + Container: "webm", + Type: "Video", + AudioCodec: webmAudioCodecs.join(","), + VideoCodec: "VP9" + }), profile.TranscodingProfiles = []; + var hlsBreakOnNonKeyFrames = !(!(browser.iOS || browser.osx || browser.edge) && canPlayNativeHls()); + canPlayHls() && !1 !== browser.enableHlsAudio && profile.TranscodingProfiles.push({ + Container: !canPlayNativeHls() || browser.edge || browser.android ? "ts" : "aac", + Type: "Audio", + AudioCodec: "aac", + Context: "Streaming", + Protocol: "hls", + MaxAudioChannels: physicalAudioChannels.toString(), + MinSegments: browser.iOS || browser.osx ? "2" : "1", + BreakOnNonKeyFrames: hlsBreakOnNonKeyFrames + }), ["aac", "mp3", "opus", "wav"].filter(canPlayAudioFormat).forEach(function(audioFormat) { + profile.TranscodingProfiles.push({ + Container: audioFormat, + Type: "Audio", + AudioCodec: audioFormat, + Context: "Streaming", + Protocol: "http", + MaxAudioChannels: physicalAudioChannels.toString() + }) + }), ["opus", "mp3", "aac", "wav"].filter(canPlayAudioFormat).forEach(function(audioFormat) { + profile.TranscodingProfiles.push({ + Container: audioFormat, + Type: "Audio", + AudioCodec: audioFormat, + Context: "Static", + Protocol: "http", + MaxAudioChannels: physicalAudioChannels.toString() + }) + }), !canPlayMkv || browser.tizen || browser.orsay || !1 === options.enableMkvProgressive || profile.TranscodingProfiles.push({ + Container: "mkv", + Type: "Video", + AudioCodec: videoAudioCodecs.join(","), + VideoCodec: mp4VideoCodecs.join(","), + Context: "Streaming", + MaxAudioChannels: physicalAudioChannels.toString(), + CopyTimestamps: !0 + }), canPlayMkv && profile.TranscodingProfiles.push({ + Container: "mkv", + Type: "Video", + AudioCodec: videoAudioCodecs.join(","), + VideoCodec: mp4VideoCodecs.join(","), + Context: "Static", + MaxAudioChannels: physicalAudioChannels.toString(), + CopyTimestamps: !0 + }), canPlayHls() && !1 !== options.enableHls && profile.TranscodingProfiles.push({ + Container: "ts", + Type: "Video", + AudioCodec: hlsVideoAudioCodecs.join(","), + VideoCodec: hlsVideoCodecs.join(","), + Context: "Streaming", + Protocol: "hls", + MaxAudioChannels: physicalAudioChannels.toString(), + MinSegments: browser.iOS || browser.osx ? "2" : "1", + BreakOnNonKeyFrames: hlsBreakOnNonKeyFrames + }), canPlayVp8 && profile.TranscodingProfiles.push({ + Container: "webm", + Type: "Video", + AudioCodec: "vorbis", + VideoCodec: "vpx", + Context: "Streaming", + Protocol: "http", + MaxAudioChannels: physicalAudioChannels.toString() + }), profile.TranscodingProfiles.push({ + Container: "mp4", + Type: "Video", + AudioCodec: videoAudioCodecs.join(","), + VideoCodec: "h264", + Context: "Static", + Protocol: "http" + }), profile.ContainerProfiles = [], profile.CodecProfiles = []; + var supportsSecondaryAudio = browser.tizen || browser.orsay || videoTestElement.audioTracks, + aacCodecProfileConditions = []; + videoTestElement.canPlayType('video/mp4; codecs="avc1.640029, mp4a.40.5"').replace(/no/, "") || aacCodecProfileConditions.push({ + Condition: "NotEquals", + Property: "AudioProfile", + Value: "HE-AAC" + }), supportsSecondaryAudio || aacCodecProfileConditions.push({ + Condition: "Equals", + Property: "IsSecondaryAudio", + Value: "false", + IsRequired: "false" + }), browser.chromecast && aacCodecProfileConditions.push({ + Condition: "LessThanEqual", + Property: "AudioChannels", + Value: "2", + IsRequired: !0 + }), aacCodecProfileConditions.length && profile.CodecProfiles.push({ + Type: "VideoAudio", + Codec: "aac", + Conditions: aacCodecProfileConditions + }), supportsSecondaryAudio || profile.CodecProfiles.push({ + Type: "VideoAudio", + Conditions: [{ + Condition: "Equals", + Property: "IsSecondaryAudio", + Value: "false", + IsRequired: "false" + }] + }); + var maxH264Level = browser.chromecast ? 42 : 51, + h264Profiles = "high|main|baseline|constrained baseline"; + maxH264Level >= 51 && browser.chrome && !browser.osx && (h264Profiles += "|high 10"), profile.CodecProfiles.push({ + Type: "Video", + Codec: "h264", + Conditions: [{ + Condition: "NotEquals", + Property: "IsAnamorphic", + Value: "true", + IsRequired: !1 + }, { + Condition: "EqualsAny", + Property: "VideoProfile", + Value: h264Profiles + }, { + Condition: "LessThanEqual", + Property: "VideoLevel", + Value: maxH264Level.toString() + }] + }), browser.edgeUwp || browser.tizen || browser.orsay || browser.web0s, maxVideoWidth && profile.CodecProfiles[profile.CodecProfiles.length - 1].Conditions.push({ + Condition: "LessThanEqual", + Property: "Width", + Value: maxVideoWidth.toString(), + IsRequired: !1 + }); + var globalMaxVideoBitrate = (getGlobalMaxVideoBitrate() || "").toString(), + h264MaxVideoBitrate = globalMaxVideoBitrate; + h264MaxVideoBitrate && profile.CodecProfiles[profile.CodecProfiles.length - 1].Conditions.push({ + Condition: "LessThanEqual", + Property: "VideoBitrate", + Value: h264MaxVideoBitrate, + IsRequired: !0 + }); + var globalVideoConditions = []; + return globalMaxVideoBitrate && globalVideoConditions.push({ + Condition: "LessThanEqual", + Property: "VideoBitrate", + Value: globalMaxVideoBitrate + }), maxVideoWidth && globalVideoConditions.push({ + Condition: "LessThanEqual", + Property: "Width", + Value: maxVideoWidth.toString(), + IsRequired: !1 + }), globalVideoConditions.length && profile.CodecProfiles.push({ + Type: "Video", + Conditions: globalVideoConditions + }), browser.chromecast && profile.CodecProfiles.push({ + Type: "Audio", + Codec: "flac", + Conditions: [{ + Condition: "LessThanEqual", + Property: "AudioSampleRate", + Value: "96000" + }] + }), profile.SubtitleProfiles = [], supportsTextTracks() && profile.SubtitleProfiles.push({ + Format: "vtt", + Method: "External" + }), profile.ResponseProfiles = [], profile.ResponseProfiles.push({ + Type: "Video", + Container: "m4v", + MimeType: "video/mp4" + }), profile + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/cardbuilder/cardbuilder.js b/dashboard-ui/bower_components/emby-webcomponents/cardbuilder/cardbuilder.js index b13ef8b45a..ffb42171bc 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/cardbuilder/cardbuilder.js +++ b/dashboard-ui/bower_components/emby-webcomponents/cardbuilder/cardbuilder.js @@ -1,2 +1,515 @@ -define(["datetime","imageLoader","connectionManager","itemHelper","focusManager","indicators","globalize","layoutManager","apphost","dom","browser","playbackManager","itemShortcuts","css!./card","paper-icon-button-light","programStyles"],function(datetime,imageLoader,connectionManager,itemHelper,focusManager,indicators,globalize,layoutManager,appHost,dom,browser,playbackManager,itemShortcuts){"use strict";function getCardsHtml(items,options){return 1===arguments.length&&(options=arguments[0],items=options.items),buildCardsHtmlInternal(items,options)}function getPostersPerRow(shape,screenWidth,isOrientationLandscape){switch(shape){case"portrait":return layoutManager.tv?5.9999999988:screenWidth>=2200?10:screenWidth>=1920?9.000000000009:screenWidth>=1600?8:screenWidth>=1400?7.0000000000021:screenWidth>=1200?5.9999999988:screenWidth>=800?5:screenWidth>=700?4:3.0000000003;case"square":return layoutManager.tv?5.9999999988:screenWidth>=2200?10:screenWidth>=1920?9.000000000009:screenWidth>=1600?8:screenWidth>=1400?7.0000000000021:screenWidth>=1200?5.9999999988:screenWidth>=800?5:screenWidth>=700?4:screenWidth>=500?3.0000000003:2;case"banner":return screenWidth>=2200?4:screenWidth>=1200?3.0000000003:screenWidth>=800?2:1;case"backdrop":return layoutManager.tv?4:screenWidth>=2500?6:screenWidth>=1600?5:screenWidth>=1200?4:screenWidth>=770?3:screenWidth>=420?2:1;case"smallBackdrop":return screenWidth>=1600?8:screenWidth>=1400?7.000000000007001:screenWidth>=1200?6:screenWidth>=1e3?5:screenWidth>=800?4:screenWidth>=500?3.0000000003:2;case"overflowSmallBackdrop":return layoutManager.tv?100/18.9:isOrientationLandscape?screenWidth>=800?100/15.5:100/23.3:screenWidth>=540?100/30:100/72;case"overflowPortrait":return layoutManager.tv?100/15.5:isOrientationLandscape?screenWidth>=1700?100/11.6:100/15.5:screenWidth>=1400?100/15:screenWidth>=1200?100/18:screenWidth>=760?100/23:screenWidth>=400?100/31.5:100/42;case"overflowSquare":return layoutManager.tv?100/15.5:isOrientationLandscape?screenWidth>=1700?100/11.6:100/15.5:screenWidth>=1400?100/15:screenWidth>=1200?100/18:screenWidth>=760?100/23:screenWidth>=540?100/31.5:100/42;case"overflowBackdrop":return layoutManager.tv?100/23.3:isOrientationLandscape?screenWidth>=1700?100/18.5:100/23.3:screenWidth>=1800?100/23.5:screenWidth>=1400?100/30:screenWidth>=760?2.5:screenWidth>=640?100/56:100/72;default:return 4}}function isResizable(windowWidth){var screen=window.screen;if(screen){if(screen.availWidth-windowWidth>20)return!0}return!1}function getImageWidth(shape,screenWidth,isOrientationLandscape){var imagesPerRow=getPostersPerRow(shape,screenWidth,isOrientationLandscape),shapeWidth=screenWidth/imagesPerRow;return Math.round(shapeWidth)}function setCardData(items,options){options.shape=options.shape||"auto";var primaryImageAspectRatio=imageLoader.getPrimaryImageAspectRatio(items);if("auto"===options.shape||"autohome"===options.shape||"autooverflow"===options.shape||"autoVertical"===options.shape){var requestedShape=options.shape;options.shape=null,primaryImageAspectRatio&&(primaryImageAspectRatio>=3?(options.shape="banner",options.coverImage=!0):options.shape=primaryImageAspectRatio>=1.33?"autooverflow"===requestedShape?"overflowBackdrop":"backdrop":primaryImageAspectRatio>.71?"autooverflow"===requestedShape?"overflowSquare":"square":"autooverflow"===requestedShape?"overflowPortrait":"portrait"),options.shape||(options.shape=options.defaultShape||("autooverflow"===requestedShape?"overflowSquare":"square"))}if("auto"===options.preferThumb&&(options.preferThumb="backdrop"===options.shape||"overflowBackdrop"===options.shape),options.uiAspect=getDesiredAspect(options.shape),options.primaryImageAspectRatio=primaryImageAspectRatio,!options.width&&options.widths&&(options.width=options.widths[options.shape]),options.rows&&"number"!=typeof options.rows&&(options.rows=options.rows[options.shape]),!options.width){var screenWidth=dom.getWindowSize().innerWidth,screenHeight=dom.getWindowSize().innerHeight;if(isResizable(screenWidth)){screenWidth=100*Math.floor(screenWidth/100)}options.width=getImageWidth(options.shape,screenWidth,screenWidth>1.3*screenHeight)}}function buildCardsHtmlInternal(items,options){var isVertical;"autoVertical"===options.shape&&(isVertical=!0),setCardData(items,options);var currentIndexValue,hasOpenRow,hasOpenSection,apiClient,lastServerId,i,length,html="",itemsInRow=0,sectionTitleTagName=options.sectionTitleTagName||"div";for(i=0,length=items.length;i=.5?.5:0)+"+":null);newIndexValue!==currentIndexValue&&(hasOpenRow&&(html+="
",hasOpenRow=!1,itemsInRow=0),hasOpenSection&&(html+="",isVertical&&(html+=""),hasOpenSection=!1),html+=isVertical?'
':'
',html+="<"+sectionTitleTagName+' class="sectionTitle">'+newIndexValue+"",isVertical&&(html+='
'),currentIndexValue=newIndexValue,hasOpenSection=!0)}options.rows&&0===itemsInRow&&(hasOpenRow&&(html+="
",hasOpenRow=!1),html+='
',hasOpenRow=!0),html+=buildCard(i,item,apiClient,options),itemsInRow++,options.rows&&itemsInRow>=options.rows&&(html+="
",hasOpenRow=!1,itemsInRow=0)}hasOpenRow&&(html+="
"),hasOpenSection&&(html+="
",isVertical&&(html+=""));var cardFooterHtml="";for(i=0,length=options.lines||0;i ':'
 
';return html}function getDesiredAspect(shape){if(shape){if(shape=shape.toLowerCase(),-1!==shape.indexOf("portrait"))return 2/3;if(-1!==shape.indexOf("backdrop"))return 16/9;if(-1!==shape.indexOf("square"))return 1;if(-1!==shape.indexOf("banner"))return 1e3/185}return null}function getCardImageUrl(item,apiClient,options,shape){item=item.ProgramInfo||item;var width=options.width,height=null,primaryImageAspectRatio=item.PrimaryImageAspectRatio,forceName=!1,imgUrl=null,coverImage=!1,uiAspect=null;return options.preferThumb&&item.ImageTags&&item.ImageTags.Thumb?imgUrl=apiClient.getScaledImageUrl(item.Id,{type:"Thumb",maxWidth:width,tag:item.ImageTags.Thumb}):(options.preferBanner||"banner"===shape)&&item.ImageTags&&item.ImageTags.Banner?imgUrl=apiClient.getScaledImageUrl(item.Id,{type:"Banner",maxWidth:width,tag:item.ImageTags.Banner}):options.preferDisc&&item.ImageTags&&item.ImageTags.Disc?imgUrl=apiClient.getScaledImageUrl(item.Id,{type:"Disc",maxWidth:width,tag:item.ImageTags.Disc}):options.preferLogo&&item.ImageTags&&item.ImageTags.Logo?imgUrl=apiClient.getScaledImageUrl(item.Id,{type:"Logo",maxWidth:width,tag:item.ImageTags.Logo}):options.preferLogo&&item.ParentLogoImageTag&&item.ParentLogoItemId?imgUrl=apiClient.getScaledImageUrl(item.ParentLogoItemId,{type:"Logo",maxWidth:width,tag:item.ParentLogoImageTag}):options.preferThumb&&item.SeriesThumbImageTag&&!1!==options.inheritThumb?imgUrl=apiClient.getScaledImageUrl(item.SeriesId,{type:"Thumb",maxWidth:width,tag:item.SeriesThumbImageTag}):options.preferThumb&&item.ParentThumbItemId&&!1!==options.inheritThumb&&"Photo"!==item.MediaType?imgUrl=apiClient.getScaledImageUrl(item.ParentThumbItemId,{type:"Thumb",maxWidth:width,tag:item.ParentThumbImageTag}):options.preferThumb&&item.BackdropImageTags&&item.BackdropImageTags.length?(imgUrl=apiClient.getScaledImageUrl(item.Id,{type:"Backdrop",maxWidth:width,tag:item.BackdropImageTags[0]}),forceName=!0):options.preferThumb&&item.ParentBackdropImageTags&&item.ParentBackdropImageTags.length&&!1!==options.inheritThumb&&"Episode"===item.Type?imgUrl=apiClient.getScaledImageUrl(item.ParentBackdropItemId,{type:"Backdrop",maxWidth:width,tag:item.ParentBackdropImageTags[0]}):item.ImageTags&&item.ImageTags.Primary?(height=width&&primaryImageAspectRatio?Math.round(width/primaryImageAspectRatio):null,imgUrl=apiClient.getScaledImageUrl(item.Id,{type:"Primary",maxHeight:height,maxWidth:width,tag:item.ImageTags.Primary}),options.preferThumb&&!1!==options.showTitle&&(forceName=!0),primaryImageAspectRatio&&(uiAspect=getDesiredAspect(shape))&&(coverImage=Math.abs(primaryImageAspectRatio-uiAspect)/uiAspect<=.2)):item.PrimaryImageTag?(height=width&&primaryImageAspectRatio?Math.round(width/primaryImageAspectRatio):null,imgUrl=apiClient.getScaledImageUrl(item.PrimaryImageItemId||item.Id||item.ItemId,{type:"Primary",maxHeight:height,maxWidth:width,tag:item.PrimaryImageTag}),options.preferThumb&&!1!==options.showTitle&&(forceName=!0),primaryImageAspectRatio&&(uiAspect=getDesiredAspect(shape))&&(coverImage=Math.abs(primaryImageAspectRatio-uiAspect)/uiAspect<=.2)):item.ParentPrimaryImageTag?imgUrl=apiClient.getScaledImageUrl(item.ParentPrimaryImageItemId,{type:"Primary",maxWidth:width,tag:item.ParentPrimaryImageTag}):item.SeriesPrimaryImageTag?imgUrl=apiClient.getScaledImageUrl(item.SeriesId,{type:"Primary",maxWidth:width,tag:item.SeriesPrimaryImageTag}):item.AlbumId&&item.AlbumPrimaryImageTag?(width=primaryImageAspectRatio?Math.round(height*primaryImageAspectRatio):null,imgUrl=apiClient.getScaledImageUrl(item.AlbumId,{type:"Primary",maxHeight:height,maxWidth:width,tag:item.AlbumPrimaryImageTag}),primaryImageAspectRatio&&(uiAspect=getDesiredAspect(shape))&&(coverImage=Math.abs(primaryImageAspectRatio-uiAspect)/uiAspect<=.2)):"Season"===item.Type&&item.ImageTags&&item.ImageTags.Thumb?imgUrl=apiClient.getScaledImageUrl(item.Id,{type:"Thumb",maxWidth:width,tag:item.ImageTags.Thumb}):item.BackdropImageTags&&item.BackdropImageTags.length?imgUrl=apiClient.getScaledImageUrl(item.Id,{type:"Backdrop",maxWidth:width,tag:item.BackdropImageTags[0]}):item.ImageTags&&item.ImageTags.Thumb?imgUrl=apiClient.getScaledImageUrl(item.Id,{type:"Thumb",maxWidth:width,tag:item.ImageTags.Thumb}):item.SeriesThumbImageTag&&!1!==options.inheritThumb?imgUrl=apiClient.getScaledImageUrl(item.SeriesId,{type:"Thumb",maxWidth:width,tag:item.SeriesThumbImageTag}):item.ParentThumbItemId&&!1!==options.inheritThumb?imgUrl=apiClient.getScaledImageUrl(item.ParentThumbItemId,{type:"Thumb",maxWidth:width,tag:item.ParentThumbImageTag}):item.ParentBackdropImageTags&&item.ParentBackdropImageTags.length&&!1!==options.inheritThumb&&(imgUrl=apiClient.getScaledImageUrl(item.ParentBackdropItemId,{type:"Backdrop",maxWidth:width,tag:item.ParentBackdropImageTags[0]})),{imgUrl:imgUrl,forceName:forceName,coverImage:coverImage}}function getRandomInt(min,max){return Math.floor(Math.random()*(max-min+1))+min}function getDefaultColorIndex(str){if(str){for(var charIndex=Math.floor(str.length/2),character=String(str.substr(charIndex,1).charCodeAt()),sum=0,i=0;i0&&isOuterFooter?currentCssClass+=" cardText-secondary":0===valid&&isOuterFooter&&(currentCssClass+=" cardText-first"),addRightMargin&&(currentCssClass+=" cardText-rightmargin"),text&&(html+="
",html+=text,html+="
",valid++,maxLines&&valid>=maxLines))break}if(forceLines)for(length=maxLines||Math.min(lines.length,maxLines||lines.length);valid ",valid++;return html}function isUsingLiveTvNaming(item){return"Program"===item.Type||"Timer"===item.Type||"Recording"===item.Type}function getAirTimeText(item,showAirDateTime,showAirEndTime){var airTimeText="";if(item.StartDate)try{var date=datetime.parseISO8601Date(item.StartDate);showAirDateTime&&(airTimeText+=datetime.toLocaleDateString(date,{weekday:"short",month:"short",day:"numeric"})+" "),airTimeText+=datetime.getDisplayTime(date),item.EndDate&&showAirEndTime&&(date=datetime.parseISO8601Date(item.EndDate),airTimeText+=" - "+datetime.getDisplayTime(date))}catch(e){console.log("Error parsing date: "+item.StartDate)}return airTimeText}function getCardFooterText(item,apiClient,options,showTitle,forceName,overlayText,imgUrl,footerClass,progressHtml,logoUrl,isOuterFooter){var html="";logoUrl&&(html+='');var showOtherText=isOuterFooter?!overlayText:overlayText;isOuterFooter&&options.cardLayout&&layoutManager.mobile&&"none"!==options.cardFooterAside&&(html+='');var titleAdded,cssClass=options.centerText?"cardText cardTextCentered":"cardText",lines=[],parentTitleUnderneath="MusicAlbum"===item.Type||"Audio"===item.Type||"MusicVideo"===item.Type;if(showOtherText&&(options.showParentTitle||options.showParentTitleOrTitle)&&!parentTitleUnderneath)if(isOuterFooter&&"Episode"===item.Type&&item.SeriesName)item.SeriesId?lines.push(getTextActionButton({Id:item.SeriesId,ServerId:item.ServerId,Name:item.SeriesName,Type:"Series",IsFolder:!0})):lines.push(item.SeriesName);else if(isUsingLiveTvNaming(item))lines.push(item.Name),item.EpisodeTitle||(titleAdded=!0);else{var parentTitle=item.SeriesName||item.Series||item.Album||item.AlbumArtist||item.GameSystem||"";(parentTitle||showTitle)&&lines.push(parentTitle)}var showMediaTitle=showTitle&&!titleAdded||options.showParentTitleOrTitle&&!lines.length;if(showMediaTitle||titleAdded||!showTitle&&!forceName||(showMediaTitle=!0),showMediaTitle){var name="auto"!==options.showTitle||item.IsFolder||"Photo"!==item.MediaType?itemHelper.getDisplayName(item,{includeParentInfo:options.includeParentInfoInTitle}):"";lines.push(name)}if(showOtherText){if(options.showParentTitle&&parentTitleUnderneath&&(isOuterFooter&&item.AlbumArtists&&item.AlbumArtists.length?(item.AlbumArtists[0].Type="MusicArtist",item.AlbumArtists[0].IsFolder=!0,lines.push(getTextActionButton(item.AlbumArtists[0],null,item.ServerId))):lines.push(isUsingLiveTvNaming(item)?item.Name:item.SeriesName||item.Series||item.Album||item.AlbumArtist||item.GameSystem||"")),options.showItemCounts){var itemCountHtml=getItemCountsHtml(options,item);lines.push(itemCountHtml)}if(options.textLines)for(var additionalLines=options.textLines(item),i=0,length=additionalLines.length;i'+html,html+=""),html}function getTextActionButton(item,text,serverId){if(text||(text=itemHelper.getDisplayName(item)),layoutManager.tv)return text;var html=""}function getItemCountsHtml(options,item){var childText,counts=[];if("Playlist"===item.Type){if(childText="",item.RunTimeTicks){var minutes=item.RunTimeTicks/6e8;minutes=minutes||1,childText+=globalize.translate("sharedcomponents#ValueMinutes",Math.round(minutes))}else childText+=globalize.translate("sharedcomponents#ValueMinutes",0);counts.push(childText)}else"Genre"===item.Type||"Studio"===item.Type?(item.MovieCount&&(childText=1===item.MovieCount?globalize.translate("sharedcomponents#ValueOneMovie"):globalize.translate("sharedcomponents#ValueMovieCount",item.MovieCount),counts.push(childText)),item.SeriesCount&&(childText=1===item.SeriesCount?globalize.translate("sharedcomponents#ValueOneSeries"):globalize.translate("sharedcomponents#ValueSeriesCount",item.SeriesCount),counts.push(childText)),item.EpisodeCount&&(childText=1===item.EpisodeCount?globalize.translate("sharedcomponents#ValueOneEpisode"):globalize.translate("sharedcomponents#ValueEpisodeCount",item.EpisodeCount),counts.push(childText)),item.GameCount&&(childText=1===item.GameCount?globalize.translate("sharedcomponents#ValueOneGame"):globalize.translate("sharedcomponents#ValueGameCount",item.GameCount),counts.push(childText))):"GameGenre"===item.Type?item.GameCount&&(childText=1===item.GameCount?globalize.translate("sharedcomponents#ValueOneGame"):globalize.translate("sharedcomponents#ValueGameCount",item.GameCount),counts.push(childText)):"MusicGenre"===item.Type||"MusicArtist"===options.context?(item.AlbumCount&&(childText=1===item.AlbumCount?globalize.translate("sharedcomponents#ValueOneAlbum"):globalize.translate("sharedcomponents#ValueAlbumCount",item.AlbumCount),counts.push(childText)),item.SongCount&&(childText=1===item.SongCount?globalize.translate("sharedcomponents#ValueOneSong"):globalize.translate("sharedcomponents#ValueSongCount",item.SongCount),counts.push(childText)),item.MusicVideoCount&&(childText=1===item.MusicVideoCount?globalize.translate("sharedcomponents#ValueOneMusicVideo"):globalize.translate("sharedcomponents#ValueMusicVideoCount",item.MusicVideoCount),counts.push(childText))):"Series"===item.Type&&(childText=1===item.RecursiveItemCount?globalize.translate("sharedcomponents#ValueOneEpisode"):globalize.translate("sharedcomponents#ValueEpisodeCount",item.RecursiveItemCount),counts.push(childText));return counts.join(", ")}function requireRefreshIndicator(){refreshIndicatorLoaded||(refreshIndicatorLoaded=!0,require(["emby-itemrefreshindicator"]))}function getDefaultBackgroundClass(str){return"defaultCardBackground defaultCardBackground"+getDefaultColorIndex(str)}function buildCard(index,item,apiClient,options){var action=options.action||"link";"play"===action&&item.IsFolder?action="link":"Photo"===item.MediaType&&(action="play");var shape=options.shape;if("mixed"===shape){shape=null;var primaryImageAspectRatio=item.PrimaryImageAspectRatio;primaryImageAspectRatio&&(shape=primaryImageAspectRatio>=1.33?"mixedBackdrop":primaryImageAspectRatio>.71?"mixedSquare":"mixedPortrait"),shape=shape||"mixedSquare"}var className="card";shape&&(className+=" "+shape+"Card"),options.cardCssClass&&(className+=" "+options.cardCssClass),options.cardClass&&(className+=" "+options.cardClass),layoutManager.desktop&&(className+=" card-hoverable"),enableFocusTransfrom&&layoutManager.tv||(className+=" card-nofocustransform");var imgInfo=getCardImageUrl(item,apiClient,options,shape),imgUrl=imgInfo.imgUrl,forceName=imgInfo.forceName,showTitle="auto"===options.showTitle||(options.showTitle||"PhotoAlbum"===item.Type||"Folder"===item.Type),overlayText=options.overlayText;forceName&&!options.cardLayout&&null==overlayText&&(overlayText=!0);var cardImageContainerClass="cardImageContainer";(options.coverImage||imgInfo.coverImage)&&(cardImageContainerClass+=" coveredImage",("Photo"===item.MediaType||"PhotoAlbum"===item.Type||"Folder"===item.Type||item.ProgramInfo||"Program"===item.Type||"Recording"===item.Type)&&(cardImageContainerClass+=" coveredImage-noScale")),imgUrl||(cardImageContainerClass+=" "+getDefaultBackgroundClass(item.Name));var cardBoxClass=options.cardLayout?"cardBox visualCardBox":"cardBox";layoutManager.tv&&(cardBoxClass+=enableFocusTransfrom?" cardBox-focustransform cardBox-withfocuscontent":" cardBox-withfocuscontent-large",options.cardLayout&&(cardBoxClass+=" card-focuscontent",enableFocusTransfrom||(cardBoxClass+=" card-focuscontent-large")));var footerCssClass,logoUrl,progressHtml=indicators.getProgressBarHtml(item),innerCardFooter="",footerOverlayed=!1;options.showChannelLogo&&item.ChannelPrimaryImageTag?logoUrl=apiClient.getScaledImageUrl(item.ChannelId,{type:"Primary",height:40,tag:item.ChannelPrimaryImageTag}):options.showLogo&&item.ParentLogoImageTag&&(logoUrl=apiClient.getScaledImageUrl(item.ParentLogoItemId,{type:"Logo",height:40,tag:item.ParentLogoImageTag})),overlayText?(logoUrl=null,footerCssClass=progressHtml?"innerCardFooter fullInnerCardFooter":"innerCardFooter",innerCardFooter+=getCardFooterText(item,apiClient,options,showTitle,forceName,overlayText,imgUrl,footerCssClass,progressHtml,logoUrl,!1),footerOverlayed=!0):progressHtml&&(innerCardFooter+='
',innerCardFooter+=progressHtml,innerCardFooter+="
",progressHtml="");var mediaSourceCount=item.MediaSourceCount||1;mediaSourceCount>1&&(innerCardFooter+='
'+mediaSourceCount+"
");var outerCardFooter="";overlayText||footerOverlayed||(footerCssClass=options.cardLayout?"cardFooter":"cardFooter cardFooter-transparent",logoUrl&&(footerCssClass+=" cardFooter-withlogo"),options.cardLayout||(logoUrl=null),outerCardFooter=getCardFooterText(item,apiClient,options,showTitle,forceName,overlayText,imgUrl,footerCssClass,progressHtml,logoUrl,!0)),outerCardFooter&&!options.cardLayout&&(cardBoxClass+=" cardBox-bottompadded");var overlayButtons="";if(layoutManager.mobile){var overlayPlayButton=options.overlayPlayButton;null!=overlayPlayButton||options.overlayMoreButton||options.overlayInfoButton||options.cardLayout||(overlayPlayButton="Video"===item.MediaType);var btnCssClass="cardOverlayButton cardOverlayButton-br itemAction";options.centerPlayButton&&(overlayButtons+=''),!overlayPlayButton||item.IsPlaceHolder||"Virtual"===item.LocationType&&item.MediaType&&"Program"!==item.Type||"Person"===item.Type||(overlayButtons+=''),options.overlayMoreButton&&(overlayButtons+='')}options.showChildCountIndicator&&item.ChildCount&&(className+=" groupedCard");var cardImageContainerOpen,cardImageContainerClose="",cardBoxClose="",cardScalableClose="",cardContentClass="cardContent";options.cardLayout||(cardContentClass+=" cardContent-shadow"),layoutManager.tv?(cardImageContainerOpen=imgUrl?'
':'
',cardImageContainerClose="
"):(cardImageContainerOpen=imgUrl?'");var cardScalableClass="cardScalable";layoutManager.tv&&!options.cardLayout&&(cardScalableClass+=" card-focuscontent",enableFocusTransfrom||(cardScalableClass+=" card-focuscontent-large")),cardImageContainerOpen='
'+cardImageContainerOpen,cardBoxClose="
",cardScalableClose="
";var indicatorsHtml="";if(!1!==options.missingIndicator&&(indicatorsHtml+=indicators.getMissingIndicator(item)),indicatorsHtml+=indicators.getSyncIndicator(item),indicatorsHtml+=indicators.getTimerIndicator(item),indicatorsHtml+=indicators.getTypeIndicator(item),options.showGroupCount?indicatorsHtml+=indicators.getChildCountIndicatorHtml(item,{minCount:1}):indicatorsHtml+=indicators.getPlayedIndicatorHtml(item),"CollectionFolder"===item.Type||item.CollectionType){indicatorsHtml+='
',requireRefreshIndicator()}indicatorsHtml&&(cardImageContainerOpen+='
'+indicatorsHtml+"
"),imgUrl||(cardImageContainerOpen+=getCardDefaultText(item,options));var tagName=layoutManager.tv&&!overlayButtons?"button":"div",nameWithPrefix=item.SortName||item.Name||"",prefix=nameWithPrefix.substring(0,Math.min(3,nameWithPrefix.length));prefix&&(prefix=prefix.toUpperCase());var timerAttributes="";item.TimerId&&(timerAttributes+=' data-timerid="'+item.TimerId+'"'),item.SeriesTimerId&&(timerAttributes+=' data-seriestimerid="'+item.SeriesTimerId+'"');var actionAttribute;"button"===tagName?(className+=" itemAction",actionAttribute=' data-action="'+action+'"'):actionAttribute="","MusicAlbum"!==item.Type&&"MusicArtist"!==item.Type&&"Audio"!==item.Type&&(className+=" card-withuserdata");var positionTicksData=item.UserData&&item.UserData.PlaybackPositionTicks?' data-positionticks="'+item.UserData.PlaybackPositionTicks+'"':"",collectionIdData=options.collectionId?' data-collectionid="'+options.collectionId+'"':"",playlistIdData=options.playlistId?' data-playlistid="'+options.playlistId+'"':"",mediaTypeData=item.MediaType?' data-mediatype="'+item.MediaType+'"':"",collectionTypeData=item.CollectionType?' data-collectiontype="'+item.CollectionType+'"':"",channelIdData=item.ChannelId?' data-channelid="'+item.ChannelId+'"':"",contextData=options.context?' data-context="'+options.context+'"':"",parentIdData=options.parentId?' data-parentid="'+options.parentId+'"':"",additionalCardContent="";return layoutManager.desktop&&(additionalCardContent+=getHoverMenuHtml(item,action)),"<"+tagName+' data-index="'+index+'"'+timerAttributes+actionAttribute+' data-isfolder="'+(item.IsFolder||!1)+'" data-serverid="'+(item.ServerId||options.serverId)+'" data-id="'+(item.Id||item.ItemId)+'" data-type="'+item.Type+'"'+mediaTypeData+collectionTypeData+channelIdData+positionTicksData+collectionIdData+playlistIdData+contextData+parentIdData+' data-prefix="'+prefix+'" class="'+className+'">'+cardImageContainerOpen+innerCardFooter+cardImageContainerClose+overlayButtons+additionalCardContent+cardScalableClose+outerCardFooter+cardBoxClose+""}function getHoverMenuHtml(item,action){var html="";html+='
';var btnCssClass="cardOverlayButton cardOverlayButton-hover itemAction";playbackManager.canPlay(item)&&(html+=''),html+='
';var userData=item.UserData||{};if(itemHelper.canMarkPlayed(item)&&(require(["emby-playstatebutton"]),html+=''),itemHelper.canRate(item)){var likes=null==userData.Likes?"":userData.Likes;require(["emby-ratingbutton"]),html+=''}return html+='',html+="
",html+="
"}function getCardDefaultText(item,options){var collectionType=item.CollectionType;return"livetv"===collectionType?'':"homevideos"===collectionType||"photos"===collectionType?'':"music"===collectionType?'':"MusicAlbum"===item.Type?'':"MusicArtist"===item.Type||"Person"===item.Type?'':options.defaultCardImageIcon?''+options.defaultCardImageIcon+"":'
'+(isUsingLiveTvNaming(item)?item.Name:itemHelper.getDisplayName(item))+"
"}function buildCards(items,options){if(document.body.contains(options.itemsContainer)){if(options.parentContainer){if(!items.length)return void options.parentContainer.classList.add("hide");options.parentContainer.classList.remove("hide")}var html=buildCardsHtmlInternal(items,options);html?(options.itemsContainer.cardBuilderHtml!==html&&(options.itemsContainer.innerHTML=html,items.length<50?options.itemsContainer.cardBuilderHtml=html:options.itemsContainer.cardBuilderHtml=null),imageLoader.lazyChildren(options.itemsContainer)):(options.itemsContainer.innerHTML=html,options.itemsContainer.cardBuilderHtml=null),options.autoFocus&&focusManager.autoFocus(options.itemsContainer,!0)}}function ensureIndicators(card,indicatorsElem){if(indicatorsElem)return indicatorsElem;if(!(indicatorsElem=card.querySelector(".cardIndicators"))){var cardImageContainer=card.querySelector(".cardImageContainer");indicatorsElem=document.createElement("div"), -indicatorsElem.classList.add("cardIndicators"),cardImageContainer.appendChild(indicatorsElem)}return indicatorsElem}function updateUserData(card,userData){var type=card.getAttribute("data-type"),enableCountIndicator="Series"===type||"BoxSet"===type||"Season"===type,indicatorsElem=null,playedIndicator=null,countIndicator=null,itemProgressBar=null;userData.Played?(playedIndicator=card.querySelector(".playedIndicator"),playedIndicator||(playedIndicator=document.createElement("div"),playedIndicator.classList.add("playedIndicator"),playedIndicator.classList.add("indicator"),indicatorsElem=ensureIndicators(card,indicatorsElem),indicatorsElem.appendChild(playedIndicator)),playedIndicator.innerHTML=''):(playedIndicator=card.querySelector(".playedIndicator"))&&playedIndicator.parentNode.removeChild(playedIndicator),userData.UnplayedItemCount?(countIndicator=card.querySelector(".countIndicator"),countIndicator||(countIndicator=document.createElement("div"),countIndicator.classList.add("countIndicator"),indicatorsElem=ensureIndicators(card,indicatorsElem),indicatorsElem.appendChild(countIndicator)),countIndicator.innerHTML=userData.UnplayedItemCount):enableCountIndicator&&(countIndicator=card.querySelector(".countIndicator"))&&countIndicator.parentNode.removeChild(countIndicator);var progressHtml=indicators.getProgressBarHtml({Type:type,UserData:userData,MediaType:"Video"});if(progressHtml){if(!(itemProgressBar=card.querySelector(".itemProgressBar"))){itemProgressBar=document.createElement("div"),itemProgressBar.classList.add("itemProgressBar");var innerCardFooter=card.querySelector(".innerCardFooter");if(!innerCardFooter){innerCardFooter=document.createElement("div"),innerCardFooter.classList.add("innerCardFooter");card.querySelector(".cardImageContainer").appendChild(innerCardFooter)}innerCardFooter.appendChild(itemProgressBar)}itemProgressBar.innerHTML=progressHtml}else(itemProgressBar=card.querySelector(".itemProgressBar"))&&itemProgressBar.parentNode.removeChild(itemProgressBar)}function onUserDataChanged(userData,scope){for(var cards=(scope||document.body).querySelectorAll('.card-withuserdata[data-id="'+userData.ItemId+'"]'),i=0,length=cards.length;i')}cell.setAttribute("data-timerid",newTimerId)}}function onTimerCancelled(id,itemsContainer){for(var cells=itemsContainer.querySelectorAll('.card[data-timerid="'+id+'"]'),i=0,length=cells.length;i= 2200 ? 10 : screenWidth >= 1920 ? 9.000000000009 : screenWidth >= 1600 ? 8 : screenWidth >= 1400 ? 7.0000000000021 : screenWidth >= 1200 ? 5.9999999988 : screenWidth >= 800 ? 5 : screenWidth >= 700 ? 4 : 3.0000000003; + case "square": + return layoutManager.tv ? 5.9999999988 : screenWidth >= 2200 ? 10 : screenWidth >= 1920 ? 9.000000000009 : screenWidth >= 1600 ? 8 : screenWidth >= 1400 ? 7.0000000000021 : screenWidth >= 1200 ? 5.9999999988 : screenWidth >= 800 ? 5 : screenWidth >= 700 ? 4 : screenWidth >= 500 ? 3.0000000003 : 2; + case "banner": + return screenWidth >= 2200 ? 4 : screenWidth >= 1200 ? 3.0000000003 : screenWidth >= 800 ? 2 : 1; + case "backdrop": + return layoutManager.tv ? 4 : screenWidth >= 2500 ? 6 : screenWidth >= 1600 ? 5 : screenWidth >= 1200 ? 4 : screenWidth >= 770 ? 3 : screenWidth >= 420 ? 2 : 1; + case "smallBackdrop": + return screenWidth >= 1600 ? 8 : screenWidth >= 1400 ? 7.000000000007001 : screenWidth >= 1200 ? 6 : screenWidth >= 1e3 ? 5 : screenWidth >= 800 ? 4 : screenWidth >= 500 ? 3.0000000003 : 2; + case "overflowSmallBackdrop": + return layoutManager.tv ? 100 / 18.9 : isOrientationLandscape ? screenWidth >= 800 ? 100 / 15.5 : 100 / 23.3 : screenWidth >= 540 ? 100 / 30 : 100 / 72; + case "overflowPortrait": + return layoutManager.tv ? 100 / 15.5 : isOrientationLandscape ? screenWidth >= 1700 ? 100 / 11.6 : 100 / 15.5 : screenWidth >= 1400 ? 100 / 15 : screenWidth >= 1200 ? 100 / 18 : screenWidth >= 760 ? 100 / 23 : screenWidth >= 400 ? 100 / 31.5 : 100 / 42; + case "overflowSquare": + return layoutManager.tv ? 100 / 15.5 : isOrientationLandscape ? screenWidth >= 1700 ? 100 / 11.6 : 100 / 15.5 : screenWidth >= 1400 ? 100 / 15 : screenWidth >= 1200 ? 100 / 18 : screenWidth >= 760 ? 100 / 23 : screenWidth >= 540 ? 100 / 31.5 : 100 / 42; + case "overflowBackdrop": + return layoutManager.tv ? 100 / 23.3 : isOrientationLandscape ? screenWidth >= 1700 ? 100 / 18.5 : 100 / 23.3 : screenWidth >= 1800 ? 100 / 23.5 : screenWidth >= 1400 ? 100 / 30 : screenWidth >= 760 ? 2.5 : screenWidth >= 640 ? 100 / 56 : 100 / 72; + default: + return 4 + } + } + + function isResizable(windowWidth) { + var screen = window.screen; + if (screen) { + if (screen.availWidth - windowWidth > 20) return !0 + } + return !1 + } + + function getImageWidth(shape, screenWidth, isOrientationLandscape) { + var imagesPerRow = getPostersPerRow(shape, screenWidth, isOrientationLandscape), + shapeWidth = screenWidth / imagesPerRow; + return Math.round(shapeWidth) + } + + function setCardData(items, options) { + options.shape = options.shape || "auto"; + var primaryImageAspectRatio = imageLoader.getPrimaryImageAspectRatio(items); + if ("auto" === options.shape || "autohome" === options.shape || "autooverflow" === options.shape || "autoVertical" === options.shape) { + var requestedShape = options.shape; + options.shape = null, primaryImageAspectRatio && (primaryImageAspectRatio >= 3 ? (options.shape = "banner", options.coverImage = !0) : options.shape = primaryImageAspectRatio >= 1.33 ? "autooverflow" === requestedShape ? "overflowBackdrop" : "backdrop" : primaryImageAspectRatio > .71 ? "autooverflow" === requestedShape ? "overflowSquare" : "square" : "autooverflow" === requestedShape ? "overflowPortrait" : "portrait"), options.shape || (options.shape = options.defaultShape || ("autooverflow" === requestedShape ? "overflowSquare" : "square")) + } + if ("auto" === options.preferThumb && (options.preferThumb = "backdrop" === options.shape || "overflowBackdrop" === options.shape), options.uiAspect = getDesiredAspect(options.shape), options.primaryImageAspectRatio = primaryImageAspectRatio, !options.width && options.widths && (options.width = options.widths[options.shape]), options.rows && "number" != typeof options.rows && (options.rows = options.rows[options.shape]), !options.width) { + var screenWidth = dom.getWindowSize().innerWidth, + screenHeight = dom.getWindowSize().innerHeight; + if (isResizable(screenWidth)) { + screenWidth = 100 * Math.floor(screenWidth / 100) + } + options.width = getImageWidth(options.shape, screenWidth, screenWidth > 1.3 * screenHeight) + } + } + + function buildCardsHtmlInternal(items, options) { + var isVertical; + "autoVertical" === options.shape && (isVertical = !0), setCardData(items, options); + var currentIndexValue, hasOpenRow, hasOpenSection, apiClient, lastServerId, i, length, html = "", + itemsInRow = 0, + sectionTitleTagName = options.sectionTitleTagName || "div"; + for (i = 0, length = items.length; i < length; i++) { + var item = items[i], + serverId = item.ServerId || options.serverId; + if (serverId !== lastServerId && (lastServerId = serverId, apiClient = connectionManager.getApiClient(lastServerId)), options.indexBy) { + var newIndexValue = ""; + if ("PremiereDate" === options.indexBy) { + if (item.PremiereDate) try { + newIndexValue = datetime.toLocaleDateString(datetime.parseISO8601Date(item.PremiereDate), { + weekday: "long", + month: "long", + day: "numeric" + }) + } catch (err) {} + } else "ProductionYear" === options.indexBy ? newIndexValue = item.ProductionYear : "CommunityRating" === options.indexBy && (newIndexValue = item.CommunityRating ? Math.floor(item.CommunityRating) + (item.CommunityRating % 1 >= .5 ? .5 : 0) + "+" : null); + newIndexValue !== currentIndexValue && (hasOpenRow && (html += "
", hasOpenRow = !1, itemsInRow = 0), hasOpenSection && (html += "", isVertical && (html += ""), hasOpenSection = !1), html += isVertical ? '
' : '
', html += "<" + sectionTitleTagName + ' class="sectionTitle">' + newIndexValue + "", isVertical && (html += '
'), currentIndexValue = newIndexValue, hasOpenSection = !0) + } + options.rows && 0 === itemsInRow && (hasOpenRow && (html += "
", hasOpenRow = !1), html += '
', hasOpenRow = !0), html += buildCard(i, item, apiClient, options), itemsInRow++, options.rows && itemsInRow >= options.rows && (html += "
", hasOpenRow = !1, itemsInRow = 0) + } + hasOpenRow && (html += "
"), hasOpenSection && (html += "
", isVertical && (html += "")); + var cardFooterHtml = ""; + for (i = 0, length = options.lines || 0; i < length; i++) cardFooterHtml += 0 === i ? '
 
' : '
 
'; + return html + } + + function getDesiredAspect(shape) { + if (shape) { + if (shape = shape.toLowerCase(), -1 !== shape.indexOf("portrait")) return 2 / 3; + if (-1 !== shape.indexOf("backdrop")) return 16 / 9; + if (-1 !== shape.indexOf("square")) return 1; + if (-1 !== shape.indexOf("banner")) return 1e3 / 185 + } + return null + } + + function getCardImageUrl(item, apiClient, options, shape) { + item = item.ProgramInfo || item; + var width = options.width, + height = null, + primaryImageAspectRatio = item.PrimaryImageAspectRatio, + forceName = !1, + imgUrl = null, + coverImage = !1, + uiAspect = null; + return options.preferThumb && item.ImageTags && item.ImageTags.Thumb ? imgUrl = apiClient.getScaledImageUrl(item.Id, { + type: "Thumb", + maxWidth: width, + tag: item.ImageTags.Thumb + }) : (options.preferBanner || "banner" === shape) && item.ImageTags && item.ImageTags.Banner ? imgUrl = apiClient.getScaledImageUrl(item.Id, { + type: "Banner", + maxWidth: width, + tag: item.ImageTags.Banner + }) : options.preferDisc && item.ImageTags && item.ImageTags.Disc ? imgUrl = apiClient.getScaledImageUrl(item.Id, { + type: "Disc", + maxWidth: width, + tag: item.ImageTags.Disc + }) : options.preferLogo && item.ImageTags && item.ImageTags.Logo ? imgUrl = apiClient.getScaledImageUrl(item.Id, { + type: "Logo", + maxWidth: width, + tag: item.ImageTags.Logo + }) : options.preferLogo && item.ParentLogoImageTag && item.ParentLogoItemId ? imgUrl = apiClient.getScaledImageUrl(item.ParentLogoItemId, { + type: "Logo", + maxWidth: width, + tag: item.ParentLogoImageTag + }) : options.preferThumb && item.SeriesThumbImageTag && !1 !== options.inheritThumb ? imgUrl = apiClient.getScaledImageUrl(item.SeriesId, { + type: "Thumb", + maxWidth: width, + tag: item.SeriesThumbImageTag + }) : options.preferThumb && item.ParentThumbItemId && !1 !== options.inheritThumb && "Photo" !== item.MediaType ? imgUrl = apiClient.getScaledImageUrl(item.ParentThumbItemId, { + type: "Thumb", + maxWidth: width, + tag: item.ParentThumbImageTag + }) : options.preferThumb && item.BackdropImageTags && item.BackdropImageTags.length ? (imgUrl = apiClient.getScaledImageUrl(item.Id, { + type: "Backdrop", + maxWidth: width, + tag: item.BackdropImageTags[0] + }), forceName = !0) : options.preferThumb && item.ParentBackdropImageTags && item.ParentBackdropImageTags.length && !1 !== options.inheritThumb && "Episode" === item.Type ? imgUrl = apiClient.getScaledImageUrl(item.ParentBackdropItemId, { + type: "Backdrop", + maxWidth: width, + tag: item.ParentBackdropImageTags[0] + }) : item.ImageTags && item.ImageTags.Primary ? (height = width && primaryImageAspectRatio ? Math.round(width / primaryImageAspectRatio) : null, imgUrl = apiClient.getScaledImageUrl(item.Id, { + type: "Primary", + maxHeight: height, + maxWidth: width, + tag: item.ImageTags.Primary + }), options.preferThumb && !1 !== options.showTitle && (forceName = !0), primaryImageAspectRatio && (uiAspect = getDesiredAspect(shape)) && (coverImage = Math.abs(primaryImageAspectRatio - uiAspect) / uiAspect <= .2)) : item.PrimaryImageTag ? (height = width && primaryImageAspectRatio ? Math.round(width / primaryImageAspectRatio) : null, imgUrl = apiClient.getScaledImageUrl(item.PrimaryImageItemId || item.Id || item.ItemId, { + type: "Primary", + maxHeight: height, + maxWidth: width, + tag: item.PrimaryImageTag + }), options.preferThumb && !1 !== options.showTitle && (forceName = !0), primaryImageAspectRatio && (uiAspect = getDesiredAspect(shape)) && (coverImage = Math.abs(primaryImageAspectRatio - uiAspect) / uiAspect <= .2)) : item.ParentPrimaryImageTag ? imgUrl = apiClient.getScaledImageUrl(item.ParentPrimaryImageItemId, { + type: "Primary", + maxWidth: width, + tag: item.ParentPrimaryImageTag + }) : item.SeriesPrimaryImageTag ? imgUrl = apiClient.getScaledImageUrl(item.SeriesId, { + type: "Primary", + maxWidth: width, + tag: item.SeriesPrimaryImageTag + }) : item.AlbumId && item.AlbumPrimaryImageTag ? (width = primaryImageAspectRatio ? Math.round(height * primaryImageAspectRatio) : null, imgUrl = apiClient.getScaledImageUrl(item.AlbumId, { + type: "Primary", + maxHeight: height, + maxWidth: width, + tag: item.AlbumPrimaryImageTag + }), primaryImageAspectRatio && (uiAspect = getDesiredAspect(shape)) && (coverImage = Math.abs(primaryImageAspectRatio - uiAspect) / uiAspect <= .2)) : "Season" === item.Type && item.ImageTags && item.ImageTags.Thumb ? imgUrl = apiClient.getScaledImageUrl(item.Id, { + type: "Thumb", + maxWidth: width, + tag: item.ImageTags.Thumb + }) : item.BackdropImageTags && item.BackdropImageTags.length ? imgUrl = apiClient.getScaledImageUrl(item.Id, { + type: "Backdrop", + maxWidth: width, + tag: item.BackdropImageTags[0] + }) : item.ImageTags && item.ImageTags.Thumb ? imgUrl = apiClient.getScaledImageUrl(item.Id, { + type: "Thumb", + maxWidth: width, + tag: item.ImageTags.Thumb + }) : item.SeriesThumbImageTag && !1 !== options.inheritThumb ? imgUrl = apiClient.getScaledImageUrl(item.SeriesId, { + type: "Thumb", + maxWidth: width, + tag: item.SeriesThumbImageTag + }) : item.ParentThumbItemId && !1 !== options.inheritThumb ? imgUrl = apiClient.getScaledImageUrl(item.ParentThumbItemId, { + type: "Thumb", + maxWidth: width, + tag: item.ParentThumbImageTag + }) : item.ParentBackdropImageTags && item.ParentBackdropImageTags.length && !1 !== options.inheritThumb && (imgUrl = apiClient.getScaledImageUrl(item.ParentBackdropItemId, { + type: "Backdrop", + maxWidth: width, + tag: item.ParentBackdropImageTags[0] + })), { + imgUrl: imgUrl, + forceName: forceName, + coverImage: coverImage + } + } + + function getRandomInt(min, max) { + return Math.floor(Math.random() * (max - min + 1)) + min + } + + function getDefaultColorIndex(str) { + if (str) { + for (var charIndex = Math.floor(str.length / 2), character = String(str.substr(charIndex, 1).charCodeAt()), sum = 0, i = 0; i < character.length; i++) sum += parseInt(character.charAt(i)); + return String(sum).substr(-1) % numRandomColors + 1 + } + return getRandomInt(1, numRandomColors) + } + + function getCardTextLines(lines, cssClass, forceLines, isOuterFooter, cardLayout, addRightMargin, maxLines) { + var i, length, html = "", + valid = 0; + for (i = 0, length = lines.length; i < length; i++) { + var currentCssClass = cssClass, + text = lines[i]; + if (valid > 0 && isOuterFooter ? currentCssClass += " cardText-secondary" : 0 === valid && isOuterFooter && (currentCssClass += " cardText-first"), addRightMargin && (currentCssClass += " cardText-rightmargin"), text && (html += "
", html += text, html += "
", valid++, maxLines && valid >= maxLines)) break + } + if (forceLines) + for (length = maxLines || Math.min(lines.length, maxLines || lines.length); valid < length;) html += "
 
", valid++; + return html + } + + function isUsingLiveTvNaming(item) { + return "Program" === item.Type || "Timer" === item.Type || "Recording" === item.Type + } + + function getAirTimeText(item, showAirDateTime, showAirEndTime) { + var airTimeText = ""; + if (item.StartDate) try { + var date = datetime.parseISO8601Date(item.StartDate); + showAirDateTime && (airTimeText += datetime.toLocaleDateString(date, { + weekday: "short", + month: "short", + day: "numeric" + }) + " "), airTimeText += datetime.getDisplayTime(date), item.EndDate && showAirEndTime && (date = datetime.parseISO8601Date(item.EndDate), airTimeText += " - " + datetime.getDisplayTime(date)) + } catch (e) { + console.log("Error parsing date: " + item.StartDate) + } + return airTimeText + } + + function getCardFooterText(item, apiClient, options, showTitle, forceName, overlayText, imgUrl, footerClass, progressHtml, logoUrl, isOuterFooter) { + var html = ""; + logoUrl && (html += ''); + var showOtherText = isOuterFooter ? !overlayText : overlayText; + isOuterFooter && options.cardLayout && layoutManager.mobile && "none" !== options.cardFooterAside && (html += ''); + var titleAdded, cssClass = options.centerText ? "cardText cardTextCentered" : "cardText", + lines = [], + parentTitleUnderneath = "MusicAlbum" === item.Type || "Audio" === item.Type || "MusicVideo" === item.Type; + if (showOtherText && (options.showParentTitle || options.showParentTitleOrTitle) && !parentTitleUnderneath) + if (isOuterFooter && "Episode" === item.Type && item.SeriesName) item.SeriesId ? lines.push(getTextActionButton({ + Id: item.SeriesId, + ServerId: item.ServerId, + Name: item.SeriesName, + Type: "Series", + IsFolder: !0 + })) : lines.push(item.SeriesName); + else if (isUsingLiveTvNaming(item)) lines.push(item.Name), item.EpisodeTitle || (titleAdded = !0); + else { + var parentTitle = item.SeriesName || item.Series || item.Album || item.AlbumArtist || item.GameSystem || ""; + (parentTitle || showTitle) && lines.push(parentTitle) + } + var showMediaTitle = showTitle && !titleAdded || options.showParentTitleOrTitle && !lines.length; + if (showMediaTitle || titleAdded || !showTitle && !forceName || (showMediaTitle = !0), showMediaTitle) { + var name = "auto" !== options.showTitle || item.IsFolder || "Photo" !== item.MediaType ? itemHelper.getDisplayName(item, { + includeParentInfo: options.includeParentInfoInTitle + }) : ""; + lines.push(name) + } + if (showOtherText) { + if (options.showParentTitle && parentTitleUnderneath && (isOuterFooter && item.AlbumArtists && item.AlbumArtists.length ? (item.AlbumArtists[0].Type = "MusicArtist", item.AlbumArtists[0].IsFolder = !0, lines.push(getTextActionButton(item.AlbumArtists[0], null, item.ServerId))) : lines.push(isUsingLiveTvNaming(item) ? item.Name : item.SeriesName || item.Series || item.Album || item.AlbumArtist || item.GameSystem || "")), options.showItemCounts) { + var itemCountHtml = getItemCountsHtml(options, item); + lines.push(itemCountHtml) + } + if (options.textLines) + for (var additionalLines = options.textLines(item), i = 0, length = additionalLines.length; i < length; i++) lines.push(additionalLines[i]); + if (options.showSongCount) { + var songLine = ""; + item.SongCount && (songLine = 1 === item.SongCount ? globalize.translate("sharedcomponents#ValueOneSong") : globalize.translate("sharedcomponents#ValueSongCount", item.SongCount)), lines.push(songLine) + } + if (options.showPremiereDate) + if (item.PremiereDate) try { + lines.push(getPremiereDateText(item)) + } catch (err) { + lines.push("") + } else lines.push(""); + (options.showYear || options.showSeriesYear) && ("Series" === item.Type ? "Continuing" === item.Status ? lines.push(globalize.translate("sharedcomponents#SeriesYearToPresent", item.ProductionYear || "")) : item.EndDate && item.ProductionYear ? lines.push(item.ProductionYear + " - " + datetime.parseISO8601Date(item.EndDate).getFullYear()) : lines.push(item.ProductionYear || "") : lines.push(item.ProductionYear || "")), options.showRuntime && (item.RunTimeTicks ? lines.push(datetime.getDisplayRunningTime(item.RunTimeTicks)) : lines.push("")), options.showAirTime && lines.push(getAirTimeText(item, options.showAirDateTime, options.showAirEndTime) || ""), options.showChannelName && (item.ChannelId ? lines.push(getTextActionButton({ + Id: item.ChannelId, + ServerId: item.ServerId, + Name: item.ChannelName, + Type: "TvChannel", + MediaType: item.MediaType, + IsFolder: !1 + }, item.ChannelName)) : lines.push(item.ChannelName || " ")), options.showCurrentProgram && "TvChannel" === item.Type && (item.CurrentProgram ? lines.push(item.CurrentProgram.Name) : lines.push("")), options.showCurrentProgramTime && "TvChannel" === item.Type && (item.CurrentProgram ? lines.push(getAirTimeText(item.CurrentProgram, !1, !0) || "") : lines.push("")), options.showSeriesTimerTime && (item.RecordAnyTime ? lines.push(globalize.translate("sharedcomponents#Anytime")) : lines.push(datetime.getDisplayTime(item.StartDate))), options.showSeriesTimerChannel && (item.RecordAnyChannel ? lines.push(globalize.translate("sharedcomponents#AllChannels")) : lines.push(item.ChannelName || globalize.translate("sharedcomponents#OneChannel"))), options.showPersonRoleOrType && (item.Role ? lines.push("as " + item.Role) : item.Type ? lines.push(globalize.translate("sharedcomponents#" + item.Type)) : lines.push("")) + }(showTitle || !imgUrl) && forceName && overlayText && 1 === lines.length && (lines = []); + var addRightTextMargin = isOuterFooter && options.cardLayout && !options.centerText && "none" !== options.cardFooterAside && layoutManager.mobile; + return html += getCardTextLines(lines, cssClass, !options.overlayText, isOuterFooter, options.cardLayout, addRightTextMargin, options.lines), progressHtml && (html += progressHtml), html && (!isOuterFooter || logoUrl || options.cardLayout) && (html = '
' + html, html += "
"), html + } + + function getTextActionButton(item, text, serverId) { + if (text || (text = itemHelper.getDisplayName(item)), layoutManager.tv) return text; + var html = "" + } + + function getItemCountsHtml(options, item) { + var childText, counts = []; + if ("Playlist" === item.Type) { + if (childText = "", item.RunTimeTicks) { + var minutes = item.RunTimeTicks / 6e8; + minutes = minutes || 1, childText += globalize.translate("sharedcomponents#ValueMinutes", Math.round(minutes)) + } else childText += globalize.translate("sharedcomponents#ValueMinutes", 0); + counts.push(childText) + } else "Genre" === item.Type || "Studio" === item.Type ? (item.MovieCount && (childText = 1 === item.MovieCount ? globalize.translate("sharedcomponents#ValueOneMovie") : globalize.translate("sharedcomponents#ValueMovieCount", item.MovieCount), counts.push(childText)), item.SeriesCount && (childText = 1 === item.SeriesCount ? globalize.translate("sharedcomponents#ValueOneSeries") : globalize.translate("sharedcomponents#ValueSeriesCount", item.SeriesCount), counts.push(childText)), item.EpisodeCount && (childText = 1 === item.EpisodeCount ? globalize.translate("sharedcomponents#ValueOneEpisode") : globalize.translate("sharedcomponents#ValueEpisodeCount", item.EpisodeCount), counts.push(childText)), item.GameCount && (childText = 1 === item.GameCount ? globalize.translate("sharedcomponents#ValueOneGame") : globalize.translate("sharedcomponents#ValueGameCount", item.GameCount), counts.push(childText))) : "GameGenre" === item.Type ? item.GameCount && (childText = 1 === item.GameCount ? globalize.translate("sharedcomponents#ValueOneGame") : globalize.translate("sharedcomponents#ValueGameCount", item.GameCount), counts.push(childText)) : "MusicGenre" === item.Type || "MusicArtist" === options.context ? (item.AlbumCount && (childText = 1 === item.AlbumCount ? globalize.translate("sharedcomponents#ValueOneAlbum") : globalize.translate("sharedcomponents#ValueAlbumCount", item.AlbumCount), counts.push(childText)), item.SongCount && (childText = 1 === item.SongCount ? globalize.translate("sharedcomponents#ValueOneSong") : globalize.translate("sharedcomponents#ValueSongCount", item.SongCount), counts.push(childText)), item.MusicVideoCount && (childText = 1 === item.MusicVideoCount ? globalize.translate("sharedcomponents#ValueOneMusicVideo") : globalize.translate("sharedcomponents#ValueMusicVideoCount", item.MusicVideoCount), counts.push(childText))) : "Series" === item.Type && (childText = 1 === item.RecursiveItemCount ? globalize.translate("sharedcomponents#ValueOneEpisode") : globalize.translate("sharedcomponents#ValueEpisodeCount", item.RecursiveItemCount), counts.push(childText)); + return counts.join(", ") + } + + function requireRefreshIndicator() { + refreshIndicatorLoaded || (refreshIndicatorLoaded = !0, require(["emby-itemrefreshindicator"])) + } + + function getDefaultBackgroundClass(str) { + return "defaultCardBackground defaultCardBackground" + getDefaultColorIndex(str) + } + + function buildCard(index, item, apiClient, options) { + var action = options.action || "link"; + "play" === action && item.IsFolder ? action = "link" : "Photo" === item.MediaType && (action = "play"); + var shape = options.shape; + if ("mixed" === shape) { + shape = null; + var primaryImageAspectRatio = item.PrimaryImageAspectRatio; + primaryImageAspectRatio && (shape = primaryImageAspectRatio >= 1.33 ? "mixedBackdrop" : primaryImageAspectRatio > .71 ? "mixedSquare" : "mixedPortrait"), shape = shape || "mixedSquare" + } + var className = "card"; + shape && (className += " " + shape + "Card"), options.cardCssClass && (className += " " + options.cardCssClass), options.cardClass && (className += " " + options.cardClass), layoutManager.desktop && (className += " card-hoverable"), enableFocusTransfrom && layoutManager.tv || (className += " card-nofocustransform"); + var imgInfo = getCardImageUrl(item, apiClient, options, shape), + imgUrl = imgInfo.imgUrl, + forceName = imgInfo.forceName, + showTitle = "auto" === options.showTitle || (options.showTitle || "PhotoAlbum" === item.Type || "Folder" === item.Type), + overlayText = options.overlayText; + forceName && !options.cardLayout && null == overlayText && (overlayText = !0); + var cardImageContainerClass = "cardImageContainer"; + (options.coverImage || imgInfo.coverImage) && (cardImageContainerClass += " coveredImage", ("Photo" === item.MediaType || "PhotoAlbum" === item.Type || "Folder" === item.Type || item.ProgramInfo || "Program" === item.Type || "Recording" === item.Type) && (cardImageContainerClass += " coveredImage-noScale")), imgUrl || (cardImageContainerClass += " " + getDefaultBackgroundClass(item.Name)); + var cardBoxClass = options.cardLayout ? "cardBox visualCardBox" : "cardBox"; + layoutManager.tv && (cardBoxClass += enableFocusTransfrom ? " cardBox-focustransform cardBox-withfocuscontent" : " cardBox-withfocuscontent-large", options.cardLayout && (cardBoxClass += " card-focuscontent", enableFocusTransfrom || (cardBoxClass += " card-focuscontent-large"))); + var footerCssClass, logoUrl, progressHtml = indicators.getProgressBarHtml(item), + innerCardFooter = "", + footerOverlayed = !1; + options.showChannelLogo && item.ChannelPrimaryImageTag ? logoUrl = apiClient.getScaledImageUrl(item.ChannelId, { + type: "Primary", + height: 40, + tag: item.ChannelPrimaryImageTag + }) : options.showLogo && item.ParentLogoImageTag && (logoUrl = apiClient.getScaledImageUrl(item.ParentLogoItemId, { + type: "Logo", + height: 40, + tag: item.ParentLogoImageTag + })), overlayText ? (logoUrl = null, footerCssClass = progressHtml ? "innerCardFooter fullInnerCardFooter" : "innerCardFooter", innerCardFooter += getCardFooterText(item, apiClient, options, showTitle, forceName, overlayText, imgUrl, footerCssClass, progressHtml, logoUrl, !1), footerOverlayed = !0) : progressHtml && (innerCardFooter += '
', innerCardFooter += progressHtml, innerCardFooter += "
", progressHtml = ""); + var mediaSourceCount = item.MediaSourceCount || 1; + mediaSourceCount > 1 && (innerCardFooter += '
' + mediaSourceCount + "
"); + var outerCardFooter = ""; + overlayText || footerOverlayed || (footerCssClass = options.cardLayout ? "cardFooter" : "cardFooter cardFooter-transparent", logoUrl && (footerCssClass += " cardFooter-withlogo"), options.cardLayout || (logoUrl = null), outerCardFooter = getCardFooterText(item, apiClient, options, showTitle, forceName, overlayText, imgUrl, footerCssClass, progressHtml, logoUrl, !0)), outerCardFooter && !options.cardLayout && (cardBoxClass += " cardBox-bottompadded"); + var overlayButtons = ""; + if (layoutManager.mobile) { + var overlayPlayButton = options.overlayPlayButton; + null != overlayPlayButton || options.overlayMoreButton || options.overlayInfoButton || options.cardLayout || (overlayPlayButton = "Video" === item.MediaType); + var btnCssClass = "cardOverlayButton cardOverlayButton-br itemAction"; + options.centerPlayButton && (overlayButtons += ''), !overlayPlayButton || item.IsPlaceHolder || "Virtual" === item.LocationType && item.MediaType && "Program" !== item.Type || "Person" === item.Type || (overlayButtons += ''), options.overlayMoreButton && (overlayButtons += '') + } + options.showChildCountIndicator && item.ChildCount && (className += " groupedCard"); + var cardImageContainerOpen, cardImageContainerClose = "", + cardBoxClose = "", + cardScalableClose = "", + cardContentClass = "cardContent"; + options.cardLayout || (cardContentClass += " cardContent-shadow"), layoutManager.tv ? (cardImageContainerOpen = imgUrl ? '
' : '
', cardImageContainerClose = "
") : (cardImageContainerOpen = imgUrl ? '"); + var cardScalableClass = "cardScalable"; + layoutManager.tv && !options.cardLayout && (cardScalableClass += " card-focuscontent", enableFocusTransfrom || (cardScalableClass += " card-focuscontent-large")), cardImageContainerOpen = '
' + cardImageContainerOpen, cardBoxClose = "
", cardScalableClose = "
"; + var indicatorsHtml = ""; + if (!1 !== options.missingIndicator && (indicatorsHtml += indicators.getMissingIndicator(item)), indicatorsHtml += indicators.getSyncIndicator(item), indicatorsHtml += indicators.getTimerIndicator(item), indicatorsHtml += indicators.getTypeIndicator(item), options.showGroupCount ? indicatorsHtml += indicators.getChildCountIndicatorHtml(item, { + minCount: 1 + }) : indicatorsHtml += indicators.getPlayedIndicatorHtml(item), "CollectionFolder" === item.Type || item.CollectionType) { + indicatorsHtml += '
', requireRefreshIndicator() + } + indicatorsHtml && (cardImageContainerOpen += '
' + indicatorsHtml + "
"), imgUrl || (cardImageContainerOpen += getCardDefaultText(item, options)); + var tagName = layoutManager.tv && !overlayButtons ? "button" : "div", + nameWithPrefix = item.SortName || item.Name || "", + prefix = nameWithPrefix.substring(0, Math.min(3, nameWithPrefix.length)); + prefix && (prefix = prefix.toUpperCase()); + var timerAttributes = ""; + item.TimerId && (timerAttributes += ' data-timerid="' + item.TimerId + '"'), item.SeriesTimerId && (timerAttributes += ' data-seriestimerid="' + item.SeriesTimerId + '"'); + var actionAttribute; + "button" === tagName ? (className += " itemAction", actionAttribute = ' data-action="' + action + '"') : actionAttribute = "", "MusicAlbum" !== item.Type && "MusicArtist" !== item.Type && "Audio" !== item.Type && (className += " card-withuserdata"); + var positionTicksData = item.UserData && item.UserData.PlaybackPositionTicks ? ' data-positionticks="' + item.UserData.PlaybackPositionTicks + '"' : "", + collectionIdData = options.collectionId ? ' data-collectionid="' + options.collectionId + '"' : "", + playlistIdData = options.playlistId ? ' data-playlistid="' + options.playlistId + '"' : "", + mediaTypeData = item.MediaType ? ' data-mediatype="' + item.MediaType + '"' : "", + collectionTypeData = item.CollectionType ? ' data-collectiontype="' + item.CollectionType + '"' : "", + channelIdData = item.ChannelId ? ' data-channelid="' + item.ChannelId + '"' : "", + contextData = options.context ? ' data-context="' + options.context + '"' : "", + parentIdData = options.parentId ? ' data-parentid="' + options.parentId + '"' : "", + additionalCardContent = ""; + return layoutManager.desktop && (additionalCardContent += getHoverMenuHtml(item, action)), "<" + tagName + ' data-index="' + index + '"' + timerAttributes + actionAttribute + ' data-isfolder="' + (item.IsFolder || !1) + '" data-serverid="' + (item.ServerId || options.serverId) + '" data-id="' + (item.Id || item.ItemId) + '" data-type="' + item.Type + '"' + mediaTypeData + collectionTypeData + channelIdData + positionTicksData + collectionIdData + playlistIdData + contextData + parentIdData + ' data-prefix="' + prefix + '" class="' + className + '">' + cardImageContainerOpen + innerCardFooter + cardImageContainerClose + overlayButtons + additionalCardContent + cardScalableClose + outerCardFooter + cardBoxClose + "" + } + + function getHoverMenuHtml(item, action) { + var html = ""; + html += '
'; + var btnCssClass = "cardOverlayButton cardOverlayButton-hover itemAction"; + playbackManager.canPlay(item) && (html += ''), html += '
'; + var userData = item.UserData || {}; + if (itemHelper.canMarkPlayed(item) && (require(["emby-playstatebutton"]), html += ''), itemHelper.canRate(item)) { + var likes = null == userData.Likes ? "" : userData.Likes; + require(["emby-ratingbutton"]), html += '' + } + return html += '', html += "
", html += "
" + } + + function getCardDefaultText(item, options) { + var collectionType = item.CollectionType; + return "livetv" === collectionType ? '' : "homevideos" === collectionType || "photos" === collectionType ? '' : "music" === collectionType ? '' : "MusicAlbum" === item.Type ? '' : "MusicArtist" === item.Type || "Person" === item.Type ? '' : options.defaultCardImageIcon ? '' + options.defaultCardImageIcon + "" : '
' + (isUsingLiveTvNaming(item) ? item.Name : itemHelper.getDisplayName(item)) + "
" + } + + function buildCards(items, options) { + if (document.body.contains(options.itemsContainer)) { + if (options.parentContainer) { + if (!items.length) return void options.parentContainer.classList.add("hide"); + options.parentContainer.classList.remove("hide") + } + var html = buildCardsHtmlInternal(items, options); + html ? (options.itemsContainer.cardBuilderHtml !== html && (options.itemsContainer.innerHTML = html, items.length < 50 ? options.itemsContainer.cardBuilderHtml = html : options.itemsContainer.cardBuilderHtml = null), imageLoader.lazyChildren(options.itemsContainer)) : (options.itemsContainer.innerHTML = html, options.itemsContainer.cardBuilderHtml = null), options.autoFocus && focusManager.autoFocus(options.itemsContainer, !0) + } + } + + function ensureIndicators(card, indicatorsElem) { + if (indicatorsElem) return indicatorsElem; + if (!(indicatorsElem = card.querySelector(".cardIndicators"))) { + var cardImageContainer = card.querySelector(".cardImageContainer"); + indicatorsElem = document.createElement("div"), + indicatorsElem.classList.add("cardIndicators"), cardImageContainer.appendChild(indicatorsElem) + } + return indicatorsElem + } + + function updateUserData(card, userData) { + var type = card.getAttribute("data-type"), + enableCountIndicator = "Series" === type || "BoxSet" === type || "Season" === type, + indicatorsElem = null, + playedIndicator = null, + countIndicator = null, + itemProgressBar = null; + userData.Played ? (playedIndicator = card.querySelector(".playedIndicator"), playedIndicator || (playedIndicator = document.createElement("div"), playedIndicator.classList.add("playedIndicator"), playedIndicator.classList.add("indicator"), indicatorsElem = ensureIndicators(card, indicatorsElem), indicatorsElem.appendChild(playedIndicator)), playedIndicator.innerHTML = '') : (playedIndicator = card.querySelector(".playedIndicator")) && playedIndicator.parentNode.removeChild(playedIndicator), userData.UnplayedItemCount ? (countIndicator = card.querySelector(".countIndicator"), countIndicator || (countIndicator = document.createElement("div"), countIndicator.classList.add("countIndicator"), indicatorsElem = ensureIndicators(card, indicatorsElem), indicatorsElem.appendChild(countIndicator)), countIndicator.innerHTML = userData.UnplayedItemCount) : enableCountIndicator && (countIndicator = card.querySelector(".countIndicator")) && countIndicator.parentNode.removeChild(countIndicator); + var progressHtml = indicators.getProgressBarHtml({ + Type: type, + UserData: userData, + MediaType: "Video" + }); + if (progressHtml) { + if (!(itemProgressBar = card.querySelector(".itemProgressBar"))) { + itemProgressBar = document.createElement("div"), itemProgressBar.classList.add("itemProgressBar"); + var innerCardFooter = card.querySelector(".innerCardFooter"); + if (!innerCardFooter) { + innerCardFooter = document.createElement("div"), innerCardFooter.classList.add("innerCardFooter"); + card.querySelector(".cardImageContainer").appendChild(innerCardFooter) + } + innerCardFooter.appendChild(itemProgressBar) + } + itemProgressBar.innerHTML = progressHtml + } else(itemProgressBar = card.querySelector(".itemProgressBar")) && itemProgressBar.parentNode.removeChild(itemProgressBar) + } + + function onUserDataChanged(userData, scope) { + for (var cards = (scope || document.body).querySelectorAll('.card-withuserdata[data-id="' + userData.ItemId + '"]'), i = 0, length = cards.length; i < length; i++) updateUserData(cards[i], userData) + } + + function onTimerCreated(programId, newTimerId, itemsContainer) { + for (var cells = itemsContainer.querySelectorAll('.card[data-id="' + programId + '"]'), i = 0, length = cells.length; i < length; i++) { + var cell = cells[i]; + if (!cell.querySelector(".timerIndicator")) { + ensureIndicators(cell).insertAdjacentHTML("beforeend", '') + } + cell.setAttribute("data-timerid", newTimerId) + } + } + + function onTimerCancelled(id, itemsContainer) { + for (var cells = itemsContainer.querySelectorAll('.card[data-timerid="' + id + '"]'), i = 0, length = cells.length; i < length; i++) { + var cell = cells[i], + icon = cell.querySelector(".timerIndicator"); + icon && icon.parentNode.removeChild(icon), cell.removeAttribute("data-timerid") + } + } + + function onSeriesTimerCancelled(id, itemsContainer) { + for (var cells = itemsContainer.querySelectorAll('.card[data-seriestimerid="' + id + '"]'), i = 0, length = cells.length; i < length; i++) { + var cell = cells[i], + icon = cell.querySelector(".timerIndicator"); + icon && icon.parentNode.removeChild(icon), cell.removeAttribute("data-seriestimerid") + } + } + var refreshIndicatorLoaded, enableFocusTransfrom = (window.devicePixelRatio, !browser.slow && !browser.edge), + numRandomColors = 5; + return { + getCardsHtml: getCardsHtml, + buildCards: buildCards, + onUserDataChanged: onUserDataChanged, + onTimerCreated: onTimerCreated, + onTimerCancelled: onTimerCancelled, + onSeriesTimerCancelled: onSeriesTimerCancelled + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/cardbuilder/chaptercardbuilder.js b/dashboard-ui/bower_components/emby-webcomponents/cardbuilder/chaptercardbuilder.js index cf7af0cae0..55ff68eb5a 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/cardbuilder/chaptercardbuilder.js +++ b/dashboard-ui/bower_components/emby-webcomponents/cardbuilder/chaptercardbuilder.js @@ -1 +1,59 @@ -define(["datetime","imageLoader","connectionManager","layoutManager","browser"],function(datetime,imageLoader,connectionManager,layoutManager,browser){"use strict";function buildChapterCardsHtml(item,chapters,options){var className="card itemAction chapterCard";layoutManager.tv&&(browser.animate||browser.edge)&&(className+=" card-focusscale");var mediaStreams=((item.MediaSources||[])[0]||{}).MediaStreams||[],videoStream=mediaStreams.filter(function(i){return"Video"===i.Type})[0]||{},shape=options.backdropShape||"backdrop";videoStream.Width&&videoStream.Height&&videoStream.Width/videoStream.Height<=1.2&&(shape=options.squareShape||"square"),className+=" "+shape+"Card",(options.block||options.rows)&&(className+=" block");for(var html="",itemsInRow=0,apiClient=connectionManager.getApiClient(item.ServerId),i=0,length=chapters.length;i');html+=buildChapterCard(item,apiClient,chapters[i],i,options,className,shape),itemsInRow++,options.rows&&itemsInRow>=options.rows&&(itemsInRow=0,html+="
")}return html}function getImgUrl(item,chapter,index,maxWidth,apiClient){return chapter.ImageTag?apiClient.getScaledImageUrl(item.Id,{maxWidth:maxWidth,tag:chapter.ImageTag,type:"Chapter",index:index}):null}function buildChapterCard(item,apiClient,chapter,index,options,className,shape){var imgUrl=getImgUrl(item,chapter,index,options.width||400,apiClient),cardImageContainerClass="cardContent cardContent-shadow cardImageContainer chapterCardImageContainer";options.coverImage&&(cardImageContainerClass+=" coveredImage");var dataAttributes=' data-action="play" data-isfolder="'+item.IsFolder+'" data-id="'+item.Id+'" data-serverid="'+item.ServerId+'" data-type="'+item.Type+'" data-mediatype="'+item.MediaType+'" data-positionticks="'+chapter.StartPositionTicks+'"',cardImageContainer=imgUrl?'
':'
';imgUrl||(cardImageContainer+='local_movies');var nameHtml="";nameHtml+='
'+chapter.Name+"
",nameHtml+='
'+datetime.getDisplayRunningTime(chapter.StartPositionTicks)+"
";var cardBoxCssClass="cardBox",cardScalableClass="cardScalable";if(layoutManager.tv){var enableFocusTransfrom=!browser.slow&&!browser.edge;cardScalableClass+=" card-focuscontent",enableFocusTransfrom?cardBoxCssClass+=" cardBox-focustransform cardBox-withfocuscontent":(cardBoxCssClass+=" cardBox-withfocuscontent-large",cardScalableClass+=" card-focuscontent-large")}return'
"}function buildChapterCards(item,chapters,options){if(options.parentContainer){if(!document.body.contains(options.parentContainer))return;if(!chapters.length)return void options.parentContainer.classList.add("hide");options.parentContainer.classList.remove("hide")}var html=buildChapterCardsHtml(item,chapters,options);options.itemsContainer.innerHTML=html,imageLoader.lazyChildren(options.itemsContainer)}return{buildChapterCards:buildChapterCards}}); \ No newline at end of file +define(["datetime", "imageLoader", "connectionManager", "layoutManager", "browser"], function(datetime, imageLoader, connectionManager, layoutManager, browser) { + "use strict"; + + function buildChapterCardsHtml(item, chapters, options) { + var className = "card itemAction chapterCard"; + layoutManager.tv && (browser.animate || browser.edge) && (className += " card-focusscale"); + var mediaStreams = ((item.MediaSources || [])[0] || {}).MediaStreams || [], + videoStream = mediaStreams.filter(function(i) { + return "Video" === i.Type + })[0] || {}, + shape = options.backdropShape || "backdrop"; + videoStream.Width && videoStream.Height && videoStream.Width / videoStream.Height <= 1.2 && (shape = options.squareShape || "square"), className += " " + shape + "Card", (options.block || options.rows) && (className += " block"); + for (var html = "", itemsInRow = 0, apiClient = connectionManager.getApiClient(item.ServerId), i = 0, length = chapters.length; i < length; i++) { + options.rows && 0 === itemsInRow && (html += '
'); + html += buildChapterCard(item, apiClient, chapters[i], i, options, className, shape), itemsInRow++, options.rows && itemsInRow >= options.rows && (itemsInRow = 0, html += "
") + } + return html + } + + function getImgUrl(item, chapter, index, maxWidth, apiClient) { + return chapter.ImageTag ? apiClient.getScaledImageUrl(item.Id, { + maxWidth: maxWidth, + tag: chapter.ImageTag, + type: "Chapter", + index: index + }) : null + } + + function buildChapterCard(item, apiClient, chapter, index, options, className, shape) { + var imgUrl = getImgUrl(item, chapter, index, options.width || 400, apiClient), + cardImageContainerClass = "cardContent cardContent-shadow cardImageContainer chapterCardImageContainer"; + options.coverImage && (cardImageContainerClass += " coveredImage"); + var dataAttributes = ' data-action="play" data-isfolder="' + item.IsFolder + '" data-id="' + item.Id + '" data-serverid="' + item.ServerId + '" data-type="' + item.Type + '" data-mediatype="' + item.MediaType + '" data-positionticks="' + chapter.StartPositionTicks + '"', + cardImageContainer = imgUrl ? '
' : '
'; + imgUrl || (cardImageContainer += 'local_movies'); + var nameHtml = ""; + nameHtml += '
' + chapter.Name + "
", nameHtml += '
' + datetime.getDisplayRunningTime(chapter.StartPositionTicks) + "
"; + var cardBoxCssClass = "cardBox", + cardScalableClass = "cardScalable"; + if (layoutManager.tv) { + var enableFocusTransfrom = !browser.slow && !browser.edge; + cardScalableClass += " card-focuscontent", enableFocusTransfrom ? cardBoxCssClass += " cardBox-focustransform cardBox-withfocuscontent" : (cardBoxCssClass += " cardBox-withfocuscontent-large", cardScalableClass += " card-focuscontent-large") + } + return '
" + } + + function buildChapterCards(item, chapters, options) { + if (options.parentContainer) { + if (!document.body.contains(options.parentContainer)) return; + if (!chapters.length) return void options.parentContainer.classList.add("hide"); + options.parentContainer.classList.remove("hide") + } + var html = buildChapterCardsHtml(item, chapters, options); + options.itemsContainer.innerHTML = html, imageLoader.lazyChildren(options.itemsContainer) + } + return { + buildChapterCards: buildChapterCards + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/cardbuilder/peoplecardbuilder.js b/dashboard-ui/bower_components/emby-webcomponents/cardbuilder/peoplecardbuilder.js index 41cc212ce0..4dc70f7ed4 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/cardbuilder/peoplecardbuilder.js +++ b/dashboard-ui/bower_components/emby-webcomponents/cardbuilder/peoplecardbuilder.js @@ -1 +1,18 @@ -define(["cardBuilder"],function(cardBuilder){"use strict";function buildPeopleCards(items,options){options=Object.assign(options||{},{cardLayout:!1,centerText:!0,showTitle:!0,cardFooterAside:"none",showPersonRoleOrType:!0,cardCssClass:"personCard",defaultCardImageIcon:""}),cardBuilder.buildCards(items,options)}return{buildPeopleCards:buildPeopleCards}}); \ No newline at end of file +define(["cardBuilder"], function(cardBuilder) { + "use strict"; + + function buildPeopleCards(items, options) { + options = Object.assign(options || {}, { + cardLayout: !1, + centerText: !0, + showTitle: !0, + cardFooterAside: "none", + showPersonRoleOrType: !0, + cardCssClass: "personCard", + defaultCardImageIcon: "" + }), cardBuilder.buildCards(items, options) + } + return { + buildPeopleCards: buildPeopleCards + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/chromecast/chromecasthelpers.js b/dashboard-ui/bower_components/emby-webcomponents/chromecast/chromecasthelpers.js index 45b034b1e6..e3330bf37e 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/chromecast/chromecasthelpers.js +++ b/dashboard-ui/bower_components/emby-webcomponents/chromecast/chromecasthelpers.js @@ -1 +1,67 @@ -define(["events"],function(events){"use strict";function isValidIpAddress(address){return 1==LinkParser.parse(address).length}function isLocalIpAddress(address){return address=address.toLowerCase(),-1!==address.indexOf("127.0.0.1")||-1!==address.indexOf("localhost")}function getServerAddress(apiClient){var serverAddress=apiClient.serverAddress();if(isValidIpAddress(serverAddress)&&!isLocalIpAddress(serverAddress))return Promise.resolve(serverAddress);var cachedValue=getCachedValue(serverAddress);return cachedValue?Promise.resolve(cachedValue):apiClient.getEndpointInfo().then(function(endpoint){return endpoint.IsInNetwork?apiClient.getPublicSystemInfo().then(function(info){return addToCache(serverAddress,info.LocalAddress),info.LocalAddress}):(addToCache(serverAddress,serverAddress),serverAddress)})}function clearCache(){cache={}}function addToCache(key,value){cache[key]={value:value,time:(new Date).getTime()}}function getCachedValue(key){var obj=cache[key];return obj&&(new Date).getTime()-obj.time<18e4?obj.value:null}!function(){function ensureProtocol(url){return url.match(protocolRegExp)||(url="http://"+url),url}var protocols="(?:(?:http|https|rtsp|ftp):\\/\\/)",linkRegExp=RegExp("(?:(?:(?:http|https|rtsp|ftp):\\/\\/)?(?:(?:[a-z0-9\\$\\-\\_\\.\\+\\!\\*\\'\\(\\)\\,\\;\\?\\&\\=]|(?:\\%[a-f0-9]{2})){1,64}(?:\\:(?:[a-z0-9\\$\\-\\_\\.\\+\\!\\*\\'\\(\\)\\,\\;\\?\\&\\=]|(?:\\%[a-f0-9]{2})){1,25})?\\@)?(?:((([0-9A-Fa-f]{1,4}:){7}([0-9A-Fa-f]{1,4}|:))|(([0-9A-Fa-f]{1,4}:){6}(:[0-9A-Fa-f]{1,4}|((25[0-5]|2[0-4]d|1dd|[1-9]?d)(.(25[0-5]|2[0-4]d|1dd|[1-9]?d)){3})|:))|(([0-9A-Fa-f]{1,4}:){5}(((:[0-9A-Fa-f]{1,4}){1,2})|:((25[0-5]|2[0-4]d|1dd|[1-9]?d)(.(25[0-5]|2[0-4]d|1dd|[1-9]?d)){3})|:))|(([0-9A-Fa-f]{1,4}:){4}(((:[0-9A-Fa-f]{1,4}){1,3})|((:[0-9A-Fa-f]{1,4})?:((25[0-5]|2[0-4]d|1dd|[1-9]?d)(.(25[0-5]|2[0-4]d|1dd|[1-9]?d)){3}))|:))|(([0-9A-Fa-f]{1,4}:){3}(((:[0-9A-Fa-f]{1,4}){1,4})|((:[0-9A-Fa-f]{1,4}){0,2}:((25[0-5]|2[0-4]d|1dd|[1-9]?d)(.(25[0-5]|2[0-4]d|1dd|[1-9]?d)){3}))|:))|(([0-9A-Fa-f]{1,4}:){2}(((:[0-9A-Fa-f]{1,4}){1,5})|((:[0-9A-Fa-f]{1,4}){0,3}:((25[0-5]|2[0-4]d|1dd|[1-9]?d)(.(25[0-5]|2[0-4]d|1dd|[1-9]?d)){3}))|:))|(([0-9A-Fa-f]{1,4}:){1}(((:[0-9A-Fa-f]{1,4}){1,6})|((:[0-9A-Fa-f]{1,4}){0,4}:((25[0-5]|2[0-4]d|1dd|[1-9]?d)(.(25[0-5]|2[0-4]d|1dd|[1-9]?d)){3}))|:))|(:(((:[0-9A-Fa-f]{1,4}){1,7})|((:[0-9A-Fa-f]{1,4}){0,5}:((25[0-5]|2[0-4]d|1dd|[1-9]?d)(.(25[0-5]|2[0-4]d|1dd|[1-9]?d)){3}))|:)))(%.+)?|(?:25[0-5]|2[0-4][0-9]|[0-1][0-9]{2}|[1-9][0-9]|[1-9])\\.(?:25[0-5]|2[0-4][0-9]|[0-1][0-9]{2}|[1-9][0-9]|[1-9]|0)\\.(?:25[0-5]|2[0-4][0-9]|[0-1][0-9]{2}|[1-9][0-9]|[1-9]|0)\\.(?:25[0-5]|2[0-4][0-9]|[0-1][0-9]{2}|[1-9][0-9]|[0-9])))(?:\\:\\d{1,5})?(?:\\/(?:(?:[a-z0-9\\/\\@\\&\\#\\~\\*\\_\\-\\+])|(?:\\%[a-f0-9]{2})|(?:[\\;\\?\\:\\.\\!\\'\\(\\)\\,\\=]+(?=(?:[a-z0-9\\/\\@\\&\\#\\~\\*\\_\\-\\+])|(?:\\%[a-f0-9]{2}))))*|\\b|$)","gi"),protocolRegExp=RegExp("^"+protocols,"i"),LinkParser={parse:function(text){for(var match,links=[];match=linkRegExp.exec(text);){var txt=match[0],pos=match.index,len=txt.length,url=ensureProtocol(text);links.push({pos:pos,text:txt,len:len,url:url})}return links}};window.LinkParser=LinkParser}();var cache={};return events.on(ConnectionManager,"localusersignedin",clearCache),events.on(ConnectionManager,"localusersignedout",clearCache),{getServerAddress:getServerAddress}}); \ No newline at end of file +define(["events"], function(events) { + "use strict"; + + function isValidIpAddress(address) { + return 1 == LinkParser.parse(address).length + } + + function isLocalIpAddress(address) { + return address = address.toLowerCase(), -1 !== address.indexOf("127.0.0.1") || -1 !== address.indexOf("localhost") + } + + function getServerAddress(apiClient) { + var serverAddress = apiClient.serverAddress(); + if (isValidIpAddress(serverAddress) && !isLocalIpAddress(serverAddress)) return Promise.resolve(serverAddress); + var cachedValue = getCachedValue(serverAddress); + return cachedValue ? Promise.resolve(cachedValue) : apiClient.getEndpointInfo().then(function(endpoint) { + return endpoint.IsInNetwork ? apiClient.getPublicSystemInfo().then(function(info) { + return addToCache(serverAddress, info.LocalAddress), info.LocalAddress + }) : (addToCache(serverAddress, serverAddress), serverAddress) + }) + } + + function clearCache() { + cache = {} + } + + function addToCache(key, value) { + cache[key] = { + value: value, + time: (new Date).getTime() + } + } + + function getCachedValue(key) { + var obj = cache[key]; + return obj && (new Date).getTime() - obj.time < 18e4 ? obj.value : null + }! function() { + function ensureProtocol(url) { + return url.match(protocolRegExp) || (url = "http://" + url), url + } + var protocols = "(?:(?:http|https|rtsp|ftp):\\/\\/)", + linkRegExp = RegExp("(?:(?:(?:http|https|rtsp|ftp):\\/\\/)?(?:(?:[a-z0-9\\$\\-\\_\\.\\+\\!\\*\\'\\(\\)\\,\\;\\?\\&\\=]|(?:\\%[a-f0-9]{2})){1,64}(?:\\:(?:[a-z0-9\\$\\-\\_\\.\\+\\!\\*\\'\\(\\)\\,\\;\\?\\&\\=]|(?:\\%[a-f0-9]{2})){1,25})?\\@)?(?:((([0-9A-Fa-f]{1,4}:){7}([0-9A-Fa-f]{1,4}|:))|(([0-9A-Fa-f]{1,4}:){6}(:[0-9A-Fa-f]{1,4}|((25[0-5]|2[0-4]d|1dd|[1-9]?d)(.(25[0-5]|2[0-4]d|1dd|[1-9]?d)){3})|:))|(([0-9A-Fa-f]{1,4}:){5}(((:[0-9A-Fa-f]{1,4}){1,2})|:((25[0-5]|2[0-4]d|1dd|[1-9]?d)(.(25[0-5]|2[0-4]d|1dd|[1-9]?d)){3})|:))|(([0-9A-Fa-f]{1,4}:){4}(((:[0-9A-Fa-f]{1,4}){1,3})|((:[0-9A-Fa-f]{1,4})?:((25[0-5]|2[0-4]d|1dd|[1-9]?d)(.(25[0-5]|2[0-4]d|1dd|[1-9]?d)){3}))|:))|(([0-9A-Fa-f]{1,4}:){3}(((:[0-9A-Fa-f]{1,4}){1,4})|((:[0-9A-Fa-f]{1,4}){0,2}:((25[0-5]|2[0-4]d|1dd|[1-9]?d)(.(25[0-5]|2[0-4]d|1dd|[1-9]?d)){3}))|:))|(([0-9A-Fa-f]{1,4}:){2}(((:[0-9A-Fa-f]{1,4}){1,5})|((:[0-9A-Fa-f]{1,4}){0,3}:((25[0-5]|2[0-4]d|1dd|[1-9]?d)(.(25[0-5]|2[0-4]d|1dd|[1-9]?d)){3}))|:))|(([0-9A-Fa-f]{1,4}:){1}(((:[0-9A-Fa-f]{1,4}){1,6})|((:[0-9A-Fa-f]{1,4}){0,4}:((25[0-5]|2[0-4]d|1dd|[1-9]?d)(.(25[0-5]|2[0-4]d|1dd|[1-9]?d)){3}))|:))|(:(((:[0-9A-Fa-f]{1,4}){1,7})|((:[0-9A-Fa-f]{1,4}){0,5}:((25[0-5]|2[0-4]d|1dd|[1-9]?d)(.(25[0-5]|2[0-4]d|1dd|[1-9]?d)){3}))|:)))(%.+)?|(?:25[0-5]|2[0-4][0-9]|[0-1][0-9]{2}|[1-9][0-9]|[1-9])\\.(?:25[0-5]|2[0-4][0-9]|[0-1][0-9]{2}|[1-9][0-9]|[1-9]|0)\\.(?:25[0-5]|2[0-4][0-9]|[0-1][0-9]{2}|[1-9][0-9]|[1-9]|0)\\.(?:25[0-5]|2[0-4][0-9]|[0-1][0-9]{2}|[1-9][0-9]|[0-9])))(?:\\:\\d{1,5})?(?:\\/(?:(?:[a-z0-9\\/\\@\\&\\#\\~\\*\\_\\-\\+])|(?:\\%[a-f0-9]{2})|(?:[\\;\\?\\:\\.\\!\\'\\(\\)\\,\\=]+(?=(?:[a-z0-9\\/\\@\\&\\#\\~\\*\\_\\-\\+])|(?:\\%[a-f0-9]{2}))))*|\\b|$)", "gi"), + protocolRegExp = RegExp("^" + protocols, "i"), + LinkParser = { + parse: function(text) { + for (var match, links = []; match = linkRegExp.exec(text);) { + var txt = match[0], + pos = match.index, + len = txt.length, + url = ensureProtocol(text); + links.push({ + pos: pos, + text: txt, + len: len, + url: url + }) + } + return links + } + }; + window.LinkParser = LinkParser + }(); + var cache = {}; + return events.on(ConnectionManager, "localusersignedin", clearCache), events.on(ConnectionManager, "localusersignedout", clearCache), { + getServerAddress: getServerAddress + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/chromecast/chromecastplayer.js b/dashboard-ui/bower_components/emby-webcomponents/chromecast/chromecastplayer.js index b09ee406d7..08b28d1aec 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/chromecast/chromecastplayer.js +++ b/dashboard-ui/bower_components/emby-webcomponents/chromecast/chromecastplayer.js @@ -1 +1,425 @@ -define(["appSettings","userSettings","playbackManager","connectionManager","globalize","events","require","castSenderApiLoader"],function(appSettings,userSettings,playbackManager,connectionManager,globalize,events,require,castSenderApiLoader){"use strict";function sendConnectionResult(isOk){var resolve=currentResolve,reject=currentReject;currentResolve=null,currentReject=null,isOk?resolve&&resolve():reject?reject():playbackManager.removeActivePlayer(PlayerName)}function alertText(text,title){require(["alert"],function(alert){alert({text:text,title:title})})}function normalizeImages(state){if(state&&state.NowPlayingItem){var item=state.NowPlayingItem;item.ImageTags&&item.ImageTags.Primary||item.PrimaryImageTag&&(item.ImageTags=item.ImageTags||{},item.ImageTags.Primary=item.PrimaryImageTag),item.BackdropImageTag&&item.BackdropItemId===item.Id&&(item.BackdropImageTags=[item.BackdropImageTag]),item.BackdropImageTag&&item.BackdropItemId!==item.Id&&(item.ParentBackdropImageTags=[item.BackdropImageTag],item.ParentBackdropItemId=item.BackdropItemId)}}function getItemsForPlayback(apiClient,query){var userId=apiClient.getCurrentUserId();return query.Ids&&1===query.Ids.split(",").length?apiClient.getItem(userId,query.Ids.split(",")).then(function(item){return{Items:[item],TotalRecordCount:1}}):(query.Limit=query.Limit||100,query.ExcludeLocationTypes="Virtual",query.EnableTotalRecordCount=!1,apiClient.getItems(userId,query))}function bindEventForRelay(instance,eventName){events.on(instance._castPlayer,eventName,function(e,data){var state=instance.getPlayerStateInternal(data);events.trigger(instance,eventName,[state])})}function initializeChromecast(){var instance=this;instance._castPlayer=new CastPlayer,document.dispatchEvent(new CustomEvent("chromecastloaded",{detail:{player:instance}})),events.on(instance._castPlayer,"connect",function(e){currentResolve?sendConnectionResult(!0):playbackManager.setActivePlayer(PlayerName,instance.getCurrentTargetInfo()),console.log("cc: connect"),instance.lastPlayerData=null}),events.on(instance._castPlayer,"playbackstart",function(e,data){console.log("cc: playbackstart"),instance._castPlayer.initializeCastPlayer();var state=instance.getPlayerStateInternal(data);events.trigger(instance,"playbackstart",[state])}),events.on(instance._castPlayer,"playbackstop",function(e,data){console.log("cc: playbackstop");var state=instance.getPlayerStateInternal(data);events.trigger(instance,"playbackstop",[state]),instance.lastPlayerData={}}),events.on(instance._castPlayer,"playbackprogress",function(e,data){var state=instance.getPlayerStateInternal(data);events.trigger(instance,"timeupdate",[state])}),bindEventForRelay(instance,"timeupdate"),bindEventForRelay(instance,"pause"),bindEventForRelay(instance,"unpause"),bindEventForRelay(instance,"volumechange"),bindEventForRelay(instance,"repeatmodechange"),events.on(instance._castPlayer,"playstatechange",function(e,data){var state=instance.getPlayerStateInternal(data);events.trigger(instance,"pause",[state])})}function ChromecastPlayer(){this.name=PlayerName,this.type="mediaplayer",this.id="chromecast",this.isLocalPlayer=!1,this.lastPlayerData={},castSenderApiLoader.load().then(initializeChromecast.bind(this))}var currentResolve,currentReject,PlayerName="Chromecast",DEVICE_STATE={IDLE:0,ACTIVE:1,WARNING:2,ERROR:3},PLAYER_STATE={IDLE:"IDLE",LOADING:"LOADING",LOADED:"LOADED",PLAYING:"PLAYING",PAUSED:"PAUSED",STOPPED:"STOPPED",SEEKING:"SEEKING",ERROR:"ERROR"},CastPlayer=function(){this.deviceState=DEVICE_STATE.IDLE,this.currentMediaSession=null,this.session=null,this.castPlayerState=PLAYER_STATE.IDLE,this.hasReceivers=!1,this.errorHandler=this.onError.bind(this),this.mediaStatusUpdateHandler=this.onMediaStatusUpdate.bind(this),this.initializeCastPlayer()};return CastPlayer.prototype.initializeCastPlayer=function(){var chrome=window.chrome;if(chrome){if(!chrome.cast||!chrome.cast.isAvailable)return void setTimeout(this.initializeCastPlayer.bind(this),1e3);var sessionRequest=new chrome.cast.SessionRequest("2D4B1DA3"),apiConfig=new chrome.cast.ApiConfig(sessionRequest,this.sessionListener.bind(this),this.receiverListener.bind(this),"origin_scoped");console.log("chromecast.initialize"),chrome.cast.initialize(apiConfig,this.onInitSuccess.bind(this),this.errorHandler)}},CastPlayer.prototype.onInitSuccess=function(){this.isInitialized=!0,console.log("chromecast init success")},CastPlayer.prototype.onError=function(){console.log("chromecast error")},CastPlayer.prototype.sessionListener=function(e){this.session=e,this.session&&(this.session.media[0]&&this.onMediaDiscovered("activeSession",this.session.media[0]),this.onSessionConnected(e))},CastPlayer.prototype.messageListener=function(namespace,message){if("string"==typeof message&&(message=JSON.parse(message)),"playbackerror"===message.type){var errorCode=message.data;setTimeout(function(){alertText(globalize.translate("MessagePlaybackError"+errorCode),globalize.translate("HeaderPlaybackError"))},300)}else"connectionerror"===message.type?setTimeout(function(){alertText(globalize.translate("MessageChromecastConnectionError"),globalize.translate("HeaderError"))},300):message.type&&events.trigger(this,message.type,[message.data])},CastPlayer.prototype.receiverListener=function(e){this.hasReceivers="available"===e},CastPlayer.prototype.sessionUpdateListener=function(isAlive){isAlive||(this.session=null,this.deviceState=DEVICE_STATE.IDLE,this.castPlayerState=PLAYER_STATE.IDLE,this.currentMediaSession=null,sendConnectionResult(!1))},CastPlayer.prototype.launchApp=function(){chrome.cast.requestSession(this.onRequestSessionSuccess.bind(this),this.onLaunchError.bind(this))},CastPlayer.prototype.onRequestSessionSuccess=function(e){this.onSessionConnected(e)},CastPlayer.prototype.onSessionConnected=function(session){this.session=session,this.deviceState=DEVICE_STATE.ACTIVE,this.session.addMessageListener("urn:x-cast:com.connectsdk",this.messageListener.bind(this)),this.session.addMediaListener(this.sessionMediaListener.bind(this)),this.session.addUpdateListener(this.sessionUpdateListener.bind(this)),events.trigger(this,"connect"),this.sendMessage({options:{},command:"Identify"})},CastPlayer.prototype.sessionMediaListener=function(e){this.currentMediaSession=e,this.currentMediaSession.addUpdateListener(this.mediaStatusUpdateHandler)},CastPlayer.prototype.onLaunchError=function(){this.deviceState=DEVICE_STATE.ERROR,sendConnectionResult(!1)},CastPlayer.prototype.stopApp=function(){this.session&&this.session.stop(this.onStopAppSuccess.bind(this,"Session stopped"),this.errorHandler)},CastPlayer.prototype.onStopAppSuccess=function(message){this.deviceState=DEVICE_STATE.IDLE,this.castPlayerState=PLAYER_STATE.IDLE,this.currentMediaSession=null},CastPlayer.prototype.loadMedia=function(options,command){return this.session?(options.items=options.items.map(function(i){return{Id:i.Id,ServerId:i.ServerId,Name:i.Name,Type:i.Type,MediaType:i.MediaType,IsFolder:i.IsFolder}}),this.sendMessage({options:options,command:command})):Promise.reject()},CastPlayer.prototype.sendMessage=function(message){var player=this,receiverName=null,session=player.session;session&&session.receiver&&session.receiver.friendlyName&&(receiverName=session.receiver.friendlyName);var apiClient;apiClient=message.options&&message.options.ServerId?connectionManager.getApiClient(message.options.ServerId):message.options&&message.options.items&&message.options.items.length?connectionManager.getApiClient(message.options.items[0].ServerId):connectionManager.currentApiClient(),message=Object.assign(message,{userId:apiClient.getCurrentUserId(),deviceId:apiClient.deviceId(),accessToken:apiClient.accessToken(),serverAddress:apiClient.serverAddress(),serverId:apiClient.serverId(),serverVersion:apiClient.serverVersion(),receiverName:receiverName});var bitrateSetting=appSettings.maxChromecastBitrate();return bitrateSetting&&(message.maxBitrate=bitrateSetting),message.options&&message.options.items&&(message.subtitleAppearance=userSettings.getSubtitleAppearanceSettings(),message.subtitleBurnIn=appSettings.get("subtitleburnin")||""),new Promise(function(resolve,reject){require(["chromecastHelper"],function(chromecastHelper){chromecastHelper.getServerAddress(apiClient).then(function(serverAddress){message.serverAddress=serverAddress,player.sendMessageInternal(message).then(resolve,reject)},reject)})})},CastPlayer.prototype.sendMessageInternal=function(message){return message=JSON.stringify(message),this.session.sendMessage("urn:x-cast:com.connectsdk",message,this.onPlayCommandSuccess.bind(this),this.errorHandler),Promise.resolve()},CastPlayer.prototype.onPlayCommandSuccess=function(){},CastPlayer.prototype.onMediaDiscovered=function(how,mediaSession){this.currentMediaSession=mediaSession,"loadMedia"===how&&(this.castPlayerState=PLAYER_STATE.PLAYING),"activeSession"===how&&(this.castPlayerState=mediaSession.playerState),this.currentMediaSession.addUpdateListener(this.mediaStatusUpdateHandler)},CastPlayer.prototype.onMediaStatusUpdate=function(e){!1===e&&(this.castPlayerState=PLAYER_STATE.IDLE)},CastPlayer.prototype.setReceiverVolume=function(mute,vol){this.currentMediaSession&&(mute?this.session.setReceiverMuted(!0,this.mediaCommandSuccessCallback.bind(this),this.errorHandler):this.session.setReceiverVolumeLevel(vol||1,this.mediaCommandSuccessCallback.bind(this),this.errorHandler))},CastPlayer.prototype.mute=function(){this.setReceiverVolume(!0)},CastPlayer.prototype.mediaCommandSuccessCallback=function(info,e){},ChromecastPlayer.prototype.tryPair=function(target){var castPlayer=this._castPlayer;return castPlayer.deviceState!==DEVICE_STATE.ACTIVE&&castPlayer.isInitialized?new Promise(function(resolve,reject){currentResolve=resolve,currentReject=reject,castPlayer.launchApp()}):(currentResolve=null,currentReject=null,Promise.reject())},ChromecastPlayer.prototype.getTargets=function(){var targets=[];return this._castPlayer&&this._castPlayer.hasReceivers&&targets.push(this.getCurrentTargetInfo()),Promise.resolve(targets)},ChromecastPlayer.prototype.getCurrentTargetInfo=function(){var appName=null,castPlayer=this._castPlayer;return castPlayer.session&&castPlayer.session.receiver&&castPlayer.session.receiver.friendlyName&&(appName=castPlayer.session.receiver.friendlyName),{name:PlayerName,id:PlayerName,playerName:PlayerName,playableMediaTypes:["Audio","Video"],isLocalPlayer:!1,appName:PlayerName,deviceName:appName,supportedCommands:["VolumeUp","VolumeDown","Mute","Unmute","ToggleMute","SetVolume","SetAudioStreamIndex","SetSubtitleStreamIndex","DisplayContent","SetRepeatMode","EndSession","PlayMediaSource","PlayTrailers"]}},ChromecastPlayer.prototype.getPlayerStateInternal=function(data){var triggerStateChange=!1;return data&&!this.lastPlayerData&&(triggerStateChange=!0),data=data||this.lastPlayerData,this.lastPlayerData=data,normalizeImages(data),triggerStateChange&&events.trigger(this,"statechange",[data]),data},ChromecastPlayer.prototype.playWithCommand=function(options,command){if(!options.items){var apiClient=connectionManager.getApiClient(options.serverId),instance=this;return apiClient.getItem(apiClient.getCurrentUserId(),options.ids[0]).then(function(item){return options.items=[item],instance.playWithCommand(options,command)})}return this._castPlayer.loadMedia(options,command)},ChromecastPlayer.prototype.seek=function(position){position=parseInt(position),position/=1e7,this._castPlayer.sendMessage({options:{position:position},command:"Seek"})},ChromecastPlayer.prototype.setAudioStreamIndex=function(index){this._castPlayer.sendMessage({options:{index:index},command:"SetAudioStreamIndex"})},ChromecastPlayer.prototype.setSubtitleStreamIndex=function(index){this._castPlayer.sendMessage({options:{index:index},command:"SetSubtitleStreamIndex"})},ChromecastPlayer.prototype.setMaxStreamingBitrate=function(options){this._castPlayer.sendMessage({options:options,command:"SetMaxStreamingBitrate"})},ChromecastPlayer.prototype.isFullscreen=function(){var state=this.lastPlayerData||{};return state=state.PlayState||{},state.IsFullscreen},ChromecastPlayer.prototype.nextTrack=function(){this._castPlayer.sendMessage({options:{},command:"NextTrack"})},ChromecastPlayer.prototype.previousTrack=function(){this._castPlayer.sendMessage({options:{},command:"PreviousTrack"})},ChromecastPlayer.prototype.volumeDown=function(){this._castPlayer.sendMessage({options:{},command:"VolumeDown"})},ChromecastPlayer.prototype.endSession=function(){var instance=this;this.stop().then(function(){setTimeout(function(){instance._castPlayer.stopApp()},1e3)})},ChromecastPlayer.prototype.volumeUp=function(){this._castPlayer.sendMessage({options:{},command:"VolumeUp"})},ChromecastPlayer.prototype.setVolume=function(vol){vol=Math.min(vol,100),vol=Math.max(vol,0),this._castPlayer.sendMessage({options:{volume:vol},command:"SetVolume"})},ChromecastPlayer.prototype.unpause=function(){this._castPlayer.sendMessage({options:{},command:"Unpause"})},ChromecastPlayer.prototype.playPause=function(){this._castPlayer.sendMessage({options:{},command:"PlayPause"})},ChromecastPlayer.prototype.pause=function(){this._castPlayer.sendMessage({options:{},command:"Pause"})},ChromecastPlayer.prototype.stop=function(){return this._castPlayer.sendMessage({options:{},command:"Stop"})},ChromecastPlayer.prototype.displayContent=function(options){this._castPlayer.sendMessage({options:options,command:"DisplayContent"})},ChromecastPlayer.prototype.setMute=function(isMuted){var castPlayer=this._castPlayer;isMuted?castPlayer.sendMessage({options:{},command:"Mute"}):castPlayer.sendMessage({options:{},command:"Unmute"})},ChromecastPlayer.prototype.getRepeatMode=function(){var state=this.lastPlayerData||{};return state=state.PlayState||{},state.RepeatMode},ChromecastPlayer.prototype.playTrailers=function(item){this._castPlayer.sendMessage({options:{ItemId:item.Id,ServerId:item.ServerId},command:"PlayTrailers"})},ChromecastPlayer.prototype.setRepeatMode=function(mode){this._castPlayer.sendMessage({options:{RepeatMode:mode},command:"SetRepeatMode"})},ChromecastPlayer.prototype.toggleMute=function(){this._castPlayer.sendMessage({options:{},command:"ToggleMute"})},ChromecastPlayer.prototype.audioTracks=function(){var state=this.lastPlayerData||{};return state=state.NowPlayingItem||{},(state.MediaStreams||[]).filter(function(s){return"Audio"===s.Type})},ChromecastPlayer.prototype.getAudioStreamIndex=function(){var state=this.lastPlayerData||{};return state=state.PlayState||{},state.AudioStreamIndex},ChromecastPlayer.prototype.subtitleTracks=function(){var state=this.lastPlayerData||{};return state=state.NowPlayingItem||{},(state.MediaStreams||[]).filter(function(s){return"Subtitle"===s.Type})},ChromecastPlayer.prototype.getSubtitleStreamIndex=function(){var state=this.lastPlayerData||{};return state=state.PlayState||{},state.SubtitleStreamIndex},ChromecastPlayer.prototype.getMaxStreamingBitrate=function(){var state=this.lastPlayerData||{};return state=state.PlayState||{},state.MaxStreamingBitrate},ChromecastPlayer.prototype.getVolume=function(){var state=this.lastPlayerData||{};return state=state.PlayState||{},null==state.VolumeLevel?100:state.VolumeLevel},ChromecastPlayer.prototype.isPlaying=function(){return null!=(this.lastPlayerData||{}).NowPlayingItem},ChromecastPlayer.prototype.isPlayingVideo=function(){var state=this.lastPlayerData||{};return state=state.NowPlayingItem||{},"Video"===state.MediaType},ChromecastPlayer.prototype.isPlayingAudio=function(){var state=this.lastPlayerData||{};return state=state.NowPlayingItem||{},"Audio"===state.MediaType},ChromecastPlayer.prototype.currentTime=function(val){if(null!=val)return this.seek(val);var state=this.lastPlayerData||{};return state=state.PlayState||{},state.PositionTicks},ChromecastPlayer.prototype.duration=function(){var state=this.lastPlayerData||{};return state=state.NowPlayingItem||{},state.RunTimeTicks},ChromecastPlayer.prototype.getBufferedRanges=function(){var state=this.lastPlayerData||{};return state=state.PlayState||{},state.BufferedRanges||[]},ChromecastPlayer.prototype.paused=function(){var state=this.lastPlayerData||{};return state=state.PlayState||{},state.IsPaused},ChromecastPlayer.prototype.isMuted=function(){var state=this.lastPlayerData||{};return state=state.PlayState||{},state.IsMuted},ChromecastPlayer.prototype.shuffle=function(item){var apiClient=connectionManager.getApiClient(item.ServerId),userId=apiClient.getCurrentUserId(),instance=this;apiClient.getItem(userId,item.Id).then(function(item){instance.playWithCommand({items:[item]},"Shuffle")})},ChromecastPlayer.prototype.instantMix=function(item){var apiClient=connectionManager.getApiClient(item.ServerId),userId=apiClient.getCurrentUserId(),instance=this;apiClient.getItem(userId,item.Id).then(function(item){instance.playWithCommand({items:[item]},"InstantMix")})},ChromecastPlayer.prototype.canPlayMediaType=function(mediaType){return"audio"===(mediaType=(mediaType||"").toLowerCase())||"video"===mediaType},ChromecastPlayer.prototype.canQueueMediaType=function(mediaType){return this.canPlayMediaType(mediaType)},ChromecastPlayer.prototype.queue=function(options){this.playWithCommand(options,"PlayLast")},ChromecastPlayer.prototype.queueNext=function(options){this.playWithCommand(options,"PlayNext")},ChromecastPlayer.prototype.play=function(options){if(options.items)return this.playWithCommand(options,"PlayNow");if(!options.serverId)throw new Error("serverId required!");var instance=this;return getItemsForPlayback(connectionManager.getApiClient(options.serverId),{Ids:options.ids.join(",")}).then(function(result){return options.items=result.Items,instance.playWithCommand(options,"PlayNow")})},ChromecastPlayer.prototype.toggleFullscreen=function(){},ChromecastPlayer.prototype.beginPlayerUpdates=function(){},ChromecastPlayer.prototype.endPlayerUpdates=function(){},ChromecastPlayer.prototype.getPlaylist=function(){return Promise.resolve([])},ChromecastPlayer.prototype.getCurrentPlaylistItemId=function(){},ChromecastPlayer.prototype.setCurrentPlaylistItem=function(playlistItemId){return Promise.resolve()},ChromecastPlayer.prototype.removeFromPlaylist=function(playlistItemIds){return Promise.resolve()},ChromecastPlayer.prototype.getPlayerState=function(){return this.getPlayerStateInternal()||{}},ChromecastPlayer}); \ No newline at end of file +define(["appSettings", "userSettings", "playbackManager", "connectionManager", "globalize", "events", "require", "castSenderApiLoader"], function(appSettings, userSettings, playbackManager, connectionManager, globalize, events, require, castSenderApiLoader) { + "use strict"; + + function sendConnectionResult(isOk) { + var resolve = currentResolve, + reject = currentReject; + currentResolve = null, currentReject = null, isOk ? resolve && resolve() : reject ? reject() : playbackManager.removeActivePlayer(PlayerName) + } + + function alertText(text, title) { + require(["alert"], function(alert) { + alert({ + text: text, + title: title + }) + }) + } + + function normalizeImages(state) { + if (state && state.NowPlayingItem) { + var item = state.NowPlayingItem; + item.ImageTags && item.ImageTags.Primary || item.PrimaryImageTag && (item.ImageTags = item.ImageTags || {}, item.ImageTags.Primary = item.PrimaryImageTag), item.BackdropImageTag && item.BackdropItemId === item.Id && (item.BackdropImageTags = [item.BackdropImageTag]), item.BackdropImageTag && item.BackdropItemId !== item.Id && (item.ParentBackdropImageTags = [item.BackdropImageTag], item.ParentBackdropItemId = item.BackdropItemId) + } + } + + function getItemsForPlayback(apiClient, query) { + var userId = apiClient.getCurrentUserId(); + return query.Ids && 1 === query.Ids.split(",").length ? apiClient.getItem(userId, query.Ids.split(",")).then(function(item) { + return { + Items: [item], + TotalRecordCount: 1 + } + }) : (query.Limit = query.Limit || 100, query.ExcludeLocationTypes = "Virtual", query.EnableTotalRecordCount = !1, apiClient.getItems(userId, query)) + } + + function bindEventForRelay(instance, eventName) { + events.on(instance._castPlayer, eventName, function(e, data) { + var state = instance.getPlayerStateInternal(data); + events.trigger(instance, eventName, [state]) + }) + } + + function initializeChromecast() { + var instance = this; + instance._castPlayer = new CastPlayer, document.dispatchEvent(new CustomEvent("chromecastloaded", { + detail: { + player: instance + } + })), events.on(instance._castPlayer, "connect", function(e) { + currentResolve ? sendConnectionResult(!0) : playbackManager.setActivePlayer(PlayerName, instance.getCurrentTargetInfo()), console.log("cc: connect"), instance.lastPlayerData = null + }), events.on(instance._castPlayer, "playbackstart", function(e, data) { + console.log("cc: playbackstart"), instance._castPlayer.initializeCastPlayer(); + var state = instance.getPlayerStateInternal(data); + events.trigger(instance, "playbackstart", [state]) + }), events.on(instance._castPlayer, "playbackstop", function(e, data) { + console.log("cc: playbackstop"); + var state = instance.getPlayerStateInternal(data); + events.trigger(instance, "playbackstop", [state]), instance.lastPlayerData = {} + }), events.on(instance._castPlayer, "playbackprogress", function(e, data) { + var state = instance.getPlayerStateInternal(data); + events.trigger(instance, "timeupdate", [state]) + }), bindEventForRelay(instance, "timeupdate"), bindEventForRelay(instance, "pause"), bindEventForRelay(instance, "unpause"), bindEventForRelay(instance, "volumechange"), bindEventForRelay(instance, "repeatmodechange"), events.on(instance._castPlayer, "playstatechange", function(e, data) { + var state = instance.getPlayerStateInternal(data); + events.trigger(instance, "pause", [state]) + }) + } + + function ChromecastPlayer() { + this.name = PlayerName, this.type = "mediaplayer", this.id = "chromecast", this.isLocalPlayer = !1, this.lastPlayerData = {}, castSenderApiLoader.load().then(initializeChromecast.bind(this)) + } + var currentResolve, currentReject, PlayerName = "Chromecast", + DEVICE_STATE = { + IDLE: 0, + ACTIVE: 1, + WARNING: 2, + ERROR: 3 + }, + PLAYER_STATE = { + IDLE: "IDLE", + LOADING: "LOADING", + LOADED: "LOADED", + PLAYING: "PLAYING", + PAUSED: "PAUSED", + STOPPED: "STOPPED", + SEEKING: "SEEKING", + ERROR: "ERROR" + }, + CastPlayer = function() { + this.deviceState = DEVICE_STATE.IDLE, this.currentMediaSession = null, this.session = null, this.castPlayerState = PLAYER_STATE.IDLE, this.hasReceivers = !1, this.errorHandler = this.onError.bind(this), this.mediaStatusUpdateHandler = this.onMediaStatusUpdate.bind(this), this.initializeCastPlayer() + }; + return CastPlayer.prototype.initializeCastPlayer = function() { + var chrome = window.chrome; + if (chrome) { + if (!chrome.cast || !chrome.cast.isAvailable) return void setTimeout(this.initializeCastPlayer.bind(this), 1e3); + var sessionRequest = new chrome.cast.SessionRequest("2D4B1DA3"), + apiConfig = new chrome.cast.ApiConfig(sessionRequest, this.sessionListener.bind(this), this.receiverListener.bind(this), "origin_scoped"); + console.log("chromecast.initialize"), chrome.cast.initialize(apiConfig, this.onInitSuccess.bind(this), this.errorHandler) + } + }, CastPlayer.prototype.onInitSuccess = function() { + this.isInitialized = !0, console.log("chromecast init success") + }, CastPlayer.prototype.onError = function() { + console.log("chromecast error") + }, CastPlayer.prototype.sessionListener = function(e) { + this.session = e, this.session && (this.session.media[0] && this.onMediaDiscovered("activeSession", this.session.media[0]), this.onSessionConnected(e)) + }, CastPlayer.prototype.messageListener = function(namespace, message) { + if ("string" == typeof message && (message = JSON.parse(message)), "playbackerror" === message.type) { + var errorCode = message.data; + setTimeout(function() { + alertText(globalize.translate("MessagePlaybackError" + errorCode), globalize.translate("HeaderPlaybackError")) + }, 300) + } else "connectionerror" === message.type ? setTimeout(function() { + alertText(globalize.translate("MessageChromecastConnectionError"), globalize.translate("HeaderError")) + }, 300) : message.type && events.trigger(this, message.type, [message.data]) + }, CastPlayer.prototype.receiverListener = function(e) { + this.hasReceivers = "available" === e + }, CastPlayer.prototype.sessionUpdateListener = function(isAlive) { + isAlive || (this.session = null, this.deviceState = DEVICE_STATE.IDLE, this.castPlayerState = PLAYER_STATE.IDLE, this.currentMediaSession = null, sendConnectionResult(!1)) + }, CastPlayer.prototype.launchApp = function() { + chrome.cast.requestSession(this.onRequestSessionSuccess.bind(this), this.onLaunchError.bind(this)) + }, CastPlayer.prototype.onRequestSessionSuccess = function(e) { + this.onSessionConnected(e) + }, CastPlayer.prototype.onSessionConnected = function(session) { + this.session = session, this.deviceState = DEVICE_STATE.ACTIVE, this.session.addMessageListener("urn:x-cast:com.connectsdk", this.messageListener.bind(this)), this.session.addMediaListener(this.sessionMediaListener.bind(this)), this.session.addUpdateListener(this.sessionUpdateListener.bind(this)), events.trigger(this, "connect"), this.sendMessage({ + options: {}, + command: "Identify" + }) + }, CastPlayer.prototype.sessionMediaListener = function(e) { + this.currentMediaSession = e, this.currentMediaSession.addUpdateListener(this.mediaStatusUpdateHandler) + }, CastPlayer.prototype.onLaunchError = function() { + this.deviceState = DEVICE_STATE.ERROR, sendConnectionResult(!1) + }, CastPlayer.prototype.stopApp = function() { + this.session && this.session.stop(this.onStopAppSuccess.bind(this, "Session stopped"), this.errorHandler) + }, CastPlayer.prototype.onStopAppSuccess = function(message) { + this.deviceState = DEVICE_STATE.IDLE, this.castPlayerState = PLAYER_STATE.IDLE, this.currentMediaSession = null + }, CastPlayer.prototype.loadMedia = function(options, command) { + return this.session ? (options.items = options.items.map(function(i) { + return { + Id: i.Id, + ServerId: i.ServerId, + Name: i.Name, + Type: i.Type, + MediaType: i.MediaType, + IsFolder: i.IsFolder + } + }), this.sendMessage({ + options: options, + command: command + })) : Promise.reject() + }, CastPlayer.prototype.sendMessage = function(message) { + var player = this, + receiverName = null, + session = player.session; + session && session.receiver && session.receiver.friendlyName && (receiverName = session.receiver.friendlyName); + var apiClient; + apiClient = message.options && message.options.ServerId ? connectionManager.getApiClient(message.options.ServerId) : message.options && message.options.items && message.options.items.length ? connectionManager.getApiClient(message.options.items[0].ServerId) : connectionManager.currentApiClient(), message = Object.assign(message, { + userId: apiClient.getCurrentUserId(), + deviceId: apiClient.deviceId(), + accessToken: apiClient.accessToken(), + serverAddress: apiClient.serverAddress(), + serverId: apiClient.serverId(), + serverVersion: apiClient.serverVersion(), + receiverName: receiverName + }); + var bitrateSetting = appSettings.maxChromecastBitrate(); + return bitrateSetting && (message.maxBitrate = bitrateSetting), message.options && message.options.items && (message.subtitleAppearance = userSettings.getSubtitleAppearanceSettings(), message.subtitleBurnIn = appSettings.get("subtitleburnin") || ""), new Promise(function(resolve, reject) { + require(["chromecastHelper"], function(chromecastHelper) { + chromecastHelper.getServerAddress(apiClient).then(function(serverAddress) { + message.serverAddress = serverAddress, player.sendMessageInternal(message).then(resolve, reject) + }, reject) + }) + }) + }, CastPlayer.prototype.sendMessageInternal = function(message) { + return message = JSON.stringify(message), this.session.sendMessage("urn:x-cast:com.connectsdk", message, this.onPlayCommandSuccess.bind(this), this.errorHandler), Promise.resolve() + }, CastPlayer.prototype.onPlayCommandSuccess = function() {}, CastPlayer.prototype.onMediaDiscovered = function(how, mediaSession) { + this.currentMediaSession = mediaSession, "loadMedia" === how && (this.castPlayerState = PLAYER_STATE.PLAYING), "activeSession" === how && (this.castPlayerState = mediaSession.playerState), this.currentMediaSession.addUpdateListener(this.mediaStatusUpdateHandler) + }, CastPlayer.prototype.onMediaStatusUpdate = function(e) { + !1 === e && (this.castPlayerState = PLAYER_STATE.IDLE) + }, CastPlayer.prototype.setReceiverVolume = function(mute, vol) { + this.currentMediaSession && (mute ? this.session.setReceiverMuted(!0, this.mediaCommandSuccessCallback.bind(this), this.errorHandler) : this.session.setReceiverVolumeLevel(vol || 1, this.mediaCommandSuccessCallback.bind(this), this.errorHandler)) + }, CastPlayer.prototype.mute = function() { + this.setReceiverVolume(!0) + }, CastPlayer.prototype.mediaCommandSuccessCallback = function(info, e) {}, ChromecastPlayer.prototype.tryPair = function(target) { + var castPlayer = this._castPlayer; + return castPlayer.deviceState !== DEVICE_STATE.ACTIVE && castPlayer.isInitialized ? new Promise(function(resolve, reject) { + currentResolve = resolve, currentReject = reject, castPlayer.launchApp() + }) : (currentResolve = null, currentReject = null, Promise.reject()) + }, ChromecastPlayer.prototype.getTargets = function() { + var targets = []; + return this._castPlayer && this._castPlayer.hasReceivers && targets.push(this.getCurrentTargetInfo()), Promise.resolve(targets) + }, ChromecastPlayer.prototype.getCurrentTargetInfo = function() { + var appName = null, + castPlayer = this._castPlayer; + return castPlayer.session && castPlayer.session.receiver && castPlayer.session.receiver.friendlyName && (appName = castPlayer.session.receiver.friendlyName), { + name: PlayerName, + id: PlayerName, + playerName: PlayerName, + playableMediaTypes: ["Audio", "Video"], + isLocalPlayer: !1, + appName: PlayerName, + deviceName: appName, + supportedCommands: ["VolumeUp", "VolumeDown", "Mute", "Unmute", "ToggleMute", "SetVolume", "SetAudioStreamIndex", "SetSubtitleStreamIndex", "DisplayContent", "SetRepeatMode", "EndSession", "PlayMediaSource", "PlayTrailers"] + } + }, ChromecastPlayer.prototype.getPlayerStateInternal = function(data) { + var triggerStateChange = !1; + return data && !this.lastPlayerData && (triggerStateChange = !0), data = data || this.lastPlayerData, this.lastPlayerData = data, normalizeImages(data), triggerStateChange && events.trigger(this, "statechange", [data]), data + }, ChromecastPlayer.prototype.playWithCommand = function(options, command) { + if (!options.items) { + var apiClient = connectionManager.getApiClient(options.serverId), + instance = this; + return apiClient.getItem(apiClient.getCurrentUserId(), options.ids[0]).then(function(item) { + return options.items = [item], instance.playWithCommand(options, command) + }) + } + return this._castPlayer.loadMedia(options, command) + }, ChromecastPlayer.prototype.seek = function(position) { + position = parseInt(position), position /= 1e7, this._castPlayer.sendMessage({ + options: { + position: position + }, + command: "Seek" + }) + }, ChromecastPlayer.prototype.setAudioStreamIndex = function(index) { + this._castPlayer.sendMessage({ + options: { + index: index + }, + command: "SetAudioStreamIndex" + }) + }, ChromecastPlayer.prototype.setSubtitleStreamIndex = function(index) { + this._castPlayer.sendMessage({ + options: { + index: index + }, + command: "SetSubtitleStreamIndex" + }) + }, ChromecastPlayer.prototype.setMaxStreamingBitrate = function(options) { + this._castPlayer.sendMessage({ + options: options, + command: "SetMaxStreamingBitrate" + }) + }, ChromecastPlayer.prototype.isFullscreen = function() { + var state = this.lastPlayerData || {}; + return state = state.PlayState || {}, state.IsFullscreen + }, ChromecastPlayer.prototype.nextTrack = function() { + this._castPlayer.sendMessage({ + options: {}, + command: "NextTrack" + }) + }, ChromecastPlayer.prototype.previousTrack = function() { + this._castPlayer.sendMessage({ + options: {}, + command: "PreviousTrack" + }) + }, ChromecastPlayer.prototype.volumeDown = function() { + this._castPlayer.sendMessage({ + options: {}, + command: "VolumeDown" + }) + }, ChromecastPlayer.prototype.endSession = function() { + var instance = this; + this.stop().then(function() { + setTimeout(function() { + instance._castPlayer.stopApp() + }, 1e3) + }) + }, ChromecastPlayer.prototype.volumeUp = function() { + this._castPlayer.sendMessage({ + options: {}, + command: "VolumeUp" + }) + }, ChromecastPlayer.prototype.setVolume = function(vol) { + vol = Math.min(vol, 100), vol = Math.max(vol, 0), this._castPlayer.sendMessage({ + options: { + volume: vol + }, + command: "SetVolume" + }) + }, ChromecastPlayer.prototype.unpause = function() { + this._castPlayer.sendMessage({ + options: {}, + command: "Unpause" + }) + }, ChromecastPlayer.prototype.playPause = function() { + this._castPlayer.sendMessage({ + options: {}, + command: "PlayPause" + }) + }, ChromecastPlayer.prototype.pause = function() { + this._castPlayer.sendMessage({ + options: {}, + command: "Pause" + }) + }, ChromecastPlayer.prototype.stop = function() { + return this._castPlayer.sendMessage({ + options: {}, + command: "Stop" + }) + }, ChromecastPlayer.prototype.displayContent = function(options) { + this._castPlayer.sendMessage({ + options: options, + command: "DisplayContent" + }) + }, ChromecastPlayer.prototype.setMute = function(isMuted) { + var castPlayer = this._castPlayer; + isMuted ? castPlayer.sendMessage({ + options: {}, + command: "Mute" + }) : castPlayer.sendMessage({ + options: {}, + command: "Unmute" + }) + }, ChromecastPlayer.prototype.getRepeatMode = function() { + var state = this.lastPlayerData || {}; + return state = state.PlayState || {}, state.RepeatMode + }, ChromecastPlayer.prototype.playTrailers = function(item) { + this._castPlayer.sendMessage({ + options: { + ItemId: item.Id, + ServerId: item.ServerId + }, + command: "PlayTrailers" + }) + }, ChromecastPlayer.prototype.setRepeatMode = function(mode) { + this._castPlayer.sendMessage({ + options: { + RepeatMode: mode + }, + command: "SetRepeatMode" + }) + }, ChromecastPlayer.prototype.toggleMute = function() { + this._castPlayer.sendMessage({ + options: {}, + command: "ToggleMute" + }) + }, ChromecastPlayer.prototype.audioTracks = function() { + var state = this.lastPlayerData || {}; + return state = state.NowPlayingItem || {}, (state.MediaStreams || []).filter(function(s) { + return "Audio" === s.Type + }) + }, ChromecastPlayer.prototype.getAudioStreamIndex = function() { + var state = this.lastPlayerData || {}; + return state = state.PlayState || {}, state.AudioStreamIndex + }, ChromecastPlayer.prototype.subtitleTracks = function() { + var state = this.lastPlayerData || {}; + return state = state.NowPlayingItem || {}, (state.MediaStreams || []).filter(function(s) { + return "Subtitle" === s.Type + }) + }, ChromecastPlayer.prototype.getSubtitleStreamIndex = function() { + var state = this.lastPlayerData || {}; + return state = state.PlayState || {}, state.SubtitleStreamIndex + }, ChromecastPlayer.prototype.getMaxStreamingBitrate = function() { + var state = this.lastPlayerData || {}; + return state = state.PlayState || {}, state.MaxStreamingBitrate + }, ChromecastPlayer.prototype.getVolume = function() { + var state = this.lastPlayerData || {}; + return state = state.PlayState || {}, null == state.VolumeLevel ? 100 : state.VolumeLevel + }, ChromecastPlayer.prototype.isPlaying = function() { + return null != (this.lastPlayerData || {}).NowPlayingItem + }, ChromecastPlayer.prototype.isPlayingVideo = function() { + var state = this.lastPlayerData || {}; + return state = state.NowPlayingItem || {}, "Video" === state.MediaType + }, ChromecastPlayer.prototype.isPlayingAudio = function() { + var state = this.lastPlayerData || {}; + return state = state.NowPlayingItem || {}, "Audio" === state.MediaType + }, ChromecastPlayer.prototype.currentTime = function(val) { + if (null != val) return this.seek(val); + var state = this.lastPlayerData || {}; + return state = state.PlayState || {}, state.PositionTicks + }, ChromecastPlayer.prototype.duration = function() { + var state = this.lastPlayerData || {}; + return state = state.NowPlayingItem || {}, state.RunTimeTicks + }, ChromecastPlayer.prototype.getBufferedRanges = function() { + var state = this.lastPlayerData || {}; + return state = state.PlayState || {}, state.BufferedRanges || [] + }, ChromecastPlayer.prototype.paused = function() { + var state = this.lastPlayerData || {}; + return state = state.PlayState || {}, state.IsPaused + }, ChromecastPlayer.prototype.isMuted = function() { + var state = this.lastPlayerData || {}; + return state = state.PlayState || {}, state.IsMuted + }, ChromecastPlayer.prototype.shuffle = function(item) { + var apiClient = connectionManager.getApiClient(item.ServerId), + userId = apiClient.getCurrentUserId(), + instance = this; + apiClient.getItem(userId, item.Id).then(function(item) { + instance.playWithCommand({ + items: [item] + }, "Shuffle") + }) + }, ChromecastPlayer.prototype.instantMix = function(item) { + var apiClient = connectionManager.getApiClient(item.ServerId), + userId = apiClient.getCurrentUserId(), + instance = this; + apiClient.getItem(userId, item.Id).then(function(item) { + instance.playWithCommand({ + items: [item] + }, "InstantMix") + }) + }, ChromecastPlayer.prototype.canPlayMediaType = function(mediaType) { + return "audio" === (mediaType = (mediaType || "").toLowerCase()) || "video" === mediaType + }, ChromecastPlayer.prototype.canQueueMediaType = function(mediaType) { + return this.canPlayMediaType(mediaType) + }, ChromecastPlayer.prototype.queue = function(options) { + this.playWithCommand(options, "PlayLast") + }, ChromecastPlayer.prototype.queueNext = function(options) { + this.playWithCommand(options, "PlayNext") + }, ChromecastPlayer.prototype.play = function(options) { + if (options.items) return this.playWithCommand(options, "PlayNow"); + if (!options.serverId) throw new Error("serverId required!"); + var instance = this; + return getItemsForPlayback(connectionManager.getApiClient(options.serverId), { + Ids: options.ids.join(",") + }).then(function(result) { + return options.items = result.Items, instance.playWithCommand(options, "PlayNow") + }) + }, ChromecastPlayer.prototype.toggleFullscreen = function() {}, ChromecastPlayer.prototype.beginPlayerUpdates = function() {}, ChromecastPlayer.prototype.endPlayerUpdates = function() {}, ChromecastPlayer.prototype.getPlaylist = function() { + return Promise.resolve([]) + }, ChromecastPlayer.prototype.getCurrentPlaylistItemId = function() {}, ChromecastPlayer.prototype.setCurrentPlaylistItem = function(playlistItemId) { + return Promise.resolve() + }, ChromecastPlayer.prototype.removeFromPlaylist = function(playlistItemIds) { + return Promise.resolve() + }, ChromecastPlayer.prototype.getPlayerState = function() { + return this.getPlayerStateInternal() || {} + }, ChromecastPlayer +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/collectioneditor/collectioneditor.js b/dashboard-ui/bower_components/emby-webcomponents/collectioneditor/collectioneditor.js index 1d626c301e..d1aeec3c8e 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/collectioneditor/collectioneditor.js +++ b/dashboard-ui/bower_components/emby-webcomponents/collectioneditor/collectioneditor.js @@ -1 +1,119 @@ -define(["dialogHelper","loading","apphost","layoutManager","connectionManager","appRouter","globalize","emby-checkbox","emby-input","paper-icon-button-light","emby-select","material-icons","css!./../formdialog","emby-button","emby-linkbutton","flexStyles"],function(dialogHelper,loading,appHost,layoutManager,connectionManager,appRouter,globalize){"use strict";function parentWithClass(elem,className){for(;!elem.classList||!elem.classList.contains(className);)if(!(elem=elem.parentNode))return null;return elem}function onSubmit(e){loading.show();var panel=parentWithClass(this,"dialog"),collectionId=panel.querySelector("#selectCollectionToAddTo").value,apiClient=connectionManager.getApiClient(currentServerId);return collectionId?addToCollection(apiClient,panel,collectionId):createCollection(apiClient,panel),e.preventDefault(),!1}function createCollection(apiClient,dlg){var url=apiClient.getUrl("Collections",{Name:dlg.querySelector("#txtNewCollectionName").value,IsLocked:!dlg.querySelector("#chkEnableInternetMetadata").checked,Ids:dlg.querySelector(".fldSelectedItemIds").value||""});apiClient.ajax({type:"POST",url:url,dataType:"json"}).then(function(result){loading.hide();var id=result.Id;dlg.submitted=!0,dialogHelper.close(dlg),redirectToCollection(apiClient,id)})}function redirectToCollection(apiClient,id){appRouter.showItem(id,apiClient.serverId())}function addToCollection(apiClient,dlg,id){var url=apiClient.getUrl("Collections/"+id+"/Items",{Ids:dlg.querySelector(".fldSelectedItemIds").value||""});apiClient.ajax({type:"POST",url:url}).then(function(){loading.hide(),dlg.submitted=!0,dialogHelper.close(dlg),require(["toast"],function(toast){toast(globalize.translate("sharedcomponents#MessageItemsAdded"))})})}function triggerChange(select){select.dispatchEvent(new CustomEvent("change",{}))}function populateCollections(panel){loading.show();var select=panel.querySelector("#selectCollectionToAddTo");panel.querySelector(".newCollectionInfo").classList.add("hide");var options={Recursive:!0,IncludeItemTypes:"BoxSet",SortBy:"SortName",EnableTotalRecordCount:!1},apiClient=connectionManager.getApiClient(currentServerId);apiClient.getItems(apiClient.getCurrentUserId(),options).then(function(result){var html="";html+='",html+=result.Items.map(function(i){return'"}),select.innerHTML=html,select.value="",triggerChange(select),loading.hide()})}function getEditorHtml(){var html="";return html+='
',html+='
',html+='
',html+="
",html+=globalize.translate("sharedcomponents#NewCollectionHelp"),html+="
",html+='
',html+="
",html+="
",html+='
',html+='',html+="
",html+="
",html+='
',html+='
',html+='',html+='
'+globalize.translate("sharedcomponents#NewCollectionNameExample")+"
",html+="
",html+='",html+="
",html+='
',html+='",html+="
",html+='',html+="
",html+="
",html+="
"}function initEditor(content,items){if(content.querySelector("#selectCollectionToAddTo").addEventListener("change",function(){this.value?(content.querySelector(".newCollectionInfo").classList.add("hide"),content.querySelector("#txtNewCollectionName").removeAttribute("required")):(content.querySelector(".newCollectionInfo").classList.remove("hide"),content.querySelector("#txtNewCollectionName").setAttribute("required","required"))}),content.querySelector("form").addEventListener("submit",onSubmit),content.querySelector(".fldSelectedItemIds",content).value=items.join(","),items.length)content.querySelector(".fldSelectCollection").classList.remove("hide"),populateCollections(content);else{content.querySelector(".fldSelectCollection").classList.add("hide");var selectCollectionToAddTo=content.querySelector("#selectCollectionToAddTo");selectCollectionToAddTo.innerHTML="",selectCollectionToAddTo.value="",triggerChange(selectCollectionToAddTo)}}function centerFocus(elem,horiz,on){require(["scrollHelper"],function(scrollHelper){var fn=on?"on":"off";scrollHelper.centerFocus[fn](elem,horiz)})}function CollectionEditor(){}var currentServerId;return CollectionEditor.prototype.show=function(options){var items=options.items||{};currentServerId=options.serverId;var dialogOptions={removeOnClose:!0,scrollY:!1};layoutManager.tv?dialogOptions.size="fullscreen":dialogOptions.size="small";var dlg=dialogHelper.createDialog(dialogOptions);dlg.classList.add("formDialog");var html="",title=items.length?globalize.translate("sharedcomponents#HeaderAddToCollection"):globalize.translate("sharedcomponents#NewCollection");return html+='
',html+='',html+='

',html+=title,html+="

",appHost.supports("externallinks")&&(html+=''+globalize.translate("sharedcomponents#Help")+""),html+="
",html+=getEditorHtml(),dlg.innerHTML=html,initEditor(dlg,items),dlg.querySelector(".btnCancel").addEventListener("click",function(){dialogHelper.close(dlg)}),layoutManager.tv&¢erFocus(dlg.querySelector(".formDialogContent"),!1,!0),dialogHelper.open(dlg).then(function(){return layoutManager.tv&¢erFocus(dlg.querySelector(".formDialogContent"),!1,!1),dlg.submitted?Promise.resolve():Promise.reject()})},CollectionEditor}); \ No newline at end of file +define(["dialogHelper", "loading", "apphost", "layoutManager", "connectionManager", "appRouter", "globalize", "emby-checkbox", "emby-input", "paper-icon-button-light", "emby-select", "material-icons", "css!./../formdialog", "emby-button", "emby-linkbutton", "flexStyles"], function(dialogHelper, loading, appHost, layoutManager, connectionManager, appRouter, globalize) { + "use strict"; + + function parentWithClass(elem, className) { + for (; !elem.classList || !elem.classList.contains(className);) + if (!(elem = elem.parentNode)) return null; + return elem + } + + function onSubmit(e) { + loading.show(); + var panel = parentWithClass(this, "dialog"), + collectionId = panel.querySelector("#selectCollectionToAddTo").value, + apiClient = connectionManager.getApiClient(currentServerId); + return collectionId ? addToCollection(apiClient, panel, collectionId) : createCollection(apiClient, panel), e.preventDefault(), !1 + } + + function createCollection(apiClient, dlg) { + var url = apiClient.getUrl("Collections", { + Name: dlg.querySelector("#txtNewCollectionName").value, + IsLocked: !dlg.querySelector("#chkEnableInternetMetadata").checked, + Ids: dlg.querySelector(".fldSelectedItemIds").value || "" + }); + apiClient.ajax({ + type: "POST", + url: url, + dataType: "json" + }).then(function(result) { + loading.hide(); + var id = result.Id; + dlg.submitted = !0, dialogHelper.close(dlg), redirectToCollection(apiClient, id) + }) + } + + function redirectToCollection(apiClient, id) { + appRouter.showItem(id, apiClient.serverId()) + } + + function addToCollection(apiClient, dlg, id) { + var url = apiClient.getUrl("Collections/" + id + "/Items", { + Ids: dlg.querySelector(".fldSelectedItemIds").value || "" + }); + apiClient.ajax({ + type: "POST", + url: url + }).then(function() { + loading.hide(), dlg.submitted = !0, dialogHelper.close(dlg), require(["toast"], function(toast) { + toast(globalize.translate("sharedcomponents#MessageItemsAdded")) + }) + }) + } + + function triggerChange(select) { + select.dispatchEvent(new CustomEvent("change", {})) + } + + function populateCollections(panel) { + loading.show(); + var select = panel.querySelector("#selectCollectionToAddTo"); + panel.querySelector(".newCollectionInfo").classList.add("hide"); + var options = { + Recursive: !0, + IncludeItemTypes: "BoxSet", + SortBy: "SortName", + EnableTotalRecordCount: !1 + }, + apiClient = connectionManager.getApiClient(currentServerId); + apiClient.getItems(apiClient.getCurrentUserId(), options).then(function(result) { + var html = ""; + html += '", html += result.Items.map(function(i) { + return '" + }), select.innerHTML = html, select.value = "", triggerChange(select), loading.hide() + }) + } + + function getEditorHtml() { + var html = ""; + return html += '
', html += '
', html += '
', html += "
", html += globalize.translate("sharedcomponents#NewCollectionHelp"), html += "
", html += '
', html += "
", html += "
", html += '
', html += '', html += "
", html += "
", html += '
', html += '
', html += '', html += '
' + globalize.translate("sharedcomponents#NewCollectionNameExample") + "
", html += "
", html += '", html += "
", html += '
', html += '", html += "
", html += '', html += "
", html += "
", html += "
" + } + + function initEditor(content, items) { + if (content.querySelector("#selectCollectionToAddTo").addEventListener("change", function() { + this.value ? (content.querySelector(".newCollectionInfo").classList.add("hide"), content.querySelector("#txtNewCollectionName").removeAttribute("required")) : (content.querySelector(".newCollectionInfo").classList.remove("hide"), content.querySelector("#txtNewCollectionName").setAttribute("required", "required")) + }), content.querySelector("form").addEventListener("submit", onSubmit), content.querySelector(".fldSelectedItemIds", content).value = items.join(","), items.length) content.querySelector(".fldSelectCollection").classList.remove("hide"), populateCollections(content); + else { + content.querySelector(".fldSelectCollection").classList.add("hide"); + var selectCollectionToAddTo = content.querySelector("#selectCollectionToAddTo"); + selectCollectionToAddTo.innerHTML = "", selectCollectionToAddTo.value = "", triggerChange(selectCollectionToAddTo) + } + } + + function centerFocus(elem, horiz, on) { + require(["scrollHelper"], function(scrollHelper) { + var fn = on ? "on" : "off"; + scrollHelper.centerFocus[fn](elem, horiz) + }) + } + + function CollectionEditor() {} + var currentServerId; + return CollectionEditor.prototype.show = function(options) { + var items = options.items || {}; + currentServerId = options.serverId; + var dialogOptions = { + removeOnClose: !0, + scrollY: !1 + }; + layoutManager.tv ? dialogOptions.size = "fullscreen" : dialogOptions.size = "small"; + var dlg = dialogHelper.createDialog(dialogOptions); + dlg.classList.add("formDialog"); + var html = "", + title = items.length ? globalize.translate("sharedcomponents#HeaderAddToCollection") : globalize.translate("sharedcomponents#NewCollection"); + return html += '
', html += '', html += '

', html += title, html += "

", appHost.supports("externallinks") && (html += '' + globalize.translate("sharedcomponents#Help") + ""), html += "
", html += getEditorHtml(), dlg.innerHTML = html, initEditor(dlg, items), dlg.querySelector(".btnCancel").addEventListener("click", function() { + dialogHelper.close(dlg) + }), layoutManager.tv && centerFocus(dlg.querySelector(".formDialogContent"), !1, !0), dialogHelper.open(dlg).then(function() { + return layoutManager.tv && centerFocus(dlg.querySelector(".formDialogContent"), !1, !1), dlg.submitted ? Promise.resolve() : Promise.reject() + }) + }, CollectionEditor +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/confirm/confirm.js b/dashboard-ui/bower_components/emby-webcomponents/confirm/confirm.js index 11da3a08ef..22890d52cb 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/confirm/confirm.js +++ b/dashboard-ui/bower_components/emby-webcomponents/confirm/confirm.js @@ -1 +1,22 @@ -define(["dialog","globalize"],function(dialog,globalize){"use strict";return function(text,title){var options;options="string"==typeof text?{title:title,text:text}:text;var items=[];return items.push({name:options.cancelText||globalize.translate("sharedcomponents#ButtonCancel"),id:"cancel",type:"cancel"===options.primary?"submit":"cancel"}),items.push({name:options.confirmText||globalize.translate("sharedcomponents#ButtonOk"),id:"ok",type:"cancel"===options.primary?"cancel":"submit"}),options.buttons=items,dialog(options).then(function(result){return"ok"===result?Promise.resolve():Promise.reject()})}}); \ No newline at end of file +define(["dialog", "globalize"], function(dialog, globalize) { + "use strict"; + return function(text, title) { + var options; + options = "string" == typeof text ? { + title: title, + text: text + } : text; + var items = []; + return items.push({ + name: options.cancelText || globalize.translate("sharedcomponents#ButtonCancel"), + id: "cancel", + type: "cancel" === options.primary ? "submit" : "cancel" + }), items.push({ + name: options.confirmText || globalize.translate("sharedcomponents#ButtonOk"), + id: "ok", + type: "cancel" === options.primary ? "cancel" : "submit" + }), options.buttons = items, dialog(options).then(function(result) { + return "ok" === result ? Promise.resolve() : Promise.reject() + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/confirm/nativeconfirm.js b/dashboard-ui/bower_components/emby-webcomponents/confirm/nativeconfirm.js index a816c416a3..d909e687e8 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/confirm/nativeconfirm.js +++ b/dashboard-ui/bower_components/emby-webcomponents/confirm/nativeconfirm.js @@ -1 +1,15 @@ -define([],function(){"use strict";function replaceAll(str,find,replace){return str.split(find).join(replace)}return function(options){"string"==typeof options&&(options={title:"",text:options});var text=replaceAll(options.text||"","
","\n");return confirm(text)?Promise.resolve():Promise.reject()}}); \ No newline at end of file +define([], function() { + "use strict"; + + function replaceAll(str, find, replace) { + return str.split(find).join(replace) + } + return function(options) { + "string" == typeof options && (options = { + title: "", + text: options + }); + var text = replaceAll(options.text || "", "
", "\n"); + return confirm(text) ? Promise.resolve() : Promise.reject() + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/datetime.js b/dashboard-ui/bower_components/emby-webcomponents/datetime.js index 516ff794e8..9d3edd6786 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/datetime.js +++ b/dashboard-ui/bower_components/emby-webcomponents/datetime.js @@ -1 +1,123 @@ -define(["globalize"],function(globalize){"use strict";function parseISO8601Date(s,toLocal){var re=/(\d{4})-(\d{2})-(\d{2})T(\d{2}):(\d{2}):(\d{2})(\.\d+)?(Z|([+-])(\d{2}):(\d{2}))?/,d=s.match(re);if(!d)throw"Couldn't parse ISO 8601 date string '"+s+"'";var a=[1,2,3,4,5,6,10,11];for(var i in a)d[a[i]]=parseInt(d[a[i]],10);d[7]=parseFloat(d[7]);var ms=Date.UTC(d[1],d[2]-1,d[3],d[4],d[5],d[6]);if(d[7]>0&&(ms+=Math.round(1e3*d[7])),"Z"!==d[8]&&d[10]){var offset=60*d[10]*60*1e3;d[11]&&(offset+=60*d[11]*1e3),"-"===d[9]?ms-=offset:ms+=offset}else!1===toLocal&&(ms+=6e4*(new Date).getTimezoneOffset());return new Date(ms)}function getDisplayRunningTime(ticks){var parts=[],hours=ticks/36e9;hours=Math.floor(hours),hours&&parts.push(hours),ticks-=36e9*hours;var minutes=ticks/6e8;minutes=Math.floor(minutes),ticks-=6e8*minutes,minutes<10&&hours&&(minutes="0"+minutes),parts.push(minutes);var seconds=ticks/1e7;return seconds=Math.floor(seconds),seconds<10&&(seconds="0"+seconds),parts.push(seconds),parts.join(":")}function getOptionList(options){var list=[];for(var i in options)list.push({name:i,value:options[i]});return list}function toLocaleString(date,options){if(!date)throw new Error("date cannot be null");if(options=options||{},toLocaleTimeStringSupportsLocales){var currentLocale=globalize.getCurrentDateTimeLocale();if(currentLocale)return date.toLocaleString(currentLocale,options)}return date.toLocaleString()}function toLocaleDateString(date,options){if(!date)throw new Error("date cannot be null");if(options=options||{},toLocaleTimeStringSupportsLocales){var currentLocale=globalize.getCurrentDateTimeLocale();if(currentLocale)return date.toLocaleDateString(currentLocale,options)}var optionList=getOptionList(options);if(1===optionList.length&&"weekday"===optionList[0].name){var weekday=[];return weekday[0]="Sun",weekday[1]="Mon",weekday[2]="Tue",weekday[3]="Wed",weekday[4]="Thu",weekday[5]="Fri",weekday[6]="Sat",weekday[date.getDay()]}return date.toLocaleDateString()}function toLocaleTimeString(date,options){if(!date)throw new Error("date cannot be null");if(options=options||{},toLocaleTimeStringSupportsLocales){var currentLocale=globalize.getCurrentDateTimeLocale();if(currentLocale)return date.toLocaleTimeString(currentLocale,options)}return date.toLocaleTimeString()}function getDisplayTime(date){if(!date)throw new Error("date cannot be null");if("string"===(typeof date).toString().toLowerCase())try{date=parseISO8601Date(date,!0)}catch(err){return date}if(toLocaleTimeStringSupportsLocales)return toLocaleTimeString(date,{hour:"numeric",minute:"2-digit"});var time=toLocaleTimeString(date),timeLower=time.toLowerCase();if(-1!==timeLower.indexOf("am")||-1!==timeLower.indexOf("pm")){time=timeLower;var hour=date.getHours()%12,suffix=date.getHours()>11?"pm":"am";hour||(hour=12);var minutes=date.getMinutes();minutes<10&&(minutes="0"+minutes),minutes=":"+minutes,time=hour+minutes+suffix}else{var timeParts=time.split(":");timeParts.length>2&&(timeParts.length=2,time=timeParts.join(":"))}return time}function isRelativeDay(date,offsetInDays){if(!date)throw new Error("date cannot be null");var yesterday=new Date,day=yesterday.getDate()+offsetInDays;return yesterday.setDate(day),date.getFullYear()===yesterday.getFullYear()&&date.getMonth()===yesterday.getMonth()&&date.getDate()===day}var toLocaleTimeStringSupportsLocales=function(){try{(new Date).toLocaleTimeString("i")}catch(e){return"RangeError"===e.name}return!1}();return{parseISO8601Date:parseISO8601Date,getDisplayRunningTime:getDisplayRunningTime,toLocaleDateString:toLocaleDateString,toLocaleString:toLocaleString,getDisplayTime:getDisplayTime,isRelativeDay:isRelativeDay,toLocaleTimeString:toLocaleTimeString,supportsLocalization:function(){return toLocaleTimeStringSupportsLocales}}}); \ No newline at end of file +define(["globalize"], function(globalize) { + "use strict"; + + function parseISO8601Date(s, toLocal) { + var re = /(\d{4})-(\d{2})-(\d{2})T(\d{2}):(\d{2}):(\d{2})(\.\d+)?(Z|([+-])(\d{2}):(\d{2}))?/, + d = s.match(re); + if (!d) throw "Couldn't parse ISO 8601 date string '" + s + "'"; + var a = [1, 2, 3, 4, 5, 6, 10, 11]; + for (var i in a) d[a[i]] = parseInt(d[a[i]], 10); + d[7] = parseFloat(d[7]); + var ms = Date.UTC(d[1], d[2] - 1, d[3], d[4], d[5], d[6]); + if (d[7] > 0 && (ms += Math.round(1e3 * d[7])), "Z" !== d[8] && d[10]) { + var offset = 60 * d[10] * 60 * 1e3; + d[11] && (offset += 60 * d[11] * 1e3), "-" === d[9] ? ms -= offset : ms += offset + } else !1 === toLocal && (ms += 6e4 * (new Date).getTimezoneOffset()); + return new Date(ms) + } + + function getDisplayRunningTime(ticks) { + var parts = [], + hours = ticks / 36e9; + hours = Math.floor(hours), hours && parts.push(hours), ticks -= 36e9 * hours; + var minutes = ticks / 6e8; + minutes = Math.floor(minutes), ticks -= 6e8 * minutes, minutes < 10 && hours && (minutes = "0" + minutes), parts.push(minutes); + var seconds = ticks / 1e7; + return seconds = Math.floor(seconds), seconds < 10 && (seconds = "0" + seconds), parts.push(seconds), parts.join(":") + } + + function getOptionList(options) { + var list = []; + for (var i in options) list.push({ + name: i, + value: options[i] + }); + return list + } + + function toLocaleString(date, options) { + if (!date) throw new Error("date cannot be null"); + if (options = options || {}, toLocaleTimeStringSupportsLocales) { + var currentLocale = globalize.getCurrentDateTimeLocale(); + if (currentLocale) return date.toLocaleString(currentLocale, options) + } + return date.toLocaleString() + } + + function toLocaleDateString(date, options) { + if (!date) throw new Error("date cannot be null"); + if (options = options || {}, toLocaleTimeStringSupportsLocales) { + var currentLocale = globalize.getCurrentDateTimeLocale(); + if (currentLocale) return date.toLocaleDateString(currentLocale, options) + } + var optionList = getOptionList(options); + if (1 === optionList.length && "weekday" === optionList[0].name) { + var weekday = []; + return weekday[0] = "Sun", weekday[1] = "Mon", weekday[2] = "Tue", weekday[3] = "Wed", weekday[4] = "Thu", weekday[5] = "Fri", weekday[6] = "Sat", weekday[date.getDay()] + } + return date.toLocaleDateString() + } + + function toLocaleTimeString(date, options) { + if (!date) throw new Error("date cannot be null"); + if (options = options || {}, toLocaleTimeStringSupportsLocales) { + var currentLocale = globalize.getCurrentDateTimeLocale(); + if (currentLocale) return date.toLocaleTimeString(currentLocale, options) + } + return date.toLocaleTimeString() + } + + function getDisplayTime(date) { + if (!date) throw new Error("date cannot be null"); + if ("string" === (typeof date).toString().toLowerCase()) try { + date = parseISO8601Date(date, !0) + } catch (err) { + return date + } + if (toLocaleTimeStringSupportsLocales) return toLocaleTimeString(date, { + hour: "numeric", + minute: "2-digit" + }); + var time = toLocaleTimeString(date), + timeLower = time.toLowerCase(); + if (-1 !== timeLower.indexOf("am") || -1 !== timeLower.indexOf("pm")) { + time = timeLower; + var hour = date.getHours() % 12, + suffix = date.getHours() > 11 ? "pm" : "am"; + hour || (hour = 12); + var minutes = date.getMinutes(); + minutes < 10 && (minutes = "0" + minutes), minutes = ":" + minutes, time = hour + minutes + suffix + } else { + var timeParts = time.split(":"); + timeParts.length > 2 && (timeParts.length = 2, time = timeParts.join(":")) + } + return time + } + + function isRelativeDay(date, offsetInDays) { + if (!date) throw new Error("date cannot be null"); + var yesterday = new Date, + day = yesterday.getDate() + offsetInDays; + return yesterday.setDate(day), date.getFullYear() === yesterday.getFullYear() && date.getMonth() === yesterday.getMonth() && date.getDate() === day + } + var toLocaleTimeStringSupportsLocales = function() { + try { + (new Date).toLocaleTimeString("i") + } catch (e) { + return "RangeError" === e.name + } + return !1 + }(); + return { + parseISO8601Date: parseISO8601Date, + getDisplayRunningTime: getDisplayRunningTime, + toLocaleDateString: toLocaleDateString, + toLocaleString: toLocaleString, + getDisplayTime: getDisplayTime, + isRelativeDay: isRelativeDay, + toLocaleTimeString: toLocaleTimeString, + supportsLocalization: function() { + return toLocaleTimeStringSupportsLocales + } + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/deletehelper.js b/dashboard-ui/bower_components/emby-webcomponents/deletehelper.js index df2be95655..e31b9104e3 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/deletehelper.js +++ b/dashboard-ui/bower_components/emby-webcomponents/deletehelper.js @@ -1 +1,39 @@ -define(["connectionManager","confirm","appRouter","globalize"],function(connectionManager,confirm,appRouter,globalize){"use strict";function alertText(options){return new Promise(function(resolve,reject){require(["alert"],function(alert){alert(options).then(resolve,resolve)})})}function deleteItem(options){var item=options.item,itemId=item.Id,parentId=item.SeasonId||item.SeriesId||item.ParentId,serverId=item.ServerId,msg=globalize.translate("sharedcomponents#ConfirmDeleteItem"),title=globalize.translate("sharedcomponents#HeaderDeleteItem"),apiClient=connectionManager.getApiClient(item.ServerId);return confirm({title:title,text:msg,confirmText:globalize.translate("sharedcomponents#Delete"),primary:"cancel"}).then(function(){return apiClient.deleteItem(itemId).then(function(){options.navigate&&(parentId?appRouter.showItem(parentId,serverId):appRouter.goHome())},function(err){var result=function(){return Promise.reject(err)};return alertText(globalize.translate("sharedcomponents#ErrorDeletingItem")).then(result,result)})})}return{deleteItem:deleteItem}}); \ No newline at end of file +define(["connectionManager", "confirm", "appRouter", "globalize"], function(connectionManager, confirm, appRouter, globalize) { + "use strict"; + + function alertText(options) { + return new Promise(function(resolve, reject) { + require(["alert"], function(alert) { + alert(options).then(resolve, resolve) + }) + }) + } + + function deleteItem(options) { + var item = options.item, + itemId = item.Id, + parentId = item.SeasonId || item.SeriesId || item.ParentId, + serverId = item.ServerId, + msg = globalize.translate("sharedcomponents#ConfirmDeleteItem"), + title = globalize.translate("sharedcomponents#HeaderDeleteItem"), + apiClient = connectionManager.getApiClient(item.ServerId); + return confirm({ + title: title, + text: msg, + confirmText: globalize.translate("sharedcomponents#Delete"), + primary: "cancel" + }).then(function() { + return apiClient.deleteItem(itemId).then(function() { + options.navigate && (parentId ? appRouter.showItem(parentId, serverId) : appRouter.goHome()) + }, function(err) { + var result = function() { + return Promise.reject(err) + }; + return alertText(globalize.translate("sharedcomponents#ErrorDeletingItem")).then(result, result) + }) + }) + } + return { + deleteItem: deleteItem + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/dialog/dialog.js b/dashboard-ui/bower_components/emby-webcomponents/dialog/dialog.js index 382e7e013e..1208719886 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/dialog/dialog.js +++ b/dashboard-ui/bower_components/emby-webcomponents/dialog/dialog.js @@ -1 +1,46 @@ -define(["dialogHelper","dom","layoutManager","scrollHelper","globalize","require","material-icons","emby-button","paper-icon-button-light","emby-input","formDialogStyle","flexStyles"],function(dialogHelper,dom,layoutManager,scrollHelper,globalize,require){"use strict";function showDialog(options,template){function onButtonClick(){dialogResult=this.getAttribute("data-id"),dialogHelper.close(dlg)}var dialogOptions={removeOnClose:!0,scrollY:!1},enableTvLayout=layoutManager.tv;enableTvLayout&&(dialogOptions.size="fullscreen");var dlg=dialogHelper.createDialog(dialogOptions);dlg.classList.add("formDialog"),dlg.innerHTML=globalize.translateHtml(template,"sharedcomponents"),dlg.classList.add("align-items-center"),dlg.classList.add("justify-content-center");var formDialogContent=dlg.querySelector(".formDialogContent");formDialogContent.classList.add("no-grow"),enableTvLayout?(formDialogContent.style["max-width"]="50%",formDialogContent.style["max-height"]="60%",scrollHelper.centerFocus.on(formDialogContent,!1)):(formDialogContent.style.maxWidth=Math.min(150*options.buttons.length+200,dom.getWindowSize().innerWidth-50)+"px",dlg.classList.add("dialog-fullscreen-lowres")),options.title?dlg.querySelector(".formDialogHeaderTitle").innerHTML=options.title||"":dlg.querySelector(".formDialogHeaderTitle").classList.add("hide");var displayText=options.html||options.text||"";dlg.querySelector(".text").innerHTML=displayText,displayText||dlg.querySelector(".dialogContentInner").classList.add("hide");var i,length,html="",hasDescriptions=!1;for(i=0,length=options.buttons.length;i"+item.name+"",item.description&&(html+='
'+item.description+"
")}dlg.querySelector(".formDialogFooter").innerHTML=html,hasDescriptions&&dlg.querySelector(".formDialogFooter").classList.add("formDialogFooter-vertical");var dialogResult,buttons=dlg.querySelectorAll(".btnOption");for(i=0,length=buttons.length;i" + item.name + "", item.description && (html += '
' + item.description + "
") + } + dlg.querySelector(".formDialogFooter").innerHTML = html, hasDescriptions && dlg.querySelector(".formDialogFooter").classList.add("formDialogFooter-vertical"); + var dialogResult, buttons = dlg.querySelectorAll(".btnOption"); + for (i = 0, length = buttons.length; i < length; i++) buttons[i].addEventListener("click", onButtonClick); + return dialogHelper.open(dlg).then(function() { + return enableTvLayout && scrollHelper.centerFocus.off(dlg.querySelector(".formDialogContent"), !1), dialogResult || Promise.reject() + }) + } + return function(text, title) { + var options; + return options = "string" == typeof text ? { + title: title, + text: text + } : text, new Promise(function(resolve, reject) { + require(["text!./dialog.template.html"], function(template) { + showDialog(options, template).then(resolve, reject) + }) + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/dialoghelper/dialoghelper.js b/dashboard-ui/bower_components/emby-webcomponents/dialoghelper/dialoghelper.js index da652e834d..9c5f6b0064 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/dialoghelper/dialoghelper.js +++ b/dashboard-ui/bower_components/emby-webcomponents/dialoghelper/dialoghelper.js @@ -1 +1,225 @@ -define(["appRouter","focusManager","browser","layoutManager","inputManager","dom","css!./dialoghelper.css","scrollStyles"],function(appRouter,focusManager,browser,layoutManager,inputManager,dom){"use strict";function enableAnimation(){return!browser.tv&&browser.supportsCssAnimation()}function removeCenterFocus(dlg){layoutManager.tv&&(dlg.classList.contains("scrollX")?centerFocus(dlg,!0,!1):dlg.classList.contains("smoothScrollY")&¢erFocus(dlg,!1,!1))}function tryRemoveElement(elem){var parentNode=elem.parentNode;if(parentNode)try{parentNode.removeChild(elem)}catch(err){console.log("Error removing dialog element: "+err)}}function DialogHashHandler(dlg,hash,resolve){function onHashChange(e){var isBack=self.originalUrl===window.location.href;!isBack&&isOpened(dlg)||window.removeEventListener("popstate",onHashChange),isBack&&(self.closedByBack=!0,closeDialog(dlg))}function onBackCommand(e){"back"===e.detail.command&&(self.closedByBack=!0,e.preventDefault(),e.stopPropagation(),closeDialog(dlg))}function onDialogClosed(){if(isHistoryEnabled(dlg)||inputManager.off(dlg,onBackCommand),window.removeEventListener("popstate",onHashChange),removeBackdrop(dlg),dlg.classList.remove("opened"),removeScrollLockOnClose&&document.body.classList.remove("noScroll"),!self.closedByBack&&isHistoryEnabled(dlg)){(history.state||{}).dialogId===hash&&history.back()}if(layoutManager.tv&&focusManager.focus(activeElement),"false"!==dlg.getAttribute("data-removeonclose")){removeCenterFocus(dlg);var dialogContainer=dlg.dialogContainer;dialogContainer?(tryRemoveElement(dialogContainer),dlg.dialogContainer=null):tryRemoveElement(dlg)}setTimeout(function(){resolve({element:dlg,closedByBack:self.closedByBack})},1)}var self=this;self.originalUrl=window.location.href;var activeElement=document.activeElement,removeScrollLockOnClose=!1;dlg.addEventListener("close",onDialogClosed),!dlg.classList.contains("dialog-fixedSize")&&dlg.classList.add("centeredDialog"),dlg.classList.remove("hide"),addBackdropOverlay(dlg),dlg.classList.add("opened"),dlg.dispatchEvent(new CustomEvent("open",{bubbles:!1,cancelable:!1})),"true"!==dlg.getAttribute("data-lockscroll")||document.body.classList.contains("noScroll")||(document.body.classList.add("noScroll"),removeScrollLockOnClose=!0),animateDialogOpen(dlg),isHistoryEnabled(dlg)?(appRouter.pushState({dialogId:hash},"Dialog","#"+hash),window.addEventListener("popstate",onHashChange)):inputManager.on(dlg,onBackCommand)}function addBackdropOverlay(dlg){var backdrop=document.createElement("div");backdrop.classList.add("dialogBackdrop");var backdropParent=dlg.dialogContainer||dlg;backdropParent.parentNode.insertBefore(backdrop,backdropParent),dlg.backdrop=backdrop,backdrop.offsetWidth,backdrop.classList.add("dialogBackdropOpened"),dom.addEventListener(dlg.dialogContainer||backdrop,"click",function(e){e.target===dlg.dialogContainer&&close(dlg)},{passive:!0})}function isHistoryEnabled(dlg){return"true"===dlg.getAttribute("data-history")}function open(dlg){globalOnOpenCallback&&globalOnOpenCallback(dlg);var parent=dlg.parentNode;parent&&parent.removeChild(dlg);var dialogContainer=document.createElement("div");return dialogContainer.classList.add("dialogContainer"),dialogContainer.appendChild(dlg),dlg.dialogContainer=dialogContainer,document.body.appendChild(dialogContainer),new Promise(function(resolve,reject){new DialogHashHandler(dlg,"dlg"+(new Date).getTime(),resolve)})}function isOpened(dlg){return!dlg.classList.contains("hide")}function close(dlg){isOpened(dlg)&&(isHistoryEnabled(dlg)?history.back():closeDialog(dlg))}function closeDialog(dlg){if(!dlg.classList.contains("hide")){dlg.dispatchEvent(new CustomEvent("closing",{bubbles:!1,cancelable:!1}));animateDialogClose(dlg,function(){focusManager.popScope(dlg),dlg.classList.add("hide"),dlg.dispatchEvent(new CustomEvent("close",{bubbles:!1,cancelable:!1}))})}}function animateDialogOpen(dlg){var onAnimationFinish=function(){focusManager.pushScope(dlg),"true"===dlg.getAttribute("data-autofocus")&&focusManager.autoFocus(dlg)};if(enableAnimation()){var onFinish=function(){dom.removeEventListener(dlg,dom.whichAnimationEvent(),onFinish,{once:!0}),onAnimationFinish()};return void dom.addEventListener(dlg,dom.whichAnimationEvent(),onFinish,{once:!0})}onAnimationFinish()}function animateDialogClose(dlg,onAnimationFinish){if(enableAnimation()){var animated=!0;switch(dlg.animationConfig.exit.name){case"fadeout":dlg.style.animation="fadeout "+dlg.animationConfig.exit.timing.duration+"ms ease-out normal both";break;case"scaledown":dlg.style.animation="scaledown "+dlg.animationConfig.exit.timing.duration+"ms ease-out normal both";break;case"slidedown":dlg.style.animation="slidedown "+dlg.animationConfig.exit.timing.duration+"ms ease-out normal both";break;default:animated=!1}var onFinish=function(){dom.removeEventListener(dlg,dom.whichAnimationEvent(),onFinish,{once:!0}),onAnimationFinish()};if(dom.addEventListener(dlg,dom.whichAnimationEvent(),onFinish,{once:!0}),animated)return}onAnimationFinish()}function shouldLockDocumentScroll(options){return!(supportsOverscrollBehavior&&(options.size||!browser.touch))&&(null!=options.lockScroll?options.lockScroll:"fullscreen"===options.size||(!!options.size||browser.touch))}function removeBackdrop(dlg){var backdrop=dlg.backdrop;if(backdrop){dlg.backdrop=null;var onAnimationFinish=function(){tryRemoveElement(backdrop)};if(enableAnimation())return backdrop.classList.remove("dialogBackdropOpened"),void setTimeout(onAnimationFinish,300);onAnimationFinish()}}function centerFocus(elem,horiz,on){require(["scrollHelper"],function(scrollHelper){var fn=on?"on":"off";scrollHelper.centerFocus[fn](elem,horiz)})}function createDialog(options){options=options||{};var dlg=document.createElement("div");dlg.classList.add("focuscontainer"),dlg.classList.add("hide"),shouldLockDocumentScroll(options)&&dlg.setAttribute("data-lockscroll","true"),!1!==options.enableHistory&&appRouter.enableNativeHistory()&&dlg.setAttribute("data-history","true"),!1!==options.modal&&dlg.setAttribute("modal","modal"),!1!==options.autoFocus&&dlg.setAttribute("data-autofocus","true");var defaultEntryAnimation,defaultExitAnimation;defaultEntryAnimation="scaleup",defaultExitAnimation="scaledown";var entryAnimation=options.entryAnimation||defaultEntryAnimation,exitAnimation=options.exitAnimation||defaultExitAnimation,entryAnimationDuration=options.entryAnimationDuration||("fullscreen"!==options.size?180:280),exitAnimationDuration=options.exitAnimationDuration||("fullscreen"!==options.size?120:220);if(dlg.animationConfig={entry:{name:entryAnimation,timing:{duration:entryAnimationDuration,easing:"ease-out"}},exit:{name:exitAnimation,timing:{duration:exitAnimationDuration,easing:"ease-out",fill:"both"}}},dlg.classList.add("dialog"),options.scrollX?(dlg.classList.add("scrollX"),dlg.classList.add("smoothScrollX"),layoutManager.tv&¢erFocus(dlg,!0,!0)):!1!==options.scrollY&&(dlg.classList.add("smoothScrollY"),layoutManager.tv&¢erFocus(dlg,!1,!0)),options.removeOnClose&&dlg.setAttribute("data-removeonclose","true"),options.size&&(dlg.classList.add("dialog-fixedSize"),dlg.classList.add("dialog-"+options.size)),enableAnimation())switch(dlg.animationConfig.entry.name){case"fadein":dlg.style.animation="fadein "+entryAnimationDuration+"ms ease-out normal";break;case"scaleup":dlg.style.animation="scaleup "+entryAnimationDuration+"ms ease-out normal both";break;case"slideup":dlg.style.animation="slideup "+entryAnimationDuration+"ms ease-out normal";break;case"slidedown":dlg.style.animation="slidedown "+entryAnimationDuration+"ms ease-out normal"}return dlg}var globalOnOpenCallback,supportsOverscrollBehavior="overscroll-behavior-y"in document.body.style;return{open:open,close:close,createDialog:createDialog,setOnOpen:function(val){globalOnOpenCallback=val}}}); \ No newline at end of file +define(["appRouter", "focusManager", "browser", "layoutManager", "inputManager", "dom", "css!./dialoghelper.css", "scrollStyles"], function(appRouter, focusManager, browser, layoutManager, inputManager, dom) { + "use strict"; + + function enableAnimation() { + return !browser.tv && browser.supportsCssAnimation() + } + + function removeCenterFocus(dlg) { + layoutManager.tv && (dlg.classList.contains("scrollX") ? centerFocus(dlg, !0, !1) : dlg.classList.contains("smoothScrollY") && centerFocus(dlg, !1, !1)) + } + + function tryRemoveElement(elem) { + var parentNode = elem.parentNode; + if (parentNode) try { + parentNode.removeChild(elem) + } catch (err) { + console.log("Error removing dialog element: " + err) + } + } + + function DialogHashHandler(dlg, hash, resolve) { + function onHashChange(e) { + var isBack = self.originalUrl === window.location.href; + !isBack && isOpened(dlg) || window.removeEventListener("popstate", onHashChange), isBack && (self.closedByBack = !0, closeDialog(dlg)) + } + + function onBackCommand(e) { + "back" === e.detail.command && (self.closedByBack = !0, e.preventDefault(), e.stopPropagation(), closeDialog(dlg)) + } + + function onDialogClosed() { + if (isHistoryEnabled(dlg) || inputManager.off(dlg, onBackCommand), window.removeEventListener("popstate", onHashChange), removeBackdrop(dlg), dlg.classList.remove("opened"), removeScrollLockOnClose && document.body.classList.remove("noScroll"), !self.closedByBack && isHistoryEnabled(dlg)) { + (history.state || {}).dialogId === hash && history.back() + } + if (layoutManager.tv && focusManager.focus(activeElement), "false" !== dlg.getAttribute("data-removeonclose")) { + removeCenterFocus(dlg); + var dialogContainer = dlg.dialogContainer; + dialogContainer ? (tryRemoveElement(dialogContainer), dlg.dialogContainer = null) : tryRemoveElement(dlg) + } + setTimeout(function() { + resolve({ + element: dlg, + closedByBack: self.closedByBack + }) + }, 1) + } + var self = this; + self.originalUrl = window.location.href; + var activeElement = document.activeElement, + removeScrollLockOnClose = !1; + dlg.addEventListener("close", onDialogClosed), !dlg.classList.contains("dialog-fixedSize") && dlg.classList.add("centeredDialog"), dlg.classList.remove("hide"), addBackdropOverlay(dlg), dlg.classList.add("opened"), dlg.dispatchEvent(new CustomEvent("open", { + bubbles: !1, + cancelable: !1 + })), "true" !== dlg.getAttribute("data-lockscroll") || document.body.classList.contains("noScroll") || (document.body.classList.add("noScroll"), removeScrollLockOnClose = !0), animateDialogOpen(dlg), isHistoryEnabled(dlg) ? (appRouter.pushState({ + dialogId: hash + }, "Dialog", "#" + hash), window.addEventListener("popstate", onHashChange)) : inputManager.on(dlg, onBackCommand) + } + + function addBackdropOverlay(dlg) { + var backdrop = document.createElement("div"); + backdrop.classList.add("dialogBackdrop"); + var backdropParent = dlg.dialogContainer || dlg; + backdropParent.parentNode.insertBefore(backdrop, backdropParent), dlg.backdrop = backdrop, backdrop.offsetWidth, backdrop.classList.add("dialogBackdropOpened"), dom.addEventListener(dlg.dialogContainer || backdrop, "click", function(e) { + e.target === dlg.dialogContainer && close(dlg) + }, { + passive: !0 + }) + } + + function isHistoryEnabled(dlg) { + return "true" === dlg.getAttribute("data-history") + } + + function open(dlg) { + globalOnOpenCallback && globalOnOpenCallback(dlg); + var parent = dlg.parentNode; + parent && parent.removeChild(dlg); + var dialogContainer = document.createElement("div"); + return dialogContainer.classList.add("dialogContainer"), dialogContainer.appendChild(dlg), dlg.dialogContainer = dialogContainer, document.body.appendChild(dialogContainer), new Promise(function(resolve, reject) { + new DialogHashHandler(dlg, "dlg" + (new Date).getTime(), resolve) + }) + } + + function isOpened(dlg) { + return !dlg.classList.contains("hide") + } + + function close(dlg) { + isOpened(dlg) && (isHistoryEnabled(dlg) ? history.back() : closeDialog(dlg)) + } + + function closeDialog(dlg) { + if (!dlg.classList.contains("hide")) { + dlg.dispatchEvent(new CustomEvent("closing", { + bubbles: !1, + cancelable: !1 + })); + animateDialogClose(dlg, function() { + focusManager.popScope(dlg), dlg.classList.add("hide"), dlg.dispatchEvent(new CustomEvent("close", { + bubbles: !1, + cancelable: !1 + })) + }) + } + } + + function animateDialogOpen(dlg) { + var onAnimationFinish = function() { + focusManager.pushScope(dlg), "true" === dlg.getAttribute("data-autofocus") && focusManager.autoFocus(dlg) + }; + if (enableAnimation()) { + var onFinish = function() { + dom.removeEventListener(dlg, dom.whichAnimationEvent(), onFinish, { + once: !0 + }), onAnimationFinish() + }; + return void dom.addEventListener(dlg, dom.whichAnimationEvent(), onFinish, { + once: !0 + }) + } + onAnimationFinish() + } + + function animateDialogClose(dlg, onAnimationFinish) { + if (enableAnimation()) { + var animated = !0; + switch (dlg.animationConfig.exit.name) { + case "fadeout": + dlg.style.animation = "fadeout " + dlg.animationConfig.exit.timing.duration + "ms ease-out normal both"; + break; + case "scaledown": + dlg.style.animation = "scaledown " + dlg.animationConfig.exit.timing.duration + "ms ease-out normal both"; + break; + case "slidedown": + dlg.style.animation = "slidedown " + dlg.animationConfig.exit.timing.duration + "ms ease-out normal both"; + break; + default: + animated = !1 + } + var onFinish = function() { + dom.removeEventListener(dlg, dom.whichAnimationEvent(), onFinish, { + once: !0 + }), onAnimationFinish() + }; + if (dom.addEventListener(dlg, dom.whichAnimationEvent(), onFinish, { + once: !0 + }), animated) return + } + onAnimationFinish() + } + + function shouldLockDocumentScroll(options) { + return !(supportsOverscrollBehavior && (options.size || !browser.touch)) && (null != options.lockScroll ? options.lockScroll : "fullscreen" === options.size || (!!options.size || browser.touch)) + } + + function removeBackdrop(dlg) { + var backdrop = dlg.backdrop; + if (backdrop) { + dlg.backdrop = null; + var onAnimationFinish = function() { + tryRemoveElement(backdrop) + }; + if (enableAnimation()) return backdrop.classList.remove("dialogBackdropOpened"), void setTimeout(onAnimationFinish, 300); + onAnimationFinish() + } + } + + function centerFocus(elem, horiz, on) { + require(["scrollHelper"], function(scrollHelper) { + var fn = on ? "on" : "off"; + scrollHelper.centerFocus[fn](elem, horiz) + }) + } + + function createDialog(options) { + options = options || {}; + var dlg = document.createElement("div"); + dlg.classList.add("focuscontainer"), dlg.classList.add("hide"), shouldLockDocumentScroll(options) && dlg.setAttribute("data-lockscroll", "true"), !1 !== options.enableHistory && appRouter.enableNativeHistory() && dlg.setAttribute("data-history", "true"), !1 !== options.modal && dlg.setAttribute("modal", "modal"), !1 !== options.autoFocus && dlg.setAttribute("data-autofocus", "true"); + var defaultEntryAnimation, defaultExitAnimation; + defaultEntryAnimation = "scaleup", defaultExitAnimation = "scaledown"; + var entryAnimation = options.entryAnimation || defaultEntryAnimation, + exitAnimation = options.exitAnimation || defaultExitAnimation, + entryAnimationDuration = options.entryAnimationDuration || ("fullscreen" !== options.size ? 180 : 280), + exitAnimationDuration = options.exitAnimationDuration || ("fullscreen" !== options.size ? 120 : 220); + if (dlg.animationConfig = { + entry: { + name: entryAnimation, + timing: { + duration: entryAnimationDuration, + easing: "ease-out" + } + }, + exit: { + name: exitAnimation, + timing: { + duration: exitAnimationDuration, + easing: "ease-out", + fill: "both" + } + } + }, dlg.classList.add("dialog"), options.scrollX ? (dlg.classList.add("scrollX"), dlg.classList.add("smoothScrollX"), layoutManager.tv && centerFocus(dlg, !0, !0)) : !1 !== options.scrollY && (dlg.classList.add("smoothScrollY"), layoutManager.tv && centerFocus(dlg, !1, !0)), options.removeOnClose && dlg.setAttribute("data-removeonclose", "true"), options.size && (dlg.classList.add("dialog-fixedSize"), dlg.classList.add("dialog-" + options.size)), enableAnimation()) switch (dlg.animationConfig.entry.name) { + case "fadein": + dlg.style.animation = "fadein " + entryAnimationDuration + "ms ease-out normal"; + break; + case "scaleup": + dlg.style.animation = "scaleup " + entryAnimationDuration + "ms ease-out normal both"; + break; + case "slideup": + dlg.style.animation = "slideup " + entryAnimationDuration + "ms ease-out normal"; + break; + case "slidedown": + dlg.style.animation = "slidedown " + entryAnimationDuration + "ms ease-out normal" + } + return dlg + } + var globalOnOpenCallback, supportsOverscrollBehavior = "overscroll-behavior-y" in document.body.style; + return { + open: open, + close: close, + createDialog: createDialog, + setOnOpen: function(val) { + globalOnOpenCallback = val + } + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/displaysettings/displaysettings.js b/dashboard-ui/bower_components/emby-webcomponents/displaysettings/displaysettings.js index b855f3b9a9..36158eaecc 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/displaysettings/displaysettings.js +++ b/dashboard-ui/bower_components/emby-webcomponents/displaysettings/displaysettings.js @@ -1 +1,122 @@ -define(["require","browser","layoutManager","appSettings","pluginManager","apphost","focusManager","datetime","globalize","loading","connectionManager","skinManager","dom","events","emby-select","emby-checkbox","emby-linkbutton"],function(require,browser,layoutManager,appSettings,pluginManager,appHost,focusManager,datetime,globalize,loading,connectionManager,skinManager,dom,events){"use strict";function fillThemes(select,isDashboard){select.innerHTML=skinManager.getThemes().map(function(t){var value=t.id;return t.isDefault&&!isDashboard?value="":t.isDefaultServerDashboard&&isDashboard&&(value=""),'"}).join("")}function loadScreensavers(context,userSettings){var selectScreensaver=context.querySelector(".selectScreensaver"),options=pluginManager.ofType("screensaver").map(function(plugin){return{name:plugin.name,value:plugin.id}});options.unshift({name:globalize.translate("sharedcomponents#None"),value:"none"}),selectScreensaver.innerHTML=options.map(function(o){return'"}).join(""),selectScreensaver.value=userSettings.screensaver(),selectScreensaver.value||(selectScreensaver.value="none")}function loadSoundEffects(context,userSettings){var selectSoundEffects=context.querySelector(".selectSoundEffects"),options=pluginManager.ofType("soundeffects").map(function(plugin){return{name:plugin.name,value:plugin.id}});options.unshift({name:globalize.translate("sharedcomponents#None"),value:"none"}),selectSoundEffects.innerHTML=options.map(function(o){return'"}).join(""),selectSoundEffects.value=userSettings.soundEffects(),selectSoundEffects.value||(selectSoundEffects.value="none")}function loadSkins(context,userSettings){var selectSkin=context.querySelector(".selectSkin"),options=pluginManager.ofType("skin").map(function(plugin){return{name:plugin.name,value:plugin.id}});selectSkin.innerHTML=options.map(function(o){return'"}).join(""),selectSkin.value=userSettings.skin(),!selectSkin.value&&options.length&&(selectSkin.value=options[0].value),options.length>1&&appHost.supports("skins")?context.querySelector(".selectSkinContainer").classList.remove("hide"):context.querySelector(".selectSkinContainer").classList.add("hide")}function showOrHideMissingEpisodesField(context,user,apiClient){if(browser.tizen||browser.web0s)return void context.querySelector(".fldDisplayMissingEpisodes").classList.add("hide");context.querySelector(".fldDisplayMissingEpisodes").classList.remove("hide")}function loadForm(context,user,userSettings,apiClient){apiClient.getCurrentUserId(),user.Id;user.Policy.IsAdministrator?context.querySelector(".selectDashboardThemeContainer").classList.remove("hide"):context.querySelector(".selectDashboardThemeContainer").classList.add("hide"),appHost.supports("displaylanguage")?context.querySelector(".languageSection").classList.remove("hide"):context.querySelector(".languageSection").classList.add("hide"),appHost.supports("displaymode")?context.querySelector(".fldDisplayMode").classList.remove("hide"):context.querySelector(".fldDisplayMode").classList.add("hide"),appHost.supports("externallinks")?context.querySelector(".learnHowToContributeContainer").classList.remove("hide"):context.querySelector(".learnHowToContributeContainer").classList.add("hide"),appHost.supports("runatstartup")?context.querySelector(".fldAutorun").classList.remove("hide"):context.querySelector(".fldAutorun").classList.add("hide"),appHost.supports("soundeffects")?context.querySelector(".fldSoundEffects").classList.remove("hide"):context.querySelector(".fldSoundEffects").classList.add("hide"),appHost.supports("screensaver")?context.querySelector(".selectScreensaverContainer").classList.remove("hide"):context.querySelector(".selectScreensaverContainer").classList.add("hide"),datetime.supportsLocalization()?context.querySelector(".fldDateTimeLocale").classList.remove("hide"):context.querySelector(".fldDateTimeLocale").classList.add("hide"),browser.tizen||browser.web0s?(context.querySelector(".fldSeasonalThemes").classList.add("hide"),context.querySelector(".fldBackdrops").classList.add("hide"),context.querySelector(".fldThemeSong").classList.add("hide"),context.querySelector(".fldThemeVideo").classList.add("hide")):(context.querySelector(".fldSeasonalThemes").classList.remove("hide"),context.querySelector(".fldBackdrops").classList.remove("hide"),context.querySelector(".fldThemeSong").classList.remove("hide"),context.querySelector(".fldThemeVideo").classList.remove("hide")),context.querySelector(".chkRunAtStartup").checked=appSettings.runAtStartup();var selectTheme=context.querySelector("#selectTheme"),selectDashboardTheme=context.querySelector("#selectDashboardTheme");fillThemes(selectTheme),fillThemes(selectDashboardTheme,!0),loadScreensavers(context,userSettings),loadSoundEffects(context,userSettings),loadSkins(context,userSettings),context.querySelector(".chkDisplayMissingEpisodes").checked=user.Configuration.DisplayMissingEpisodes||!1,context.querySelector("#chkThemeSong").checked=userSettings.enableThemeSongs(),context.querySelector("#chkThemeVideo").checked=userSettings.enableThemeVideos(),context.querySelector("#chkBackdrops").checked=userSettings.enableBackdrops(),context.querySelector("#chkSeasonalThemes").checked=userSettings.enableSeasonalThemes(),context.querySelector("#selectLanguage").value=userSettings.language()||"",context.querySelector(".selectDateTimeLocale").value=userSettings.dateTimeLocale()||"",selectDashboardTheme.value=userSettings.dashboardTheme()||"",selectTheme.value=userSettings.theme()||"",context.querySelector(".selectLayout").value=layoutManager.getSavedLayout()||"",showOrHideMissingEpisodesField(context,user,apiClient),loading.hide()}function saveUser(context,user,userSettingsInstance,apiClient){return appSettings.runAtStartup(context.querySelector(".chkRunAtStartup").checked),user.Configuration.DisplayMissingEpisodes=context.querySelector(".chkDisplayMissingEpisodes").checked,appHost.supports("displaylanguage")&&userSettingsInstance.language(context.querySelector("#selectLanguage").value),userSettingsInstance.dateTimeLocale(context.querySelector(".selectDateTimeLocale").value),userSettingsInstance.enableThemeSongs(context.querySelector("#chkThemeSong").checked),userSettingsInstance.enableThemeVideos(context.querySelector("#chkThemeVideo").checked),userSettingsInstance.dashboardTheme(context.querySelector("#selectDashboardTheme").value),userSettingsInstance.theme(context.querySelector("#selectTheme").value),userSettingsInstance.soundEffects(context.querySelector(".selectSoundEffects").value),userSettingsInstance.screensaver(context.querySelector(".selectScreensaver").value),userSettingsInstance.skin(context.querySelector(".selectSkin").value),userSettingsInstance.enableBackdrops(context.querySelector("#chkBackdrops").checked),userSettingsInstance.enableSeasonalThemes(context.querySelector("#chkSeasonalThemes").checked),user.Id===apiClient.getCurrentUserId()&&skinManager.setTheme(userSettingsInstance.theme()),layoutManager.setLayout(context.querySelector(".selectLayout").value),apiClient.updateUserConfiguration(user.Id,user.Configuration)}function save(instance,context,userId,userSettings,apiClient,enableSaveConfirmation){loading.show(),apiClient.getUser(userId).then(function(user){saveUser(context,user,userSettings,apiClient).then(function(){loading.hide(),enableSaveConfirmation&&require(["toast"],function(toast){toast(globalize.translate("sharedcomponents#SettingsSaved"))}),events.trigger(instance,"saved")},function(){loading.hide()})})}function onSubmit(e){var self=this,apiClient=connectionManager.getApiClient(self.options.serverId),userId=self.options.userId,userSettings=self.options.userSettings;return userSettings.setUserInfo(userId,apiClient).then(function(){var enableSaveConfirmation=self.options.enableSaveConfirmation;save(self,self.options.element,userId,userSettings,apiClient,enableSaveConfirmation)}),e&&e.preventDefault(),!1}function embed(options,self){require(["text!./displaysettings.template.html"],function(template){options.element.innerHTML=globalize.translateDocument(template,"sharedcomponents"),options.element.querySelector("form").addEventListener("submit",onSubmit.bind(self)),options.enableSaveButton&&options.element.querySelector(".btnSave").classList.remove("hide"),self.loadData(options.autoFocus)})}function DisplaySettings(options){this.options=options,embed(options,this)}return DisplaySettings.prototype.loadData=function(autoFocus){var self=this,context=self.options.element;loading.show();var userId=self.options.userId,apiClient=connectionManager.getApiClient(self.options.serverId),userSettings=self.options.userSettings;return apiClient.getUser(userId).then(function(user){return userSettings.setUserInfo(userId,apiClient).then(function(){self.dataLoaded=!0,loadForm(context,user,userSettings,apiClient),autoFocus&&focusManager.autoFocus(context)})})},DisplaySettings.prototype.submit=function(){onSubmit.call(this)},DisplaySettings.prototype.destroy=function(){this.options=null},DisplaySettings}); \ No newline at end of file +define(["require", "browser", "layoutManager", "appSettings", "pluginManager", "apphost", "focusManager", "datetime", "globalize", "loading", "connectionManager", "skinManager", "dom", "events", "emby-select", "emby-checkbox", "emby-linkbutton"], function(require, browser, layoutManager, appSettings, pluginManager, appHost, focusManager, datetime, globalize, loading, connectionManager, skinManager, dom, events) { + "use strict"; + + function fillThemes(select, isDashboard) { + select.innerHTML = skinManager.getThemes().map(function(t) { + var value = t.id; + return t.isDefault && !isDashboard ? value = "" : t.isDefaultServerDashboard && isDashboard && (value = ""), '" + }).join("") + } + + function loadScreensavers(context, userSettings) { + var selectScreensaver = context.querySelector(".selectScreensaver"), + options = pluginManager.ofType("screensaver").map(function(plugin) { + return { + name: plugin.name, + value: plugin.id + } + }); + options.unshift({ + name: globalize.translate("sharedcomponents#None"), + value: "none" + }), selectScreensaver.innerHTML = options.map(function(o) { + return '" + }).join(""), selectScreensaver.value = userSettings.screensaver(), selectScreensaver.value || (selectScreensaver.value = "none") + } + + function loadSoundEffects(context, userSettings) { + var selectSoundEffects = context.querySelector(".selectSoundEffects"), + options = pluginManager.ofType("soundeffects").map(function(plugin) { + return { + name: plugin.name, + value: plugin.id + } + }); + options.unshift({ + name: globalize.translate("sharedcomponents#None"), + value: "none" + }), selectSoundEffects.innerHTML = options.map(function(o) { + return '" + }).join(""), selectSoundEffects.value = userSettings.soundEffects(), selectSoundEffects.value || (selectSoundEffects.value = "none") + } + + function loadSkins(context, userSettings) { + var selectSkin = context.querySelector(".selectSkin"), + options = pluginManager.ofType("skin").map(function(plugin) { + return { + name: plugin.name, + value: plugin.id + } + }); + selectSkin.innerHTML = options.map(function(o) { + return '" + }).join(""), selectSkin.value = userSettings.skin(), !selectSkin.value && options.length && (selectSkin.value = options[0].value), options.length > 1 && appHost.supports("skins") ? context.querySelector(".selectSkinContainer").classList.remove("hide") : context.querySelector(".selectSkinContainer").classList.add("hide") + } + + function showOrHideMissingEpisodesField(context, user, apiClient) { + if (browser.tizen || browser.web0s) return void context.querySelector(".fldDisplayMissingEpisodes").classList.add("hide"); + context.querySelector(".fldDisplayMissingEpisodes").classList.remove("hide") + } + + function loadForm(context, user, userSettings, apiClient) { + apiClient.getCurrentUserId(), user.Id; + user.Policy.IsAdministrator ? context.querySelector(".selectDashboardThemeContainer").classList.remove("hide") : context.querySelector(".selectDashboardThemeContainer").classList.add("hide"), appHost.supports("displaylanguage") ? context.querySelector(".languageSection").classList.remove("hide") : context.querySelector(".languageSection").classList.add("hide"), appHost.supports("displaymode") ? context.querySelector(".fldDisplayMode").classList.remove("hide") : context.querySelector(".fldDisplayMode").classList.add("hide"), appHost.supports("externallinks") ? context.querySelector(".learnHowToContributeContainer").classList.remove("hide") : context.querySelector(".learnHowToContributeContainer").classList.add("hide"), appHost.supports("runatstartup") ? context.querySelector(".fldAutorun").classList.remove("hide") : context.querySelector(".fldAutorun").classList.add("hide"), appHost.supports("soundeffects") ? context.querySelector(".fldSoundEffects").classList.remove("hide") : context.querySelector(".fldSoundEffects").classList.add("hide"), appHost.supports("screensaver") ? context.querySelector(".selectScreensaverContainer").classList.remove("hide") : context.querySelector(".selectScreensaverContainer").classList.add("hide"), datetime.supportsLocalization() ? context.querySelector(".fldDateTimeLocale").classList.remove("hide") : context.querySelector(".fldDateTimeLocale").classList.add("hide"), browser.tizen || browser.web0s ? (context.querySelector(".fldSeasonalThemes").classList.add("hide"), context.querySelector(".fldBackdrops").classList.add("hide"), context.querySelector(".fldThemeSong").classList.add("hide"), context.querySelector(".fldThemeVideo").classList.add("hide")) : (context.querySelector(".fldSeasonalThemes").classList.remove("hide"), context.querySelector(".fldBackdrops").classList.remove("hide"), context.querySelector(".fldThemeSong").classList.remove("hide"), context.querySelector(".fldThemeVideo").classList.remove("hide")), context.querySelector(".chkRunAtStartup").checked = appSettings.runAtStartup(); + var selectTheme = context.querySelector("#selectTheme"), + selectDashboardTheme = context.querySelector("#selectDashboardTheme"); + fillThemes(selectTheme), fillThemes(selectDashboardTheme, !0), loadScreensavers(context, userSettings), loadSoundEffects(context, userSettings), loadSkins(context, userSettings), context.querySelector(".chkDisplayMissingEpisodes").checked = user.Configuration.DisplayMissingEpisodes || !1, context.querySelector("#chkThemeSong").checked = userSettings.enableThemeSongs(), context.querySelector("#chkThemeVideo").checked = userSettings.enableThemeVideos(), context.querySelector("#chkBackdrops").checked = userSettings.enableBackdrops(), context.querySelector("#chkSeasonalThemes").checked = userSettings.enableSeasonalThemes(), context.querySelector("#selectLanguage").value = userSettings.language() || "", context.querySelector(".selectDateTimeLocale").value = userSettings.dateTimeLocale() || "", selectDashboardTheme.value = userSettings.dashboardTheme() || "", selectTheme.value = userSettings.theme() || "", context.querySelector(".selectLayout").value = layoutManager.getSavedLayout() || "", showOrHideMissingEpisodesField(context, user, apiClient), loading.hide() + } + + function saveUser(context, user, userSettingsInstance, apiClient) { + return appSettings.runAtStartup(context.querySelector(".chkRunAtStartup").checked), user.Configuration.DisplayMissingEpisodes = context.querySelector(".chkDisplayMissingEpisodes").checked, appHost.supports("displaylanguage") && userSettingsInstance.language(context.querySelector("#selectLanguage").value), userSettingsInstance.dateTimeLocale(context.querySelector(".selectDateTimeLocale").value), userSettingsInstance.enableThemeSongs(context.querySelector("#chkThemeSong").checked), userSettingsInstance.enableThemeVideos(context.querySelector("#chkThemeVideo").checked), userSettingsInstance.dashboardTheme(context.querySelector("#selectDashboardTheme").value), userSettingsInstance.theme(context.querySelector("#selectTheme").value), userSettingsInstance.soundEffects(context.querySelector(".selectSoundEffects").value), userSettingsInstance.screensaver(context.querySelector(".selectScreensaver").value), userSettingsInstance.skin(context.querySelector(".selectSkin").value), userSettingsInstance.enableBackdrops(context.querySelector("#chkBackdrops").checked), userSettingsInstance.enableSeasonalThemes(context.querySelector("#chkSeasonalThemes").checked), user.Id === apiClient.getCurrentUserId() && skinManager.setTheme(userSettingsInstance.theme()), layoutManager.setLayout(context.querySelector(".selectLayout").value), apiClient.updateUserConfiguration(user.Id, user.Configuration) + } + + function save(instance, context, userId, userSettings, apiClient, enableSaveConfirmation) { + loading.show(), apiClient.getUser(userId).then(function(user) { + saveUser(context, user, userSettings, apiClient).then(function() { + loading.hide(), enableSaveConfirmation && require(["toast"], function(toast) { + toast(globalize.translate("sharedcomponents#SettingsSaved")) + }), events.trigger(instance, "saved") + }, function() { + loading.hide() + }) + }) + } + + function onSubmit(e) { + var self = this, + apiClient = connectionManager.getApiClient(self.options.serverId), + userId = self.options.userId, + userSettings = self.options.userSettings; + return userSettings.setUserInfo(userId, apiClient).then(function() { + var enableSaveConfirmation = self.options.enableSaveConfirmation; + save(self, self.options.element, userId, userSettings, apiClient, enableSaveConfirmation) + }), e && e.preventDefault(), !1 + } + + function embed(options, self) { + require(["text!./displaysettings.template.html"], function(template) { + options.element.innerHTML = globalize.translateDocument(template, "sharedcomponents"), options.element.querySelector("form").addEventListener("submit", onSubmit.bind(self)), options.enableSaveButton && options.element.querySelector(".btnSave").classList.remove("hide"), self.loadData(options.autoFocus) + }) + } + + function DisplaySettings(options) { + this.options = options, embed(options, this) + } + return DisplaySettings.prototype.loadData = function(autoFocus) { + var self = this, + context = self.options.element; + loading.show(); + var userId = self.options.userId, + apiClient = connectionManager.getApiClient(self.options.serverId), + userSettings = self.options.userSettings; + return apiClient.getUser(userId).then(function(user) { + return userSettings.setUserInfo(userId, apiClient).then(function() { + self.dataLoaded = !0, loadForm(context, user, userSettings, apiClient), autoFocus && focusManager.autoFocus(context) + }) + }) + }, DisplaySettings.prototype.submit = function() { + onSubmit.call(this) + }, DisplaySettings.prototype.destroy = function() { + this.options = null + }, DisplaySettings +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/dom.js b/dashboard-ui/bower_components/emby-webcomponents/dom.js index 2ddf5f0779..cbc85e28a4 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/dom.js +++ b/dashboard-ui/bower_components/emby-webcomponents/dom.js @@ -1 +1,105 @@ -define([],function(){"use strict";function parentWithAttribute(elem,name,value){for(;value?elem.getAttribute(name)!==value:!elem.getAttribute(name);)if(!(elem=elem.parentNode)||!elem.getAttribute)return null;return elem}function parentWithTag(elem,tagNames){for(Array.isArray(tagNames)||(tagNames=[tagNames]);-1===tagNames.indexOf(elem.tagName||"");)if(!(elem=elem.parentNode))return null;return elem}function containsAnyClass(classList,classNames){for(var i=0,length=classNames.length;i'+checkedIcon+"",uncheckedHtml=''+uncheckedIcon+"";labelElement.insertAdjacentHTML("beforeend",''+checkHtml+uncheckedHtml+""),labelTextElement.classList.add("checkboxLabel"),this.addEventListener("keydown",onKeyDown),enableRefreshHack&&(forceRefresh.call(this,!0),dom.addEventListener(this,"click",forceRefresh,{passive:!0}),dom.addEventListener(this,"blur",forceRefresh,{passive:!0}),dom.addEventListener(this,"focus",forceRefresh,{passive:!0}),dom.addEventListener(this,"change",forceRefresh,{passive:!0}))}},EmbyCheckboxPrototype.detachedCallback=function(){this.removeEventListener("keydown",onKeyDown),dom.removeEventListener(this,"click",forceRefresh,{passive:!0}),dom.removeEventListener(this,"blur",forceRefresh,{passive:!0}),dom.removeEventListener(this,"focus",forceRefresh,{passive:!0}),dom.removeEventListener(this,"change",forceRefresh,{passive:!0})},document.registerElement("emby-checkbox",{prototype:EmbyCheckboxPrototype,extends:"input"})}); \ No newline at end of file +define(["browser", "dom", "css!./emby-checkbox", "registerElement"], function(browser, dom) { + "use strict"; + + function onKeyDown(e) { + if (13 === e.keyCode) return e.preventDefault(), this.checked = !this.checked, this.dispatchEvent(new CustomEvent("change", { + bubbles: !0 + })), !1 + } + + function forceRefresh(loading) { + var elem = this.parentNode; + elem.style.webkitAnimationName = "repaintChrome", elem.style.webkitAnimationDelay = !0 === loading ? "500ms" : "", elem.style.webkitAnimationDuration = "10ms", elem.style.webkitAnimationIterationCount = "1", setTimeout(function() { + elem.style.webkitAnimationName = "" + }, !0 === loading ? 520 : 20) + } + var EmbyCheckboxPrototype = Object.create(HTMLInputElement.prototype), + enableRefreshHack = !!(browser.tizen || browser.orsay || browser.operaTv || browser.web0s); + EmbyCheckboxPrototype.attachedCallback = function() { + if ("true" !== this.getAttribute("data-embycheckbox")) { + this.setAttribute("data-embycheckbox", "true"), this.classList.add("emby-checkbox"); + var labelElement = this.parentNode; + labelElement.classList.add("emby-checkbox-label"); + var labelTextElement = labelElement.querySelector("span"), + outlineClass = "checkboxOutline", + customClass = this.getAttribute("data-outlineclass"); + customClass && (outlineClass += " " + customClass); + var checkedIcon = this.getAttribute("data-checkedicon") || "", + uncheckedIcon = this.getAttribute("data-uncheckedicon") || "", + checkHtml = '' + checkedIcon + "", + uncheckedHtml = '' + uncheckedIcon + ""; + labelElement.insertAdjacentHTML("beforeend", '' + checkHtml + uncheckedHtml + ""), labelTextElement.classList.add("checkboxLabel"), this.addEventListener("keydown", onKeyDown), enableRefreshHack && (forceRefresh.call(this, !0), dom.addEventListener(this, "click", forceRefresh, { + passive: !0 + }), dom.addEventListener(this, "blur", forceRefresh, { + passive: !0 + }), dom.addEventListener(this, "focus", forceRefresh, { + passive: !0 + }), dom.addEventListener(this, "change", forceRefresh, { + passive: !0 + })) + } + }, EmbyCheckboxPrototype.detachedCallback = function() { + this.removeEventListener("keydown", onKeyDown), dom.removeEventListener(this, "click", forceRefresh, { + passive: !0 + }), dom.removeEventListener(this, "blur", forceRefresh, { + passive: !0 + }), dom.removeEventListener(this, "focus", forceRefresh, { + passive: !0 + }), dom.removeEventListener(this, "change", forceRefresh, { + passive: !0 + }) + }, document.registerElement("emby-checkbox", { + prototype: EmbyCheckboxPrototype, + extends: "input" + }) +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/emby-collapse/emby-collapse.js b/dashboard-ui/bower_components/emby-webcomponents/emby-collapse/emby-collapse.js index 913f1d0797..4a237a9174 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/emby-collapse/emby-collapse.js +++ b/dashboard-ui/bower_components/emby-webcomponents/emby-collapse/emby-collapse.js @@ -1 +1,43 @@ -define(["browser","css!./emby-collapse","registerElement","emby-button"],function(browser){"use strict";function slideDownToShow(button,elem){elem.classList.remove("hide"),elem.classList.add("expanded"),elem.style.height="auto";var height=elem.offsetHeight+"px";elem.style.height="0";elem.offsetHeight;elem.style.height=height,setTimeout(function(){elem.classList.contains("expanded")?elem.classList.remove("hide"):elem.classList.add("hide"),elem.style.height="auto"},300),button.querySelector("i").classList.add("emby-collapse-expandIconExpanded")}function slideUpToHide(button,elem){elem.style.height=elem.offsetHeight+"px";elem.offsetHeight;elem.classList.remove("expanded"),elem.style.height="0",setTimeout(function(){elem.classList.contains("expanded")?elem.classList.remove("hide"):elem.classList.add("hide")},300),button.querySelector("i").classList.remove("emby-collapse-expandIconExpanded")}function onButtonClick(e){var button=this,collapseContent=button.parentNode.querySelector(".collapseContent");collapseContent.expanded?(collapseContent.expanded=!1,slideUpToHide(button,collapseContent)):(collapseContent.expanded=!0,slideDownToShow(button,collapseContent))}var EmbyButtonPrototype=Object.create(HTMLDivElement.prototype);EmbyButtonPrototype.attachedCallback=function(){if(!this.classList.contains("emby-collapse")){this.classList.add("emby-collapse");var collapseContent=this.querySelector(".collapseContent");collapseContent&&collapseContent.classList.add("hide");var title=this.getAttribute("title"),html='';this.insertAdjacentHTML("afterbegin",html);var button=this.querySelector(".emby-collapsible-button");button.addEventListener("click",onButtonClick),"true"===this.getAttribute("data-expanded")&&onButtonClick.call(button)}},document.registerElement("emby-collapse",{prototype:EmbyButtonPrototype,extends:"div"})}); \ No newline at end of file +define(["browser", "css!./emby-collapse", "registerElement", "emby-button"], function(browser) { + "use strict"; + + function slideDownToShow(button, elem) { + elem.classList.remove("hide"), elem.classList.add("expanded"), elem.style.height = "auto"; + var height = elem.offsetHeight + "px"; + elem.style.height = "0"; + elem.offsetHeight; + elem.style.height = height, setTimeout(function() { + elem.classList.contains("expanded") ? elem.classList.remove("hide") : elem.classList.add("hide"), elem.style.height = "auto" + }, 300), button.querySelector("i").classList.add("emby-collapse-expandIconExpanded") + } + + function slideUpToHide(button, elem) { + elem.style.height = elem.offsetHeight + "px"; + elem.offsetHeight; + elem.classList.remove("expanded"), elem.style.height = "0", setTimeout(function() { + elem.classList.contains("expanded") ? elem.classList.remove("hide") : elem.classList.add("hide") + }, 300), button.querySelector("i").classList.remove("emby-collapse-expandIconExpanded") + } + + function onButtonClick(e) { + var button = this, + collapseContent = button.parentNode.querySelector(".collapseContent"); + collapseContent.expanded ? (collapseContent.expanded = !1, slideUpToHide(button, collapseContent)) : (collapseContent.expanded = !0, slideDownToShow(button, collapseContent)) + } + var EmbyButtonPrototype = Object.create(HTMLDivElement.prototype); + EmbyButtonPrototype.attachedCallback = function() { + if (!this.classList.contains("emby-collapse")) { + this.classList.add("emby-collapse"); + var collapseContent = this.querySelector(".collapseContent"); + collapseContent && collapseContent.classList.add("hide"); + var title = this.getAttribute("title"), + html = ''; + this.insertAdjacentHTML("afterbegin", html); + var button = this.querySelector(".emby-collapsible-button"); + button.addEventListener("click", onButtonClick), "true" === this.getAttribute("data-expanded") && onButtonClick.call(button) + } + }, document.registerElement("emby-collapse", { + prototype: EmbyButtonPrototype, + extends: "div" + }) +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/emby-connect/connecthelper.js b/dashboard-ui/bower_components/emby-webcomponents/emby-connect/connecthelper.js index 2105bddcf4..8bd49a42be 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/emby-connect/connecthelper.js +++ b/dashboard-ui/bower_components/emby-webcomponents/emby-connect/connecthelper.js @@ -1 +1,106 @@ -define(["globalize","apphost","loading","alert","emby-linkbutton"],function(globalize,appHost,loading,alert){"use strict";function resolvePromise(){return Promise.resolve()}function rejectPromise(){return Promise.reject()}function showNewUserInviteMessage(result){if(!result.IsNewUserInvitation&&!result.IsPending)return Promise.resolve();var message=result.IsNewUserInvitation?globalize.translate("sharedcomponents#MessageInvitationSentToNewUser",result.GuestDisplayName):globalize.translate("sharedcomponents#MessageInvitationSentToUser",result.GuestDisplayName);return alert({text:message,title:globalize.translate("sharedcomponents#HeaderInvitationSent")}).then(resolvePromise,resolvePromise)}function inviteGuest(options){var apiClient=options.apiClient;return loading.show(),apiClient.ajax({type:"POST",url:apiClient.getUrl("Connect/Invite"),dataType:"json",data:options.guestOptions||{}}).then(function(result){return loading.hide(),showNewUserInviteMessage(result)},function(response){loading.hide();var statusCode=response?response.status:0;return 502===statusCode?showConnectServerUnreachableErrorMessage().then(rejectPromise,rejectPromise):404===statusCode?alert({text:globalize.translate("sharedcomponents#GuestUserNotFound")}).then(rejectPromise,rejectPromise):(statusCode||0)>=500?alert({text:globalize.translate("sharedcomponents#ErrorReachingEmbyConnect")}).then(rejectPromise,rejectPromise):showGuestGeneralErrorMessage().then(rejectPromise,rejectPromise)})}function showGuestGeneralErrorMessage(){var html;appHost.supports("externallinks")&&(html=globalize.translate("sharedcomponents#ErrorAddingGuestAccount1",'https://emby.media/connect'),html+="

"+globalize.translate("sharedcomponents#ErrorAddingGuestAccount2","apps@emby.media"));var text=globalize.translate("sharedcomponents#ErrorAddingGuestAccount1","https://emby.media/connect");return text+="\n\n"+globalize.translate("sharedcomponents#ErrorAddingGuestAccount2","apps@emby.media"),alert({text:text,html:html})}function showConnectServerUnreachableErrorMessage(){var text=globalize.translate("sharedcomponents#ErrorConnectServerUnreachable","https://connect.emby.media");return alert({text:text})}function showLinkUserErrorMessage(username,statusCode){var html,text;return 502===statusCode?showConnectServerUnreachableErrorMessage():(username?(appHost.supports("externallinks")&&(html=globalize.translate("sharedcomponents#ErrorAddingEmbyConnectAccount1",'https://emby.media/connect'),html+="

"+globalize.translate("sharedcomponents#ErrorAddingEmbyConnectAccount2","apps@emby.media")),text=globalize.translate("sharedcomponents#ErrorAddingEmbyConnectAccount1","https://emby.media/connect"),text+="\n\n"+globalize.translate("sharedcomponents#ErrorAddingEmbyConnectAccount2","apps@emby.media")):html=text=globalize.translate("sharedcomponents#DefaultErrorMessage"),alert({text:text,html:html}))}function updateUserLink(apiClient,user,newConnectUsername){var currentConnectUsername=user.ConnectUserName||"",enteredConnectUsername=newConnectUsername,linkUrl=apiClient.getUrl("Users/"+user.Id+"/Connect/Link");return currentConnectUsername&&!enteredConnectUsername?apiClient.ajax({type:"DELETE",url:linkUrl}).then(function(){return alert({text:globalize.translate("sharedcomponents#MessageEmbyAccontRemoved"),title:globalize.translate("sharedcomponents#HeaderEmbyAccountRemoved")}).catch(resolvePromise)},function(response){return 502===(response?response.status:0)?showConnectServerUnreachableErrorMessage().then(rejectPromise):alert({text:globalize.translate("sharedcomponents#ErrorRemovingEmbyConnectAccount")}).then(rejectPromise)}):currentConnectUsername!==enteredConnectUsername?apiClient.ajax({type:"POST",url:linkUrl,data:{ConnectUsername:enteredConnectUsername},dataType:"json"}).then(function(result){var msgKey=result.IsPending?"sharedcomponents#MessagePendingEmbyAccountAdded":"sharedcomponents#MessageEmbyAccountAdded";return alert({text:globalize.translate(msgKey),title:globalize.translate("sharedcomponents#HeaderEmbyAccountAdded")}).catch(resolvePromise)},function(response){var statusCode=response?response.status:0;return 502===statusCode?showConnectServerUnreachableErrorMessage().then(rejectPromise):showLinkUserErrorMessage(".",statusCode).then(rejectPromise)}):Promise.reject()}return{inviteGuest:inviteGuest,updateUserLink:updateUserLink,showLinkUserErrorMessage:showLinkUserErrorMessage,showConnectServerUnreachableErrorMessage:showConnectServerUnreachableErrorMessage}}); \ No newline at end of file +define(["globalize", "apphost", "loading", "alert", "emby-linkbutton"], function(globalize, appHost, loading, alert) { + "use strict"; + + function resolvePromise() { + return Promise.resolve() + } + + function rejectPromise() { + return Promise.reject() + } + + function showNewUserInviteMessage(result) { + if (!result.IsNewUserInvitation && !result.IsPending) return Promise.resolve(); + var message = result.IsNewUserInvitation ? globalize.translate("sharedcomponents#MessageInvitationSentToNewUser", result.GuestDisplayName) : globalize.translate("sharedcomponents#MessageInvitationSentToUser", result.GuestDisplayName); + return alert({ + text: message, + title: globalize.translate("sharedcomponents#HeaderInvitationSent") + }).then(resolvePromise, resolvePromise) + } + + function inviteGuest(options) { + var apiClient = options.apiClient; + return loading.show(), apiClient.ajax({ + type: "POST", + url: apiClient.getUrl("Connect/Invite"), + dataType: "json", + data: options.guestOptions || {} + }).then(function(result) { + return loading.hide(), showNewUserInviteMessage(result) + }, function(response) { + loading.hide(); + var statusCode = response ? response.status : 0; + return 502 === statusCode ? showConnectServerUnreachableErrorMessage().then(rejectPromise, rejectPromise) : 404 === statusCode ? alert({ + text: globalize.translate("sharedcomponents#GuestUserNotFound") + }).then(rejectPromise, rejectPromise) : (statusCode || 0) >= 500 ? alert({ + text: globalize.translate("sharedcomponents#ErrorReachingEmbyConnect") + }).then(rejectPromise, rejectPromise) : showGuestGeneralErrorMessage().then(rejectPromise, rejectPromise) + }) + } + + function showGuestGeneralErrorMessage() { + var html; + appHost.supports("externallinks") && (html = globalize.translate("sharedcomponents#ErrorAddingGuestAccount1", 'https://emby.media/connect'), html += "

" + globalize.translate("sharedcomponents#ErrorAddingGuestAccount2", "apps@emby.media")); + var text = globalize.translate("sharedcomponents#ErrorAddingGuestAccount1", "https://emby.media/connect"); + return text += "\n\n" + globalize.translate("sharedcomponents#ErrorAddingGuestAccount2", "apps@emby.media"), alert({ + text: text, + html: html + }) + } + + function showConnectServerUnreachableErrorMessage() { + var text = globalize.translate("sharedcomponents#ErrorConnectServerUnreachable", "https://connect.emby.media"); + return alert({ + text: text + }) + } + + function showLinkUserErrorMessage(username, statusCode) { + var html, text; + return 502 === statusCode ? showConnectServerUnreachableErrorMessage() : (username ? (appHost.supports("externallinks") && (html = globalize.translate("sharedcomponents#ErrorAddingEmbyConnectAccount1", 'https://emby.media/connect'), html += "

" + globalize.translate("sharedcomponents#ErrorAddingEmbyConnectAccount2", "apps@emby.media")), text = globalize.translate("sharedcomponents#ErrorAddingEmbyConnectAccount1", "https://emby.media/connect"), text += "\n\n" + globalize.translate("sharedcomponents#ErrorAddingEmbyConnectAccount2", "apps@emby.media")) : html = text = globalize.translate("sharedcomponents#DefaultErrorMessage"), alert({ + text: text, + html: html + })) + } + + function updateUserLink(apiClient, user, newConnectUsername) { + var currentConnectUsername = user.ConnectUserName || "", + enteredConnectUsername = newConnectUsername, + linkUrl = apiClient.getUrl("Users/" + user.Id + "/Connect/Link"); + return currentConnectUsername && !enteredConnectUsername ? apiClient.ajax({ + type: "DELETE", + url: linkUrl + }).then(function() { + return alert({ + text: globalize.translate("sharedcomponents#MessageEmbyAccontRemoved"), + title: globalize.translate("sharedcomponents#HeaderEmbyAccountRemoved") + }).catch(resolvePromise) + }, function(response) { + return 502 === (response ? response.status : 0) ? showConnectServerUnreachableErrorMessage().then(rejectPromise) : alert({ + text: globalize.translate("sharedcomponents#ErrorRemovingEmbyConnectAccount") + }).then(rejectPromise) + }) : currentConnectUsername !== enteredConnectUsername ? apiClient.ajax({ + type: "POST", + url: linkUrl, + data: { + ConnectUsername: enteredConnectUsername + }, + dataType: "json" + }).then(function(result) { + var msgKey = result.IsPending ? "sharedcomponents#MessagePendingEmbyAccountAdded" : "sharedcomponents#MessageEmbyAccountAdded"; + return alert({ + text: globalize.translate(msgKey), + title: globalize.translate("sharedcomponents#HeaderEmbyAccountAdded") + }).catch(resolvePromise) + }, function(response) { + var statusCode = response ? response.status : 0; + return 502 === statusCode ? showConnectServerUnreachableErrorMessage().then(rejectPromise) : showLinkUserErrorMessage(".", statusCode).then(rejectPromise) + }) : Promise.reject() + } + return { + inviteGuest: inviteGuest, + updateUserLink: updateUserLink, + showLinkUserErrorMessage: showLinkUserErrorMessage, + showConnectServerUnreachableErrorMessage: showConnectServerUnreachableErrorMessage + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/emby-input/emby-input.js b/dashboard-ui/bower_components/emby-webcomponents/emby-input/emby-input.js index ea0fba310a..e6d6c0aeb7 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/emby-input/emby-input.js +++ b/dashboard-ui/bower_components/emby-webcomponents/emby-input/emby-input.js @@ -1 +1,56 @@ -define(["layoutManager","browser","dom","css!./emby-input","registerElement"],function(layoutManager,browser,dom){"use strict";function onChange(){var label=this.labelElement;if(this.value)label.classList.remove("inputLabel-float");else{supportsFloatingLabel&&"date"!==this.type&&"time"!==this.type&&label.classList.add("inputLabel-float")}}var EmbyInputPrototype=Object.create(HTMLInputElement.prototype),inputId=0,supportsFloatingLabel=!1;if(Object.getOwnPropertyDescriptor&&Object.defineProperty){var descriptor=Object.getOwnPropertyDescriptor(HTMLInputElement.prototype,"value");if(descriptor&&descriptor.configurable){var baseSetMethod=descriptor.set;descriptor.set=function(value){baseSetMethod.call(this,value),this.dispatchEvent(new CustomEvent("valueset",{bubbles:!1,cancelable:!1}))},Object.defineProperty(HTMLInputElement.prototype,"value",descriptor),supportsFloatingLabel=!0}}EmbyInputPrototype.createdCallback=function(){if(this.id||(this.id="embyinput"+inputId,inputId++),!this.classList.contains("emby-input")){this.classList.add("emby-input");var parentNode=this.parentNode,document=this.ownerDocument,label=document.createElement("label");label.innerHTML=this.getAttribute("label")||"",label.classList.add("inputLabel"),label.classList.add("inputLabelUnfocused"),label.htmlFor=this.id,parentNode.insertBefore(label,this),this.labelElement=label,dom.addEventListener(this,"focus",function(){onChange.call(this),document.attachIME&&document.attachIME(this),label.classList.add("inputLabelFocused"),label.classList.remove("inputLabelUnfocused")},{passive:!0}),dom.addEventListener(this,"blur",function(){onChange.call(this),label.classList.remove("inputLabelFocused"),label.classList.add("inputLabelUnfocused")},{passive:!0}),dom.addEventListener(this,"change",onChange,{passive:!0}),dom.addEventListener(this,"input",onChange,{passive:!0}),dom.addEventListener(this,"valueset",onChange,{passive:!0}),browser.orsay&&this===document.activeElement&&document.attachIME&&document.attachIME(this)}},EmbyInputPrototype.attachedCallback=function(){this.labelElement.htmlFor=this.id,onChange.call(this)},EmbyInputPrototype.label=function(text){this.labelElement.innerHTML=text},document.registerElement("emby-input",{prototype:EmbyInputPrototype,extends:"input"})}); \ No newline at end of file +define(["layoutManager", "browser", "dom", "css!./emby-input", "registerElement"], function(layoutManager, browser, dom) { + "use strict"; + + function onChange() { + var label = this.labelElement; + if (this.value) label.classList.remove("inputLabel-float"); + else { + supportsFloatingLabel && "date" !== this.type && "time" !== this.type && label.classList.add("inputLabel-float") + } + } + var EmbyInputPrototype = Object.create(HTMLInputElement.prototype), + inputId = 0, + supportsFloatingLabel = !1; + if (Object.getOwnPropertyDescriptor && Object.defineProperty) { + var descriptor = Object.getOwnPropertyDescriptor(HTMLInputElement.prototype, "value"); + if (descriptor && descriptor.configurable) { + var baseSetMethod = descriptor.set; + descriptor.set = function(value) { + baseSetMethod.call(this, value), this.dispatchEvent(new CustomEvent("valueset", { + bubbles: !1, + cancelable: !1 + })) + }, Object.defineProperty(HTMLInputElement.prototype, "value", descriptor), supportsFloatingLabel = !0 + } + } + EmbyInputPrototype.createdCallback = function() { + if (this.id || (this.id = "embyinput" + inputId, inputId++), !this.classList.contains("emby-input")) { + this.classList.add("emby-input"); + var parentNode = this.parentNode, + document = this.ownerDocument, + label = document.createElement("label"); + label.innerHTML = this.getAttribute("label") || "", label.classList.add("inputLabel"), label.classList.add("inputLabelUnfocused"), label.htmlFor = this.id, parentNode.insertBefore(label, this), this.labelElement = label, dom.addEventListener(this, "focus", function() { + onChange.call(this), document.attachIME && document.attachIME(this), label.classList.add("inputLabelFocused"), label.classList.remove("inputLabelUnfocused") + }, { + passive: !0 + }), dom.addEventListener(this, "blur", function() { + onChange.call(this), label.classList.remove("inputLabelFocused"), label.classList.add("inputLabelUnfocused") + }, { + passive: !0 + }), dom.addEventListener(this, "change", onChange, { + passive: !0 + }), dom.addEventListener(this, "input", onChange, { + passive: !0 + }), dom.addEventListener(this, "valueset", onChange, { + passive: !0 + }), browser.orsay && this === document.activeElement && document.attachIME && document.attachIME(this) + } + }, EmbyInputPrototype.attachedCallback = function() { + this.labelElement.htmlFor = this.id, onChange.call(this) + }, EmbyInputPrototype.label = function(text) { + this.labelElement.innerHTML = text + }, document.registerElement("emby-input", { + prototype: EmbyInputPrototype, + extends: "input" + }) +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/emby-itemrefreshindicator/emby-itemrefreshindicator.js b/dashboard-ui/bower_components/emby-webcomponents/emby-itemrefreshindicator/emby-itemrefreshindicator.js index 229ee3b544..a575c8ec27 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/emby-itemrefreshindicator/emby-itemrefreshindicator.js +++ b/dashboard-ui/bower_components/emby-webcomponents/emby-itemrefreshindicator/emby-itemrefreshindicator.js @@ -1 +1,32 @@ -define(["emby-progressring","dom","serverNotifications","events","registerElement"],function(EmbyProgressRing,dom,serverNotifications,events){"use strict";function addNotificationEvent(instance,name,handler){var localHandler=handler.bind(instance);events.on(serverNotifications,name,localHandler),instance[name]=localHandler}function removeNotificationEvent(instance,name){var handler=instance[name];handler&&(events.off(serverNotifications,name,handler),instance[name]=null)}function onRefreshProgress(e,apiClient,info){var indicator=this;if(indicator.itemId||(indicator.itemId=dom.parentWithAttribute(indicator,"data-id").getAttribute("data-id")),info.ItemId===indicator.itemId){var progress=parseFloat(info.Progress);progress&&progress<100?this.classList.remove("hide"):this.classList.add("hide"),this.setProgress(progress)}}var EmbyItemRefreshIndicatorPrototype=Object.create(EmbyProgressRing);EmbyItemRefreshIndicatorPrototype.createdCallback=function(){EmbyProgressRing.createdCallback&&EmbyProgressRing.createdCallback.call(this),addNotificationEvent(this,"RefreshProgress",onRefreshProgress)},EmbyItemRefreshIndicatorPrototype.attachedCallback=function(){EmbyProgressRing.attachedCallback&&EmbyProgressRing.attachedCallback.call(this)},EmbyItemRefreshIndicatorPrototype.detachedCallback=function(){EmbyProgressRing.detachedCallback&&EmbyProgressRing.detachedCallback.call(this),removeNotificationEvent(this,"RefreshProgress"),this.itemId=null},document.registerElement("emby-itemrefreshindicator",{prototype:EmbyItemRefreshIndicatorPrototype,extends:"div"})}); \ No newline at end of file +define(["emby-progressring", "dom", "serverNotifications", "events", "registerElement"], function(EmbyProgressRing, dom, serverNotifications, events) { + "use strict"; + + function addNotificationEvent(instance, name, handler) { + var localHandler = handler.bind(instance); + events.on(serverNotifications, name, localHandler), instance[name] = localHandler + } + + function removeNotificationEvent(instance, name) { + var handler = instance[name]; + handler && (events.off(serverNotifications, name, handler), instance[name] = null) + } + + function onRefreshProgress(e, apiClient, info) { + var indicator = this; + if (indicator.itemId || (indicator.itemId = dom.parentWithAttribute(indicator, "data-id").getAttribute("data-id")), info.ItemId === indicator.itemId) { + var progress = parseFloat(info.Progress); + progress && progress < 100 ? this.classList.remove("hide") : this.classList.add("hide"), this.setProgress(progress) + } + } + var EmbyItemRefreshIndicatorPrototype = Object.create(EmbyProgressRing); + EmbyItemRefreshIndicatorPrototype.createdCallback = function() { + EmbyProgressRing.createdCallback && EmbyProgressRing.createdCallback.call(this), addNotificationEvent(this, "RefreshProgress", onRefreshProgress) + }, EmbyItemRefreshIndicatorPrototype.attachedCallback = function() { + EmbyProgressRing.attachedCallback && EmbyProgressRing.attachedCallback.call(this) + }, EmbyItemRefreshIndicatorPrototype.detachedCallback = function() { + EmbyProgressRing.detachedCallback && EmbyProgressRing.detachedCallback.call(this), removeNotificationEvent(this, "RefreshProgress"), this.itemId = null + }, document.registerElement("emby-itemrefreshindicator", { + prototype: EmbyItemRefreshIndicatorPrototype, + extends: "div" + }) +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/emby-itemscontainer/emby-itemscontainer.js b/dashboard-ui/bower_components/emby-webcomponents/emby-itemscontainer/emby-itemscontainer.js index d70bc69e96..b33c3f4509 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/emby-itemscontainer/emby-itemscontainer.js +++ b/dashboard-ui/bower_components/emby-webcomponents/emby-itemscontainer/emby-itemscontainer.js @@ -1 +1,220 @@ -define(["itemShortcuts","inputManager","connectionManager","playbackManager","imageLoader","layoutManager","browser","dom","loading","focusManager","serverNotifications","events","registerElement"],function(itemShortcuts,inputManager,connectionManager,playbackManager,imageLoader,layoutManager,browser,dom,loading,focusManager,serverNotifications,events){"use strict";function onClick(e){var itemsContainer=this,multiSelect=(e.target,itemsContainer.multiSelect);multiSelect&&!1===multiSelect.onContainerClick.call(itemsContainer,e)||itemShortcuts.onClick.call(itemsContainer,e)}function disableEvent(e){return e.preventDefault(),e.stopPropagation(),!1}function onContextMenu(e){var target=e.target,card=dom.parentWithAttribute(target,"data-id");if(card&&card.getAttribute("data-serverid"))return inputManager.trigger("menu",{sourceElement:card}),e.preventDefault(),e.stopPropagation(),!1}function getShortcutOptions(){return{click:!1}}function onDrop(evt,itemsContainer){var el=evt.item,newIndex=evt.newIndex,itemId=el.getAttribute("data-playlistitemid"),playlistId=el.getAttribute("data-playlistid");if(!playlistId){var oldIndex=evt.oldIndex;return void el.dispatchEvent(new CustomEvent("itemdrop",{detail:{oldIndex:oldIndex,newIndex:newIndex,playlistItemId:itemId},bubbles:!0,cancelable:!1}))}var serverId=el.getAttribute("data-serverid"),apiClient=connectionManager.getApiClient(serverId);loading.show(),apiClient.ajax({url:apiClient.getUrl("Playlists/"+playlistId+"/Items/"+itemId+"/Move/"+newIndex),type:"POST"}).then(function(){loading.hide()},function(){loading.hide(),itemsContainer.refreshItems()})}function onUserDataChanged(e,apiClient,userData){var itemsContainer=this;require(["cardBuilder"],function(cardBuilder){cardBuilder.onUserDataChanged(userData,itemsContainer)});var eventsToMonitor=getEventsToMonitor(itemsContainer);-1!==eventsToMonitor.indexOf("markfavorite")?itemsContainer.notifyRefreshNeeded():-1!==eventsToMonitor.indexOf("markplayed")&&itemsContainer.notifyRefreshNeeded()}function getEventsToMonitor(itemsContainer){var monitor=itemsContainer.getAttribute("data-monitor");return monitor?monitor.split(","):[]}function onTimerCreated(e,apiClient,data){var itemsContainer=this;if(-1!==getEventsToMonitor(itemsContainer).indexOf("timers"))return void itemsContainer.notifyRefreshNeeded();var programId=data.ProgramId,newTimerId=data.Id;require(["cardBuilder"],function(cardBuilder){cardBuilder.onTimerCreated(programId,newTimerId,itemsContainer)})}function onSeriesTimerCreated(e,apiClient,data){var itemsContainer=this;if(-1!==getEventsToMonitor(itemsContainer).indexOf("seriestimers"))return void itemsContainer.notifyRefreshNeeded()}function onTimerCancelled(e,apiClient,data){var itemsContainer=this;if(-1!==getEventsToMonitor(itemsContainer).indexOf("timers"))return void itemsContainer.notifyRefreshNeeded();var id=data.Id;require(["cardBuilder"],function(cardBuilder){cardBuilder.onTimerCancelled(id,itemsContainer)})}function onSeriesTimerCancelled(e,apiClient,data){var itemsContainer=this;if(-1!==getEventsToMonitor(itemsContainer).indexOf("seriestimers"))return void itemsContainer.notifyRefreshNeeded();var id=data.Id;require(["cardBuilder"],function(cardBuilder){cardBuilder.onSeriesTimerCancelled(id,itemsContainer)})}function onLibraryChanged(e,apiClient,data){var itemsContainer=this,eventsToMonitor=getEventsToMonitor(itemsContainer);if(-1===eventsToMonitor.indexOf("seriestimers")&&-1===eventsToMonitor.indexOf("timers")){var itemsAdded=data.ItemsAdded||[],itemsRemoved=data.ItemsRemoved||[];if(itemsAdded.length||itemsRemoved.length){var parentId=itemsContainer.getAttribute("data-parentid");if(parentId){var foldersAddedTo=data.FoldersAddedTo||[],foldersRemovedFrom=data.FoldersRemovedFrom||[],collectionFolders=data.CollectionFolders||[];if(-1===foldersAddedTo.indexOf(parentId)&&-1===foldersRemovedFrom.indexOf(parentId)&&-1===collectionFolders.indexOf(parentId))return}itemsContainer.notifyRefreshNeeded()}}}function onPlaybackStopped(e,stopInfo){var itemsContainer=this,state=stopInfo.state,eventsToMonitor=getEventsToMonitor(itemsContainer);if(state.NowPlayingItem&&"Video"===state.NowPlayingItem.MediaType){if(-1!==eventsToMonitor.indexOf("videoplayback"))return void itemsContainer.notifyRefreshNeeded(!0)}else if(state.NowPlayingItem&&"Audio"===state.NowPlayingItem.MediaType&&-1!==eventsToMonitor.indexOf("audioplayback"))return void itemsContainer.notifyRefreshNeeded(!0)}function addNotificationEvent(instance,name,handler,owner){var localHandler=handler.bind(instance);owner=owner||serverNotifications,events.on(owner,name,localHandler),instance["event_"+name]=localHandler}function removeNotificationEvent(instance,name,owner){var handler=instance["event_"+name];handler&&(owner=owner||serverNotifications,events.off(owner,name,handler),instance["event_"+name]=null)}function clearRefreshInterval(itemsContainer,isPausing){itemsContainer.refreshInterval&&(clearInterval(itemsContainer.refreshInterval),itemsContainer.refreshInterval=null,isPausing||(itemsContainer.refreshIntervalEndTime=null))}function resetRefreshInterval(itemsContainer,intervalMs){clearRefreshInterval(itemsContainer),intervalMs||(intervalMs=parseInt(itemsContainer.getAttribute("data-refreshinterval")||"0")),intervalMs&&(itemsContainer.refreshInterval=setInterval(itemsContainer.notifyRefreshNeeded.bind(itemsContainer),intervalMs),itemsContainer.refreshIntervalEndTime=(new Date).getTime()+intervalMs)}function onDataFetched(result){var items=result.Items||result,parentContainer=this.parentContainer;parentContainer&&(items.length?parentContainer.classList.remove("hide"):parentContainer.classList.add("hide"));var focusId,hasActiveElement,activeElement=document.activeElement;this.contains(activeElement)&&(hasActiveElement=!0,focusId=activeElement.getAttribute("data-id")),this.innerHTML=this.getItemsHtml(items),imageLoader.lazyChildren(this),hasActiveElement&&setFocus(this,focusId),resetRefreshInterval(this),this.afterRefresh&&this.afterRefresh(result)}function setFocus(itemsContainer,focusId){if(focusId){var newElement=itemsContainer.querySelector('[data-id="'+focusId+'"]');if(newElement)try{return void focusManager.focus(newElement)}catch(err){}}focusManager.autoFocus(itemsContainer)}var ItemsContainerProtoType=Object.create(HTMLDivElement.prototype);ItemsContainerProtoType.enableMultiSelect=function(enabled){var current=this.multiSelect;if(!enabled)return void(current&&(current.destroy(),this.multiSelect=null));if(!current){var self=this;require(["multiSelect"],function(MultiSelect){self.multiSelect=new MultiSelect({container:self,bindOnClick:!1})})}},ItemsContainerProtoType.enableDragReordering=function(enabled){var current=this.sortable;if(!enabled)return void(current&&(current.destroy(),this.sortable=null));if(!current){var self=this;require(["sortable"],function(Sortable){self.sortable=new Sortable(self,{draggable:".listItem",handle:".listViewDragHandle",onEnd:function(evt){return onDrop(evt,self)}})})}},ItemsContainerProtoType.createdCallback=function(){this.classList.add("itemsContainer")},ItemsContainerProtoType.attachedCallback=function(){this.addEventListener("click",onClick),browser.touch?this.addEventListener("contextmenu",disableEvent):"false"!==this.getAttribute("data-contextmenu")&&this.addEventListener("contextmenu",onContextMenu),(layoutManager.desktop||layoutManager.mobile)&&"false"!==this.getAttribute("data-multiselect")&&this.enableMultiSelect(!0),layoutManager.tv&&this.classList.add("itemsContainer-tv"),itemShortcuts.on(this,getShortcutOptions()),addNotificationEvent(this,"UserDataChanged",onUserDataChanged),addNotificationEvent(this,"TimerCreated",onTimerCreated),addNotificationEvent(this,"SeriesTimerCreated",onSeriesTimerCreated),addNotificationEvent(this,"TimerCancelled",onTimerCancelled),addNotificationEvent(this,"SeriesTimerCancelled",onSeriesTimerCancelled),addNotificationEvent(this,"LibraryChanged",onLibraryChanged),addNotificationEvent(this,"playbackstop",onPlaybackStopped,playbackManager),"true"===this.getAttribute("data-dragreorder")&&this.enableDragReordering(!0)},ItemsContainerProtoType.detachedCallback=function(){clearRefreshInterval(this),this.enableMultiSelect(!1),this.enableDragReordering(!1),this.removeEventListener("click",onClick),this.removeEventListener("contextmenu",onContextMenu),this.removeEventListener("contextmenu",disableEvent),itemShortcuts.off(this,getShortcutOptions()),removeNotificationEvent(this,"UserDataChanged"),removeNotificationEvent(this,"TimerCreated"),removeNotificationEvent(this,"SeriesTimerCreated"),removeNotificationEvent(this,"TimerCancelled"),removeNotificationEvent(this,"SeriesTimerCancelled"),removeNotificationEvent(this,"LibraryChanged"),removeNotificationEvent(this,"playbackstop",playbackManager),this.fetchData=null,this.getItemsHtml=null,this.parentContainer=null},ItemsContainerProtoType.pause=function(){clearRefreshInterval(this,!0),this.paused=!0},ItemsContainerProtoType.resume=function(options){this.paused=!1;var refreshIntervalEndTime=this.refreshIntervalEndTime;if(refreshIntervalEndTime){var remainingMs=refreshIntervalEndTime-(new Date).getTime();remainingMs>0&&!this.needsRefresh?resetRefreshInterval(this,remainingMs):(this.needsRefresh=!0,this.refreshIntervalEndTime=null)}return this.needsRefresh||options&&options.refresh?this.refreshItems():Promise.resolve()},ItemsContainerProtoType.refreshItems=function(){return this.fetchData?this.paused?(this.needsRefresh=!0,Promise.resolve()):(this.needsRefresh=!1,this.fetchData().then(onDataFetched.bind(this))):Promise.resolve()},ItemsContainerProtoType.notifyRefreshNeeded=function(isInForeground){if(this.paused)return void(this.needsRefresh=!0);var timeout=this.refreshTimeout;timeout&&clearTimeout(timeout),!0===isInForeground?this.refreshItems():this.refreshTimeout=setTimeout(this.refreshItems.bind(this),1e4)},document.registerElement("emby-itemscontainer",{prototype:ItemsContainerProtoType,extends:"div"})}); \ No newline at end of file +define(["itemShortcuts", "inputManager", "connectionManager", "playbackManager", "imageLoader", "layoutManager", "browser", "dom", "loading", "focusManager", "serverNotifications", "events", "registerElement"], function(itemShortcuts, inputManager, connectionManager, playbackManager, imageLoader, layoutManager, browser, dom, loading, focusManager, serverNotifications, events) { + "use strict"; + + function onClick(e) { + var itemsContainer = this, + multiSelect = (e.target, itemsContainer.multiSelect); + multiSelect && !1 === multiSelect.onContainerClick.call(itemsContainer, e) || itemShortcuts.onClick.call(itemsContainer, e) + } + + function disableEvent(e) { + return e.preventDefault(), e.stopPropagation(), !1 + } + + function onContextMenu(e) { + var target = e.target, + card = dom.parentWithAttribute(target, "data-id"); + if (card && card.getAttribute("data-serverid")) return inputManager.trigger("menu", { + sourceElement: card + }), e.preventDefault(), e.stopPropagation(), !1 + } + + function getShortcutOptions() { + return { + click: !1 + } + } + + function onDrop(evt, itemsContainer) { + var el = evt.item, + newIndex = evt.newIndex, + itemId = el.getAttribute("data-playlistitemid"), + playlistId = el.getAttribute("data-playlistid"); + if (!playlistId) { + var oldIndex = evt.oldIndex; + return void el.dispatchEvent(new CustomEvent("itemdrop", { + detail: { + oldIndex: oldIndex, + newIndex: newIndex, + playlistItemId: itemId + }, + bubbles: !0, + cancelable: !1 + })) + } + var serverId = el.getAttribute("data-serverid"), + apiClient = connectionManager.getApiClient(serverId); + loading.show(), apiClient.ajax({ + url: apiClient.getUrl("Playlists/" + playlistId + "/Items/" + itemId + "/Move/" + newIndex), + type: "POST" + }).then(function() { + loading.hide() + }, function() { + loading.hide(), itemsContainer.refreshItems() + }) + } + + function onUserDataChanged(e, apiClient, userData) { + var itemsContainer = this; + require(["cardBuilder"], function(cardBuilder) { + cardBuilder.onUserDataChanged(userData, itemsContainer) + }); + var eventsToMonitor = getEventsToMonitor(itemsContainer); - 1 !== eventsToMonitor.indexOf("markfavorite") ? itemsContainer.notifyRefreshNeeded() : -1 !== eventsToMonitor.indexOf("markplayed") && itemsContainer.notifyRefreshNeeded() + } + + function getEventsToMonitor(itemsContainer) { + var monitor = itemsContainer.getAttribute("data-monitor"); + return monitor ? monitor.split(",") : [] + } + + function onTimerCreated(e, apiClient, data) { + var itemsContainer = this; + if (-1 !== getEventsToMonitor(itemsContainer).indexOf("timers")) return void itemsContainer.notifyRefreshNeeded(); + var programId = data.ProgramId, + newTimerId = data.Id; + require(["cardBuilder"], function(cardBuilder) { + cardBuilder.onTimerCreated(programId, newTimerId, itemsContainer) + }) + } + + function onSeriesTimerCreated(e, apiClient, data) { + var itemsContainer = this; + if (-1 !== getEventsToMonitor(itemsContainer).indexOf("seriestimers")) return void itemsContainer.notifyRefreshNeeded() + } + + function onTimerCancelled(e, apiClient, data) { + var itemsContainer = this; + if (-1 !== getEventsToMonitor(itemsContainer).indexOf("timers")) return void itemsContainer.notifyRefreshNeeded(); + var id = data.Id; + require(["cardBuilder"], function(cardBuilder) { + cardBuilder.onTimerCancelled(id, itemsContainer) + }) + } + + function onSeriesTimerCancelled(e, apiClient, data) { + var itemsContainer = this; + if (-1 !== getEventsToMonitor(itemsContainer).indexOf("seriestimers")) return void itemsContainer.notifyRefreshNeeded(); + var id = data.Id; + require(["cardBuilder"], function(cardBuilder) { + cardBuilder.onSeriesTimerCancelled(id, itemsContainer) + }) + } + + function onLibraryChanged(e, apiClient, data) { + var itemsContainer = this, + eventsToMonitor = getEventsToMonitor(itemsContainer); + if (-1 === eventsToMonitor.indexOf("seriestimers") && -1 === eventsToMonitor.indexOf("timers")) { + var itemsAdded = data.ItemsAdded || [], + itemsRemoved = data.ItemsRemoved || []; + if (itemsAdded.length || itemsRemoved.length) { + var parentId = itemsContainer.getAttribute("data-parentid"); + if (parentId) { + var foldersAddedTo = data.FoldersAddedTo || [], + foldersRemovedFrom = data.FoldersRemovedFrom || [], + collectionFolders = data.CollectionFolders || []; + if (-1 === foldersAddedTo.indexOf(parentId) && -1 === foldersRemovedFrom.indexOf(parentId) && -1 === collectionFolders.indexOf(parentId)) return + } + itemsContainer.notifyRefreshNeeded() + } + } + } + + function onPlaybackStopped(e, stopInfo) { + var itemsContainer = this, + state = stopInfo.state, + eventsToMonitor = getEventsToMonitor(itemsContainer); + if (state.NowPlayingItem && "Video" === state.NowPlayingItem.MediaType) { + if (-1 !== eventsToMonitor.indexOf("videoplayback")) return void itemsContainer.notifyRefreshNeeded(!0) + } else if (state.NowPlayingItem && "Audio" === state.NowPlayingItem.MediaType && -1 !== eventsToMonitor.indexOf("audioplayback")) return void itemsContainer.notifyRefreshNeeded(!0) + } + + function addNotificationEvent(instance, name, handler, owner) { + var localHandler = handler.bind(instance); + owner = owner || serverNotifications, events.on(owner, name, localHandler), instance["event_" + name] = localHandler + } + + function removeNotificationEvent(instance, name, owner) { + var handler = instance["event_" + name]; + handler && (owner = owner || serverNotifications, events.off(owner, name, handler), instance["event_" + name] = null) + } + + function clearRefreshInterval(itemsContainer, isPausing) { + itemsContainer.refreshInterval && (clearInterval(itemsContainer.refreshInterval), itemsContainer.refreshInterval = null, isPausing || (itemsContainer.refreshIntervalEndTime = null)) + } + + function resetRefreshInterval(itemsContainer, intervalMs) { + clearRefreshInterval(itemsContainer), intervalMs || (intervalMs = parseInt(itemsContainer.getAttribute("data-refreshinterval") || "0")), intervalMs && (itemsContainer.refreshInterval = setInterval(itemsContainer.notifyRefreshNeeded.bind(itemsContainer), intervalMs), itemsContainer.refreshIntervalEndTime = (new Date).getTime() + intervalMs) + } + + function onDataFetched(result) { + var items = result.Items || result, + parentContainer = this.parentContainer; + parentContainer && (items.length ? parentContainer.classList.remove("hide") : parentContainer.classList.add("hide")); + var focusId, hasActiveElement, activeElement = document.activeElement; + this.contains(activeElement) && (hasActiveElement = !0, focusId = activeElement.getAttribute("data-id")), this.innerHTML = this.getItemsHtml(items), imageLoader.lazyChildren(this), hasActiveElement && setFocus(this, focusId), resetRefreshInterval(this), this.afterRefresh && this.afterRefresh(result) + } + + function setFocus(itemsContainer, focusId) { + if (focusId) { + var newElement = itemsContainer.querySelector('[data-id="' + focusId + '"]'); + if (newElement) try { + return void focusManager.focus(newElement) + } catch (err) {} + } + focusManager.autoFocus(itemsContainer) + } + var ItemsContainerProtoType = Object.create(HTMLDivElement.prototype); + ItemsContainerProtoType.enableMultiSelect = function(enabled) { + var current = this.multiSelect; + if (!enabled) return void(current && (current.destroy(), this.multiSelect = null)); + if (!current) { + var self = this; + require(["multiSelect"], function(MultiSelect) { + self.multiSelect = new MultiSelect({ + container: self, + bindOnClick: !1 + }) + }) + } + }, ItemsContainerProtoType.enableDragReordering = function(enabled) { + var current = this.sortable; + if (!enabled) return void(current && (current.destroy(), this.sortable = null)); + if (!current) { + var self = this; + require(["sortable"], function(Sortable) { + self.sortable = new Sortable(self, { + draggable: ".listItem", + handle: ".listViewDragHandle", + onEnd: function(evt) { + return onDrop(evt, self) + } + }) + }) + } + }, ItemsContainerProtoType.createdCallback = function() { + this.classList.add("itemsContainer") + }, ItemsContainerProtoType.attachedCallback = function() { + this.addEventListener("click", onClick), browser.touch ? this.addEventListener("contextmenu", disableEvent) : "false" !== this.getAttribute("data-contextmenu") && this.addEventListener("contextmenu", onContextMenu), (layoutManager.desktop || layoutManager.mobile) && "false" !== this.getAttribute("data-multiselect") && this.enableMultiSelect(!0), layoutManager.tv && this.classList.add("itemsContainer-tv"), itemShortcuts.on(this, getShortcutOptions()), addNotificationEvent(this, "UserDataChanged", onUserDataChanged), addNotificationEvent(this, "TimerCreated", onTimerCreated), addNotificationEvent(this, "SeriesTimerCreated", onSeriesTimerCreated), addNotificationEvent(this, "TimerCancelled", onTimerCancelled), addNotificationEvent(this, "SeriesTimerCancelled", onSeriesTimerCancelled), addNotificationEvent(this, "LibraryChanged", onLibraryChanged), addNotificationEvent(this, "playbackstop", onPlaybackStopped, playbackManager), "true" === this.getAttribute("data-dragreorder") && this.enableDragReordering(!0) + }, ItemsContainerProtoType.detachedCallback = function() { + clearRefreshInterval(this), this.enableMultiSelect(!1), this.enableDragReordering(!1), this.removeEventListener("click", onClick), this.removeEventListener("contextmenu", onContextMenu), this.removeEventListener("contextmenu", disableEvent), itemShortcuts.off(this, getShortcutOptions()), removeNotificationEvent(this, "UserDataChanged"), removeNotificationEvent(this, "TimerCreated"), removeNotificationEvent(this, "SeriesTimerCreated"), removeNotificationEvent(this, "TimerCancelled"), removeNotificationEvent(this, "SeriesTimerCancelled"), removeNotificationEvent(this, "LibraryChanged"), removeNotificationEvent(this, "playbackstop", playbackManager), this.fetchData = null, this.getItemsHtml = null, this.parentContainer = null + }, ItemsContainerProtoType.pause = function() { + clearRefreshInterval(this, !0), this.paused = !0 + }, ItemsContainerProtoType.resume = function(options) { + this.paused = !1; + var refreshIntervalEndTime = this.refreshIntervalEndTime; + if (refreshIntervalEndTime) { + var remainingMs = refreshIntervalEndTime - (new Date).getTime(); + remainingMs > 0 && !this.needsRefresh ? resetRefreshInterval(this, remainingMs) : (this.needsRefresh = !0, this.refreshIntervalEndTime = null) + } + return this.needsRefresh || options && options.refresh ? this.refreshItems() : Promise.resolve() + }, ItemsContainerProtoType.refreshItems = function() { + return this.fetchData ? this.paused ? (this.needsRefresh = !0, Promise.resolve()) : (this.needsRefresh = !1, this.fetchData().then(onDataFetched.bind(this))) : Promise.resolve() + }, ItemsContainerProtoType.notifyRefreshNeeded = function(isInForeground) { + if (this.paused) return void(this.needsRefresh = !0); + var timeout = this.refreshTimeout; + timeout && clearTimeout(timeout), !0 === isInForeground ? this.refreshItems() : this.refreshTimeout = setTimeout(this.refreshItems.bind(this), 1e4) + }, document.registerElement("emby-itemscontainer", { + prototype: ItemsContainerProtoType, + extends: "div" + }) +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/emby-progressring/emby-progressring.js b/dashboard-ui/bower_components/emby-webcomponents/emby-progressring/emby-progressring.js index 1db2139085..c5358f32e2 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/emby-progressring/emby-progressring.js +++ b/dashboard-ui/bower_components/emby-webcomponents/emby-progressring/emby-progressring.js @@ -1 +1,21 @@ -define(["require","css!./emby-progressring","registerElement"],function(require){"use strict";var EmbyProgressRing=Object.create(HTMLDivElement.prototype);return EmbyProgressRing.createdCallback=function(){this.classList.add("progressring");var instance=this;require(["text!./emby-progressring.template.html"],function(template){instance.innerHTML=template,instance.setProgress(parseFloat(instance.getAttribute("data-progress")||"0"))})},EmbyProgressRing.setProgress=function(progress){progress=Math.floor(progress);var angle;progress<25?(angle=progress/100*360-90,this.querySelector(".animate-0-25-b").style.transform="rotate("+angle+"deg)",this.querySelector(".animate-25-50-b").style.transform="rotate(-90deg)",this.querySelector(".animate-50-75-b").style.transform="rotate(-90deg)",this.querySelector(".animate-75-100-b").style.transform="rotate(-90deg)"):progress>=25&&progress<50?(angle=(progress-25)/100*360-90,this.querySelector(".animate-0-25-b").style.transform="none",this.querySelector(".animate-25-50-b").style.transform="rotate("+angle+"deg)",this.querySelector(".animate-50-75-b").style.transform="rotate(-90deg)",this.querySelector(".animate-75-100-b").style.transform="rotate(-90deg)"):progress>=50&&progress<75?(angle=(progress-50)/100*360-90,this.querySelector(".animate-0-25-b").style.transform="none",this.querySelector(".animate-25-50-b").style.transform="none",this.querySelector(".animate-50-75-b").style.transform="rotate("+angle+"deg)",this.querySelector(".animate-75-100-b").style.transform="rotate(-90deg)"):progress>=75&&progress<=100&&(angle=(progress-75)/100*360-90,this.querySelector(".animate-0-25-b").style.transform="none",this.querySelector(".animate-25-50-b").style.transform="none",this.querySelector(".animate-50-75-b").style.transform="none",this.querySelector(".animate-75-100-b").style.transform="rotate("+angle+"deg)"),this.querySelector(".progressring-text").innerHTML=progress+"%"},EmbyProgressRing.attachedCallback=function(){},EmbyProgressRing.detachedCallback=function(){var observer=this.observer;observer&&(observer.disconnect(),this.observer=null)},document.registerElement("emby-progressring",{prototype:EmbyProgressRing,extends:"div"}),EmbyProgressRing}); \ No newline at end of file +define(["require", "css!./emby-progressring", "registerElement"], function(require) { + "use strict"; + var EmbyProgressRing = Object.create(HTMLDivElement.prototype); + return EmbyProgressRing.createdCallback = function() { + this.classList.add("progressring"); + var instance = this; + require(["text!./emby-progressring.template.html"], function(template) { + instance.innerHTML = template, instance.setProgress(parseFloat(instance.getAttribute("data-progress") || "0")) + }) + }, EmbyProgressRing.setProgress = function(progress) { + progress = Math.floor(progress); + var angle; + progress < 25 ? (angle = progress / 100 * 360 - 90, this.querySelector(".animate-0-25-b").style.transform = "rotate(" + angle + "deg)", this.querySelector(".animate-25-50-b").style.transform = "rotate(-90deg)", this.querySelector(".animate-50-75-b").style.transform = "rotate(-90deg)", this.querySelector(".animate-75-100-b").style.transform = "rotate(-90deg)") : progress >= 25 && progress < 50 ? (angle = (progress - 25) / 100 * 360 - 90, this.querySelector(".animate-0-25-b").style.transform = "none", this.querySelector(".animate-25-50-b").style.transform = "rotate(" + angle + "deg)", this.querySelector(".animate-50-75-b").style.transform = "rotate(-90deg)", this.querySelector(".animate-75-100-b").style.transform = "rotate(-90deg)") : progress >= 50 && progress < 75 ? (angle = (progress - 50) / 100 * 360 - 90, this.querySelector(".animate-0-25-b").style.transform = "none", this.querySelector(".animate-25-50-b").style.transform = "none", this.querySelector(".animate-50-75-b").style.transform = "rotate(" + angle + "deg)", this.querySelector(".animate-75-100-b").style.transform = "rotate(-90deg)") : progress >= 75 && progress <= 100 && (angle = (progress - 75) / 100 * 360 - 90, this.querySelector(".animate-0-25-b").style.transform = "none", this.querySelector(".animate-25-50-b").style.transform = "none", this.querySelector(".animate-50-75-b").style.transform = "none", this.querySelector(".animate-75-100-b").style.transform = "rotate(" + angle + "deg)"), this.querySelector(".progressring-text").innerHTML = progress + "%" + }, EmbyProgressRing.attachedCallback = function() {}, EmbyProgressRing.detachedCallback = function() { + var observer = this.observer; + observer && (observer.disconnect(), this.observer = null) + }, document.registerElement("emby-progressring", { + prototype: EmbyProgressRing, + extends: "div" + }), EmbyProgressRing +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/emby-radio/emby-radio.js b/dashboard-ui/bower_components/emby-webcomponents/emby-radio/emby-radio.js index 70635c5431..a41b3ed06d 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/emby-radio/emby-radio.js +++ b/dashboard-ui/bower_components/emby-webcomponents/emby-radio/emby-radio.js @@ -1 +1,20 @@ -define(["css!./emby-radio","registerElement"],function(){"use strict";function onKeyDown(e){if(13===e.keyCode)return e.preventDefault(),this.checked=!0,!1}var EmbyRadioPrototype=Object.create(HTMLInputElement.prototype);EmbyRadioPrototype.attachedCallback=function(){if("true"!==this.getAttribute("data-radio")){this.setAttribute("data-radio","true"),this.classList.add("mdl-radio__button");var labelElement=this.parentNode;labelElement.classList.add("mdl-radio"),labelElement.classList.add("mdl-js-radio"),labelElement.classList.add("mdl-js-ripple-effect");var labelTextElement=labelElement.querySelector("span");labelTextElement.classList.add("radioButtonLabel"),labelTextElement.classList.add("mdl-radio__label"),labelElement.insertAdjacentHTML("beforeend",''),this.addEventListener("keydown",onKeyDown)}},document.registerElement("emby-radio",{prototype:EmbyRadioPrototype,extends:"input"})}); \ No newline at end of file +define(["css!./emby-radio", "registerElement"], function() { + "use strict"; + + function onKeyDown(e) { + if (13 === e.keyCode) return e.preventDefault(), this.checked = !0, !1 + } + var EmbyRadioPrototype = Object.create(HTMLInputElement.prototype); + EmbyRadioPrototype.attachedCallback = function() { + if ("true" !== this.getAttribute("data-radio")) { + this.setAttribute("data-radio", "true"), this.classList.add("mdl-radio__button"); + var labelElement = this.parentNode; + labelElement.classList.add("mdl-radio"), labelElement.classList.add("mdl-js-radio"), labelElement.classList.add("mdl-js-ripple-effect"); + var labelTextElement = labelElement.querySelector("span"); + labelTextElement.classList.add("radioButtonLabel"), labelTextElement.classList.add("mdl-radio__label"), labelElement.insertAdjacentHTML("beforeend", ''), this.addEventListener("keydown", onKeyDown) + } + }, document.registerElement("emby-radio", { + prototype: EmbyRadioPrototype, + extends: "input" + }) +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/emby-scrollbuttons/emby-scrollbuttons.js b/dashboard-ui/bower_components/emby-webcomponents/emby-scrollbuttons/emby-scrollbuttons.js index 2fabc5df06..fc9c7be825 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/emby-scrollbuttons/emby-scrollbuttons.js +++ b/dashboard-ui/bower_components/emby-webcomponents/emby-scrollbuttons/emby-scrollbuttons.js @@ -1 +1,75 @@ -define(["layoutManager","dom","css!./emby-scrollbuttons","registerElement","paper-icon-button-light"],function(layoutManager,dom){"use strict";function getScrollButtonContainerHtml(direction){var html="";html+='
';var icon="left"===direction?"":"";return html+='",html+="
"}function getScrollPosition(parent){return parent.getScrollPosition?parent.getScrollPosition():0}function getScrollWidth(parent){return parent.getScrollSize?parent.getScrollSize():0}function onScrolledToPosition(scrollButtons,pos,scrollWidth){pos>0?scrollButtons.scrollButtonsLeft.classList.remove("hide"):scrollButtons.scrollButtonsLeft.classList.add("hide"),scrollWidth>0&&(pos+=scrollButtons.offsetWidth,pos>=scrollWidth?scrollButtons.scrollButtonsRight.classList.add("hide"):scrollButtons.scrollButtonsRight.classList.remove("hide"))}function onScroll(e){var scrollButtons=this,scroller=this.scroller;onScrolledToPosition(scrollButtons,getScrollPosition(scroller),getScrollWidth(scroller))}function getStyleValue(style,name){var value=style.getPropertyValue(name);return value&&(value=value.replace("px",""))?(value=parseInt(value),isNaN(value)?0:value):0}function getScrollSize(elem){var scrollSize=elem.offsetWidth,style=window.getComputedStyle(elem,null),paddingLeft=getStyleValue(style,"padding-left");paddingLeft&&(scrollSize-=paddingLeft);var paddingRight=getStyleValue(style,"padding-right");paddingRight&&(scrollSize-=paddingRight);var slider=elem.getScrollSlider();return style=window.getComputedStyle(slider,null),paddingLeft=getStyleValue(style,"padding-left"),paddingLeft&&(scrollSize-=paddingLeft),paddingRight=getStyleValue(style,"padding-right"),paddingRight&&(scrollSize-=paddingRight),scrollSize}function onScrollButtonClick(e){var newPos,parent=dom.parentWithAttribute(this,"is","emby-scroller"),direction=this.getAttribute("data-direction"),scrollSize=getScrollSize(parent),pos=getScrollPosition(parent);newPos="left"===direction?Math.max(0,pos-scrollSize):pos+scrollSize,parent.scrollToPosition(newPos,!1)}var EmbyScrollButtonsPrototype=Object.create(HTMLDivElement.prototype);EmbyScrollButtonsPrototype.createdCallback=function(){},EmbyScrollButtonsPrototype.attachedCallback=function(){var parent=dom.parentWithAttribute(this,"is","emby-scroller");this.scroller=parent,parent.classList.add("emby-scrollbuttons-scroller"),this.innerHTML=getScrollButtonContainerHtml("left")+getScrollButtonContainerHtml("right");var scrollHandler=onScroll.bind(this);this.scrollHandler=scrollHandler;var buttons=this.querySelectorAll(".emby-scrollbuttons-scrollbutton");buttons[0].addEventListener("click",onScrollButtonClick),buttons[1].addEventListener("click",onScrollButtonClick),buttons=this.querySelectorAll(".scrollbuttoncontainer"),this.scrollButtonsLeft=buttons[0],this.scrollButtonsRight=buttons[1],parent.addScrollEventListener(scrollHandler,{capture:!1,passive:!0})},EmbyScrollButtonsPrototype.detachedCallback=function(){var parent=this.scroller;this.scroller=null;var scrollHandler=this.scrollHandler;parent&&scrollHandler&&parent.removeScrollEventListener(scrollHandler,{capture:!1,passive:!0}),this.scrollHandler=null,this.scrollButtonsLeft=null,this.scrollButtonsRight=null},document.registerElement("emby-scrollbuttons",{prototype:EmbyScrollButtonsPrototype,extends:"div"})}); \ No newline at end of file +define(["layoutManager", "dom", "css!./emby-scrollbuttons", "registerElement", "paper-icon-button-light"], function(layoutManager, dom) { + "use strict"; + + function getScrollButtonContainerHtml(direction) { + var html = ""; + html += '
'; + var icon = "left" === direction ? "" : ""; + return html += '", html += "
" + } + + function getScrollPosition(parent) { + return parent.getScrollPosition ? parent.getScrollPosition() : 0 + } + + function getScrollWidth(parent) { + return parent.getScrollSize ? parent.getScrollSize() : 0 + } + + function onScrolledToPosition(scrollButtons, pos, scrollWidth) { + pos > 0 ? scrollButtons.scrollButtonsLeft.classList.remove("hide") : scrollButtons.scrollButtonsLeft.classList.add("hide"), scrollWidth > 0 && (pos += scrollButtons.offsetWidth, pos >= scrollWidth ? scrollButtons.scrollButtonsRight.classList.add("hide") : scrollButtons.scrollButtonsRight.classList.remove("hide")) + } + + function onScroll(e) { + var scrollButtons = this, + scroller = this.scroller; + onScrolledToPosition(scrollButtons, getScrollPosition(scroller), getScrollWidth(scroller)) + } + + function getStyleValue(style, name) { + var value = style.getPropertyValue(name); + return value && (value = value.replace("px", "")) ? (value = parseInt(value), isNaN(value) ? 0 : value) : 0 + } + + function getScrollSize(elem) { + var scrollSize = elem.offsetWidth, + style = window.getComputedStyle(elem, null), + paddingLeft = getStyleValue(style, "padding-left"); + paddingLeft && (scrollSize -= paddingLeft); + var paddingRight = getStyleValue(style, "padding-right"); + paddingRight && (scrollSize -= paddingRight); + var slider = elem.getScrollSlider(); + return style = window.getComputedStyle(slider, null), paddingLeft = getStyleValue(style, "padding-left"), paddingLeft && (scrollSize -= paddingLeft), paddingRight = getStyleValue(style, "padding-right"), paddingRight && (scrollSize -= paddingRight), scrollSize + } + + function onScrollButtonClick(e) { + var newPos, parent = dom.parentWithAttribute(this, "is", "emby-scroller"), + direction = this.getAttribute("data-direction"), + scrollSize = getScrollSize(parent), + pos = getScrollPosition(parent); + newPos = "left" === direction ? Math.max(0, pos - scrollSize) : pos + scrollSize, parent.scrollToPosition(newPos, !1) + } + var EmbyScrollButtonsPrototype = Object.create(HTMLDivElement.prototype); + EmbyScrollButtonsPrototype.createdCallback = function() {}, EmbyScrollButtonsPrototype.attachedCallback = function() { + var parent = dom.parentWithAttribute(this, "is", "emby-scroller"); + this.scroller = parent, parent.classList.add("emby-scrollbuttons-scroller"), this.innerHTML = getScrollButtonContainerHtml("left") + getScrollButtonContainerHtml("right"); + var scrollHandler = onScroll.bind(this); + this.scrollHandler = scrollHandler; + var buttons = this.querySelectorAll(".emby-scrollbuttons-scrollbutton"); + buttons[0].addEventListener("click", onScrollButtonClick), buttons[1].addEventListener("click", onScrollButtonClick), buttons = this.querySelectorAll(".scrollbuttoncontainer"), this.scrollButtonsLeft = buttons[0], this.scrollButtonsRight = buttons[1], parent.addScrollEventListener(scrollHandler, { + capture: !1, + passive: !0 + }) + }, EmbyScrollButtonsPrototype.detachedCallback = function() { + var parent = this.scroller; + this.scroller = null; + var scrollHandler = this.scrollHandler; + parent && scrollHandler && parent.removeScrollEventListener(scrollHandler, { + capture: !1, + passive: !0 + }), this.scrollHandler = null, this.scrollButtonsLeft = null, this.scrollButtonsRight = null + }, document.registerElement("emby-scrollbuttons", { + prototype: EmbyScrollButtonsPrototype, + extends: "div" + }) +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/emby-scroller/emby-scroller.js b/dashboard-ui/bower_components/emby-webcomponents/emby-scroller/emby-scroller.js index e965c0bd99..d358666f97 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/emby-scroller/emby-scroller.js +++ b/dashboard-ui/bower_components/emby-webcomponents/emby-scroller/emby-scroller.js @@ -1 +1,101 @@ -define(["scroller","dom","layoutManager","inputManager","focusManager","browser","registerElement"],function(scroller,dom,layoutManager,inputManager,focusManager,browser){"use strict";function initCenterFocus(elem,scrollerInstance){dom.addEventListener(elem,"focus",function(e){var focused=focusManager.focusableParent(e.target);focused&&scrollerInstance.toCenter(focused)},{capture:!0,passive:!0})}function onInputCommand(e){var cmd=e.detail.command;"end"===cmd?(focusManager.focusLast(this,"."+this.getAttribute("data-navcommands")),e.preventDefault(),e.stopPropagation()):"pageup"===cmd?(focusManager.moveFocus(e.target,this,"."+this.getAttribute("data-navcommands"),-12),e.preventDefault(),e.stopPropagation()):"pagedown"===cmd&&(focusManager.moveFocus(e.target,this,"."+this.getAttribute("data-navcommands"),12),e.preventDefault(),e.stopPropagation())}function initHeadroom(elem){require(["headroom"],function(Headroom){var headroom=new Headroom([],{scroller:elem});headroom.init(),headroom.add(document.querySelector(".skinHeader")),elem.headroom=headroom})}function loadScrollButtons(scroller){require(["emby-scrollbuttons"],function(){scroller.insertAdjacentHTML("beforeend",'
')})}var ScrollerProtoType=Object.create(HTMLDivElement.prototype);ScrollerProtoType.createdCallback=function(){this.classList.add("emby-scroller")},ScrollerProtoType.scrollToBeginning=function(){this.scroller&&this.scroller.slideTo(0,!0)},ScrollerProtoType.toStart=function(elem,immediate){this.scroller&&this.scroller.toStart(elem,immediate)},ScrollerProtoType.toCenter=function(elem,immediate){this.scroller&&this.scroller.toCenter(elem,immediate)},ScrollerProtoType.scrollToPosition=function(pos,immediate){this.scroller&&this.scroller.slideTo(pos,immediate)},ScrollerProtoType.getScrollPosition=function(){if(this.scroller)return this.scroller.getScrollPosition()},ScrollerProtoType.getScrollSize=function(){if(this.scroller)return this.scroller.getScrollSize()},ScrollerProtoType.getScrollEventName=function(){if(this.scroller)return this.scroller.getScrollEventName()},ScrollerProtoType.getScrollSlider=function(){if(this.scroller)return this.scroller.getScrollSlider()},ScrollerProtoType.addScrollEventListener=function(fn,options){this.scroller&&dom.addEventListener(this.scroller.getScrollFrame(),this.scroller.getScrollEventName(),fn,options)},ScrollerProtoType.removeScrollEventListener=function(fn,options){this.scroller&&dom.removeEventListener(this.scroller.getScrollFrame(),this.scroller.getScrollEventName(),fn,options)},ScrollerProtoType.attachedCallback=function(){this.getAttribute("data-navcommands")&&inputManager.on(this,onInputCommand);var horizontal="false"!==this.getAttribute("data-horizontal"),slider=this.querySelector(".scrollSlider");horizontal&&(slider.style["white-space"]="nowrap");var bindHeader="true"===this.getAttribute("data-bindheader"),scrollFrame=this,enableScrollButtons=layoutManager.desktop&&horizontal&&"false"!==this.getAttribute("data-scrollbuttons"),options={horizontal:horizontal,mouseDragging:1,mouseWheel:"false"!==this.getAttribute("data-mousewheel"),touchDragging:1,slidee:slider,scrollBy:200,speed:horizontal?270:240,elasticBounds:1,dragHandle:1,scrollWidth:"auto"===this.getAttribute("data-scrollsize")?null:5e6,autoImmediate:!0,skipSlideToWhenVisible:"true"===this.getAttribute("data-skipfocuswhenvisible"),dispatchScrollEvent:enableScrollButtons||bindHeader||"true"===this.getAttribute("data-scrollevent"),hideScrollbar:enableScrollButtons||"true"===this.getAttribute("data-hidescrollbar"),allowNativeSmoothScroll:"true"===this.getAttribute("data-allownativesmoothscroll")&&!enableScrollButtons,allowNativeScroll:!enableScrollButtons,forceHideScrollbars:enableScrollButtons,requireAnimation:enableScrollButtons&&browser.edge};this.scroller=new scroller(scrollFrame,options),this.scroller.init(),layoutManager.tv&&this.getAttribute("data-centerfocus")&&initCenterFocus(this,this.scroller),bindHeader&&initHeadroom(this),enableScrollButtons&&loadScrollButtons(this)},ScrollerProtoType.pause=function(){var headroom=this.headroom;headroom&&headroom.pause()},ScrollerProtoType.resume=function(){var headroom=this.headroom;headroom&&headroom.resume()},ScrollerProtoType.detachedCallback=function(){this.getAttribute("data-navcommands")&&inputManager.off(this,onInputCommand);var headroom=this.headroom;headroom&&(headroom.destroy(),this.headroom=null);var scrollerInstance=this.scroller;scrollerInstance&&(scrollerInstance.destroy(),this.scroller=null)},document.registerElement("emby-scroller",{prototype:ScrollerProtoType,extends:"div"})}); \ No newline at end of file +define(["scroller", "dom", "layoutManager", "inputManager", "focusManager", "browser", "registerElement"], function(scroller, dom, layoutManager, inputManager, focusManager, browser) { + "use strict"; + + function initCenterFocus(elem, scrollerInstance) { + dom.addEventListener(elem, "focus", function(e) { + var focused = focusManager.focusableParent(e.target); + focused && scrollerInstance.toCenter(focused) + }, { + capture: !0, + passive: !0 + }) + } + + function onInputCommand(e) { + var cmd = e.detail.command; + "end" === cmd ? (focusManager.focusLast(this, "." + this.getAttribute("data-navcommands")), e.preventDefault(), e.stopPropagation()) : "pageup" === cmd ? (focusManager.moveFocus(e.target, this, "." + this.getAttribute("data-navcommands"), -12), e.preventDefault(), e.stopPropagation()) : "pagedown" === cmd && (focusManager.moveFocus(e.target, this, "." + this.getAttribute("data-navcommands"), 12), e.preventDefault(), e.stopPropagation()) + } + + function initHeadroom(elem) { + require(["headroom"], function(Headroom) { + var headroom = new Headroom([], { + scroller: elem + }); + headroom.init(), headroom.add(document.querySelector(".skinHeader")), elem.headroom = headroom + }) + } + + function loadScrollButtons(scroller) { + require(["emby-scrollbuttons"], function() { + scroller.insertAdjacentHTML("beforeend", '
') + }) + } + var ScrollerProtoType = Object.create(HTMLDivElement.prototype); + ScrollerProtoType.createdCallback = function() { + this.classList.add("emby-scroller") + }, ScrollerProtoType.scrollToBeginning = function() { + this.scroller && this.scroller.slideTo(0, !0) + }, ScrollerProtoType.toStart = function(elem, immediate) { + this.scroller && this.scroller.toStart(elem, immediate) + }, ScrollerProtoType.toCenter = function(elem, immediate) { + this.scroller && this.scroller.toCenter(elem, immediate) + }, ScrollerProtoType.scrollToPosition = function(pos, immediate) { + this.scroller && this.scroller.slideTo(pos, immediate) + }, ScrollerProtoType.getScrollPosition = function() { + if (this.scroller) return this.scroller.getScrollPosition() + }, ScrollerProtoType.getScrollSize = function() { + if (this.scroller) return this.scroller.getScrollSize() + }, ScrollerProtoType.getScrollEventName = function() { + if (this.scroller) return this.scroller.getScrollEventName() + }, ScrollerProtoType.getScrollSlider = function() { + if (this.scroller) return this.scroller.getScrollSlider() + }, ScrollerProtoType.addScrollEventListener = function(fn, options) { + this.scroller && dom.addEventListener(this.scroller.getScrollFrame(), this.scroller.getScrollEventName(), fn, options) + }, ScrollerProtoType.removeScrollEventListener = function(fn, options) { + this.scroller && dom.removeEventListener(this.scroller.getScrollFrame(), this.scroller.getScrollEventName(), fn, options) + }, ScrollerProtoType.attachedCallback = function() { + this.getAttribute("data-navcommands") && inputManager.on(this, onInputCommand); + var horizontal = "false" !== this.getAttribute("data-horizontal"), + slider = this.querySelector(".scrollSlider"); + horizontal && (slider.style["white-space"] = "nowrap"); + var bindHeader = "true" === this.getAttribute("data-bindheader"), + scrollFrame = this, + enableScrollButtons = layoutManager.desktop && horizontal && "false" !== this.getAttribute("data-scrollbuttons"), + options = { + horizontal: horizontal, + mouseDragging: 1, + mouseWheel: "false" !== this.getAttribute("data-mousewheel"), + touchDragging: 1, + slidee: slider, + scrollBy: 200, + speed: horizontal ? 270 : 240, + elasticBounds: 1, + dragHandle: 1, + scrollWidth: "auto" === this.getAttribute("data-scrollsize") ? null : 5e6, + autoImmediate: !0, + skipSlideToWhenVisible: "true" === this.getAttribute("data-skipfocuswhenvisible"), + dispatchScrollEvent: enableScrollButtons || bindHeader || "true" === this.getAttribute("data-scrollevent"), + hideScrollbar: enableScrollButtons || "true" === this.getAttribute("data-hidescrollbar"), + allowNativeSmoothScroll: "true" === this.getAttribute("data-allownativesmoothscroll") && !enableScrollButtons, + allowNativeScroll: !enableScrollButtons, + forceHideScrollbars: enableScrollButtons, + requireAnimation: enableScrollButtons && browser.edge + }; + this.scroller = new scroller(scrollFrame, options), this.scroller.init(), layoutManager.tv && this.getAttribute("data-centerfocus") && initCenterFocus(this, this.scroller), bindHeader && initHeadroom(this), enableScrollButtons && loadScrollButtons(this) + }, ScrollerProtoType.pause = function() { + var headroom = this.headroom; + headroom && headroom.pause() + }, ScrollerProtoType.resume = function() { + var headroom = this.headroom; + headroom && headroom.resume() + }, ScrollerProtoType.detachedCallback = function() { + this.getAttribute("data-navcommands") && inputManager.off(this, onInputCommand); + var headroom = this.headroom; + headroom && (headroom.destroy(), this.headroom = null); + var scrollerInstance = this.scroller; + scrollerInstance && (scrollerInstance.destroy(), this.scroller = null) + }, document.registerElement("emby-scroller", { + prototype: ScrollerProtoType, + extends: "div" + }) +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/emby-select/emby-select.js b/dashboard-ui/bower_components/emby-webcomponents/emby-select/emby-select.js index 1da83c4f91..25e646fcdb 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/emby-select/emby-select.js +++ b/dashboard-ui/bower_components/emby-webcomponents/emby-select/emby-select.js @@ -1 +1,75 @@ -define(["layoutManager","browser","actionsheet","css!./emby-select","registerElement"],function(layoutManager,browser,actionsheet){"use strict";function enableNativeMenu(){return!(!browser.edgeUwp&&!browser.xboxOne)||!(browser.tizen||browser.orsay||browser.web0s)&&(!!browser.tv||!layoutManager.tv)}function triggerChange(select){var evt=document.createEvent("HTMLEvents");evt.initEvent("change",!1,!0),select.dispatchEvent(evt)}function setValue(select,value){select.value=value}function showActionSheet(select){var labelElem=getLabel(select),title=labelElem?labelElem.textContent||labelElem.innerText:null;actionsheet.show({items:select.options,positionTo:select,title:title}).then(function(value){setValue(select,value),triggerChange(select)})}function getLabel(select){for(var elem=select.previousSibling;elem&&"LABEL"!==elem.tagName;)elem=elem.previousSibling;return elem}function onFocus(e){var label=getLabel(this);label&&label.classList.add("selectLabelFocused")}function onBlur(e){var label=getLabel(this);label&&label.classList.remove("selectLabelFocused")}function onMouseDown(e){e.button||enableNativeMenu()||(e.preventDefault(),showActionSheet(this))}function onKeyDown(e){switch(e.keyCode){case 13:return void(enableNativeMenu()||(e.preventDefault(),showActionSheet(this)));case 37:case 38:case 39:case 40:return void(layoutManager.tv&&e.preventDefault())}}var EmbySelectPrototype=Object.create(HTMLSelectElement.prototype),inputId=0;EmbySelectPrototype.createdCallback=function(){this.id||(this.id="embyselect"+inputId,inputId++),browser.firefox||(this.classList.add("emby-select-withcolor"),layoutManager.tv&&this.classList.add("emby-select-tv-withcolor")),layoutManager.tv&&this.classList.add("emby-select-focusscale"),this.addEventListener("mousedown",onMouseDown),this.addEventListener("keydown",onKeyDown),this.addEventListener("focus",onFocus),this.addEventListener("blur",onBlur)},EmbySelectPrototype.attachedCallback=function(){if(!this.classList.contains("emby-select")){this.classList.add("emby-select");var label=this.ownerDocument.createElement("label");label.innerHTML=this.getAttribute("label")||"",label.classList.add("selectLabel"),label.htmlFor=this.id,this.parentNode.insertBefore(label,this),this.classList.contains("emby-select-withcolor")&&this.parentNode.insertAdjacentHTML("beforeend",'
0
')}},EmbySelectPrototype.setLabel=function(text){this.parentNode.querySelector("label").innerHTML=text},document.registerElement("emby-select",{prototype:EmbySelectPrototype,extends:"select"})}); \ No newline at end of file +define(["layoutManager", "browser", "actionsheet", "css!./emby-select", "registerElement"], function(layoutManager, browser, actionsheet) { + "use strict"; + + function enableNativeMenu() { + return !(!browser.edgeUwp && !browser.xboxOne) || !(browser.tizen || browser.orsay || browser.web0s) && (!!browser.tv || !layoutManager.tv) + } + + function triggerChange(select) { + var evt = document.createEvent("HTMLEvents"); + evt.initEvent("change", !1, !0), select.dispatchEvent(evt) + } + + function setValue(select, value) { + select.value = value + } + + function showActionSheet(select) { + var labelElem = getLabel(select), + title = labelElem ? labelElem.textContent || labelElem.innerText : null; + actionsheet.show({ + items: select.options, + positionTo: select, + title: title + }).then(function(value) { + setValue(select, value), triggerChange(select) + }) + } + + function getLabel(select) { + for (var elem = select.previousSibling; elem && "LABEL" !== elem.tagName;) elem = elem.previousSibling; + return elem + } + + function onFocus(e) { + var label = getLabel(this); + label && label.classList.add("selectLabelFocused") + } + + function onBlur(e) { + var label = getLabel(this); + label && label.classList.remove("selectLabelFocused") + } + + function onMouseDown(e) { + e.button || enableNativeMenu() || (e.preventDefault(), showActionSheet(this)) + } + + function onKeyDown(e) { + switch (e.keyCode) { + case 13: + return void(enableNativeMenu() || (e.preventDefault(), showActionSheet(this))); + case 37: + case 38: + case 39: + case 40: + return void(layoutManager.tv && e.preventDefault()) + } + } + var EmbySelectPrototype = Object.create(HTMLSelectElement.prototype), + inputId = 0; + EmbySelectPrototype.createdCallback = function() { + this.id || (this.id = "embyselect" + inputId, inputId++), browser.firefox || (this.classList.add("emby-select-withcolor"), layoutManager.tv && this.classList.add("emby-select-tv-withcolor")), layoutManager.tv && this.classList.add("emby-select-focusscale"), this.addEventListener("mousedown", onMouseDown), this.addEventListener("keydown", onKeyDown), this.addEventListener("focus", onFocus), this.addEventListener("blur", onBlur) + }, EmbySelectPrototype.attachedCallback = function() { + if (!this.classList.contains("emby-select")) { + this.classList.add("emby-select"); + var label = this.ownerDocument.createElement("label"); + label.innerHTML = this.getAttribute("label") || "", label.classList.add("selectLabel"), label.htmlFor = this.id, this.parentNode.insertBefore(label, this), this.classList.contains("emby-select-withcolor") && this.parentNode.insertAdjacentHTML("beforeend", '
0
') + } + }, EmbySelectPrototype.setLabel = function(text) { + this.parentNode.querySelector("label").innerHTML = text + }, document.registerElement("emby-select", { + prototype: EmbySelectPrototype, + extends: "select" + }) +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/emby-slider/emby-slider.js b/dashboard-ui/bower_components/emby-webcomponents/emby-slider/emby-slider.js index 7687224fad..74e160d5b7 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/emby-slider/emby-slider.js +++ b/dashboard-ui/bower_components/emby-webcomponents/emby-slider/emby-slider.js @@ -1 +1,101 @@ -define(["browser","dom","layoutManager","css!./emby-slider","registerElement","emby-input"],function(browser,dom,layoutManager){"use strict";function updateValues(){var range=this,value=range.value;requestAnimationFrame(function(){var backgroundLower=range.backgroundLower;if(backgroundLower){var fraction=(value-range.min)/(range.max-range.min);enableWidthWithTransform?backgroundLower.style.transform="scaleX("+fraction+")":(fraction*=100,backgroundLower.style.width=fraction+"%")}})}function updateBubble(range,value,bubble,bubbleText){requestAnimationFrame(function(){bubble.style.left=value+"%",range.getBubbleHtml?value=range.getBubbleHtml(value):(value=range.getBubbleText?range.getBubbleText(value):Math.round(value),value='

'+value+"

"),bubble.innerHTML=value})}function setRange(elem,startPercent,endPercent){var style=elem.style;style.left=Math.max(startPercent,0)+"%";var widthPercent=endPercent-startPercent;style.width=Math.max(Math.min(widthPercent,100),0)+"%"}function mapRangesFromRuntimeToPercent(ranges,runtime){return runtime?ranges.map(function(r){return{start:r.start/runtime*100,end:r.end/runtime*100}}):[]}function startInterval(range){var interval=range.interval;interval&&clearInterval(interval),range.interval=setInterval(updateValues.bind(range),100)}var enableWidthWithTransform,EmbySliderPrototype=Object.create(HTMLInputElement.prototype),supportsNativeProgressStyle=browser.firefox,supportsValueSetOverride=!1;if(Object.getOwnPropertyDescriptor&&Object.defineProperty){var descriptor=Object.getOwnPropertyDescriptor(HTMLInputElement.prototype,"value");descriptor&&descriptor.configurable&&(supportsValueSetOverride=!0)}EmbySliderPrototype.attachedCallback=function(){if("true"!==this.getAttribute("data-embyslider")){this.setAttribute("data-embyslider","true"),this.classList.add("mdl-slider"),this.classList.add("mdl-js-slider"),browser.noFlex&&this.classList.add("slider-no-webkit-thumb"),layoutManager.mobile||this.classList.add("mdl-slider-hoverthumb");var containerElement=this.parentNode;containerElement.classList.add("mdl-slider-container");var htmlToInsert="";supportsNativeProgressStyle||(htmlToInsert+='
',htmlToInsert+='
',htmlToInsert+='
',htmlToInsert+=enableWidthWithTransform?'
':'
',htmlToInsert+="
",htmlToInsert+="
"),htmlToInsert+='
',containerElement.insertAdjacentHTML("beforeend",htmlToInsert),this.backgroundLower=containerElement.querySelector(".mdl-slider-background-lower"),this.backgroundUpper=containerElement.querySelector(".mdl-slider-background-upper");var sliderBubble=containerElement.querySelector(".sliderBubble"),hasHideClass=sliderBubble.classList.contains("hide");dom.addEventListener(this,"input",function(e){this.dragging=!0,updateBubble(this,this.value,sliderBubble),hasHideClass&&(sliderBubble.classList.remove("hide"),hasHideClass=!1)},{passive:!0}),dom.addEventListener(this,"change",function(){this.dragging=!1,updateValues.call(this),sliderBubble.classList.add("hide"),hasHideClass=!0},{passive:!0}),browser.firefox||(dom.addEventListener(this,window.PointerEvent?"pointermove":"mousemove",function(e){if(!this.dragging){var rect=this.getBoundingClientRect(),clientX=e.clientX,bubbleValue=(clientX-rect.left)/rect.width;bubbleValue*=100,updateBubble(this,bubbleValue,sliderBubble),hasHideClass&&(sliderBubble.classList.remove("hide"),hasHideClass=!1)}},{passive:!0}),dom.addEventListener(this,window.PointerEvent?"pointerleave":"mouseleave",function(){sliderBubble.classList.add("hide"),hasHideClass=!0},{passive:!0})),supportsNativeProgressStyle||(supportsValueSetOverride?this.addEventListener("valueset",updateValues):startInterval(this))}},EmbySliderPrototype.setBufferedRanges=function(ranges,runtime,position){var elem=this.backgroundUpper;if(elem){null!=runtime&&(ranges=mapRangesFromRuntimeToPercent(ranges,runtime),position=position/runtime*100);for(var i=0,length=ranges.length;i=range.end))return void setRange(elem,range.start,range.end)}setRange(elem,0,0)}},EmbySliderPrototype.setIsClear=function(isClear){var backgroundLower=this.backgroundLower;backgroundLower&&(isClear?backgroundLower.classList.add("mdl-slider-background-lower-clear"):backgroundLower.classList.remove("mdl-slider-background-lower-clear"))},EmbySliderPrototype.detachedCallback=function(){var interval=this.interval;interval&&clearInterval(interval),this.interval=null,this.backgroundUpper=null,this.backgroundLower=null},document.registerElement("emby-slider",{prototype:EmbySliderPrototype,extends:"input"})}); \ No newline at end of file +define(["browser", "dom", "layoutManager", "css!./emby-slider", "registerElement", "emby-input"], function(browser, dom, layoutManager) { + "use strict"; + + function updateValues() { + var range = this, + value = range.value; + requestAnimationFrame(function() { + var backgroundLower = range.backgroundLower; + if (backgroundLower) { + var fraction = (value - range.min) / (range.max - range.min); + enableWidthWithTransform ? backgroundLower.style.transform = "scaleX(" + fraction + ")" : (fraction *= 100, backgroundLower.style.width = fraction + "%") + } + }) + } + + function updateBubble(range, value, bubble, bubbleText) { + requestAnimationFrame(function() { + bubble.style.left = value + "%", range.getBubbleHtml ? value = range.getBubbleHtml(value) : (value = range.getBubbleText ? range.getBubbleText(value) : Math.round(value), value = '

' + value + "

"), bubble.innerHTML = value + }) + } + + function setRange(elem, startPercent, endPercent) { + var style = elem.style; + style.left = Math.max(startPercent, 0) + "%"; + var widthPercent = endPercent - startPercent; + style.width = Math.max(Math.min(widthPercent, 100), 0) + "%" + } + + function mapRangesFromRuntimeToPercent(ranges, runtime) { + return runtime ? ranges.map(function(r) { + return { + start: r.start / runtime * 100, + end: r.end / runtime * 100 + } + }) : [] + } + + function startInterval(range) { + var interval = range.interval; + interval && clearInterval(interval), range.interval = setInterval(updateValues.bind(range), 100) + } + var enableWidthWithTransform, EmbySliderPrototype = Object.create(HTMLInputElement.prototype), + supportsNativeProgressStyle = browser.firefox, + supportsValueSetOverride = !1; + if (Object.getOwnPropertyDescriptor && Object.defineProperty) { + var descriptor = Object.getOwnPropertyDescriptor(HTMLInputElement.prototype, "value"); + descriptor && descriptor.configurable && (supportsValueSetOverride = !0) + } + EmbySliderPrototype.attachedCallback = function() { + if ("true" !== this.getAttribute("data-embyslider")) { + this.setAttribute("data-embyslider", "true"), this.classList.add("mdl-slider"), this.classList.add("mdl-js-slider"), browser.noFlex && this.classList.add("slider-no-webkit-thumb"), layoutManager.mobile || this.classList.add("mdl-slider-hoverthumb"); + var containerElement = this.parentNode; + containerElement.classList.add("mdl-slider-container"); + var htmlToInsert = ""; + supportsNativeProgressStyle || (htmlToInsert += '
', htmlToInsert += '
', htmlToInsert += '
', htmlToInsert += enableWidthWithTransform ? '
' : '
', htmlToInsert += "
", htmlToInsert += "
"), htmlToInsert += '
', containerElement.insertAdjacentHTML("beforeend", htmlToInsert), this.backgroundLower = containerElement.querySelector(".mdl-slider-background-lower"), this.backgroundUpper = containerElement.querySelector(".mdl-slider-background-upper"); + var sliderBubble = containerElement.querySelector(".sliderBubble"), + hasHideClass = sliderBubble.classList.contains("hide"); + dom.addEventListener(this, "input", function(e) { + this.dragging = !0, updateBubble(this, this.value, sliderBubble), hasHideClass && (sliderBubble.classList.remove("hide"), hasHideClass = !1) + }, { + passive: !0 + }), dom.addEventListener(this, "change", function() { + this.dragging = !1, updateValues.call(this), sliderBubble.classList.add("hide"), hasHideClass = !0 + }, { + passive: !0 + }), browser.firefox || (dom.addEventListener(this, window.PointerEvent ? "pointermove" : "mousemove", function(e) { + if (!this.dragging) { + var rect = this.getBoundingClientRect(), + clientX = e.clientX, + bubbleValue = (clientX - rect.left) / rect.width; + bubbleValue *= 100, updateBubble(this, bubbleValue, sliderBubble), hasHideClass && (sliderBubble.classList.remove("hide"), hasHideClass = !1) + } + }, { + passive: !0 + }), dom.addEventListener(this, window.PointerEvent ? "pointerleave" : "mouseleave", function() { + sliderBubble.classList.add("hide"), hasHideClass = !0 + }, { + passive: !0 + })), supportsNativeProgressStyle || (supportsValueSetOverride ? this.addEventListener("valueset", updateValues) : startInterval(this)) + } + }, EmbySliderPrototype.setBufferedRanges = function(ranges, runtime, position) { + var elem = this.backgroundUpper; + if (elem) { + null != runtime && (ranges = mapRangesFromRuntimeToPercent(ranges, runtime), position = position / runtime * 100); + for (var i = 0, length = ranges.length; i < length; i++) { + var range = ranges[i]; + if (!(null != position && position >= range.end)) return void setRange(elem, range.start, range.end) + } + setRange(elem, 0, 0) + } + }, EmbySliderPrototype.setIsClear = function(isClear) { + var backgroundLower = this.backgroundLower; + backgroundLower && (isClear ? backgroundLower.classList.add("mdl-slider-background-lower-clear") : backgroundLower.classList.remove("mdl-slider-background-lower-clear")) + }, EmbySliderPrototype.detachedCallback = function() { + var interval = this.interval; + interval && clearInterval(interval), this.interval = null, this.backgroundUpper = null, this.backgroundLower = null + }, document.registerElement("emby-slider", { + prototype: EmbySliderPrototype, + extends: "input" + }) +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/emby-tabs/emby-tabs.js b/dashboard-ui/bower_components/emby-webcomponents/emby-tabs/emby-tabs.js index bbaca2277e..3408072a8a 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/emby-tabs/emby-tabs.js +++ b/dashboard-ui/bower_components/emby-webcomponents/emby-tabs/emby-tabs.js @@ -1 +1,191 @@ -define(["dom","scroller","browser","layoutManager","focusManager","registerElement","css!./emby-tabs","scrollStyles"],function(dom,scroller,browser,layoutManager,focusManager){"use strict";function setActiveTabButton(tabs,newButton,oldButton,animate){newButton.classList.add(activeButtonClass)}function getFocusCallback(tabs,e){return function(){onClick.call(tabs,e)}}function onFocus(e){layoutManager.tv&&(this.focusTimeout&&clearTimeout(this.focusTimeout),this.focusTimeout=setTimeout(getFocusCallback(this,e),700))}function getTabPanel(tabs,index){return null}function removeActivePanelClass(tabs,index){var tabPanel=getTabPanel(tabs,index);tabPanel&&tabPanel.classList.remove("is-active")}function fadeInRight(elem){var pct=browser.mobile?"4%":"0.5%",keyframes=[{opacity:"0",transform:"translate3d("+pct+", 0, 0)",offset:0},{opacity:"1",transform:"none",offset:1}];elem.animate(keyframes,{duration:160,iterations:1,easing:"ease-out"})}function triggerBeforeTabChange(tabs,index,previousIndex){tabs.dispatchEvent(new CustomEvent("beforetabchange",{detail:{selectedTabIndex:index,previousIndex:previousIndex}})),null!=previousIndex&&previousIndex!==index&&removeActivePanelClass(tabs,previousIndex);var newPanel=getTabPanel(tabs,index);newPanel&&(newPanel.animate&&fadeInRight(newPanel),newPanel.classList.add("is-active"))}function onClick(e){this.focusTimeout&&clearTimeout(this.focusTimeout);var tabs=this,current=tabs.querySelector("."+activeButtonClass),tabButton=dom.parentWithClass(e.target,buttonClass);if(tabButton&&tabButton!==current){current&¤t.classList.remove(activeButtonClass);var previousIndex=current?parseInt(current.getAttribute("data-index")):null;setActiveTabButton(tabs,tabButton,current,!0);var index=parseInt(tabButton.getAttribute("data-index"));triggerBeforeTabChange(tabs,index,previousIndex),setTimeout(function(){tabs.selectedTabIndex=index,tabs.dispatchEvent(new CustomEvent("tabchange",{detail:{selectedTabIndex:index,previousIndex:previousIndex}}))},120),tabs.scroller&&tabs.scroller.toCenter(tabButton,!1)}}function initScroller(tabs){if(!tabs.scroller){var contentScrollSlider=tabs.querySelector(".emby-tabs-slider");contentScrollSlider?(tabs.scroller=new scroller(tabs,{horizontal:1,itemNav:0,mouseDragging:1,touchDragging:1,slidee:contentScrollSlider,smart:!0,releaseSwing:!0,scrollBy:200,speed:120,elasticBounds:1,dragHandle:1,dynamicHandle:1,clickBar:1,hiddenScroll:!0,requireAnimation:!browser.safari,allowNativeSmoothScroll:!0}),tabs.scroller.init()):(tabs.classList.add("scrollX"),tabs.classList.add("hiddenScrollX"),tabs.classList.add("smoothScrollX"))}}function getSelectedTabButton(elem){return elem.querySelector("."+activeButtonClass)}function getSibling(elem,method){for(var sibling=elem[method];sibling;){if(sibling.classList.contains(buttonClass)&&!sibling.classList.contains("hide"))return sibling;sibling=sibling[method]}return null}var EmbyTabs=Object.create(HTMLDivElement.prototype),buttonClass="emby-tab-button",activeButtonClass=buttonClass+"-active";EmbyTabs.createdCallback=function(){this.classList.contains("emby-tabs")||(this.classList.add("emby-tabs"),this.classList.add("focusable"),dom.addEventListener(this,"click",onClick,{passive:!0}),dom.addEventListener(this,"focus",onFocus,{passive:!0,capture:!0}))},EmbyTabs.focus=function(){var selected=this.querySelector("."+activeButtonClass);selected?focusManager.focus(selected):focusManager.autoFocus(this)},EmbyTabs.refresh=function(){this.scroller&&this.scroller.reload()},EmbyTabs.attachedCallback=function(){initScroller(this);var current=this.querySelector("."+activeButtonClass),currentIndex=current?parseInt(current.getAttribute("data-index")):parseInt(this.getAttribute("data-index")||"0");if(-1!==currentIndex){this.selectedTabIndex=currentIndex;var tabButtons=this.querySelectorAll("."+buttonClass),newTabButton=tabButtons[currentIndex];newTabButton&&setActiveTabButton(this,newTabButton,current,!1)}this.readyFired||(this.readyFired=!0,this.dispatchEvent(new CustomEvent("ready",{})))},EmbyTabs.detachedCallback=function(){this.scroller&&(this.scroller.destroy(),this.scroller=null),dom.removeEventListener(this,"click",onClick,{passive:!0}),dom.removeEventListener(this,"focus",onFocus,{passive:!0,capture:!0})},EmbyTabs.selectedIndex=function(selected,triggerEvent){var tabs=this;if(null==selected)return tabs.selectedTabIndex||0;var current=tabs.selectedIndex();tabs.selectedTabIndex=selected;var tabButtons=tabs.querySelectorAll("."+buttonClass);if(current===selected||!1===triggerEvent){triggerBeforeTabChange(tabs,selected,current),tabs.dispatchEvent(new CustomEvent("tabchange",{detail:{selectedTabIndex:selected}}));var currentTabButton=tabButtons[current];setActiveTabButton(tabs,tabButtons[selected],currentTabButton,!1),current!==selected&¤tTabButton&¤tTabButton.classList.remove(activeButtonClass)}else onClick.call(tabs,{target:tabButtons[selected]})},EmbyTabs.selectNext=function(){var current=getSelectedTabButton(this),sibling=getSibling(current,"nextSibling");sibling&&onClick.call(this,{target:sibling})},EmbyTabs.selectPrevious=function(){var current=getSelectedTabButton(this),sibling=getSibling(current,"previousSibling");sibling&&onClick.call(this,{target:sibling})},EmbyTabs.triggerBeforeTabChange=function(selected){var tabs=this;triggerBeforeTabChange(tabs,tabs.selectedIndex())},EmbyTabs.triggerTabChange=function(selected){var tabs=this;tabs.dispatchEvent(new CustomEvent("tabchange",{detail:{selectedTabIndex:tabs.selectedIndex()}}))},EmbyTabs.setTabEnabled=function(index,enabled){var btn=this.querySelector('.emby-tab-button[data-index="'+index+'"]');enabled?btn.classList.remove("hide"):btn.classList.remove("add")},document.registerElement("emby-tabs",{prototype:EmbyTabs,extends:"div"})}); \ No newline at end of file +define(["dom", "scroller", "browser", "layoutManager", "focusManager", "registerElement", "css!./emby-tabs", "scrollStyles"], function(dom, scroller, browser, layoutManager, focusManager) { + "use strict"; + + function setActiveTabButton(tabs, newButton, oldButton, animate) { + newButton.classList.add(activeButtonClass) + } + + function getFocusCallback(tabs, e) { + return function() { + onClick.call(tabs, e) + } + } + + function onFocus(e) { + layoutManager.tv && (this.focusTimeout && clearTimeout(this.focusTimeout), this.focusTimeout = setTimeout(getFocusCallback(this, e), 700)) + } + + function getTabPanel(tabs, index) { + return null + } + + function removeActivePanelClass(tabs, index) { + var tabPanel = getTabPanel(tabs, index); + tabPanel && tabPanel.classList.remove("is-active") + } + + function fadeInRight(elem) { + var pct = browser.mobile ? "4%" : "0.5%", + keyframes = [{ + opacity: "0", + transform: "translate3d(" + pct + ", 0, 0)", + offset: 0 + }, { + opacity: "1", + transform: "none", + offset: 1 + }]; + elem.animate(keyframes, { + duration: 160, + iterations: 1, + easing: "ease-out" + }) + } + + function triggerBeforeTabChange(tabs, index, previousIndex) { + tabs.dispatchEvent(new CustomEvent("beforetabchange", { + detail: { + selectedTabIndex: index, + previousIndex: previousIndex + } + })), null != previousIndex && previousIndex !== index && removeActivePanelClass(tabs, previousIndex); + var newPanel = getTabPanel(tabs, index); + newPanel && (newPanel.animate && fadeInRight(newPanel), newPanel.classList.add("is-active")) + } + + function onClick(e) { + this.focusTimeout && clearTimeout(this.focusTimeout); + var tabs = this, + current = tabs.querySelector("." + activeButtonClass), + tabButton = dom.parentWithClass(e.target, buttonClass); + if (tabButton && tabButton !== current) { + current && current.classList.remove(activeButtonClass); + var previousIndex = current ? parseInt(current.getAttribute("data-index")) : null; + setActiveTabButton(tabs, tabButton, current, !0); + var index = parseInt(tabButton.getAttribute("data-index")); + triggerBeforeTabChange(tabs, index, previousIndex), setTimeout(function() { + tabs.selectedTabIndex = index, tabs.dispatchEvent(new CustomEvent("tabchange", { + detail: { + selectedTabIndex: index, + previousIndex: previousIndex + } + })) + }, 120), tabs.scroller && tabs.scroller.toCenter(tabButton, !1) + } + } + + function initScroller(tabs) { + if (!tabs.scroller) { + var contentScrollSlider = tabs.querySelector(".emby-tabs-slider"); + contentScrollSlider ? (tabs.scroller = new scroller(tabs, { + horizontal: 1, + itemNav: 0, + mouseDragging: 1, + touchDragging: 1, + slidee: contentScrollSlider, + smart: !0, + releaseSwing: !0, + scrollBy: 200, + speed: 120, + elasticBounds: 1, + dragHandle: 1, + dynamicHandle: 1, + clickBar: 1, + hiddenScroll: !0, + requireAnimation: !browser.safari, + allowNativeSmoothScroll: !0 + }), tabs.scroller.init()) : (tabs.classList.add("scrollX"), tabs.classList.add("hiddenScrollX"), tabs.classList.add("smoothScrollX")) + } + } + + function getSelectedTabButton(elem) { + return elem.querySelector("." + activeButtonClass) + } + + function getSibling(elem, method) { + for (var sibling = elem[method]; sibling;) { + if (sibling.classList.contains(buttonClass) && !sibling.classList.contains("hide")) return sibling; + sibling = sibling[method] + } + return null + } + var EmbyTabs = Object.create(HTMLDivElement.prototype), + buttonClass = "emby-tab-button", + activeButtonClass = buttonClass + "-active"; + EmbyTabs.createdCallback = function() { + this.classList.contains("emby-tabs") || (this.classList.add("emby-tabs"), this.classList.add("focusable"), dom.addEventListener(this, "click", onClick, { + passive: !0 + }), dom.addEventListener(this, "focus", onFocus, { + passive: !0, + capture: !0 + })) + }, EmbyTabs.focus = function() { + var selected = this.querySelector("." + activeButtonClass); + selected ? focusManager.focus(selected) : focusManager.autoFocus(this) + }, EmbyTabs.refresh = function() { + this.scroller && this.scroller.reload() + }, EmbyTabs.attachedCallback = function() { + initScroller(this); + var current = this.querySelector("." + activeButtonClass), + currentIndex = current ? parseInt(current.getAttribute("data-index")) : parseInt(this.getAttribute("data-index") || "0"); + if (-1 !== currentIndex) { + this.selectedTabIndex = currentIndex; + var tabButtons = this.querySelectorAll("." + buttonClass), + newTabButton = tabButtons[currentIndex]; + newTabButton && setActiveTabButton(this, newTabButton, current, !1) + } + this.readyFired || (this.readyFired = !0, this.dispatchEvent(new CustomEvent("ready", {}))) + }, EmbyTabs.detachedCallback = function() { + this.scroller && (this.scroller.destroy(), this.scroller = null), dom.removeEventListener(this, "click", onClick, { + passive: !0 + }), dom.removeEventListener(this, "focus", onFocus, { + passive: !0, + capture: !0 + }) + }, EmbyTabs.selectedIndex = function(selected, triggerEvent) { + var tabs = this; + if (null == selected) return tabs.selectedTabIndex || 0; + var current = tabs.selectedIndex(); + tabs.selectedTabIndex = selected; + var tabButtons = tabs.querySelectorAll("." + buttonClass); + if (current === selected || !1 === triggerEvent) { + triggerBeforeTabChange(tabs, selected, current), tabs.dispatchEvent(new CustomEvent("tabchange", { + detail: { + selectedTabIndex: selected + } + })); + var currentTabButton = tabButtons[current]; + setActiveTabButton(tabs, tabButtons[selected], currentTabButton, !1), current !== selected && currentTabButton && currentTabButton.classList.remove(activeButtonClass) + } else onClick.call(tabs, { + target: tabButtons[selected] + }) + }, EmbyTabs.selectNext = function() { + var current = getSelectedTabButton(this), + sibling = getSibling(current, "nextSibling"); + sibling && onClick.call(this, { + target: sibling + }) + }, EmbyTabs.selectPrevious = function() { + var current = getSelectedTabButton(this), + sibling = getSibling(current, "previousSibling"); + sibling && onClick.call(this, { + target: sibling + }) + }, EmbyTabs.triggerBeforeTabChange = function(selected) { + var tabs = this; + triggerBeforeTabChange(tabs, tabs.selectedIndex()) + }, EmbyTabs.triggerTabChange = function(selected) { + var tabs = this; + tabs.dispatchEvent(new CustomEvent("tabchange", { + detail: { + selectedTabIndex: tabs.selectedIndex() + } + })) + }, EmbyTabs.setTabEnabled = function(index, enabled) { + var btn = this.querySelector('.emby-tab-button[data-index="' + index + '"]'); + enabled ? btn.classList.remove("hide") : btn.classList.remove("add") + }, document.registerElement("emby-tabs", { + prototype: EmbyTabs, + extends: "div" + }) +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/emby-textarea/emby-textarea.js b/dashboard-ui/bower_components/emby-webcomponents/emby-textarea/emby-textarea.js index 70108e0143..f5725c2301 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/emby-textarea/emby-textarea.js +++ b/dashboard-ui/bower_components/emby-webcomponents/emby-textarea/emby-textarea.js @@ -1 +1,55 @@ -define(["layoutManager","browser","css!./emby-textarea","registerElement","emby-input"],function(layoutManager,browser){"use strict";function autoGrow(textarea,maxLines){function reset(){textarea.rows=1,offset=self.getOffset(textarea),self.rows=textarea.rows||1,self.lineHeight=textarea.scrollHeight/self.rows-offset/self.rows,self.maxAllowedHeight=self.lineHeight*maxLines-offset}function autogrowFn(){if((!self.lineHeight||self.lineHeight<=0)&&reset(),self.lineHeight<=0)return textarea.style.overflowY="scroll",textarea.style.height="auto",void(textarea.rows=3);var newHeight=0;textarea.scrollHeight-offset>self.maxAllowedHeight?(textarea.style.overflowY="scroll",newHeight=self.maxAllowedHeight):(textarea.style.overflowY="hidden",textarea.style.height="auto",newHeight=textarea.scrollHeight),textarea.style.height=newHeight+"px"}var self=this;void 0===maxLines&&(maxLines=999),self.getOffset=function(textarea){for(var style=window.getComputedStyle(textarea,null),props=["paddingTop","paddingBottom"],offset=0,i=0;i self.maxAllowedHeight ? (textarea.style.overflowY = "scroll", newHeight = self.maxAllowedHeight) : (textarea.style.overflowY = "hidden", textarea.style.height = "auto", newHeight = textarea.scrollHeight), textarea.style.height = newHeight + "px" + } + var self = this; + void 0 === maxLines && (maxLines = 999), self.getOffset = function(textarea) { + for (var style = window.getComputedStyle(textarea, null), props = ["paddingTop", "paddingBottom"], offset = 0, i = 0; i < props.length; i++) offset += parseInt(style[props[i]]); + return offset + }; + var offset; + textarea.addEventListener("input", autogrowFn), textarea.addEventListener("focus", autogrowFn), textarea.addEventListener("valueset", autogrowFn), autogrowFn() + } + var EmbyTextAreaPrototype = Object.create(HTMLTextAreaElement.prototype), + elementId = 0; + if (Object.getOwnPropertyDescriptor && Object.defineProperty) { + var descriptor = Object.getOwnPropertyDescriptor(HTMLTextAreaElement.prototype, "value"); + if (descriptor && descriptor.configurable) { + var baseSetMethod = descriptor.set; + descriptor.set = function(value) { + baseSetMethod.call(this, value), this.dispatchEvent(new CustomEvent("valueset", { + bubbles: !1, + cancelable: !1 + })) + }, Object.defineProperty(HTMLTextAreaElement.prototype, "value", descriptor) + } + } + EmbyTextAreaPrototype.createdCallback = function() { + this.id || (this.id = "embytextarea" + elementId, elementId++) + }, EmbyTextAreaPrototype.attachedCallback = function() { + if (!this.classList.contains("emby-textarea")) { + this.rows = 1, this.classList.add("emby-textarea"); + var parentNode = this.parentNode, + label = this.ownerDocument.createElement("label"); + label.innerHTML = this.getAttribute("label") || "", label.classList.add("textareaLabel"), label.htmlFor = this.id, parentNode.insertBefore(label, this), this.addEventListener("focus", function() { + label.classList.add("textareaLabelFocused"), label.classList.remove("textareaLabelUnfocused") + }), this.addEventListener("blur", function() { + label.classList.remove("textareaLabelFocused"), label.classList.add("textareaLabelUnfocused") + }), this.label = function(text) { + label.innerHTML = text + }, new autoGrow(this) + } + }, document.registerElement("emby-textarea", { + prototype: EmbyTextAreaPrototype, + extends: "textarea" + }) +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/emby-toggle/emby-toggle.js b/dashboard-ui/bower_components/emby-webcomponents/emby-toggle/emby-toggle.js index 3dc060fd84..f62899902d 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/emby-toggle/emby-toggle.js +++ b/dashboard-ui/bower_components/emby-webcomponents/emby-toggle/emby-toggle.js @@ -1 +1,22 @@ -define(["css!./emby-toggle","registerElement"],function(){"use strict";function onKeyDown(e){if(13===e.keyCode)return e.preventDefault(),this.checked=!this.checked,this.dispatchEvent(new CustomEvent("change",{bubbles:!0})),!1}var EmbyTogglePrototype=Object.create(HTMLInputElement.prototype);EmbyTogglePrototype.attachedCallback=function(){if("true"!==this.getAttribute("data-embytoggle")){this.setAttribute("data-embytoggle","true"),this.classList.add("mdl-switch__input");var labelElement=this.parentNode;labelElement.classList.add("mdl-switch"),labelElement.classList.add("mdl-js-switch");var labelTextElement=labelElement.querySelector("span");labelElement.insertAdjacentHTML("beforeend",'
'),labelTextElement.classList.add("toggleButtonLabel"),labelTextElement.classList.add("mdl-switch__label"),this.addEventListener("keydown",onKeyDown)}},document.registerElement("emby-toggle",{prototype:EmbyTogglePrototype,extends:"input"})}); \ No newline at end of file +define(["css!./emby-toggle", "registerElement"], function() { + "use strict"; + + function onKeyDown(e) { + if (13 === e.keyCode) return e.preventDefault(), this.checked = !this.checked, this.dispatchEvent(new CustomEvent("change", { + bubbles: !0 + })), !1 + } + var EmbyTogglePrototype = Object.create(HTMLInputElement.prototype); + EmbyTogglePrototype.attachedCallback = function() { + if ("true" !== this.getAttribute("data-embytoggle")) { + this.setAttribute("data-embytoggle", "true"), this.classList.add("mdl-switch__input"); + var labelElement = this.parentNode; + labelElement.classList.add("mdl-switch"), labelElement.classList.add("mdl-js-switch"); + var labelTextElement = labelElement.querySelector("span"); + labelElement.insertAdjacentHTML("beforeend", '
'), labelTextElement.classList.add("toggleButtonLabel"), labelTextElement.classList.add("mdl-switch__label"), this.addEventListener("keydown", onKeyDown) + } + }, document.registerElement("emby-toggle", { + prototype: EmbyTogglePrototype, + extends: "input" + }) +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/fetchhelper.js b/dashboard-ui/bower_components/emby-webcomponents/fetchhelper.js index 2789db0370..ed0c74d6c4 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/fetchhelper.js +++ b/dashboard-ui/bower_components/emby-webcomponents/fetchhelper.js @@ -1 +1,54 @@ -define([],function(){"use strict";function getFetchPromise(request){var headers=request.headers||{};"json"===request.dataType&&(headers.accept="application/json");var fetchRequest={headers:headers,method:request.type,credentials:"same-origin"},contentType=request.contentType;request.data&&("string"==typeof request.data?fetchRequest.body=request.data:(fetchRequest.body=paramsToString(request.data),contentType=contentType||"application/x-www-form-urlencoded; charset=UTF-8")),contentType&&(headers["Content-Type"]=contentType);var url=request.url;if(request.query){var paramString=paramsToString(request.query);paramString&&(url+="?"+paramString)}return request.timeout?fetchWithTimeout(url,fetchRequest,request.timeout):fetch(url,fetchRequest)}function fetchWithTimeout(url,options,timeoutMs){return console.log("fetchWithTimeout: timeoutMs: "+timeoutMs+", url: "+url),new Promise(function(resolve,reject){var timeout=setTimeout(reject,timeoutMs);options=options||{},options.credentials="same-origin",fetch(url,options).then(function(response){clearTimeout(timeout),console.log("fetchWithTimeout: succeeded connecting to url: "+url),resolve(response)},function(error){clearTimeout(timeout),console.log("fetchWithTimeout: timed out connecting to url: "+url),reject()})})}function paramsToString(params){var values=[];for(var key in params){var value=params[key];null!==value&&void 0!==value&&""!==value&&values.push(encodeURIComponent(key)+"="+encodeURIComponent(value))}return values.join("&")}function ajax(request){if(!request)throw new Error("Request cannot be null");return request.headers=request.headers||{},console.log("requesting url: "+request.url),getFetchPromise(request).then(function(response){return console.log("response status: "+response.status+", url: "+request.url),response.status<400?"json"===request.dataType||"application/json"===request.headers.accept?response.json():"text"===request.dataType||0===(response.headers.get("Content-Type")||"").toLowerCase().indexOf("text/")?response.text():response:Promise.reject(response)},function(err){throw console.log("request failed to url: "+request.url),err})}return{getFetchPromise:getFetchPromise,ajax:ajax}}); \ No newline at end of file +define([], function() { + "use strict"; + + function getFetchPromise(request) { + var headers = request.headers || {}; + "json" === request.dataType && (headers.accept = "application/json"); + var fetchRequest = { + headers: headers, + method: request.type, + credentials: "same-origin" + }, + contentType = request.contentType; + request.data && ("string" == typeof request.data ? fetchRequest.body = request.data : (fetchRequest.body = paramsToString(request.data), contentType = contentType || "application/x-www-form-urlencoded; charset=UTF-8")), contentType && (headers["Content-Type"] = contentType); + var url = request.url; + if (request.query) { + var paramString = paramsToString(request.query); + paramString && (url += "?" + paramString) + } + return request.timeout ? fetchWithTimeout(url, fetchRequest, request.timeout) : fetch(url, fetchRequest) + } + + function fetchWithTimeout(url, options, timeoutMs) { + return console.log("fetchWithTimeout: timeoutMs: " + timeoutMs + ", url: " + url), new Promise(function(resolve, reject) { + var timeout = setTimeout(reject, timeoutMs); + options = options || {}, options.credentials = "same-origin", fetch(url, options).then(function(response) { + clearTimeout(timeout), console.log("fetchWithTimeout: succeeded connecting to url: " + url), resolve(response) + }, function(error) { + clearTimeout(timeout), console.log("fetchWithTimeout: timed out connecting to url: " + url), reject() + }) + }) + } + + function paramsToString(params) { + var values = []; + for (var key in params) { + var value = params[key]; + null !== value && void 0 !== value && "" !== value && values.push(encodeURIComponent(key) + "=" + encodeURIComponent(value)) + } + return values.join("&") + } + + function ajax(request) { + if (!request) throw new Error("Request cannot be null"); + return request.headers = request.headers || {}, console.log("requesting url: " + request.url), getFetchPromise(request).then(function(response) { + return console.log("response status: " + response.status + ", url: " + request.url), response.status < 400 ? "json" === request.dataType || "application/json" === request.headers.accept ? response.json() : "text" === request.dataType || 0 === (response.headers.get("Content-Type") || "").toLowerCase().indexOf("text/") ? response.text() : response : Promise.reject(response) + }, function(err) { + throw console.log("request failed to url: " + request.url), err + }) + } + return { + getFetchPromise: getFetchPromise, + ajax: ajax + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/filedownloader.js b/dashboard-ui/bower_components/emby-webcomponents/filedownloader.js index 84ba0c7650..ea7a1ff99f 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/filedownloader.js +++ b/dashboard-ui/bower_components/emby-webcomponents/filedownloader.js @@ -1 +1,10 @@ -define(["multi-download"],function(multiDownload){"use strict";return{download:function(items){multiDownload(items.map(function(item){return item.url}))}}}); \ No newline at end of file +define(["multi-download"], function(multiDownload) { + "use strict"; + return { + download: function(items) { + multiDownload(items.map(function(item) { + return item.url + })) + } + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/filesystem.js b/dashboard-ui/bower_components/emby-webcomponents/filesystem.js index eee606d15e..7f9599cc14 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/filesystem.js +++ b/dashboard-ui/bower_components/emby-webcomponents/filesystem.js @@ -1 +1,11 @@ -define([],function(){"use strict";return{fileExists:function(path){return Promise.reject()},directoryExists:function(path){return Promise.reject()}}}); \ No newline at end of file +define([], function() { + "use strict"; + return { + fileExists: function(path) { + return Promise.reject() + }, + directoryExists: function(path) { + return Promise.reject() + } + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/filtermenu/filtermenu.js b/dashboard-ui/bower_components/emby-webcomponents/filtermenu/filtermenu.js index 87818d167d..e0fe446ebe 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/filtermenu/filtermenu.js +++ b/dashboard-ui/bower_components/emby-webcomponents/filtermenu/filtermenu.js @@ -1 +1,125 @@ -define(["require","dom","focusManager","dialogHelper","loading","apphost","inputManager","layoutManager","connectionManager","appRouter","globalize","userSettings","emby-checkbox","emby-input","paper-icon-button-light","emby-select","material-icons","css!./../formdialog","emby-button","emby-linkbutton","flexStyles"],function(require,dom,focusManager,dialogHelper,loading,appHost,inputManager,layoutManager,connectionManager,appRouter,globalize,userSettings){"use strict";function onSubmit(e){return e.preventDefault(),!1}function renderOptions(context,selector,cssClass,items,isCheckedFn){var elem=context.querySelector(selector);items.length?elem.classList.remove("hide"):elem.classList.add("hide");var html="";html+=items.map(function(filter){var itemHtml="",checkedHtml=isCheckedFn(filter)?" checked":"";return itemHtml+=""}).join(""),elem.querySelector(".filterOptions").innerHTML=html}function renderDynamicFilters(context,result,options){renderOptions(context,".genreFilters","chkGenreFilter",result.Genres,function(i){var delimeter=-1===(options.settings.GenreIds||"").indexOf("|")?",":"|";return-1!==(delimeter+(options.settings.GenreIds||"")+delimeter).indexOf(delimeter+i.Id+delimeter)})}function loadDynamicFilters(context,options){var apiClient=connectionManager.getApiClient(options.serverId),filterMenuOptions=Object.assign(options.filterMenuOptions,{UserId:apiClient.getCurrentUserId(),ParentId:options.parentId,IncludeItemTypes:options.itemTypes.join(",")});apiClient.getFilters(filterMenuOptions).then(function(result){renderDynamicFilters(context,result,options)},function(){})}function initEditor(context,settings){context.querySelector("form").addEventListener("submit",onSubmit);var i,length,elems=context.querySelectorAll(".simpleFilter");for(i=0,length=elems.length;i', itemHtml += "" + filter.Name + "", itemHtml += "" + }).join(""), elem.querySelector(".filterOptions").innerHTML = html + } + + function renderDynamicFilters(context, result, options) { + renderOptions(context, ".genreFilters", "chkGenreFilter", result.Genres, function(i) { + var delimeter = -1 === (options.settings.GenreIds || "").indexOf("|") ? "," : "|"; + return -1 !== (delimeter + (options.settings.GenreIds || "") + delimeter).indexOf(delimeter + i.Id + delimeter) + }) + } + + function loadDynamicFilters(context, options) { + var apiClient = connectionManager.getApiClient(options.serverId), + filterMenuOptions = Object.assign(options.filterMenuOptions, { + UserId: apiClient.getCurrentUserId(), + ParentId: options.parentId, + IncludeItemTypes: options.itemTypes.join(",") + }); + apiClient.getFilters(filterMenuOptions).then(function(result) { + renderDynamicFilters(context, result, options) + }, function() {}) + } + + function initEditor(context, settings) { + context.querySelector("form").addEventListener("submit", onSubmit); + var i, length, elems = context.querySelectorAll(".simpleFilter"); + for (i = 0, length = elems.length; i < length; i++) "INPUT" === elems[i].tagName ? elems[i].checked = settings[elems[i].getAttribute("data-settingname")] || !1 : elems[i].querySelector("input").checked = settings[elems[i].getAttribute("data-settingname")] || !1; + var videoTypes = settings.VideoTypes ? settings.VideoTypes.split(",") : []; + for (elems = context.querySelectorAll(".chkVideoTypeFilter"), i = 0, length = elems.length; i < length; i++) elems[i].checked = -1 !== videoTypes.indexOf(elems[i].getAttribute("data-filter")); + var seriesStatuses = settings.SeriesStatus ? settings.SeriesStatus.split(",") : []; + for (elems = context.querySelectorAll(".chkSeriesStatus"), i = 0, length = elems.length; i < length; i++) elems[i].checked = -1 !== seriesStatuses.indexOf(elems[i].getAttribute("data-filter")); + context.querySelector(".basicFilterSection .viewSetting:not(.hide)") ? context.querySelector(".basicFilterSection").classList.remove("hide") : context.querySelector(".basicFilterSection").classList.add("hide"), context.querySelector(".featureSection .viewSetting:not(.hide)") ? context.querySelector(".featureSection").classList.remove("hide") : context.querySelector(".featureSection").classList.add("hide") + } + + function saveValues(context, settings, settingsKey) { + var i, length, elems = context.querySelectorAll(".simpleFilter"); + for (i = 0, length = elems.length; i < length; i++) "INPUT" === elems[i].tagName ? setBasicFilter(context, settingsKey + "-filter-" + elems[i].getAttribute("data-settingname"), elems[i]) : setBasicFilter(context, settingsKey + "-filter-" + elems[i].getAttribute("data-settingname"), elems[i].querySelector("input")); + var videoTypes = []; + for (elems = context.querySelectorAll(".chkVideoTypeFilter"), i = 0, length = elems.length; i < length; i++) elems[i].checked && videoTypes.push(elems[i].getAttribute("data-filter")); + userSettings.setFilter(settingsKey + "-filter-VideoTypes", videoTypes.join(",")); + var seriesStatuses = []; + for (elems = context.querySelectorAll(".chkSeriesStatus"), i = 0, length = elems.length; i < length; i++) elems[i].checked && seriesStatuses.push(elems[i].getAttribute("data-filter")); + var genres = []; + for (elems = context.querySelectorAll(".chkGenreFilter"), i = 0, length = elems.length; i < length; i++) elems[i].checked && genres.push(elems[i].getAttribute("data-filter")); + userSettings.setFilter(settingsKey + "-filter-GenreIds", genres.join(",")) + } + + function setBasicFilter(context, key, elem) { + var value = elem.checked; + value = value || null, userSettings.setFilter(key, value) + } + + function centerFocus(elem, horiz, on) { + require(["scrollHelper"], function(scrollHelper) { + var fn = on ? "on" : "off"; + scrollHelper.centerFocus[fn](elem, horiz) + }) + } + + function moveCheckboxFocus(elem, offset) { + for (var parent = dom.parentWithClass(elem, "checkboxList-verticalwrap"), elems = focusManager.getFocusableElements(parent), index = -1, i = 0, length = elems.length; i < length; i++) + if (elems[i] === elem) { + index = i; + break + } index += offset, index = Math.min(elems.length - 1, index), index = Math.max(0, index); + var newElem = elems[index]; + newElem && focusManager.focus(newElem) + } + + function onInputCommand(e) { + switch (e.detail.command) { + case "left": + moveCheckboxFocus(e.target, -1), e.preventDefault(); + break; + case "right": + moveCheckboxFocus(e.target, 1), e.preventDefault() + } + } + + function FilterMenu() {} + + function bindCheckboxInput(context, on) { + for (var elems = context.querySelectorAll(".checkboxList-verticalwrap"), i = 0, length = elems.length; i < length; i++) on ? inputManager.on(elems[i], onInputCommand) : inputManager.off(elems[i], onInputCommand) + } + return FilterMenu.prototype.show = function(options) { + return new Promise(function(resolve, reject) { + require(["text!./filtermenu.template.html"], function(template) { + var dialogOptions = { + removeOnClose: !0, + scrollY: !1 + }; + layoutManager.tv ? dialogOptions.size = "fullscreen" : dialogOptions.size = "small"; + var dlg = dialogHelper.createDialog(dialogOptions); + dlg.classList.add("formDialog"); + var html = ""; + html += '
', html += '', html += '

${Filters}

', html += "
", html += template, dlg.innerHTML = globalize.translateDocument(html, "sharedcomponents"); + for (var settingElements = dlg.querySelectorAll(".viewSetting"), i = 0, length = settingElements.length; i < length; i++) - 1 === options.visibleSettings.indexOf(settingElements[i].getAttribute("data-settingname")) ? settingElements[i].classList.add("hide") : settingElements[i].classList.remove("hide"); + initEditor(dlg, options.settings), loadDynamicFilters(dlg, options), bindCheckboxInput(dlg, !0), dlg.querySelector(".btnCancel").addEventListener("click", function() { + dialogHelper.close(dlg) + }), layoutManager.tv && centerFocus(dlg.querySelector(".formDialogContent"), !1, !0); + var submitted; + dlg.querySelector("form").addEventListener("change", function() { + submitted = !0 + }, !0), dialogHelper.open(dlg).then(function() { + if (bindCheckboxInput(dlg, !1), layoutManager.tv && centerFocus(dlg.querySelector(".formDialogContent"), !1, !1), submitted) return saveValues(dlg, options.settings, options.settingsKey), void resolve(); + reject() + }) + }) + }) + }, FilterMenu +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/flvjs/flv.min.js b/dashboard-ui/bower_components/emby-webcomponents/flvjs/flv.min.js index 4a3efed93f..bc71e64626 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/flvjs/flv.min.js +++ b/dashboard-ui/bower_components/emby-webcomponents/flvjs/flv.min.js @@ -1,7 +1,6277 @@ -!function(e){if("object"==typeof exports&&"undefined"!=typeof module)module.exports=e();else if("function"==typeof define&&define.amd)define([],e);else{var t;t="undefined"!=typeof window?window:"undefined"!=typeof global?global:"undefined"!=typeof self?self:this,t.flvjs=e()}}(function(){var e;return function e(t,n,i){function r(a,o){if(!n[a]){if(!t[a]){var u="function"==typeof require&&require;if(!o&&u)return u(a,!0);if(s)return s(a,!0);var l=new Error("Cannot find module '"+a+"'");throw l.code="MODULE_NOT_FOUND",l}var d=n[a]={exports:{}};t[a][0].call(d.exports,function(e){var n=t[a][1][e];return r(n||e)},d,d.exports,e,t,n,i)}return n[a].exports}for(var s="function"==typeof require&&require,a=0;a0&&this._events[e].length>n&&(this._events[e].warned=!0,console.error("(node) warning: possible EventEmitter memory leak detected. %d listeners added. Use emitter.setMaxListeners() to increase limit.",this._events[e].length),"function"==typeof console.trace&&console.trace()),this},i.prototype.on=i.prototype.addListener,i.prototype.once=function(e,t){function n(){this.removeListener(e,n),i||(i=!0,t.apply(this,arguments))}if(!r(t))throw TypeError("listener must be a function");var i=!1;return n.listener=t,this.on(e,n),this},i.prototype.removeListener=function(e,t){var n,i,s,o;if(!r(t))throw TypeError("listener must be a function");if(!this._events||!this._events[e])return this;if(n=this._events[e],s=n.length,i=-1,n===t||r(n.listener)&&n.listener===t)delete this._events[e],this._events.removeListener&&this.emit("removeListener",e,t);else if(a(n)){for(o=s;o-- >0;)if(n[o]===t||n[o].listener&&n[o].listener===t){i=o;break}if(i<0)return this;1===n.length?(n.length=0,delete this._events[e]):n.splice(i,1),this._events.removeListener&&this.emit("removeListener",e,t)}return this},i.prototype.removeAllListeners=function(e){var t,n;if(!this._events)return this;if(!this._events.removeListener)return 0===arguments.length?this._events={}:this._events[e]&&delete this._events[e],this;if(0===arguments.length){for(t in this._events)"removeListener"!==t&&this.removeAllListeners(t);return this.removeAllListeners("removeListener"),this._events={},this}if(n=this._events[e],r(n))this.removeListener(e,n);else if(n)for(;n.length;)this.removeListener(e,n[n.length-1]);return delete this._events[e],this},i.prototype.listeners=function(e){return this._events&&this._events[e]?r(this._events[e])?[this._events[e]]:this._events[e].slice():[]},i.prototype.listenerCount=function(e){if(this._events){var t=this._events[e];if(r(t))return 1;if(t)return t.length}return 0},i.listenerCount=function(e,t){return e.listenerCount(t)}},{}],3:[function(e,t,n){function i(){throw new Error("setTimeout has not been defined")}function r(){throw new Error("clearTimeout has not been defined")}function s(e){if(h===setTimeout)return setTimeout(e,0);if((h===i||!h)&&setTimeout)return h=setTimeout,setTimeout(e,0);try{return h(e,0)}catch(t){try{return h.call(null,e,0)}catch(t){return h.call(this,e,0)}}}function a(e){if(f===clearTimeout)return clearTimeout(e);if((f===r||!f)&&clearTimeout)return f=clearTimeout,clearTimeout(e);try{return f(e)}catch(t){try{return f.call(null,e)}catch(t){return f.call(this,e)}}}function o(){p&&_&&(p=!1,_.length?m=_.concat(m):v=-1,m.length&&u())}function u(){if(!p){var e=s(o);p=!0;for(var t=m.length;t;){for(_=m,m=[];++v1)for(var n=1;n=e[r]&&t0&&e[0].originalDts=t[r].dts&&et[i].lastSample.originalDts&&e=t[i].lastSample.originalDts&&(i===t.length-1||i0&&(r=this._searchNearestSegmentBefore(n.originalBeginDts)+1),this._lastAppendLocation=r,this._list.splice(r,0,n)}},{key:"getLastSegmentBefore",value:function(e){var t=this._searchNearestSegmentBefore(e);return t>=0?this._list[t]:null}},{key:"getLastSampleBefore",value:function(e){var t=this.getLastSegmentBefore(e);return null!=t?t.lastSample:null}},{key:"getLastSyncPointBefore",value:function(e){for(var t=this._searchNearestSegmentBefore(e),n=this._list[t].syncPoints;0===n.length&&t>0;)t--,n=this._list[t].syncPoints;return n.length>0?n[n.length-1]:null}},{key:"type",get:function(){return this._type}},{key:"length",get:function(){return this._list.length}}]),e}()},{}],9:[function(e,t,n){"use strict";function i(e){return e&&e.__esModule?e:{default:e}}function r(e,t){if(!(e instanceof t))throw new TypeError("Cannot call a class as a function")}Object.defineProperty(n,"__esModule",{value:!0});var s=function(){function e(e,t){for(var n=0;n0&&(i+=";codecs="+n.codec);var r=!1;if(l.default.v(this.TAG,"Received Initialization Segment, mimeType: "+i),this._lastInitSegments[n.type]=n,i!==this._mimeTypes[n.type]){if(this._mimeTypes[n.type])l.default.v(this.TAG,"Notice: "+n.type+" mimeType changed, origin: "+this._mimeTypes[n.type]+", target: "+i);else{r=!0;try{var s=this._sourceBuffers[n.type]=this._mediaSource.addSourceBuffer(i);s.addEventListener("error",this.e.onSourceBufferError),s.addEventListener("updateend",this.e.onSourceBufferUpdateEnd)}catch(e){return l.default.e(this.TAG,e.message),void this._emitter.emit(c.default.ERROR,{code:e.code,msg:e.message})}}this._mimeTypes[n.type]=i}t||this._pendingSegments[n.type].push(n),r||this._sourceBuffers[n.type]&&!this._sourceBuffers[n.type].updating&&this._doAppendSegments(),h.default.safari&&"audio/mpeg"===n.container&&n.mediaDuration>0&&(this._requireSetMediaDuration=!0,this._pendingMediaDuration=n.mediaDuration/1e3,this._updateMediaSourceDuration())}},{key:"appendMediaSegment",value:function(e){var t=e;this._pendingSegments[t.type].push(t),this._config.autoCleanupSourceBuffer&&this._needCleanupSourceBuffer()&&this._doCleanupSourceBuffer();var n=this._sourceBuffers[t.type];!n||n.updating||this._hasPendingRemoveRanges()||this._doAppendSegments()}},{key:"seek",value:function(e){for(var t in this._sourceBuffers)if(this._sourceBuffers[t]){var n=this._sourceBuffers[t];if("open"===this._mediaSource.readyState)try{n.abort()}catch(e){l.default.e(this.TAG,e.message)}this._idrList.clear();var i=this._pendingSegments[t];if(i.splice(0,i.length),"closed"!==this._mediaSource.readyState){for(var r=0;r=1&&e-i.start(0)>=this._config.autoCleanupMaxBackwardDuration)return!0}}return!1}},{key:"_doCleanupSourceBuffer",value:function(){var e=this._mediaElement.currentTime;for(var t in this._sourceBuffers){var n=this._sourceBuffers[t];if(n){for(var i=n.buffered,r=!1,s=0;s=this._config.autoCleanupMaxBackwardDuration){r=!0;var u=e-this._config.autoCleanupMinBackwardDuration;this._pendingRemoveRanges[t].push({start:a,end:u})}}else o0&&(isNaN(t)||n>t)&&(l.default.v(this.TAG,"Update MediaSource duration from "+t+" to "+n),this._mediaSource.duration=n),this._requireSetMediaDuration=!1,this._pendingMediaDuration=0}}},{key:"_doRemoveRanges",value:function(){for(var e in this._pendingRemoveRanges)if(this._sourceBuffers[e]&&!this._sourceBuffers[e].updating)for(var t=this._sourceBuffers[e],n=this._pendingRemoveRanges[e];n.length&&!t.updating;){var i=n.shift();t.remove(i.start,i.end)}}},{key:"_doAppendSegments",value:function(){var e=this._pendingSegments;for(var t in e)if(this._sourceBuffers[t]&&!this._sourceBuffers[t].updating&&e[t].length>0){var n=e[t].shift();if(n.timestampOffset){var i=this._sourceBuffers[t].timestampOffset,r=n.timestampOffset/1e3,s=Math.abs(i-r);s>.1&&(l.default.v(this.TAG,"Update MPEG audio timestampOffset from "+i+" to "+r),this._sourceBuffers[t].timestampOffset=r),delete n.timestampOffset}if(!n.data||0===n.data.byteLength)continue;try{this._sourceBuffers[t].appendBuffer(n.data),this._isBufferFull=!1,"video"===t&&n.hasOwnProperty("info")&&this._idrList.appendArray(n.info.syncPoints)}catch(e){this._pendingSegments[t].unshift(n),22===e.code?(this._isBufferFull||this._emitter.emit(c.default.BUFFER_FULL),this._isBufferFull=!0):(l.default.e(this.TAG,e.message),this._emitter.emit(c.default.ERROR,{code:e.code,msg:e.message}))}}}},{key:"_onSourceOpen",value:function(){if(l.default.v(this.TAG,"MediaSource onSourceOpen"),this._mediaSource.removeEventListener("sourceopen",this.e.onSourceOpen),this._pendingSourceBufferInit.length>0)for(var e=this._pendingSourceBufferInit;e.length;){var t=e.shift();this.appendInitSegment(t,!0)}this._hasPendingSegments()&&this._doAppendSegments(),this._emitter.emit(c.default.SOURCE_OPEN)}},{key:"_onSourceEnded",value:function(){l.default.v(this.TAG,"MediaSource onSourceEnded")}},{key:"_onSourceClose",value:function(){l.default.v(this.TAG,"MediaSource onSourceClose"),this._mediaSource&&null!=this.e&&(this._mediaSource.removeEventListener("sourceopen",this.e.onSourceOpen),this._mediaSource.removeEventListener("sourceended",this.e.onSourceEnded),this._mediaSource.removeEventListener("sourceclose",this.e.onSourceClose))}},{key:"_hasPendingSegments",value:function(){var e=this._pendingSegments;return e.video.length>0||e.audio.length>0}},{key:"_hasPendingRemoveRanges",value:function(){var e=this._pendingRemoveRanges;return e.video.length>0||e.audio.length>0}},{key:"_onSourceBufferUpdateEnd",value:function(){this._requireSetMediaDuration?this._updateMediaSourceDuration():this._hasPendingRemoveRanges()?this._doRemoveRanges():this._hasPendingSegments()?this._doAppendSegments():this._hasPendingEos&&this.endOfStream(),this._emitter.emit(c.default.UPDATE_END)}},{key:"_onSourceBufferError",value:function(e){l.default.e(this.TAG,"SourceBuffer Error: "+e)}}]),e}();n.default=p},{"../utils/browser.js":39,"../utils/exception.js":40,"../utils/logger.js":41,"./media-segment-info.js":8,"./mse-events.js":10,events:2}],10:[function(e,t,n){"use strict";Object.defineProperty(n,"__esModule",{value:!0});var i={ERROR:"error",SOURCE_OPEN:"source_open",UPDATE_END:"update_end",BUFFER_FULL:"buffer_full"};n.default=i},{}],11:[function(e,t,n){"use strict";function i(e){return e&&e.__esModule?e:{default:e}}function r(e,t){if(!(e instanceof t))throw new TypeError("Cannot call a class as a function")}Object.defineProperty(n,"__esModule",{value:!0});var s=function(){function e(e,t){for(var n=0;n0)this._demuxer.bindDataSource(this._ioctl),this._demuxer.timestampBase=this._mediaDataSource.segments[this._currentSegmentIndex].timestampBase,r=this._demuxer.parseChunks(e,t);else if((i=m.default.probe(e)).match){this._demuxer=new m.default(i,this._config),this._remuxer||(this._remuxer=new v.default(this._config));var s=this._mediaDataSource;void 0==s.duration||isNaN(s.duration)||(this._demuxer.overridedDuration=s.duration),"boolean"==typeof s.hasAudio&&(this._demuxer.overridedHasAudio=s.hasAudio),"boolean"==typeof s.hasVideo&&(this._demuxer.overridedHasVideo=s.hasVideo),this._demuxer.timestampBase=s.segments[this._currentSegmentIndex].timestampBase,this._demuxer.onError=this._onDemuxException.bind(this),this._demuxer.onMediaInfo=this._onMediaInfo.bind(this),this._remuxer.bindDataSource(this._demuxer.bindDataSource(this._ioctl)),this._remuxer.onInitSegment=this._onRemuxerInitSegmentArrival.bind(this),this._remuxer.onMediaSegment=this._onRemuxerMediaSegmentArrival.bind(this),r=this._demuxer.parseChunks(e,t)}else i=null,l.default.e(this.TAG,"Non-FLV, Unsupported media type!"),Promise.resolve().then(function(){n._internalAbort()}),this._emitter.emit(k.default.DEMUX_ERROR,y.default.FORMAT_UNSUPPORTED,"Non-FLV, Unsupported media type"),r=0;return r}},{key:"_onMediaInfo",value:function(e){var t=this;null==this._mediaInfo&&(this._mediaInfo=Object.assign({},e),this._mediaInfo.keyframesIndex=null,this._mediaInfo.segments=[],this._mediaInfo.segmentCount=this._mediaDataSource.segments.length,Object.setPrototypeOf(this._mediaInfo,c.default.prototype));var n=Object.assign({},e);Object.setPrototypeOf(n,c.default.prototype),this._mediaInfo.segments[this._currentSegmentIndex]=n,this._reportSegmentMediaInfo(this._currentSegmentIndex),null!=this._pendingSeekTime&&Promise.resolve().then(function(){var e=t._pendingSeekTime;t._pendingSeekTime=null,t.seek(e)})}},{key:"_onIOSeeked",value:function(){this._remuxer.insertDiscontinuity()}},{key:"_onIOComplete",value:function(e){var t=e,n=t+1;n0&&n[0].originalDts===i&&(i=n[0].pts),this._emitter.emit(k.default.RECOMMEND_SEEKPOINT,i)}}},{key:"_enableStatisticsReporter",value:function(){null==this._statisticsReporter&&(this._statisticsReporter=self.setInterval(this._reportStatisticsInfo.bind(this),this._config.statisticsInfoReportInterval))}},{key:"_disableStatisticsReporter",value:function(){this._statisticsReporter&&(self.clearInterval(this._statisticsReporter),this._statisticsReporter=null)}},{key:"_reportSegmentMediaInfo",value:function(e){var t=this._mediaInfo.segments[e],n=Object.assign({},t);n.duration=this._mediaInfo.duration,n.segmentCount=this._mediaInfo.segmentCount,delete n.segments,delete n.keyframesIndex,this._emitter.emit(k.default.MEDIA_INFO,n)}},{key:"_reportStatisticsInfo",value:function(){var e={};e.url=this._ioctl.currentURL,e.hasRedirect=this._ioctl.hasRedirect,e.hasRedirect&&(e.redirectedURL=this._ioctl.currentRedirectedURL),e.speed=this._ioctl.currentSpeed,e.loaderType=this._ioctl.loaderType,e.currentSegmentIndex=this._currentSegmentIndex,e.totalSegmentCount=this._mediaDataSource.segments.length,this._emitter.emit(k.default.STATISTICS_INFO,e)}}]),e}());n.default=L},{"../demux/demux-errors.js":16,"../demux/flv-demuxer.js":18,"../io/io-controller.js":23,"../io/loader.js":24,"../remux/mp4-remuxer.js":38,"../utils/browser.js":39,"../utils/logger.js":41,"./media-info.js":7,"./transmuxing-events.js":13,events:2}],13:[function(e,t,n){"use strict";Object.defineProperty(n,"__esModule",{value:!0});var i={IO_ERROR:"io_error",DEMUX_ERROR:"demux_error",INIT_SEGMENT:"init_segment",MEDIA_SEGMENT:"media_segment",LOADING_COMPLETE:"loading_complete",RECOVERED_EARLY_EOF:"recovered_early_eof",MEDIA_INFO:"media_info",STATISTICS_INFO:"statistics_info",RECOMMEND_SEEKPOINT:"recommend_seekpoint"};n.default=i},{}],14:[function(e,t,n){"use strict";function i(e){return e&&e.__esModule?e:{default:e}}Object.defineProperty(n,"__esModule",{value:!0});var r=e("../utils/logger.js"),s=(i(r),e("../utils/logging-control.js")),a=i(s),o=e("../utils/polyfill.js"),u=i(o),l=e("./transmuxing-controller.js"),d=i(l),h=e("./transmuxing-events.js"),f=i(h),c=function(e){function t(t,n){var i={msg:f.default.INIT_SEGMENT,data:{type:t,data:n}};e.postMessage(i,[n.data])}function n(t,n){var i={msg:f.default.MEDIA_SEGMENT,data:{type:t,data:n}};e.postMessage(i,[n.data])}function i(){var t={msg:f.default.LOADING_COMPLETE};e.postMessage(t)}function r(){var t={msg:f.default.RECOVERED_EARLY_EOF};e.postMessage(t)}function s(t){var n={msg:f.default.MEDIA_INFO,data:t};e.postMessage(n)}function o(t){var n={msg:f.default.STATISTICS_INFO,data:t};e.postMessage(n)}function l(t,n){e.postMessage({msg:f.default.IO_ERROR,data:{type:t,info:n}})}function h(t,n){e.postMessage({msg:f.default.DEMUX_ERROR,data:{type:t,info:n}})}function c(t){e.postMessage({msg:f.default.RECOMMEND_SEEKPOINT,data:t})}function _(t,n){e.postMessage({msg:"logcat_callback",data:{type:t,logcat:n}})}var m=null,p=_.bind(this);u.default.install(),e.addEventListener("message",function(u){switch(u.data.cmd){case"init":m=new d.default(u.data.param[0],u.data.param[1]),m.on(f.default.IO_ERROR,l.bind(this)),m.on(f.default.DEMUX_ERROR,h.bind(this)),m.on(f.default.INIT_SEGMENT,t.bind(this)),m.on(f.default.MEDIA_SEGMENT,n.bind(this)),m.on(f.default.LOADING_COMPLETE,i.bind(this)),m.on(f.default.RECOVERED_EARLY_EOF,r.bind(this)),m.on(f.default.MEDIA_INFO,s.bind(this)),m.on(f.default.STATISTICS_INFO,o.bind(this)),m.on(f.default.RECOMMEND_SEEKPOINT,c.bind(this));break;case"destroy":m&&(m.destroy(),m=null),e.postMessage({msg:"destroyed"});break;case"start":m.start();break;case"stop":m.stop();break;case"seek":m.seek(u.data.param);break;case"pause":m.pause();break;case"resume":m.resume();break;case"logging_config":var _=u.data.param;a.default.applyConfig(_),!0===_.enableCallback?a.default.addLogListener(p):a.default.removeLogListener(p)}})};n.default=c},{"../utils/logger.js":41,"../utils/logging-control.js":42,"../utils/polyfill.js":43,"./transmuxing-controller.js":12,"./transmuxing-events.js":13}],15:[function(e,t,n){"use strict";function i(e){return e&&e.__esModule?e:{default:e}}function r(e,t){if(!(e instanceof t))throw new TypeError("Cannot call a class as a function")}Object.defineProperty(n,"__esModule",{value:!0});var s=function(){function e(e,t){for(var n=0;n0?(0,l.default)(new Uint8Array(e,t+2,r)):"",{data:s,size:2+r}}},{key:"parseLongString",value:function(e,t,n){if(n<4)throw new d.IllegalStateException("Data not enough when parse LongString");var i=new DataView(e,t,n),r=i.getUint32(0,!h),s=void 0;return s=r>0?(0,l.default)(new Uint8Array(e,t+4,r)):"",{data:s,size:4+r}}},{key:"parseDate",value:function(e,t,n){if(n<10)throw new d.IllegalStateException("Data size invalid when parse Date");var i=new DataView(e,t,n),r=i.getFloat64(0,!h);return r+=60*i.getInt16(8,!h)*1e3,{data:new Date(r),size:10}}},{key:"parseValue",value:function(t,n,i){if(i<1)throw new d.IllegalStateException("Data not enough when parse Value");var r=new DataView(t,n,i),s=1,a=r.getUint8(0),u=void 0,l=!1;try{switch(a){case 0:u=r.getFloat64(1,!h),s+=8;break;case 1:u=!!r.getUint8(1),s+=1;break;case 2:var f=e.parseString(t,n+1,i-1);u=f.data,s+=f.size;break;case 3:u={};var c=0;for(9==(16777215&r.getUint32(i-4,!h))&&(c=3);s32)throw new s.InvalidArgumentException("ExpGolomb: readBits() bits exceeded max 32bits!");if(e<=this._current_word_bits_left){var t=this._current_word>>>32-e;return this._current_word<<=e,this._current_word_bits_left-=e,t}var n=this._current_word_bits_left?this._current_word:0;n>>>=32-this._current_word_bits_left;var i=e-this._current_word_bits_left;this._fillCurrentWord();var r=Math.min(i,this._current_word_bits_left),a=this._current_word>>>32-r;return this._current_word<<=r,this._current_word_bits_left-=r,n=n<>>e))return this._current_word<<=e,this._current_word_bits_left-=e,e;return this._fillCurrentWord(),e+this._skipLeadingZero()}},{key:"readUEG",value:function(){var e=this._skipLeadingZero();return this.readBits(e+1)-1}},{key:"readSEG",value:function(){var e=this.readUEG();return 1&e?e+1>>>1:-1*(e>>>1)}}]),e}();n.default=a},{"../utils/exception.js":40}],18:[function(e,t,n){"use strict";function i(e){return e&&e.__esModule?e:{default:e}}function r(e,t){if(!(e instanceof t))throw new TypeError("Cannot call a class as a function")}function s(e,t){return e[t]<<24|e[t+1]<<16|e[t+2]<<8|e[t+3]}Object.defineProperty(n,"__esModule",{value:!0});var a="function"==typeof Symbol&&"symbol"==typeof Symbol.iterator?function(e){return typeof e}:function(e){return e&&"function"==typeof Symbol&&e.constructor===Symbol&&e!==Symbol.prototype?"symbol":typeof e},o=function(){function e(e,t){for(var n=0;n13))return 0;i=e.probe(t).dataOffset}if(this._firstParse){this._firstParse=!1,n+i!==this._dataOffset&&l.default.w(this.TAG,"First time parsing but chunk byteStart invalid!");0!==new DataView(t,i).getUint32(0,!r)&&l.default.w(this.TAG,"PrevTagSize0 !== 0 !!!"),i+=4}for(;it.byteLength)break;var a=s.getUint8(0),o=16777215&s.getUint32(0,!r);if(i+11+o+4>t.byteLength)break;if(8===a||9===a||18===a){var u=s.getUint8(4),d=s.getUint8(5),h=s.getUint8(6),f=s.getUint8(7),c=h|d<<8|u<<16|f<<24;0!==(16777215&s.getUint32(7,!r))&&l.default.w(this.TAG,"Meet tag which has StreamID != 0!");var _=i+11;switch(a){case 8:this._parseAudioData(t,_,o,c);break;case 9:this._parseVideoData(t,_,o,c,n+i);break;case 18:this._parseScriptData(t,_,o)}var m=s.getUint32(11+o,!r);m!==11+o&&l.default.w(this.TAG,"Invalid PrevTagSize "+m),i+=11+o+4}else l.default.w(this.TAG,"Unsupported tag type "+a+", skipped"),i+=11+o+4}return this._isInitialMetadataDispatched()&&this._dispatch&&(this._audioTrack.length||this._videoTrack.length)&&this._onDataAvailable(this._audioTrack,this._videoTrack),i}},{key:"_parseScriptData",value:function(e,t,n){var i=h.default.parseScriptData(e,t,n);if(i.hasOwnProperty("onMetaData")){if(null==i.onMetaData||"object"!==a(i.onMetaData))return void l.default.w(this.TAG,"Invalid onMetaData structure!");this._metadata&&l.default.w(this.TAG,"Found another onMetaData tag!"),this._metadata=i;var r=this._metadata.onMetaData;if("boolean"==typeof r.hasAudio&&!1===this._hasAudioFlagOverrided&&(this._hasAudio=r.hasAudio,this._mediaInfo.hasAudio=this._hasAudio),"boolean"==typeof r.hasVideo&&!1===this._hasVideoFlagOverrided&&(this._hasVideo=r.hasVideo,this._mediaInfo.hasVideo=this._hasVideo),"number"==typeof r.audiodatarate&&(this._mediaInfo.audioDataRate=r.audiodatarate),"number"==typeof r.videodatarate&&(this._mediaInfo.videoDataRate=r.videodatarate),"number"==typeof r.width&&(this._mediaInfo.width=r.width),"number"==typeof r.height&&(this._mediaInfo.height=r.height),"number"==typeof r.duration){if(!this._durationOverrided){var s=Math.floor(r.duration*this._timescale);this._duration=s,this._mediaInfo.duration=s}}else this._mediaInfo.duration=0;if("number"==typeof r.framerate){var o=Math.floor(1e3*r.framerate);if(o>0){var u=o/1e3;this._referenceFrameRate.fixed=!0,this._referenceFrameRate.fps=u,this._referenceFrameRate.fps_num=o,this._referenceFrameRate.fps_den=1e3,this._mediaInfo.fps=u}}if("object"===a(r.keyframes)){this._mediaInfo.hasKeyframesIndex=!0;var d=r.keyframes;this._mediaInfo.keyframesIndex=this._parseKeyframesIndex(d),r.keyframes=null}else this._mediaInfo.hasKeyframesIndex=!1;this._dispatch=!1,this._mediaInfo.metadata=r,l.default.v(this.TAG,"Parsed onMetaData"),this._mediaInfo.isComplete()&&this._onMediaInfo(this._mediaInfo)}}},{key:"_parseKeyframesIndex",value:function(e){for(var t=[],n=[],i=1;i>>4;if(2!==a&&10!==a)return void this._onError(m.default.CODEC_UNSUPPORTED,"Flv: Unsupported audio codec idx: "+a);var o=0,u=(12&s)>>>2;if(!(u>=0&&u<=4))return void this._onError(m.default.FORMAT_ERROR,"Flv: Invalid audio sample rate idx: "+u);o=this._flvSoundRateTable[u];var d=1&s,h=this._audioMetadata,f=this._audioTrack;if(h||(!1===this._hasAudio&&!1===this._hasAudioFlagOverrided&&(this._hasAudio=!0,this._mediaInfo.hasAudio=!0),h=this._audioMetadata={},h.type="audio",h.id=f.id,h.timescale=this._timescale,h.duration=this._duration,h.audioSampleRate=o,h.channelCount=0===d?1:2),10===a){var c=this._parseAACAudioData(e,t+1,n-1);if(void 0==c)return;if(0===c.packetType){h.config&&l.default.w(this.TAG,"Found another AudioSpecificConfig!");var _=c.data;h.audioSampleRate=_.samplingRate,h.channelCount=_.channelCount,h.codec=_.codec,h.originalCodec=_.originalCodec,h.config=_.config,h.refSampleDuration=1024/h.audioSampleRate*h.timescale,l.default.v(this.TAG,"Parsed AudioSpecificConfig"),this._isInitialMetadataDispatched()?this._dispatch&&(this._audioTrack.length||this._videoTrack.length)&&this._onDataAvailable(this._audioTrack,this._videoTrack):this._audioInitialMetadataDispatched=!0,this._dispatch=!1,this._onTrackMetadata("audio",h);var p=this._mediaInfo;p.audioCodec=h.originalCodec,p.audioSampleRate=h.audioSampleRate,p.audioChannelCount=h.channelCount,p.hasVideo?null!=p.videoCodec&&(p.mimeType='video/x-flv; codecs="'+p.videoCodec+","+p.audioCodec+'"'):p.mimeType='video/x-flv; codecs="'+p.audioCodec+'"',p.isComplete()&&this._onMediaInfo(p)}else if(1===c.packetType){var v=this._timestampBase+i,g={unit:c.data,length:c.data.byteLength,dts:v,pts:v};f.samples.push(g),f.length+=c.data.length}else l.default.e(this.TAG,"Flv: Unsupported AAC data type "+c.packetType)}else if(2===a){if(!h.codec){var y=this._parseMP3AudioData(e,t+1,n-1,!0);if(void 0==y)return;h.audioSampleRate=y.samplingRate,h.channelCount=y.channelCount,h.codec=y.codec,h.originalCodec=y.originalCodec,h.refSampleDuration=1152/h.audioSampleRate*h.timescale,l.default.v(this.TAG,"Parsed MPEG Audio Frame Header"),this._audioInitialMetadataDispatched=!0,this._onTrackMetadata("audio",h);var E=this._mediaInfo;E.audioCodec=h.codec,E.audioSampleRate=h.audioSampleRate,E.audioChannelCount=h.channelCount,E.audioDataRate=y.bitRate,E.hasVideo?null!=E.videoCodec&&(E.mimeType='video/x-flv; codecs="'+E.videoCodec+","+E.audioCodec+'"'):E.mimeType='video/x-flv; codecs="'+E.audioCodec+'"',E.isComplete()&&this._onMediaInfo(E)}var b=this._parseMP3AudioData(e,t+1,n-1,!1);if(void 0==b)return -;var S=this._timestampBase+i,k={unit:b,length:b.byteLength,dts:S,pts:S};f.samples.push(k),f.length+=b.length}}}},{key:"_parseAACAudioData",value:function(e,t,n){if(n<=1)return void l.default.w(this.TAG,"Flv: Invalid AAC packet, missing AACPacketType or/and Data!");var i={},r=new Uint8Array(e,t,n);return i.packetType=r[0],0===r[0]?i.data=this._parseAACAudioSpecificConfig(e,t+1,n-1):i.data=r.subarray(1),i}},{key:"_parseAACAudioSpecificConfig",value:function(e,t,n){var i=new Uint8Array(e,t,n),r=null,s=0,a=0,o=0,u=null;if(s=a=i[0]>>>3,(o=(7&i[0])<<1|i[1]>>>7)<0||o>=this._mpegSamplingRates.length)return void this._onError(m.default.FORMAT_ERROR,"Flv: AAC invalid sampling frequency index!");var l=this._mpegSamplingRates[o],d=(120&i[1])>>>3;if(d<0||d>=8)return void this._onError(m.default.FORMAT_ERROR,"Flv: AAC invalid channel configuration");5===s&&(u=(7&i[1])<<1|i[2]>>>7,i[2]);var h=self.navigator.userAgent.toLowerCase();return-1!==h.indexOf("firefox")?o>=6?(s=5,r=new Array(4),u=o-3):(s=2,r=new Array(2),u=o):-1!==h.indexOf("android")?(s=2,r=new Array(2),u=o):(s=5,u=o,r=new Array(4),o>=6?u=o-3:1===d&&(s=2,r=new Array(2),u=o)),r[0]=s<<3,r[0]|=(15&o)>>>1,r[1]=(15&o)<<7,r[1]|=(15&d)<<3,5===s&&(r[1]|=(15&u)>>>1,r[2]=(1&u)<<7,r[2]|=8,r[3]=0),{config:r,samplingRate:l,channelCount:d,codec:"mp4a.40."+s,originalCodec:"mp4a.40."+a}}},{key:"_parseMP3AudioData",value:function(e,t,n,i){if(n<4)return void l.default.w(this.TAG,"Flv: Invalid MP3 packet, header missing!");var r=(this._littleEndian,new Uint8Array(e,t,n)),s=null;if(i){if(255!==r[0])return;var a=r[1]>>>3&3,o=(6&r[1])>>1,u=(240&r[2])>>>4,d=(12&r[2])>>>2,h=r[3]>>>6&3,f=3!==h?2:1,c=0,_=0;switch(a){case 0:c=this._mpegAudioV25SampleRateTable[d];break;case 2:c=this._mpegAudioV20SampleRateTable[d];break;case 3:c=this._mpegAudioV10SampleRateTable[d]}switch(o){case 1:34,u>>4,o=15&s;if(7!==o)return void this._onError(m.default.CODEC_UNSUPPORTED,"Flv: Unsupported codec in video frame: "+o);this._parseAVCVideoPacket(e,t+1,n-1,i,r,a)}}},{key:"_parseAVCVideoPacket",value:function(e,t,n,i,r,s){if(n<4)return void l.default.w(this.TAG,"Flv: Invalid AVC packet, missing AVCPacketType or/and CompositionTime");var a=this._littleEndian,o=new DataView(e,t,n),u=o.getUint8(0),d=16777215&o.getUint32(0,!a),h=d<<8>>8;if(0===u)this._parseAVCDecoderConfigurationRecord(e,t+4,n-4);else if(1===u)this._parseAVCVideoData(e,t+4,n-4,i,r,s,h);else if(2!==u)return void this._onError(m.default.FORMAT_ERROR,"Flv: Invalid video packet type "+u)}},{key:"_parseAVCDecoderConfigurationRecord",value:function(e,t,n){if(n<7)return void l.default.w(this.TAG,"Flv: Invalid AVCDecoderConfigurationRecord, lack of data!");var i=this._videoMetadata,r=this._videoTrack,s=this._littleEndian,a=new DataView(e,t,n);i?void 0!==i.avcc&&l.default.w(this.TAG,"Found another AVCDecoderConfigurationRecord!"):(!1===this._hasVideo&&!1===this._hasVideoFlagOverrided&&(this._hasVideo=!0,this._mediaInfo.hasVideo=!0),i=this._videoMetadata={},i.type="video",i.id=r.id,i.timescale=this._timescale,i.duration=this._duration);var o=a.getUint8(0),u=a.getUint8(1);a.getUint8(2),a.getUint8(3);if(1!==o||0===u)return void this._onError(m.default.FORMAT_ERROR,"Flv: Invalid AVCDecoderConfigurationRecord");if(this._naluLengthSize=1+(3&a.getUint8(4)),3!==this._naluLengthSize&&4!==this._naluLengthSize)return void this._onError(m.default.FORMAT_ERROR,"Flv: Strange NaluLengthSizeMinusOne: "+(this._naluLengthSize-1));var d=31&a.getUint8(5);if(0===d)return void this._onError(m.default.FORMAT_ERROR,"Flv: Invalid AVCDecoderConfigurationRecord: No SPS");d>1&&l.default.w(this.TAG,"Flv: Strange AVCDecoderConfigurationRecord: SPS Count = "+d);for(var h=6,f=0;f1&&l.default.w(this.TAG,"Flv: Strange AVCDecoderConfigurationRecord: PPS Count = "+w),h++;for(var R=0;R=n){l.default.w(this.TAG,"Malformed Nalu near timestamp "+_+", offset = "+f+", dataSize = "+n);break}var p=u.getUint32(f,!o);if(3===c&&(p>>>=8),p>n-c)return void l.default.w(this.TAG,"Malformed Nalus near timestamp "+_+", NaluSize > DataSize!");var v=31&u.getUint8(f+c);5===v&&(m=!0);var g=new Uint8Array(e,t+f,c+p),y={type:v,data:g};d.push(y),h+=g.byteLength,f+=c+p}if(d.length){var E=this._videoTrack,b={units:d,length:h,isKeyframe:m,dts:_,cts:a,pts:_+a};m&&(b.fileposition=r),E.samples.push(b),E.length+=h}}},{key:"onTrackMetadata",get:function(){return this._onTrackMetadata},set:function(e){this._onTrackMetadata=e}},{key:"onMediaInfo",get:function(){return this._onMediaInfo},set:function(e){this._onMediaInfo=e}},{key:"onError",get:function(){return this._onError},set:function(e){this._onError=e}},{key:"onDataAvailable",get:function(){return this._onDataAvailable},set:function(e){this._onDataAvailable=e}},{key:"timestampBase",get:function(){return this._timestampBase},set:function(e){this._timestampBase=e}},{key:"overridedDuration",get:function(){return this._duration},set:function(e){this._durationOverrided=!0,this._duration=e,this._mediaInfo.duration=e}},{key:"overridedHasAudio",set:function(e){this._hasAudioFlagOverrided=!0,this._hasAudio=e,this._mediaInfo.hasAudio=e}},{key:"overridedHasVideo",set:function(e){this._hasVideoFlagOverrided=!0,this._hasVideo=e,this._mediaInfo.hasVideo=e}}],[{key:"probe",value:function(e){var t=new Uint8Array(e),n={match:!1};if(70!==t[0]||76!==t[1]||86!==t[2]||1!==t[3])return n;var i=(4&t[4])>>>2!=0,r=0!=(1&t[4]),a=s(t,5);return a<9?n:{match:!0,consumed:a,dataOffset:a,hasAudioTrack:i,hasVideoTrack:r}}}]),e}();n.default=y},{"../core/media-info.js":7,"../utils/exception.js":40,"../utils/logger.js":41,"./amf-parser.js":15,"./demux-errors.js":16,"./sps-parser.js":19}],19:[function(e,t,n){"use strict";function i(e,t){if(!(e instanceof t))throw new TypeError("Cannot call a class as a function")}Object.defineProperty(n,"__esModule",{value:!0});var r=function(){function e(e,t){for(var n=0;n=2&&3===t[s]&&0===t[s-1]&&0===t[s-2]||(i[r]=t[s],r++);return new Uint8Array(i.buffer,0,r)}},{key:"parseSPS",value:function(t){var n=e._ebsp2rbsp(t),i=new a.default(n);i.readByte();var r=i.readByte();i.readByte();var s=i.readByte();i.readUEG();var o=e.getProfileString(r),u=e.getLevelString(s),l=1,d=420,h=[0,420,422,444],f=8;if((100===r||110===r||122===r||244===r||44===r||83===r||86===r||118===r||128===r||138===r||144===r)&&(l=i.readUEG(),3===l&&i.readBits(1),l<=3&&(d=h[l]),f=i.readUEG()+8,i.readUEG(),i.readBits(1),i.readBool()))for(var c=3!==l?8:12,_=0;_0&&x<16?(R=M[x-1],A=D[x-1]):255===x&&(R=i.readByte()<<8|i.readByte(),A=i.readByte()<<8|i.readByte())}if(i.readBool()&&i.readBool(),i.readBool()&&(i.readBits(4),i.readBool()&&i.readBits(24)),i.readBool()&&(i.readUEG(),i.readUEG()),i.readBool()){var B=i.readBits(32),j=i.readBits(32);T=i.readBool(),C=j,I=2*B,O=C/I}}var P=1;1===R&&1===A||(P=R/A);var U=0,N=0;if(0===l)U=1,N=2-b;else{var F=3===l?1:2,G=1===l?2:1;U=F,N=G*(2-b)}var V=16*(y+1),z=16*(E+1)*(2-b);V-=(S+k)*U,z-=(L+w)*N;var H=Math.ceil(V*P);return i.destroy(),i=null,{profile_string:o,level_string:u,bit_depth:f,ref_frames:g,chroma_format:d,chroma_format_string:e.getChromaFormatString(d),frame_rate:{fixed:T,fps:O,fps_den:I,fps_num:C},sar_ratio:{width:R,height:A},codec_size:{width:V,height:z},present_size:{width:H,height:z}}}},{key:"_skipScalingList",value:function(e,t){for(var n=8,i=8,r=0,s=0;s=15048,t=!f.default.msedge||e;return self.fetch&&self.ReadableStream&&t}catch(e){return!1}}}]),l(t,[{key:"destroy",value:function(){this.isWorking()&&this.abort(),u(t.prototype.__proto__||Object.getPrototypeOf(t.prototype),"destroy",this).call(this)}},{key:"open",value:function(e,t){var n=this;this._dataSource=e,this._range=t;var i=e.url;this._config.reuseRedirectedURL&&void 0!=e.redirectedURL&&(i=e.redirectedURL);var r=this._seekHandler.getConfig(i,t),s=new self.Headers;if("object"===o(r.headers)){var a=r.headers;for(var u in a)a.hasOwnProperty(u)&&s.append(u,a[u])}var l={method:"GET",headers:s,mode:"cors",cache:"default",referrerPolicy:"no-referrer-when-downgrade"};!1===e.cors&&(l.mode="same-origin"),e.withCredentials&&(l.credentials="include"),e.referrerPolicy&&(l.referrerPolicy=e.referrerPolicy),this._status=c.LoaderStatus.kConnecting,self.fetch(r.url,l).then(function(e){if(n._requestAbort)return n._requestAbort=!1,void(n._status=c.LoaderStatus.kIdle);if(e.ok&&e.status>=200&&e.status<=299){if(e.url!==r.url&&n._onURLRedirect){var t=n._seekHandler.removeURLParameters(e.url);n._onURLRedirect(t)}var i=e.headers.get("Content-Length");return null!=i&&(n._contentLength=parseInt(i),0!==n._contentLength&&n._onContentLengthKnown&&n._onContentLengthKnown(n._contentLength)),n._pump.call(n,e.body.getReader())}if(n._status=c.LoaderStatus.kError,!n._onError)throw new _.RuntimeException("FetchStreamLoader: Http code invalid, "+e.status+" "+e.statusText);n._onError(c.LoaderErrors.HTTP_STATUS_CODE_INVALID,{code:e.status,msg:e.statusText})}).catch(function(e){if(n._status=c.LoaderStatus.kError,!n._onError)throw e;n._onError(c.LoaderErrors.EXCEPTION,{code:-1,msg:e.message})})}},{key:"abort",value:function(){this._requestAbort=!0}},{key:"_pump",value:function(e){var t=this;return e.read().then(function(n){if(n.done)if(null!==t._contentLength&&t._receivedLength0&&(this._stashInitialSize=n.stashInitialSize),this._stashUsed=0,this._stashSize=this._stashInitialSize,this._bufferSize=3145728,this._stashBuffer=new ArrayBuffer(this._bufferSize),this._stashByteStart=0,this._enableStash=!0,!1===n.enableStashBuffer&&(this._enableStash=!1),this._loader=null,this._loaderClass=null,this._seekHandler=null,this._dataSource=t,this._isWebSocketURL=/wss?:\/\/(.+?)/.test(t.url),this._refTotalLength=t.filesize?t.filesize:null,this._totalLength=this._refTotalLength,this._fullRequestFlag=!1,this._currentRange=null,this._redirectedURL=null,this._speedNormalized=0,this._speedSampler=new l.default,this._speedNormalizeList=[64,128,256,384,512,768,1024,1536,2048,3072,4096],this._isEarlyEofReconnecting=!1,this._paused=!1,this._resumeFrom=0,this._onDataArrival=null,this._onSeeked=null,this._onError=null,this._onComplete=null,this._onRedirect=null,this._onRecoveredEarlyEof=null,this._selectSeekHandler(),this._selectLoader(),this._createLoader()}return s(e,[{key:"destroy",value:function(){this._loader.isWorking()&&this._loader.abort(),this._loader.destroy(),this._loader=null,this._loaderClass=null,this._dataSource=null,this._stashBuffer=null,this._stashUsed=this._stashSize=this._bufferSize=this._stashByteStart=0,this._currentRange=null,this._speedSampler=null,this._isEarlyEofReconnecting=!1,this._onDataArrival=null,this._onSeeked=null,this._onError=null,this._onComplete=null,this._onRedirect=null,this._onRecoveredEarlyEof=null,this._extraData=null}},{key:"isWorking",value:function(){return this._loader&&this._loader.isWorking()&&!this._paused}},{key:"isPaused",value:function(){return this._paused}},{key:"_selectSeekHandler",value:function(){var e=this._config;if("range"===e.seekType)this._seekHandler=new b.default(this._config.rangeLoadZeroStart);else if("param"===e.seekType){var t=e.seekParamStart||"bstart",n=e.seekParamEnd||"bend";this._seekHandler=new k.default(t,n)}else{if("custom"!==e.seekType)throw new L.InvalidArgumentException("Invalid seekType in config: "+e.seekType);if("function"!=typeof e.customSeekHandler)throw new L.InvalidArgumentException("Custom seekType specified in config but invalid customSeekHandler!");this._seekHandler=new e.customSeekHandler}}},{key:"_selectLoader",value:function(){if(this._isWebSocketURL)this._loaderClass=y.default;else if(f.default.isSupported())this._loaderClass=f.default;else if(_.default.isSupported())this._loaderClass=_.default;else{if(!v.default.isSupported())throw new L.RuntimeException("Your browser doesn't support xhr with arraybuffer responseType!");this._loaderClass=v.default}}},{key:"_createLoader",value:function(){this._loader=new this._loaderClass(this._seekHandler,this._config),!1===this._loader.needStashBuffer&&(this._enableStash=!1),this._loader.onContentLengthKnown=this._onContentLengthKnown.bind(this),this._loader.onURLRedirect=this._onURLRedirect.bind(this),this._loader.onDataArrival=this._onLoaderChunkArrival.bind(this),this._loader.onComplete=this._onLoaderComplete.bind(this),this._loader.onError=this._onLoaderError.bind(this)}},{key:"open",value:function(e){this._currentRange={from:0,to:-1},e&&(this._currentRange.from=e),this._speedSampler.reset(),e||(this._fullRequestFlag=!0),this._loader.open(this._dataSource,Object.assign({},this._currentRange))}},{key:"abort",value:function(){this._loader.abort(),this._paused&&(this._paused=!1,this._resumeFrom=0)}},{key:"pause",value:function(){this.isWorking()&&(this._loader.abort(),0!==this._stashUsed?(this._resumeFrom=this._stashByteStart,this._currentRange.to=this._stashByteStart-1):this._resumeFrom=this._currentRange.to+1,this._stashUsed=0,this._stashByteStart=0,this._paused=!0)}},{key:"resume",value:function(){if(this._paused){this._paused=!1;var e=this._resumeFrom;this._resumeFrom=0,this._internalSeek(e,!0)}}},{key:"seek",value:function(e){this._paused=!1,this._stashUsed=0,this._stashByteStart=0,this._internalSeek(e,!0)}},{key:"_internalSeek",value:function(e,t){this._loader.isWorking()&&this._loader.abort(),this._flushStashBuffer(t),this._loader.destroy(),this._loader=null;var n={from:e,to:-1};this._currentRange={from:n.from,to:-1},this._speedSampler.reset(),this._stashSize=this._stashInitialSize,this._createLoader(),this._loader.open(this._dataSource,n),this._onSeeked&&this._onSeeked()}},{key:"updateUrl",value:function(e){if(!e||"string"!=typeof e||0===e.length)throw new L.InvalidArgumentException("Url must be a non-empty string!");this._dataSource.url=e}},{key:"_expandBuffer",value:function(e){for(var t=this._stashSize;t+10485760){var i=new Uint8Array(this._stashBuffer,0,this._stashUsed);new Uint8Array(n,0,t).set(i,0)}this._stashBuffer=n,this._bufferSize=t}}},{key:"_normalizeSpeed",value:function(e){var t=this._speedNormalizeList,n=t.length-1,i=0,r=0,s=n;if(e=t[i]&&e=512&&e<=1024?Math.floor(1.5*e):2*e)>8192&&(t=8192);var n=1024*t+1048576;this._bufferSize0){var o=this._stashBuffer.slice(0,this._stashUsed),u=this._dispatchChunks(o,this._stashByteStart);if(u0){var l=new Uint8Array(o,u);a.set(l,0),this._stashUsed=l.byteLength,this._stashByteStart+=u}}else this._stashUsed=0,this._stashByteStart+=u;this._stashUsed+e.byteLength>this._bufferSize&&(this._expandBuffer(this._stashUsed+e.byteLength),a=new Uint8Array(this._stashBuffer,0,this._bufferSize)),a.set(new Uint8Array(e),this._stashUsed),this._stashUsed+=e.byteLength}else{var d=this._dispatchChunks(e,t);if(dthis._bufferSize&&(this._expandBuffer(h),a=new Uint8Array(this._stashBuffer,0,this._bufferSize)),a.set(new Uint8Array(e,d),0),this._stashUsed+=h,this._stashByteStart=t+d}}}else if(0===this._stashUsed){var f=this._dispatchChunks(e,t);if(fthis._bufferSize&&this._expandBuffer(c);var _=new Uint8Array(this._stashBuffer,0,this._bufferSize);_.set(new Uint8Array(e,f),0),this._stashUsed+=c,this._stashByteStart=t+f}}else{this._stashUsed+e.byteLength>this._bufferSize&&this._expandBuffer(this._stashUsed+e.byteLength);var m=new Uint8Array(this._stashBuffer,0,this._bufferSize);m.set(new Uint8Array(e),this._stashUsed),this._stashUsed+=e.byteLength;var p=this._dispatchChunks(this._stashBuffer.slice(0,this._stashUsed),this._stashByteStart);if(p0){var v=new Uint8Array(this._stashBuffer,p);m.set(v,0)}this._stashUsed-=p,this._stashByteStart+=p}}}},{key:"_flushStashBuffer",value:function(e){if(this._stashUsed>0){var t=this._stashBuffer.slice(0,this._stashUsed),n=this._dispatchChunks(t,this._stashByteStart),i=t.byteLength-n;if(n0){var r=new Uint8Array(this._stashBuffer,0,this._bufferSize),s=new Uint8Array(t,n);r.set(s,0),this._stashUsed=s.byteLength,this._stashByteStart+=n}return 0}o.default.w(this.TAG,i+" bytes unconsumed data remain when flush buffer, dropped")}return this._stashUsed=0,this._stashByteStart=0,i}return 0}},{key:"_onLoaderComplete",value:function(e,t){this._flushStashBuffer(!0),this._onComplete&&this._onComplete(this._extraData)}},{key:"_onLoaderError",value:function(e,t){switch(o.default.e(this.TAG,"Loader error, code = "+t.code+", msg = "+t.msg),this._flushStashBuffer(!1),this._isEarlyEofReconnecting&&(this._isEarlyEofReconnecting=!1,e=d.LoaderErrors.UNRECOVERABLE_EARLY_EOF),e){case d.LoaderErrors.EARLY_EOF:if(!this._config.isLive&&this._totalLength){var n=this._currentRange.to+1;return void(n0)for(var s=n.split("&"),a=0;a0;o[0]!==this._startName&&o[0]!==this._endName&&(u&&(r+="&"),r+=s[a])}return 0===r.length?t:t+"?"+r}}]),e}();n.default=s},{}],26:[function(e,t,n){"use strict";function i(e,t){if(!(e instanceof t))throw new TypeError("Cannot call a class as a function")}Object.defineProperty(n,"__esModule",{value:!0});var r=function(){function e(e,t){for(var n=0;n=500?this.currentKBps:0}},{key:"averageKBps",get:function(){var e=(this._now()-this._firstCheckpoint)/1e3;return this._totalBytes/e/1024}}]),e}();n.default=s},{}],28:[function(e,t,n){"use strict";function i(e,t){if(!(e instanceof t))throw new TypeError("Cannot call a class as a function")}function r(e,t){if(!e)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!t||"object"!=typeof t&&"function"!=typeof t?e:t}function s(e,t){if("function"!=typeof t&&null!==t)throw new TypeError("Super expression must either be null or a function, not "+typeof t);e.prototype=Object.create(t&&t.prototype,{constructor:{value:e,enumerable:!1,writable:!0,configurable:!0}}),t&&(Object.setPrototypeOf?Object.setPrototypeOf(e,t):e.__proto__=t)}Object.defineProperty(n,"__esModule",{value:!0});var a=function e(t,n,i){null===t&&(t=Function.prototype);var r=Object.getOwnPropertyDescriptor(t,n);if(void 0===r){var s=Object.getPrototypeOf(t);return null===s?void 0:e(s,n,i)}if("value"in r)return r.value;var a=r.get;if(void 0!==a)return a.call(i)},o=function(){function e(e,t){for(var n=0;n299)){if(this._status=h.LoaderStatus.kError,!this._onError)throw new f.RuntimeException("MozChunkedLoader: Http code invalid, "+t.status+" "+t.statusText);this._onError(h.LoaderErrors.HTTP_STATUS_CODE_INVALID,{code:t.status,msg:t.statusText})}else this._status=h.LoaderStatus.kBuffering}}},{key:"_onProgress",value:function(e){if(this._status!==h.LoaderStatus.kError){null===this._contentLength&&null!==e.total&&0!==e.total&&(this._contentLength=e.total,this._onContentLengthKnown&&this._onContentLengthKnown(this._contentLength));var t=e.target.response,n=this._range.from+this._receivedLength;this._receivedLength+=t.byteLength,this._onDataArrival&&this._onDataArrival(t,n,this._receivedLength)}}},{key:"_onLoadEnd",value:function(e){if(!0===this._requestAbort)return void(this._requestAbort=!1);this._status!==h.LoaderStatus.kError&&(this._status=h.LoaderStatus.kComplete,this._onComplete&&this._onComplete(this._range.from,this._range.from+this._receivedLength-1))}},{key:"_onXhrError",value:function(e){this._status=h.LoaderStatus.kError;var t=0,n=null;if(this._contentLength&&e.loaded=200&&t.status<=299){if(this._status=h.LoaderStatus.kBuffering,void 0!=t.responseURL){var n=this._seekHandler.removeURLParameters(t.responseURL);t.responseURL!==this._currentRequestURL&&n!==this._currentRedirectedURL&&(this._currentRedirectedURL=n,this._onURLRedirect&&this._onURLRedirect(n))}var i=t.getResponseHeader("Content-Length");if(null!=i&&null==this._contentLength){var r=parseInt(i);r>0&&(this._contentLength=r,this._onContentLengthKnown&&this._onContentLengthKnown(this._contentLength))}}else{if(this._status=h.LoaderStatus.kError,!this._onError)throw new f.RuntimeException("MSStreamLoader: Http code invalid, "+t.status+" "+t.statusText);this._onError(h.LoaderErrors.HTTP_STATUS_CODE_INVALID,{code:t.status,msg:t.statusText})}else if(3===t.readyState&&t.status>=200&&t.status<=299){this._status=h.LoaderStatus.kBuffering;var s=t.response;this._reader.readAsArrayBuffer(s)}}},{key:"_xhrOnError",value:function(e){this._status=h.LoaderStatus.kError;var t=h.LoaderErrors.EXCEPTION,n={code:-1,msg:e.constructor.name+" "+e.type};if(!this._onError)throw new f.RuntimeException(n.msg);this._onError(t,n)}},{key:"_msrOnProgress",value:function(e){var t=e.target,n=t.result;if(null==n)return void this._doReconnectIfNeeded();var i=n.slice(this._lastTimeBufferSize);this._lastTimeBufferSize=n.byteLength;var r=this._totalRange.from+this._receivedLength;this._receivedLength+=i.byteLength,this._onDataArrival&&this._onDataArrival(i,r,this._receivedLength),n.byteLength>=this._bufferLimit&&(d.default.v(this.TAG,"MSStream buffer exceeded max size near "+(r+i.byteLength)+", reconnecting..."),this._doReconnectIfNeeded())}},{key:"_doReconnectIfNeeded",value:function(){if(null==this._contentLength||this._receivedLength=this._contentLength&&(n=this._range.from+this._contentLength-1),this._currentRequestRange={from:t,to:n},this._internalOpen(this._dataSource,this._currentRequestRange)}},{key:"_internalOpen",value:function(e,t){this._lastTimeLoaded=0;var n=e.url;this._config.reuseRedirectedURL&&(void 0!=this._currentRedirectedURL?n=this._currentRedirectedURL:void 0!=e.redirectedURL&&(n=e.redirectedURL));var i=this._seekHandler.getConfig(n,t);this._currentRequestURL=i.url;var r=this._xhr=new XMLHttpRequest;if(r.open("GET",i.url,!0),r.responseType="arraybuffer",r.onreadystatechange=this._onReadyStateChange.bind(this),r.onprogress=this._onProgress.bind(this),r.onload=this._onLoad.bind(this),r.onerror=this._onXhrError.bind(this),e.withCredentials&&(r.withCredentials=!0),"object"===o(i.headers)){var s=i.headers;for(var a in s)s.hasOwnProperty(a)&&r.setRequestHeader(a,s[a])}r.send()}},{key:"abort",value:function(){this._requestAbort=!0,this._internalAbort(),this._status=_.LoaderStatus.kComplete}},{key:"_internalAbort",value:function(){this._xhr&&(this._xhr.onreadystatechange=null,this._xhr.onprogress=null,this._xhr.onload=null,this._xhr.onerror=null,this._xhr.abort(),this._xhr=null)}},{key:"_onReadyStateChange",value:function(e){var t=e.target;if(2===t.readyState){if(void 0!=t.responseURL){var n=this._seekHandler.removeURLParameters(t.responseURL);t.responseURL!==this._currentRequestURL&&n!==this._currentRedirectedURL&&(this._currentRedirectedURL=n,this._onURLRedirect&&this._onURLRedirect(n))}if(t.status>=200&&t.status<=299){if(this._waitForTotalLength)return;this._status=_.LoaderStatus.kBuffering}else{if(this._status=_.LoaderStatus.kError,!this._onError)throw new m.RuntimeException("RangeLoader: Http code invalid, "+t.status+" "+t.statusText);this._onError(_.LoaderErrors.HTTP_STATUS_CODE_INVALID,{code:t.status,msg:t.statusText})}}}},{key:"_onProgress",value:function(e){if(this._status!==_.LoaderStatus.kError){if(null===this._contentLength){var t=!1;if(this._waitForTotalLength){this._waitForTotalLength=!1,this._totalLengthReceived=!0,t=!0;var n=e.total;this._internalAbort(),null!=n&0!==n&&(this._totalLength=n)}if(-1===this._range.to?this._contentLength=this._totalLength-this._range.from:this._contentLength=this._range.to-this._range.from+1,t)return void this._openSubRange();this._onContentLengthKnown&&this._onContentLengthKnown(this._contentLength)}var i=e.loaded-this._lastTimeLoaded;this._lastTimeLoaded=e.loaded,this._speedSampler.addBytes(i)}}},{key:"_normalizeSpeed",value:function(e){var t=this._chunkSizeKBList,n=t.length-1,i=0,r=0,s=n;if(e=t[i]&&e=3&&(t=this._speedSampler.currentKBps),0!==t){var n=this._normalizeSpeed(t);this._currentSpeedNormalized!==n&&(this._currentSpeedNormalized=n,this._currentChunkSizeKB=n)}var i=e.target.response,r=this._range.from+this._receivedLength;this._receivedLength+=i.byteLength;var s=!1;null!=this._contentLength&&this._receivedLength0&&this._receivedLength0&&(this._requestSetTime=!0,this._mediaElement.currentTime=0),this._transmuxer=new p.default(this._mediaDataSource,this._config),this._transmuxer.on(g.default.INIT_SEGMENT,function(t,n){e._msectl.appendInitSegment(n)}),this._transmuxer.on(g.default.MEDIA_SEGMENT,function(t,n){if(e._msectl.appendMediaSegment(n),e._config.lazyLoad&&!e._config.isLive){var i=e._mediaElement.currentTime;n.info.endDts>=1e3*(i+e._config.lazyLoadMaxDuration)&&null==e._progressChecker&&(d.default.v(e.TAG,"Maximum buffering duration exceeded, suspend transmuxing task"),e._suspendTransmuxer())}}),this._transmuxer.on(g.default.LOADING_COMPLETE,function(){e._msectl.endOfStream(),e._emitter.emit(_.default.LOADING_COMPLETE)}), -this._transmuxer.on(g.default.RECOVERED_EARLY_EOF,function(){e._emitter.emit(_.default.RECOVERED_EARLY_EOF)}),this._transmuxer.on(g.default.IO_ERROR,function(t,n){e._emitter.emit(_.default.ERROR,k.ErrorTypes.NETWORK_ERROR,t,n)}),this._transmuxer.on(g.default.DEMUX_ERROR,function(t,n){e._emitter.emit(_.default.ERROR,k.ErrorTypes.MEDIA_ERROR,t,{code:-1,msg:n})}),this._transmuxer.on(g.default.MEDIA_INFO,function(t){e._mediaInfo=t,e._emitter.emit(_.default.MEDIA_INFO,Object.assign({},t))}),this._transmuxer.on(g.default.STATISTICS_INFO,function(t){e._statisticsInfo=e._fillStatisticsInfo(t),e._emitter.emit(_.default.STATISTICS_INFO,Object.assign({},e._statisticsInfo))}),this._transmuxer.on(g.default.RECOMMEND_SEEKPOINT,function(t){e._mediaElement&&!e._config.accurateSeek&&(e._requestSetTime=!0,e._mediaElement.currentTime=t/1e3)}),this._transmuxer.open()}}},{key:"unload",value:function(){this._mediaElement&&this._mediaElement.pause(),this._msectl&&this._msectl.seek(0),this._transmuxer&&(this._transmuxer.close(),this._transmuxer.destroy(),this._transmuxer=null)}},{key:"play",value:function(){return this._mediaElement.play()}},{key:"pause",value:function(){this._mediaElement.pause()}},{key:"_fillStatisticsInfo",value:function(e){if(e.playerType=this._type,!(this._mediaElement instanceof HTMLVideoElement))return e;var t=!0,n=0,i=0;if(this._mediaElement.getVideoPlaybackQuality){var r=this._mediaElement.getVideoPlaybackQuality();n=r.totalVideoFrames,i=r.droppedVideoFrames}else void 0!=this._mediaElement.webkitDecodedFrameCount?(n=this._mediaElement.webkitDecodedFrameCount,i=this._mediaElement.webkitDroppedFrameCount):t=!1;return t&&(e.decodedFrames=n,e.droppedFrames=i),e}},{key:"_onmseUpdateEnd",value:function(){if(this._config.lazyLoad&&!this._config.isLive){for(var e=this._mediaElement.buffered,t=this._mediaElement.currentTime,n=0,i=0;i=t+this._config.lazyLoadMaxDuration&&null==this._progressChecker&&(d.default.v(this.TAG,"Maximum buffering duration exceeded, suspend transmuxing task"),this._suspendTransmuxer())}}},{key:"_onmseBufferFull",value:function(){d.default.v(this.TAG,"MSE SourceBuffer is full, suspend transmuxing task"),null==this._progressChecker&&this._suspendTransmuxer()}},{key:"_suspendTransmuxer",value:function(){this._transmuxer&&(this._transmuxer.pause(),null==this._progressChecker&&(this._progressChecker=window.setInterval(this._checkProgressAndResume.bind(this),1e3)))}},{key:"_checkProgressAndResume",value:function(){for(var e=this._mediaElement.currentTime,t=this._mediaElement.buffered,n=!1,i=0;i=r&&e=s-this._config.lazyLoadRecoverDuration&&(n=!0);break}}n&&(window.clearInterval(this._progressChecker),this._progressChecker=null,n&&(d.default.v(this.TAG,"Continue loading from paused position"),this._transmuxer.resume()))}},{key:"_isTimepointBuffered",value:function(e){for(var t=this._mediaElement.buffered,n=0;n=i&&e0){var r=this._mediaElement.buffered.start(0);(r<1&&e0&&t.currentTime0){var i=n.start(0);if(i<1&&t0&&(this._mediaElement.currentTime=0),this._mediaElement.preload="auto",this._mediaElement.load(),this._statisticsReporter=window.setInterval(this._reportStatisticsInfo.bind(this),this._config.statisticsInfoReportInterval)}},{key:"unload",value:function(){this._mediaElement&&(this._mediaElement.src="",this._mediaElement.removeAttribute("src")),null!=this._statisticsReporter&&(window.clearInterval(this._statisticsReporter),this._statisticsReporter=null)}},{key:"play",value:function(){return this._mediaElement.play()}},{key:"pause",value:function(){this._mediaElement.pause()}},{key:"_onvLoadedMetadata",value:function(e){null!=this._pendingSeekTime&&(this._mediaElement.currentTime=this._pendingSeekTime,this._pendingSeekTime=null),this._emitter.emit(d.default.MEDIA_INFO,this.mediaInfo)}},{key:"_reportStatisticsInfo",value:function(){this._emitter.emit(d.default.STATISTICS_INFO,this.statisticsInfo)}},{key:"type",get:function(){return this._type}},{key:"buffered",get:function(){return this._mediaElement.buffered}},{key:"duration",get:function(){return this._mediaElement.duration}},{key:"volume",get:function(){return this._mediaElement.volume},set:function(e){this._mediaElement.volume=e}},{key:"muted",get:function(){return this._mediaElement.muted},set:function(e){this._mediaElement.muted=e}},{key:"currentTime",get:function(){return this._mediaElement?this._mediaElement.currentTime:0},set:function(e){this._mediaElement?this._mediaElement.currentTime=e:this._pendingSeekTime=e}},{key:"mediaInfo",get:function(){var e=this._mediaElement instanceof HTMLAudioElement?"audio/":"video/",t={mimeType:e+this._mediaDataSource.type};return this._mediaElement&&(t.duration=Math.floor(1e3*this._mediaElement.duration),this._mediaElement instanceof HTMLVideoElement&&(t.width=this._mediaElement.videoWidth,t.height=this._mediaElement.videoHeight)),t}},{key:"statisticsInfo",get:function(){var e={playerType:this._type,url:this._mediaDataSource.url};if(!(this._mediaElement instanceof HTMLVideoElement))return e;var t=!0,n=0,i=0;if(this._mediaElement.getVideoPlaybackQuality){var r=this._mediaElement.getVideoPlaybackQuality();n=r.totalVideoFrames,i=r.droppedVideoFrames}else void 0!=this._mediaElement.webkitDecodedFrameCount?(n=this._mediaElement.webkitDecodedFrameCount,i=this._mediaElement.webkitDroppedFrameCount):t=!1;return t&&(e.decodedFrames=n,e.droppedFrames=i),e}}]),e}();n.default=c},{"../config.js":5,"../utils/exception.js":40,"./player-events.js":35,events:2}],34:[function(e,t,n){"use strict";Object.defineProperty(n,"__esModule",{value:!0}),n.ErrorDetails=n.ErrorTypes=void 0;var i=e("../io/loader.js"),r=e("../demux/demux-errors.js"),s=function(e){return e&&e.__esModule?e:{default:e}}(r);n.ErrorTypes={NETWORK_ERROR:"NetworkError",MEDIA_ERROR:"MediaError",OTHER_ERROR:"OtherError"},n.ErrorDetails={NETWORK_EXCEPTION:i.LoaderErrors.EXCEPTION,NETWORK_STATUS_CODE_INVALID:i.LoaderErrors.HTTP_STATUS_CODE_INVALID,NETWORK_TIMEOUT:i.LoaderErrors.CONNECTING_TIMEOUT,NETWORK_UNRECOVERABLE_EARLY_EOF:i.LoaderErrors.UNRECOVERABLE_EARLY_EOF,MEDIA_MSE_ERROR:"MediaMSEError",MEDIA_FORMAT_ERROR:s.default.FORMAT_ERROR,MEDIA_FORMAT_UNSUPPORTED:s.default.FORMAT_UNSUPPORTED,MEDIA_CODEC_UNSUPPORTED:s.default.CODEC_UNSUPPORTED}},{"../demux/demux-errors.js":16,"../io/loader.js":24}],35:[function(e,t,n){"use strict";Object.defineProperty(n,"__esModule",{value:!0});var i={ERROR:"error",LOADING_COMPLETE:"loading_complete",RECOVERED_EARLY_EOF:"recovered_early_eof",MEDIA_INFO:"media_info",STATISTICS_INFO:"statistics_info"};n.default=i},{}],36:[function(e,t,n){"use strict";function i(e,t){if(!(e instanceof t))throw new TypeError("Cannot call a class as a function")}Object.defineProperty(n,"__esModule",{value:!0});var r=function(){function e(e,t){for(var n=0;n>>24&255,n[1]=t>>>16&255,n[2]=t>>>8&255,n[3]=255&t,n.set(e,4);for(var a=8,o=0;o>>24&255,t>>>16&255,t>>>8&255,255&t,n>>>24&255,n>>>16&255,n>>>8&255,255&n,0,1,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,64,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,255,255,255,255]))}},{key:"trak",value:function(t){return e.box(e.types.trak,e.tkhd(t),e.mdia(t))}},{key:"tkhd",value:function(t){var n=t.id,i=t.duration,r=t.presentWidth,s=t.presentHeight;return e.box(e.types.tkhd,new Uint8Array([0,0,0,7,0,0,0,0,0,0,0,0,n>>>24&255,n>>>16&255,n>>>8&255,255&n,0,0,0,0,i>>>24&255,i>>>16&255,i>>>8&255,255&i,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,64,0,0,0,r>>>8&255,255&r,0,0,s>>>8&255,255&s,0,0]))}},{key:"mdia",value:function(t){return e.box(e.types.mdia,e.mdhd(t),e.hdlr(t),e.minf(t))}},{key:"mdhd",value:function(t){var n=t.timescale,i=t.duration;return e.box(e.types.mdhd,new Uint8Array([0,0,0,0,0,0,0,0,0,0,0,0,n>>>24&255,n>>>16&255,n>>>8&255,255&n,i>>>24&255,i>>>16&255,i>>>8&255,255&i,85,196,0,0]))}},{key:"hdlr",value:function(t){var n=null;return n="audio"===t.type?e.constants.HDLR_AUDIO:e.constants.HDLR_VIDEO,e.box(e.types.hdlr,n)}},{key:"minf",value:function(t){var n=null;return n="audio"===t.type?e.box(e.types.smhd,e.constants.SMHD):e.box(e.types.vmhd,e.constants.VMHD),e.box(e.types.minf,n,e.dinf(),e.stbl(t))}},{key:"dinf",value:function(){return e.box(e.types.dinf,e.box(e.types.dref,e.constants.DREF))}},{key:"stbl",value:function(t){return e.box(e.types.stbl,e.stsd(t),e.box(e.types.stts,e.constants.STTS),e.box(e.types.stsc,e.constants.STSC),e.box(e.types.stsz,e.constants.STSZ),e.box(e.types.stco,e.constants.STCO))}},{key:"stsd",value:function(t){return"audio"===t.type?"mp3"===t.codec?e.box(e.types.stsd,e.constants.STSD_PREFIX,e.mp3(t)):e.box(e.types.stsd,e.constants.STSD_PREFIX,e.mp4a(t)):e.box(e.types.stsd,e.constants.STSD_PREFIX,e.avc1(t))}},{key:"mp3",value:function(t){var n=t.channelCount,i=t.audioSampleRate,r=new Uint8Array([0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,n,0,16,0,0,0,0,i>>>8&255,255&i,0,0]);return e.box(e.types[".mp3"],r)}},{key:"mp4a",value:function(t){var n=t.channelCount,i=t.audioSampleRate,r=new Uint8Array([0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,n,0,16,0,0,0,0,i>>>8&255,255&i,0,0]);return e.box(e.types.mp4a,r,e.esds(t))}},{key:"esds",value:function(t){var n=t.config||[],i=n.length,r=new Uint8Array([0,0,0,0,3,23+i,0,1,0,4,15+i,64,21,0,0,0,0,0,0,0,0,0,0,0,5].concat([i]).concat(n).concat([6,1,2]));return e.box(e.types.esds,r)}},{key:"avc1",value:function(t){var n=t.avcc,i=t.codecWidth,r=t.codecHeight,s=new Uint8Array([0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,i>>>8&255,255&i,r>>>8&255,255&r,0,72,0,0,0,72,0,0,0,0,0,0,0,1,10,120,113,113,47,102,108,118,46,106,115,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,24,255,255]);return e.box(e.types.avc1,s,e.box(e.types.avcC,n))}},{key:"mvex",value:function(t){return e.box(e.types.mvex,e.trex(t))}},{key:"trex",value:function(t){var n=t.id,i=new Uint8Array([0,0,0,0,n>>>24&255,n>>>16&255,n>>>8&255,255&n,0,0,0,1,0,0,0,0,0,0,0,0,0,1,0,1]);return e.box(e.types.trex,i)}},{key:"moof",value:function(t,n){return e.box(e.types.moof,e.mfhd(t.sequenceNumber),e.traf(t,n))}},{key:"mfhd",value:function(t){var n=new Uint8Array([0,0,0,0,t>>>24&255,t>>>16&255,t>>>8&255,255&t]);return e.box(e.types.mfhd,n)}},{key:"traf",value:function(t,n){var i=t.id,r=e.box(e.types.tfhd,new Uint8Array([0,0,0,0,i>>>24&255,i>>>16&255,i>>>8&255,255&i])),s=e.box(e.types.tfdt,new Uint8Array([0,0,0,0,n>>>24&255,n>>>16&255,n>>>8&255,255&n])),a=e.sdtp(t),o=e.trun(t,a.byteLength+16+16+8+16+8+8);return e.box(e.types.traf,r,s,o,a)}},{key:"sdtp",value:function(t){for(var n=t.samples||[],i=n.length,r=new Uint8Array(4+i),s=0;s>>24&255,r>>>16&255,r>>>8&255,255&r,n>>>24&255,n>>>16&255,n>>>8&255,255&n],0);for(var o=0;o>>24&255,u>>>16&255,u>>>8&255,255&u,l>>>24&255,l>>>16&255,l>>>8&255,255&l,d.isLeading<<2|d.dependsOn,d.isDependedOn<<6|d.hasRedundancy<<4|d.isNonSync,0,0,h>>>24&255,h>>>16&255,h>>>8&255,255&h],12+16*o)}return e.box(e.types.trun,a)}},{key:"mdat",value:function(t){return e.box(e.types.mdat,t)}}]),e}();s.init(),n.default=s},{}],38:[function(e,t,n){"use strict";function i(e){return e&&e.__esModule?e:{default:e}}function r(e,t){if(!(e instanceof t))throw new TypeError("Cannot call a class as a function")}Object.defineProperty(n,"__esModule",{value:!0});var s=function(){function e(e,t){for(var n=0;n1&&(y=i.pop(),g-=y.length),null!=this._audioStashedLastSample){var E=this._audioStashedLastSample;this._audioStashedLastSample=null,i.unshift(E),g+=E.length}null!=y&&(this._audioStashedLastSample=y);var b=i[0].dts-this._dtsBase;if(this._audioNextDts)r=b-this._audioNextDts;else if(this._audioSegmentInfoList.isEmpty())r=0,this._fillSilentAfterSeek&&!this._videoSegmentInfoList.isEmpty()&&"mp3"!==this._audioMeta.originalCodec&&(m=!0);else{var S=this._audioSegmentInfoList.getLastSampleBefore(b);if(null!=S){var k=b-(S.originalDts+S.duration);k<=3&&(k=0);var L=S.dts+S.duration+k;r=b-L}else r=0}if(m){var w=b-r,R=this._videoSegmentInfoList.getLastSegmentBefore(b);if(null!=R&&R.beginDts=1?C[C.length-1].duration:Math.floor(u);var U=!1,N=null;if(j>1.5*u&&"mp3"!==this._audioMeta.codec&&this._fillAudioTimestampGap&&!c.default.safari){U=!0;var F=Math.abs(j-u),G=Math.ceil(F/u),V=B+u;o.default.w(this.TAG,"Large audio timestamp gap detected, may cause AV sync to drift. Silent frames will be generated to avoid unsync.\ndts: "+(B+j)+" ms, expected: "+(B+Math.round(u))+" ms, delta: "+Math.round(F)+" ms, generate: "+G+" frames");var z=h.default.getSilentFrame(this._audioMeta.originalCodec,this._audioMeta.channelCount);null==z&&(o.default.w(this.TAG,"Unable to generate silent frame for "+this._audioMeta.originalCodec+" with "+this._audioMeta.channelCount+" channels, repeat last frame"),z=M),N=[];for(var H=0;H0){var q=N[N.length-1];q.duration=K-q.dts}var W={dts:K,pts:K,cts:0,unit:z,size:z.byteLength,duration:0,originalDts:D,flags:{isLeading:0,dependsOn:1,isDependedOn:0,hasRedundancy:0}};N.push(W),g+=M.byteLength,V+=u}var X=N[N.length-1];X.duration=B+j-X.dts,j=Math.round(u)}C.push({dts:B,pts:B,cts:0,unit:x.unit,size:x.unit.byteLength,duration:j,originalDts:D,flags:{isLeading:0,dependsOn:1,isDependedOn:0,hasRedundancy:0}}),U&&C.push.apply(C,N)}d?v=new Uint8Array(g):(v=new Uint8Array(g),v[0]=g>>>24&255,v[1]=g>>>16&255,v[2]=g>>>8&255,v[3]=255&g,v.set(l.default.types.mdat,4));for(var Y=0;Y1&&(c=i.pop(),f-=c.length),null!=this._videoStashedLastSample){var m=this._videoStashedLastSample;this._videoStashedLastSample=null,i.unshift(m),f+=m.length}null!=c&&(this._videoStashedLastSample=c);var p=i[0].dts-this._dtsBase;if(this._videoNextDts)r=p-this._videoNextDts;else if(this._videoSegmentInfoList.isEmpty())r=0;else{var v=this._videoSegmentInfoList.getLastSampleBefore(p);if(null!=v){var g=p-(v.originalDts+v.duration);g<=3&&(g=0);var y=v.dts+v.duration+g;r=p-y}else r=0}for(var E=new _.MediaSegmentInfo,b=[],S=0;S=1?b[b.length-1].duration:Math.floor(this._videoMeta.refSampleDuration);if(w){var I=new _.SampleInfo(R,O,T,k.dts,!0);I.fileposition=k.fileposition,E.appendSyncPoint(I)}b.push({dts:R,pts:O,cts:A,units:k.units,size:k.length,isKeyframe:w,duration:T,originalDts:L,flags:{isLeading:0,dependsOn:w?2:1,isDependedOn:w?1:0,hasRedundancy:0,isNonSync:w?0:1}})}h=new Uint8Array(f),h[0]=f>>>24&255,h[1]=f>>>16&255,h[2]=f>>>8&255,h[3]=255&f,h.set(l.default.types.mdat,4);for(var x=0;x=0&&/(rv)(?::| )([\w.]+)/.exec(e)||e.indexOf("compatible")<0&&/(firefox)[ \/]([\w.]+)/.exec(e)||[],n=/(ipad)/.exec(e)||/(ipod)/.exec(e)||/(windows phone)/.exec(e)||/(iphone)/.exec(e)||/(kindle)/.exec(e)||/(android)/.exec(e)||/(windows)/.exec(e)||/(mac)/.exec(e)||/(linux)/.exec(e)||/(cros)/.exec(e)||[],r={browser:t[5]||t[3]||t[1]||"",version:t[2]||t[4]||"0",majorVersion:t[4]||t[2]||"0",platform:n[0]||""},s={};if(r.browser){s[r.browser]=!0;var a=r.majorVersion.split(".");s.version={major:parseInt(r.majorVersion,10),string:r.version},a.length>1&&(s.version.minor=parseInt(a[1],10)),a.length>2&&(s.version.build=parseInt(a[2],10))}r.platform&&(s[r.platform]=!0),(s.chrome||s.opr||s.safari)&&(s.webkit=!0),(s.rv||s.iemobile)&&(s.rv&&delete s.rv,r.browser="msie",s.msie=!0),s.edge&&(delete s.edge,r.browser="msedge",s.msedge=!0),s.opr&&(r.browser="opera",s.opera=!0),s.safari&&s.android&&(r.browser="android",s.android=!0),s.name=r.browser,s.platform=r.platform;for(var o in i)i.hasOwnProperty(o)&&delete i[o];Object.assign(i,s)}(),n.default=i},{}],40:[function(e,t,n){"use strict";function i(e,t){if(!e)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!t||"object"!=typeof t&&"function"!=typeof t?e:t}function r(e,t){if("function"!=typeof t&&null!==t)throw new TypeError("Super expression must either be null or a function, not "+typeof t);e.prototype=Object.create(t&&t.prototype,{constructor:{value:e,enumerable:!1,writable:!0,configurable:!0}}),t&&(Object.setPrototypeOf?Object.setPrototypeOf(e,t):e.__proto__=t)}function s(e,t){if(!(e instanceof t))throw new TypeError("Cannot call a class as a function")}Object.defineProperty(n,"__esModule",{value:!0});var a=function(){function e(e,t){for(var n=0;n "+n;e.ENABLE_CALLBACK&&e.emitter.emit("log","error",i),e.ENABLE_ERROR&&(console.error?console.error(i):console.warn?console.warn(i):console.log(i))}},{key:"i",value:function(t,n){t&&!e.FORCE_GLOBAL_TAG||(t=e.GLOBAL_TAG);var i="["+t+"] > "+n;e.ENABLE_CALLBACK&&e.emitter.emit("log","info",i),e.ENABLE_INFO&&(console.info?console.info(i):console.log(i))}},{key:"w",value:function(t,n){t&&!e.FORCE_GLOBAL_TAG||(t=e.GLOBAL_TAG);var i="["+t+"] > "+n;e.ENABLE_CALLBACK&&e.emitter.emit("log","warn",i),e.ENABLE_WARN&&(console.warn?console.warn(i):console.log(i))}},{key:"d",value:function(t,n){t&&!e.FORCE_GLOBAL_TAG||(t=e.GLOBAL_TAG);var i="["+t+"] > "+n;e.ENABLE_CALLBACK&&e.emitter.emit("log","debug",i),e.ENABLE_DEBUG&&(console.debug?console.debug(i):console.log(i))}},{key:"v",value:function(t,n){t&&!e.FORCE_GLOBAL_TAG||(t=e.GLOBAL_TAG);var i="["+t+"] > "+n;e.ENABLE_CALLBACK&&e.emitter.emit("log","verbose",i),e.ENABLE_VERBOSE&&console.log(i)}}]),e}();o.GLOBAL_TAG="flv.js",o.FORCE_GLOBAL_TAG=!1,o.ENABLE_ERROR=!0,o.ENABLE_INFO=!0,o.ENABLE_WARN=!0,o.ENABLE_DEBUG=!0,o.ENABLE_VERBOSE=!0,o.ENABLE_CALLBACK=!1,o.emitter=new a.default,n.default=o},{events:2}],42:[function(e,t,n){"use strict";function i(e){return e&&e.__esModule?e:{default:e}}function r(e,t){if(!(e instanceof t))throw new TypeError("Cannot call a class as a function")}Object.defineProperty(n,"__esModule",{value:!0});var s=function(){function e(e,t){for(var n=0;n0){var n=e.getConfig();t.emit("change",n)}}},{key:"registerListener",value:function(t){e.emitter.addListener("change",t)}},{key:"removeListener",value:function(t){e.emitter.removeListener("change",t)}},{key:"addLogListener",value:function(t){l.default.emitter.addListener("log",t),l.default.emitter.listenerCount("log")>0&&(l.default.ENABLE_CALLBACK=!0,e._notifyChange())}},{key:"removeLogListener",value:function(t){l.default.emitter.removeListener("log",t),0===l.default.emitter.listenerCount("log")&&(l.default.ENABLE_CALLBACK=!1,e._notifyChange())}},{key:"forceGlobalTag",get:function(){return l.default.FORCE_GLOBAL_TAG},set:function(t){l.default.FORCE_GLOBAL_TAG=t,e._notifyChange()}},{key:"globalTag",get:function(){return l.default.GLOBAL_TAG},set:function(t){l.default.GLOBAL_TAG=t,e._notifyChange()}},{key:"enableAll",get:function(){return l.default.ENABLE_VERBOSE&&l.default.ENABLE_DEBUG&&l.default.ENABLE_INFO&&l.default.ENABLE_WARN&&l.default.ENABLE_ERROR},set:function(t){l.default.ENABLE_VERBOSE=t,l.default.ENABLE_DEBUG=t,l.default.ENABLE_INFO=t,l.default.ENABLE_WARN=t,l.default.ENABLE_ERROR=t,e._notifyChange()}},{key:"enableDebug",get:function(){return l.default.ENABLE_DEBUG},set:function(t){l.default.ENABLE_DEBUG=t,e._notifyChange()}},{key:"enableVerbose",get:function(){return l.default.ENABLE_VERBOSE},set:function(t){l.default.ENABLE_VERBOSE=t,e._notifyChange()}},{key:"enableInfo",get:function(){return l.default.ENABLE_INFO},set:function(t){l.default.ENABLE_INFO=t,e._notifyChange()}},{key:"enableWarn",get:function(){return l.default.ENABLE_WARN},set:function(t){l.default.ENABLE_WARN=t,e._notifyChange()}},{key:"enableError",get:function(){return l.default.ENABLE_ERROR},set:function(t){l.default.ENABLE_ERROR=t,e._notifyChange()}}]),e}();d.emitter=new o.default,n.default=d},{"./logger.js":41,events:2}],43:[function(e,t,n){"use strict";function i(e,t){if(!(e instanceof t))throw new TypeError("Cannot call a class as a function")}Object.defineProperty(n,"__esModule",{value:!0});var r=function(){function e(e,t){for(var n=0;n=128){t.push(String.fromCharCode(65535&a)),r+=2;continue}}}else if(n[r]<240){if(i(n,r,2)){var o=(15&n[r])<<12|(63&n[r+1])<<6|63&n[r+2];if(o>=2048&&55296!=(63488&o)){t.push(String.fromCharCode(65535&o)),r+=3;continue}}}else if(n[r]<248&&i(n,r,3)){var u=(7&n[r])<<18|(63&n[r+1])<<12|(63&n[r+2])<<6|63&n[r+3];if(u>65536&&u<1114112){u-=65536,t.push(String.fromCharCode(u>>>10|55296)),t.push(String.fromCharCode(1023&u|56320)),r+=4;continue}}t.push(String.fromCharCode(65533)),++r}return t.join("")}Object.defineProperty(n,"__esModule",{value:!0}),n.default=r},{}]},{},[21])(21)}); -//# sourceMappingURL=flv.min.js.map +! function(e) { + if ("object" == typeof exports && "undefined" != typeof module) module.exports = e(); + else if ("function" == typeof define && define.amd) define([], e); + else { + var t; + t = "undefined" != typeof window ? window : "undefined" != typeof global ? global : "undefined" != typeof self ? self : this, t.flvjs = e() + } +}(function() { + var e; + return function e(t, n, i) { + function r(a, o) { + if (!n[a]) { + if (!t[a]) { + var u = "function" == typeof require && require; + if (!o && u) return u(a, !0); + if (s) return s(a, !0); + var l = new Error("Cannot find module '" + a + "'"); + throw l.code = "MODULE_NOT_FOUND", l + } + var d = n[a] = { + exports: {} + }; + t[a][0].call(d.exports, function(e) { + var n = t[a][1][e]; + return r(n || e) + }, d, d.exports, e, t, n, i) + } + return n[a].exports + } + for (var s = "function" == typeof require && require, a = 0; a < i.length; a++) r(i[a]); + return r + }({ + 1: [function(t, n, i) { + (function(r, s) { + ! function(t, r) { + "object" == typeof i && void 0 !== n ? n.exports = r() : "function" == typeof e && e.amd ? e(r) : t.ES6Promise = r() + }(this, function() { + "use strict"; + + function e(e) { + return "function" == typeof e || "object" == typeof e && null !== e + } + + function n(e) { + return "function" == typeof e + } + + function i(e) { + K = e + } + + function a(e) { + q = e + } + + function o() { + return void 0 !== H ? function() { + H(l) + } : u() + } + + function u() { + var e = setTimeout; + return function() { + return e(l, 1) + } + } + + function l() { + for (var e = 0; e < z; e += 2) { + (0, J[e])(J[e + 1]), J[e] = void 0, J[e + 1] = void 0 + } + z = 0 + } + + function d(e, t) { + var n = arguments, + i = this, + r = new this.constructor(f); + void 0 === r[ee] && I(r); + var s = i._state; + return s ? function() { + var e = n[s - 1]; + q(function() { + return O(s, r, e, i._result) + }) + }() : L(i, r, e, t), r + } + + function h(e) { + var t = this; + if (e && "object" == typeof e && e.constructor === t) return e; + var n = new t(f); + return E(n, e), n + } + + function f() {} + + function c() { + return new TypeError("You cannot resolve a promise with itself") + } + + function _() { + return new TypeError("A promises callback cannot return that same promise.") + } + + function m(e) { + try { + return e.then + } catch (e) { + return re.error = e, re + } + } + + function p(e, t, n, i) { + try { + e.call(t, n, i) + } catch (e) { + return e + } + } + + function v(e, t, n) { + q(function(e) { + var i = !1, + r = p(n, t, function(n) { + i || (i = !0, t !== n ? E(e, n) : S(e, n)) + }, function(t) { + i || (i = !0, k(e, t)) + }, "Settle: " + (e._label || " unknown promise")); + !i && r && (i = !0, k(e, r)) + }, e) + } + + function g(e, t) { + t._state === ne ? S(e, t._result) : t._state === ie ? k(e, t._result) : L(t, void 0, function(t) { + return E(e, t) + }, function(t) { + return k(e, t) + }) + } + + function y(e, t, i) { + t.constructor === e.constructor && i === d && t.constructor.resolve === h ? g(e, t) : i === re ? (k(e, re.error), re.error = null) : void 0 === i ? S(e, t) : n(i) ? v(e, t, i) : S(e, t) + } + + function E(t, n) { + t === n ? k(t, c()) : e(n) ? y(t, n, m(n)) : S(t, n) + } + + function b(e) { + e._onerror && e._onerror(e._result), w(e) + } + + function S(e, t) { + e._state === te && (e._result = t, e._state = ne, 0 !== e._subscribers.length && q(w, e)) + } + + function k(e, t) { + e._state === te && (e._state = ie, e._result = t, q(b, e)) + } + + function L(e, t, n, i) { + var r = e._subscribers, + s = r.length; + e._onerror = null, r[s] = t, r[s + ne] = n, r[s + ie] = i, 0 === s && e._state && q(w, e) + } + + function w(e) { + var t = e._subscribers, + n = e._state; + if (0 !== t.length) { + for (var i = void 0, r = void 0, s = e._result, a = 0; a < t.length; a += 3) i = t[a], r = t[a + n], i ? O(n, i, r, s) : r(s); + e._subscribers.length = 0 + } + } + + function R() { + this.error = null + } + + function A(e, t) { + try { + return e(t) + } catch (e) { + return se.error = e, se + } + } + + function O(e, t, i, r) { + var s = n(i), + a = void 0, + o = void 0, + u = void 0, + l = void 0; + if (s) { + if (a = A(i, r), a === se ? (l = !0, o = a.error, a.error = null) : u = !0, t === a) return void k(t, _()) + } else a = r, u = !0; + t._state !== te || (s && u ? E(t, a) : l ? k(t, o) : e === ne ? S(t, a) : e === ie && k(t, a)) + } + + function T(e, t) { + try { + t(function(t) { + E(e, t) + }, function(t) { + k(e, t) + }) + } catch (t) { + k(e, t) + } + } + + function C() { + return ae++ + } + + function I(e) { + e[ee] = ae++, e._state = void 0, e._result = void 0, e._subscribers = [] + } + + function x(e, t) { + this._instanceConstructor = e, this.promise = new e(f), this.promise[ee] || I(this.promise), V(t) ? (this._input = t, this.length = t.length, this._remaining = t.length, this._result = new Array(this.length), 0 === this.length ? S(this.promise, this._result) : (this.length = this.length || 0, this._enumerate(), 0 === this._remaining && S(this.promise, this._result))) : k(this.promise, M()) + } + + function M() { + return new Error("Array Methods must be provided an Array") + } + + function D(e) { + return new x(this, e).promise + } + + function B(e) { + var t = this; + return new t(V(e) ? function(n, i) { + for (var r = e.length, s = 0; s < r; s++) t.resolve(e[s]).then(n, i) + } : function(e, t) { + return t(new TypeError("You must pass an array to race.")) + }) + } + + function j(e) { + var t = this, + n = new t(f); + return k(n, e), n + } + + function P() { + throw new TypeError("You must pass a resolver function as the first argument to the promise constructor") + } + + function U() { + throw new TypeError("Failed to construct 'Promise': Please use the 'new' operator, this object constructor cannot be called as a function.") + } + + function N(e) { + this[ee] = C(), this._result = this._state = void 0, this._subscribers = [], f !== e && ("function" != typeof e && P(), this instanceof N ? T(this, e) : U()) + } + + function F() { + var e = void 0; + if (void 0 !== s) e = s; + else if ("undefined" != typeof self) e = self; + else try { + e = Function("return this")() + } catch (e) { + throw new Error("polyfill failed because global object is unavailable in this environment") + } + var t = e.Promise; + if (t) { + var n = null; + try { + n = Object.prototype.toString.call(t.resolve()) + } catch (e) {} + if ("[object Promise]" === n && !t.cast) return + } + e.Promise = N + } + var G = void 0; + G = Array.isArray ? Array.isArray : function(e) { + return "[object Array]" === Object.prototype.toString.call(e) + }; + var V = G, + z = 0, + H = void 0, + K = void 0, + q = function(e, t) { + J[z] = e, J[z + 1] = t, 2 === (z += 2) && (K ? K(l) : $()) + }, + W = "undefined" != typeof window ? window : void 0, + X = W || {}, + Y = X.MutationObserver || X.WebKitMutationObserver, + Z = "undefined" == typeof self && void 0 !== r && "[object process]" === {}.toString.call(r), + Q = "undefined" != typeof Uint8ClampedArray && "undefined" != typeof importScripts && "undefined" != typeof MessageChannel, + J = new Array(1e3), + $ = void 0; + $ = Z ? function() { + return function() { + return r.nextTick(l) + } + }() : Y ? function() { + var e = 0, + t = new Y(l), + n = document.createTextNode(""); + return t.observe(n, { + characterData: !0 + }), + function() { + n.data = e = ++e % 2 + } + }() : Q ? function() { + var e = new MessageChannel; + return e.port1.onmessage = l, + function() { + return e.port2.postMessage(0) + } + }() : void 0 === W && "function" == typeof t ? function() { + try { + var e = t, + n = e("vertx"); + return H = n.runOnLoop || n.runOnContext, o() + } catch (e) { + return u() + } + }() : u(); + var ee = Math.random().toString(36).substring(16), + te = void 0, + ne = 1, + ie = 2, + re = new R, + se = new R, + ae = 0; + return x.prototype._enumerate = function() { + for (var e = this.length, t = this._input, n = 0; this._state === te && n < e; n++) this._eachEntry(t[n], n) + }, x.prototype._eachEntry = function(e, t) { + var n = this._instanceConstructor, + i = n.resolve; + if (i === h) { + var r = m(e); + if (r === d && e._state !== te) this._settledAt(e._state, t, e._result); + else if ("function" != typeof r) this._remaining--, this._result[t] = e; + else if (n === N) { + var s = new n(f); + y(s, e, r), this._willSettleAt(s, t) + } else this._willSettleAt(new n(function(t) { + return t(e) + }), t) + } else this._willSettleAt(i(e), t) + }, x.prototype._settledAt = function(e, t, n) { + var i = this.promise; + i._state === te && (this._remaining--, e === ie ? k(i, n) : this._result[t] = n), 0 === this._remaining && S(i, this._result) + }, x.prototype._willSettleAt = function(e, t) { + var n = this; + L(e, void 0, function(e) { + return n._settledAt(ne, t, e) + }, function(e) { + return n._settledAt(ie, t, e) + }) + }, N.all = D, N.race = B, N.resolve = h, N.reject = j, N._setScheduler = i, N._setAsap = a, N._asap = q, N.prototype = { + constructor: N, + then: d, + catch: function(e) { + return this.then(null, e) + } + }, N.polyfill = F, N.Promise = N, N + }) + }).call(this, t("_process"), "undefined" != typeof global ? global : "undefined" != typeof self ? self : "undefined" != typeof window ? window : {}) + }, { + _process: 3 + }], + 2: [function(e, t, n) { + function i() { + this._events = this._events || {}, this._maxListeners = this._maxListeners || void 0 + } + + function r(e) { + return "function" == typeof e + } + + function s(e) { + return "number" == typeof e + } + + function a(e) { + return "object" == typeof e && null !== e + } + + function o(e) { + return void 0 === e + } + t.exports = i, i.EventEmitter = i, i.prototype._events = void 0, i.prototype._maxListeners = void 0, i.defaultMaxListeners = 10, i.prototype.setMaxListeners = function(e) { + if (!s(e) || e < 0 || isNaN(e)) throw TypeError("n must be a positive number"); + return this._maxListeners = e, this + }, i.prototype.emit = function(e) { + var t, n, i, s, u, l; + if (this._events || (this._events = {}), "error" === e && (!this._events.error || a(this._events.error) && !this._events.error.length)) { + if ((t = arguments[1]) instanceof Error) throw t; + var d = new Error('Uncaught, unspecified "error" event. (' + t + ")"); + throw d.context = t, d + } + if (n = this._events[e], o(n)) return !1; + if (r(n)) switch (arguments.length) { + case 1: + n.call(this); + break; + case 2: + n.call(this, arguments[1]); + break; + case 3: + n.call(this, arguments[1], arguments[2]); + break; + default: + s = Array.prototype.slice.call(arguments, 1), n.apply(this, s) + } else if (a(n)) + for (s = Array.prototype.slice.call(arguments, 1), l = n.slice(), i = l.length, u = 0; u < i; u++) l[u].apply(this, s); + return !0 + }, i.prototype.addListener = function(e, t) { + var n; + if (!r(t)) throw TypeError("listener must be a function"); + return this._events || (this._events = {}), this._events.newListener && this.emit("newListener", e, r(t.listener) ? t.listener : t), this._events[e] ? a(this._events[e]) ? this._events[e].push(t) : this._events[e] = [this._events[e], t] : this._events[e] = t, a(this._events[e]) && !this._events[e].warned && (n = o(this._maxListeners) ? i.defaultMaxListeners : this._maxListeners) && n > 0 && this._events[e].length > n && (this._events[e].warned = !0, console.error("(node) warning: possible EventEmitter memory leak detected. %d listeners added. Use emitter.setMaxListeners() to increase limit.", this._events[e].length), "function" == typeof console.trace && console.trace()), this + }, i.prototype.on = i.prototype.addListener, i.prototype.once = function(e, t) { + function n() { + this.removeListener(e, n), i || (i = !0, t.apply(this, arguments)) + } + if (!r(t)) throw TypeError("listener must be a function"); + var i = !1; + return n.listener = t, this.on(e, n), this + }, i.prototype.removeListener = function(e, t) { + var n, i, s, o; + if (!r(t)) throw TypeError("listener must be a function"); + if (!this._events || !this._events[e]) return this; + if (n = this._events[e], s = n.length, i = -1, n === t || r(n.listener) && n.listener === t) delete this._events[e], this._events.removeListener && this.emit("removeListener", e, t); + else if (a(n)) { + for (o = s; o-- > 0;) + if (n[o] === t || n[o].listener && n[o].listener === t) { + i = o; + break + } if (i < 0) return this; + 1 === n.length ? (n.length = 0, delete this._events[e]) : n.splice(i, 1), this._events.removeListener && this.emit("removeListener", e, t) + } + return this + }, i.prototype.removeAllListeners = function(e) { + var t, n; + if (!this._events) return this; + if (!this._events.removeListener) return 0 === arguments.length ? this._events = {} : this._events[e] && delete this._events[e], this; + if (0 === arguments.length) { + for (t in this._events) "removeListener" !== t && this.removeAllListeners(t); + return this.removeAllListeners("removeListener"), this._events = {}, this + } + if (n = this._events[e], r(n)) this.removeListener(e, n); + else if (n) + for (; n.length;) this.removeListener(e, n[n.length - 1]); + return delete this._events[e], this + }, i.prototype.listeners = function(e) { + return this._events && this._events[e] ? r(this._events[e]) ? [this._events[e]] : this._events[e].slice() : [] + }, i.prototype.listenerCount = function(e) { + if (this._events) { + var t = this._events[e]; + if (r(t)) return 1; + if (t) return t.length + } + return 0 + }, i.listenerCount = function(e, t) { + return e.listenerCount(t) + } + }, {}], + 3: [function(e, t, n) { + function i() { + throw new Error("setTimeout has not been defined") + } + + function r() { + throw new Error("clearTimeout has not been defined") + } + + function s(e) { + if (h === setTimeout) return setTimeout(e, 0); + if ((h === i || !h) && setTimeout) return h = setTimeout, setTimeout(e, 0); + try { + return h(e, 0) + } catch (t) { + try { + return h.call(null, e, 0) + } catch (t) { + return h.call(this, e, 0) + } + } + } + + function a(e) { + if (f === clearTimeout) return clearTimeout(e); + if ((f === r || !f) && clearTimeout) return f = clearTimeout, clearTimeout(e); + try { + return f(e) + } catch (t) { + try { + return f.call(null, e) + } catch (t) { + return f.call(this, e) + } + } + } + + function o() { + p && _ && (p = !1, _.length ? m = _.concat(m) : v = -1, m.length && u()) + } + + function u() { + if (!p) { + var e = s(o); + p = !0; + for (var t = m.length; t;) { + for (_ = m, m = []; ++v < t;) _ && _[v].run(); + v = -1, t = m.length + } + _ = null, p = !1, a(e) + } + } + + function l(e, t) { + this.fun = e, this.array = t + } + + function d() {} + var h, f, c = t.exports = {}; + ! function() { + try { + h = "function" == typeof setTimeout ? setTimeout : i + } catch (e) { + h = i + } + try { + f = "function" == typeof clearTimeout ? clearTimeout : r + } catch (e) { + f = r + } + }(); + var _, m = [], + p = !1, + v = -1; + c.nextTick = function(e) { + var t = new Array(arguments.length - 1); + if (arguments.length > 1) + for (var n = 1; n < arguments.length; n++) t[n - 1] = arguments[n]; + m.push(new l(e, t)), 1 !== m.length || p || s(u) + }, l.prototype.run = function() { + this.fun.apply(null, this.array) + }, c.title = "browser", c.browser = !0, c.env = {}, c.argv = [], c.version = "", c.versions = {}, c.on = d, c.addListener = d, c.once = d, c.off = d, c.removeListener = d, c.removeAllListeners = d, c.emit = d, c.prependListener = d, c.prependOnceListener = d, c.listeners = function(e) { + return [] + }, c.binding = function(e) { + throw new Error("process.binding is not supported") + }, c.cwd = function() { + return "/" + }, c.chdir = function(e) { + throw new Error("process.chdir is not supported") + }, c.umask = function() { + return 0 + } + }, {}], + 4: [function(e, t, n) { + var i = arguments[3], + r = arguments[4], + s = arguments[5], + a = JSON.stringify; + t.exports = function(e, t) { + function n(e) { + p[e] = !0; + for (var t in r[e][1]) { + var i = r[e][1][t]; + p[i] || n(i) + } + } + for (var o, u = Object.keys(s), l = 0, d = u.length; l < d; l++) { + var h = u[l], + f = s[h].exports; + if (f === e || f && f.default === e) { + o = h; + break + } + } + if (!o) { + o = Math.floor(Math.pow(16, 8) * Math.random()).toString(16); + for (var c = {}, l = 0, d = u.length; l < d; l++) { + var h = u[l]; + c[h] = h + } + r[o] = [Function(["require", "module", "exports"], "(" + e + ")(self)"), c] + } + var _ = Math.floor(Math.pow(16, 8) * Math.random()).toString(16), + m = {}; + m[o] = o, r[_] = [Function(["require"], "var f = require(" + a(o) + ");(f.default ? f.default : f)(self);"), m]; + var p = {}; + n(_); + var v = "(" + i + ")({" + Object.keys(p).map(function(e) { + return a(e) + ":[" + r[e][0] + "," + a(r[e][1]) + "]" + }).join(",") + "},{},[" + a(_) + "])", + g = window.URL || window.webkitURL || window.mozURL || window.msURL, + y = new Blob([v], { + type: "text/javascript" + }); + if (t && t.bare) return y; + var E = g.createObjectURL(y), + b = new Worker(E); + return b.objectURL = E, b + } + }, {}], + 5: [function(e, t, n) { + "use strict"; + + function i() { + return Object.assign({}, r) + } + Object.defineProperty(n, "__esModule", { + value: !0 + }), n.createDefaultConfig = i; + var r = n.defaultConfig = { + enableWorker: !1, + enableStashBuffer: !0, + stashInitialSize: void 0, + isLive: !1, + lazyLoad: !0, + lazyLoadMaxDuration: 180, + lazyLoadRecoverDuration: 30, + deferLoadAfterSourceOpen: !0, + autoCleanupMaxBackwardDuration: 180, + autoCleanupMinBackwardDuration: 120, + statisticsInfoReportInterval: 600, + fixAudioTimestampGap: !0, + accurateSeek: !1, + seekType: "range", + seekParamStart: "bstart", + seekParamEnd: "bend", + rangeLoadZeroStart: !1, + customSeekHandler: void 0, + reuseRedirectedURL: !1 + } + }, {}], + 6: [function(e, t, n) { + "use strict"; + + function i(e, t) { + if (!(e instanceof t)) throw new TypeError("Cannot call a class as a function") + } + Object.defineProperty(n, "__esModule", { + value: !0 + }); + var r = function() { + function e(e, t) { + for (var n = 0; n < t.length; n++) { + var i = t[n]; + i.enumerable = i.enumerable || !1, i.configurable = !0, "value" in i && (i.writable = !0), Object.defineProperty(e, i.key, i) + } + } + return function(t, n, i) { + return n && e(t.prototype, n), i && e(t, i), t + } + }(), + s = e("../io/io-controller.js"), + a = function(e) { + return e && e.__esModule ? e : { + default: e + } + }(s), + o = e("../config.js"), + u = function() { + function e() { + i(this, e) + } + return r(e, null, [{ + key: "supportMSEH264Playback", + value: function() { + return window.MediaSource && window.MediaSource.isTypeSupported('video/mp4; codecs="avc1.42E01E,mp4a.40.2"') + } + }, { + key: "supportNetworkStreamIO", + value: function() { + var e = new a.default({}, (0, o.createDefaultConfig)()), + t = e.loaderType; + return e.destroy(), "fetch-stream-loader" == t || "xhr-moz-chunked-loader" == t + } + }, { + key: "getNetworkLoaderTypeName", + value: function() { + var e = new a.default({}, (0, o.createDefaultConfig)()), + t = e.loaderType; + return e.destroy(), t + } + }, { + key: "supportNativeMediaPlayback", + value: function(t) { + void 0 == e.videoElement && (e.videoElement = window.document.createElement("video")); + var n = e.videoElement.canPlayType(t); + return "probably" === n || "maybe" == n + } + }, { + key: "getFeatureList", + value: function() { + var t = { + mseFlvPlayback: !1, + mseLiveFlvPlayback: !1, + networkStreamIO: !1, + networkLoaderName: "", + nativeMP4H264Playback: !1, + nativeWebmVP8Playback: !1, + nativeWebmVP9Playback: !1 + }; + return t.mseFlvPlayback = e.supportMSEH264Playback(), t.networkStreamIO = e.supportNetworkStreamIO(), t.networkLoaderName = e.getNetworkLoaderTypeName(), t.mseLiveFlvPlayback = t.mseFlvPlayback && t.networkStreamIO, t.nativeMP4H264Playback = e.supportNativeMediaPlayback('video/mp4; codecs="avc1.42001E, mp4a.40.2"'), t.nativeWebmVP8Playback = e.supportNativeMediaPlayback('video/webm; codecs="vp8.0, vorbis"'), t.nativeWebmVP9Playback = e.supportNativeMediaPlayback('video/webm; codecs="vp9"'), t + } + }]), e + }(); + n.default = u + }, { + "../config.js": 5, + "../io/io-controller.js": 23 + }], + 7: [function(e, t, n) { + "use strict"; + + function i(e, t) { + if (!(e instanceof t)) throw new TypeError("Cannot call a class as a function") + } + Object.defineProperty(n, "__esModule", { + value: !0 + }); + var r = function() { + function e(e, t) { + for (var n = 0; n < t.length; n++) { + var i = t[n]; + i.enumerable = i.enumerable || !1, i.configurable = !0, "value" in i && (i.writable = !0), Object.defineProperty(e, i.key, i) + } + } + return function(t, n, i) { + return n && e(t.prototype, n), i && e(t, i), t + } + }(), + s = function() { + function e() { + i(this, e), this.mimeType = null, this.duration = null, this.hasAudio = null, this.hasVideo = null, this.audioCodec = null, this.videoCodec = null, this.audioDataRate = null, this.videoDataRate = null, this.audioSampleRate = null, this.audioChannelCount = null, this.width = null, this.height = null, this.fps = null, this.profile = null, this.level = null, this.refFrames = null, this.chromaFormat = null, this.sarNum = null, this.sarDen = null, this.metadata = null, this.segments = null, this.segmentCount = null, this.hasKeyframesIndex = null, this.keyframesIndex = null + } + return r(e, [{ + key: "isComplete", + value: function() { + var e = !1 === this.hasAudio || !0 === this.hasAudio && null != this.audioCodec && null != this.audioSampleRate && null != this.audioChannelCount, + t = !1 === this.hasVideo || !0 === this.hasVideo && null != this.videoCodec && null != this.width && null != this.height && null != this.fps && null != this.profile && null != this.level && null != this.refFrames && null != this.chromaFormat && null != this.sarNum && null != this.sarDen; + return null != this.mimeType && null != this.duration && null != this.metadata && null != this.hasKeyframesIndex && e && t + } + }, { + key: "isSeekable", + value: function() { + return !0 === this.hasKeyframesIndex + } + }, { + key: "getNearestKeyframe", + value: function(e) { + if (null == this.keyframesIndex) return null; + var t = this.keyframesIndex, + n = this._search(t.times, e); + return { + index: n, + milliseconds: t.times[n], + fileposition: t.filepositions[n] + } + } + }, { + key: "_search", + value: function(e, t) { + var n = 0, + i = e.length - 1, + r = 0, + s = 0, + a = i; + for (t < e[0] && (n = 0, s = a + 1); s <= a;) { + if ((r = s + Math.floor((a - s) / 2)) === i || t >= e[r] && t < e[r + 1]) { + n = r; + break + } + e[r] < t ? s = r + 1 : a = r - 1 + } + return n + } + }]), e + }(); + n.default = s + }, {}], + 8: [function(e, t, n) { + "use strict"; + + function i(e, t) { + if (!(e instanceof t)) throw new TypeError("Cannot call a class as a function") + } + Object.defineProperty(n, "__esModule", { + value: !0 + }); + var r = function() { + function e(e, t) { + for (var n = 0; n < t.length; n++) { + var i = t[n]; + i.enumerable = i.enumerable || !1, i.configurable = !0, "value" in i && (i.writable = !0), Object.defineProperty(e, i.key, i) + } + } + return function(t, n, i) { + return n && e(t.prototype, n), i && e(t, i), t + } + }(); + n.SampleInfo = function e(t, n, r, s, a) { + i(this, e), this.dts = t, this.pts = n, this.duration = r, this.originalDts = s, this.isSyncPoint = a, this.fileposition = null + }, n.MediaSegmentInfo = function() { + function e() { + i(this, e), this.beginDts = 0, this.endDts = 0, this.beginPts = 0, this.endPts = 0, this.originalBeginDts = 0, this.originalEndDts = 0, this.syncPoints = [], this.firstSample = null, this.lastSample = null + } + return r(e, [{ + key: "appendSyncPoint", + value: function(e) { + e.isSyncPoint = !0, this.syncPoints.push(e) + } + }]), e + }(), n.IDRSampleList = function() { + function e() { + i(this, e), this._list = [] + } + return r(e, [{ + key: "clear", + value: function() { + this._list = [] + } + }, { + key: "appendArray", + value: function(e) { + var t = this._list; + 0 !== e.length && (t.length > 0 && e[0].originalDts < t[t.length - 1].originalDts && this.clear(), Array.prototype.push.apply(t, e)) + } + }, { + key: "getLastSyncPointBeforeDts", + value: function(e) { + if (0 == this._list.length) return null; + var t = this._list, + n = 0, + i = t.length - 1, + r = 0, + s = 0, + a = i; + for (e < t[0].dts && (n = 0, s = a + 1); s <= a;) { + if ((r = s + Math.floor((a - s) / 2)) === i || e >= t[r].dts && e < t[r + 1].dts) { + n = r; + break + } + t[r].dts < e ? s = r + 1 : a = r - 1 + } + return this._list[n] + } + }]), e + }(), n.MediaSegmentInfoList = function() { + function e(t) { + i(this, e), this._type = t, this._list = [], this._lastAppendLocation = -1 + } + return r(e, [{ + key: "isEmpty", + value: function() { + return 0 === this._list.length + } + }, { + key: "clear", + value: function() { + this._list = [], this._lastAppendLocation = -1 + } + }, { + key: "_searchNearestSegmentBefore", + value: function(e) { + var t = this._list; + if (0 === t.length) return -2; + var n = t.length - 1, + i = 0, + r = 0, + s = n, + a = 0; + if (e < t[0].originalBeginDts) return a = -1; + for (; r <= s;) { + if ((i = r + Math.floor((s - r) / 2)) === n || e > t[i].lastSample.originalDts && e < t[i + 1].originalBeginDts) { + a = i; + break + } + t[i].originalBeginDts < e ? r = i + 1 : s = i - 1 + } + return a + } + }, { + key: "_searchNearestSegmentAfter", + value: function(e) { + return this._searchNearestSegmentBefore(e) + 1 + } + }, { + key: "append", + value: function(e) { + var t = this._list, + n = e, + i = this._lastAppendLocation, + r = 0; - 1 !== i && i < t.length && n.originalBeginDts >= t[i].lastSample.originalDts && (i === t.length - 1 || i < t.length - 1 && n.originalBeginDts < t[i + 1].originalBeginDts) ? r = i + 1 : t.length > 0 && (r = this._searchNearestSegmentBefore(n.originalBeginDts) + 1), this._lastAppendLocation = r, this._list.splice(r, 0, n) + } + }, { + key: "getLastSegmentBefore", + value: function(e) { + var t = this._searchNearestSegmentBefore(e); + return t >= 0 ? this._list[t] : null + } + }, { + key: "getLastSampleBefore", + value: function(e) { + var t = this.getLastSegmentBefore(e); + return null != t ? t.lastSample : null + } + }, { + key: "getLastSyncPointBefore", + value: function(e) { + for (var t = this._searchNearestSegmentBefore(e), n = this._list[t].syncPoints; 0 === n.length && t > 0;) t--, n = this._list[t].syncPoints; + return n.length > 0 ? n[n.length - 1] : null + } + }, { + key: "type", + get: function() { + return this._type + } + }, { + key: "length", + get: function() { + return this._list.length + } + }]), e + }() + }, {}], + 9: [function(e, t, n) { + "use strict"; + + function i(e) { + return e && e.__esModule ? e : { + default: e + } + } + + function r(e, t) { + if (!(e instanceof t)) throw new TypeError("Cannot call a class as a function") + } + Object.defineProperty(n, "__esModule", { + value: !0 + }); + var s = function() { + function e(e, t) { + for (var n = 0; n < t.length; n++) { + var i = t[n]; + i.enumerable = i.enumerable || !1, i.configurable = !0, "value" in i && (i.writable = !0), Object.defineProperty(e, i.key, i) + } + } + return function(t, n, i) { + return n && e(t.prototype, n), i && e(t, i), t + } + }(), + a = e("events"), + o = i(a), + u = e("../utils/logger.js"), + l = i(u), + d = e("../utils/browser.js"), + h = i(d), + f = e("./mse-events.js"), + c = i(f), + _ = e("./media-segment-info.js"), + m = e("../utils/exception.js"), + p = function() { + function e(t) { + r(this, e), this.TAG = "MSEController", this._config = t, this._emitter = new o.default, this._config.isLive && void 0 == this._config.autoCleanupSourceBuffer && (this._config.autoCleanupSourceBuffer = !0), this.e = { + onSourceOpen: this._onSourceOpen.bind(this), + onSourceEnded: this._onSourceEnded.bind(this), + onSourceClose: this._onSourceClose.bind(this), + onSourceBufferError: this._onSourceBufferError.bind(this), + onSourceBufferUpdateEnd: this._onSourceBufferUpdateEnd.bind(this) + }, this._mediaSource = null, this._mediaSourceObjectURL = null, this._mediaElement = null, this._isBufferFull = !1, this._hasPendingEos = !1, this._requireSetMediaDuration = !1, this._pendingMediaDuration = 0, this._pendingSourceBufferInit = [], this._mimeTypes = { + video: null, + audio: null + }, this._sourceBuffers = { + video: null, + audio: null + }, this._lastInitSegments = { + video: null, + audio: null + }, this._pendingSegments = { + video: [], + audio: [] + }, this._pendingRemoveRanges = { + video: [], + audio: [] + }, this._idrList = new _.IDRSampleList + } + return s(e, [{ + key: "destroy", + value: function() { + (this._mediaElement || this._mediaSource) && this.detachMediaElement(), this.e = null, this._emitter.removeAllListeners(), this._emitter = null + } + }, { + key: "on", + value: function(e, t) { + this._emitter.addListener(e, t) + } + }, { + key: "off", + value: function(e, t) { + this._emitter.removeListener(e, t) + } + }, { + key: "attachMediaElement", + value: function(e) { + if (this._mediaSource) throw new m.IllegalStateException("MediaSource has been attached to an HTMLMediaElement!"); + var t = this._mediaSource = new window.MediaSource; + t.addEventListener("sourceopen", this.e.onSourceOpen), t.addEventListener("sourceended", this.e.onSourceEnded), t.addEventListener("sourceclose", this.e.onSourceClose), this._mediaElement = e, this._mediaSourceObjectURL = window.URL.createObjectURL(this._mediaSource), e.src = this._mediaSourceObjectURL + } + }, { + key: "detachMediaElement", + value: function() { + if (this._mediaSource) { + var e = this._mediaSource; + for (var t in this._sourceBuffers) { + var n = this._pendingSegments[t]; + n.splice(0, n.length), this._pendingSegments[t] = null, this._pendingRemoveRanges[t] = null, this._lastInitSegments[t] = null; + var i = this._sourceBuffers[t]; + i && ("closed" !== e.readyState && (e.removeSourceBuffer(i), i.removeEventListener("error", this.e.onSourceBufferError), i.removeEventListener("updateend", this.e.onSourceBufferUpdateEnd)), this._mimeTypes[t] = null, this._sourceBuffers[t] = null) + } + if ("open" === e.readyState) try { + e.endOfStream() + } catch (e) { + l.default.e(this.TAG, e.message) + } + e.removeEventListener("sourceopen", this.e.onSourceOpen), e.removeEventListener("sourceended", this.e.onSourceEnded), e.removeEventListener("sourceclose", this.e.onSourceClose), this._pendingSourceBufferInit = [], this._isBufferFull = !1, this._idrList.clear(), this._mediaSource = null + } + this._mediaElement && (this._mediaElement.src = "", this._mediaElement.removeAttribute("src"), this._mediaElement = null), this._mediaSourceObjectURL && (window.URL.revokeObjectURL(this._mediaSourceObjectURL), this._mediaSourceObjectURL = null) + } + }, { + key: "appendInitSegment", + value: function(e, t) { + if (!this._mediaSource || "open" !== this._mediaSource.readyState) return this._pendingSourceBufferInit.push(e), void this._pendingSegments[e.type].push(e); + var n = e, + i = "" + n.container; + n.codec && n.codec.length > 0 && (i += ";codecs=" + n.codec); + var r = !1; + if (l.default.v(this.TAG, "Received Initialization Segment, mimeType: " + i), this._lastInitSegments[n.type] = n, i !== this._mimeTypes[n.type]) { + if (this._mimeTypes[n.type]) l.default.v(this.TAG, "Notice: " + n.type + " mimeType changed, origin: " + this._mimeTypes[n.type] + ", target: " + i); + else { + r = !0; + try { + var s = this._sourceBuffers[n.type] = this._mediaSource.addSourceBuffer(i); + s.addEventListener("error", this.e.onSourceBufferError), s.addEventListener("updateend", this.e.onSourceBufferUpdateEnd) + } catch (e) { + return l.default.e(this.TAG, e.message), void this._emitter.emit(c.default.ERROR, { + code: e.code, + msg: e.message + }) + } + } + this._mimeTypes[n.type] = i + } + t || this._pendingSegments[n.type].push(n), r || this._sourceBuffers[n.type] && !this._sourceBuffers[n.type].updating && this._doAppendSegments(), h.default.safari && "audio/mpeg" === n.container && n.mediaDuration > 0 && (this._requireSetMediaDuration = !0, this._pendingMediaDuration = n.mediaDuration / 1e3, this._updateMediaSourceDuration()) + } + }, { + key: "appendMediaSegment", + value: function(e) { + var t = e; + this._pendingSegments[t.type].push(t), this._config.autoCleanupSourceBuffer && this._needCleanupSourceBuffer() && this._doCleanupSourceBuffer(); + var n = this._sourceBuffers[t.type]; + !n || n.updating || this._hasPendingRemoveRanges() || this._doAppendSegments() + } + }, { + key: "seek", + value: function(e) { + for (var t in this._sourceBuffers) + if (this._sourceBuffers[t]) { + var n = this._sourceBuffers[t]; + if ("open" === this._mediaSource.readyState) try { + n.abort() + } catch (e) { + l.default.e(this.TAG, e.message) + } + this._idrList.clear(); + var i = this._pendingSegments[t]; + if (i.splice(0, i.length), "closed" !== this._mediaSource.readyState) { + for (var r = 0; r < n.buffered.length; r++) { + var s = n.buffered.start(r), + a = n.buffered.end(r); + this._pendingRemoveRanges[t].push({ + start: s, + end: a + }) + } + if (n.updating || this._doRemoveRanges(), h.default.safari) { + var o = this._lastInitSegments[t]; + o && (this._pendingSegments[t].push(o), n.updating || this._doAppendSegments()) + } + } + } + } + }, { + key: "endOfStream", + value: function() { + var e = this._mediaSource, + t = this._sourceBuffers; + if (!e || "open" !== e.readyState) return void(e && "closed" === e.readyState && this._hasPendingSegments() && (this._hasPendingEos = !0)); + t.video && t.video.updating || t.audio && t.audio.updating ? this._hasPendingEos = !0 : (this._hasPendingEos = !1, e.endOfStream()) + } + }, { + key: "getNearestKeyframe", + value: function(e) { + return this._idrList.getLastSyncPointBeforeDts(e) + } + }, { + key: "_needCleanupSourceBuffer", + value: function() { + if (!this._config.autoCleanupSourceBuffer) return !1; + var e = this._mediaElement.currentTime; + for (var t in this._sourceBuffers) { + var n = this._sourceBuffers[t]; + if (n) { + var i = n.buffered; + if (i.length >= 1 && e - i.start(0) >= this._config.autoCleanupMaxBackwardDuration) return !0 + } + } + return !1 + } + }, { + key: "_doCleanupSourceBuffer", + value: function() { + var e = this._mediaElement.currentTime; + for (var t in this._sourceBuffers) { + var n = this._sourceBuffers[t]; + if (n) { + for (var i = n.buffered, r = !1, s = 0; s < i.length; s++) { + var a = i.start(s), + o = i.end(s); + if (a <= e && e < o + 3) { + if (e - a >= this._config.autoCleanupMaxBackwardDuration) { + r = !0; + var u = e - this._config.autoCleanupMinBackwardDuration; + this._pendingRemoveRanges[t].push({ + start: a, + end: u + }) + } + } else o < e && (r = !0, this._pendingRemoveRanges[t].push({ + start: a, + end: o + })) + } + r && !n.updating && this._doRemoveRanges() + } + } + } + }, { + key: "_updateMediaSourceDuration", + value: function() { + var e = this._sourceBuffers; + if (0 !== this._mediaElement.readyState && "open" === this._mediaSource.readyState && !(e.video && e.video.updating || e.audio && e.audio.updating)) { + var t = this._mediaSource.duration, + n = this._pendingMediaDuration; + n > 0 && (isNaN(t) || n > t) && (l.default.v(this.TAG, "Update MediaSource duration from " + t + " to " + n), this._mediaSource.duration = n), this._requireSetMediaDuration = !1, this._pendingMediaDuration = 0 + } + } + }, { + key: "_doRemoveRanges", + value: function() { + for (var e in this._pendingRemoveRanges) + if (this._sourceBuffers[e] && !this._sourceBuffers[e].updating) + for (var t = this._sourceBuffers[e], n = this._pendingRemoveRanges[e]; n.length && !t.updating;) { + var i = n.shift(); + t.remove(i.start, i.end) + } + } + }, { + key: "_doAppendSegments", + value: function() { + var e = this._pendingSegments; + for (var t in e) + if (this._sourceBuffers[t] && !this._sourceBuffers[t].updating && e[t].length > 0) { + var n = e[t].shift(); + if (n.timestampOffset) { + var i = this._sourceBuffers[t].timestampOffset, + r = n.timestampOffset / 1e3, + s = Math.abs(i - r); + s > .1 && (l.default.v(this.TAG, "Update MPEG audio timestampOffset from " + i + " to " + r), this._sourceBuffers[t].timestampOffset = r), delete n.timestampOffset + } + if (!n.data || 0 === n.data.byteLength) continue; + try { + this._sourceBuffers[t].appendBuffer(n.data), this._isBufferFull = !1, "video" === t && n.hasOwnProperty("info") && this._idrList.appendArray(n.info.syncPoints) + } catch (e) { + this._pendingSegments[t].unshift(n), 22 === e.code ? (this._isBufferFull || this._emitter.emit(c.default.BUFFER_FULL), this._isBufferFull = !0) : (l.default.e(this.TAG, e.message), this._emitter.emit(c.default.ERROR, { + code: e.code, + msg: e.message + })) + } + } + } + }, { + key: "_onSourceOpen", + value: function() { + if (l.default.v(this.TAG, "MediaSource onSourceOpen"), this._mediaSource.removeEventListener("sourceopen", this.e.onSourceOpen), this._pendingSourceBufferInit.length > 0) + for (var e = this._pendingSourceBufferInit; e.length;) { + var t = e.shift(); + this.appendInitSegment(t, !0) + } + this._hasPendingSegments() && this._doAppendSegments(), this._emitter.emit(c.default.SOURCE_OPEN) + } + }, { + key: "_onSourceEnded", + value: function() { + l.default.v(this.TAG, "MediaSource onSourceEnded") + } + }, { + key: "_onSourceClose", + value: function() { + l.default.v(this.TAG, "MediaSource onSourceClose"), this._mediaSource && null != this.e && (this._mediaSource.removeEventListener("sourceopen", this.e.onSourceOpen), this._mediaSource.removeEventListener("sourceended", this.e.onSourceEnded), this._mediaSource.removeEventListener("sourceclose", this.e.onSourceClose)) + } + }, { + key: "_hasPendingSegments", + value: function() { + var e = this._pendingSegments; + return e.video.length > 0 || e.audio.length > 0 + } + }, { + key: "_hasPendingRemoveRanges", + value: function() { + var e = this._pendingRemoveRanges; + return e.video.length > 0 || e.audio.length > 0 + } + }, { + key: "_onSourceBufferUpdateEnd", + value: function() { + this._requireSetMediaDuration ? this._updateMediaSourceDuration() : this._hasPendingRemoveRanges() ? this._doRemoveRanges() : this._hasPendingSegments() ? this._doAppendSegments() : this._hasPendingEos && this.endOfStream(), this._emitter.emit(c.default.UPDATE_END) + } + }, { + key: "_onSourceBufferError", + value: function(e) { + l.default.e(this.TAG, "SourceBuffer Error: " + e) + } + }]), e + }(); + n.default = p + }, { + "../utils/browser.js": 39, + "../utils/exception.js": 40, + "../utils/logger.js": 41, + "./media-segment-info.js": 8, + "./mse-events.js": 10, + events: 2 + }], + 10: [function(e, t, n) { + "use strict"; + Object.defineProperty(n, "__esModule", { + value: !0 + }); + var i = { + ERROR: "error", + SOURCE_OPEN: "source_open", + UPDATE_END: "update_end", + BUFFER_FULL: "buffer_full" + }; + n.default = i + }, {}], + 11: [function(e, t, n) { + "use strict"; + + function i(e) { + return e && e.__esModule ? e : { + default: e + } + } + + function r(e, t) { + if (!(e instanceof t)) throw new TypeError("Cannot call a class as a function") + } + Object.defineProperty(n, "__esModule", { + value: !0 + }); + var s = function() { + function e(e, t) { + for (var n = 0; n < t.length; n++) { + var i = t[n]; + i.enumerable = i.enumerable || !1, i.configurable = !0, "value" in i && (i.writable = !0), Object.defineProperty(e, i.key, i) + } + } + return function(t, n, i) { + return n && e(t.prototype, n), i && e(t, i), t + } + }(), + a = e("events"), + o = i(a), + u = e("../utils/logger.js"), + l = i(u), + d = e("../utils/logging-control.js"), + h = i(d), + f = e("./transmuxing-controller.js"), + c = i(f), + _ = e("./transmuxing-events.js"), + m = i(_), + p = e("./transmuxing-worker.js"), + v = i(p), + g = e("./media-info.js"), + y = i(g), + E = function() { + function t(n, i) { + if (r(this, t), this.TAG = "Transmuxer", this._emitter = new o.default, i.enableWorker && "undefined" != typeof Worker) try { + var s = e("webworkify"); + this._worker = s(v.default), this._workerDestroying = !1, this._worker.addEventListener("message", this._onWorkerMessage.bind(this)), this._worker.postMessage({ + cmd: "init", + param: [n, i] + }), this.e = { + onLoggingConfigChanged: this._onLoggingConfigChanged.bind(this) + }, h.default.registerListener(this.e.onLoggingConfigChanged), this._worker.postMessage({ + cmd: "logging_config", + param: h.default.getConfig() + }) + } catch (e) { + l.default.e(this.TAG, "Error while initialize transmuxing worker, fallback to inline transmuxing"), this._worker = null, this._controller = new c.default(n, i) + } else this._controller = new c.default(n, i); + if (this._controller) { + var a = this._controller; + a.on(m.default.IO_ERROR, this._onIOError.bind(this)), a.on(m.default.DEMUX_ERROR, this._onDemuxError.bind(this)), a.on(m.default.INIT_SEGMENT, this._onInitSegment.bind(this)), a.on(m.default.MEDIA_SEGMENT, this._onMediaSegment.bind(this)), a.on(m.default.LOADING_COMPLETE, this._onLoadingComplete.bind(this)), a.on(m.default.RECOVERED_EARLY_EOF, this._onRecoveredEarlyEof.bind(this)), a.on(m.default.MEDIA_INFO, this._onMediaInfo.bind(this)), a.on(m.default.STATISTICS_INFO, this._onStatisticsInfo.bind(this)), a.on(m.default.RECOMMEND_SEEKPOINT, this._onRecommendSeekpoint.bind(this)) + } + } + return s(t, [{ + key: "destroy", + value: function() { + this._worker ? this._workerDestroying || (this._workerDestroying = !0, this._worker.postMessage({ + cmd: "destroy" + }), h.default.removeListener(this.e.onLoggingConfigChanged), this.e = null) : (this._controller.destroy(), this._controller = null), this._emitter.removeAllListeners(), this._emitter = null + } + }, { + key: "on", + value: function(e, t) { + this._emitter.addListener(e, t) + } + }, { + key: "off", + value: function(e, t) { + this._emitter.removeListener(e, t) + } + }, { + key: "hasWorker", + value: function() { + return null != this._worker + } + }, { + key: "open", + value: function() { + this._worker ? this._worker.postMessage({ + cmd: "start" + }) : this._controller.start() + } + }, { + key: "close", + value: function() { + this._worker ? this._worker.postMessage({ + cmd: "stop" + }) : this._controller.stop() + } + }, { + key: "seek", + value: function(e) { + this._worker ? this._worker.postMessage({ + cmd: "seek", + param: e + }) : this._controller.seek(e) + } + }, { + key: "pause", + value: function() { + this._worker ? this._worker.postMessage({ + cmd: "pause" + }) : this._controller.pause() + } + }, { + key: "resume", + value: function() { + this._worker ? this._worker.postMessage({ + cmd: "resume" + }) : this._controller.resume() + } + }, { + key: "_onInitSegment", + value: function(e, t) { + var n = this; + Promise.resolve().then(function() { + n._emitter.emit(m.default.INIT_SEGMENT, e, t) + }) + } + }, { + key: "_onMediaSegment", + value: function(e, t) { + var n = this; + Promise.resolve().then(function() { + n._emitter.emit(m.default.MEDIA_SEGMENT, e, t) + }) + } + }, { + key: "_onLoadingComplete", + value: function() { + var e = this; + Promise.resolve().then(function() { + e._emitter.emit(m.default.LOADING_COMPLETE) + }) + } + }, { + key: "_onRecoveredEarlyEof", + value: function() { + var e = this; + Promise.resolve().then(function() { + e._emitter.emit(m.default.RECOVERED_EARLY_EOF) + }) + } + }, { + key: "_onMediaInfo", + value: function(e) { + var t = this; + Promise.resolve().then(function() { + t._emitter.emit(m.default.MEDIA_INFO, e) + }) + } + }, { + key: "_onStatisticsInfo", + value: function(e) { + var t = this; + Promise.resolve().then(function() { + t._emitter.emit(m.default.STATISTICS_INFO, e) + }) + } + }, { + key: "_onIOError", + value: function(e, t) { + var n = this; + Promise.resolve().then(function() { + n._emitter.emit(m.default.IO_ERROR, e, t) + }) + } + }, { + key: "_onDemuxError", + value: function(e, t) { + var n = this; + Promise.resolve().then(function() { + n._emitter.emit(m.default.DEMUX_ERROR, e, t) + }) + } + }, { + key: "_onRecommendSeekpoint", + value: function(e) { + var t = this; + Promise.resolve().then(function() { + t._emitter.emit(m.default.RECOMMEND_SEEKPOINT, e) + }) + } + }, { + key: "_onLoggingConfigChanged", + value: function(e) { + this._worker && this._worker.postMessage({ + cmd: "logging_config", + param: e + }) + } + }, { + key: "_onWorkerMessage", + value: function(e) { + var t = e.data, + n = t.data; + if ("destroyed" === t.msg || this._workerDestroying) return this._workerDestroying = !1, this._worker.terminate(), void(this._worker = null); + switch (t.msg) { + case m.default.INIT_SEGMENT: + case m.default.MEDIA_SEGMENT: + this._emitter.emit(t.msg, n.type, n.data); + break; + case m.default.LOADING_COMPLETE: + case m.default.RECOVERED_EARLY_EOF: + this._emitter.emit(t.msg); + break; + case m.default.MEDIA_INFO: + Object.setPrototypeOf(n, y.default.prototype), this._emitter.emit(t.msg, n); + break; + case m.default.STATISTICS_INFO: + this._emitter.emit(t.msg, n); + break; + case m.default.IO_ERROR: + case m.default.DEMUX_ERROR: + this._emitter.emit(t.msg, n.type, n.info); + break; + case m.default.RECOMMEND_SEEKPOINT: + this._emitter.emit(t.msg, n); + break; + case "logcat_callback": + l.default.emitter.emit("log", n.type, n.logcat) + } + } + }]), t + }(); + n.default = E + }, { + "../utils/logger.js": 41, + "../utils/logging-control.js": 42, + "./media-info.js": 7, + "./transmuxing-controller.js": 12, + "./transmuxing-events.js": 13, + "./transmuxing-worker.js": 14, + events: 2, + webworkify: 4 + }], + 12: [function(e, t, n) { + "use strict"; + + function i(e) { + return e && e.__esModule ? e : { + default: e + } + } + + function r(e, t) { + if (!(e instanceof t)) throw new TypeError("Cannot call a class as a function") + } + Object.defineProperty(n, "__esModule", { + value: !0 + }); + var s = function() { + function e(e, t) { + for (var n = 0; n < t.length; n++) { + var i = t[n]; + i.enumerable = i.enumerable || !1, i.configurable = !0, "value" in i && (i.writable = !0), Object.defineProperty(e, i.key, i) + } + } + return function(t, n, i) { + return n && e(t.prototype, n), i && e(t, i), t + } + }(), + a = e("events"), + o = i(a), + u = e("../utils/logger.js"), + l = i(u), + d = e("../utils/browser.js"), + h = i(d), + f = e("./media-info.js"), + c = i(f), + _ = e("../demux/flv-demuxer.js"), + m = i(_), + p = e("../remux/mp4-remuxer.js"), + v = i(p), + g = e("../demux/demux-errors.js"), + y = i(g), + E = e("../io/io-controller.js"), + b = i(E), + S = e("./transmuxing-events.js"), + k = i(S), + L = (e("../io/loader.js"), function() { + function e(t, n) { + r(this, e), this.TAG = "TransmuxingController", this._emitter = new o.default, this._config = n, t.segments || (t.segments = [{ + duration: t.duration, + filesize: t.filesize, + url: t.url + }]), "boolean" != typeof t.cors && (t.cors = !0), "boolean" != typeof t.withCredentials && (t.withCredentials = !1), this._mediaDataSource = t, this._currentSegmentIndex = 0; + var i = 0; + this._mediaDataSource.segments.forEach(function(e) { + e.timestampBase = i, i += e.duration, e.cors = t.cors, e.withCredentials = t.withCredentials, n.referrerPolicy && (e.referrerPolicy = n.referrerPolicy) + }), isNaN(i) || this._mediaDataSource.duration === i || (this._mediaDataSource.duration = i), this._mediaInfo = null, this._demuxer = null, this._remuxer = null, this._ioctl = null, this._pendingSeekTime = null, this._pendingResolveSeekPoint = null, this._statisticsReporter = null + } + return s(e, [{ + key: "destroy", + value: function() { + this._mediaInfo = null, this._mediaDataSource = null, this._statisticsReporter && this._disableStatisticsReporter(), this._ioctl && (this._ioctl.destroy(), this._ioctl = null), this._demuxer && (this._demuxer.destroy(), this._demuxer = null), this._remuxer && (this._remuxer.destroy(), this._remuxer = null), this._emitter.removeAllListeners(), this._emitter = null + } + }, { + key: "on", + value: function(e, t) { + this._emitter.addListener(e, t) + } + }, { + key: "off", + value: function(e, t) { + this._emitter.removeListener(e, t) + } + }, { + key: "start", + value: function() { + this._loadSegment(0), this._enableStatisticsReporter() + } + }, { + key: "_loadSegment", + value: function(e, t) { + this._currentSegmentIndex = e; + var n = this._mediaDataSource.segments[e], + i = this._ioctl = new b.default(n, this._config, e); + i.onError = this._onIOException.bind(this), i.onSeeked = this._onIOSeeked.bind(this), i.onComplete = this._onIOComplete.bind(this), i.onRedirect = this._onIORedirect.bind(this), i.onRecoveredEarlyEof = this._onIORecoveredEarlyEof.bind(this), t ? this._demuxer.bindDataSource(this._ioctl) : i.onDataArrival = this._onInitChunkArrival.bind(this), i.open(t) + } + }, { + key: "stop", + value: function() { + this._internalAbort(), this._disableStatisticsReporter() + } + }, { + key: "_internalAbort", + value: function() { + this._ioctl && (this._ioctl.destroy(), this._ioctl = null) + } + }, { + key: "pause", + value: function() { + this._ioctl && this._ioctl.isWorking() && (this._ioctl.pause(), this._disableStatisticsReporter()) + } + }, { + key: "resume", + value: function() { + this._ioctl && this._ioctl.isPaused() && (this._ioctl.resume(), this._enableStatisticsReporter()) + } + }, { + key: "seek", + value: function(e) { + if (null != this._mediaInfo && this._mediaInfo.isSeekable()) { + var t = this._searchSegmentIndexContains(e); + if (t === this._currentSegmentIndex) { + var n = this._mediaInfo.segments[t]; + if (void 0 == n) this._pendingSeekTime = e; + else { + var i = n.getNearestKeyframe(e); + this._remuxer.seek(i.milliseconds), this._ioctl.seek(i.fileposition), this._pendingResolveSeekPoint = i.milliseconds + } + } else { + var r = this._mediaInfo.segments[t]; + if (void 0 == r) this._pendingSeekTime = e, this._internalAbort(), this._remuxer.seek(), this._remuxer.insertDiscontinuity(), this._loadSegment(t); + else { + var s = r.getNearestKeyframe(e); + this._internalAbort(), this._remuxer.seek(e), this._remuxer.insertDiscontinuity(), this._demuxer.resetMediaInfo(), this._demuxer.timestampBase = this._mediaDataSource.segments[t].timestampBase, this._loadSegment(t, s.fileposition), this._pendingResolveSeekPoint = s.milliseconds, this._reportSegmentMediaInfo(t) + } + } + this._enableStatisticsReporter() + } + } + }, { + key: "_searchSegmentIndexContains", + value: function(e) { + for (var t = this._mediaDataSource.segments, n = t.length - 1, i = 0; i < t.length; i++) + if (e < t[i].timestampBase) { + n = i - 1; + break + } return n + } + }, { + key: "_onInitChunkArrival", + value: function(e, t) { + var n = this, + i = null, + r = 0; + if (t > 0) this._demuxer.bindDataSource(this._ioctl), this._demuxer.timestampBase = this._mediaDataSource.segments[this._currentSegmentIndex].timestampBase, r = this._demuxer.parseChunks(e, t); + else if ((i = m.default.probe(e)).match) { + this._demuxer = new m.default(i, this._config), this._remuxer || (this._remuxer = new v.default(this._config)); + var s = this._mediaDataSource; + void 0 == s.duration || isNaN(s.duration) || (this._demuxer.overridedDuration = s.duration), "boolean" == typeof s.hasAudio && (this._demuxer.overridedHasAudio = s.hasAudio), "boolean" == typeof s.hasVideo && (this._demuxer.overridedHasVideo = s.hasVideo), this._demuxer.timestampBase = s.segments[this._currentSegmentIndex].timestampBase, this._demuxer.onError = this._onDemuxException.bind(this), this._demuxer.onMediaInfo = this._onMediaInfo.bind(this), this._remuxer.bindDataSource(this._demuxer.bindDataSource(this._ioctl)), this._remuxer.onInitSegment = this._onRemuxerInitSegmentArrival.bind(this), this._remuxer.onMediaSegment = this._onRemuxerMediaSegmentArrival.bind(this), r = this._demuxer.parseChunks(e, t) + } else i = null, l.default.e(this.TAG, "Non-FLV, Unsupported media type!"), Promise.resolve().then(function() { + n._internalAbort() + }), this._emitter.emit(k.default.DEMUX_ERROR, y.default.FORMAT_UNSUPPORTED, "Non-FLV, Unsupported media type"), r = 0; + return r + } + }, { + key: "_onMediaInfo", + value: function(e) { + var t = this; + null == this._mediaInfo && (this._mediaInfo = Object.assign({}, e), this._mediaInfo.keyframesIndex = null, this._mediaInfo.segments = [], this._mediaInfo.segmentCount = this._mediaDataSource.segments.length, Object.setPrototypeOf(this._mediaInfo, c.default.prototype)); + var n = Object.assign({}, e); + Object.setPrototypeOf(n, c.default.prototype), this._mediaInfo.segments[this._currentSegmentIndex] = n, this._reportSegmentMediaInfo(this._currentSegmentIndex), null != this._pendingSeekTime && Promise.resolve().then(function() { + var e = t._pendingSeekTime; + t._pendingSeekTime = null, t.seek(e) + }) + } + }, { + key: "_onIOSeeked", + value: function() { + this._remuxer.insertDiscontinuity() + } + }, { + key: "_onIOComplete", + value: function(e) { + var t = e, + n = t + 1; + n < this._mediaDataSource.segments.length ? (this._internalAbort(), this._remuxer.flushStashedSamples(), this._loadSegment(n)) : (this._remuxer.flushStashedSamples(), this._emitter.emit(k.default.LOADING_COMPLETE), this._disableStatisticsReporter()) + } + }, { + key: "_onIORedirect", + value: function(e) { + var t = this._ioctl.extraData; + this._mediaDataSource.segments[t].redirectedURL = e + } + }, { + key: "_onIORecoveredEarlyEof", + value: function() { + this._emitter.emit(k.default.RECOVERED_EARLY_EOF) + } + }, { + key: "_onIOException", + value: function(e, t) { + l.default.e(this.TAG, "IOException: type = " + e + ", code = " + t.code + ", msg = " + t.msg), this._emitter.emit(k.default.IO_ERROR, e, t), this._disableStatisticsReporter() + } + }, { + key: "_onDemuxException", + value: function(e, t) { + l.default.e(this.TAG, "DemuxException: type = " + e + ", info = " + t), this._emitter.emit(k.default.DEMUX_ERROR, e, t) + } + }, { + key: "_onRemuxerInitSegmentArrival", + value: function(e, t) { + this._emitter.emit(k.default.INIT_SEGMENT, e, t) + } + }, { + key: "_onRemuxerMediaSegmentArrival", + value: function(e, t) { + if (null == this._pendingSeekTime && (this._emitter.emit(k.default.MEDIA_SEGMENT, e, t), null != this._pendingResolveSeekPoint && "video" === e)) { + var n = t.info.syncPoints, + i = this._pendingResolveSeekPoint; + this._pendingResolveSeekPoint = null, h.default.safari && n.length > 0 && n[0].originalDts === i && (i = n[0].pts), this._emitter.emit(k.default.RECOMMEND_SEEKPOINT, i) + } + } + }, { + key: "_enableStatisticsReporter", + value: function() { + null == this._statisticsReporter && (this._statisticsReporter = self.setInterval(this._reportStatisticsInfo.bind(this), this._config.statisticsInfoReportInterval)) + } + }, { + key: "_disableStatisticsReporter", + value: function() { + this._statisticsReporter && (self.clearInterval(this._statisticsReporter), this._statisticsReporter = null) + } + }, { + key: "_reportSegmentMediaInfo", + value: function(e) { + var t = this._mediaInfo.segments[e], + n = Object.assign({}, t); + n.duration = this._mediaInfo.duration, n.segmentCount = this._mediaInfo.segmentCount, delete n.segments, delete n.keyframesIndex, this._emitter.emit(k.default.MEDIA_INFO, n) + } + }, { + key: "_reportStatisticsInfo", + value: function() { + var e = {}; + e.url = this._ioctl.currentURL, e.hasRedirect = this._ioctl.hasRedirect, e.hasRedirect && (e.redirectedURL = this._ioctl.currentRedirectedURL), e.speed = this._ioctl.currentSpeed, e.loaderType = this._ioctl.loaderType, e.currentSegmentIndex = this._currentSegmentIndex, e.totalSegmentCount = this._mediaDataSource.segments.length, this._emitter.emit(k.default.STATISTICS_INFO, e) + } + }]), e + }()); + n.default = L + }, { + "../demux/demux-errors.js": 16, + "../demux/flv-demuxer.js": 18, + "../io/io-controller.js": 23, + "../io/loader.js": 24, + "../remux/mp4-remuxer.js": 38, + "../utils/browser.js": 39, + "../utils/logger.js": 41, + "./media-info.js": 7, + "./transmuxing-events.js": 13, + events: 2 + }], + 13: [function(e, t, n) { + "use strict"; + Object.defineProperty(n, "__esModule", { + value: !0 + }); + var i = { + IO_ERROR: "io_error", + DEMUX_ERROR: "demux_error", + INIT_SEGMENT: "init_segment", + MEDIA_SEGMENT: "media_segment", + LOADING_COMPLETE: "loading_complete", + RECOVERED_EARLY_EOF: "recovered_early_eof", + MEDIA_INFO: "media_info", + STATISTICS_INFO: "statistics_info", + RECOMMEND_SEEKPOINT: "recommend_seekpoint" + }; + n.default = i + }, {}], + 14: [function(e, t, n) { + "use strict"; + + function i(e) { + return e && e.__esModule ? e : { + default: e + } + } + Object.defineProperty(n, "__esModule", { + value: !0 + }); + var r = e("../utils/logger.js"), + s = (i(r), e("../utils/logging-control.js")), + a = i(s), + o = e("../utils/polyfill.js"), + u = i(o), + l = e("./transmuxing-controller.js"), + d = i(l), + h = e("./transmuxing-events.js"), + f = i(h), + c = function(e) { + function t(t, n) { + var i = { + msg: f.default.INIT_SEGMENT, + data: { + type: t, + data: n + } + }; + e.postMessage(i, [n.data]) + } + + function n(t, n) { + var i = { + msg: f.default.MEDIA_SEGMENT, + data: { + type: t, + data: n + } + }; + e.postMessage(i, [n.data]) + } + + function i() { + var t = { + msg: f.default.LOADING_COMPLETE + }; + e.postMessage(t) + } + + function r() { + var t = { + msg: f.default.RECOVERED_EARLY_EOF + }; + e.postMessage(t) + } + + function s(t) { + var n = { + msg: f.default.MEDIA_INFO, + data: t + }; + e.postMessage(n) + } + + function o(t) { + var n = { + msg: f.default.STATISTICS_INFO, + data: t + }; + e.postMessage(n) + } + + function l(t, n) { + e.postMessage({ + msg: f.default.IO_ERROR, + data: { + type: t, + info: n + } + }) + } + + function h(t, n) { + e.postMessage({ + msg: f.default.DEMUX_ERROR, + data: { + type: t, + info: n + } + }) + } + + function c(t) { + e.postMessage({ + msg: f.default.RECOMMEND_SEEKPOINT, + data: t + }) + } + + function _(t, n) { + e.postMessage({ + msg: "logcat_callback", + data: { + type: t, + logcat: n + } + }) + } + var m = null, + p = _.bind(this); + u.default.install(), e.addEventListener("message", function(u) { + switch (u.data.cmd) { + case "init": + m = new d.default(u.data.param[0], u.data.param[1]), m.on(f.default.IO_ERROR, l.bind(this)), m.on(f.default.DEMUX_ERROR, h.bind(this)), m.on(f.default.INIT_SEGMENT, t.bind(this)), m.on(f.default.MEDIA_SEGMENT, n.bind(this)), m.on(f.default.LOADING_COMPLETE, i.bind(this)), m.on(f.default.RECOVERED_EARLY_EOF, r.bind(this)), m.on(f.default.MEDIA_INFO, s.bind(this)), m.on(f.default.STATISTICS_INFO, o.bind(this)), m.on(f.default.RECOMMEND_SEEKPOINT, c.bind(this)); + break; + case "destroy": + m && (m.destroy(), m = null), e.postMessage({ + msg: "destroyed" + }); + break; + case "start": + m.start(); + break; + case "stop": + m.stop(); + break; + case "seek": + m.seek(u.data.param); + break; + case "pause": + m.pause(); + break; + case "resume": + m.resume(); + break; + case "logging_config": + var _ = u.data.param; + a.default.applyConfig(_), !0 === _.enableCallback ? a.default.addLogListener(p) : a.default.removeLogListener(p) + } + }) + }; + n.default = c + }, { + "../utils/logger.js": 41, + "../utils/logging-control.js": 42, + "../utils/polyfill.js": 43, + "./transmuxing-controller.js": 12, + "./transmuxing-events.js": 13 + }], + 15: [function(e, t, n) { + "use strict"; + + function i(e) { + return e && e.__esModule ? e : { + default: e + } + } + + function r(e, t) { + if (!(e instanceof t)) throw new TypeError("Cannot call a class as a function") + } + Object.defineProperty(n, "__esModule", { + value: !0 + }); + var s = function() { + function e(e, t) { + for (var n = 0; n < t.length; n++) { + var i = t[n]; + i.enumerable = i.enumerable || !1, i.configurable = !0, "value" in i && (i.writable = !0), Object.defineProperty(e, i.key, i) + } + } + return function(t, n, i) { + return n && e(t.prototype, n), i && e(t, i), t + } + }(), + a = e("../utils/logger.js"), + o = i(a), + u = e("../utils/utf8-conv.js"), + l = i(u), + d = e("../utils/exception.js"), + h = function() { + var e = new ArrayBuffer(2); + return new DataView(e).setInt16(0, 256, !0), 256 === new Int16Array(e)[0] + }(), + f = function() { + function e() { + r(this, e) + } + return s(e, null, [{ + key: "parseScriptData", + value: function(t, n, i) { + var r = {}; + try { + var s = e.parseValue(t, n, i), + a = e.parseValue(t, n + s.size, i - s.size); + r[s.data] = a.data + } catch (e) { + o.default.e("AMF", e.toString()) + } + return r + } + }, { + key: "parseObject", + value: function(t, n, i) { + if (i < 3) throw new d.IllegalStateException("Data not enough when parse ScriptDataObject"); + var r = e.parseString(t, n, i), + s = e.parseValue(t, n + r.size, i - r.size), + a = s.objectEnd; + return { + data: { + name: r.data, + value: s.data + }, + size: r.size + s.size, + objectEnd: a + } + } + }, { + key: "parseVariable", + value: function(t, n, i) { + return e.parseObject(t, n, i) + } + }, { + key: "parseString", + value: function(e, t, n) { + if (n < 2) throw new d.IllegalStateException("Data not enough when parse String"); + var i = new DataView(e, t, n), + r = i.getUint16(0, !h), + s = void 0; + return s = r > 0 ? (0, l.default)(new Uint8Array(e, t + 2, r)) : "", { + data: s, + size: 2 + r + } + } + }, { + key: "parseLongString", + value: function(e, t, n) { + if (n < 4) throw new d.IllegalStateException("Data not enough when parse LongString"); + var i = new DataView(e, t, n), + r = i.getUint32(0, !h), + s = void 0; + return s = r > 0 ? (0, l.default)(new Uint8Array(e, t + 4, r)) : "", { + data: s, + size: 4 + r + } + } + }, { + key: "parseDate", + value: function(e, t, n) { + if (n < 10) throw new d.IllegalStateException("Data size invalid when parse Date"); + var i = new DataView(e, t, n), + r = i.getFloat64(0, !h); + return r += 60 * i.getInt16(8, !h) * 1e3, { + data: new Date(r), + size: 10 + } + } + }, { + key: "parseValue", + value: function(t, n, i) { + if (i < 1) throw new d.IllegalStateException("Data not enough when parse Value"); + var r = new DataView(t, n, i), + s = 1, + a = r.getUint8(0), + u = void 0, + l = !1; + try { + switch (a) { + case 0: + u = r.getFloat64(1, !h), s += 8; + break; + case 1: + u = !!r.getUint8(1), s += 1; + break; + case 2: + var f = e.parseString(t, n + 1, i - 1); + u = f.data, s += f.size; + break; + case 3: + u = {}; + var c = 0; + for (9 == (16777215 & r.getUint32(i - 4, !h)) && (c = 3); s < i - 4;) { + var _ = e.parseObject(t, n + s, i - s - c); + if (_.objectEnd) break; + u[_.data.name] = _.data.value, s += _.size + } + if (s <= i - 3) { + 9 === (16777215 & r.getUint32(s - 1, !h)) && (s += 3) + } + break; + case 8: + u = {}, s += 4; + var m = 0; + for (9 == (16777215 & r.getUint32(i - 4, !h)) && (m = 3); s < i - 8;) { + var p = e.parseVariable(t, n + s, i - s - m); + if (p.objectEnd) break; + u[p.data.name] = p.data.value, s += p.size + } + if (s <= i - 3) { + 9 === (16777215 & r.getUint32(s - 1, !h)) && (s += 3) + } + break; + case 9: + u = void 0, s = 1, l = !0; + break; + case 10: + u = []; + var v = r.getUint32(1, !h); + s += 4; + for (var g = 0; g < v; g++) { + var y = e.parseValue(t, n + s, i - s); + u.push(y.data), s += y.size + } + break; + case 11: + var E = e.parseDate(t, n + 1, i - 1); + u = E.data, s += E.size; + break; + case 12: + var b = e.parseString(t, n + 1, i - 1); + u = b.data, s += b.size; + break; + default: + s = i, o.default.w("AMF", "Unsupported AMF value type " + a) + } + } catch (e) { + o.default.e("AMF", e.toString()) + } + return { + data: u, + size: s, + objectEnd: l + } + } + }]), e + }(); + n.default = f + }, { + "../utils/exception.js": 40, + "../utils/logger.js": 41, + "../utils/utf8-conv.js": 44 + }], + 16: [function(e, t, n) { + "use strict"; + Object.defineProperty(n, "__esModule", { + value: !0 + }); + var i = { + OK: "OK", + FORMAT_ERROR: "FormatError", + FORMAT_UNSUPPORTED: "FormatUnsupported", + CODEC_UNSUPPORTED: "CodecUnsupported" + }; + n.default = i + }, {}], + 17: [function(e, t, n) { + "use strict"; + + function i(e, t) { + if (!(e instanceof t)) throw new TypeError("Cannot call a class as a function") + } + Object.defineProperty(n, "__esModule", { + value: !0 + }); + var r = function() { + function e(e, t) { + for (var n = 0; n < t.length; n++) { + var i = t[n]; + i.enumerable = i.enumerable || !1, i.configurable = !0, "value" in i && (i.writable = !0), Object.defineProperty(e, i.key, i) + } + } + return function(t, n, i) { + return n && e(t.prototype, n), i && e(t, i), t + } + }(), + s = e("../utils/exception.js"), + a = function() { + function e(t) { + i(this, e), this.TAG = "ExpGolomb", this._buffer = t, this._buffer_index = 0, this._total_bytes = t.byteLength, this._total_bits = 8 * t.byteLength, this._current_word = 0, this._current_word_bits_left = 0 + } + return r(e, [{ + key: "destroy", + value: function() { + this._buffer = null + } + }, { + key: "_fillCurrentWord", + value: function() { + var e = this._total_bytes - this._buffer_index; + if (e <= 0) throw new s.IllegalStateException("ExpGolomb: _fillCurrentWord() but no bytes available"); + var t = Math.min(4, e), + n = new Uint8Array(4); + n.set(this._buffer.subarray(this._buffer_index, this._buffer_index + t)), this._current_word = new DataView(n.buffer).getUint32(0, !1), this._buffer_index += t, this._current_word_bits_left = 8 * t + } + }, { + key: "readBits", + value: function(e) { + if (e > 32) throw new s.InvalidArgumentException("ExpGolomb: readBits() bits exceeded max 32bits!"); + if (e <= this._current_word_bits_left) { + var t = this._current_word >>> 32 - e; + return this._current_word <<= e, this._current_word_bits_left -= e, t + } + var n = this._current_word_bits_left ? this._current_word : 0; + n >>>= 32 - this._current_word_bits_left; + var i = e - this._current_word_bits_left; + this._fillCurrentWord(); + var r = Math.min(i, this._current_word_bits_left), + a = this._current_word >>> 32 - r; + return this._current_word <<= r, this._current_word_bits_left -= r, n = n << r | a + } + }, { + key: "readBool", + value: function() { + return 1 === this.readBits(1) + } + }, { + key: "readByte", + value: function() { + return this.readBits(8) + } + }, { + key: "_skipLeadingZero", + value: function() { + var e = void 0; + for (e = 0; e < this._current_word_bits_left; e++) + if (0 != (this._current_word & 2147483648 >>> e)) return this._current_word <<= e, this._current_word_bits_left -= e, e; + return this._fillCurrentWord(), e + this._skipLeadingZero() + } + }, { + key: "readUEG", + value: function() { + var e = this._skipLeadingZero(); + return this.readBits(e + 1) - 1 + } + }, { + key: "readSEG", + value: function() { + var e = this.readUEG(); + return 1 & e ? e + 1 >>> 1 : -1 * (e >>> 1) + } + }]), e + }(); + n.default = a + }, { + "../utils/exception.js": 40 + }], + 18: [function(e, t, n) { + "use strict"; + + function i(e) { + return e && e.__esModule ? e : { + default: e + } + } + + function r(e, t) { + if (!(e instanceof t)) throw new TypeError("Cannot call a class as a function") + } + + function s(e, t) { + return e[t] << 24 | e[t + 1] << 16 | e[t + 2] << 8 | e[t + 3] + } + Object.defineProperty(n, "__esModule", { + value: !0 + }); + var a = "function" == typeof Symbol && "symbol" == typeof Symbol.iterator ? function(e) { + return typeof e + } : function(e) { + return e && "function" == typeof Symbol && e.constructor === Symbol && e !== Symbol.prototype ? "symbol" : typeof e + }, + o = function() { + function e(e, t) { + for (var n = 0; n < t.length; n++) { + var i = t[n]; + i.enumerable = i.enumerable || !1, i.configurable = !0, "value" in i && (i.writable = !0), Object.defineProperty(e, i.key, i) + } + } + return function(t, n, i) { + return n && e(t.prototype, n), i && e(t, i), t + } + }(), + u = e("../utils/logger.js"), + l = i(u), + d = e("./amf-parser.js"), + h = i(d), + f = e("./sps-parser.js"), + c = i(f), + _ = e("./demux-errors.js"), + m = i(_), + p = e("../core/media-info.js"), + v = i(p), + g = e("../utils/exception.js"), + y = function() { + function e(t, n) { + r(this, e), this.TAG = "FLVDemuxer", this._config = n, this._onError = null, this._onMediaInfo = null, this._onTrackMetadata = null, this._onDataAvailable = null, this._dataOffset = t.dataOffset, this._firstParse = !0, this._dispatch = !1, this._hasAudio = t.hasAudioTrack, this._hasVideo = t.hasVideoTrack, this._hasAudioFlagOverrided = !1, this._hasVideoFlagOverrided = !1, this._audioInitialMetadataDispatched = !1, this._videoInitialMetadataDispatched = !1, this._mediaInfo = new v.default, this._mediaInfo.hasAudio = this._hasAudio, this._mediaInfo.hasVideo = this._hasVideo, this._metadata = null, this._audioMetadata = null, this._videoMetadata = null, this._naluLengthSize = 4, this._timestampBase = 0, this._timescale = 1e3, this._duration = 0, this._durationOverrided = !1, this._referenceFrameRate = { + fixed: !0, + fps: 23.976, + fps_num: 23976, + fps_den: 1e3 + }, this._flvSoundRateTable = [5500, 11025, 22050, 44100, 48e3], this._mpegSamplingRates = [96e3, 88200, 64e3, 48e3, 44100, 32e3, 24e3, 22050, 16e3, 12e3, 11025, 8e3, 7350], this._mpegAudioV10SampleRateTable = [44100, 48e3, 32e3, 0], this._mpegAudioV20SampleRateTable = [22050, 24e3, 16e3, 0], this._mpegAudioV25SampleRateTable = [11025, 12e3, 8e3, 0], this._mpegAudioL1BitRateTable = [0, 32, 64, 96, 128, 160, 192, 224, 256, 288, 320, 352, 384, 416, 448, -1], this._mpegAudioL2BitRateTable = [0, 32, 48, 56, 64, 80, 96, 112, 128, 160, 192, 224, 256, 320, 384, -1], this._mpegAudioL3BitRateTable = [0, 32, 40, 48, 56, 64, 80, 96, 112, 128, 160, 192, 224, 256, 320, -1], this._videoTrack = { + type: "video", + id: 1, + sequenceNumber: 0, + samples: [], + length: 0 + }, this._audioTrack = { + type: "audio", + id: 2, + sequenceNumber: 0, + samples: [], + length: 0 + }, this._littleEndian = function() { + var e = new ArrayBuffer(2); + return new DataView(e).setInt16(0, 256, !0), 256 === new Int16Array(e)[0] + }() + } + return o(e, [{ + key: "destroy", + value: function() { + this._mediaInfo = null, this._metadata = null, this._audioMetadata = null, this._videoMetadata = null, this._videoTrack = null, this._audioTrack = null, this._onError = null, this._onMediaInfo = null, this._onTrackMetadata = null, this._onDataAvailable = null + } + }, { + key: "bindDataSource", + value: function(e) { + return e.onDataArrival = this.parseChunks.bind(this), this + } + }, { + key: "resetMediaInfo", + value: function() { + this._mediaInfo = new v.default + } + }, { + key: "_isInitialMetadataDispatched", + value: function() { + return this._hasAudio && this._hasVideo ? this._audioInitialMetadataDispatched && this._videoInitialMetadataDispatched : this._hasAudio && !this._hasVideo ? this._audioInitialMetadataDispatched : !(this._hasAudio || !this._hasVideo) && this._videoInitialMetadataDispatched + } + }, { + key: "parseChunks", + value: function(t, n) { + if (!(this._onError && this._onMediaInfo && this._onTrackMetadata && this._onDataAvailable)) throw new g.IllegalStateException("Flv: onError & onMediaInfo & onTrackMetadata & onDataAvailable callback must be specified"); + var i = 0, + r = this._littleEndian; + if (0 === n) { + if (!(t.byteLength > 13)) return 0; + i = e.probe(t).dataOffset + } + if (this._firstParse) { + this._firstParse = !1, n + i !== this._dataOffset && l.default.w(this.TAG, "First time parsing but chunk byteStart invalid!"); + 0 !== new DataView(t, i).getUint32(0, !r) && l.default.w(this.TAG, "PrevTagSize0 !== 0 !!!"), i += 4 + } + for (; i < t.byteLength;) { + this._dispatch = !0; + var s = new DataView(t, i); + if (i + 11 + 4 > t.byteLength) break; + var a = s.getUint8(0), + o = 16777215 & s.getUint32(0, !r); + if (i + 11 + o + 4 > t.byteLength) break; + if (8 === a || 9 === a || 18 === a) { + var u = s.getUint8(4), + d = s.getUint8(5), + h = s.getUint8(6), + f = s.getUint8(7), + c = h | d << 8 | u << 16 | f << 24; + 0 !== (16777215 & s.getUint32(7, !r)) && l.default.w(this.TAG, "Meet tag which has StreamID != 0!"); + var _ = i + 11; + switch (a) { + case 8: + this._parseAudioData(t, _, o, c); + break; + case 9: + this._parseVideoData(t, _, o, c, n + i); + break; + case 18: + this._parseScriptData(t, _, o) + } + var m = s.getUint32(11 + o, !r); + m !== 11 + o && l.default.w(this.TAG, "Invalid PrevTagSize " + m), i += 11 + o + 4 + } else l.default.w(this.TAG, "Unsupported tag type " + a + ", skipped"), i += 11 + o + 4 + } + return this._isInitialMetadataDispatched() && this._dispatch && (this._audioTrack.length || this._videoTrack.length) && this._onDataAvailable(this._audioTrack, this._videoTrack), i + } + }, { + key: "_parseScriptData", + value: function(e, t, n) { + var i = h.default.parseScriptData(e, t, n); + if (i.hasOwnProperty("onMetaData")) { + if (null == i.onMetaData || "object" !== a(i.onMetaData)) return void l.default.w(this.TAG, "Invalid onMetaData structure!"); + this._metadata && l.default.w(this.TAG, "Found another onMetaData tag!"), this._metadata = i; + var r = this._metadata.onMetaData; + if ("boolean" == typeof r.hasAudio && !1 === this._hasAudioFlagOverrided && (this._hasAudio = r.hasAudio, this._mediaInfo.hasAudio = this._hasAudio), "boolean" == typeof r.hasVideo && !1 === this._hasVideoFlagOverrided && (this._hasVideo = r.hasVideo, this._mediaInfo.hasVideo = this._hasVideo), "number" == typeof r.audiodatarate && (this._mediaInfo.audioDataRate = r.audiodatarate), "number" == typeof r.videodatarate && (this._mediaInfo.videoDataRate = r.videodatarate), "number" == typeof r.width && (this._mediaInfo.width = r.width), "number" == typeof r.height && (this._mediaInfo.height = r.height), "number" == typeof r.duration) { + if (!this._durationOverrided) { + var s = Math.floor(r.duration * this._timescale); + this._duration = s, this._mediaInfo.duration = s + } + } else this._mediaInfo.duration = 0; + if ("number" == typeof r.framerate) { + var o = Math.floor(1e3 * r.framerate); + if (o > 0) { + var u = o / 1e3; + this._referenceFrameRate.fixed = !0, this._referenceFrameRate.fps = u, this._referenceFrameRate.fps_num = o, this._referenceFrameRate.fps_den = 1e3, this._mediaInfo.fps = u + } + } + if ("object" === a(r.keyframes)) { + this._mediaInfo.hasKeyframesIndex = !0; + var d = r.keyframes; + this._mediaInfo.keyframesIndex = this._parseKeyframesIndex(d), r.keyframes = null + } else this._mediaInfo.hasKeyframesIndex = !1; + this._dispatch = !1, this._mediaInfo.metadata = r, l.default.v(this.TAG, "Parsed onMetaData"), this._mediaInfo.isComplete() && this._onMediaInfo(this._mediaInfo) + } + } + }, { + key: "_parseKeyframesIndex", + value: function(e) { + for (var t = [], n = [], i = 1; i < e.times.length; i++) { + var r = this._timestampBase + Math.floor(1e3 * e.times[i]); + t.push(r), n.push(e.filepositions[i]) + } + return { + times: t, + filepositions: n + } + } + }, { + key: "_parseAudioData", + value: function(e, t, n, i) { + if (n <= 1) return void l.default.w(this.TAG, "Flv: Invalid audio packet, missing SoundData payload!"); + if (!0 !== this._hasAudioFlagOverrided || !1 !== this._hasAudio) { + var r = (this._littleEndian, new DataView(e, t, n)), + s = r.getUint8(0), + a = s >>> 4; + if (2 !== a && 10 !== a) return void this._onError(m.default.CODEC_UNSUPPORTED, "Flv: Unsupported audio codec idx: " + a); + var o = 0, + u = (12 & s) >>> 2; + if (!(u >= 0 && u <= 4)) return void this._onError(m.default.FORMAT_ERROR, "Flv: Invalid audio sample rate idx: " + u); + o = this._flvSoundRateTable[u]; + var d = 1 & s, + h = this._audioMetadata, + f = this._audioTrack; + if (h || (!1 === this._hasAudio && !1 === this._hasAudioFlagOverrided && (this._hasAudio = !0, this._mediaInfo.hasAudio = !0), h = this._audioMetadata = {}, h.type = "audio", h.id = f.id, h.timescale = this._timescale, h.duration = this._duration, h.audioSampleRate = o, h.channelCount = 0 === d ? 1 : 2), 10 === a) { + var c = this._parseAACAudioData(e, t + 1, n - 1); + if (void 0 == c) return; + if (0 === c.packetType) { + h.config && l.default.w(this.TAG, "Found another AudioSpecificConfig!"); + var _ = c.data; + h.audioSampleRate = _.samplingRate, h.channelCount = _.channelCount, h.codec = _.codec, h.originalCodec = _.originalCodec, h.config = _.config, h.refSampleDuration = 1024 / h.audioSampleRate * h.timescale, l.default.v(this.TAG, "Parsed AudioSpecificConfig"), this._isInitialMetadataDispatched() ? this._dispatch && (this._audioTrack.length || this._videoTrack.length) && this._onDataAvailable(this._audioTrack, this._videoTrack) : this._audioInitialMetadataDispatched = !0, this._dispatch = !1, this._onTrackMetadata("audio", h); + var p = this._mediaInfo; + p.audioCodec = h.originalCodec, p.audioSampleRate = h.audioSampleRate, p.audioChannelCount = h.channelCount, p.hasVideo ? null != p.videoCodec && (p.mimeType = 'video/x-flv; codecs="' + p.videoCodec + "," + p.audioCodec + '"') : p.mimeType = 'video/x-flv; codecs="' + p.audioCodec + '"', p.isComplete() && this._onMediaInfo(p) + } else if (1 === c.packetType) { + var v = this._timestampBase + i, + g = { + unit: c.data, + length: c.data.byteLength, + dts: v, + pts: v + }; + f.samples.push(g), f.length += c.data.length + } else l.default.e(this.TAG, "Flv: Unsupported AAC data type " + c.packetType) + } else if (2 === a) { + if (!h.codec) { + var y = this._parseMP3AudioData(e, t + 1, n - 1, !0); + if (void 0 == y) return; + h.audioSampleRate = y.samplingRate, h.channelCount = y.channelCount, h.codec = y.codec, h.originalCodec = y.originalCodec, h.refSampleDuration = 1152 / h.audioSampleRate * h.timescale, l.default.v(this.TAG, "Parsed MPEG Audio Frame Header"), this._audioInitialMetadataDispatched = !0, this._onTrackMetadata("audio", h); + var E = this._mediaInfo; + E.audioCodec = h.codec, E.audioSampleRate = h.audioSampleRate, E.audioChannelCount = h.channelCount, E.audioDataRate = y.bitRate, E.hasVideo ? null != E.videoCodec && (E.mimeType = 'video/x-flv; codecs="' + E.videoCodec + "," + E.audioCodec + '"') : E.mimeType = 'video/x-flv; codecs="' + E.audioCodec + '"', E.isComplete() && this._onMediaInfo(E) + } + var b = this._parseMP3AudioData(e, t + 1, n - 1, !1); + if (void 0 == b) return; + var S = this._timestampBase + i, + k = { + unit: b, + length: b.byteLength, + dts: S, + pts: S + }; + f.samples.push(k), f.length += b.length + } + } + } + }, { + key: "_parseAACAudioData", + value: function(e, t, n) { + if (n <= 1) return void l.default.w(this.TAG, "Flv: Invalid AAC packet, missing AACPacketType or/and Data!"); + var i = {}, + r = new Uint8Array(e, t, n); + return i.packetType = r[0], 0 === r[0] ? i.data = this._parseAACAudioSpecificConfig(e, t + 1, n - 1) : i.data = r.subarray(1), i + } + }, { + key: "_parseAACAudioSpecificConfig", + value: function(e, t, n) { + var i = new Uint8Array(e, t, n), + r = null, + s = 0, + a = 0, + o = 0, + u = null; + if (s = a = i[0] >>> 3, (o = (7 & i[0]) << 1 | i[1] >>> 7) < 0 || o >= this._mpegSamplingRates.length) return void this._onError(m.default.FORMAT_ERROR, "Flv: AAC invalid sampling frequency index!"); + var l = this._mpegSamplingRates[o], + d = (120 & i[1]) >>> 3; + if (d < 0 || d >= 8) return void this._onError(m.default.FORMAT_ERROR, "Flv: AAC invalid channel configuration"); + 5 === s && (u = (7 & i[1]) << 1 | i[2] >>> 7, i[2]); + var h = self.navigator.userAgent.toLowerCase(); + return -1 !== h.indexOf("firefox") ? o >= 6 ? (s = 5, r = new Array(4), u = o - 3) : (s = 2, r = new Array(2), u = o) : -1 !== h.indexOf("android") ? (s = 2, r = new Array(2), u = o) : (s = 5, u = o, r = new Array(4), o >= 6 ? u = o - 3 : 1 === d && (s = 2, r = new Array(2), u = o)), r[0] = s << 3, r[0] |= (15 & o) >>> 1, r[1] = (15 & o) << 7, r[1] |= (15 & d) << 3, 5 === s && (r[1] |= (15 & u) >>> 1, r[2] = (1 & u) << 7, r[2] |= 8, r[3] = 0), { + config: r, + samplingRate: l, + channelCount: d, + codec: "mp4a.40." + s, + originalCodec: "mp4a.40." + a + } + } + }, { + key: "_parseMP3AudioData", + value: function(e, t, n, i) { + if (n < 4) return void l.default.w(this.TAG, "Flv: Invalid MP3 packet, header missing!"); + var r = (this._littleEndian, new Uint8Array(e, t, n)), + s = null; + if (i) { + if (255 !== r[0]) return; + var a = r[1] >>> 3 & 3, + o = (6 & r[1]) >> 1, + u = (240 & r[2]) >>> 4, + d = (12 & r[2]) >>> 2, + h = r[3] >>> 6 & 3, + f = 3 !== h ? 2 : 1, + c = 0, + _ = 0; + switch (a) { + case 0: + c = this._mpegAudioV25SampleRateTable[d]; + break; + case 2: + c = this._mpegAudioV20SampleRateTable[d]; + break; + case 3: + c = this._mpegAudioV10SampleRateTable[d] + } + switch (o) { + case 1: + 34, u < this._mpegAudioL3BitRateTable.length && (_ = this._mpegAudioL3BitRateTable[u]); + break; + case 2: + 33, u < this._mpegAudioL2BitRateTable.length && (_ = this._mpegAudioL2BitRateTable[u]); + break; + case 3: + 32, u < this._mpegAudioL1BitRateTable.length && (_ = this._mpegAudioL1BitRateTable[u]) + } + s = { + bitRate: _, + samplingRate: c, + channelCount: f, + codec: "mp3", + originalCodec: "mp3" + } + } else s = r; + return s + } + }, { + key: "_parseVideoData", + value: function(e, t, n, i, r) { + if (n <= 1) return void l.default.w(this.TAG, "Flv: Invalid video packet, missing VideoData payload!"); + if (!0 !== this._hasVideoFlagOverrided || !1 !== this._hasVideo) { + var s = new Uint8Array(e, t, n)[0], + a = (240 & s) >>> 4, + o = 15 & s; + if (7 !== o) return void this._onError(m.default.CODEC_UNSUPPORTED, "Flv: Unsupported codec in video frame: " + o); + this._parseAVCVideoPacket(e, t + 1, n - 1, i, r, a) + } + } + }, { + key: "_parseAVCVideoPacket", + value: function(e, t, n, i, r, s) { + if (n < 4) return void l.default.w(this.TAG, "Flv: Invalid AVC packet, missing AVCPacketType or/and CompositionTime"); + var a = this._littleEndian, + o = new DataView(e, t, n), + u = o.getUint8(0), + d = 16777215 & o.getUint32(0, !a), + h = d << 8 >> 8; + if (0 === u) this._parseAVCDecoderConfigurationRecord(e, t + 4, n - 4); + else if (1 === u) this._parseAVCVideoData(e, t + 4, n - 4, i, r, s, h); + else if (2 !== u) return void this._onError(m.default.FORMAT_ERROR, "Flv: Invalid video packet type " + u) + } + }, { + key: "_parseAVCDecoderConfigurationRecord", + value: function(e, t, n) { + if (n < 7) return void l.default.w(this.TAG, "Flv: Invalid AVCDecoderConfigurationRecord, lack of data!"); + var i = this._videoMetadata, + r = this._videoTrack, + s = this._littleEndian, + a = new DataView(e, t, n); + i ? void 0 !== i.avcc && l.default.w(this.TAG, "Found another AVCDecoderConfigurationRecord!") : (!1 === this._hasVideo && !1 === this._hasVideoFlagOverrided && (this._hasVideo = !0, this._mediaInfo.hasVideo = !0), i = this._videoMetadata = {}, i.type = "video", i.id = r.id, i.timescale = this._timescale, i.duration = this._duration); + var o = a.getUint8(0), + u = a.getUint8(1); + a.getUint8(2), a.getUint8(3); + if (1 !== o || 0 === u) return void this._onError(m.default.FORMAT_ERROR, "Flv: Invalid AVCDecoderConfigurationRecord"); + if (this._naluLengthSize = 1 + (3 & a.getUint8(4)), 3 !== this._naluLengthSize && 4 !== this._naluLengthSize) return void this._onError(m.default.FORMAT_ERROR, "Flv: Strange NaluLengthSizeMinusOne: " + (this._naluLengthSize - 1)); + var d = 31 & a.getUint8(5); + if (0 === d) return void this._onError(m.default.FORMAT_ERROR, "Flv: Invalid AVCDecoderConfigurationRecord: No SPS"); + d > 1 && l.default.w(this.TAG, "Flv: Strange AVCDecoderConfigurationRecord: SPS Count = " + d); + for (var h = 6, f = 0; f < d; f++) { + var _ = a.getUint16(h, !s); + if (h += 2, 0 !== _) { + var p = new Uint8Array(e, t + h, _); + h += _; + var v = c.default.parseSPS(p); + if (0 === f) { + i.codecWidth = v.codec_size.width, i.codecHeight = v.codec_size.height, i.presentWidth = v.present_size.width, i.presentHeight = v.present_size.height, i.profile = v.profile_string, i.level = v.level_string, i.bitDepth = v.bit_depth, i.chromaFormat = v.chroma_format, i.sarRatio = v.sar_ratio, i.frameRate = v.frame_rate, !1 !== v.frame_rate.fixed && 0 !== v.frame_rate.fps_num && 0 !== v.frame_rate.fps_den || (i.frameRate = this._referenceFrameRate); + var g = i.frameRate.fps_den, + y = i.frameRate.fps_num; + i.refSampleDuration = i.timescale * (g / y); + for (var E = p.subarray(1, 4), b = "avc1.", S = 0; S < 3; S++) { + var k = E[S].toString(16); + k.length < 2 && (k = "0" + k), b += k + } + i.codec = b; + var L = this._mediaInfo; + L.width = i.codecWidth, L.height = i.codecHeight, L.fps = i.frameRate.fps, L.profile = i.profile, L.level = i.level, L.refFrames = v.ref_frames, L.chromaFormat = v.chroma_format_string, L.sarNum = i.sarRatio.width, L.sarDen = i.sarRatio.height, L.videoCodec = b, L.hasAudio ? null != L.audioCodec && (L.mimeType = 'video/x-flv; codecs="' + L.videoCodec + "," + L.audioCodec + '"') : L.mimeType = 'video/x-flv; codecs="' + L.videoCodec + '"', L.isComplete() && this._onMediaInfo(L) + } + } + } + var w = a.getUint8(h); + if (0 === w) return void this._onError(m.default.FORMAT_ERROR, "Flv: Invalid AVCDecoderConfigurationRecord: No PPS"); + w > 1 && l.default.w(this.TAG, "Flv: Strange AVCDecoderConfigurationRecord: PPS Count = " + w), h++; + for (var R = 0; R < w; R++) { + var A = a.getUint16(h, !s); + h += 2, 0 !== A && (h += A) + } + i.avcc = new Uint8Array(n), i.avcc.set(new Uint8Array(e, t, n), 0), l.default.v(this.TAG, "Parsed AVCDecoderConfigurationRecord"), this._isInitialMetadataDispatched() ? this._dispatch && (this._audioTrack.length || this._videoTrack.length) && this._onDataAvailable(this._audioTrack, this._videoTrack) : this._videoInitialMetadataDispatched = !0, this._dispatch = !1, this._onTrackMetadata("video", i) + } + }, { + key: "_parseAVCVideoData", + value: function(e, t, n, i, r, s, a) { + for (var o = this._littleEndian, u = new DataView(e, t, n), d = [], h = 0, f = 0, c = this._naluLengthSize, _ = this._timestampBase + i, m = 1 === s; f < n;) { + if (f + 4 >= n) { + l.default.w(this.TAG, "Malformed Nalu near timestamp " + _ + ", offset = " + f + ", dataSize = " + n); + break + } + var p = u.getUint32(f, !o); + if (3 === c && (p >>>= 8), p > n - c) return void l.default.w(this.TAG, "Malformed Nalus near timestamp " + _ + ", NaluSize > DataSize!"); + var v = 31 & u.getUint8(f + c); + 5 === v && (m = !0); + var g = new Uint8Array(e, t + f, c + p), + y = { + type: v, + data: g + }; + d.push(y), h += g.byteLength, f += c + p + } + if (d.length) { + var E = this._videoTrack, + b = { + units: d, + length: h, + isKeyframe: m, + dts: _, + cts: a, + pts: _ + a + }; + m && (b.fileposition = r), E.samples.push(b), E.length += h + } + } + }, { + key: "onTrackMetadata", + get: function() { + return this._onTrackMetadata + }, + set: function(e) { + this._onTrackMetadata = e + } + }, { + key: "onMediaInfo", + get: function() { + return this._onMediaInfo + }, + set: function(e) { + this._onMediaInfo = e + } + }, { + key: "onError", + get: function() { + return this._onError + }, + set: function(e) { + this._onError = e + } + }, { + key: "onDataAvailable", + get: function() { + return this._onDataAvailable + }, + set: function(e) { + this._onDataAvailable = e + } + }, { + key: "timestampBase", + get: function() { + return this._timestampBase + }, + set: function(e) { + this._timestampBase = e + } + }, { + key: "overridedDuration", + get: function() { + return this._duration + }, + set: function(e) { + this._durationOverrided = !0, this._duration = e, this._mediaInfo.duration = e + } + }, { + key: "overridedHasAudio", + set: function(e) { + this._hasAudioFlagOverrided = !0, this._hasAudio = e, this._mediaInfo.hasAudio = e + } + }, { + key: "overridedHasVideo", + set: function(e) { + this._hasVideoFlagOverrided = !0, this._hasVideo = e, this._mediaInfo.hasVideo = e + } + }], [{ + key: "probe", + value: function(e) { + var t = new Uint8Array(e), + n = { + match: !1 + }; + if (70 !== t[0] || 76 !== t[1] || 86 !== t[2] || 1 !== t[3]) return n; + var i = (4 & t[4]) >>> 2 != 0, + r = 0 != (1 & t[4]), + a = s(t, 5); + return a < 9 ? n : { + match: !0, + consumed: a, + dataOffset: a, + hasAudioTrack: i, + hasVideoTrack: r + } + } + }]), e + }(); + n.default = y + }, { + "../core/media-info.js": 7, + "../utils/exception.js": 40, + "../utils/logger.js": 41, + "./amf-parser.js": 15, + "./demux-errors.js": 16, + "./sps-parser.js": 19 + }], + 19: [function(e, t, n) { + "use strict"; + + function i(e, t) { + if (!(e instanceof t)) throw new TypeError("Cannot call a class as a function") + } + Object.defineProperty(n, "__esModule", { + value: !0 + }); + var r = function() { + function e(e, t) { + for (var n = 0; n < t.length; n++) { + var i = t[n]; + i.enumerable = i.enumerable || !1, i.configurable = !0, "value" in i && (i.writable = !0), Object.defineProperty(e, i.key, i) + } + } + return function(t, n, i) { + return n && e(t.prototype, n), i && e(t, i), t + } + }(), + s = e("./exp-golomb.js"), + a = function(e) { + return e && e.__esModule ? e : { + default: e + } + }(s), + o = function() { + function e() { + i(this, e) + } + return r(e, null, [{ + key: "_ebsp2rbsp", + value: function(e) { + for (var t = e, n = t.byteLength, i = new Uint8Array(n), r = 0, s = 0; s < n; s++) s >= 2 && 3 === t[s] && 0 === t[s - 1] && 0 === t[s - 2] || (i[r] = t[s], r++); + return new Uint8Array(i.buffer, 0, r) + } + }, { + key: "parseSPS", + value: function(t) { + var n = e._ebsp2rbsp(t), + i = new a.default(n); + i.readByte(); + var r = i.readByte(); + i.readByte(); + var s = i.readByte(); + i.readUEG(); + var o = e.getProfileString(r), + u = e.getLevelString(s), + l = 1, + d = 420, + h = [0, 420, 422, 444], + f = 8; + if ((100 === r || 110 === r || 122 === r || 244 === r || 44 === r || 83 === r || 86 === r || 118 === r || 128 === r || 138 === r || 144 === r) && (l = i.readUEG(), 3 === l && i.readBits(1), l <= 3 && (d = h[l]), f = i.readUEG() + 8, i.readUEG(), i.readBits(1), i.readBool())) + for (var c = 3 !== l ? 8 : 12, _ = 0; _ < c; _++) i.readBool() && (_ < 6 ? e._skipScalingList(i, 16) : e._skipScalingList(i, 64)); + i.readUEG(); + var m = i.readUEG(); + if (0 === m) i.readUEG(); + else if (1 === m) { + i.readBits(1), i.readSEG(), i.readSEG(); + for (var p = i.readUEG(), v = 0; v < p; v++) i.readSEG() + } + var g = i.readUEG(); + i.readBits(1); + var y = i.readUEG(), + E = i.readUEG(), + b = i.readBits(1); + 0 === b && i.readBits(1), i.readBits(1); + var S = 0, + k = 0, + L = 0, + w = 0; + i.readBool() && (S = i.readUEG(), k = i.readUEG(), L = i.readUEG(), w = i.readUEG()); + var R = 1, + A = 1, + O = 0, + T = !0, + C = 0, + I = 0; + if (i.readBool()) { + if (i.readBool()) { + var x = i.readByte(), + M = [1, 12, 10, 16, 40, 24, 20, 32, 80, 18, 15, 64, 160, 4, 3, 2], + D = [1, 11, 11, 11, 33, 11, 11, 11, 33, 11, 11, 33, 99, 3, 2, 1]; + x > 0 && x < 16 ? (R = M[x - 1], A = D[x - 1]) : 255 === x && (R = i.readByte() << 8 | i.readByte(), A = i.readByte() << 8 | i.readByte()) + } + if (i.readBool() && i.readBool(), i.readBool() && (i.readBits(4), i.readBool() && i.readBits(24)), i.readBool() && (i.readUEG(), i.readUEG()), i.readBool()) { + var B = i.readBits(32), + j = i.readBits(32); + T = i.readBool(), C = j, I = 2 * B, O = C / I + } + } + var P = 1; + 1 === R && 1 === A || (P = R / A); + var U = 0, + N = 0; + if (0 === l) U = 1, N = 2 - b; + else { + var F = 3 === l ? 1 : 2, + G = 1 === l ? 2 : 1; + U = F, N = G * (2 - b) + } + var V = 16 * (y + 1), + z = 16 * (E + 1) * (2 - b); + V -= (S + k) * U, z -= (L + w) * N; + var H = Math.ceil(V * P); + return i.destroy(), i = null, { + profile_string: o, + level_string: u, + bit_depth: f, + ref_frames: g, + chroma_format: d, + chroma_format_string: e.getChromaFormatString(d), + frame_rate: { + fixed: T, + fps: O, + fps_den: I, + fps_num: C + }, + sar_ratio: { + width: R, + height: A + }, + codec_size: { + width: V, + height: z + }, + present_size: { + width: H, + height: z + } + } + } + }, { + key: "_skipScalingList", + value: function(e, t) { + for (var n = 8, i = 8, r = 0, s = 0; s < t; s++) 0 !== i && (r = e.readSEG(), i = (n + r + 256) % 256), n = 0 === i ? n : i + } + }, { + key: "getProfileString", + value: function(e) { + switch (e) { + case 66: + return "Baseline"; + case 77: + return "Main"; + case 88: + return "Extended"; + case 100: + return "High"; + case 110: + return "High10"; + case 122: + return "High422"; + case 244: + return "High444"; + default: + return "Unknown" + } + } + }, { + key: "getLevelString", + value: function(e) { + return (e / 10).toFixed(1) + } + }, { + key: "getChromaFormatString", + value: function(e) { + switch (e) { + case 420: + return "4:2:0"; + case 422: + return "4:2:2"; + case 444: + return "4:4:4"; + default: + return "Unknown" + } + } + }]), e + }(); + n.default = o + }, { + "./exp-golomb.js": 17 + }], + 20: [function(e, t, n) { + "use strict"; + + function i(e) { + return e && e.__esModule ? e : { + default: e + } + } + + function r(e, t) { + var n = e; + if (null == n || "object" !== (void 0 === n ? "undefined" : o(n))) throw new b.InvalidArgumentException("MediaDataSource must be an javascript object!"); + if (!n.hasOwnProperty("type")) throw new b.InvalidArgumentException("MediaDataSource must has type field to indicate video file type!"); + switch (n.type) { + case "flv": + return new c.default(n, t); + default: + return new m.default(n, t) + } + } + + function s() { + return h.default.supportMSEH264Playback() + } + + function a() { + return h.default.getFeatureList() + } + Object.defineProperty(n, "__esModule", { + value: !0 + }); + var o = "function" == typeof Symbol && "symbol" == typeof Symbol.iterator ? function(e) { + return typeof e + } : function(e) { + return e && "function" == typeof Symbol && e.constructor === Symbol && e !== Symbol.prototype ? "symbol" : typeof e + }, + u = e("./utils/polyfill.js"), + l = i(u), + d = e("./core/features.js"), + h = i(d), + f = e("./player/flv-player.js"), + c = i(f), + _ = e("./player/native-player.js"), + m = i(_), + p = e("./player/player-events.js"), + v = i(p), + g = e("./player/player-errors.js"), + y = e("./utils/logging-control.js"), + E = i(y), + b = e("./utils/exception.js"); + l.default.install(); + var S = {}; + S.createPlayer = r, S.isSupported = s, S.getFeatureList = a, S.Events = v.default, S.ErrorTypes = g.ErrorTypes, S.ErrorDetails = g.ErrorDetails, S.FlvPlayer = c.default, S.NativePlayer = m.default, S.LoggingControl = E.default, Object.defineProperty(S, "version", { + enumerable: !0, + get: function() { + return "1.4.2" + } + }), n.default = S + }, { + "./core/features.js": 6, + "./player/flv-player.js": 32, + "./player/native-player.js": 33, + "./player/player-errors.js": 34, + "./player/player-events.js": 35, + "./utils/exception.js": 40, + "./utils/logging-control.js": 42, + "./utils/polyfill.js": 43 + }], + 21: [function(e, t, n) { + "use strict"; + t.exports = e("./flv.js").default + }, { + "./flv.js": 20 + }], + 22: [function(e, t, n) { + "use strict"; + + function i(e) { + return e && e.__esModule ? e : { + default: e + } + } + + function r(e, t) { + if (!(e instanceof t)) throw new TypeError("Cannot call a class as a function") + } + + function s(e, t) { + if (!e) throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); + return !t || "object" != typeof t && "function" != typeof t ? e : t + } + + function a(e, t) { + if ("function" != typeof t && null !== t) throw new TypeError("Super expression must either be null or a function, not " + typeof t); + e.prototype = Object.create(t && t.prototype, { + constructor: { + value: e, + enumerable: !1, + writable: !0, + configurable: !0 + } + }), t && (Object.setPrototypeOf ? Object.setPrototypeOf(e, t) : e.__proto__ = t) + } + Object.defineProperty(n, "__esModule", { + value: !0 + }); + var o = "function" == typeof Symbol && "symbol" == typeof Symbol.iterator ? function(e) { + return typeof e + } : function(e) { + return e && "function" == typeof Symbol && e.constructor === Symbol && e !== Symbol.prototype ? "symbol" : typeof e + }, + u = function e(t, n, i) { + null === t && (t = Function.prototype); + var r = Object.getOwnPropertyDescriptor(t, n); + if (void 0 === r) { + var s = Object.getPrototypeOf(t); + return null === s ? void 0 : e(s, n, i) + } + if ("value" in r) return r.value; + var a = r.get; + if (void 0 !== a) return a.call(i) + }, + l = function() { + function e(e, t) { + for (var n = 0; n < t.length; n++) { + var i = t[n]; + i.enumerable = i.enumerable || !1, i.configurable = !0, "value" in i && (i.writable = !0), Object.defineProperty(e, i.key, i) + } + } + return function(t, n, i) { + return n && e(t.prototype, n), i && e(t, i), t + } + }(), + d = e("../utils/logger.js"), + h = (i(d), e("../utils/browser.js")), + f = i(h), + c = e("./loader.js"), + _ = e("../utils/exception.js"), + m = function(e) { + function t(e, n) { + r(this, t); + var i = s(this, (t.__proto__ || Object.getPrototypeOf(t)).call(this, "fetch-stream-loader")); + return i.TAG = "FetchStreamLoader", i._seekHandler = e, i._config = n, i._needStash = !0, i._requestAbort = !1, i._contentLength = null, i._receivedLength = 0, i + } + return a(t, e), l(t, null, [{ + key: "isSupported", + value: function() { + try { + var e = f.default.msedge && f.default.version.minor >= 15048, + t = !f.default.msedge || e; + return self.fetch && self.ReadableStream && t + } catch (e) { + return !1 + } + } + }]), l(t, [{ + key: "destroy", + value: function() { + this.isWorking() && this.abort(), u(t.prototype.__proto__ || Object.getPrototypeOf(t.prototype), "destroy", this).call(this) + } + }, { + key: "open", + value: function(e, t) { + var n = this; + this._dataSource = e, this._range = t; + var i = e.url; + this._config.reuseRedirectedURL && void 0 != e.redirectedURL && (i = e.redirectedURL); + var r = this._seekHandler.getConfig(i, t), + s = new self.Headers; + if ("object" === o(r.headers)) { + var a = r.headers; + for (var u in a) a.hasOwnProperty(u) && s.append(u, a[u]) + } + var l = { + method: "GET", + headers: s, + mode: "cors", + cache: "default", + referrerPolicy: "no-referrer-when-downgrade" + }; + !1 === e.cors && (l.mode = "same-origin"), e.withCredentials && (l.credentials = "include"), e.referrerPolicy && (l.referrerPolicy = e.referrerPolicy), this._status = c.LoaderStatus.kConnecting, self.fetch(r.url, l).then(function(e) { + if (n._requestAbort) return n._requestAbort = !1, void(n._status = c.LoaderStatus.kIdle); + if (e.ok && e.status >= 200 && e.status <= 299) { + if (e.url !== r.url && n._onURLRedirect) { + var t = n._seekHandler.removeURLParameters(e.url); + n._onURLRedirect(t) + } + var i = e.headers.get("Content-Length"); + return null != i && (n._contentLength = parseInt(i), 0 !== n._contentLength && n._onContentLengthKnown && n._onContentLengthKnown(n._contentLength)), n._pump.call(n, e.body.getReader()) + } + if (n._status = c.LoaderStatus.kError, !n._onError) throw new _.RuntimeException("FetchStreamLoader: Http code invalid, " + e.status + " " + e.statusText); + n._onError(c.LoaderErrors.HTTP_STATUS_CODE_INVALID, { + code: e.status, + msg: e.statusText + }) + }).catch(function(e) { + if (n._status = c.LoaderStatus.kError, !n._onError) throw e; + n._onError(c.LoaderErrors.EXCEPTION, { + code: -1, + msg: e.message + }) + }) + } + }, { + key: "abort", + value: function() { + this._requestAbort = !0 + } + }, { + key: "_pump", + value: function(e) { + var t = this; + return e.read().then(function(n) { + if (n.done) + if (null !== t._contentLength && t._receivedLength < t._contentLength) { + t._status = c.LoaderStatus.kError; + var i = c.LoaderErrors.EARLY_EOF, + r = { + code: -1, + msg: "Fetch stream meet Early-EOF" + }; + if (!t._onError) throw new _.RuntimeException(r.msg); + t._onError(i, r) + } else t._status = c.LoaderStatus.kComplete, t._onComplete && t._onComplete(t._range.from, t._range.from + t._receivedLength - 1); + else { + if (!0 === t._requestAbort) return t._requestAbort = !1, t._status = c.LoaderStatus.kComplete, e.cancel(); + t._status = c.LoaderStatus.kBuffering; + var s = n.value.buffer, + a = t._range.from + t._receivedLength; + t._receivedLength += s.byteLength, t._onDataArrival && t._onDataArrival(s, a, t._receivedLength), t._pump(e) + } + }).catch(function(e) { + if (11 !== e.code || !f.default.msedge) { + t._status = c.LoaderStatus.kError; + var n = 0, + i = null; + if (19 !== e.code && "network error" !== e.message || !(null === t._contentLength || null !== t._contentLength && t._receivedLength < t._contentLength) ? (n = c.LoaderErrors.EXCEPTION, i = { + code: e.code, + msg: e.message + }) : (n = c.LoaderErrors.EARLY_EOF, i = { + code: e.code, + msg: "Fetch stream meet Early-EOF" + }), !t._onError) throw new _.RuntimeException(i.msg); + t._onError(n, i) + } + }) + } + }]), t + }(c.BaseLoader); + n.default = m + }, { + "../utils/browser.js": 39, + "../utils/exception.js": 40, + "../utils/logger.js": 41, + "./loader.js": 24 + }], + 23: [function(e, t, n) { + "use strict"; + + function i(e) { + return e && e.__esModule ? e : { + default: e + } + } + + function r(e, t) { + if (!(e instanceof t)) throw new TypeError("Cannot call a class as a function") + } + Object.defineProperty(n, "__esModule", { + value: !0 + }); + var s = function() { + function e(e, t) { + for (var n = 0; n < t.length; n++) { + var i = t[n]; + i.enumerable = i.enumerable || !1, i.configurable = !0, "value" in i && (i.writable = !0), Object.defineProperty(e, i.key, i) + } + } + return function(t, n, i) { + return n && e(t.prototype, n), i && e(t, i), t + } + }(), + a = e("../utils/logger.js"), + o = i(a), + u = e("./speed-sampler.js"), + l = i(u), + d = e("./loader.js"), + h = e("./fetch-stream-loader.js"), + f = i(h), + c = e("./xhr-moz-chunked-loader.js"), + _ = i(c), + m = e("./xhr-msstream-loader.js"), + p = (i(m), e("./xhr-range-loader.js")), + v = i(p), + g = e("./websocket-loader.js"), + y = i(g), + E = e("./range-seek-handler.js"), + b = i(E), + S = e("./param-seek-handler.js"), + k = i(S), + L = e("../utils/exception.js"), + w = function() { + function e(t, n, i) { + r(this, e), this.TAG = "IOController", this._config = n, this._extraData = i, this._stashInitialSize = 393216, void 0 != n.stashInitialSize && n.stashInitialSize > 0 && (this._stashInitialSize = n.stashInitialSize), this._stashUsed = 0, this._stashSize = this._stashInitialSize, this._bufferSize = 3145728, this._stashBuffer = new ArrayBuffer(this._bufferSize), this._stashByteStart = 0, this._enableStash = !0, !1 === n.enableStashBuffer && (this._enableStash = !1), this._loader = null, this._loaderClass = null, this._seekHandler = null, this._dataSource = t, this._isWebSocketURL = /wss?:\/\/(.+?)/.test(t.url), this._refTotalLength = t.filesize ? t.filesize : null, this._totalLength = this._refTotalLength, this._fullRequestFlag = !1, this._currentRange = null, this._redirectedURL = null, this._speedNormalized = 0, this._speedSampler = new l.default, this._speedNormalizeList = [64, 128, 256, 384, 512, 768, 1024, 1536, 2048, 3072, 4096], this._isEarlyEofReconnecting = !1, this._paused = !1, this._resumeFrom = 0, this._onDataArrival = null, this._onSeeked = null, this._onError = null, this._onComplete = null, this._onRedirect = null, this._onRecoveredEarlyEof = null, this._selectSeekHandler(), this._selectLoader(), this._createLoader() + } + return s(e, [{ + key: "destroy", + value: function() { + this._loader.isWorking() && this._loader.abort(), this._loader.destroy(), this._loader = null, this._loaderClass = null, this._dataSource = null, this._stashBuffer = null, this._stashUsed = this._stashSize = this._bufferSize = this._stashByteStart = 0, this._currentRange = null, this._speedSampler = null, this._isEarlyEofReconnecting = !1, this._onDataArrival = null, this._onSeeked = null, this._onError = null, this._onComplete = null, this._onRedirect = null, this._onRecoveredEarlyEof = null, this._extraData = null + } + }, { + key: "isWorking", + value: function() { + return this._loader && this._loader.isWorking() && !this._paused + } + }, { + key: "isPaused", + value: function() { + return this._paused + } + }, { + key: "_selectSeekHandler", + value: function() { + var e = this._config; + if ("range" === e.seekType) this._seekHandler = new b.default(this._config.rangeLoadZeroStart); + else if ("param" === e.seekType) { + var t = e.seekParamStart || "bstart", + n = e.seekParamEnd || "bend"; + this._seekHandler = new k.default(t, n) + } else { + if ("custom" !== e.seekType) throw new L.InvalidArgumentException("Invalid seekType in config: " + e.seekType); + if ("function" != typeof e.customSeekHandler) throw new L.InvalidArgumentException("Custom seekType specified in config but invalid customSeekHandler!"); + this._seekHandler = new e.customSeekHandler + } + } + }, { + key: "_selectLoader", + value: function() { + if (this._isWebSocketURL) this._loaderClass = y.default; + else if (f.default.isSupported()) this._loaderClass = f.default; + else if (_.default.isSupported()) this._loaderClass = _.default; + else { + if (!v.default.isSupported()) throw new L.RuntimeException("Your browser doesn't support xhr with arraybuffer responseType!"); + this._loaderClass = v.default + } + } + }, { + key: "_createLoader", + value: function() { + this._loader = new this._loaderClass(this._seekHandler, this._config), !1 === this._loader.needStashBuffer && (this._enableStash = !1), this._loader.onContentLengthKnown = this._onContentLengthKnown.bind(this), this._loader.onURLRedirect = this._onURLRedirect.bind(this), this._loader.onDataArrival = this._onLoaderChunkArrival.bind(this), this._loader.onComplete = this._onLoaderComplete.bind(this), this._loader.onError = this._onLoaderError.bind(this) + } + }, { + key: "open", + value: function(e) { + this._currentRange = { + from: 0, + to: -1 + }, e && (this._currentRange.from = e), this._speedSampler.reset(), e || (this._fullRequestFlag = !0), this._loader.open(this._dataSource, Object.assign({}, this._currentRange)) + } + }, { + key: "abort", + value: function() { + this._loader.abort(), this._paused && (this._paused = !1, this._resumeFrom = 0) + } + }, { + key: "pause", + value: function() { + this.isWorking() && (this._loader.abort(), 0 !== this._stashUsed ? (this._resumeFrom = this._stashByteStart, this._currentRange.to = this._stashByteStart - 1) : this._resumeFrom = this._currentRange.to + 1, this._stashUsed = 0, this._stashByteStart = 0, this._paused = !0) + } + }, { + key: "resume", + value: function() { + if (this._paused) { + this._paused = !1; + var e = this._resumeFrom; + this._resumeFrom = 0, this._internalSeek(e, !0) + } + } + }, { + key: "seek", + value: function(e) { + this._paused = !1, this._stashUsed = 0, this._stashByteStart = 0, this._internalSeek(e, !0) + } + }, { + key: "_internalSeek", + value: function(e, t) { + this._loader.isWorking() && this._loader.abort(), this._flushStashBuffer(t), this._loader.destroy(), this._loader = null; + var n = { + from: e, + to: -1 + }; + this._currentRange = { + from: n.from, + to: -1 + }, this._speedSampler.reset(), this._stashSize = this._stashInitialSize, this._createLoader(), this._loader.open(this._dataSource, n), this._onSeeked && this._onSeeked() + } + }, { + key: "updateUrl", + value: function(e) { + if (!e || "string" != typeof e || 0 === e.length) throw new L.InvalidArgumentException("Url must be a non-empty string!"); + this._dataSource.url = e + } + }, { + key: "_expandBuffer", + value: function(e) { + for (var t = this._stashSize; t + 1048576 < e;) t *= 2; + if ((t += 1048576) !== this._bufferSize) { + var n = new ArrayBuffer(t); + if (this._stashUsed > 0) { + var i = new Uint8Array(this._stashBuffer, 0, this._stashUsed); + new Uint8Array(n, 0, t).set(i, 0) + } + this._stashBuffer = n, this._bufferSize = t + } + } + }, { + key: "_normalizeSpeed", + value: function(e) { + var t = this._speedNormalizeList, + n = t.length - 1, + i = 0, + r = 0, + s = n; + if (e < t[0]) return t[0]; + for (; r <= s;) { + if ((i = r + Math.floor((s - r) / 2)) === n || e >= t[i] && e < t[i + 1]) return t[i]; + t[i] < e ? r = i + 1 : s = i - 1 + } + } + }, { + key: "_adjustStashSize", + value: function(e) { + var t = 0; + (t = this._config.isLive ? e : e < 512 ? e : e >= 512 && e <= 1024 ? Math.floor(1.5 * e) : 2 * e) > 8192 && (t = 8192); + var n = 1024 * t + 1048576; + this._bufferSize < n && this._expandBuffer(n), this._stashSize = 1024 * t + } + }, { + key: "_dispatchChunks", + value: function(e, t) { + return this._currentRange.to = t + e.byteLength - 1, this._onDataArrival(e, t) + } + }, { + key: "_onURLRedirect", + value: function(e) { + this._redirectedURL = e, this._onRedirect && this._onRedirect(e) + } + }, { + key: "_onContentLengthKnown", + value: function(e) { + e && this._fullRequestFlag && (this._totalLength = e, this._fullRequestFlag = !1) + } + }, { + key: "_onLoaderChunkArrival", + value: function(e, t, n) { + if (!this._onDataArrival) throw new L.IllegalStateException("IOController: No existing consumer (onDataArrival) callback!"); + if (!this._paused) { + this._isEarlyEofReconnecting && (this._isEarlyEofReconnecting = !1, this._onRecoveredEarlyEof && this._onRecoveredEarlyEof()), this._speedSampler.addBytes(e.byteLength); + var i = this._speedSampler.lastSecondKBps; + if (0 !== i) { + var r = this._normalizeSpeed(i); + this._speedNormalized !== r && (this._speedNormalized = r, this._adjustStashSize(r)) + } + if (this._enableStash) + if (0 === this._stashUsed && 0 === this._stashByteStart && (this._stashByteStart = t), this._stashUsed + e.byteLength <= this._stashSize) { + var s = new Uint8Array(this._stashBuffer, 0, this._stashSize); + s.set(new Uint8Array(e), this._stashUsed), this._stashUsed += e.byteLength + } else { + var a = new Uint8Array(this._stashBuffer, 0, this._bufferSize); + if (this._stashUsed > 0) { + var o = this._stashBuffer.slice(0, this._stashUsed), + u = this._dispatchChunks(o, this._stashByteStart); + if (u < o.byteLength) { + if (u > 0) { + var l = new Uint8Array(o, u); + a.set(l, 0), this._stashUsed = l.byteLength, this._stashByteStart += u + } + } else this._stashUsed = 0, this._stashByteStart += u; + this._stashUsed + e.byteLength > this._bufferSize && (this._expandBuffer(this._stashUsed + e.byteLength), a = new Uint8Array(this._stashBuffer, 0, this._bufferSize)), a.set(new Uint8Array(e), this._stashUsed), this._stashUsed += e.byteLength + } else { + var d = this._dispatchChunks(e, t); + if (d < e.byteLength) { + var h = e.byteLength - d; + h > this._bufferSize && (this._expandBuffer(h), a = new Uint8Array(this._stashBuffer, 0, this._bufferSize)), a.set(new Uint8Array(e, d), 0), this._stashUsed += h, this._stashByteStart = t + d + } + } + } + else if (0 === this._stashUsed) { + var f = this._dispatchChunks(e, t); + if (f < e.byteLength) { + var c = e.byteLength - f; + c > this._bufferSize && this._expandBuffer(c); + var _ = new Uint8Array(this._stashBuffer, 0, this._bufferSize); + _.set(new Uint8Array(e, f), 0), this._stashUsed += c, this._stashByteStart = t + f + } + } else { + this._stashUsed + e.byteLength > this._bufferSize && this._expandBuffer(this._stashUsed + e.byteLength); + var m = new Uint8Array(this._stashBuffer, 0, this._bufferSize); + m.set(new Uint8Array(e), this._stashUsed), this._stashUsed += e.byteLength; + var p = this._dispatchChunks(this._stashBuffer.slice(0, this._stashUsed), this._stashByteStart); + if (p < this._stashUsed && p > 0) { + var v = new Uint8Array(this._stashBuffer, p); + m.set(v, 0) + } + this._stashUsed -= p, this._stashByteStart += p + } + } + } + }, { + key: "_flushStashBuffer", + value: function(e) { + if (this._stashUsed > 0) { + var t = this._stashBuffer.slice(0, this._stashUsed), + n = this._dispatchChunks(t, this._stashByteStart), + i = t.byteLength - n; + if (n < t.byteLength) { + if (!e) { + if (n > 0) { + var r = new Uint8Array(this._stashBuffer, 0, this._bufferSize), + s = new Uint8Array(t, n); + r.set(s, 0), this._stashUsed = s.byteLength, this._stashByteStart += n + } + return 0 + } + o.default.w(this.TAG, i + " bytes unconsumed data remain when flush buffer, dropped") + } + return this._stashUsed = 0, this._stashByteStart = 0, i + } + return 0 + } + }, { + key: "_onLoaderComplete", + value: function(e, t) { + this._flushStashBuffer(!0), this._onComplete && this._onComplete(this._extraData) + } + }, { + key: "_onLoaderError", + value: function(e, t) { + switch (o.default.e(this.TAG, "Loader error, code = " + t.code + ", msg = " + t.msg), this._flushStashBuffer(!1), this._isEarlyEofReconnecting && (this._isEarlyEofReconnecting = !1, e = d.LoaderErrors.UNRECOVERABLE_EARLY_EOF), e) { + case d.LoaderErrors.EARLY_EOF: + if (!this._config.isLive && this._totalLength) { + var n = this._currentRange.to + 1; + return void(n < this._totalLength && (o.default.w(this.TAG, "Connection lost, trying reconnect..."), this._isEarlyEofReconnecting = !0, this._internalSeek(n, !1))) + } + e = d.LoaderErrors.UNRECOVERABLE_EARLY_EOF; + break; + case d.LoaderErrors.UNRECOVERABLE_EARLY_EOF: + case d.LoaderErrors.CONNECTING_TIMEOUT: + case d.LoaderErrors.HTTP_STATUS_CODE_INVALID: + case d.LoaderErrors.EXCEPTION: + } + if (!this._onError) throw new L.RuntimeException("IOException: " + t.msg); + this._onError(e, t) + } + }, { + key: "status", + get: function() { + return this._loader.status + } + }, { + key: "extraData", + get: function() { + return this._extraData + }, + set: function(e) { + this._extraData = e + } + }, { + key: "onDataArrival", + get: function() { + return this._onDataArrival + }, + set: function(e) { + this._onDataArrival = e + } + }, { + key: "onSeeked", + get: function() { + return this._onSeeked + }, + set: function(e) { + this._onSeeked = e + } + }, { + key: "onError", + get: function() { + return this._onError + }, + set: function(e) { + this._onError = e + } + }, { + key: "onComplete", + get: function() { + return this._onComplete + }, + set: function(e) { + this._onComplete = e + } + }, { + key: "onRedirect", + get: function() { + return this._onRedirect + }, + set: function(e) { + this._onRedirect = e + } + }, { + key: "onRecoveredEarlyEof", + get: function() { + return this._onRecoveredEarlyEof + }, + set: function(e) { + this._onRecoveredEarlyEof = e + } + }, { + key: "currentURL", + get: function() { + return this._dataSource.url + } + }, { + key: "hasRedirect", + get: function() { + return null != this._redirectedURL || void 0 != this._dataSource.redirectedURL + } + }, { + key: "currentRedirectedURL", + get: function() { + return this._redirectedURL || this._dataSource.redirectedURL + } + }, { + key: "currentSpeed", + get: function() { + return this._loaderClass === v.default ? this._loader.currentSpeed : this._speedSampler.lastSecondKBps + } + }, { + key: "loaderType", + get: function() { + return this._loader.type + } + }]), e + }(); + n.default = w + }, { + "../utils/exception.js": 40, + "../utils/logger.js": 41, + "./fetch-stream-loader.js": 22, + "./loader.js": 24, + "./param-seek-handler.js": 25, + "./range-seek-handler.js": 26, + "./speed-sampler.js": 27, + "./websocket-loader.js": 28, + "./xhr-moz-chunked-loader.js": 29, + "./xhr-msstream-loader.js": 30, + "./xhr-range-loader.js": 31 + }], + 24: [function(e, t, n) { + "use strict"; + + function i(e, t) { + if (!(e instanceof t)) throw new TypeError("Cannot call a class as a function") + } + Object.defineProperty(n, "__esModule", { + value: !0 + }), n.BaseLoader = n.LoaderErrors = n.LoaderStatus = void 0; + var r = function() { + function e(e, t) { + for (var n = 0; n < t.length; n++) { + var i = t[n]; + i.enumerable = i.enumerable || !1, i.configurable = !0, "value" in i && (i.writable = !0), Object.defineProperty(e, i.key, i) + } + } + return function(t, n, i) { + return n && e(t.prototype, n), i && e(t, i), t + } + }(), + s = e("../utils/exception.js"), + a = n.LoaderStatus = { + kIdle: 0, + kConnecting: 1, + kBuffering: 2, + kError: 3, + kComplete: 4 + }; + n.LoaderErrors = { + OK: "OK", + EXCEPTION: "Exception", + HTTP_STATUS_CODE_INVALID: "HttpStatusCodeInvalid", + CONNECTING_TIMEOUT: "ConnectingTimeout", + EARLY_EOF: "EarlyEof", + UNRECOVERABLE_EARLY_EOF: "UnrecoverableEarlyEof" + }, n.BaseLoader = function() { + function e(t) { + i(this, e), this._type = t || "undefined", this._status = a.kIdle, this._needStash = !1, this._onContentLengthKnown = null, this._onURLRedirect = null, this._onDataArrival = null, this._onError = null, this._onComplete = null + } + return r(e, [{ + key: "destroy", + value: function() { + this._status = a.kIdle, this._onContentLengthKnown = null, this._onURLRedirect = null, this._onDataArrival = null, this._onError = null, this._onComplete = null + } + }, { + key: "isWorking", + value: function() { + return this._status === a.kConnecting || this._status === a.kBuffering + } + }, { + key: "open", + value: function(e, t) { + throw new s.NotImplementedException("Unimplemented abstract function!") + } + }, { + key: "abort", + value: function() { + throw new s.NotImplementedException("Unimplemented abstract function!") + } + }, { + key: "type", + get: function() { + return this._type + } + }, { + key: "status", + get: function() { + return this._status + } + }, { + key: "needStashBuffer", + get: function() { + return this._needStash + } + }, { + key: "onContentLengthKnown", + get: function() { + return this._onContentLengthKnown + }, + set: function(e) { + this._onContentLengthKnown = e + } + }, { + key: "onURLRedirect", + get: function() { + return this._onURLRedirect + }, + set: function(e) { + this._onURLRedirect = e + } + }, { + key: "onDataArrival", + get: function() { + return this._onDataArrival + }, + set: function(e) { + this._onDataArrival = e + } + }, { + key: "onError", + get: function() { + return this._onError + }, + set: function(e) { + this._onError = e + } + }, { + key: "onComplete", + get: function() { + return this._onComplete + }, + set: function(e) { + this._onComplete = e + } + }]), e + }() + }, { + "../utils/exception.js": 40 + }], + 25: [function(e, t, n) { + "use strict"; + + function i(e, t) { + if (!(e instanceof t)) throw new TypeError("Cannot call a class as a function") + } + Object.defineProperty(n, "__esModule", { + value: !0 + }); + var r = function() { + function e(e, t) { + for (var n = 0; n < t.length; n++) { + var i = t[n]; + i.enumerable = i.enumerable || !1, i.configurable = !0, "value" in i && (i.writable = !0), Object.defineProperty(e, i.key, i) + } + } + return function(t, n, i) { + return n && e(t.prototype, n), i && e(t, i), t + } + }(), + s = function() { + function e(t, n) { + i(this, e), this._startName = t, this._endName = n + } + return r(e, [{ + key: "getConfig", + value: function(e, t) { + var n = e; + if (0 !== t.from || -1 !== t.to) { + var i = !0; - 1 === n.indexOf("?") && (n += "?", i = !1), i && (n += "&"), n += this._startName + "=" + t.from.toString(), -1 !== t.to && (n += "&" + this._endName + "=" + t.to.toString()) + } + return { + url: n, + headers: {} + } + } + }, { + key: "removeURLParameters", + value: function(e) { + var t = e.split("?")[0], + n = void 0, + i = e.indexOf("?"); - 1 !== i && (n = e.substring(i + 1)); + var r = ""; + if (void 0 != n && n.length > 0) + for (var s = n.split("&"), a = 0; a < s.length; a++) { + var o = s[a].split("="), + u = a > 0; + o[0] !== this._startName && o[0] !== this._endName && (u && (r += "&"), r += s[a]) + } + return 0 === r.length ? t : t + "?" + r + } + }]), e + }(); + n.default = s + }, {}], + 26: [function(e, t, n) { + "use strict"; + + function i(e, t) { + if (!(e instanceof t)) throw new TypeError("Cannot call a class as a function") + } + Object.defineProperty(n, "__esModule", { + value: !0 + }); + var r = function() { + function e(e, t) { + for (var n = 0; n < t.length; n++) { + var i = t[n]; + i.enumerable = i.enumerable || !1, i.configurable = !0, "value" in i && (i.writable = !0), Object.defineProperty(e, i.key, i) + } + } + return function(t, n, i) { + return n && e(t.prototype, n), i && e(t, i), t + } + }(), + s = function() { + function e(t) { + i(this, e), this._zeroStart = t || !1 + } + return r(e, [{ + key: "getConfig", + value: function(e, t) { + var n = {}; + if (0 !== t.from || -1 !== t.to) { + var i = void 0; + i = -1 !== t.to ? "bytes=" + t.from.toString() + "-" + t.to.toString() : "bytes=" + t.from.toString() + "-", n.Range = i + } else this._zeroStart && (n.Range = "bytes=0-"); + return { + url: e, + headers: n + } + } + }, { + key: "removeURLParameters", + value: function(e) { + return e + } + }]), e + }(); + n.default = s + }, {}], + 27: [function(e, t, n) { + "use strict"; + + function i(e, t) { + if (!(e instanceof t)) throw new TypeError("Cannot call a class as a function") + } + Object.defineProperty(n, "__esModule", { + value: !0 + }); + var r = function() { + function e(e, t) { + for (var n = 0; n < t.length; n++) { + var i = t[n]; + i.enumerable = i.enumerable || !1, i.configurable = !0, "value" in i && (i.writable = !0), Object.defineProperty(e, i.key, i) + } + } + return function(t, n, i) { + return n && e(t.prototype, n), i && e(t, i), t + } + }(), + s = function() { + function e() { + i(this, e), this._firstCheckpoint = 0, this._lastCheckpoint = 0, this._intervalBytes = 0, this._totalBytes = 0, this._lastSecondBytes = 0, self.performance && self.performance.now ? this._now = self.performance.now.bind(self.performance) : this._now = Date.now + } + return r(e, [{ + key: "reset", + value: function() { + this._firstCheckpoint = this._lastCheckpoint = 0, this._totalBytes = this._intervalBytes = 0, this._lastSecondBytes = 0 + } + }, { + key: "addBytes", + value: function(e) { + 0 === this._firstCheckpoint ? (this._firstCheckpoint = this._now(), this._lastCheckpoint = this._firstCheckpoint, this._intervalBytes += e, this._totalBytes += e) : this._now() - this._lastCheckpoint < 1e3 ? (this._intervalBytes += e, this._totalBytes += e) : (this._lastSecondBytes = this._intervalBytes, this._intervalBytes = e, this._totalBytes += e, this._lastCheckpoint = this._now()) + } + }, { + key: "currentKBps", + get: function() { + this.addBytes(0); + var e = (this._now() - this._lastCheckpoint) / 1e3; + return 0 == e && (e = 1), this._intervalBytes / e / 1024 + } + }, { + key: "lastSecondKBps", + get: function() { + return this.addBytes(0), 0 !== this._lastSecondBytes ? this._lastSecondBytes / 1024 : this._now() - this._lastCheckpoint >= 500 ? this.currentKBps : 0 + } + }, { + key: "averageKBps", + get: function() { + var e = (this._now() - this._firstCheckpoint) / 1e3; + return this._totalBytes / e / 1024 + } + }]), e + }(); + n.default = s + }, {}], + 28: [function(e, t, n) { + "use strict"; + + function i(e, t) { + if (!(e instanceof t)) throw new TypeError("Cannot call a class as a function") + } + + function r(e, t) { + if (!e) throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); + return !t || "object" != typeof t && "function" != typeof t ? e : t + } + + function s(e, t) { + if ("function" != typeof t && null !== t) throw new TypeError("Super expression must either be null or a function, not " + typeof t); + e.prototype = Object.create(t && t.prototype, { + constructor: { + value: e, + enumerable: !1, + writable: !0, + configurable: !0 + } + }), t && (Object.setPrototypeOf ? Object.setPrototypeOf(e, t) : e.__proto__ = t) + } + Object.defineProperty(n, "__esModule", { + value: !0 + }); + var a = function e(t, n, i) { + null === t && (t = Function.prototype); + var r = Object.getOwnPropertyDescriptor(t, n); + if (void 0 === r) { + var s = Object.getPrototypeOf(t); + return null === s ? void 0 : e(s, n, i) + } + if ("value" in r) return r.value; + var a = r.get; + if (void 0 !== a) return a.call(i) + }, + o = function() { + function e(e, t) { + for (var n = 0; n < t.length; n++) { + var i = t[n]; + i.enumerable = i.enumerable || !1, i.configurable = !0, "value" in i && (i.writable = !0), Object.defineProperty(e, i.key, i) + } + } + return function(t, n, i) { + return n && e(t.prototype, n), i && e(t, i), t + } + }(), + u = e("../utils/logger.js"), + l = (function(e) { + e && e.__esModule + }(u), e("./loader.js")), + d = e("../utils/exception.js"), + h = function(e) { + function t() { + i(this, t); + var e = r(this, (t.__proto__ || Object.getPrototypeOf(t)).call(this, "websocket-loader")); + return e.TAG = "WebSocketLoader", e._needStash = !0, e._ws = null, e._requestAbort = !1, e._receivedLength = 0, e + } + return s(t, e), o(t, null, [{ + key: "isSupported", + value: function() { + try { + return void 0 !== self.WebSocket + } catch (e) { + return !1 + } + } + }]), o(t, [{ + key: "destroy", + value: function() { + this._ws && this.abort(), a(t.prototype.__proto__ || Object.getPrototypeOf(t.prototype), "destroy", this).call(this) + } + }, { + key: "open", + value: function(e) { + try { + var t = this._ws = new self.WebSocket(e.url); + t.binaryType = "arraybuffer", t.onopen = this._onWebSocketOpen.bind(this), t.onclose = this._onWebSocketClose.bind(this), t.onmessage = this._onWebSocketMessage.bind(this), t.onerror = this._onWebSocketError.bind(this), this._status = l.LoaderStatus.kConnecting + } catch (e) { + this._status = l.LoaderStatus.kError; + var n = { + code: e.code, + msg: e.message + }; + if (!this._onError) throw new d.RuntimeException(n.msg); + this._onError(l.LoaderErrors.EXCEPTION, n) + } + } + }, { + key: "abort", + value: function() { + var e = this._ws; + !e || 0 !== e.readyState && 1 !== e.readyState || (this._requestAbort = !0, e.close()), this._ws = null, this._status = l.LoaderStatus.kComplete + } + }, { + key: "_onWebSocketOpen", + value: function(e) { + this._status = l.LoaderStatus.kBuffering + } + }, { + key: "_onWebSocketClose", + value: function(e) { + if (!0 === this._requestAbort) return void(this._requestAbort = !1); + this._status = l.LoaderStatus.kComplete, this._onComplete && this._onComplete(0, this._receivedLength - 1) + } + }, { + key: "_onWebSocketMessage", + value: function(e) { + var t = this; + if (e.data instanceof ArrayBuffer) this._dispatchArrayBuffer(e.data); + else if (e.data instanceof Blob) { + var n = new FileReader; + n.onload = function() { + t._dispatchArrayBuffer(n.result) + }, n.readAsArrayBuffer(e.data) + } else { + this._status = l.LoaderStatus.kError; + var i = { + code: -1, + msg: "Unsupported WebSocket message type: " + e.data.constructor.name + }; + if (!this._onError) throw new d.RuntimeException(i.msg); + this._onError(l.LoaderErrors.EXCEPTION, i) + } + } + }, { + key: "_dispatchArrayBuffer", + value: function(e) { + var t = e, + n = this._receivedLength; + this._receivedLength += t.byteLength, this._onDataArrival && this._onDataArrival(t, n, this._receivedLength) + } + }, { + key: "_onWebSocketError", + value: function(e) { + this._status = l.LoaderStatus.kError; + var t = { + code: e.code, + msg: e.message + }; + if (!this._onError) throw new d.RuntimeException(t.msg); + this._onError(l.LoaderErrors.EXCEPTION, t) + } + }]), t + }(l.BaseLoader); + n.default = h + }, { + "../utils/exception.js": 40, + "../utils/logger.js": 41, + "./loader.js": 24 + }], + 29: [function(e, t, n) { + "use strict"; + + function i(e, t) { + if (!(e instanceof t)) throw new TypeError("Cannot call a class as a function") + } + + function r(e, t) { + if (!e) throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); + return !t || "object" != typeof t && "function" != typeof t ? e : t + } + + function s(e, t) { + if ("function" != typeof t && null !== t) throw new TypeError("Super expression must either be null or a function, not " + typeof t); + e.prototype = Object.create(t && t.prototype, { + constructor: { + value: e, + enumerable: !1, + writable: !0, + configurable: !0 + } + }), t && (Object.setPrototypeOf ? Object.setPrototypeOf(e, t) : e.__proto__ = t) + } + Object.defineProperty(n, "__esModule", { + value: !0 + }); + var a = "function" == typeof Symbol && "symbol" == typeof Symbol.iterator ? function(e) { + return typeof e + } : function(e) { + return e && "function" == typeof Symbol && e.constructor === Symbol && e !== Symbol.prototype ? "symbol" : typeof e + }, + o = function e(t, n, i) { + null === t && (t = Function.prototype); + var r = Object.getOwnPropertyDescriptor(t, n); + if (void 0 === r) { + var s = Object.getPrototypeOf(t); + return null === s ? void 0 : e(s, n, i) + } + if ("value" in r) return r.value; + var a = r.get; + if (void 0 !== a) return a.call(i) + }, + u = function() { + function e(e, t) { + for (var n = 0; n < t.length; n++) { + var i = t[n]; + i.enumerable = i.enumerable || !1, i.configurable = !0, "value" in i && (i.writable = !0), Object.defineProperty(e, i.key, i) + } + } + return function(t, n, i) { + return n && e(t.prototype, n), i && e(t, i), t + } + }(), + l = e("../utils/logger.js"), + d = function(e) { + return e && e.__esModule ? e : { + default: e + } + }(l), + h = e("./loader.js"), + f = e("../utils/exception.js"), + c = function(e) { + function t(e, n) { + i(this, t); + var s = r(this, (t.__proto__ || Object.getPrototypeOf(t)).call(this, "xhr-moz-chunked-loader")); + return s.TAG = "MozChunkedLoader", s._seekHandler = e, s._config = n, s._needStash = !0, s._xhr = null, s._requestAbort = !1, s._contentLength = null, s._receivedLength = 0, s + } + return s(t, e), u(t, null, [{ + key: "isSupported", + value: function() { + try { + var e = new XMLHttpRequest; + return e.open("GET", "https://example.com", !0), e.responseType = "moz-chunked-arraybuffer", "moz-chunked-arraybuffer" === e.responseType + } catch (e) { + return d.default.w("MozChunkedLoader", e.message), !1 + } + } + }]), u(t, [{ + key: "destroy", + value: function() { + this.isWorking() && this.abort(), this._xhr && (this._xhr.onreadystatechange = null, this._xhr.onprogress = null, this._xhr.onloadend = null, this._xhr.onerror = null, this._xhr = null), o(t.prototype.__proto__ || Object.getPrototypeOf(t.prototype), "destroy", this).call(this) + } + }, { + key: "open", + value: function(e, t) { + this._dataSource = e, this._range = t; + var n = e.url; + this._config.reuseRedirectedURL && void 0 != e.redirectedURL && (n = e.redirectedURL); + var i = this._seekHandler.getConfig(n, t); + this._requestURL = i.url; + var r = this._xhr = new XMLHttpRequest; + if (r.open("GET", i.url, !0), r.responseType = "moz-chunked-arraybuffer", r.onreadystatechange = this._onReadyStateChange.bind(this), r.onprogress = this._onProgress.bind(this), r.onloadend = this._onLoadEnd.bind(this), r.onerror = this._onXhrError.bind(this), e.withCredentials && (r.withCredentials = !0), "object" === a(i.headers)) { + var s = i.headers; + for (var o in s) s.hasOwnProperty(o) && r.setRequestHeader(o, s[o]) + } + this._status = h.LoaderStatus.kConnecting, r.send() + } + }, { + key: "abort", + value: function() { + this._requestAbort = !0, this._xhr && this._xhr.abort(), this._status = h.LoaderStatus.kComplete + } + }, { + key: "_onReadyStateChange", + value: function(e) { + var t = e.target; + if (2 === t.readyState) { + if (void 0 != t.responseURL && t.responseURL !== this._requestURL && this._onURLRedirect) { + var n = this._seekHandler.removeURLParameters(t.responseURL); + this._onURLRedirect(n) + } + if (0 !== t.status && (t.status < 200 || t.status > 299)) { + if (this._status = h.LoaderStatus.kError, !this._onError) throw new f.RuntimeException("MozChunkedLoader: Http code invalid, " + t.status + " " + t.statusText); + this._onError(h.LoaderErrors.HTTP_STATUS_CODE_INVALID, { + code: t.status, + msg: t.statusText + }) + } else this._status = h.LoaderStatus.kBuffering + } + } + }, { + key: "_onProgress", + value: function(e) { + if (this._status !== h.LoaderStatus.kError) { + null === this._contentLength && null !== e.total && 0 !== e.total && (this._contentLength = e.total, this._onContentLengthKnown && this._onContentLengthKnown(this._contentLength)); + var t = e.target.response, + n = this._range.from + this._receivedLength; + this._receivedLength += t.byteLength, this._onDataArrival && this._onDataArrival(t, n, this._receivedLength) + } + } + }, { + key: "_onLoadEnd", + value: function(e) { + if (!0 === this._requestAbort) return void(this._requestAbort = !1); + this._status !== h.LoaderStatus.kError && (this._status = h.LoaderStatus.kComplete, this._onComplete && this._onComplete(this._range.from, this._range.from + this._receivedLength - 1)) + } + }, { + key: "_onXhrError", + value: function(e) { + this._status = h.LoaderStatus.kError; + var t = 0, + n = null; + if (this._contentLength && e.loaded < this._contentLength ? (t = h.LoaderErrors.EARLY_EOF, n = { + code: -1, + msg: "Moz-Chunked stream meet Early-Eof" + }) : (t = h.LoaderErrors.EXCEPTION, n = { + code: -1, + msg: e.constructor.name + " " + e.type + }), !this._onError) throw new f.RuntimeException(n.msg); + this._onError(t, n) + } + }]), t + }(h.BaseLoader); + n.default = c + }, { + "../utils/exception.js": 40, + "../utils/logger.js": 41, + "./loader.js": 24 + }], + 30: [function(e, t, n) { + "use strict"; + + function i(e, t) { + if (!(e instanceof t)) throw new TypeError("Cannot call a class as a function") + } + + function r(e, t) { + if (!e) throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); + return !t || "object" != typeof t && "function" != typeof t ? e : t + } + + function s(e, t) { + if ("function" != typeof t && null !== t) throw new TypeError("Super expression must either be null or a function, not " + typeof t); + e.prototype = Object.create(t && t.prototype, { + constructor: { + value: e, + enumerable: !1, + writable: !0, + configurable: !0 + } + }), t && (Object.setPrototypeOf ? Object.setPrototypeOf(e, t) : e.__proto__ = t) + } + Object.defineProperty(n, "__esModule", { + value: !0 + }); + var a = "function" == typeof Symbol && "symbol" == typeof Symbol.iterator ? function(e) { + return typeof e + } : function(e) { + return e && "function" == typeof Symbol && e.constructor === Symbol && e !== Symbol.prototype ? "symbol" : typeof e + }, + o = function e(t, n, i) { + null === t && (t = Function.prototype); + var r = Object.getOwnPropertyDescriptor(t, n); + if (void 0 === r) { + var s = Object.getPrototypeOf(t); + return null === s ? void 0 : e(s, n, i) + } + if ("value" in r) return r.value; + var a = r.get; + if (void 0 !== a) return a.call(i) + }, + u = function() { + function e(e, t) { + for (var n = 0; n < t.length; n++) { + var i = t[n]; + i.enumerable = i.enumerable || !1, i.configurable = !0, "value" in i && (i.writable = !0), Object.defineProperty(e, i.key, i) + } + } + return function(t, n, i) { + return n && e(t.prototype, n), i && e(t, i), t + } + }(), + l = e("../utils/logger.js"), + d = function(e) { + return e && e.__esModule ? e : { + default: e + } + }(l), + h = e("./loader.js"), + f = e("../utils/exception.js"), + c = function(e) { + function t(e, n) { + i(this, t); + var s = r(this, (t.__proto__ || Object.getPrototypeOf(t)).call(this, "xhr-msstream-loader")); + return s.TAG = "MSStreamLoader", s._seekHandler = e, s._config = n, s._needStash = !0, s._xhr = null, s._reader = null, s._totalRange = null, s._currentRange = null, s._currentRequestURL = null, s._currentRedirectedURL = null, s._contentLength = null, s._receivedLength = 0, s._bufferLimit = 16777216, s._lastTimeBufferSize = 0, s._isReconnecting = !1, s + } + return s(t, e), u(t, null, [{ + key: "isSupported", + value: function() { + try { + if (void 0 === self.MSStream || void 0 === self.MSStreamReader) return !1; + var e = new XMLHttpRequest; + return e.open("GET", "https://example.com", !0), e.responseType = "ms-stream", "ms-stream" === e.responseType + } catch (e) { + return d.default.w("MSStreamLoader", e.message), !1 + } + } + }]), u(t, [{ + key: "destroy", + value: function() { + this.isWorking() && this.abort(), this._reader && (this._reader.onprogress = null, this._reader.onload = null, this._reader.onerror = null, this._reader = null), this._xhr && (this._xhr.onreadystatechange = null, this._xhr = null), o(t.prototype.__proto__ || Object.getPrototypeOf(t.prototype), "destroy", this).call(this) + } + }, { + key: "open", + value: function(e, t) { + this._internalOpen(e, t, !1) + } + }, { + key: "_internalOpen", + value: function(e, t, n) { + this._dataSource = e, n ? this._currentRange = t : this._totalRange = t; + var i = e.url; + this._config.reuseRedirectedURL && (void 0 != this._currentRedirectedURL ? i = this._currentRedirectedURL : void 0 != e.redirectedURL && (i = e.redirectedURL)); + var r = this._seekHandler.getConfig(i, t); + this._currentRequestURL = r.url; + var s = this._reader = new self.MSStreamReader; + s.onprogress = this._msrOnProgress.bind(this), s.onload = this._msrOnLoad.bind(this), s.onerror = this._msrOnError.bind(this); + var o = this._xhr = new XMLHttpRequest; + if (o.open("GET", r.url, !0), o.responseType = "ms-stream", o.onreadystatechange = this._xhrOnReadyStateChange.bind(this), o.onerror = this._xhrOnError.bind(this), e.withCredentials && (o.withCredentials = !0), "object" === a(r.headers)) { + var u = r.headers; + for (var l in u) u.hasOwnProperty(l) && o.setRequestHeader(l, u[l]) + } + this._isReconnecting ? this._isReconnecting = !1 : this._status = h.LoaderStatus.kConnecting, o.send() + } + }, { + key: "abort", + value: function() { + this._internalAbort(), this._status = h.LoaderStatus.kComplete + } + }, { + key: "_internalAbort", + value: function() { + this._reader && (1 === this._reader.readyState && this._reader.abort(), this._reader.onprogress = null, this._reader.onload = null, this._reader.onerror = null, this._reader = null), this._xhr && (this._xhr.abort(), this._xhr.onreadystatechange = null, this._xhr = null) + } + }, { + key: "_xhrOnReadyStateChange", + value: function(e) { + var t = e.target; + if (2 === t.readyState) + if (t.status >= 200 && t.status <= 299) { + if (this._status = h.LoaderStatus.kBuffering, void 0 != t.responseURL) { + var n = this._seekHandler.removeURLParameters(t.responseURL); + t.responseURL !== this._currentRequestURL && n !== this._currentRedirectedURL && (this._currentRedirectedURL = n, this._onURLRedirect && this._onURLRedirect(n)) + } + var i = t.getResponseHeader("Content-Length"); + if (null != i && null == this._contentLength) { + var r = parseInt(i); + r > 0 && (this._contentLength = r, this._onContentLengthKnown && this._onContentLengthKnown(this._contentLength)) + } + } else { + if (this._status = h.LoaderStatus.kError, !this._onError) throw new f.RuntimeException("MSStreamLoader: Http code invalid, " + t.status + " " + t.statusText); + this._onError(h.LoaderErrors.HTTP_STATUS_CODE_INVALID, { + code: t.status, + msg: t.statusText + }) + } + else if (3 === t.readyState && t.status >= 200 && t.status <= 299) { + this._status = h.LoaderStatus.kBuffering; + var s = t.response; + this._reader.readAsArrayBuffer(s) + } + } + }, { + key: "_xhrOnError", + value: function(e) { + this._status = h.LoaderStatus.kError; + var t = h.LoaderErrors.EXCEPTION, + n = { + code: -1, + msg: e.constructor.name + " " + e.type + }; + if (!this._onError) throw new f.RuntimeException(n.msg); + this._onError(t, n) + } + }, { + key: "_msrOnProgress", + value: function(e) { + var t = e.target, + n = t.result; + if (null == n) return void this._doReconnectIfNeeded(); + var i = n.slice(this._lastTimeBufferSize); + this._lastTimeBufferSize = n.byteLength; + var r = this._totalRange.from + this._receivedLength; + this._receivedLength += i.byteLength, this._onDataArrival && this._onDataArrival(i, r, this._receivedLength), n.byteLength >= this._bufferLimit && (d.default.v(this.TAG, "MSStream buffer exceeded max size near " + (r + i.byteLength) + ", reconnecting..."), this._doReconnectIfNeeded()) + } + }, { + key: "_doReconnectIfNeeded", + value: function() { + if (null == this._contentLength || this._receivedLength < this._contentLength) { + this._isReconnecting = !0, this._lastTimeBufferSize = 0, this._internalAbort(); + var e = { + from: this._totalRange.from + this._receivedLength, + to: -1 + }; + this._internalOpen(this._dataSource, e, !0) + } + } + }, { + key: "_msrOnLoad", + value: function(e) { + this._status = h.LoaderStatus.kComplete, this._onComplete && this._onComplete(this._totalRange.from, this._totalRange.from + this._receivedLength - 1) + } + }, { + key: "_msrOnError", + value: function(e) { + this._status = h.LoaderStatus.kError; + var t = 0, + n = null; + if (this._contentLength && this._receivedLength < this._contentLength ? (t = h.LoaderErrors.EARLY_EOF, n = { + code: -1, + msg: "MSStream meet Early-Eof" + }) : (t = h.LoaderErrors.EARLY_EOF, n = { + code: -1, + msg: e.constructor.name + " " + e.type + }), !this._onError) throw new f.RuntimeException(n.msg); + this._onError(t, n) + } + }]), t + }(h.BaseLoader); + n.default = c + }, { + "../utils/exception.js": 40, + "../utils/logger.js": 41, + "./loader.js": 24 + }], + 31: [function(e, t, n) { + "use strict"; + + function i(e) { + return e && e.__esModule ? e : { + default: e + } + } + + function r(e, t) { + if (!(e instanceof t)) throw new TypeError("Cannot call a class as a function") + } + + function s(e, t) { + if (!e) throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); + return !t || "object" != typeof t && "function" != typeof t ? e : t + } + + function a(e, t) { + if ("function" != typeof t && null !== t) throw new TypeError("Super expression must either be null or a function, not " + typeof t); + e.prototype = Object.create(t && t.prototype, { + constructor: { + value: e, + enumerable: !1, + writable: !0, + configurable: !0 + } + }), t && (Object.setPrototypeOf ? Object.setPrototypeOf(e, t) : e.__proto__ = t) + } + Object.defineProperty(n, "__esModule", { + value: !0 + }); + var o = "function" == typeof Symbol && "symbol" == typeof Symbol.iterator ? function(e) { + return typeof e + } : function(e) { + return e && "function" == typeof Symbol && e.constructor === Symbol && e !== Symbol.prototype ? "symbol" : typeof e + }, + u = function e(t, n, i) { + null === t && (t = Function.prototype); + var r = Object.getOwnPropertyDescriptor(t, n); + if (void 0 === r) { + var s = Object.getPrototypeOf(t); + return null === s ? void 0 : e(s, n, i) + } + if ("value" in r) return r.value; + var a = r.get; + if (void 0 !== a) return a.call(i) + }, + l = function() { + function e(e, t) { + for (var n = 0; n < t.length; n++) { + var i = t[n]; + i.enumerable = i.enumerable || !1, i.configurable = !0, "value" in i && (i.writable = !0), Object.defineProperty(e, i.key, i) + } + } + return function(t, n, i) { + return n && e(t.prototype, n), i && e(t, i), t + } + }(), + d = e("../utils/logger.js"), + h = i(d), + f = e("./speed-sampler.js"), + c = i(f), + _ = e("./loader.js"), + m = e("../utils/exception.js"), + p = function(e) { + function t(e, n) { + r(this, t); + var i = s(this, (t.__proto__ || Object.getPrototypeOf(t)).call(this, "xhr-range-loader")); + return i.TAG = "RangeLoader", i._seekHandler = e, i._config = n, i._needStash = !1, i._chunkSizeKBList = [128, 256, 384, 512, 768, 1024, 1536, 2048, 3072, 4096, 5120, 6144, 7168, 8192], i._currentChunkSizeKB = 384, i._currentSpeedNormalized = 0, i._zeroSpeedChunkCount = 0, i._xhr = null, i._speedSampler = new c.default, i._requestAbort = !1, i._waitForTotalLength = !1, i._totalLengthReceived = !1, i._currentRequestURL = null, i._currentRedirectedURL = null, i._currentRequestRange = null, i._totalLength = null, i._contentLength = null, i._receivedLength = 0, i._lastTimeLoaded = 0, i + } + return a(t, e), l(t, null, [{ + key: "isSupported", + value: function() { + try { + var e = new XMLHttpRequest; + return e.open("GET", "https://example.com", !0), e.responseType = "arraybuffer", "arraybuffer" === e.responseType + } catch (e) { + return h.default.w("RangeLoader", e.message), !1 + } + } + }]), l(t, [{ + key: "destroy", + value: function() { + this.isWorking() && this.abort(), this._xhr && (this._xhr.onreadystatechange = null, this._xhr.onprogress = null, this._xhr.onload = null, this._xhr.onerror = null, this._xhr = null), u(t.prototype.__proto__ || Object.getPrototypeOf(t.prototype), "destroy", this).call(this) + } + }, { + key: "open", + value: function(e, t) { + this._dataSource = e, this._range = t, this._status = _.LoaderStatus.kConnecting; + var n = !1; + void 0 != this._dataSource.filesize && 0 !== this._dataSource.filesize && (n = !0, this._totalLength = this._dataSource.filesize), this._totalLengthReceived || n ? this._openSubRange() : (this._waitForTotalLength = !0, this._internalOpen(this._dataSource, { + from: 0, + to: -1 + })) + } + }, { + key: "_openSubRange", + value: function() { + var e = 1024 * this._currentChunkSizeKB, + t = this._range.from + this._receivedLength, + n = t + e; + null != this._contentLength && n - this._range.from >= this._contentLength && (n = this._range.from + this._contentLength - 1), this._currentRequestRange = { + from: t, + to: n + }, this._internalOpen(this._dataSource, this._currentRequestRange) + } + }, { + key: "_internalOpen", + value: function(e, t) { + this._lastTimeLoaded = 0; + var n = e.url; + this._config.reuseRedirectedURL && (void 0 != this._currentRedirectedURL ? n = this._currentRedirectedURL : void 0 != e.redirectedURL && (n = e.redirectedURL)); + var i = this._seekHandler.getConfig(n, t); + this._currentRequestURL = i.url; + var r = this._xhr = new XMLHttpRequest; + if (r.open("GET", i.url, !0), r.responseType = "arraybuffer", r.onreadystatechange = this._onReadyStateChange.bind(this), r.onprogress = this._onProgress.bind(this), r.onload = this._onLoad.bind(this), r.onerror = this._onXhrError.bind(this), e.withCredentials && (r.withCredentials = !0), "object" === o(i.headers)) { + var s = i.headers; + for (var a in s) s.hasOwnProperty(a) && r.setRequestHeader(a, s[a]) + } + r.send() + } + }, { + key: "abort", + value: function() { + this._requestAbort = !0, this._internalAbort(), this._status = _.LoaderStatus.kComplete + } + }, { + key: "_internalAbort", + value: function() { + this._xhr && (this._xhr.onreadystatechange = null, this._xhr.onprogress = null, this._xhr.onload = null, this._xhr.onerror = null, this._xhr.abort(), this._xhr = null) + } + }, { + key: "_onReadyStateChange", + value: function(e) { + var t = e.target; + if (2 === t.readyState) { + if (void 0 != t.responseURL) { + var n = this._seekHandler.removeURLParameters(t.responseURL); + t.responseURL !== this._currentRequestURL && n !== this._currentRedirectedURL && (this._currentRedirectedURL = n, this._onURLRedirect && this._onURLRedirect(n)) + } + if (t.status >= 200 && t.status <= 299) { + if (this._waitForTotalLength) return; + this._status = _.LoaderStatus.kBuffering + } else { + if (this._status = _.LoaderStatus.kError, !this._onError) throw new m.RuntimeException("RangeLoader: Http code invalid, " + t.status + " " + t.statusText); + this._onError(_.LoaderErrors.HTTP_STATUS_CODE_INVALID, { + code: t.status, + msg: t.statusText + }) + } + } + } + }, { + key: "_onProgress", + value: function(e) { + if (this._status !== _.LoaderStatus.kError) { + if (null === this._contentLength) { + var t = !1; + if (this._waitForTotalLength) { + this._waitForTotalLength = !1, this._totalLengthReceived = !0, t = !0; + var n = e.total; + this._internalAbort(), null != n & 0 !== n && (this._totalLength = n) + } + if (-1 === this._range.to ? this._contentLength = this._totalLength - this._range.from : this._contentLength = this._range.to - this._range.from + 1, t) return void this._openSubRange(); + this._onContentLengthKnown && this._onContentLengthKnown(this._contentLength) + } + var i = e.loaded - this._lastTimeLoaded; + this._lastTimeLoaded = e.loaded, this._speedSampler.addBytes(i) + } + } + }, { + key: "_normalizeSpeed", + value: function(e) { + var t = this._chunkSizeKBList, + n = t.length - 1, + i = 0, + r = 0, + s = n; + if (e < t[0]) return t[0]; + for (; r <= s;) { + if ((i = r + Math.floor((s - r) / 2)) === n || e >= t[i] && e < t[i + 1]) return t[i]; + t[i] < e ? r = i + 1 : s = i - 1 + } + } + }, { + key: "_onLoad", + value: function(e) { + if (this._status !== _.LoaderStatus.kError) { + if (this._waitForTotalLength) return void(this._waitForTotalLength = !1); + this._lastTimeLoaded = 0; + var t = this._speedSampler.lastSecondKBps; + if (0 === t && ++this._zeroSpeedChunkCount >= 3 && (t = this._speedSampler.currentKBps), 0 !== t) { + var n = this._normalizeSpeed(t); + this._currentSpeedNormalized !== n && (this._currentSpeedNormalized = n, this._currentChunkSizeKB = n) + } + var i = e.target.response, + r = this._range.from + this._receivedLength; + this._receivedLength += i.byteLength; + var s = !1; + null != this._contentLength && this._receivedLength < this._contentLength ? this._openSubRange() : s = !0, this._onDataArrival && this._onDataArrival(i, r, this._receivedLength), s && (this._status = _.LoaderStatus.kComplete, this._onComplete && this._onComplete(this._range.from, this._range.from + this._receivedLength - 1)) + } + } + }, { + key: "_onXhrError", + value: function(e) { + this._status = _.LoaderStatus.kError; + var t = 0, + n = null; + if (this._contentLength && this._receivedLength > 0 && this._receivedLength < this._contentLength ? (t = _.LoaderErrors.EARLY_EOF, n = { + code: -1, + msg: "RangeLoader meet Early-Eof" + }) : (t = _.LoaderErrors.EXCEPTION, n = { + code: -1, + msg: e.constructor.name + " " + e.type + }), !this._onError) throw new m.RuntimeException(n.msg); + this._onError(t, n) + } + }, { + key: "currentSpeed", + get: function() { + return this._speedSampler.lastSecondKBps + } + }]), t + }(_.BaseLoader); + n.default = p + }, { + "../utils/exception.js": 40, + "../utils/logger.js": 41, + "./loader.js": 24, + "./speed-sampler.js": 27 + }], + 32: [function(e, t, n) { + "use strict"; + + function i(e) { + return e && e.__esModule ? e : { + default: e + } + } + + function r(e, t) { + if (!(e instanceof t)) throw new TypeError("Cannot call a class as a function") + } + Object.defineProperty(n, "__esModule", { + value: !0 + }); + var s = "function" == typeof Symbol && "symbol" == typeof Symbol.iterator ? function(e) { + return typeof e + } : function(e) { + return e && "function" == typeof Symbol && e.constructor === Symbol && e !== Symbol.prototype ? "symbol" : typeof e + }, + a = function() { + function e(e, t) { + for (var n = 0; n < t.length; n++) { + var i = t[n]; + i.enumerable = i.enumerable || !1, i.configurable = !0, "value" in i && (i.writable = !0), Object.defineProperty(e, i.key, i) + } + } + return function(t, n, i) { + return n && e(t.prototype, n), i && e(t, i), t + } + }(), + o = e("events"), + u = i(o), + l = e("../utils/logger.js"), + d = i(l), + h = e("../utils/browser.js"), + f = i(h), + c = e("./player-events.js"), + _ = i(c), + m = e("../core/transmuxer.js"), + p = i(m), + v = e("../core/transmuxing-events.js"), + g = i(v), + y = e("../core/mse-controller.js"), + E = i(y), + b = e("../core/mse-events.js"), + S = i(b), + k = e("./player-errors.js"), + L = e("../config.js"), + w = e("../utils/exception.js"), + R = function() { + function e(t, n) { + if (r(this, e), this.TAG = "FlvPlayer", this._type = "FlvPlayer", this._emitter = new u.default, this._config = (0, L.createDefaultConfig)(), "object" === (void 0 === n ? "undefined" : s(n)) && Object.assign(this._config, n), "flv" !== t.type.toLowerCase()) throw new w.InvalidArgumentException("FlvPlayer requires an flv MediaDataSource input!"); + !0 === t.isLive && (this._config.isLive = !0), this.e = { + onvLoadedMetadata: this._onvLoadedMetadata.bind(this), + onvSeeking: this._onvSeeking.bind(this), + onvCanPlay: this._onvCanPlay.bind(this), + onvStalled: this._onvStalled.bind(this), + onvProgress: this._onvProgress.bind(this) + }, self.performance && self.performance.now ? this._now = self.performance.now.bind(self.performance) : this._now = Date.now, this._pendingSeekTime = null, this._requestSetTime = !1, this._seekpointRecord = null, this._progressChecker = null, this._mediaDataSource = t, this._mediaElement = null, this._msectl = null, this._transmuxer = null, this._mseSourceOpened = !1, this._hasPendingLoad = !1, this._receivedCanPlay = !1, this._mediaInfo = null, this._statisticsInfo = null; + var i = f.default.chrome && (f.default.version.major < 50 || 50 === f.default.version.major && f.default.version.build < 2661); + this._alwaysSeekKeyframe = !!(i || f.default.msedge || f.default.msie), this._alwaysSeekKeyframe && (this._config.accurateSeek = !1) + } + return a(e, [{ + key: "destroy", + value: function() { + null != this._progressChecker && (window.clearInterval(this._progressChecker), this._progressChecker = null), this._transmuxer && this.unload(), this._mediaElement && this.detachMediaElement(), this.e = null, this._mediaDataSource = null, this._emitter.removeAllListeners(), this._emitter = null + } + }, { + key: "on", + value: function(e, t) { + var n = this; + e === _.default.MEDIA_INFO ? null != this._mediaInfo && Promise.resolve().then(function() { + n._emitter.emit(_.default.MEDIA_INFO, n.mediaInfo) + }) : e === _.default.STATISTICS_INFO && null != this._statisticsInfo && Promise.resolve().then(function() { + n._emitter.emit(_.default.STATISTICS_INFO, n.statisticsInfo) + }), this._emitter.addListener(e, t) + } + }, { + key: "off", + value: function(e, t) { + this._emitter.removeListener(e, t) + } + }, { + key: "attachMediaElement", + value: function(e) { + var t = this; + if (this._mediaElement = e, e.addEventListener("loadedmetadata", this.e.onvLoadedMetadata), e.addEventListener("seeking", this.e.onvSeeking), e.addEventListener("canplay", this.e.onvCanPlay), e.addEventListener("stalled", this.e.onvStalled), e.addEventListener("progress", this.e.onvProgress), this._msectl = new E.default(this._config), this._msectl.on(S.default.UPDATE_END, this._onmseUpdateEnd.bind(this)), this._msectl.on(S.default.BUFFER_FULL, this._onmseBufferFull.bind(this)), this._msectl.on(S.default.SOURCE_OPEN, function() { + t._mseSourceOpened = !0, t._hasPendingLoad && (t._hasPendingLoad = !1, t.load()) + }), this._msectl.on(S.default.ERROR, function(e) { + t._emitter.emit(_.default.ERROR, k.ErrorTypes.MEDIA_ERROR, k.ErrorDetails.MEDIA_MSE_ERROR, e) + }), this._msectl.attachMediaElement(e), null != this._pendingSeekTime) try { + e.currentTime = this._pendingSeekTime, this._pendingSeekTime = null + } catch (e) {} + } + }, { + key: "detachMediaElement", + value: function() { + this._mediaElement && (this._msectl.detachMediaElement(), this._mediaElement.removeEventListener("loadedmetadata", this.e.onvLoadedMetadata), this._mediaElement.removeEventListener("seeking", this.e.onvSeeking), this._mediaElement.removeEventListener("canplay", this.e.onvCanPlay), this._mediaElement.removeEventListener("stalled", this.e.onvStalled), this._mediaElement.removeEventListener("progress", this.e.onvProgress), this._mediaElement = null), this._msectl && (this._msectl.destroy(), this._msectl = null) + } + }, { + key: "load", + value: function() { + var e = this; + if (!this._mediaElement) throw new w.IllegalStateException("HTMLMediaElement must be attached before load()!"); + if (this._transmuxer) throw new w.IllegalStateException("FlvPlayer.load() has been called, please call unload() first!"); + if (!this._hasPendingLoad) { + if (this._config.deferLoadAfterSourceOpen && !1 === this._mseSourceOpened) return void(this._hasPendingLoad = !0); + this._mediaElement.readyState > 0 && (this._requestSetTime = !0, this._mediaElement.currentTime = 0), this._transmuxer = new p.default(this._mediaDataSource, this._config), this._transmuxer.on(g.default.INIT_SEGMENT, function(t, n) { + e._msectl.appendInitSegment(n) + }), this._transmuxer.on(g.default.MEDIA_SEGMENT, function(t, n) { + if (e._msectl.appendMediaSegment(n), e._config.lazyLoad && !e._config.isLive) { + var i = e._mediaElement.currentTime; + n.info.endDts >= 1e3 * (i + e._config.lazyLoadMaxDuration) && null == e._progressChecker && (d.default.v(e.TAG, "Maximum buffering duration exceeded, suspend transmuxing task"), e._suspendTransmuxer()) + } + }), this._transmuxer.on(g.default.LOADING_COMPLETE, function() { + e._msectl.endOfStream(), e._emitter.emit(_.default.LOADING_COMPLETE) + }), + this._transmuxer.on(g.default.RECOVERED_EARLY_EOF, function() { + e._emitter.emit(_.default.RECOVERED_EARLY_EOF) + }), this._transmuxer.on(g.default.IO_ERROR, function(t, n) { + e._emitter.emit(_.default.ERROR, k.ErrorTypes.NETWORK_ERROR, t, n) + }), this._transmuxer.on(g.default.DEMUX_ERROR, function(t, n) { + e._emitter.emit(_.default.ERROR, k.ErrorTypes.MEDIA_ERROR, t, { + code: -1, + msg: n + }) + }), this._transmuxer.on(g.default.MEDIA_INFO, function(t) { + e._mediaInfo = t, e._emitter.emit(_.default.MEDIA_INFO, Object.assign({}, t)) + }), this._transmuxer.on(g.default.STATISTICS_INFO, function(t) { + e._statisticsInfo = e._fillStatisticsInfo(t), e._emitter.emit(_.default.STATISTICS_INFO, Object.assign({}, e._statisticsInfo)) + }), this._transmuxer.on(g.default.RECOMMEND_SEEKPOINT, function(t) { + e._mediaElement && !e._config.accurateSeek && (e._requestSetTime = !0, e._mediaElement.currentTime = t / 1e3) + }), this._transmuxer.open() + } + } + }, { + key: "unload", + value: function() { + this._mediaElement && this._mediaElement.pause(), this._msectl && this._msectl.seek(0), this._transmuxer && (this._transmuxer.close(), this._transmuxer.destroy(), this._transmuxer = null) + } + }, { + key: "play", + value: function() { + return this._mediaElement.play() + } + }, { + key: "pause", + value: function() { + this._mediaElement.pause() + } + }, { + key: "_fillStatisticsInfo", + value: function(e) { + if (e.playerType = this._type, !(this._mediaElement instanceof HTMLVideoElement)) return e; + var t = !0, + n = 0, + i = 0; + if (this._mediaElement.getVideoPlaybackQuality) { + var r = this._mediaElement.getVideoPlaybackQuality(); + n = r.totalVideoFrames, i = r.droppedVideoFrames + } else void 0 != this._mediaElement.webkitDecodedFrameCount ? (n = this._mediaElement.webkitDecodedFrameCount, i = this._mediaElement.webkitDroppedFrameCount) : t = !1; + return t && (e.decodedFrames = n, e.droppedFrames = i), e + } + }, { + key: "_onmseUpdateEnd", + value: function() { + if (this._config.lazyLoad && !this._config.isLive) { + for (var e = this._mediaElement.buffered, t = this._mediaElement.currentTime, n = 0, i = 0; i < e.length; i++) { + var r = e.start(i), + s = e.end(i); + if (r <= t && t < s) { + r, + n = s; + break + } + } + n >= t + this._config.lazyLoadMaxDuration && null == this._progressChecker && (d.default.v(this.TAG, "Maximum buffering duration exceeded, suspend transmuxing task"), this._suspendTransmuxer()) + } + } + }, { + key: "_onmseBufferFull", + value: function() { + d.default.v(this.TAG, "MSE SourceBuffer is full, suspend transmuxing task"), null == this._progressChecker && this._suspendTransmuxer() + } + }, { + key: "_suspendTransmuxer", + value: function() { + this._transmuxer && (this._transmuxer.pause(), null == this._progressChecker && (this._progressChecker = window.setInterval(this._checkProgressAndResume.bind(this), 1e3))) + } + }, { + key: "_checkProgressAndResume", + value: function() { + for (var e = this._mediaElement.currentTime, t = this._mediaElement.buffered, n = !1, i = 0; i < t.length; i++) { + var r = t.start(i), + s = t.end(i); + if (e >= r && e < s) { + e >= s - this._config.lazyLoadRecoverDuration && (n = !0); + break + } + } + n && (window.clearInterval(this._progressChecker), this._progressChecker = null, n && (d.default.v(this.TAG, "Continue loading from paused position"), this._transmuxer.resume())) + } + }, { + key: "_isTimepointBuffered", + value: function(e) { + for (var t = this._mediaElement.buffered, n = 0; n < t.length; n++) { + var i = t.start(n), + r = t.end(n); + if (e >= i && e < r) return !0 + } + return !1 + } + }, { + key: "_internalSeek", + value: function(e) { + var t = this._isTimepointBuffered(e), + n = !1, + i = 0; + if (e < 1 && this._mediaElement.buffered.length > 0) { + var r = this._mediaElement.buffered.start(0); + (r < 1 && e < r || f.default.safari) && (n = !0, i = f.default.safari ? .1 : r) + } + if (n) this._requestSetTime = !0, this._mediaElement.currentTime = i; + else if (t) { + if (this._alwaysSeekKeyframe) { + var s = this._msectl.getNearestKeyframe(Math.floor(1e3 * e)); + this._requestSetTime = !0, this._mediaElement.currentTime = null != s ? s.dts / 1e3 : e + } else this._requestSetTime = !0, this._mediaElement.currentTime = e; + null != this._progressChecker && this._checkProgressAndResume() + } else null != this._progressChecker && (window.clearInterval(this._progressChecker), this._progressChecker = null), this._msectl.seek(e), this._transmuxer.seek(Math.floor(1e3 * e)), this._config.accurateSeek && (this._requestSetTime = !0, this._mediaElement.currentTime = e) + } + }, { + key: "_checkAndApplyUnbufferedSeekpoint", + value: function() { + if (this._seekpointRecord) + if (this._seekpointRecord.recordTime <= this._now() - 100) { + var e = this._mediaElement.currentTime; + this._seekpointRecord = null, this._isTimepointBuffered(e) || (null != this._progressChecker && (window.clearTimeout(this._progressChecker), this._progressChecker = null), this._msectl.seek(e), this._transmuxer.seek(Math.floor(1e3 * e)), this._config.accurateSeek && (this._requestSetTime = !0, this._mediaElement.currentTime = e)) + } else window.setTimeout(this._checkAndApplyUnbufferedSeekpoint.bind(this), 50) + } + }, { + key: "_checkAndResumeStuckPlayback", + value: function(e) { + var t = this._mediaElement; + if (e || !this._receivedCanPlay || t.readyState < 2) { + var n = t.buffered; + n.length > 0 && t.currentTime < n.start(0) && (d.default.w(this.TAG, "Playback seems stuck at " + t.currentTime + ", seek to " + n.start(0)), this._requestSetTime = !0, this._mediaElement.currentTime = n.start(0), this._mediaElement.removeEventListener("progress", this.e.onvProgress)) + } else this._mediaElement.removeEventListener("progress", this.e.onvProgress) + } + }, { + key: "_onvLoadedMetadata", + value: function(e) { + null != this._pendingSeekTime && (this._mediaElement.currentTime = this._pendingSeekTime, this._pendingSeekTime = null) + } + }, { + key: "_onvSeeking", + value: function(e) { + var t = this._mediaElement.currentTime, + n = this._mediaElement.buffered; + if (this._requestSetTime) return void(this._requestSetTime = !1); + if (t < 1 && n.length > 0) { + var i = n.start(0); + if (i < 1 && t < i || f.default.safari) return this._requestSetTime = !0, void(this._mediaElement.currentTime = f.default.safari ? .1 : i) + } + if (this._isTimepointBuffered(t)) { + if (this._alwaysSeekKeyframe) { + var r = this._msectl.getNearestKeyframe(Math.floor(1e3 * t)); + null != r && (this._requestSetTime = !0, this._mediaElement.currentTime = r.dts / 1e3) + } + return void(null != this._progressChecker && this._checkProgressAndResume()) + } + this._seekpointRecord = { + seekPoint: t, + recordTime: this._now() + }, window.setTimeout(this._checkAndApplyUnbufferedSeekpoint.bind(this), 50) + } + }, { + key: "_onvCanPlay", + value: function(e) { + this._receivedCanPlay = !0, this._mediaElement.removeEventListener("canplay", this.e.onvCanPlay) + } + }, { + key: "_onvStalled", + value: function(e) { + this._checkAndResumeStuckPlayback(!0) + } + }, { + key: "_onvProgress", + value: function(e) { + this._checkAndResumeStuckPlayback() + } + }, { + key: "type", + get: function() { + return this._type + } + }, { + key: "buffered", + get: function() { + return this._mediaElement.buffered + } + }, { + key: "duration", + get: function() { + return this._mediaElement.duration + } + }, { + key: "volume", + get: function() { + return this._mediaElement.volume + }, + set: function(e) { + this._mediaElement.volume = e + } + }, { + key: "muted", + get: function() { + return this._mediaElement.muted + }, + set: function(e) { + this._mediaElement.muted = e + } + }, { + key: "currentTime", + get: function() { + return this._mediaElement ? this._mediaElement.currentTime : 0 + }, + set: function(e) { + this._mediaElement ? this._internalSeek(e) : this._pendingSeekTime = e + } + }, { + key: "mediaInfo", + get: function() { + return Object.assign({}, this._mediaInfo) + } + }, { + key: "statisticsInfo", + get: function() { + return null == this._statisticsInfo && (this._statisticsInfo = {}), this._statisticsInfo = this._fillStatisticsInfo(this._statisticsInfo), Object.assign({}, this._statisticsInfo) + } + }]), e + }(); + n.default = R + }, { + "../config.js": 5, + "../core/mse-controller.js": 9, + "../core/mse-events.js": 10, + "../core/transmuxer.js": 11, + "../core/transmuxing-events.js": 13, + "../utils/browser.js": 39, + "../utils/exception.js": 40, + "../utils/logger.js": 41, + "./player-errors.js": 34, + "./player-events.js": 35, + events: 2 + }], + 33: [function(e, t, n) { + "use strict"; + + function i(e) { + return e && e.__esModule ? e : { + default: e + } + } + + function r(e, t) { + if (!(e instanceof t)) throw new TypeError("Cannot call a class as a function") + } + Object.defineProperty(n, "__esModule", { + value: !0 + }); + var s = "function" == typeof Symbol && "symbol" == typeof Symbol.iterator ? function(e) { + return typeof e + } : function(e) { + return e && "function" == typeof Symbol && e.constructor === Symbol && e !== Symbol.prototype ? "symbol" : typeof e + }, + a = function() { + function e(e, t) { + for (var n = 0; n < t.length; n++) { + var i = t[n]; + i.enumerable = i.enumerable || !1, i.configurable = !0, "value" in i && (i.writable = !0), Object.defineProperty(e, i.key, i) + } + } + return function(t, n, i) { + return n && e(t.prototype, n), i && e(t, i), t + } + }(), + o = e("events"), + u = i(o), + l = e("./player-events.js"), + d = i(l), + h = e("../config.js"), + f = e("../utils/exception.js"), + c = function() { + function e(t, n) { + if (r(this, e), this.TAG = "NativePlayer", this._type = "NativePlayer", this._emitter = new u.default, this._config = (0, h.createDefaultConfig)(), "object" === (void 0 === n ? "undefined" : s(n)) && Object.assign(this._config, n), "flv" === t.type.toLowerCase()) throw new f.InvalidArgumentException("NativePlayer does't support flv MediaDataSource input!"); + if (t.hasOwnProperty("segments")) throw new f.InvalidArgumentException("NativePlayer(" + t.type + ") doesn't support multipart playback!"); + this.e = { + onvLoadedMetadata: this._onvLoadedMetadata.bind(this) + }, this._pendingSeekTime = null, this._statisticsReporter = null, this._mediaDataSource = t, this._mediaElement = null + } + return a(e, [{ + key: "destroy", + value: function() { + this._mediaElement && (this.unload(), this.detachMediaElement()), this.e = null, this._mediaDataSource = null, this._emitter.removeAllListeners(), this._emitter = null + } + }, { + key: "on", + value: function(e, t) { + var n = this; + e === d.default.MEDIA_INFO ? null != this._mediaElement && 0 !== this._mediaElement.readyState && Promise.resolve().then(function() { + n._emitter.emit(d.default.MEDIA_INFO, n.mediaInfo) + }) : e === d.default.STATISTICS_INFO && null != this._mediaElement && 0 !== this._mediaElement.readyState && Promise.resolve().then(function() { + n._emitter.emit(d.default.STATISTICS_INFO, n.statisticsInfo) + }), this._emitter.addListener(e, t) + } + }, { + key: "off", + value: function(e, t) { + this._emitter.removeListener(e, t) + } + }, { + key: "attachMediaElement", + value: function(e) { + if (this._mediaElement = e, e.addEventListener("loadedmetadata", this.e.onvLoadedMetadata), null != this._pendingSeekTime) try { + e.currentTime = this._pendingSeekTime, this._pendingSeekTime = null + } catch (e) {} + } + }, { + key: "detachMediaElement", + value: function() { + this._mediaElement && (this._mediaElement.src = "", this._mediaElement.removeAttribute("src"), this._mediaElement.removeEventListener("loadedmetadata", this.e.onvLoadedMetadata), this._mediaElement = null), null != this._statisticsReporter && (window.clearInterval(this._statisticsReporter), this._statisticsReporter = null) + } + }, { + key: "load", + value: function() { + if (!this._mediaElement) throw new f.IllegalStateException("HTMLMediaElement must be attached before load()!"); + this._mediaElement.src = this._mediaDataSource.url, this._mediaElement.readyState > 0 && (this._mediaElement.currentTime = 0), this._mediaElement.preload = "auto", this._mediaElement.load(), this._statisticsReporter = window.setInterval(this._reportStatisticsInfo.bind(this), this._config.statisticsInfoReportInterval) + } + }, { + key: "unload", + value: function() { + this._mediaElement && (this._mediaElement.src = "", this._mediaElement.removeAttribute("src")), null != this._statisticsReporter && (window.clearInterval(this._statisticsReporter), this._statisticsReporter = null) + } + }, { + key: "play", + value: function() { + return this._mediaElement.play() + } + }, { + key: "pause", + value: function() { + this._mediaElement.pause() + } + }, { + key: "_onvLoadedMetadata", + value: function(e) { + null != this._pendingSeekTime && (this._mediaElement.currentTime = this._pendingSeekTime, this._pendingSeekTime = null), this._emitter.emit(d.default.MEDIA_INFO, this.mediaInfo) + } + }, { + key: "_reportStatisticsInfo", + value: function() { + this._emitter.emit(d.default.STATISTICS_INFO, this.statisticsInfo) + } + }, { + key: "type", + get: function() { + return this._type + } + }, { + key: "buffered", + get: function() { + return this._mediaElement.buffered + } + }, { + key: "duration", + get: function() { + return this._mediaElement.duration + } + }, { + key: "volume", + get: function() { + return this._mediaElement.volume + }, + set: function(e) { + this._mediaElement.volume = e + } + }, { + key: "muted", + get: function() { + return this._mediaElement.muted + }, + set: function(e) { + this._mediaElement.muted = e + } + }, { + key: "currentTime", + get: function() { + return this._mediaElement ? this._mediaElement.currentTime : 0 + }, + set: function(e) { + this._mediaElement ? this._mediaElement.currentTime = e : this._pendingSeekTime = e + } + }, { + key: "mediaInfo", + get: function() { + var e = this._mediaElement instanceof HTMLAudioElement ? "audio/" : "video/", + t = { + mimeType: e + this._mediaDataSource.type + }; + return this._mediaElement && (t.duration = Math.floor(1e3 * this._mediaElement.duration), this._mediaElement instanceof HTMLVideoElement && (t.width = this._mediaElement.videoWidth, t.height = this._mediaElement.videoHeight)), t + } + }, { + key: "statisticsInfo", + get: function() { + var e = { + playerType: this._type, + url: this._mediaDataSource.url + }; + if (!(this._mediaElement instanceof HTMLVideoElement)) return e; + var t = !0, + n = 0, + i = 0; + if (this._mediaElement.getVideoPlaybackQuality) { + var r = this._mediaElement.getVideoPlaybackQuality(); + n = r.totalVideoFrames, i = r.droppedVideoFrames + } else void 0 != this._mediaElement.webkitDecodedFrameCount ? (n = this._mediaElement.webkitDecodedFrameCount, i = this._mediaElement.webkitDroppedFrameCount) : t = !1; + return t && (e.decodedFrames = n, e.droppedFrames = i), e + } + }]), e + }(); + n.default = c + }, { + "../config.js": 5, + "../utils/exception.js": 40, + "./player-events.js": 35, + events: 2 + }], + 34: [function(e, t, n) { + "use strict"; + Object.defineProperty(n, "__esModule", { + value: !0 + }), n.ErrorDetails = n.ErrorTypes = void 0; + var i = e("../io/loader.js"), + r = e("../demux/demux-errors.js"), + s = function(e) { + return e && e.__esModule ? e : { + default: e + } + }(r); + n.ErrorTypes = { + NETWORK_ERROR: "NetworkError", + MEDIA_ERROR: "MediaError", + OTHER_ERROR: "OtherError" + }, n.ErrorDetails = { + NETWORK_EXCEPTION: i.LoaderErrors.EXCEPTION, + NETWORK_STATUS_CODE_INVALID: i.LoaderErrors.HTTP_STATUS_CODE_INVALID, + NETWORK_TIMEOUT: i.LoaderErrors.CONNECTING_TIMEOUT, + NETWORK_UNRECOVERABLE_EARLY_EOF: i.LoaderErrors.UNRECOVERABLE_EARLY_EOF, + MEDIA_MSE_ERROR: "MediaMSEError", + MEDIA_FORMAT_ERROR: s.default.FORMAT_ERROR, + MEDIA_FORMAT_UNSUPPORTED: s.default.FORMAT_UNSUPPORTED, + MEDIA_CODEC_UNSUPPORTED: s.default.CODEC_UNSUPPORTED + } + }, { + "../demux/demux-errors.js": 16, + "../io/loader.js": 24 + }], + 35: [function(e, t, n) { + "use strict"; + Object.defineProperty(n, "__esModule", { + value: !0 + }); + var i = { + ERROR: "error", + LOADING_COMPLETE: "loading_complete", + RECOVERED_EARLY_EOF: "recovered_early_eof", + MEDIA_INFO: "media_info", + STATISTICS_INFO: "statistics_info" + }; + n.default = i + }, {}], + 36: [function(e, t, n) { + "use strict"; + + function i(e, t) { + if (!(e instanceof t)) throw new TypeError("Cannot call a class as a function") + } + Object.defineProperty(n, "__esModule", { + value: !0 + }); + var r = function() { + function e(e, t) { + for (var n = 0; n < t.length; n++) { + var i = t[n]; + i.enumerable = i.enumerable || !1, i.configurable = !0, "value" in i && (i.writable = !0), Object.defineProperty(e, i.key, i) + } + } + return function(t, n, i) { + return n && e(t.prototype, n), i && e(t, i), t + } + }(), + s = function() { + function e() { + i(this, e) + } + return r(e, null, [{ + key: "getSilentFrame", + value: function(e, t) { + if ("mp4a.40.2" === e) { + if (1 === t) return new Uint8Array([0, 200, 0, 128, 35, 128]); + if (2 === t) return new Uint8Array([33, 0, 73, 144, 2, 25, 0, 35, 128]); + if (3 === t) return new Uint8Array([0, 200, 0, 128, 32, 132, 1, 38, 64, 8, 100, 0, 142]); + if (4 === t) return new Uint8Array([0, 200, 0, 128, 32, 132, 1, 38, 64, 8, 100, 0, 128, 44, 128, 8, 2, 56]); + if (5 === t) return new Uint8Array([0, 200, 0, 128, 32, 132, 1, 38, 64, 8, 100, 0, 130, 48, 4, 153, 0, 33, 144, 2, 56]); + if (6 === t) return new Uint8Array([0, 200, 0, 128, 32, 132, 1, 38, 64, 8, 100, 0, 130, 48, 4, 153, 0, 33, 144, 2, 0, 178, 0, 32, 8, 224]) + } else { + if (1 === t) return new Uint8Array([1, 64, 34, 128, 163, 78, 230, 128, 186, 8, 0, 0, 0, 28, 6, 241, 193, 10, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 94]); + if (2 === t) return new Uint8Array([1, 64, 34, 128, 163, 94, 230, 128, 186, 8, 0, 0, 0, 0, 149, 0, 6, 241, 161, 10, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 94]); + if (3 === t) return new Uint8Array([1, 64, 34, 128, 163, 94, 230, 128, 186, 8, 0, 0, 0, 0, 149, 0, 6, 241, 161, 10, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 94]) + } + return null + } + }]), e + }(); + n.default = s + }, {}], + 37: [function(e, t, n) { + "use strict"; + + function i(e, t) { + if (!(e instanceof t)) throw new TypeError("Cannot call a class as a function") + } + Object.defineProperty(n, "__esModule", { + value: !0 + }); + var r = function() { + function e(e, t) { + for (var n = 0; n < t.length; n++) { + var i = t[n]; + i.enumerable = i.enumerable || !1, i.configurable = !0, "value" in i && (i.writable = !0), Object.defineProperty(e, i.key, i) + } + } + return function(t, n, i) { + return n && e(t.prototype, n), i && e(t, i), t + } + }(), + s = function() { + function e() { + i(this, e) + } + return r(e, null, [{ + key: "init", + value: function() { + e.types = { + avc1: [], + avcC: [], + btrt: [], + dinf: [], + dref: [], + esds: [], + ftyp: [], + hdlr: [], + mdat: [], + mdhd: [], + mdia: [], + mfhd: [], + minf: [], + moof: [], + moov: [], + mp4a: [], + mvex: [], + mvhd: [], + sdtp: [], + stbl: [], + stco: [], + stsc: [], + stsd: [], + stsz: [], + stts: [], + tfdt: [], + tfhd: [], + traf: [], + trak: [], + trun: [], + trex: [], + tkhd: [], + vmhd: [], + smhd: [], + ".mp3": [] + }; + for (var t in e.types) e.types.hasOwnProperty(t) && (e.types[t] = [t.charCodeAt(0), t.charCodeAt(1), t.charCodeAt(2), t.charCodeAt(3)]); + var n = e.constants = {}; + n.FTYP = new Uint8Array([105, 115, 111, 109, 0, 0, 0, 1, 105, 115, 111, 109, 97, 118, 99, 49]), n.STSD_PREFIX = new Uint8Array([0, 0, 0, 0, 0, 0, 0, 1]), n.STTS = new Uint8Array([0, 0, 0, 0, 0, 0, 0, 0]), n.STSC = n.STCO = n.STTS, n.STSZ = new Uint8Array([0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0]), n.HDLR_VIDEO = new Uint8Array([0, 0, 0, 0, 0, 0, 0, 0, 118, 105, 100, 101, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 86, 105, 100, 101, 111, 72, 97, 110, 100, 108, 101, 114, 0]), n.HDLR_AUDIO = new Uint8Array([0, 0, 0, 0, 0, 0, 0, 0, 115, 111, 117, 110, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 83, 111, 117, 110, 100, 72, 97, 110, 100, 108, 101, 114, 0]), n.DREF = new Uint8Array([0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 12, 117, 114, 108, 32, 0, 0, 0, 1]), n.SMHD = new Uint8Array([0, 0, 0, 0, 0, 0, 0, 0]), n.VMHD = new Uint8Array([0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0]) + } + }, { + key: "box", + value: function(e) { + for (var t = 8, n = null, i = Array.prototype.slice.call(arguments, 1), r = i.length, s = 0; s < r; s++) t += i[s].byteLength; + n = new Uint8Array(t), n[0] = t >>> 24 & 255, n[1] = t >>> 16 & 255, n[2] = t >>> 8 & 255, n[3] = 255 & t, n.set(e, 4); + for (var a = 8, o = 0; o < r; o++) n.set(i[o], a), a += i[o].byteLength; + return n + } + }, { + key: "generateInitSegment", + value: function(t) { + var n = e.box(e.types.ftyp, e.constants.FTYP), + i = e.moov(t), + r = new Uint8Array(n.byteLength + i.byteLength); + return r.set(n, 0), r.set(i, n.byteLength), r + } + }, { + key: "moov", + value: function(t) { + var n = e.mvhd(t.timescale, t.duration), + i = e.trak(t), + r = e.mvex(t); + return e.box(e.types.moov, n, i, r) + } + }, { + key: "mvhd", + value: function(t, n) { + return e.box(e.types.mvhd, new Uint8Array([0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, t >>> 24 & 255, t >>> 16 & 255, t >>> 8 & 255, 255 & t, n >>> 24 & 255, n >>> 16 & 255, n >>> 8 & 255, 255 & n, 0, 1, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 64, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 255, 255, 255, 255])) + } + }, { + key: "trak", + value: function(t) { + return e.box(e.types.trak, e.tkhd(t), e.mdia(t)) + } + }, { + key: "tkhd", + value: function(t) { + var n = t.id, + i = t.duration, + r = t.presentWidth, + s = t.presentHeight; + return e.box(e.types.tkhd, new Uint8Array([0, 0, 0, 7, 0, 0, 0, 0, 0, 0, 0, 0, n >>> 24 & 255, n >>> 16 & 255, n >>> 8 & 255, 255 & n, 0, 0, 0, 0, i >>> 24 & 255, i >>> 16 & 255, i >>> 8 & 255, 255 & i, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 64, 0, 0, 0, r >>> 8 & 255, 255 & r, 0, 0, s >>> 8 & 255, 255 & s, 0, 0])) + } + }, { + key: "mdia", + value: function(t) { + return e.box(e.types.mdia, e.mdhd(t), e.hdlr(t), e.minf(t)) + } + }, { + key: "mdhd", + value: function(t) { + var n = t.timescale, + i = t.duration; + return e.box(e.types.mdhd, new Uint8Array([0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, n >>> 24 & 255, n >>> 16 & 255, n >>> 8 & 255, 255 & n, i >>> 24 & 255, i >>> 16 & 255, i >>> 8 & 255, 255 & i, 85, 196, 0, 0])) + } + }, { + key: "hdlr", + value: function(t) { + var n = null; + return n = "audio" === t.type ? e.constants.HDLR_AUDIO : e.constants.HDLR_VIDEO, e.box(e.types.hdlr, n) + } + }, { + key: "minf", + value: function(t) { + var n = null; + return n = "audio" === t.type ? e.box(e.types.smhd, e.constants.SMHD) : e.box(e.types.vmhd, e.constants.VMHD), e.box(e.types.minf, n, e.dinf(), e.stbl(t)) + } + }, { + key: "dinf", + value: function() { + return e.box(e.types.dinf, e.box(e.types.dref, e.constants.DREF)) + } + }, { + key: "stbl", + value: function(t) { + return e.box(e.types.stbl, e.stsd(t), e.box(e.types.stts, e.constants.STTS), e.box(e.types.stsc, e.constants.STSC), e.box(e.types.stsz, e.constants.STSZ), e.box(e.types.stco, e.constants.STCO)) + } + }, { + key: "stsd", + value: function(t) { + return "audio" === t.type ? "mp3" === t.codec ? e.box(e.types.stsd, e.constants.STSD_PREFIX, e.mp3(t)) : e.box(e.types.stsd, e.constants.STSD_PREFIX, e.mp4a(t)) : e.box(e.types.stsd, e.constants.STSD_PREFIX, e.avc1(t)) + } + }, { + key: "mp3", + value: function(t) { + var n = t.channelCount, + i = t.audioSampleRate, + r = new Uint8Array([0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, n, 0, 16, 0, 0, 0, 0, i >>> 8 & 255, 255 & i, 0, 0]); + return e.box(e.types[".mp3"], r) + } + }, { + key: "mp4a", + value: function(t) { + var n = t.channelCount, + i = t.audioSampleRate, + r = new Uint8Array([0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, n, 0, 16, 0, 0, 0, 0, i >>> 8 & 255, 255 & i, 0, 0]); + return e.box(e.types.mp4a, r, e.esds(t)) + } + }, { + key: "esds", + value: function(t) { + var n = t.config || [], + i = n.length, + r = new Uint8Array([0, 0, 0, 0, 3, 23 + i, 0, 1, 0, 4, 15 + i, 64, 21, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5].concat([i]).concat(n).concat([6, 1, 2])); + return e.box(e.types.esds, r) + } + }, { + key: "avc1", + value: function(t) { + var n = t.avcc, + i = t.codecWidth, + r = t.codecHeight, + s = new Uint8Array([0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, i >>> 8 & 255, 255 & i, r >>> 8 & 255, 255 & r, 0, 72, 0, 0, 0, 72, 0, 0, 0, 0, 0, 0, 0, 1, 10, 120, 113, 113, 47, 102, 108, 118, 46, 106, 115, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 24, 255, 255]); + return e.box(e.types.avc1, s, e.box(e.types.avcC, n)) + } + }, { + key: "mvex", + value: function(t) { + return e.box(e.types.mvex, e.trex(t)) + } + }, { + key: "trex", + value: function(t) { + var n = t.id, + i = new Uint8Array([0, 0, 0, 0, n >>> 24 & 255, n >>> 16 & 255, n >>> 8 & 255, 255 & n, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1]); + return e.box(e.types.trex, i) + } + }, { + key: "moof", + value: function(t, n) { + return e.box(e.types.moof, e.mfhd(t.sequenceNumber), e.traf(t, n)) + } + }, { + key: "mfhd", + value: function(t) { + var n = new Uint8Array([0, 0, 0, 0, t >>> 24 & 255, t >>> 16 & 255, t >>> 8 & 255, 255 & t]); + return e.box(e.types.mfhd, n) + } + }, { + key: "traf", + value: function(t, n) { + var i = t.id, + r = e.box(e.types.tfhd, new Uint8Array([0, 0, 0, 0, i >>> 24 & 255, i >>> 16 & 255, i >>> 8 & 255, 255 & i])), + s = e.box(e.types.tfdt, new Uint8Array([0, 0, 0, 0, n >>> 24 & 255, n >>> 16 & 255, n >>> 8 & 255, 255 & n])), + a = e.sdtp(t), + o = e.trun(t, a.byteLength + 16 + 16 + 8 + 16 + 8 + 8); + return e.box(e.types.traf, r, s, o, a) + } + }, { + key: "sdtp", + value: function(t) { + for (var n = t.samples || [], i = n.length, r = new Uint8Array(4 + i), s = 0; s < i; s++) { + var a = n[s].flags; + r[s + 4] = a.isLeading << 6 | a.dependsOn << 4 | a.isDependedOn << 2 | a.hasRedundancy + } + return e.box(e.types.sdtp, r) + } + }, { + key: "trun", + value: function(t, n) { + var i = t.samples || [], + r = i.length, + s = 12 + 16 * r, + a = new Uint8Array(s); + n += 8 + s, a.set([0, 0, 15, 1, r >>> 24 & 255, r >>> 16 & 255, r >>> 8 & 255, 255 & r, n >>> 24 & 255, n >>> 16 & 255, n >>> 8 & 255, 255 & n], 0); + for (var o = 0; o < r; o++) { + var u = i[o].duration, + l = i[o].size, + d = i[o].flags, + h = i[o].cts; + a.set([u >>> 24 & 255, u >>> 16 & 255, u >>> 8 & 255, 255 & u, l >>> 24 & 255, l >>> 16 & 255, l >>> 8 & 255, 255 & l, d.isLeading << 2 | d.dependsOn, d.isDependedOn << 6 | d.hasRedundancy << 4 | d.isNonSync, 0, 0, h >>> 24 & 255, h >>> 16 & 255, h >>> 8 & 255, 255 & h], 12 + 16 * o) + } + return e.box(e.types.trun, a) + } + }, { + key: "mdat", + value: function(t) { + return e.box(e.types.mdat, t) + } + }]), e + }(); + s.init(), n.default = s + }, {}], + 38: [function(e, t, n) { + "use strict"; + + function i(e) { + return e && e.__esModule ? e : { + default: e + } + } + + function r(e, t) { + if (!(e instanceof t)) throw new TypeError("Cannot call a class as a function") + } + Object.defineProperty(n, "__esModule", { + value: !0 + }); + var s = function() { + function e(e, t) { + for (var n = 0; n < t.length; n++) { + var i = t[n]; + i.enumerable = i.enumerable || !1, i.configurable = !0, "value" in i && (i.writable = !0), Object.defineProperty(e, i.key, i) + } + } + return function(t, n, i) { + return n && e(t.prototype, n), i && e(t, i), t + } + }(), + a = e("../utils/logger.js"), + o = i(a), + u = e("./mp4-generator.js"), + l = i(u), + d = e("./aac-silent.js"), + h = i(d), + f = e("../utils/browser.js"), + c = i(f), + _ = e("../core/media-segment-info.js"), + m = e("../utils/exception.js"), + p = function() { + function e(t) { + r(this, e), this.TAG = "MP4Remuxer", this._config = t, this._isLive = !0 === t.isLive, this._dtsBase = -1, this._dtsBaseInited = !1, this._audioDtsBase = 1 / 0, this._videoDtsBase = 1 / 0, this._audioNextDts = void 0, this._videoNextDts = void 0, this._audioStashedLastSample = null, this._videoStashedLastSample = null, this._audioMeta = null, this._videoMeta = null, this._audioSegmentInfoList = new _.MediaSegmentInfoList("audio"), this._videoSegmentInfoList = new _.MediaSegmentInfoList("video"), this._onInitSegment = null, this._onMediaSegment = null, this._forceFirstIDR = !(!c.default.chrome || !(c.default.version.major < 50 || 50 === c.default.version.major && c.default.version.build < 2661)), this._fillSilentAfterSeek = c.default.msedge || c.default.msie, this._mp3UseMpegAudio = !c.default.firefox, this._fillAudioTimestampGap = this._config.fixAudioTimestampGap + } + return s(e, [{ + key: "destroy", + value: function() { + this._dtsBase = -1, this._dtsBaseInited = !1, this._audioMeta = null, this._videoMeta = null, this._audioSegmentInfoList.clear(), this._audioSegmentInfoList = null, this._videoSegmentInfoList.clear(), this._videoSegmentInfoList = null, this._onInitSegment = null, this._onMediaSegment = null + } + }, { + key: "bindDataSource", + value: function(e) { + return e.onDataAvailable = this.remux.bind(this), e.onTrackMetadata = this._onTrackMetadataReceived.bind(this), this + } + }, { + key: "insertDiscontinuity", + value: function() { + this._audioNextDts = this._videoNextDts = void 0 + } + }, { + key: "seek", + value: function(e) { + this._audioStashedLastSample = null, this._videoStashedLastSample = null, this._videoSegmentInfoList.clear(), this._audioSegmentInfoList.clear() + } + }, { + key: "remux", + value: function(e, t) { + if (!this._onMediaSegment) throw new m.IllegalStateException("MP4Remuxer: onMediaSegment callback must be specificed!"); + this._dtsBaseInited || this._calculateDtsBase(e, t), this._remuxVideo(t), this._remuxAudio(e) + } + }, { + key: "_onTrackMetadataReceived", + value: function(e, t) { + var n = null, + i = "mp4", + r = t.codec; + if ("audio" === e) this._audioMeta = t, "mp3" === t.codec && this._mp3UseMpegAudio ? (i = "mpeg", r = "", n = new Uint8Array) : n = l.default.generateInitSegment(t); + else { + if ("video" !== e) return; + this._videoMeta = t, n = l.default.generateInitSegment(t) + } + if (!this._onInitSegment) throw new m.IllegalStateException("MP4Remuxer: onInitSegment callback must be specified!"); + this._onInitSegment(e, { + type: e, + data: n.buffer, + codec: r, + container: e + "/" + i, + mediaDuration: t.duration + }) + } + }, { + key: "_calculateDtsBase", + value: function(e, t) { + this._dtsBaseInited || (e.samples && e.samples.length && (this._audioDtsBase = e.samples[0].dts), t.samples && t.samples.length && (this._videoDtsBase = t.samples[0].dts), this._dtsBase = Math.min(this._audioDtsBase, this._videoDtsBase), this._dtsBaseInited = !0) + } + }, { + key: "flushStashedSamples", + value: function() { + var e = this._videoStashedLastSample, + t = this._audioStashedLastSample, + n = { + type: "video", + id: 1, + sequenceNumber: 0, + samples: [], + length: 0 + }; + null != e && (n.samples.push(e), n.length = e.length); + var i = { + type: "audio", + id: 2, + sequenceNumber: 0, + samples: [], + length: 0 + }; + null != t && (i.samples.push(t), i.length = t.length), this._videoStashedLastSample = null, this._audioStashedLastSample = null, this._remuxVideo(n, !0), this._remuxAudio(i, !0) + } + }, { + key: "_remuxAudio", + value: function(e, t) { + if (null != this._audioMeta) { + var n = e, + i = n.samples, + r = void 0, + s = -1, + a = -1, + u = this._audioMeta.refSampleDuration, + d = "mp3" === this._audioMeta.codec && this._mp3UseMpegAudio, + f = this._dtsBaseInited && void 0 === this._audioNextDts, + m = !1; + if (i && 0 !== i.length && (1 !== i.length || t)) { + var p = 0, + v = null, + g = 0; + d ? (p = 0, g = n.length) : (p = 8, g = 8 + n.length); + var y = null; + if (i.length > 1 && (y = i.pop(), g -= y.length), null != this._audioStashedLastSample) { + var E = this._audioStashedLastSample; + this._audioStashedLastSample = null, i.unshift(E), g += E.length + } + null != y && (this._audioStashedLastSample = y); + var b = i[0].dts - this._dtsBase; + if (this._audioNextDts) r = b - this._audioNextDts; + else if (this._audioSegmentInfoList.isEmpty()) r = 0, this._fillSilentAfterSeek && !this._videoSegmentInfoList.isEmpty() && "mp3" !== this._audioMeta.originalCodec && (m = !0); + else { + var S = this._audioSegmentInfoList.getLastSampleBefore(b); + if (null != S) { + var k = b - (S.originalDts + S.duration); + k <= 3 && (k = 0); + var L = S.dts + S.duration + k; + r = b - L + } else r = 0 + } + if (m) { + var w = b - r, + R = this._videoSegmentInfoList.getLastSegmentBefore(b); + if (null != R && R.beginDts < w) { + var A = h.default.getSilentFrame(this._audioMeta.originalCodec, this._audioMeta.channelCount); + if (A) { + var O = R.beginDts, + T = w - R.beginDts; + o.default.v(this.TAG, "InsertPrefixSilentAudio: dts: " + O + ", duration: " + T), i.unshift({ + unit: A, + dts: O, + pts: O + }), g += A.byteLength + } + } else m = !1 + } + for (var C = [], I = 0; I < i.length; I++) { + var x = i[I], + M = x.unit, + D = x.dts - this._dtsBase, + B = D - r; - 1 === s && (s = B); + var j = 0; + if (I !== i.length - 1) { + j = i[I + 1].dts - this._dtsBase - r - B + } else if (null != y) { + var P = y.dts - this._dtsBase - r; + j = P - B + } else j = C.length >= 1 ? C[C.length - 1].duration : Math.floor(u); + var U = !1, + N = null; + if (j > 1.5 * u && "mp3" !== this._audioMeta.codec && this._fillAudioTimestampGap && !c.default.safari) { + U = !0; + var F = Math.abs(j - u), + G = Math.ceil(F / u), + V = B + u; + o.default.w(this.TAG, "Large audio timestamp gap detected, may cause AV sync to drift. Silent frames will be generated to avoid unsync.\ndts: " + (B + j) + " ms, expected: " + (B + Math.round(u)) + " ms, delta: " + Math.round(F) + " ms, generate: " + G + " frames"); + var z = h.default.getSilentFrame(this._audioMeta.originalCodec, this._audioMeta.channelCount); + null == z && (o.default.w(this.TAG, "Unable to generate silent frame for " + this._audioMeta.originalCodec + " with " + this._audioMeta.channelCount + " channels, repeat last frame"), z = M), N = []; + for (var H = 0; H < G; H++) { + var K = Math.round(V); + if (N.length > 0) { + var q = N[N.length - 1]; + q.duration = K - q.dts + } + var W = { + dts: K, + pts: K, + cts: 0, + unit: z, + size: z.byteLength, + duration: 0, + originalDts: D, + flags: { + isLeading: 0, + dependsOn: 1, + isDependedOn: 0, + hasRedundancy: 0 + } + }; + N.push(W), g += M.byteLength, V += u + } + var X = N[N.length - 1]; + X.duration = B + j - X.dts, j = Math.round(u) + } + C.push({ + dts: B, + pts: B, + cts: 0, + unit: x.unit, + size: x.unit.byteLength, + duration: j, + originalDts: D, + flags: { + isLeading: 0, + dependsOn: 1, + isDependedOn: 0, + hasRedundancy: 0 + } + }), U && C.push.apply(C, N) + } + d ? v = new Uint8Array(g) : (v = new Uint8Array(g), v[0] = g >>> 24 & 255, v[1] = g >>> 16 & 255, v[2] = g >>> 8 & 255, v[3] = 255 & g, v.set(l.default.types.mdat, 4)); + for (var Y = 0; Y < C.length; Y++) { + var Z = C[Y].unit; + v.set(Z, p), p += Z.byteLength + } + var Q = C[C.length - 1]; + a = Q.dts + Q.duration, this._audioNextDts = a; + var J = new _.MediaSegmentInfo; + J.beginDts = s, J.endDts = a, J.beginPts = s, J.endPts = a, J.originalBeginDts = C[0].originalDts, J.originalEndDts = Q.originalDts + Q.duration, J.firstSample = new _.SampleInfo(C[0].dts, C[0].pts, C[0].duration, C[0].originalDts, !1), J.lastSample = new _.SampleInfo(Q.dts, Q.pts, Q.duration, Q.originalDts, !1), this._isLive || this._audioSegmentInfoList.append(J), n.samples = C, n.sequenceNumber++; + var $ = null; + $ = d ? new Uint8Array : l.default.moof(n, s), n.samples = [], n.length = 0; + var ee = { + type: "audio", + data: this._mergeBoxes($, v).buffer, + sampleCount: C.length, + info: J + }; + d && f && (ee.timestampOffset = s), this._onMediaSegment("audio", ee) + } + } + } + }, { + key: "_remuxVideo", + value: function(e, t) { + if (null != this._videoMeta) { + var n = e, + i = n.samples, + r = void 0, + s = -1, + a = -1, + o = -1, + u = -1; + if (i && 0 !== i.length && (1 !== i.length || t)) { + var d = 8, + h = null, + f = 8 + e.length, + c = null; + if (i.length > 1 && (c = i.pop(), f -= c.length), null != this._videoStashedLastSample) { + var m = this._videoStashedLastSample; + this._videoStashedLastSample = null, i.unshift(m), f += m.length + } + null != c && (this._videoStashedLastSample = c); + var p = i[0].dts - this._dtsBase; + if (this._videoNextDts) r = p - this._videoNextDts; + else if (this._videoSegmentInfoList.isEmpty()) r = 0; + else { + var v = this._videoSegmentInfoList.getLastSampleBefore(p); + if (null != v) { + var g = p - (v.originalDts + v.duration); + g <= 3 && (g = 0); + var y = v.dts + v.duration + g; + r = p - y + } else r = 0 + } + for (var E = new _.MediaSegmentInfo, b = [], S = 0; S < i.length; S++) { + var k = i[S], + L = k.dts - this._dtsBase, + w = k.isKeyframe, + R = L - r, + A = k.cts, + O = R + A; - 1 === s && (s = R, o = O); + var T = 0; + if (S !== i.length - 1) { + T = i[S + 1].dts - this._dtsBase - r - R + } else if (null != c) { + var C = c.dts - this._dtsBase - r; + T = C - R + } else T = b.length >= 1 ? b[b.length - 1].duration : Math.floor(this._videoMeta.refSampleDuration); + if (w) { + var I = new _.SampleInfo(R, O, T, k.dts, !0); + I.fileposition = k.fileposition, E.appendSyncPoint(I) + } + b.push({ + dts: R, + pts: O, + cts: A, + units: k.units, + size: k.length, + isKeyframe: w, + duration: T, + originalDts: L, + flags: { + isLeading: 0, + dependsOn: w ? 2 : 1, + isDependedOn: w ? 1 : 0, + hasRedundancy: 0, + isNonSync: w ? 0 : 1 + } + }) + } + h = new Uint8Array(f), h[0] = f >>> 24 & 255, h[1] = f >>> 16 & 255, h[2] = f >>> 8 & 255, h[3] = 255 & f, h.set(l.default.types.mdat, 4); + for (var x = 0; x < b.length; x++) + for (var M = b[x].units; M.length;) { + var D = M.shift(), + B = D.data; + h.set(B, d), d += B.byteLength + } + var j = b[b.length - 1]; + if (a = j.dts + j.duration, u = j.pts + j.duration, this._videoNextDts = a, E.beginDts = s, E.endDts = a, E.beginPts = o, E.endPts = u, E.originalBeginDts = b[0].originalDts, E.originalEndDts = j.originalDts + j.duration, E.firstSample = new _.SampleInfo(b[0].dts, b[0].pts, b[0].duration, b[0].originalDts, b[0].isKeyframe), E.lastSample = new _.SampleInfo(j.dts, j.pts, j.duration, j.originalDts, j.isKeyframe), this._isLive || this._videoSegmentInfoList.append(E), n.samples = b, n.sequenceNumber++, this._forceFirstIDR) { + var P = b[0].flags; + P.dependsOn = 2, P.isNonSync = 0 + } + var U = l.default.moof(n, s); + n.samples = [], n.length = 0, this._onMediaSegment("video", { + type: "video", + data: this._mergeBoxes(U, h).buffer, + sampleCount: b.length, + info: E + }) + } + } + } + }, { + key: "_mergeBoxes", + value: function(e, t) { + var n = new Uint8Array(e.byteLength + t.byteLength); + return n.set(e, 0), n.set(t, e.byteLength), n + } + }, { + key: "onInitSegment", + get: function() { + return this._onInitSegment + }, + set: function(e) { + this._onInitSegment = e + } + }, { + key: "onMediaSegment", + get: function() { + return this._onMediaSegment + }, + set: function(e) { + this._onMediaSegment = e + } + }]), e + }(); + n.default = p + }, { + "../core/media-segment-info.js": 8, + "../utils/browser.js": 39, + "../utils/exception.js": 40, + "../utils/logger.js": 41, + "./aac-silent.js": 36, + "./mp4-generator.js": 37 + }], + 39: [function(e, t, n) { + "use strict"; + Object.defineProperty(n, "__esModule", { + value: !0 + }); + var i = {}; + ! function() { + var e = self.navigator.userAgent.toLowerCase(), + t = /(edge)\/([\w.]+)/.exec(e) || /(opr)[\/]([\w.]+)/.exec(e) || /(chrome)[ \/]([\w.]+)/.exec(e) || /(iemobile)[\/]([\w.]+)/.exec(e) || /(version)(applewebkit)[ \/]([\w.]+).*(safari)[ \/]([\w.]+)/.exec(e) || /(webkit)[ \/]([\w.]+).*(version)[ \/]([\w.]+).*(safari)[ \/]([\w.]+)/.exec(e) || /(webkit)[ \/]([\w.]+)/.exec(e) || /(opera)(?:.*version|)[ \/]([\w.]+)/.exec(e) || /(msie) ([\w.]+)/.exec(e) || e.indexOf("trident") >= 0 && /(rv)(?::| )([\w.]+)/.exec(e) || e.indexOf("compatible") < 0 && /(firefox)[ \/]([\w.]+)/.exec(e) || [], + n = /(ipad)/.exec(e) || /(ipod)/.exec(e) || /(windows phone)/.exec(e) || /(iphone)/.exec(e) || /(kindle)/.exec(e) || /(android)/.exec(e) || /(windows)/.exec(e) || /(mac)/.exec(e) || /(linux)/.exec(e) || /(cros)/.exec(e) || [], + r = { + browser: t[5] || t[3] || t[1] || "", + version: t[2] || t[4] || "0", + majorVersion: t[4] || t[2] || "0", + platform: n[0] || "" + }, + s = {}; + if (r.browser) { + s[r.browser] = !0; + var a = r.majorVersion.split("."); + s.version = { + major: parseInt(r.majorVersion, 10), + string: r.version + }, a.length > 1 && (s.version.minor = parseInt(a[1], 10)), a.length > 2 && (s.version.build = parseInt(a[2], 10)) + } + r.platform && (s[r.platform] = !0), (s.chrome || s.opr || s.safari) && (s.webkit = !0), (s.rv || s.iemobile) && (s.rv && delete s.rv, r.browser = "msie", s.msie = !0), s.edge && (delete s.edge, r.browser = "msedge", s.msedge = !0), s.opr && (r.browser = "opera", s.opera = !0), s.safari && s.android && (r.browser = "android", s.android = !0), s.name = r.browser, s.platform = r.platform; + for (var o in i) i.hasOwnProperty(o) && delete i[o]; + Object.assign(i, s) + }(), n.default = i + }, {}], + 40: [function(e, t, n) { + "use strict"; + + function i(e, t) { + if (!e) throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); + return !t || "object" != typeof t && "function" != typeof t ? e : t + } + + function r(e, t) { + if ("function" != typeof t && null !== t) throw new TypeError("Super expression must either be null or a function, not " + typeof t); + e.prototype = Object.create(t && t.prototype, { + constructor: { + value: e, + enumerable: !1, + writable: !0, + configurable: !0 + } + }), t && (Object.setPrototypeOf ? Object.setPrototypeOf(e, t) : e.__proto__ = t) + } + + function s(e, t) { + if (!(e instanceof t)) throw new TypeError("Cannot call a class as a function") + } + Object.defineProperty(n, "__esModule", { + value: !0 + }); + var a = function() { + function e(e, t) { + for (var n = 0; n < t.length; n++) { + var i = t[n]; + i.enumerable = i.enumerable || !1, i.configurable = !0, "value" in i && (i.writable = !0), Object.defineProperty(e, i.key, i) + } + } + return function(t, n, i) { + return n && e(t.prototype, n), i && e(t, i), t + } + }(), + o = n.RuntimeException = function() { + function e(t) { + s(this, e), this._message = t + } + return a(e, [{ + key: "toString", + value: function() { + return this.name + ": " + this.message + } + }, { + key: "name", + get: function() { + return "RuntimeException" + } + }, { + key: "message", + get: function() { + return this._message + } + }]), e + }(); + n.IllegalStateException = function(e) { + function t(e) { + return s(this, t), i(this, (t.__proto__ || Object.getPrototypeOf(t)).call(this, e)) + } + return r(t, e), a(t, [{ + key: "name", + get: function() { + return "IllegalStateException" + } + }]), t + }(o), n.InvalidArgumentException = function(e) { + function t(e) { + return s(this, t), i(this, (t.__proto__ || Object.getPrototypeOf(t)).call(this, e)) + } + return r(t, e), a(t, [{ + key: "name", + get: function() { + return "InvalidArgumentException" + } + }]), t + }(o), n.NotImplementedException = function(e) { + function t(e) { + return s(this, t), i(this, (t.__proto__ || Object.getPrototypeOf(t)).call(this, e)) + } + return r(t, e), a(t, [{ + key: "name", + get: function() { + return "NotImplementedException" + } + }]), t + }(o) + }, {}], + 41: [function(e, t, n) { + "use strict"; + + function i(e, t) { + if (!(e instanceof t)) throw new TypeError("Cannot call a class as a function") + } + Object.defineProperty(n, "__esModule", { + value: !0 + }); + var r = function() { + function e(e, t) { + for (var n = 0; n < t.length; n++) { + var i = t[n]; + i.enumerable = i.enumerable || !1, i.configurable = !0, "value" in i && (i.writable = !0), Object.defineProperty(e, i.key, i) + } + } + return function(t, n, i) { + return n && e(t.prototype, n), i && e(t, i), t + } + }(), + s = e("events"), + a = function(e) { + return e && e.__esModule ? e : { + default: e + } + }(s), + o = function() { + function e() { + i(this, e) + } + return r(e, null, [{ + key: "e", + value: function(t, n) { + t && !e.FORCE_GLOBAL_TAG || (t = e.GLOBAL_TAG); + var i = "[" + t + "] > " + n; + e.ENABLE_CALLBACK && e.emitter.emit("log", "error", i), e.ENABLE_ERROR && (console.error ? console.error(i) : console.warn ? console.warn(i) : console.log(i)) + } + }, { + key: "i", + value: function(t, n) { + t && !e.FORCE_GLOBAL_TAG || (t = e.GLOBAL_TAG); + var i = "[" + t + "] > " + n; + e.ENABLE_CALLBACK && e.emitter.emit("log", "info", i), e.ENABLE_INFO && (console.info ? console.info(i) : console.log(i)) + } + }, { + key: "w", + value: function(t, n) { + t && !e.FORCE_GLOBAL_TAG || (t = e.GLOBAL_TAG); + var i = "[" + t + "] > " + n; + e.ENABLE_CALLBACK && e.emitter.emit("log", "warn", i), e.ENABLE_WARN && (console.warn ? console.warn(i) : console.log(i)) + } + }, { + key: "d", + value: function(t, n) { + t && !e.FORCE_GLOBAL_TAG || (t = e.GLOBAL_TAG); + var i = "[" + t + "] > " + n; + e.ENABLE_CALLBACK && e.emitter.emit("log", "debug", i), e.ENABLE_DEBUG && (console.debug ? console.debug(i) : console.log(i)) + } + }, { + key: "v", + value: function(t, n) { + t && !e.FORCE_GLOBAL_TAG || (t = e.GLOBAL_TAG); + var i = "[" + t + "] > " + n; + e.ENABLE_CALLBACK && e.emitter.emit("log", "verbose", i), e.ENABLE_VERBOSE && console.log(i) + } + }]), e + }(); + o.GLOBAL_TAG = "flv.js", o.FORCE_GLOBAL_TAG = !1, o.ENABLE_ERROR = !0, o.ENABLE_INFO = !0, o.ENABLE_WARN = !0, o.ENABLE_DEBUG = !0, o.ENABLE_VERBOSE = !0, o.ENABLE_CALLBACK = !1, o.emitter = new a.default, n.default = o + }, { + events: 2 + }], + 42: [function(e, t, n) { + "use strict"; + + function i(e) { + return e && e.__esModule ? e : { + default: e + } + } + + function r(e, t) { + if (!(e instanceof t)) throw new TypeError("Cannot call a class as a function") + } + Object.defineProperty(n, "__esModule", { + value: !0 + }); + var s = function() { + function e(e, t) { + for (var n = 0; n < t.length; n++) { + var i = t[n]; + i.enumerable = i.enumerable || !1, i.configurable = !0, "value" in i && (i.writable = !0), Object.defineProperty(e, i.key, i) + } + } + return function(t, n, i) { + return n && e(t.prototype, n), i && e(t, i), t + } + }(), + a = e("events"), + o = i(a), + u = e("./logger.js"), + l = i(u), + d = function() { + function e() { + r(this, e) + } + return s(e, null, [{ + key: "getConfig", + value: function() { + return { + globalTag: l.default.GLOBAL_TAG, + forceGlobalTag: l.default.FORCE_GLOBAL_TAG, + enableVerbose: l.default.ENABLE_VERBOSE, + enableDebug: l.default.ENABLE_DEBUG, + enableInfo: l.default.ENABLE_INFO, + enableWarn: l.default.ENABLE_WARN, + enableError: l.default.ENABLE_ERROR, + enableCallback: l.default.ENABLE_CALLBACK + } + } + }, { + key: "applyConfig", + value: function(e) { + l.default.GLOBAL_TAG = e.globalTag, l.default.FORCE_GLOBAL_TAG = e.forceGlobalTag, l.default.ENABLE_VERBOSE = e.enableVerbose, l.default.ENABLE_DEBUG = e.enableDebug, l.default.ENABLE_INFO = e.enableInfo, l.default.ENABLE_WARN = e.enableWarn, l.default.ENABLE_ERROR = e.enableError, l.default.ENABLE_CALLBACK = e.enableCallback + } + }, { + key: "_notifyChange", + value: function() { + var t = e.emitter; + if (t.listenerCount("change") > 0) { + var n = e.getConfig(); + t.emit("change", n) + } + } + }, { + key: "registerListener", + value: function(t) { + e.emitter.addListener("change", t) + } + }, { + key: "removeListener", + value: function(t) { + e.emitter.removeListener("change", t) + } + }, { + key: "addLogListener", + value: function(t) { + l.default.emitter.addListener("log", t), l.default.emitter.listenerCount("log") > 0 && (l.default.ENABLE_CALLBACK = !0, e._notifyChange()) + } + }, { + key: "removeLogListener", + value: function(t) { + l.default.emitter.removeListener("log", t), 0 === l.default.emitter.listenerCount("log") && (l.default.ENABLE_CALLBACK = !1, e._notifyChange()) + } + }, { + key: "forceGlobalTag", + get: function() { + return l.default.FORCE_GLOBAL_TAG + }, + set: function(t) { + l.default.FORCE_GLOBAL_TAG = t, e._notifyChange() + } + }, { + key: "globalTag", + get: function() { + return l.default.GLOBAL_TAG + }, + set: function(t) { + l.default.GLOBAL_TAG = t, e._notifyChange() + } + }, { + key: "enableAll", + get: function() { + return l.default.ENABLE_VERBOSE && l.default.ENABLE_DEBUG && l.default.ENABLE_INFO && l.default.ENABLE_WARN && l.default.ENABLE_ERROR + }, + set: function(t) { + l.default.ENABLE_VERBOSE = t, l.default.ENABLE_DEBUG = t, l.default.ENABLE_INFO = t, l.default.ENABLE_WARN = t, l.default.ENABLE_ERROR = t, e._notifyChange() + } + }, { + key: "enableDebug", + get: function() { + return l.default.ENABLE_DEBUG + }, + set: function(t) { + l.default.ENABLE_DEBUG = t, e._notifyChange() + } + }, { + key: "enableVerbose", + get: function() { + return l.default.ENABLE_VERBOSE + }, + set: function(t) { + l.default.ENABLE_VERBOSE = t, e._notifyChange() + } + }, { + key: "enableInfo", + get: function() { + return l.default.ENABLE_INFO + }, + set: function(t) { + l.default.ENABLE_INFO = t, e._notifyChange() + } + }, { + key: "enableWarn", + get: function() { + return l.default.ENABLE_WARN + }, + set: function(t) { + l.default.ENABLE_WARN = t, e._notifyChange() + } + }, { + key: "enableError", + get: function() { + return l.default.ENABLE_ERROR + }, + set: function(t) { + l.default.ENABLE_ERROR = t, e._notifyChange() + } + }]), e + }(); + d.emitter = new o.default, n.default = d + }, { + "./logger.js": 41, + events: 2 + }], + 43: [function(e, t, n) { + "use strict"; + + function i(e, t) { + if (!(e instanceof t)) throw new TypeError("Cannot call a class as a function") + } + Object.defineProperty(n, "__esModule", { + value: !0 + }); + var r = function() { + function e(e, t) { + for (var n = 0; n < t.length; n++) { + var i = t[n]; + i.enumerable = i.enumerable || !1, i.configurable = !0, "value" in i && (i.writable = !0), Object.defineProperty(e, i.key, i) + } + } + return function(t, n, i) { + return n && e(t.prototype, n), i && e(t, i), t + } + }(), + s = function() { + function t() { + i(this, t) + } + return r(t, null, [{ + key: "install", + value: function() { + Object.setPrototypeOf = Object.setPrototypeOf || function(e, t) { + return e.__proto__ = t, e + }, Object.assign = Object.assign || function(e) { + if (void 0 === e || null === e) throw new TypeError("Cannot convert undefined or null to object"); + for (var t = Object(e), n = 1; n < arguments.length; n++) { + var i = arguments[n]; + if (void 0 !== i && null !== i) + for (var r in i) i.hasOwnProperty(r) && (t[r] = i[r]) + } + return t + }, "function" != typeof self.Promise && e("es6-promise").polyfill() + } + }]), t + }(); + s.install(), n.default = s + }, { + "es6-promise": 1 + }], + 44: [function(e, t, n) { + "use strict"; + + function i(e, t, n) { + var i = e; + if (t + n < i.length) { + for (; n--;) + if (128 != (192 & i[++t])) return !1; + return !0 + } + return !1 + } + + function r(e) { + for (var t = [], n = e, r = 0, s = e.length; r < s;) + if (n[r] < 128) t.push(String.fromCharCode(n[r])), ++r; + else { + if (n[r] < 192); + else if (n[r] < 224) { + if (i(n, r, 1)) { + var a = (31 & n[r]) << 6 | 63 & n[r + 1]; + if (a >= 128) { + t.push(String.fromCharCode(65535 & a)), r += 2; + continue + } + } + } else if (n[r] < 240) { + if (i(n, r, 2)) { + var o = (15 & n[r]) << 12 | (63 & n[r + 1]) << 6 | 63 & n[r + 2]; + if (o >= 2048 && 55296 != (63488 & o)) { + t.push(String.fromCharCode(65535 & o)), r += 3; + continue + } + } + } else if (n[r] < 248 && i(n, r, 3)) { + var u = (7 & n[r]) << 18 | (63 & n[r + 1]) << 12 | (63 & n[r + 2]) << 6 | 63 & n[r + 3]; + if (u > 65536 && u < 1114112) { + u -= 65536, t.push(String.fromCharCode(u >>> 10 | 55296)), t.push(String.fromCharCode(1023 & u | 56320)), r += 4; + continue + } + } + t.push(String.fromCharCode(65533)), ++r + } return t.join("") + } + Object.defineProperty(n, "__esModule", { + value: !0 + }), n.default = r + }, {}] + }, {}, [21])(21) +}); +//# sourceMappingURL=flv.min.js.map \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/focusmanager.js b/dashboard-ui/bower_components/emby-webcomponents/focusmanager.js index 5b56f684d7..c80ca2e3a3 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/focusmanager.js +++ b/dashboard-ui/bower_components/emby-webcomponents/focusmanager.js @@ -1 +1,256 @@ -define(["dom"],function(dom){"use strict";function pushScope(elem){scopes.push(elem)}function popScope(elem){scopes.length&&(scopes.length-=1)}function autoFocus(view,defaultToFirst,findAutoFocusElement){var element;return!1!==findAutoFocusElement&&(element=view.querySelector("*[autofocus]"))?(focus(element),element):!1!==defaultToFirst&&(element=getFocusableElements(view,1,"noautofocus")[0])?(focus(element),element):null}function focus(element){try{element.focus({preventScroll:!0})}catch(err){console.log("Error in focusManager.autoFocus: "+err)}}function isFocusable(elem){return-1!==focusableTagNames.indexOf(elem.tagName)||!(!elem.classList||!elem.classList.contains("focusable"))}function normalizeFocusable(elem,originalElement){if(elem){var tagName=elem.tagName;tagName&&"HTML"!==tagName&&"BODY"!==tagName||(elem=originalElement)}return elem}function focusableParent(elem){for(var originalElement=elem;!isFocusable(elem);){var parent=elem.parentNode;if(!parent)return normalizeFocusable(elem,originalElement);elem=parent}return normalizeFocusable(elem,originalElement)}function isCurrentlyFocusableInternal(elem){return null!==elem.offsetParent}function isCurrentlyFocusable(elem){if(elem.disabled)return!1;if("-1"===elem.getAttribute("tabindex"))return!1;if("INPUT"===elem.tagName){var type=elem.type;if("range"===type)return!1;if("file"===type)return!1}return isCurrentlyFocusableInternal(elem)}function getDefaultScope(){return scopes[0]||document.body}function getFocusableElements(parent,limit,excludeClass){for(var elems=(parent||getDefaultScope()).querySelectorAll(focusableQuery),focusableElements=[],i=0,length=elems.length;i=limit)))break}return focusableElements}function isFocusContainer(elem,direction){if(-1!==focusableContainerTagNames.indexOf(elem.tagName))return!0;var classList=elem.classList;if(classList.contains("focuscontainer"))return!0;if(0===direction){if(classList.contains("focuscontainer-x"))return!0;if(classList.contains("focuscontainer-left"))return!0}else if(1===direction){if(classList.contains("focuscontainer-x"))return!0;if(classList.contains("focuscontainer-right"))return!0}else if(2===direction){if(classList.contains("focuscontainer-y"))return!0}else if(3===direction){if(classList.contains("focuscontainer-y"))return!0;if(classList.contains("focuscontainer-down"))return!0}return!1}function getFocusContainer(elem,direction){for(;!isFocusContainer(elem,direction);)if(!(elem=elem.parentNode))return getDefaultScope();return elem}function getOffset(elem){var box;if(box=elem.getBoundingClientRect?elem.getBoundingClientRect():{top:0,left:0,width:0,height:0},null===box.right){box={top:box.top,left:box.left,width:box.width,height:box.height},box.right=box.left+box.width,box.bottom=box.top+box.height}return box}function nav(activeElement,direction,container,focusableElements){if(activeElement=activeElement||document.activeElement,activeElement&&(activeElement=focusableParent(activeElement)),container=container||(activeElement?getFocusContainer(activeElement,direction):getDefaultScope()),!activeElement)return void autoFocus(container,!0,!1);for(var nearestElement,focusableContainer=dom.parentWithClass(activeElement,"focusable"),rect=getOffset(activeElement),point1x=parseFloat(rect.left)||0,point1y=parseFloat(rect.top)||0,point2x=parseFloat(point1x+rect.width-1)||point1x,point2y=parseFloat(point1y+rect.height-1)||point1y,sourceMidX=(Math.min,Math.max,rect.left+rect.width/2),sourceMidY=rect.top+rect.height/2,focusable=focusableElements||container.querySelectorAll(focusableQuery),minDistance=1/0,i=0,length=focusable.length;i=rect.left)continue;if(elementRect.right===rect.right)continue;break;case 1:if(elementRect.right<=rect.right)continue;if(elementRect.left===rect.left)continue;break;case 2:if(elementRect.top>=rect.top)continue;if(elementRect.bottom>=rect.bottom)continue;break;case 3:if(elementRect.bottom<=rect.bottom)continue;if(elementRect.top<=rect.top)continue}var distX,distY,x=elementRect.left,y=elementRect.top,x2=x+elementRect.width-1,y2=y+elementRect.height-1,intersectX=intersects(point1x,point2x,x,x2),intersectY=intersects(point1y,point2y,y,y2),midX=elementRect.left+elementRect.width/2,midY=elementRect.top+elementRect.height/2;switch(direction){case 0:distX=Math.abs(point1x-Math.min(point1x,x2)),distY=intersectY?0:Math.abs(sourceMidY-midY);break;case 1:distX=Math.abs(point2x-Math.max(point2x,x)),distY=intersectY?0:Math.abs(sourceMidY-midY);break;case 2:distY=Math.abs(point1y-Math.min(point1y,y2)),distX=intersectX?0:Math.abs(sourceMidX-midX);break;case 3:distY=Math.abs(point2y-Math.max(point2y,y)),distX=intersectX?0:Math.abs(sourceMidX-midX)}var dist=Math.sqrt(distX*distX+distY*distY);dist=a1&&b1<=a2||b2>=a1&&b2<=a2}function intersects(a1,a2,b1,b2){return intersectsInternal(a1,a2,b1,b2)||intersectsInternal(b1,b2,a1,a2)}function sendText(text){document.activeElement.value=text}function focusFirst(container,focusableSelector){for(var elems=container.querySelectorAll(focusableSelector),i=0,length=elems.length;i= limit))) break + } + return focusableElements + } + + function isFocusContainer(elem, direction) { + if (-1 !== focusableContainerTagNames.indexOf(elem.tagName)) return !0; + var classList = elem.classList; + if (classList.contains("focuscontainer")) return !0; + if (0 === direction) { + if (classList.contains("focuscontainer-x")) return !0; + if (classList.contains("focuscontainer-left")) return !0 + } else if (1 === direction) { + if (classList.contains("focuscontainer-x")) return !0; + if (classList.contains("focuscontainer-right")) return !0 + } else if (2 === direction) { + if (classList.contains("focuscontainer-y")) return !0 + } else if (3 === direction) { + if (classList.contains("focuscontainer-y")) return !0; + if (classList.contains("focuscontainer-down")) return !0 + } + return !1 + } + + function getFocusContainer(elem, direction) { + for (; !isFocusContainer(elem, direction);) + if (!(elem = elem.parentNode)) return getDefaultScope(); + return elem + } + + function getOffset(elem) { + var box; + if (box = elem.getBoundingClientRect ? elem.getBoundingClientRect() : { + top: 0, + left: 0, + width: 0, + height: 0 + }, null === box.right) { + box = { + top: box.top, + left: box.left, + width: box.width, + height: box.height + }, box.right = box.left + box.width, box.bottom = box.top + box.height + } + return box + } + + function nav(activeElement, direction, container, focusableElements) { + if (activeElement = activeElement || document.activeElement, activeElement && (activeElement = focusableParent(activeElement)), container = container || (activeElement ? getFocusContainer(activeElement, direction) : getDefaultScope()), !activeElement) return void autoFocus(container, !0, !1); + for (var nearestElement, focusableContainer = dom.parentWithClass(activeElement, "focusable"), rect = getOffset(activeElement), point1x = parseFloat(rect.left) || 0, point1y = parseFloat(rect.top) || 0, point2x = parseFloat(point1x + rect.width - 1) || point1x, point2y = parseFloat(point1y + rect.height - 1) || point1y, sourceMidX = (Math.min, Math.max, rect.left + rect.width / 2), sourceMidY = rect.top + rect.height / 2, focusable = focusableElements || container.querySelectorAll(focusableQuery), minDistance = 1 / 0, i = 0, length = focusable.length; i < length; i++) { + var curr = focusable[i]; + if (curr !== activeElement && curr !== focusableContainer) { + var elementRect = getOffset(curr); + if (elementRect.width || elementRect.height) { + switch (direction) { + case 0: + if (elementRect.left >= rect.left) continue; + if (elementRect.right === rect.right) continue; + break; + case 1: + if (elementRect.right <= rect.right) continue; + if (elementRect.left === rect.left) continue; + break; + case 2: + if (elementRect.top >= rect.top) continue; + if (elementRect.bottom >= rect.bottom) continue; + break; + case 3: + if (elementRect.bottom <= rect.bottom) continue; + if (elementRect.top <= rect.top) continue + } + var distX, distY, x = elementRect.left, + y = elementRect.top, + x2 = x + elementRect.width - 1, + y2 = y + elementRect.height - 1, + intersectX = intersects(point1x, point2x, x, x2), + intersectY = intersects(point1y, point2y, y, y2), + midX = elementRect.left + elementRect.width / 2, + midY = elementRect.top + elementRect.height / 2; + switch (direction) { + case 0: + distX = Math.abs(point1x - Math.min(point1x, x2)), distY = intersectY ? 0 : Math.abs(sourceMidY - midY); + break; + case 1: + distX = Math.abs(point2x - Math.max(point2x, x)), distY = intersectY ? 0 : Math.abs(sourceMidY - midY); + break; + case 2: + distY = Math.abs(point1y - Math.min(point1y, y2)), distX = intersectX ? 0 : Math.abs(sourceMidX - midX); + break; + case 3: + distY = Math.abs(point2y - Math.max(point2y, y)), distX = intersectX ? 0 : Math.abs(sourceMidX - midX) + } + var dist = Math.sqrt(distX * distX + distY * distY); + dist < minDistance && (nearestElement = curr, minDistance = dist) + } + } + } + if (nearestElement) { + if (activeElement) { + var nearestElementFocusableParent = dom.parentWithClass(nearestElement, "focusable"); + nearestElementFocusableParent && nearestElementFocusableParent !== nearestElement && focusableContainer !== nearestElementFocusableParent && (nearestElement = nearestElementFocusableParent) + } + focus(nearestElement) + } + } + + function intersectsInternal(a1, a2, b1, b2) { + return b1 >= a1 && b1 <= a2 || b2 >= a1 && b2 <= a2 + } + + function intersects(a1, a2, b1, b2) { + return intersectsInternal(a1, a2, b1, b2) || intersectsInternal(b1, b2, a1, a2) + } + + function sendText(text) { + document.activeElement.value = text + } + + function focusFirst(container, focusableSelector) { + for (var elems = container.querySelectorAll(focusableSelector), i = 0, length = elems.length; i < length; i++) { + var elem = elems[i]; + if (isCurrentlyFocusableInternal(elem)) { + focus(elem); + break + } + } + } + + function focusLast(container, focusableSelector) { + for (var elems = [].slice.call(container.querySelectorAll(focusableSelector), 0).reverse(), i = 0, length = elems.length; i < length; i++) { + var elem = elems[i]; + if (isCurrentlyFocusableInternal(elem)) { + focus(elem); + break + } + } + } + + function moveFocus(sourceElement, container, focusableSelector, offset) { + var i, length, elem, elems = container.querySelectorAll(focusableSelector), + list = []; + for (i = 0, length = elems.length; i < length; i++) elem = elems[i], isCurrentlyFocusableInternal(elem) && list.push(elem); + var currentIndex = -1; + for (i = 0, length = list.length; i < length; i++) + if (elem = list[i], sourceElement === elem || elem.contains(sourceElement)) { + currentIndex = i; + break + } if (-1 !== currentIndex) { + var newIndex = currentIndex + offset; + newIndex = Math.max(0, newIndex), newIndex = Math.min(newIndex, list.length - 1); + var newElem = list[newIndex]; + newElem && focus(newElem) + } + } + var scopes = [], + focusableTagNames = ["INPUT", "TEXTAREA", "SELECT", "BUTTON", "A"], + focusableContainerTagNames = ["BODY", "DIALOG"], + focusableQuery = focusableTagNames.map(function(t) { + return "INPUT" === t && (t += ':not([type="range"]):not([type="file"])'), t + ':not([tabindex="-1"]):not(:disabled)' + }).join(",") + ",.focusable"; + return { + autoFocus: autoFocus, + focus: focus, + focusableParent: focusableParent, + getFocusableElements: getFocusableElements, + moveLeft: function(sourceElement, options) { + nav(sourceElement, 0, options ? options.container : null, options ? options.focusableElements : null) + }, + moveRight: function(sourceElement, options) { + nav(sourceElement, 1, options ? options.container : null, options ? options.focusableElements : null) + }, + moveUp: function(sourceElement, options) { + nav(sourceElement, 2, options ? options.container : null, options ? options.focusableElements : null) + }, + moveDown: function(sourceElement, options) { + nav(sourceElement, 3, options ? options.container : null, options ? options.focusableElements : null) + }, + sendText: sendText, + isCurrentlyFocusable: isCurrentlyFocusable, + pushScope: pushScope, + popScope: popScope, + focusFirst: focusFirst, + focusLast: focusLast, + moveFocus: moveFocus + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/fullscreen/fullscreen-dc.js b/dashboard-ui/bower_components/emby-webcomponents/fullscreen/fullscreen-dc.js index 21499f4000..a7f6ff1e13 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/fullscreen/fullscreen-dc.js +++ b/dashboard-ui/bower_components/emby-webcomponents/fullscreen/fullscreen-dc.js @@ -1 +1,12 @@ -define(["dom","fullscreenManager"],function(dom,fullscreenManager){"use strict";function isTargetValid(target){return!dom.parentWithTag(target,["BUTTON","INPUT","TEXTAREA"])}dom.addEventListener(window,"dblclick",function(e){isTargetValid(e.target)&&(fullscreenManager.isFullScreen()?fullscreenManager.exitFullscreen():fullscreenManager.requestFullscreen())},{passive:!0})}); \ No newline at end of file +define(["dom", "fullscreenManager"], function(dom, fullscreenManager) { + "use strict"; + + function isTargetValid(target) { + return !dom.parentWithTag(target, ["BUTTON", "INPUT", "TEXTAREA"]) + } + dom.addEventListener(window, "dblclick", function(e) { + isTargetValid(e.target) && (fullscreenManager.isFullScreen() ? fullscreenManager.exitFullscreen() : fullscreenManager.requestFullscreen()) + }, { + passive: !0 + }) +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/fullscreen/fullscreenmanager.js b/dashboard-ui/bower_components/emby-webcomponents/fullscreen/fullscreenmanager.js index 78ab06d37a..adfee87460 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/fullscreen/fullscreenmanager.js +++ b/dashboard-ui/bower_components/emby-webcomponents/fullscreen/fullscreenmanager.js @@ -1 +1,24 @@ -define(["events","dom"],function(events,dom){"use strict";function fullscreenManager(){}function onFullScreenChange(){events.trigger(manager,"fullscreenchange")}fullscreenManager.prototype.requestFullscreen=function(element){return element=element||document.documentElement,element.requestFullscreen?void element.requestFullscreen():element.mozRequestFullScreen?void element.mozRequestFullScreen():element.webkitRequestFullscreen?void element.webkitRequestFullscreen():element.msRequestFullscreen?void element.msRequestFullscreen():("VIDEO"!==element.tagName&&(element=document.querySelector("video")||element),void(element.webkitEnterFullscreen&&element.webkitEnterFullscreen()))},fullscreenManager.prototype.exitFullscreen=function(){document.exitFullscreen?document.exitFullscreen():document.mozCancelFullScreen?document.mozCancelFullScreen():document.webkitExitFullscreen?document.webkitExitFullscreen():document.webkitCancelFullscreen?document.webkitCancelFullscreen():document.msExitFullscreen&&document.msExitFullscreen()},fullscreenManager.prototype.isFullScreen=function(){return!!(document.fullscreen||document.mozFullScreen||document.webkitIsFullScreen||document.msFullscreenElement)};var manager=new fullscreenManager;return dom.addEventListener(document,"fullscreenchange",onFullScreenChange,{passive:!0}),dom.addEventListener(document,"webkitfullscreenchange",onFullScreenChange,{passive:!0}),dom.addEventListener(document,"mozfullscreenchange",onFullScreenChange,{passive:!0}),manager}); \ No newline at end of file +define(["events", "dom"], function(events, dom) { + "use strict"; + + function fullscreenManager() {} + + function onFullScreenChange() { + events.trigger(manager, "fullscreenchange") + } + fullscreenManager.prototype.requestFullscreen = function(element) { + return element = element || document.documentElement, element.requestFullscreen ? void element.requestFullscreen() : element.mozRequestFullScreen ? void element.mozRequestFullScreen() : element.webkitRequestFullscreen ? void element.webkitRequestFullscreen() : element.msRequestFullscreen ? void element.msRequestFullscreen() : ("VIDEO" !== element.tagName && (element = document.querySelector("video") || element), void(element.webkitEnterFullscreen && element.webkitEnterFullscreen())) + }, fullscreenManager.prototype.exitFullscreen = function() { + document.exitFullscreen ? document.exitFullscreen() : document.mozCancelFullScreen ? document.mozCancelFullScreen() : document.webkitExitFullscreen ? document.webkitExitFullscreen() : document.webkitCancelFullscreen ? document.webkitCancelFullscreen() : document.msExitFullscreen && document.msExitFullscreen() + }, fullscreenManager.prototype.isFullScreen = function() { + return !!(document.fullscreen || document.mozFullScreen || document.webkitIsFullScreen || document.msFullscreenElement) + }; + var manager = new fullscreenManager; + return dom.addEventListener(document, "fullscreenchange", onFullScreenChange, { + passive: !0 + }), dom.addEventListener(document, "webkitfullscreenchange", onFullScreenChange, { + passive: !0 + }), dom.addEventListener(document, "mozfullscreenchange", onFullScreenChange, { + passive: !0 + }), manager +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/globalize.js b/dashboard-ui/bower_components/emby-webcomponents/globalize.js index f193fd7d2e..0390860404 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/globalize.js +++ b/dashboard-ui/bower_components/emby-webcomponents/globalize.js @@ -1 +1,135 @@ -define(["connectionManager","userSettings","events"],function(connectionManager,userSettings,events){"use strict";function getCurrentLocale(){return currentCulture}function getCurrentDateTimeLocale(){return currentDateTimeCulture}function getDefaultLanguage(){var culture=document.documentElement.getAttribute("data-culture");return culture||(navigator.language?navigator.language:navigator.userLanguage?navigator.userLanguage:navigator.languages&&navigator.languages.length?navigator.languages[0]:"en-us")}function updateCurrentCulture(){var culture;try{culture=userSettings.language()}catch(err){}culture=culture||getDefaultLanguage(),currentCulture=normalizeLocaleName(culture);var dateTimeCulture;try{dateTimeCulture=userSettings.dateTimeLocale()}catch(err){}currentDateTimeCulture=dateTimeCulture?normalizeLocaleName(dateTimeCulture):currentCulture,ensureTranslations(currentCulture)}function ensureTranslations(culture){for(var i in allTranslations)ensureTranslation(allTranslations[i],culture)}function ensureTranslation(translationInfo,culture){return translationInfo.dictionaries[culture]?Promise.resolve():loadTranslation(translationInfo.translations,culture).then(function(dictionary){translationInfo.dictionaries[culture]=dictionary})}function normalizeLocaleName(culture){culture=culture.replace("_","-");var parts=culture.split("-");2===parts.length&&parts[0].toLowerCase()===parts[1].toLowerCase()&&(culture=parts[0].toLowerCase());var lower=culture.toLowerCase();return"ca-es"===lower?"ca":"sv-se"===lower?"sv":lower}function getDictionary(module){module||(module=defaultModule());var translations=allTranslations[module];return translations?translations.dictionaries[getCurrentLocale()]:{}}function register(options){allTranslations[options.name]={translations:options.strings||options.translations,dictionaries:{}}}function loadStrings(options){var locale=getCurrentLocale();return"string"==typeof options?ensureTranslation(allTranslations[options],locale):(register(options),ensureTranslation(allTranslations[options.name],locale))}function loadTranslation(translations,lang){lang=normalizeLocaleName(lang);var filtered=translations.filter(function(t){return normalizeLocaleName(t.lang)===lang});return filtered.length||(filtered=translations.filter(function(t){return"en-us"===normalizeLocaleName(t.lang)})),new Promise(function(resolve,reject){if(!filtered.length)return void resolve();var url=filtered[0].path;url+=-1===url.indexOf("?")?"?":"&",url+="v="+cacheParam;var xhr=new XMLHttpRequest;xhr.open("GET",url,!0),xhr.onload=function(e){resolve(this.status<400?JSON.parse(this.response):{})},xhr.onerror=function(){resolve({})},xhr.send()})}function translateKey(key){var module,parts=key.split("#");return parts.length>1&&(module=parts[0],key=parts[1]),translateKeyFromModule(key,module)}function translateKeyFromModule(key,module){var dictionary=getDictionary(module);return dictionary?dictionary[key]||key:key}function replaceAll(str,find,replace){return str.split(find).join(replace)}function translate(key){for(var val=translateKey(key),i=1;i 1 && (module = parts[0], key = parts[1]), translateKeyFromModule(key, module) + } + + function translateKeyFromModule(key, module) { + var dictionary = getDictionary(module); + return dictionary ? dictionary[key] || key : key + } + + function replaceAll(str, find, replace) { + return str.split(find).join(replace) + } + + function translate(key) { + for (var val = translateKey(key), i = 1; i < arguments.length; i++) val = replaceAll(val, "{" + (i - 1) + "}", arguments[i]); + return val + } + + function translateHtml(html, module) { + if (module || (module = defaultModule()), !module) throw new Error("module cannot be null or empty"); + var startIndex = html.indexOf("${"); + if (-1 === startIndex) return html; + startIndex += 2; + var endIndex = html.indexOf("}", startIndex); + if (-1 === endIndex) return html; + var key = html.substring(startIndex, endIndex), + val = translateKeyFromModule(key, module); + return html = html.replace("${" + key + "}", val), translateHtml(html, module) + } + + function defaultModule(val) { + return val && (_defaultModule = val), _defaultModule + } + var currentCulture, currentDateTimeCulture, _defaultModule, allTranslations = {}, + cacheParam = (new Date).getTime(); + return updateCurrentCulture(), events.on(connectionManager, "localusersignedin", updateCurrentCulture), events.on(userSettings, "change", function(e, name) { + "language" !== name && "datetimelocale" !== name || updateCurrentCulture() + }), { + getString: translate, + translate: translate, + translateDocument: translateHtml, + translateHtml: translateHtml, + loadStrings: loadStrings, + defaultModule: defaultModule, + getCurrentLocale: getCurrentLocale, + getCurrentDateTimeLocale: getCurrentDateTimeLocale, + register: register + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/guide/guide-settings.js b/dashboard-ui/bower_components/emby-webcomponents/guide/guide-settings.js index 4efd780b8c..624a582574 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/guide/guide-settings.js +++ b/dashboard-ui/bower_components/emby-webcomponents/guide/guide-settings.js @@ -1 +1,71 @@ -define(["dialogHelper","globalize","userSettings","layoutManager","connectionManager","require","loading","scrollHelper","emby-checkbox","emby-radio","css!./../formdialog","material-icons"],function(dialogHelper,globalize,userSettings,layoutManager,connectionManager,require,loading,scrollHelper){"use strict";function saveCategories(context,options){for(var categories=[],chkCategorys=context.querySelectorAll(".chkCategory"),i=0,length=chkCategorys.length;i=4&&categories.push("series"),categories.push("all"),options.categories=categories}function loadCategories(context,options){for(var selectedCategories=options.categories||[],chkCategorys=context.querySelectorAll(".chkCategory"),i=0,length=chkCategorys.length;i= 4 && categories.push("series"), categories.push("all"), options.categories = categories + } + + function loadCategories(context, options) { + for (var selectedCategories = options.categories || [], chkCategorys = context.querySelectorAll(".chkCategory"), i = 0, length = chkCategorys.length; i < length; i++) { + var type = chkCategorys[i].getAttribute("data-type"); + chkCategorys[i].checked = !selectedCategories.length || -1 !== selectedCategories.indexOf(type) + } + } + + function save(context) { + var i, length, chkIndicators = context.querySelectorAll(".chkIndicator"); + for (i = 0, length = chkIndicators.length; i < length; i++) { + var type = chkIndicators[i].getAttribute("data-type"); + userSettings.set("guide-indicator-" + type, chkIndicators[i].checked) + } + userSettings.set("guide-colorcodedbackgrounds", context.querySelector(".chkColorCodedBackgrounds").checked), userSettings.set("livetv-favoritechannelsattop", context.querySelector(".chkFavoriteChannelsAtTop").checked); + var sortBys = context.querySelectorAll(".chkSortOrder"); + for (i = 0, length = sortBys.length; i < length; i++) + if (sortBys[i].checked) { + userSettings.set("livetv-channelorder", sortBys[i].value); + break + } + } + + function load(context) { + var i, length, chkIndicators = context.querySelectorAll(".chkIndicator"); + for (i = 0, length = chkIndicators.length; i < length; i++) { + var type = chkIndicators[i].getAttribute("data-type"); + "true" === chkIndicators[i].getAttribute("data-default") ? chkIndicators[i].checked = "false" !== userSettings.get("guide-indicator-" + type) : chkIndicators[i].checked = "true" === userSettings.get("guide-indicator-" + type) + } + context.querySelector(".chkColorCodedBackgrounds").checked = "true" === userSettings.get("guide-colorcodedbackgrounds"), context.querySelector(".chkFavoriteChannelsAtTop").checked = "false" !== userSettings.get("livetv-favoritechannelsattop"); + var sortByValue = userSettings.get("livetv-channelorder") || "Number", + sortBys = context.querySelectorAll(".chkSortOrder"); + for (i = 0, length = sortBys.length; i < length; i++) sortBys[i].checked = sortBys[i].value === sortByValue + } + + function showEditor(options) { + return new Promise(function(resolve, reject) { + var settingsChanged = !1; + require(["text!./guide-settings.template.html"], function(template) { + var dialogOptions = { + removeOnClose: !0, + scrollY: !1 + }; + layoutManager.tv ? dialogOptions.size = "fullscreen" : dialogOptions.size = "small"; + var dlg = dialogHelper.createDialog(dialogOptions); + dlg.classList.add("formDialog"); + var html = ""; + html += globalize.translateDocument(template, "sharedcomponents"), dlg.innerHTML = html, dlg.addEventListener("change", function() { + settingsChanged = !0 + }), dlg.addEventListener("close", function() { + layoutManager.tv && scrollHelper.centerFocus.off(dlg.querySelector(".formDialogContent"), !1), save(dlg), saveCategories(dlg, options), settingsChanged ? resolve() : reject() + }), dlg.querySelector(".btnCancel").addEventListener("click", function() { + dialogHelper.close(dlg) + }), layoutManager.tv && scrollHelper.centerFocus.on(dlg.querySelector(".formDialogContent"), !1), load(dlg), loadCategories(dlg, options), dialogHelper.open(dlg) + }) + }) + } + return { + show: showEditor + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/guide/guide.js b/dashboard-ui/bower_components/emby-webcomponents/guide/guide.js index 7c66d74943..87fcaf8218 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/guide/guide.js +++ b/dashboard-ui/bower_components/emby-webcomponents/guide/guide.js @@ -1 +1,517 @@ -define(["require","inputManager","browser","globalize","connectionManager","scrollHelper","serverNotifications","loading","datetime","focusManager","playbackManager","userSettings","imageLoader","events","layoutManager","itemShortcuts","dom","css!./guide.css","programStyles","material-icons","scrollStyles","emby-button","paper-icon-button-light","emby-tabs","emby-scroller","flexStyles","registerElement"],function(require,inputManager,browser,globalize,connectionManager,scrollHelper,serverNotifications,loading,datetime,focusManager,playbackManager,userSettings,imageLoader,events,layoutManager,itemShortcuts,dom){"use strict";function showViewSettings(instance){require(["guide-settings-dialog"],function(guideSettingsDialog){guideSettingsDialog.show(instance.categoryOptions).then(function(){instance.refresh()})})}function updateProgramCellOnScroll(cell,scrollPct){var left=cell.posLeft;left||(left=parseFloat(cell.style.left.replace("%","")),cell.posLeft=left);var width=cell.posWidth;width||(width=parseFloat(cell.style.width.replace("%","")),cell.posWidth=width);var right=left+width,newPct=Math.max(Math.min(scrollPct,right),left),offset=newPct-left,pctOfWidth=offset/width*100,guideProgramName=cell.guideProgramName;guideProgramName||(guideProgramName=cell.querySelector(".guideProgramName"),cell.guideProgramName=guideProgramName);var caret=cell.caret;caret||(caret=cell.querySelector(".guide-programNameCaret"),cell.caret=caret),guideProgramName&&(pctOfWidth>0&&pctOfWidth<=100?(guideProgramName.style.transform="translateX("+pctOfWidth+"%)",caret.classList.remove("hide")):(guideProgramName.style.transform="none",caret.classList.add("hide")))}function updateProgramCellsOnScroll(programGrid,programCells){isUpdatingProgramCellScroll||(isUpdatingProgramCellScroll=!0,requestAnimationFrame(function(){for(var scrollLeft=programGrid.scrollLeft,scrollPct=scrollLeft?scrollLeft/programGrid.scrollWidth*100:0,i=0,length=programCells.length;i=startDate&&now=0?date.setHours(date.getHours(),cellCurationMinutes,0,0):date.setHours(date.getHours(),0,0,0),date}function showLoading(){loading.show()}function hideLoading(){loading.hide()}function reloadGuide(context,newStartDate,scrollToTimeMs,focusToTimeMs,startTimeOfDayMs,focusProgramOnRender){var apiClient=connectionManager.getApiClient(options.serverId),channelQuery={StartIndex:0,EnableFavoriteSorting:"false"!==userSettings.get("livetv-favoritechannelsattop")};channelQuery.UserId=apiClient.getCurrentUserId();currentChannelLimit=500,showLoading(),channelQuery.StartIndex=currentStartIndex,channelQuery.Limit=500,channelQuery.AddCurrentProgram=!1,channelQuery.EnableUserData=!1,channelQuery.EnableImageTypes="Primary";var categories=self.categoryOptions.categories||[],displayMovieContent=!categories.length||-1!==categories.indexOf("movies"),displaySportsContent=!categories.length||-1!==categories.indexOf("sports"),displayNewsContent=!categories.length||-1!==categories.indexOf("news"),displayKidsContent=!categories.length||-1!==categories.indexOf("kids"),displaySeriesContent=!categories.length||-1!==categories.indexOf("series");displayMovieContent&&displaySportsContent&&displayNewsContent&&displayKidsContent?(channelQuery.IsMovie=null,channelQuery.IsSports=null,channelQuery.IsKids=null,channelQuery.IsNews=null,channelQuery.IsSeries=null):(displayNewsContent&&(channelQuery.IsNews=!0),displaySportsContent&&(channelQuery.IsSports=!0),displayKidsContent&&(channelQuery.IsKids=!0),displayMovieContent&&(channelQuery.IsMovie=!0),displaySeriesContent&&(channelQuery.IsSeries=!0)),"DatePlayed"===userSettings.get("livetv-channelorder")?(channelQuery.SortBy="DatePlayed",channelQuery.SortOrder="Descending"):(channelQuery.SortBy=null,channelQuery.SortOrder=null);var date=newStartDate;date=new Date(date.getTime()+1e3);var nextDay=new Date(date.getTime()+msPerDay-2e3),allowIndicators=dom.getWindowSize().innerWidth>=600,renderOptions={showHdIcon:allowIndicators&&"true"===userSettings.get("guide-indicator-hd"),showLiveIndicator:allowIndicators&&"false"!==userSettings.get("guide-indicator-live"),showPremiereIndicator:allowIndicators&&"false"!==userSettings.get("guide-indicator-premiere"),showNewIndicator:allowIndicators&&"false"!==userSettings.get("guide-indicator-new"),showRepeatIndicator:allowIndicators&&"true"===userSettings.get("guide-indicator-repeat"),showEpisodeTitle:!layoutManager.tv};apiClient.getLiveTvChannels(channelQuery).then(function(channelsResult){var btnPreviousPage=context.querySelector(".btnPreviousPage"),btnNextPage=context.querySelector(".btnNextPage");channelsResult.TotalRecordCount>500?(context.querySelector(".guideOptions").classList.remove("hide"),btnPreviousPage.classList.remove("hide"),btnNextPage.classList.remove("hide"),channelQuery.StartIndex?context.querySelector(".btnPreviousPage").disabled=!1:context.querySelector(".btnPreviousPage").disabled=!0,channelQuery.StartIndex+500",startDate.setTime(startDate.getTime()+cellDurationMs);return html}function parseDates(program){if(!program.StartDateLocal)try{program.StartDateLocal=datetime.parseISO8601Date(program.StartDate,{toLocal:!0})}catch(err){}if(!program.EndDateLocal)try{program.EndDateLocal=datetime.parseISO8601Date(program.EndDate,{toLocal:!0})}catch(err){}return null}function getTimerIndicator(item){var status;if("SeriesTimer"===item.Type)return'';if(item.TimerId||item.SeriesTimerId)status=item.Status||"Cancelled";else{if("Timer"!==item.Type)return"";status=item.Status}return item.SeriesTimerId?"Cancelled"!==status?'':'':''}function getChannelProgramsHtml(context,date,channel,programs,options,listInfo){var html="",startMs=date.getTime(),endMs=startMs+msPerDay-1;html+='
';for(var programsFound,clickAction=layoutManager.tv?"link":"programdialog",categories=self.categoryOptions.categories||[],displayMovieContent=!categories.length||-1!==categories.indexOf("movies"),displaySportsContent=!categories.length||-1!==categories.indexOf("sports"),displayNewsContent=!categories.length||-1!==categories.indexOf("news"),displayKidsContent=!categories.length||-1!==categories.indexOf("kids"),displaySeriesContent=!categories.length||-1!==categories.indexOf("series"),enableColorCodedBackgrounds="true"===userSettings.get("guide-colorcodedbackgrounds"),now=(new Date).getTime(),i=listInfo.startIndex,length=programs.length;iendMs)break;items[program.Id]=program;var renderStartMs=Math.max(startDateLocalMs,startMs),startPercent=(startDateLocalMs-startMs)/msPerDay;startPercent*=100,startPercent=Math.max(startPercent,0);var renderEndMs=Math.min(endDateLocalMs,endMs),endPercent=(renderEndMs-renderStartMs)/msPerDay;endPercent*=100;var cssClass="programCell itemAction",accentCssClass=null,displayInnerContent=!0;program.IsKids?(displayInnerContent=displayKidsContent,accentCssClass="kids"):program.IsSports?(displayInnerContent=displaySportsContent,accentCssClass="sports"):program.IsNews?(displayInnerContent=displayNewsContent,accentCssClass="news"):program.IsMovie?(displayInnerContent=displayMovieContent,accentCssClass="movie"):displayInnerContent=program.IsSeries?displaySeriesContent:displayMovieContent&&displayNewsContent&&displaySportsContent&&displayKidsContent&&displaySeriesContent,displayInnerContent&&enableColorCodedBackgrounds&&accentCssClass&&(cssClass+=" programCell-"+accentCssClass),now>=startDateLocalMs&&now=2?' is="emby-programcell"':"")+' data-action="'+clickAction+'"'+timerAttributes+' data-channelid="'+program.ChannelId+'" data-id="'+program.Id+'" data-serverid="'+program.ServerId+'" data-startdate="'+program.StartDate+'" data-enddate="'+program.EndDate+'" data-type="'+program.Type+'" class="'+cssClass+'" style="left:'+startPercent+"%;width:"+endPercent+'%;">',displayInnerContent){html+='
',html+='
',html+='
'+program.Name;var indicatorHtml=null;program.IsLive&&options.showLiveIndicator?indicatorHtml=''+globalize.translate("sharedcomponents#Live")+"":program.IsPremiere&&options.showPremiereIndicator?indicatorHtml=''+globalize.translate("sharedcomponents#Premiere")+"":program.IsSeries&&!program.IsRepeat&&options.showNewIndicator?indicatorHtml=''+globalize.translate("sharedcomponents#AttributeNew")+"":program.IsSeries&&program.IsRepeat&&options.showRepeatIndicator&&(indicatorHtml=''+globalize.translate("sharedcomponents#Repeat")+""),html+=indicatorHtml||"",program.EpisodeTitle&&options.showEpisodeTitle&&(html+='
',program.EpisodeTitle&&options.showEpisodeTitle&&(html+=''+program.EpisodeTitle+""),html+="
"),html+="
",program.IsHD&&options.showHdIcon&&(layoutManager.tv?html+='
HD
':html+='
HD
'),html+=getTimerIndicator(program),html+="
"}html+=""}}else if(programsFound)break}return html+="
"}function renderChannelHeaders(context,channels,apiClient){for(var html="",i=0,length=channels.length;i',hasChannelImage){html+='
'}channel.ChannelNumber&&(html+='

'+channel.ChannelNumber+"

"),!hasChannelImage&&channel.Name&&(html+='
'+channel.Name+"
"),html+=""}var channelList=context.querySelector(".channelsContainer");channelList.innerHTML=html,imageLoader.lazyChildren(channelList)}function renderPrograms(context,date,channels,programs,options){for(var listInfo={startIndex:0},html=[],i=0,length=channels.length;i=pct||left+width>=pct)break;programCell=programCell.nextSibling}programCell?focusManager.focus(programCell):focusManager.autoFocus(autoFocusParent,!0)}}function nativeScrollTo(container,pos,horizontal){container.scrollTo?horizontal?container.scrollTo(pos,0):container.scrollTo(0,pos):horizontal?container.scrollLeft=Math.round(pos):container.scrollTop=Math.round(pos)}function onProgramGridScroll(context,elem,timeslotHeaders){if((new Date).getTime()-lastHeaderScroll>=1e3){lastGridScroll=(new Date).getTime();var scrollLeft=elem.scrollLeft;scrollXPct=100*scrollLeft/elem.scrollWidth,nativeScrollTo(timeslotHeaders,scrollLeft,!0)}updateProgramCellsOnScroll(elem,programCells)}function onTimeslotHeadersScroll(context,elem){(new Date).getTime()-lastGridScroll>=1e3&&(lastHeaderScroll=(new Date).getTime(),nativeScrollTo(programGrid,elem.scrollLeft,!0))}function changeDate(page,date,scrollToTimeMs,focusToTimeMs,startTimeOfDayMs,focusProgramOnRender){var newStartDate=normalizeDateToTimeslot(date);currentDate=newStartDate,reloadGuide(page,newStartDate,scrollToTimeMs,focusToTimeMs,startTimeOfDayMs,focusProgramOnRender)}function getDateTabText(date,isActive,tabIndex){var cssClass=isActive?"emby-tab-button guide-date-tab-button emby-tab-button-active":"emby-tab-button guide-date-tab-button",html='"}function setDateRange(page,guideInfo){var today=new Date,nowHours=today.getHours();today.setHours(nowHours,0,0,0);var start=datetime.parseISO8601Date(guideInfo.StartDate,{toLocal:!0}),end=datetime.parseISO8601Date(guideInfo.EndDate,{toLocal:!0});start.setHours(nowHours,0,0,0),end.setHours(0,0,0,0),start.getTime()>=end.getTime()&&end.setDate(start.getDate()+1),start=new Date(Math.max(today,start));var dateTabsHtml="",tabIndex=0,date=new Date;currentDate&&date.setTime(currentDate.getTime()),date.setHours(nowHours,0,0,0);var startTimeOfDayMs=60*start.getHours()*60*1e3;for(startTimeOfDayMs+=60*start.getMinutes()*1e3;start<=end;){dateTabsHtml+=getDateTabText(start,date.getDate()===start.getDate()&&date.getMonth()===start.getMonth()&&date.getFullYear()===start.getFullYear(),tabIndex),start.setDate(start.getDate()+1),start.setHours(0,0,0,0),tabIndex++}page.querySelector(".emby-tabs-slider").innerHTML=dateTabsHtml,page.querySelector(".guideDateTabs").refresh();var newDate=new Date,newDateHours=newDate.getHours(),scrollToTimeMs=60*newDateHours*60*1e3,minutes=newDate.getMinutes();minutes>=30&&(scrollToTimeMs+=18e5),changeDate(page,date,scrollToTimeMs,60*(60*newDateHours+minutes)*1e3,startTimeOfDayMs,layoutManager.tv)}function reloadPage(page){showLoading(),connectionManager.getApiClient(options.serverId).getLiveTvGuideInfo().then(function(guideInfo){setDateRange(page,guideInfo)})}function getChannelProgramsFocusableElements(container){for(var elements=container.querySelectorAll(".programCell"),list=[],currentScrollXPct=scrollXPct+1,i=0,length=elements.length;i=currentScrollXPct&&list.push(elem)}return list}function onInputCommand(e){var container,channelPrograms,focusableElements,newRow,target=e.target,programCell=dom.parentWithClass(target,"programCell");switch(e.detail.command){case"up":programCell?(container=programGrid,channelPrograms=dom.parentWithClass(programCell,"channelPrograms"),newRow=channelPrograms.previousSibling,newRow?(focusableElements=getChannelProgramsFocusableElements(newRow),focusableElements.length?container=newRow:focusableElements=null):container=null):container=null,lastFocusDirection=e.detail.command,focusManager.moveUp(target,{container:container,focusableElements:focusableElements});break;case"down":programCell?(container=programGrid,channelPrograms=dom.parentWithClass(programCell,"channelPrograms"),newRow=channelPrograms.nextSibling,newRow?(focusableElements=getChannelProgramsFocusableElements(newRow),focusableElements.length?container=newRow:focusableElements=null):container=null):container=null,lastFocusDirection=e.detail.command,focusManager.moveDown(target,{container:container,focusableElements:focusableElements});break;case"left":container=programCell?dom.parentWithClass(programCell,"channelPrograms"):null,container&&!programCell.previousSibling&&(container=null),lastFocusDirection=e.detail.command,focusManager.moveLeft(target,{container:container}),!0;break;case"right":container=programCell?dom.parentWithClass(programCell,"channelPrograms"):null,lastFocusDirection=e.detail.command,focusManager.moveRight(target,{container:container}),!0;break;default:return}e.preventDefault(),e.stopPropagation()}function onScrollerFocus(e){var target=e.target,programCell=dom.parentWithClass(target,"programCell");if(programCell){var focused=target,id=focused.getAttribute("data-id"),item=items[id];item&&events.trigger(self,"focus",[{item:item}])}if("left"===lastFocusDirection)programCell&&scrollHelper.toStart(programGrid,programCell,!0,!0);else if("right"===lastFocusDirection)programCell&&scrollHelper.toCenter(programGrid,programCell,!0,!0);else if("up"===lastFocusDirection||"down"===lastFocusDirection){var verticalScroller=dom.parentWithClass(target,"guideVerticalScroller");if(verticalScroller){var focusedElement=programCell||dom.parentWithTag(target,"BUTTON");verticalScroller.toCenter(focusedElement,!0)}}}function setScrollEvents(view,enabled){if(layoutManager.tv){var guideVerticalScroller=view.querySelector(".guideVerticalScroller");enabled?inputManager.on(guideVerticalScroller,onInputCommand):inputManager.off(guideVerticalScroller,onInputCommand)}}function onTimerCreated(e,apiClient,data){for(var programId=data.ProgramId,newTimerId=data.Id,cells=options.element.querySelectorAll('.programCell[data-id="'+programId+'"]'),i=0,length=cells.length;i'),newTimerId&&cell.setAttribute("data-timerid",newTimerId)}}function onSeriesTimerCreated(e,apiClient,data){}function onTimerCancelled(e,apiClient,data){for(var id=data.Id,cells=options.element.querySelectorAll('.programCell[data-timerid="'+id+'"]'),i=0,length=cells.length;i 0 && pctOfWidth <= 100 ? (guideProgramName.style.transform = "translateX(" + pctOfWidth + "%)", caret.classList.remove("hide")) : (guideProgramName.style.transform = "none", caret.classList.add("hide"))) + } + + function updateProgramCellsOnScroll(programGrid, programCells) { + isUpdatingProgramCellScroll || (isUpdatingProgramCellScroll = !0, requestAnimationFrame(function() { + for (var scrollLeft = programGrid.scrollLeft, scrollPct = scrollLeft ? scrollLeft / programGrid.scrollWidth * 100 : 0, i = 0, length = programCells.length; i < length; i++) updateProgramCellOnScroll(programCells[i], scrollPct); + isUpdatingProgramCellScroll = !1 + })) + } + + function onProgramGridClick(e) { + if (layoutManager.tv) { + var programCell = dom.parentWithClass(e.target, "programCell"); + if (programCell) { + var startDate = programCell.getAttribute("data-startdate"), + endDate = programCell.getAttribute("data-enddate"); + startDate = datetime.parseISO8601Date(startDate, { + toLocal: !0 + }).getTime(), endDate = datetime.parseISO8601Date(endDate, { + toLocal: !0 + }).getTime(); + var now = (new Date).getTime(); + if (now >= startDate && now < endDate) { + var channelId = programCell.getAttribute("data-channelid"), + serverId = programCell.getAttribute("data-serverid"); + e.preventDefault(), e.stopPropagation(), playbackManager.play({ + ids: [channelId], + serverId: serverId + }) + } + } + } + } + + function Guide(options) { + function restartAutoRefresh() { + stopAutoRefresh(); + autoRefreshInterval = setInterval(function() { + self.refresh() + }, 9e5) + } + + function stopAutoRefresh() { + autoRefreshInterval && (clearInterval(autoRefreshInterval), autoRefreshInterval = null) + } + + function normalizeDateToTimeslot(date) { + return date.getMinutes() - cellCurationMinutes >= 0 ? date.setHours(date.getHours(), cellCurationMinutes, 0, 0) : date.setHours(date.getHours(), 0, 0, 0), date + } + + function showLoading() { + loading.show() + } + + function hideLoading() { + loading.hide() + } + + function reloadGuide(context, newStartDate, scrollToTimeMs, focusToTimeMs, startTimeOfDayMs, focusProgramOnRender) { + var apiClient = connectionManager.getApiClient(options.serverId), + channelQuery = { + StartIndex: 0, + EnableFavoriteSorting: "false" !== userSettings.get("livetv-favoritechannelsattop") + }; + channelQuery.UserId = apiClient.getCurrentUserId(); + currentChannelLimit = 500, showLoading(), channelQuery.StartIndex = currentStartIndex, channelQuery.Limit = 500, channelQuery.AddCurrentProgram = !1, channelQuery.EnableUserData = !1, channelQuery.EnableImageTypes = "Primary"; + var categories = self.categoryOptions.categories || [], + displayMovieContent = !categories.length || -1 !== categories.indexOf("movies"), + displaySportsContent = !categories.length || -1 !== categories.indexOf("sports"), + displayNewsContent = !categories.length || -1 !== categories.indexOf("news"), + displayKidsContent = !categories.length || -1 !== categories.indexOf("kids"), + displaySeriesContent = !categories.length || -1 !== categories.indexOf("series"); + displayMovieContent && displaySportsContent && displayNewsContent && displayKidsContent ? (channelQuery.IsMovie = null, channelQuery.IsSports = null, channelQuery.IsKids = null, channelQuery.IsNews = null, channelQuery.IsSeries = null) : (displayNewsContent && (channelQuery.IsNews = !0), displaySportsContent && (channelQuery.IsSports = !0), displayKidsContent && (channelQuery.IsKids = !0), displayMovieContent && (channelQuery.IsMovie = !0), displaySeriesContent && (channelQuery.IsSeries = !0)), "DatePlayed" === userSettings.get("livetv-channelorder") ? (channelQuery.SortBy = "DatePlayed", channelQuery.SortOrder = "Descending") : (channelQuery.SortBy = null, channelQuery.SortOrder = null); + var date = newStartDate; + date = new Date(date.getTime() + 1e3); + var nextDay = new Date(date.getTime() + msPerDay - 2e3), + allowIndicators = dom.getWindowSize().innerWidth >= 600, + renderOptions = { + showHdIcon: allowIndicators && "true" === userSettings.get("guide-indicator-hd"), + showLiveIndicator: allowIndicators && "false" !== userSettings.get("guide-indicator-live"), + showPremiereIndicator: allowIndicators && "false" !== userSettings.get("guide-indicator-premiere"), + showNewIndicator: allowIndicators && "false" !== userSettings.get("guide-indicator-new"), + showRepeatIndicator: allowIndicators && "true" === userSettings.get("guide-indicator-repeat"), + showEpisodeTitle: !layoutManager.tv + }; + apiClient.getLiveTvChannels(channelQuery).then(function(channelsResult) { + var btnPreviousPage = context.querySelector(".btnPreviousPage"), + btnNextPage = context.querySelector(".btnNextPage"); + channelsResult.TotalRecordCount > 500 ? (context.querySelector(".guideOptions").classList.remove("hide"), btnPreviousPage.classList.remove("hide"), btnNextPage.classList.remove("hide"), channelQuery.StartIndex ? context.querySelector(".btnPreviousPage").disabled = !1 : context.querySelector(".btnPreviousPage").disabled = !0, channelQuery.StartIndex + 500 < channelsResult.TotalRecordCount ? btnNextPage.disabled = !1 : btnNextPage.disabled = !0) : context.querySelector(".guideOptions").classList.add("hide"); + var programFields = [], + programQuery = { + UserId: apiClient.getCurrentUserId(), + MaxStartDate: nextDay.toISOString(), + MinEndDate: date.toISOString(), + channelIds: channelsResult.Items.map(function(c) { + return c.Id + }).join(","), + ImageTypeLimit: 1, + EnableImages: !1, + SortBy: "StartDate", + EnableTotalRecordCount: !1, + EnableUserData: !1 + }; + renderOptions.showHdIcon && programFields.push("IsHD"), programFields.length && (programQuery.Fields = programFields.join("")), apiClient.getLiveTvPrograms(programQuery).then(function(programsResult) { + renderGuide(context, date, channelsResult.Items, programsResult.Items, renderOptions, apiClient, scrollToTimeMs, focusToTimeMs, startTimeOfDayMs, focusProgramOnRender), hideLoading() + }) + }) + } + + function getDisplayTime(date) { + if ("string" === (typeof date).toString().toLowerCase()) try { + date = datetime.parseISO8601Date(date, { + toLocal: !0 + }) + } catch (err) { + return date + } + return datetime.getDisplayTime(date).toLowerCase() + } + + function getTimeslotHeadersHtml(startDate, endDateTime) { + var html = ""; + for (startDate = new Date(startDate.getTime()), html += '
'; startDate.getTime() < endDateTime;) html += '
', html += getDisplayTime(startDate), html += "
", startDate.setTime(startDate.getTime() + cellDurationMs); + return html + } + + function parseDates(program) { + if (!program.StartDateLocal) try { + program.StartDateLocal = datetime.parseISO8601Date(program.StartDate, { + toLocal: !0 + }) + } catch (err) {} + if (!program.EndDateLocal) try { + program.EndDateLocal = datetime.parseISO8601Date(program.EndDate, { + toLocal: !0 + }) + } catch (err) {} + return null + } + + function getTimerIndicator(item) { + var status; + if ("SeriesTimer" === item.Type) return ''; + if (item.TimerId || item.SeriesTimerId) status = item.Status || "Cancelled"; + else { + if ("Timer" !== item.Type) return ""; + status = item.Status + } + return item.SeriesTimerId ? "Cancelled" !== status ? '' : '' : '' + } + + function getChannelProgramsHtml(context, date, channel, programs, options, listInfo) { + var html = "", + startMs = date.getTime(), + endMs = startMs + msPerDay - 1; + html += '
'; + for (var programsFound, clickAction = layoutManager.tv ? "link" : "programdialog", categories = self.categoryOptions.categories || [], displayMovieContent = !categories.length || -1 !== categories.indexOf("movies"), displaySportsContent = !categories.length || -1 !== categories.indexOf("sports"), displayNewsContent = !categories.length || -1 !== categories.indexOf("news"), displayKidsContent = !categories.length || -1 !== categories.indexOf("kids"), displaySeriesContent = !categories.length || -1 !== categories.indexOf("series"), enableColorCodedBackgrounds = "true" === userSettings.get("guide-colorcodedbackgrounds"), now = (new Date).getTime(), i = listInfo.startIndex, length = programs.length; i < length; i++) { + var program = programs[i]; + if (program.ChannelId === channel.Id) { + programsFound = !0, listInfo.startIndex++, parseDates(program); + var startDateLocalMs = program.StartDateLocal.getTime(), + endDateLocalMs = program.EndDateLocal.getTime(); + if (!(endDateLocalMs < startMs)) { + if (startDateLocalMs > endMs) break; + items[program.Id] = program; + var renderStartMs = Math.max(startDateLocalMs, startMs), + startPercent = (startDateLocalMs - startMs) / msPerDay; + startPercent *= 100, startPercent = Math.max(startPercent, 0); + var renderEndMs = Math.min(endDateLocalMs, endMs), + endPercent = (renderEndMs - renderStartMs) / msPerDay; + endPercent *= 100; + var cssClass = "programCell itemAction", + accentCssClass = null, + displayInnerContent = !0; + program.IsKids ? (displayInnerContent = displayKidsContent, accentCssClass = "kids") : program.IsSports ? (displayInnerContent = displaySportsContent, accentCssClass = "sports") : program.IsNews ? (displayInnerContent = displayNewsContent, accentCssClass = "news") : program.IsMovie ? (displayInnerContent = displayMovieContent, accentCssClass = "movie") : displayInnerContent = program.IsSeries ? displaySeriesContent : displayMovieContent && displayNewsContent && displaySportsContent && displayKidsContent && displaySeriesContent, displayInnerContent && enableColorCodedBackgrounds && accentCssClass && (cssClass += " programCell-" + accentCssClass), now >= startDateLocalMs && now < endDateLocalMs && (cssClass += " programCell-active"); + var timerAttributes = ""; + program.TimerId && (timerAttributes += ' data-timerid="' + program.TimerId + '"'), program.SeriesTimerId && (timerAttributes += ' data-seriestimerid="' + program.SeriesTimerId + '"'); + if (html += "= 2 ? ' is="emby-programcell"' : "") + ' data-action="' + clickAction + '"' + timerAttributes + ' data-channelid="' + program.ChannelId + '" data-id="' + program.Id + '" data-serverid="' + program.ServerId + '" data-startdate="' + program.StartDate + '" data-enddate="' + program.EndDate + '" data-type="' + program.Type + '" class="' + cssClass + '" style="left:' + startPercent + "%;width:" + endPercent + '%;">', displayInnerContent) { + html += '
', html += '
', html += '
' + program.Name; + var indicatorHtml = null; + program.IsLive && options.showLiveIndicator ? indicatorHtml = '' + globalize.translate("sharedcomponents#Live") + "" : program.IsPremiere && options.showPremiereIndicator ? indicatorHtml = '' + globalize.translate("sharedcomponents#Premiere") + "" : program.IsSeries && !program.IsRepeat && options.showNewIndicator ? indicatorHtml = '' + globalize.translate("sharedcomponents#AttributeNew") + "" : program.IsSeries && program.IsRepeat && options.showRepeatIndicator && (indicatorHtml = '' + globalize.translate("sharedcomponents#Repeat") + ""), html += indicatorHtml || "", program.EpisodeTitle && options.showEpisodeTitle && (html += '
', program.EpisodeTitle && options.showEpisodeTitle && (html += '' + program.EpisodeTitle + ""), html += "
"), html += "
", program.IsHD && options.showHdIcon && (layoutManager.tv ? html += '
HD
' : html += '
HD
'), html += getTimerIndicator(program), html += "
" + } + html += "" + } + } else if (programsFound) break + } + return html += "
" + } + + function renderChannelHeaders(context, channels, apiClient) { + for (var html = "", i = 0, length = channels.length; i < length; i++) { + var channel = channels[i], + hasChannelImage = channel.ImageTags.Primary, + cssClass = "guide-channelHeaderCell itemAction"; + layoutManager.tv && (cssClass += " guide-channelHeaderCell-tv"); + var title = []; + if (channel.ChannelNumber && title.push(channel.ChannelNumber), channel.Name && title.push(channel.Name), html += '" + } + var channelList = context.querySelector(".channelsContainer"); + channelList.innerHTML = html, imageLoader.lazyChildren(channelList) + } + + function renderPrograms(context, date, channels, programs, options) { + for (var listInfo = { + startIndex: 0 + }, html = [], i = 0, length = channels.length; i < length; i++) html.push(getChannelProgramsHtml(context, date, channels[i], programs, options, listInfo)); + programGrid.innerHTML = html.join(""), programCells = programGrid.querySelectorAll("[is=emby-programcell]"), updateProgramCellsOnScroll(programGrid, programCells) + } + + function getProgramSortOrder(program, channels) { + for (var channelId = program.ChannelId, channelIndex = -1, i = 0, length = channels.length; i < length; i++) + if (channelId === channels[i].Id) { + channelIndex = i; + break + } return 1e7 * channelIndex + datetime.parseISO8601Date(program.StartDate, { + toLocal: !0 + }).getTime() / 6e4 + } + + function renderGuide(context, date, channels, programs, renderOptions, apiClient, scrollToTimeMs, focusToTimeMs, startTimeOfDayMs, focusProgramOnRender) { + programs.sort(function(a, b) { + return getProgramSortOrder(a, channels) - getProgramSortOrder(b, channels) + }); + var activeElement = document.activeElement, + itemId = activeElement && activeElement.getAttribute ? activeElement.getAttribute("data-id") : null, + channelRowId = null; + activeElement && (channelRowId = dom.parentWithClass(activeElement, "channelPrograms"), channelRowId = channelRowId && channelRowId.getAttribute ? channelRowId.getAttribute("data-channelid") : null), renderChannelHeaders(context, channels, apiClient); + var startDate = date, + endDate = new Date(startDate.getTime() + msPerDay); + context.querySelector(".timeslotHeaders").innerHTML = getTimeslotHeadersHtml(startDate, endDate), items = {}, renderPrograms(context, date, channels, programs, renderOptions), focusProgramOnRender && focusProgram(context, itemId, channelRowId, focusToTimeMs, startTimeOfDayMs), scrollProgramGridToTimeMs(context, scrollToTimeMs, startTimeOfDayMs) + } + + function scrollProgramGridToTimeMs(context, scrollToTimeMs, startTimeOfDayMs) { + scrollToTimeMs -= startTimeOfDayMs; + var pct = scrollToTimeMs / msPerDay; + programGrid.scrollTop = 0; + var scrollPos = pct * programGrid.scrollWidth; + nativeScrollTo(programGrid, scrollPos, !0) + } + + function focusProgram(context, itemId, channelRowId, focusToTimeMs, startTimeOfDayMs) { + var focusElem; + if (itemId && (focusElem = context.querySelector('[data-id="' + itemId + '"]')), focusElem) focusManager.focus(focusElem); + else { + var autoFocusParent; + channelRowId && (autoFocusParent = context.querySelector('[data-channelid="' + channelRowId + '"]')), autoFocusParent || (autoFocusParent = programGrid), focusToTimeMs -= startTimeOfDayMs; + for (var pct = focusToTimeMs / msPerDay * 100, programCell = autoFocusParent.querySelector(".programCell"); programCell;) { + var left = (programCell.style.left || "").replace("%", ""); + left = left ? parseFloat(left) : 0; + var width = (programCell.style.width || "").replace("%", ""); + if (width = width ? parseFloat(width) : 0, left >= pct || left + width >= pct) break; + programCell = programCell.nextSibling + } + programCell ? focusManager.focus(programCell) : focusManager.autoFocus(autoFocusParent, !0) + } + } + + function nativeScrollTo(container, pos, horizontal) { + container.scrollTo ? horizontal ? container.scrollTo(pos, 0) : container.scrollTo(0, pos) : horizontal ? container.scrollLeft = Math.round(pos) : container.scrollTop = Math.round(pos) + } + + function onProgramGridScroll(context, elem, timeslotHeaders) { + if ((new Date).getTime() - lastHeaderScroll >= 1e3) { + lastGridScroll = (new Date).getTime(); + var scrollLeft = elem.scrollLeft; + scrollXPct = 100 * scrollLeft / elem.scrollWidth, nativeScrollTo(timeslotHeaders, scrollLeft, !0) + } + updateProgramCellsOnScroll(elem, programCells) + } + + function onTimeslotHeadersScroll(context, elem) { + (new Date).getTime() - lastGridScroll >= 1e3 && (lastHeaderScroll = (new Date).getTime(), nativeScrollTo(programGrid, elem.scrollLeft, !0)) + } + + function changeDate(page, date, scrollToTimeMs, focusToTimeMs, startTimeOfDayMs, focusProgramOnRender) { + var newStartDate = normalizeDateToTimeslot(date); + currentDate = newStartDate, reloadGuide(page, newStartDate, scrollToTimeMs, focusToTimeMs, startTimeOfDayMs, focusProgramOnRender) + } + + function getDateTabText(date, isActive, tabIndex) { + var cssClass = isActive ? "emby-tab-button guide-date-tab-button emby-tab-button-active" : "emby-tab-button guide-date-tab-button", + html = '" + } + + function setDateRange(page, guideInfo) { + var today = new Date, + nowHours = today.getHours(); + today.setHours(nowHours, 0, 0, 0); + var start = datetime.parseISO8601Date(guideInfo.StartDate, { + toLocal: !0 + }), + end = datetime.parseISO8601Date(guideInfo.EndDate, { + toLocal: !0 + }); + start.setHours(nowHours, 0, 0, 0), end.setHours(0, 0, 0, 0), start.getTime() >= end.getTime() && end.setDate(start.getDate() + 1), start = new Date(Math.max(today, start)); + var dateTabsHtml = "", + tabIndex = 0, + date = new Date; + currentDate && date.setTime(currentDate.getTime()), date.setHours(nowHours, 0, 0, 0); + var startTimeOfDayMs = 60 * start.getHours() * 60 * 1e3; + for (startTimeOfDayMs += 60 * start.getMinutes() * 1e3; start <= end;) { + dateTabsHtml += getDateTabText(start, date.getDate() === start.getDate() && date.getMonth() === start.getMonth() && date.getFullYear() === start.getFullYear(), tabIndex), start.setDate(start.getDate() + 1), start.setHours(0, 0, 0, 0), tabIndex++ + } + page.querySelector(".emby-tabs-slider").innerHTML = dateTabsHtml, page.querySelector(".guideDateTabs").refresh(); + var newDate = new Date, + newDateHours = newDate.getHours(), + scrollToTimeMs = 60 * newDateHours * 60 * 1e3, + minutes = newDate.getMinutes(); + minutes >= 30 && (scrollToTimeMs += 18e5), changeDate(page, date, scrollToTimeMs, 60 * (60 * newDateHours + minutes) * 1e3, startTimeOfDayMs, layoutManager.tv) + } + + function reloadPage(page) { + showLoading(), connectionManager.getApiClient(options.serverId).getLiveTvGuideInfo().then(function(guideInfo) { + setDateRange(page, guideInfo) + }) + } + + function getChannelProgramsFocusableElements(container) { + for (var elements = container.querySelectorAll(".programCell"), list = [], currentScrollXPct = scrollXPct + 1, i = 0, length = elements.length; i < length; i++) { + var elem = elements[i], + left = (elem.style.left || "").replace("%", ""); + left = left ? parseFloat(left) : 0; + var width = (elem.style.width || "").replace("%", ""); + width = width ? parseFloat(width) : 0, left + width >= currentScrollXPct && list.push(elem) + } + return list + } + + function onInputCommand(e) { + var container, channelPrograms, focusableElements, newRow, target = e.target, + programCell = dom.parentWithClass(target, "programCell"); + switch (e.detail.command) { + case "up": + programCell ? (container = programGrid, channelPrograms = dom.parentWithClass(programCell, "channelPrograms"), newRow = channelPrograms.previousSibling, newRow ? (focusableElements = getChannelProgramsFocusableElements(newRow), focusableElements.length ? container = newRow : focusableElements = null) : container = null) : container = null, lastFocusDirection = e.detail.command, focusManager.moveUp(target, { + container: container, + focusableElements: focusableElements + }); + break; + case "down": + programCell ? (container = programGrid, channelPrograms = dom.parentWithClass(programCell, "channelPrograms"), newRow = channelPrograms.nextSibling, newRow ? (focusableElements = getChannelProgramsFocusableElements(newRow), focusableElements.length ? container = newRow : focusableElements = null) : container = null) : container = null, lastFocusDirection = e.detail.command, focusManager.moveDown(target, { + container: container, + focusableElements: focusableElements + }); + break; + case "left": + container = programCell ? dom.parentWithClass(programCell, "channelPrograms") : null, container && !programCell.previousSibling && (container = null), lastFocusDirection = e.detail.command, focusManager.moveLeft(target, { + container: container + }), !0; + break; + case "right": + container = programCell ? dom.parentWithClass(programCell, "channelPrograms") : null, lastFocusDirection = e.detail.command, focusManager.moveRight(target, { + container: container + }), !0; + break; + default: + return + } + e.preventDefault(), e.stopPropagation() + } + + function onScrollerFocus(e) { + var target = e.target, + programCell = dom.parentWithClass(target, "programCell"); + if (programCell) { + var focused = target, + id = focused.getAttribute("data-id"), + item = items[id]; + item && events.trigger(self, "focus", [{ + item: item + }]) + } + if ("left" === lastFocusDirection) programCell && scrollHelper.toStart(programGrid, programCell, !0, !0); + else if ("right" === lastFocusDirection) programCell && scrollHelper.toCenter(programGrid, programCell, !0, !0); + else if ("up" === lastFocusDirection || "down" === lastFocusDirection) { + var verticalScroller = dom.parentWithClass(target, "guideVerticalScroller"); + if (verticalScroller) { + var focusedElement = programCell || dom.parentWithTag(target, "BUTTON"); + verticalScroller.toCenter(focusedElement, !0) + } + } + } + + function setScrollEvents(view, enabled) { + if (layoutManager.tv) { + var guideVerticalScroller = view.querySelector(".guideVerticalScroller"); + enabled ? inputManager.on(guideVerticalScroller, onInputCommand) : inputManager.off(guideVerticalScroller, onInputCommand) + } + } + + function onTimerCreated(e, apiClient, data) { + for (var programId = data.ProgramId, newTimerId = data.Id, cells = options.element.querySelectorAll('.programCell[data-id="' + programId + '"]'), i = 0, length = cells.length; i < length; i++) { + var cell = cells[i]; + cell.querySelector(".timerIcon") || cell.querySelector(".guideProgramName").insertAdjacentHTML("beforeend", ''), newTimerId && cell.setAttribute("data-timerid", newTimerId) + } + } + + function onSeriesTimerCreated(e, apiClient, data) {} + + function onTimerCancelled(e, apiClient, data) { + for (var id = data.Id, cells = options.element.querySelectorAll('.programCell[data-timerid="' + id + '"]'), i = 0, length = cells.length; i < length; i++) { + var cell = cells[i], + icon = cell.querySelector(".timerIcon"); + icon && icon.parentNode.removeChild(icon), cell.removeAttribute("data-timerid") + } + } + + function onSeriesTimerCancelled(e, apiClient, data) { + for (var id = data.Id, cells = options.element.querySelectorAll('.programCell[data-seriestimerid="' + id + '"]'), i = 0, length = cells.length; i < length; i++) { + var cell = cells[i], + icon = cell.querySelector(".seriesTimerIcon"); + icon && icon.parentNode.removeChild(icon), cell.removeAttribute("data-seriestimerid") + } + } + var self = this, + items = {}; + self.options = options, self.categoryOptions = { + categories: [] + }; + var currentDate, autoRefreshInterval, programCells, lastFocusDirection, programGrid, cellCurationMinutes = 30, + cellDurationMs = 60 * cellCurationMinutes * 1e3, + msPerDay = 864e5, + currentStartIndex = 0, + currentChannelLimit = 0; + self.refresh = function() { + currentDate = null, reloadPage(options.element), restartAutoRefresh() + }, self.pause = function() { + stopAutoRefresh() + }, self.resume = function(refreshData) { + refreshData ? self.refresh() : restartAutoRefresh() + }, self.destroy = function() { + stopAutoRefresh(), events.off(serverNotifications, "TimerCreated", onTimerCreated), events.off(serverNotifications, "SeriesTimerCreated", onSeriesTimerCreated), events.off(serverNotifications, "TimerCancelled", onTimerCancelled), events.off(serverNotifications, "SeriesTimerCancelled", onSeriesTimerCancelled), setScrollEvents(options.element, !1), itemShortcuts.off(options.element), items = {} + }; + var lastGridScroll = 0, + lastHeaderScroll = 0, + scrollXPct = 0; + require(["text!./tvguide.template.html"], function(template) { + var context = options.element; + context.classList.add("tvguide"), context.innerHTML = globalize.translateDocument(template, "sharedcomponents"), programGrid = context.querySelector(".programGrid"); + var timeslotHeaders = context.querySelector(".timeslotHeaders"); + layoutManager.tv ? dom.addEventListener(context.querySelector(".guideVerticalScroller"), "focus", onScrollerFocus, { + capture: !0, + passive: !0 + }) : layoutManager.desktop && timeslotHeaders.classList.add("timeslotHeaders-desktop"), (browser.iOS || browser.osx) && (context.querySelector(".channelsContainer").classList.add("noRubberBanding"), programGrid.classList.add("noRubberBanding")), dom.addEventListener(programGrid, "scroll", function(e) { + onProgramGridScroll(context, this, timeslotHeaders) + }, { + passive: !0 + }), dom.addEventListener(timeslotHeaders, "scroll", function() { + onTimeslotHeadersScroll(context, this) + }, { + passive: !0 + }), programGrid.addEventListener("click", onProgramGridClick), context.querySelector(".btnNextPage").addEventListener("click", function() { + currentStartIndex += currentChannelLimit, reloadPage(context), restartAutoRefresh() + }), context.querySelector(".btnPreviousPage").addEventListener("click", function() { + currentStartIndex = Math.max(currentStartIndex - currentChannelLimit, 0), reloadPage(context), restartAutoRefresh() + }), context.querySelector(".btnGuideViewSettings").addEventListener("click", function() { + showViewSettings(self), restartAutoRefresh() + }), context.querySelector(".guideDateTabs").addEventListener("tabchange", function(e) { + var allTabButtons = e.target.querySelectorAll(".guide-date-tab-button"), + tabButton = allTabButtons[parseInt(e.detail.selectedTabIndex)]; + if (tabButton) { + var previousButton = null == e.detail.previousIndex ? null : allTabButtons[parseInt(e.detail.previousIndex)], + date = new Date; + date.setTime(parseInt(tabButton.getAttribute("data-date"))); + var scrollToTimeMs, scrollWidth = programGrid.scrollWidth; + if (scrollToTimeMs = scrollWidth ? programGrid.scrollLeft / scrollWidth * msPerDay : 0, previousButton) { + var previousDate = new Date; + previousDate.setTime(parseInt(previousButton.getAttribute("data-date"))), scrollToTimeMs += 60 * previousDate.getHours() * 60 * 1e3, scrollToTimeMs += 60 * previousDate.getMinutes() * 1e3 + } + var startTimeOfDayMs = 60 * date.getHours() * 60 * 1e3; + startTimeOfDayMs += 60 * date.getMinutes() * 1e3, changeDate(context, date, scrollToTimeMs, scrollToTimeMs, startTimeOfDayMs, !1) + } + }), setScrollEvents(context, !0), itemShortcuts.on(context), events.trigger(self, "load"), events.on(serverNotifications, "TimerCreated", onTimerCreated), events.on(serverNotifications, "SeriesTimerCreated", onSeriesTimerCreated), events.on(serverNotifications, "TimerCancelled", onTimerCancelled), events.on(serverNotifications, "SeriesTimerCancelled", onSeriesTimerCancelled), self.refresh() + }) + } + var isUpdatingProgramCellScroll = !1, + ProgramCellPrototype = Object.create(HTMLButtonElement.prototype); + return ProgramCellPrototype.detachedCallback = function() { + this.posLeft = null, this.posWidth = null, this.guideProgramName = null + }, document.registerElement("emby-programcell", { + prototype: ProgramCellPrototype, + extends: "button" + }), Guide +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/headroom/headroom.js b/dashboard-ui/bower_components/emby-webcomponents/headroom/headroom.js index 493fe4c879..bd6573a663 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/headroom/headroom.js +++ b/dashboard-ui/bower_components/emby-webcomponents/headroom/headroom.js @@ -1 +1,136 @@ -define(["dom","layoutManager","browser","css!./headroom"],function(dom,layoutManager,browser){"use strict";function Debouncer(callback){this.callback=callback,this.ticking=!1}function onHeadroomClearedExternally(){this.state=null}function Headroom(elems,options){options=Object.assign(Headroom.options,options||{}),this.lastKnownScrollY=0,this.elems=elems,this.scroller=options.scroller,this.debouncer=onScroll.bind(this),this.offset=options.offset,this.initialised=!1,this.initialClass=options.initialClass,this.unPinnedClass=options.unPinnedClass,this.pinnedClass=options.pinnedClass,this.state="clear"}function onScroll(){this.paused||requestAnimationFrame(this.rafCallback||(this.rafCallback=this.update.bind(this)))}var requestAnimationFrame=window.requestAnimationFrame||window.webkitRequestAnimationFrame||window.mozRequestAnimationFrame;return Debouncer.prototype={constructor:Debouncer,update:function(){this.callback&&this.callback(),this.ticking=!1},handleEvent:function(){this.ticking||(requestAnimationFrame(this.rafCallback||(this.rafCallback=this.update.bind(this))),this.ticking=!0)}},Headroom.prototype={constructor:Headroom,init:function(){if(browser.supportsCssAnimation()){for(var i=0,length=this.elems.length;ithis.lastKnownScrollY,pastOffset=currentScrollY>=this.offset;return scrollingDown&&pastOffset},shouldPin:function(currentScrollY){var scrollingUp=currentScrollY=14;currentScrollY&&isTv?this.unpin():toleranceExceeded&&this.clear()}this.lastKnownScrollY=currentScrollY}}},Headroom.options={offset:0,scroller:window,initialClass:"headroom",unPinnedClass:"headroom--unpinned",pinnedClass:"headroom--pinned"},Headroom}); \ No newline at end of file +define(["dom", "layoutManager", "browser", "css!./headroom"], function(dom, layoutManager, browser) { + "use strict"; + + function Debouncer(callback) { + this.callback = callback, this.ticking = !1 + } + + function onHeadroomClearedExternally() { + this.state = null + } + + function Headroom(elems, options) { + options = Object.assign(Headroom.options, options || {}), this.lastKnownScrollY = 0, this.elems = elems, this.scroller = options.scroller, this.debouncer = onScroll.bind(this), this.offset = options.offset, this.initialised = !1, this.initialClass = options.initialClass, this.unPinnedClass = options.unPinnedClass, this.pinnedClass = options.pinnedClass, this.state = "clear" + } + + function onScroll() { + this.paused || requestAnimationFrame(this.rafCallback || (this.rafCallback = this.update.bind(this))) + } + var requestAnimationFrame = window.requestAnimationFrame || window.webkitRequestAnimationFrame || window.mozRequestAnimationFrame; + return Debouncer.prototype = { + constructor: Debouncer, + update: function() { + this.callback && this.callback(), this.ticking = !1 + }, + handleEvent: function() { + this.ticking || (requestAnimationFrame(this.rafCallback || (this.rafCallback = this.update.bind(this))), this.ticking = !0) + } + }, Headroom.prototype = { + constructor: Headroom, + init: function() { + if (browser.supportsCssAnimation()) { + for (var i = 0, length = this.elems.length; i < length; i++) this.elems[i].classList.add(this.initialClass), this.elems[i].addEventListener("clearheadroom", onHeadroomClearedExternally.bind(this)); + this.attachEvent() + } + return this + }, + add: function(elem) { + browser.supportsCssAnimation() && (elem.classList.add(this.initialClass), elem.addEventListener("clearheadroom", onHeadroomClearedExternally.bind(this)), this.elems.push(elem)) + }, + remove: function(elem) { + elem.classList.remove(this.unPinnedClass), elem.classList.remove(this.initialClass), elem.classList.remove(this.pinnedClass); + var i = this.elems.indexOf(elem); - 1 !== i && this.elems.splice(i, 1) + }, + pause: function() { + this.paused = !0 + }, + resume: function() { + this.paused = !1 + }, + destroy: function() { + this.initialised = !1; + for (var i = 0, length = this.elems.length; i < length; i++) { + var classList = this.elems[i].classList; + classList.remove(this.unPinnedClass), classList.remove(this.initialClass), classList.remove(this.pinnedClass) + } + var scrollEventName = this.scroller.getScrollEventName ? this.scroller.getScrollEventName() : "scroll"; + dom.removeEventListener(this.scroller, scrollEventName, this.debouncer, { + capture: !1, + passive: !0 + }) + }, + attachEvent: function() { + if (!this.initialised) { + this.lastKnownScrollY = this.getScrollY(), this.initialised = !0; + var scrollEventName = this.scroller.getScrollEventName ? this.scroller.getScrollEventName() : "scroll"; + dom.addEventListener(this.scroller, scrollEventName, this.debouncer, { + capture: !1, + passive: !0 + }), this.update() + } + }, + clear: function() { + if ("clear" !== this.state) { + this.state = "clear"; + for (var unpinnedClass = this.unPinnedClass, i = (this.pinnedClass, 0), length = this.elems.length; i < length; i++) { + this.elems[i].classList.remove(unpinnedClass) + } + } + }, + pin: function() { + if ("pin" !== this.state) { + this.state = "pin"; + for (var unpinnedClass = this.unPinnedClass, pinnedClass = this.pinnedClass, i = 0, length = this.elems.length; i < length; i++) { + var classList = this.elems[i].classList; + classList.remove(unpinnedClass), classList.add(pinnedClass) + } + } + }, + unpin: function() { + if ("unpin" !== this.state) { + this.state = "unpin"; + for (var unpinnedClass = this.unPinnedClass, i = (this.pinnedClass, 0), length = this.elems.length; i < length; i++) { + this.elems[i].classList.add(unpinnedClass) + } + } + }, + getScrollY: function() { + var scroller = this.scroller; + if (scroller.getScrollPosition) return scroller.getScrollPosition(); + var pageYOffset = scroller.pageYOffset; + if (void 0 !== pageYOffset) return pageYOffset; + var scrollTop = scroller.scrollTop; + return void 0 !== scrollTop ? scrollTop : (document.documentElement || document.body).scrollTop + }, + shouldUnpin: function(currentScrollY) { + var scrollingDown = currentScrollY > this.lastKnownScrollY, + pastOffset = currentScrollY >= this.offset; + return scrollingDown && pastOffset + }, + shouldPin: function(currentScrollY) { + var scrollingUp = currentScrollY < this.lastKnownScrollY, + pastOffset = currentScrollY <= this.offset; + return scrollingUp || pastOffset + }, + update: function() { + if (!this.paused) { + var currentScrollY = this.getScrollY(), + lastKnownScrollY = this.lastKnownScrollY, + isTv = layoutManager.tv; + if (currentScrollY <= (isTv ? 120 : 10)) this.clear(); + else if (this.shouldUnpin(currentScrollY)) this.unpin(); + else if (this.shouldPin(currentScrollY)) { + var toleranceExceeded = Math.abs(currentScrollY - lastKnownScrollY) >= 14; + currentScrollY && isTv ? this.unpin() : toleranceExceeded && this.clear() + } + this.lastKnownScrollY = currentScrollY + } + } + }, Headroom.options = { + offset: 0, + scroller: window, + initialClass: "headroom", + unPinnedClass: "headroom--unpinned", + pinnedClass: "headroom--pinned" + }, Headroom +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/homescreensettings/homescreensettings.js b/dashboard-ui/bower_components/emby-webcomponents/homescreensettings/homescreensettings.js index 5bee250528..8a34eb9418 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/homescreensettings/homescreensettings.js +++ b/dashboard-ui/bower_components/emby-webcomponents/homescreensettings/homescreensettings.js @@ -1 +1,233 @@ -define(["require","apphost","layoutManager","focusManager","globalize","loading","connectionManager","homeSections","dom","events","listViewStyle","emby-select","emby-checkbox"],function(require,appHost,layoutManager,focusManager,globalize,loading,connectionManager,homeSections,dom,events){"use strict";function renderViews(page,user,result){var folderHtml="";folderHtml+='
',folderHtml+=result.map(function(i){var currentHtml="",id="chkGroupFolder"+i.Id,isChecked=-1!==user.Configuration.GroupedFolders.indexOf(i.Id),checkedHtml=isChecked?' checked="checked"':"";return currentHtml+=""}).join(""),folderHtml+="
",page.querySelector(".folderGroupList").innerHTML=folderHtml}function getLandingScreenOptions(type){var list=[];return"movies"===type?(list.push({name:globalize.translate("sharedcomponents#Movies"),value:"movies",isDefault:!0}),list.push({name:globalize.translate("sharedcomponents#Suggestions"),value:"suggestions"}),list.push({name:globalize.translate("sharedcomponents#Favorites"),value:"favorites"}),list.push({name:globalize.translate("sharedcomponents#Collections"),value:"collections"})):"tvshows"===type?(list.push({name:globalize.translate("sharedcomponents#Shows"),value:"shows",isDefault:!0}),list.push({name:globalize.translate("sharedcomponents#Suggestions"),value:"suggestions"}),list.push({name:globalize.translate("sharedcomponents#Latest"),value:"latest"}),list.push({name:globalize.translate("sharedcomponents#Favorites"),value:"favorites"})):"music"===type?(list.push({name:globalize.translate("sharedcomponents#Suggestions"),value:"suggestions",isDefault:!0}),list.push({name:globalize.translate("sharedcomponents#Albums"),value:"albums"}),list.push({name:globalize.translate("sharedcomponents#HeaderAlbumArtists"),value:"albumartists"}),list.push({name:globalize.translate("sharedcomponents#Artists"),value:"artists"}),list.push({name:globalize.translate("sharedcomponents#Playlists"),value:"playlists"}),list.push({name:globalize.translate("sharedcomponents#Genres"),value:"genres"})):"livetv"===type&&(list.push({name:globalize.translate("sharedcomponents#Suggestions"),value:"suggestions",isDefault:!0}),list.push({name:globalize.translate("sharedcomponents#Guide"),value:"guide"})),list}function getLandingScreenOptionsHtml(type,userValue){return getLandingScreenOptions(type).map(function(o){var selected=userValue===o.value||o.isDefault&&!userValue,selectedHtml=selected?" selected":"";return'"}).join("")}function renderViewOrder(context,user,result){var html="",index=0;html+=result.Items.map(function(view){var currentHtml="";return currentHtml+='
',currentHtml+='',currentHtml+='
',currentHtml+="
",currentHtml+=view.Name,currentHtml+="
",currentHtml+="
",currentHtml+='',currentHtml+='',currentHtml+="
",index++,currentHtml}).join(""),context.querySelector(".viewOrderList").innerHTML=html}function updateHomeSectionValues(context,userSettings){for(var i=1;i<=7;i++){var select=context.querySelector("#selectHomeSection"+i),defaultValue=homeSections.getDefaultSection(i-1),option=select.querySelector("option[value="+defaultValue+"]")||select.querySelector('option[value=""]'),userValue=userSettings.get("homesection"+(i-1));option.value="",select.value=userValue!==defaultValue&&userValue?userValue:""}context.querySelector(".selectTVHomeScreen").value=userSettings.get("tvhome")||""}function getPerLibrarySettingsHtml(item,user,userSettings,apiClient){var isChecked,html="";if("Channel"!==item.Type&&"boxsets"!==item.CollectionType&&"playlists"!==item.CollectionType||(isChecked=-1===(user.Configuration.MyMediaExcludes||[]).indexOf(item.Id),html+="
",html+="",html+="
"),-1===["playlists","livetv","boxsets","channels"].indexOf(item.CollectionType||"")&&(isChecked=-1===user.Configuration.LatestItemsExcludes.indexOf(item.Id),html+='"),html&&(html='
'+html+"
"),"movies"===item.CollectionType||"tvshows"===item.CollectionType||"music"===item.CollectionType||"livetv"===item.CollectionType){var idForLanding="livetv"===item.CollectionType?item.CollectionType:item.Id;html+='
',html+='",html+="
"}if(html){var prefix="";prefix+='
',prefix+='

',prefix+=item.Name,prefix+="

",html=prefix+html,html+="
"}return html}function renderPerLibrarySettings(context,user,userViews,userSettings,apiClient){for(var elem=context.querySelector(".perLibrarySettings"),html="",i=0,length=userViews.length;i", currentHtml += "" + i.Name + "", currentHtml += "" + }).join(""), folderHtml += "
", page.querySelector(".folderGroupList").innerHTML = folderHtml + } + + function getLandingScreenOptions(type) { + var list = []; + return "movies" === type ? (list.push({ + name: globalize.translate("sharedcomponents#Movies"), + value: "movies", + isDefault: !0 + }), list.push({ + name: globalize.translate("sharedcomponents#Suggestions"), + value: "suggestions" + }), list.push({ + name: globalize.translate("sharedcomponents#Favorites"), + value: "favorites" + }), list.push({ + name: globalize.translate("sharedcomponents#Collections"), + value: "collections" + })) : "tvshows" === type ? (list.push({ + name: globalize.translate("sharedcomponents#Shows"), + value: "shows", + isDefault: !0 + }), list.push({ + name: globalize.translate("sharedcomponents#Suggestions"), + value: "suggestions" + }), list.push({ + name: globalize.translate("sharedcomponents#Latest"), + value: "latest" + }), list.push({ + name: globalize.translate("sharedcomponents#Favorites"), + value: "favorites" + })) : "music" === type ? (list.push({ + name: globalize.translate("sharedcomponents#Suggestions"), + value: "suggestions", + isDefault: !0 + }), list.push({ + name: globalize.translate("sharedcomponents#Albums"), + value: "albums" + }), list.push({ + name: globalize.translate("sharedcomponents#HeaderAlbumArtists"), + value: "albumartists" + }), list.push({ + name: globalize.translate("sharedcomponents#Artists"), + value: "artists" + }), list.push({ + name: globalize.translate("sharedcomponents#Playlists"), + value: "playlists" + }), list.push({ + name: globalize.translate("sharedcomponents#Genres"), + value: "genres" + })) : "livetv" === type && (list.push({ + name: globalize.translate("sharedcomponents#Suggestions"), + value: "suggestions", + isDefault: !0 + }), list.push({ + name: globalize.translate("sharedcomponents#Guide"), + value: "guide" + })), list + } + + function getLandingScreenOptionsHtml(type, userValue) { + return getLandingScreenOptions(type).map(function(o) { + var selected = userValue === o.value || o.isDefault && !userValue, + selectedHtml = selected ? " selected" : ""; + return '" + }).join("") + } + + function renderViewOrder(context, user, result) { + var html = "", + index = 0; + html += result.Items.map(function(view) { + var currentHtml = ""; + return currentHtml += '
', currentHtml += '', currentHtml += '
', currentHtml += "
", currentHtml += view.Name, currentHtml += "
", currentHtml += "
", currentHtml += '', currentHtml += '', currentHtml += "
", index++, currentHtml + }).join(""), context.querySelector(".viewOrderList").innerHTML = html + } + + function updateHomeSectionValues(context, userSettings) { + for (var i = 1; i <= 7; i++) { + var select = context.querySelector("#selectHomeSection" + i), + defaultValue = homeSections.getDefaultSection(i - 1), + option = select.querySelector("option[value=" + defaultValue + "]") || select.querySelector('option[value=""]'), + userValue = userSettings.get("homesection" + (i - 1)); + option.value = "", select.value = userValue !== defaultValue && userValue ? userValue : "" + } + context.querySelector(".selectTVHomeScreen").value = userSettings.get("tvhome") || "" + } + + function getPerLibrarySettingsHtml(item, user, userSettings, apiClient) { + var isChecked, html = ""; + if ("Channel" !== item.Type && "boxsets" !== item.CollectionType && "playlists" !== item.CollectionType || (isChecked = -1 === (user.Configuration.MyMediaExcludes || []).indexOf(item.Id), html += "
", html += "", html += "
"), -1 === ["playlists", "livetv", "boxsets", "channels"].indexOf(item.CollectionType || "") && (isChecked = -1 === user.Configuration.LatestItemsExcludes.indexOf(item.Id), html += '"), html && (html = '
' + html + "
"), "movies" === item.CollectionType || "tvshows" === item.CollectionType || "music" === item.CollectionType || "livetv" === item.CollectionType) { + var idForLanding = "livetv" === item.CollectionType ? item.CollectionType : item.Id; + html += '
', html += '", html += "
" + } + if (html) { + var prefix = ""; + prefix += '
', prefix += '

', prefix += item.Name, prefix += "

", html = prefix + html, html += "
" + } + return html + } + + function renderPerLibrarySettings(context, user, userViews, userSettings, apiClient) { + for (var elem = context.querySelector(".perLibrarySettings"), html = "", i = 0, length = userViews.length; i < length; i++) html += getPerLibrarySettingsHtml(userViews[i], user, userSettings, apiClient); + elem.innerHTML = html + } + + function loadForm(context, user, userSettings, apiClient) { + context.querySelector(".chkHidePlayedFromLatest").checked = user.Configuration.HidePlayedInLatest || !1, updateHomeSectionValues(context, userSettings); + var promise1 = apiClient.getUserViews({ + IncludeHidden: !0 + }, user.Id), + promise2 = apiClient.getJSON(apiClient.getUrl("Users/" + user.Id + "/GroupingOptions")); + Promise.all([promise1, promise2]).then(function(responses) { + renderViewOrder(context, user, responses[0]), renderPerLibrarySettings(context, user, responses[0].Items, userSettings, apiClient), renderViews(context, user, responses[1]), loading.hide() + }) + } + + function onSectionOrderListClick(e) { + var target = dom.parentWithClass(e.target, "btnViewItemMove"); + if (target) { + var viewItem = dom.parentWithClass(target, "viewItem"); + if (viewItem) { + dom.parentWithClass(viewItem, "paperList"); + if (target.classList.contains("btnViewItemDown")) { + var next = viewItem.nextSibling; + next && (viewItem.parentNode.removeChild(viewItem), next.parentNode.insertBefore(viewItem, next.nextSibling)) + } else { + var prev = viewItem.previousSibling; + prev && (viewItem.parentNode.removeChild(viewItem), prev.parentNode.insertBefore(viewItem, prev)) + } + } + } + } + + function getCheckboxItems(selector, context, isChecked) { + for (var inputs = context.querySelectorAll(selector), list = [], i = 0, length = inputs.length; i < length; i++) inputs[i].checked === isChecked && list.push(inputs[i]); + return list + } + + function saveUser(context, user, userSettingsInstance, apiClient) { + user.Configuration.HidePlayedInLatest = context.querySelector(".chkHidePlayedFromLatest").checked, user.Configuration.LatestItemsExcludes = getCheckboxItems(".chkIncludeInLatest", context, !1).map(function(i) { + return i.getAttribute("data-folderid") + }), user.Configuration.MyMediaExcludes = getCheckboxItems(".chkIncludeInMyMedia", context, !1).map(function(i) { + return i.getAttribute("data-folderid") + }), user.Configuration.GroupedFolders = getCheckboxItems(".chkGroupFolder", context, !0).map(function(i) { + return i.getAttribute("data-folderid") + }); + var i, length, viewItems = context.querySelectorAll(".viewItem"), + orderedViews = []; + for (i = 0, length = viewItems.length; i < length; i++) orderedViews.push(viewItems[i].getAttribute("data-viewid")); + user.Configuration.OrderedViews = orderedViews, userSettingsInstance.set("tvhome", context.querySelector(".selectTVHomeScreen").value), userSettingsInstance.set("homesection0", context.querySelector("#selectHomeSection1").value), userSettingsInstance.set("homesection1", context.querySelector("#selectHomeSection2").value), userSettingsInstance.set("homesection2", context.querySelector("#selectHomeSection3").value), userSettingsInstance.set("homesection3", context.querySelector("#selectHomeSection4").value), userSettingsInstance.set("homesection4", context.querySelector("#selectHomeSection5").value), userSettingsInstance.set("homesection5", context.querySelector("#selectHomeSection6").value), userSettingsInstance.set("homesection6", context.querySelector("#selectHomeSection7").value); + var selectLandings = context.querySelectorAll(".selectLanding"); + for (i = 0, length = selectLandings.length; i < length; i++) { + var selectLanding = selectLandings[i]; + userSettingsInstance.set("landing-" + selectLanding.getAttribute("data-folderid"), selectLanding.value) + } + return apiClient.updateUserConfiguration(user.Id, user.Configuration) + } + + function save(instance, context, userId, userSettings, apiClient, enableSaveConfirmation) { + loading.show(), apiClient.getUser(userId).then(function(user) { + saveUser(context, user, userSettings, apiClient).then(function() { + loading.hide(), enableSaveConfirmation && require(["toast"], function(toast) { + toast(globalize.translate("sharedcomponents#SettingsSaved")) + }), events.trigger(instance, "saved") + }, function() { + loading.hide() + }) + }) + } + + function onSubmit(e) { + var self = this, + apiClient = connectionManager.getApiClient(self.options.serverId), + userId = self.options.userId, + userSettings = self.options.userSettings; + return userSettings.setUserInfo(userId, apiClient).then(function() { + var enableSaveConfirmation = self.options.enableSaveConfirmation; + save(self, self.options.element, userId, userSettings, apiClient, enableSaveConfirmation) + }), e && e.preventDefault(), !1 + } + + function onChange(e) { + var chkIncludeInMyMedia = dom.parentWithClass(e.target, "chkIncludeInMyMedia"); + if (chkIncludeInMyMedia) { + var section = dom.parentWithClass(chkIncludeInMyMedia, "verticalSection"), + fldIncludeInLatest = section.querySelector(".fldIncludeInLatest"); + fldIncludeInLatest && (chkIncludeInMyMedia.checked ? fldIncludeInLatest.classList.remove("hide") : fldIncludeInLatest.classList.add("hide")) + } + } + + function embed(options, self) { + require(["text!./homescreensettings.template.html"], function(template) { + for (var i = 1; i <= numConfigurableSections; i++) template = template.replace("{section" + i + "label}", globalize.translate("sharedcomponents#LabelHomeScreenSectionValue", i)); + options.element.innerHTML = globalize.translateDocument(template, "sharedcomponents"), options.element.querySelector(".viewOrderList").addEventListener("click", onSectionOrderListClick), options.element.querySelector("form").addEventListener("submit", onSubmit.bind(self)), options.element.addEventListener("change", onChange), options.enableSaveButton && options.element.querySelector(".btnSave").classList.remove("hide"), layoutManager.tv ? options.element.querySelector(".selectTVHomeScreenContainer").classList.remove("hide") : options.element.querySelector(".selectTVHomeScreenContainer").classList.add("hide"), self.loadData(options.autoFocus) + }) + } + + function HomeScreenSettings(options) { + this.options = options, embed(options, this) + } + var numConfigurableSections = 7; + return HomeScreenSettings.prototype.loadData = function(autoFocus) { + var self = this, + context = self.options.element; + loading.show(); + var userId = self.options.userId, + apiClient = connectionManager.getApiClient(self.options.serverId), + userSettings = self.options.userSettings; + apiClient.getUser(userId).then(function(user) { + userSettings.setUserInfo(userId, apiClient).then(function() { + self.dataLoaded = !0, loadForm(context, user, userSettings, apiClient), autoFocus && focusManager.autoFocus(context) + }) + }) + }, HomeScreenSettings.prototype.submit = function() { + onSubmit.call(this) + }, HomeScreenSettings.prototype.destroy = function() { + this.options = null + }, HomeScreenSettings +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/homescreensettings/homescreensettingsdialog.js b/dashboard-ui/bower_components/emby-webcomponents/homescreensettings/homescreensettingsdialog.js index ff2d2c271c..a21c16ec81 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/homescreensettings/homescreensettingsdialog.js +++ b/dashboard-ui/bower_components/emby-webcomponents/homescreensettings/homescreensettingsdialog.js @@ -1 +1,47 @@ -define(["dialogHelper","layoutManager","globalize","require","events","homescreenSettings","paper-icon-button-light","css!./../formdialog"],function(dialogHelper,layoutManager,globalize,require,events,HomescreenSettings){"use strict";function centerFocus(elem,horiz,on){require(["scrollHelper"],function(scrollHelper){var fn=on?"on":"off";scrollHelper.centerFocus[fn](elem,horiz)})}function show(options){return new Promise(function(resolve,reject){require(["text!./homescreensettingsdialog.template.html"],function(template){var dialogOptions={removeOnClose:!0,scrollY:!1};layoutManager.tv?dialogOptions.size="fullscreen":dialogOptions.size="medium-tall";var dlg=dialogHelper.createDialog(dialogOptions);dlg.classList.add("formDialog");var html="",submitted=!1;html+=globalize.translateDocument(template,"sharedcomponents"),dlg.innerHTML=html,layoutManager.tv&¢erFocus(dlg.querySelector(".formDialogContent"),!1,!0);var homescreenSettingsInstance=new HomescreenSettings({serverId:options.serverId,userId:options.userId,element:dlg.querySelector(".settingsContent"),userSettings:options.userSettings,enableSaveButton:!1,enableSaveConfirmation:!1});dialogHelper.open(dlg),dlg.addEventListener("close",function(){layoutManager.tv&¢erFocus(dlg.querySelector(".formDialogContent"),!1,!1),submitted?resolve():reject()}),dlg.querySelector(".btnCancel").addEventListener("click",function(e){dialogHelper.close(dlg)}),dlg.querySelector(".btnSave").addEventListener("click",function(e){submitted=!0,homescreenSettingsInstance.submit()}),events.on(homescreenSettingsInstance,"saved",function(){submitted=!0,dialogHelper.close(dlg)})})})}return{show:show}}); \ No newline at end of file +define(["dialogHelper", "layoutManager", "globalize", "require", "events", "homescreenSettings", "paper-icon-button-light", "css!./../formdialog"], function(dialogHelper, layoutManager, globalize, require, events, HomescreenSettings) { + "use strict"; + + function centerFocus(elem, horiz, on) { + require(["scrollHelper"], function(scrollHelper) { + var fn = on ? "on" : "off"; + scrollHelper.centerFocus[fn](elem, horiz) + }) + } + + function show(options) { + return new Promise(function(resolve, reject) { + require(["text!./homescreensettingsdialog.template.html"], function(template) { + var dialogOptions = { + removeOnClose: !0, + scrollY: !1 + }; + layoutManager.tv ? dialogOptions.size = "fullscreen" : dialogOptions.size = "medium-tall"; + var dlg = dialogHelper.createDialog(dialogOptions); + dlg.classList.add("formDialog"); + var html = "", + submitted = !1; + html += globalize.translateDocument(template, "sharedcomponents"), dlg.innerHTML = html, layoutManager.tv && centerFocus(dlg.querySelector(".formDialogContent"), !1, !0); + var homescreenSettingsInstance = new HomescreenSettings({ + serverId: options.serverId, + userId: options.userId, + element: dlg.querySelector(".settingsContent"), + userSettings: options.userSettings, + enableSaveButton: !1, + enableSaveConfirmation: !1 + }); + dialogHelper.open(dlg), dlg.addEventListener("close", function() { + layoutManager.tv && centerFocus(dlg.querySelector(".formDialogContent"), !1, !1), submitted ? resolve() : reject() + }), dlg.querySelector(".btnCancel").addEventListener("click", function(e) { + dialogHelper.close(dlg) + }), dlg.querySelector(".btnSave").addEventListener("click", function(e) { + submitted = !0, homescreenSettingsInstance.submit() + }), events.on(homescreenSettingsInstance, "saved", function() { + submitted = !0, dialogHelper.close(dlg) + }) + }) + }) + } + return { + show: show + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/homesections/homesections.js b/dashboard-ui/bower_components/emby-webcomponents/homesections/homesections.js index d10f038f24..4f1258dbde 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/homesections/homesections.js +++ b/dashboard-ui/bower_components/emby-webcomponents/homesections/homesections.js @@ -1 +1,618 @@ -define(["connectionManager","cardBuilder","registrationServices","appSettings","dom","apphost","layoutManager","imageLoader","globalize","itemShortcuts","itemHelper","appRouter","emby-button","paper-icon-button-light","emby-itemscontainer","emby-scroller","emby-linkbutton","css!./homesections"],function(connectionManager,cardBuilder,registrationServices,appSettings,dom,appHost,layoutManager,imageLoader,globalize,itemShortcuts,itemHelper,appRouter){"use strict";function getDefaultSection(index){switch(index){case 0:return"smalllibrarytiles";case 1:return"resume";case 2:return"resumeaudio";case 3:return"livetv";case 4:return"nextup";case 5:return"latestmedia";case 6:return"none";default:return""}}function getAllSectionsToShow(userSettings,sectionCount){for(var sections=[],i=0,length=sectionCount;i
';elem.innerHTML=html,elem.classList.add("homeSectionsContainer");var promises=[],sections=getAllSectionsToShow(userSettings,7);for(i=0,length=sections.length;i',html+=''+globalize.translate("sharedcomponents#HeaderCustomizeHomeScreen")+"",html+="
",elem.insertAdjacentHTML("beforeend",html),resume(elem,{refresh:!0,returnPromise:!1})})})}function destroySections(elem){var i,length,elems=elem.querySelectorAll(".itemsContainer");for(i=0,length=elems.length;i",layoutManager.tv||(html+=''),html+="",html+='
';for(var i=0,length=items.length;i'+icon+""+item.Name+""}return html+="
",html+=""}function loadlibraryButtons(elem,apiClient,user,userSettings,userViews){return Promise.all([getAppInfo(apiClient),getDownloadsSectionHtml(apiClient,user,userSettings)]).then(function(responses){var infoHtml=responses[0],downloadsHtml=responses[1];elem.classList.remove("verticalSection");var html=getLibraryButtonsHtml(userViews);elem.innerHTML=html+downloadsHtml+infoHtml,bindHomeScreenSettingsIcon(elem,apiClient,user.Id,userSettings),infoHtml&&bindAppInfoEvents(elem),imageLoader.lazyChildren(elem)})}function bindAppInfoEvents(elem){elem.querySelector(".appInfoSection").addEventListener("click",function(e){dom.parentWithClass(e.target,"card")&®istrationServices.showPremiereInfo()})}function getRandomInt(min,max){return Math.floor(Math.random()*(max-min+1))+min}function getAppInfo(apiClient){var cacheKey="lastappinfopresent5",lastDatePresented=parseInt(appSettings.get(cacheKey)||"0");return lastDatePresented?(new Date).getTime()-lastDatePresented<1728e5?Promise.resolve(""):registrationServices.validateFeature("dvr",{showDialog:!1,viewOnly:!0}).then(function(){return appSettings.set(cacheKey,(new Date).getTime()),""},function(){appSettings.set(cacheKey,(new Date).getTime());var infos=[getPremiereInfo];return appHost.supports("otherapppromotions")&&infos.push(getTheaterInfo),infos[getRandomInt(0,infos.length-1)]()}):(appSettings.set(cacheKey,(new Date).getTime()),Promise.resolve(""))}function getCard(img,shape){shape=shape||"backdropCard";var html='
';return html+='
',html+='
',html+="
",html+="
"}function getTheaterInfo(){var html="";html+='
',html+='
',html+='

Discover Emby Theater

',html+='',html+="
";return html+='
',html+='

A beautiful app for your TV and large screen tablet. Emby Theater runs on Windows, Xbox One, Raspberry Pi, Samsung Smart TVs, Sony PS4, Web Browsers, and more.

',html+='
',html+=getCard("https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/apps/theater1.png"),html+=getCard("https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/apps/theater2.png"),html+=getCard("https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/apps/theater3.png"),html+="
",html+="
",html+="
"}function getPremiereInfo(){var html="";return html+='
',html+='
',html+='

Discover Emby Premiere

',html+='',html+="
",html+='
',html+='

Enjoy Emby DVR, get free access to Emby apps, and more.

',html+='
',html+=getCard("https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/apps/theater1.png"),html+=getCard("https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/apps/theater2.png"),html+=getCard("https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/apps/theater3.png"),html+="
",html+="
",html+="
"}function getFetchLatestItemsFn(serverId,parentId,collectionType){return function(){var apiClient=connectionManager.getApiClient(serverId),limit=16;enableScrollX()?"music"===collectionType&&(limit=30):limit="tvshows"===collectionType?5:"music"===collectionType?9:8;var options={Limit:limit,Fields:"PrimaryImageAspectRatio,BasicSyncInfo",ImageTypeLimit:1,EnableImageTypes:"Primary,Backdrop,Thumb",ParentId:parentId};return apiClient.getLatestItems(options)}}function getLatestItemsHtmlFn(itemType,viewType){return function(items){var shape="Channel"===itemType||"movies"===viewType?getPortraitShape():"music"===viewType?getSquareShape():getThumbShape();return cardBuilder.getCardsHtml({items:items,shape:shape,preferThumb:"movies"!==viewType&&"Channel"!==itemType&&"music"!==viewType?"auto":null,showUnplayedIndicator:!1,showChildCountIndicator:!0,context:"home",overlayText:!1,centerText:!0,overlayPlayButton:"photos"!==viewType,allowBottomPadding:!enableScrollX()&&!0,cardLayout:!1,showTitle:"photos"!==viewType,showYear:"movies"===viewType||"tvshows"===viewType||!viewType,showParentTitle:"music"===viewType||"tvshows"===viewType||!viewType||!1,lines:2})}}function renderLatestSection(elem,apiClient,user,parent){var html="";html+='
',layoutManager.tv?html+='

'+globalize.translate("sharedcomponents#LatestFromLibrary",parent.Name)+"

":(html+='',html+='

',html+=globalize.translate("sharedcomponents#LatestFromLibrary",parent.Name),html+="

",html+='',html+="
"),html+="
",enableScrollX()?html+='
':html+='
',enableScrollX()&&(html+="
"),html+="
",elem.innerHTML=html;var itemsContainer=elem.querySelector(".itemsContainer");itemsContainer.fetchData=getFetchLatestItemsFn(apiClient.serverId(),parent.Id,parent.CollectionType),itemsContainer.getItemsHtml=getLatestItemsHtmlFn(parent.Type,parent.CollectionType),itemsContainer.parentContainer=elem}function loadRecentlyAdded(elem,apiClient,user,userViews){elem.classList.remove("verticalSection");for(var excludeViewTypes=["playlists","livetv","boxsets","channels"],i=0,length=userViews.length;i":(html+='',html+='

',html+=globalize.translate("sharedcomponents#HeaderMyDownloads"),html+="

",html+='',html+="
",html+=''),html+="
",html+='
',html+=cardBuilder.getCardsHtml({items:items,preferThumb:"auto",shape:"autooverflow",overlayText:!1,showTitle:!0,showParentTitle:!0,lazy:!0,showDetailsMenu:!0,overlayPlayButton:!0,context:"home",centerText:!0,allowBottomPadding:!1,cardLayout:!1,showYear:!0,lines:2}),html+="
",html+="
"}):Promise.resolve("")}function loadLibraryTiles(elem,apiClient,user,userSettings,shape,userViews,allSections){elem.classList.remove("verticalSection");var html="",scrollX=!layoutManager.desktop;return userViews.length&&(html+='
',html+='
',html+='

'+globalize.translate("sharedcomponents#HeaderMyMedia")+"

",layoutManager.tv||(html+=''),html+="
",html+=scrollX?'
':'
',html+=cardBuilder.getCardsHtml({items:userViews,shape:scrollX?"overflowSmallBackdrop":shape,showTitle:!0,centerText:!0,overlayText:!1,lazy:!0,transition:!1,allowBottomPadding:!scrollX}),scrollX&&(html+="
"),html+="
",html+="
"),Promise.all([getAppInfo(apiClient),getDownloadsSectionHtml(apiClient,user,userSettings)]).then(function(responses){var infoHtml=responses[0],downloadsHtml=responses[1];elem.innerHTML=html+downloadsHtml+infoHtml,bindHomeScreenSettingsIcon(elem,apiClient,user.Id,userSettings),infoHtml&&bindAppInfoEvents(elem),imageLoader.lazyChildren(elem)})}function getContinueWatchingFetchFn(serverId){return function(){var limit,apiClient=connectionManager.getApiClient(serverId),screenWidth=dom.getWindowSize().innerWidth;enableScrollX()?limit=12:(limit=screenWidth>=1920?8:screenWidth>=1600?8:screenWidth>=1200?9:6,limit=Math.min(limit,5));var options={Limit:limit,Recursive:!0,Fields:"PrimaryImageAspectRatio,BasicSyncInfo",ImageTypeLimit:1,EnableImageTypes:"Primary,Backdrop,Thumb",EnableTotalRecordCount:!1,MediaTypes:"Video"};return apiClient.getResumableItems(apiClient.getCurrentUserId(),options)}}function getContinueWatchingItemsHtml(items){return cardBuilder.getCardsHtml({items:items,preferThumb:!0,shape:getThumbShape(),overlayText:!1,showTitle:!0,showParentTitle:!0,lazy:!0,showDetailsMenu:!0,overlayPlayButton:!0,context:"home",centerText:!0,allowBottomPadding:!1,cardLayout:!1,showYear:!0,lines:2})}function loadResumeVideo(elem,apiClient,userId){var html="";html+='

'+globalize.translate("sharedcomponents#HeaderContinueWatching")+"

",enableScrollX()?html+='
':html+='
',enableScrollX()&&(html+="
"),html+="
",elem.classList.add("hide"),elem.innerHTML=html;var itemsContainer=elem.querySelector(".itemsContainer");itemsContainer.fetchData=getContinueWatchingFetchFn(apiClient.serverId()),itemsContainer.getItemsHtml=getContinueWatchingItemsHtml,itemsContainer.parentContainer=elem}function getContinueListeningFetchFn(serverId){return function(){var limit,apiClient=connectionManager.getApiClient(serverId),screenWidth=dom.getWindowSize().innerWidth;enableScrollX()?limit=12:(limit=screenWidth>=1920?8:screenWidth>=1600?8:screenWidth>=1200?9:6,limit=Math.min(limit,5));var options={Limit:limit,Recursive:!0,Fields:"PrimaryImageAspectRatio,BasicSyncInfo",ImageTypeLimit:1,EnableImageTypes:"Primary,Backdrop,Thumb",EnableTotalRecordCount:!1,MediaTypes:"Audio"};return apiClient.getResumableItems(apiClient.getCurrentUserId(),options)}}function getContinueListeningItemsHtml(items){return cardBuilder.getCardsHtml({items:items,preferThumb:!0,shape:getThumbShape(),overlayText:!1,showTitle:!0,showParentTitle:!0,lazy:!0,showDetailsMenu:!0,overlayPlayButton:!0,context:"home",centerText:!0,allowBottomPadding:!1,cardLayout:!1,showYear:!0,lines:2})}function loadResumeAudio(elem,apiClient,userId){var html="";html+='

'+globalize.translate("sharedcomponents#HeaderContinueWatching")+"

",enableScrollX()?html+='
':html+='
',enableScrollX()&&(html+="
"),html+="
",elem.classList.add("hide"),elem.innerHTML=html;var itemsContainer=elem.querySelector(".itemsContainer");itemsContainer.fetchData=getContinueListeningFetchFn(apiClient.serverId()),itemsContainer.getItemsHtml=getContinueListeningItemsHtml,itemsContainer.parentContainer=elem}function bindUnlockClick(elem){var btnUnlock=elem.querySelector(".btnUnlock");btnUnlock&&btnUnlock.addEventListener("click",function(e){registrationServices.validateFeature("livetv",{viewOnly:!0}).then(function(){dom.parentWithClass(elem,"homeSectionsContainer").dispatchEvent(new CustomEvent("settingschange",{cancelable:!1}))})})}function getOnNowFetchFn(serverId){return function(){var apiClient=connectionManager.getApiClient(serverId);return apiClient.getLiveTvRecommendedPrograms({userId:apiClient.getCurrentUserId(),IsAiring:!0,limit:24,ImageTypeLimit:1,EnableImageTypes:"Primary,Thumb,Backdrop",EnableTotalRecordCount:!1,Fields:"ChannelInfo,PrimaryImageAspectRatio"})}}function getOnNowItemsHtml(items){return cardBuilder.getCardsHtml({items:items,preferThumb:"auto",inheritThumb:!1,shape:enableScrollX()?"autooverflow":"auto",showParentTitleOrTitle:!0,showTitle:!0,centerText:!0,coverImage:!0,overlayText:!1,allowBottomPadding:!enableScrollX(),showAirTime:!0,showChannelName:!1,showAirDateTime:!1,showAirEndTime:!0,defaultShape:getThumbShape(),lines:3,overlayPlayButton:!0})}function loadOnNow(elem,apiClient,user){if(!user.Policy.EnableLiveTvAccess)return Promise.resolve();var promises=[];promises.push(registrationServices.validateFeature("livetv",{viewOnly:!0,showDialog:!1}).then(function(){return!0},function(){return!1}));user.Id;return promises.push(apiClient.getLiveTvRecommendedPrograms({userId:apiClient.getCurrentUserId(),IsAiring:!0,limit:1,ImageTypeLimit:1,EnableImageTypes:"Primary,Thumb,Backdrop",EnableTotalRecordCount:!1,Fields:"ChannelInfo,PrimaryImageAspectRatio"})),Promise.all(promises).then(function(responses){var registered=responses[0],result=responses[1],html="";if(result.Items.length&®istered){elem.classList.remove("padded-left"),elem.classList.remove("padded-right"),elem.classList.remove("padded-bottom"),elem.classList.remove("verticalSection"),html+='
',html+='
',html+='

'+globalize.translate("sharedcomponents#LiveTV")+"

",html+="
",enableScrollX()?(html+='",html+="
",html+='
',html+='
',layoutManager.tv?html+='

'+globalize.translate("sharedcomponents#HeaderOnNow")+"

":(html+='',html+='

',html+=globalize.translate("sharedcomponents#HeaderOnNow"),html+="

",html+='',html+="
"),html+="
",enableScrollX()?html+='
':html+='
',enableScrollX()&&(html+="
"),html+="
",html+="
",elem.innerHTML=html;var itemsContainer=elem.querySelector(".itemsContainer");itemsContainer.parentContainer=elem,itemsContainer.fetchData=getOnNowFetchFn(apiClient.serverId()),itemsContainer.getItemsHtml=getOnNowItemsHtml}else result.Items.length&&!registered&&(elem.classList.add("padded-left"),elem.classList.add("padded-right"),elem.classList.add("padded-bottom"),html+='

'+globalize.translate("sharedcomponents#LiveTvRequiresUnlock")+"

",html+='",elem.innerHTML=html);bindUnlockClick(elem)})}function getNextUpFetchFn(serverId){return function(){var apiClient=connectionManager.getApiClient(serverId);return apiClient.getNextUpEpisodes({Limit:enableScrollX()?24:15,Fields:"PrimaryImageAspectRatio,SeriesInfo,DateCreated,BasicSyncInfo",UserId:apiClient.getCurrentUserId(),ImageTypeLimit:1,EnableImageTypes:"Primary,Backdrop,Banner,Thumb",EnableTotalRecordCount:!1})}}function getNextUpItemsHtml(items){return cardBuilder.getCardsHtml({items:items,preferThumb:!0,shape:getThumbShape(),overlayText:!1,showTitle:!0,showParentTitle:!0,lazy:!0,overlayPlayButton:!0,context:"home",centerText:!0,allowBottomPadding:!enableScrollX(),cardLayout:!1})}function loadNextUp(elem,apiClient,userId){var html="";html+='
',layoutManager.tv?html+='

'+globalize.translate("sharedcomponents#HeaderNextUp")+"

":(html+='',html+='

',html+=globalize.translate("sharedcomponents#HeaderNextUp"),html+="

",html+='',html+="
"),html+="
",enableScrollX()?html+='
':html+='
',enableScrollX()&&(html+="
"),html+="
",elem.classList.add("hide"),elem.innerHTML=html;var itemsContainer=elem.querySelector(".itemsContainer");itemsContainer.fetchData=getNextUpFetchFn(apiClient.serverId()),itemsContainer.getItemsHtml=getNextUpItemsHtml,itemsContainer.parentContainer=elem}function getLatestRecordingsFetchFn(serverId,activeRecordingsOnly){return function(){var apiClient=connectionManager.getApiClient(serverId);return apiClient.getLiveTvRecordings({userId:apiClient.getCurrentUserId(),Limit:enableScrollX()?12:5,Fields:"PrimaryImageAspectRatio,BasicSyncInfo",EnableTotalRecordCount:!1,IsLibraryItem:!!activeRecordingsOnly&&null,IsInProgress:!!activeRecordingsOnly||null})}}function getLatestRecordingItemsHtml(activeRecordingsOnly){return function(items){return cardBuilder.getCardsHtml({items:items,shape:enableScrollX()?"autooverflow":"auto",showTitle:!0,showParentTitle:!0,coverImage:!0,lazy:!0,showDetailsMenu:!0,centerText:!0,overlayText:!1,showYear:!0,lines:2,overlayPlayButton:!activeRecordingsOnly,allowBottomPadding:!enableScrollX(),preferThumb:!0,cardLayout:!1,overlayMoreButton:activeRecordingsOnly,action:activeRecordingsOnly?"none":null,centerPlayButton:activeRecordingsOnly})}}function loadLatestLiveTvRecordings(elem,activeRecordingsOnly,apiClient,userId){var title=activeRecordingsOnly?globalize.translate("sharedcomponents#HeaderActiveRecordings"):globalize.translate("sharedcomponents#HeaderLatestRecordings"),html="";html+='
',html+='

'+title+"

",layoutManager.tv,html+="
",enableScrollX()?html+='
':html+='
',enableScrollX()&&(html+="
"),html+="
",elem.classList.add("hide"),elem.innerHTML=html;var itemsContainer=elem.querySelector(".itemsContainer");itemsContainer.fetchData=getLatestRecordingsFetchFn(apiClient.serverId(),activeRecordingsOnly),itemsContainer.getItemsHtml=getLatestRecordingItemsHtml(activeRecordingsOnly),itemsContainer.parentContainer=elem}return{loadLibraryTiles:loadLibraryTiles,getDefaultSection:getDefaultSection,loadSections:loadSections,destroySections:destroySections,pause:pause,resume:resume}}); \ No newline at end of file +define(["connectionManager", "cardBuilder", "registrationServices", "appSettings", "dom", "apphost", "layoutManager", "imageLoader", "globalize", "itemShortcuts", "itemHelper", "appRouter", "emby-button", "paper-icon-button-light", "emby-itemscontainer", "emby-scroller", "emby-linkbutton", "css!./homesections"], function(connectionManager, cardBuilder, registrationServices, appSettings, dom, appHost, layoutManager, imageLoader, globalize, itemShortcuts, itemHelper, appRouter) { + "use strict"; + + function getDefaultSection(index) { + switch (index) { + case 0: + return "smalllibrarytiles"; + case 1: + return "resume"; + case 2: + return "resumeaudio"; + case 3: + return "livetv"; + case 4: + return "nextup"; + case 5: + return "latestmedia"; + case 6: + return "none"; + default: + return "" + } + } + + function getAllSectionsToShow(userSettings, sectionCount) { + for (var sections = [], i = 0, length = sectionCount; i < length; i++) { + var section = userSettings.get("homesection" + i) || getDefaultSection(i); + "folders" === section && (section = getDefaultSection(0)), sections.push(section) + } + return sections + } + + function loadSections(elem, apiClient, user, userSettings) { + return getUserViews(apiClient, user.Id).then(function(userViews) { + var i, length, html = ""; + for (i = 0, length = 7; i < length; i++) html += '
'; + elem.innerHTML = html, elem.classList.add("homeSectionsContainer"); + var promises = [], + sections = getAllSectionsToShow(userSettings, 7); + for (i = 0, length = sections.length; i < length; i++) promises.push(loadSection(elem, apiClient, user, userSettings, userViews, sections, i)); + return Promise.all(promises).then(function() { + html = ""; + var style = "margin-top:4em;"; + return layoutManager.tv && (style += "padding: 0 7.5%;"), html += '", elem.insertAdjacentHTML("beforeend", html), resume(elem, { + refresh: !0, + returnPromise: !1 + }) + }) + }) + } + + function destroySections(elem) { + var i, length, elems = elem.querySelectorAll(".itemsContainer"); + for (i = 0, length = elems.length; i < length; i++) elems[i].fetchData = null, elems[i].parentContainer = null, elems[i].getItemsHtml = null; + elem.innerHTML = "" + } + + function pause(elem) { + var i, length, elems = elem.querySelectorAll(".itemsContainer"); + for (i = 0, length = elems.length; i < length; i++) elems[i].pause() + } + + function resume(elem, options) { + var i, length, elems = elem.querySelectorAll(".itemsContainer"), + promises = []; + for (i = 0, length = elems.length; i < length; i++) promises.push(elems[i].resume(options)); + var promise = Promise.all(promises).then(function() { + elem.querySelector(".customizeSection").classList.remove("hide") + }); + if (!options || !1 !== options.returnPromise) return promise + } + + function loadSection(page, apiClient, user, userSettings, userViews, allSections, index) { + var section = allSections[index], + userId = user.Id, + elem = page.querySelector(".section" + index); + if ("latestmedia" === section) loadRecentlyAdded(elem, apiClient, user, userViews); + else { + if ("librarytiles" === section || "smalllibrarytiles" === section || "smalllibrarytiles-automobile" === section || "librarytiles-automobile" === section) return loadLibraryTiles(elem, apiClient, user, userSettings, "smallBackdrop", userViews, allSections); + if ("librarybuttons" === section) return loadlibraryButtons(elem, apiClient, user, userSettings, userViews); + if ("resume" === section) loadResumeVideo(elem, apiClient, userId); + else if ("resumeaudio" === section) loadResumeAudio(elem, apiClient, userId); + else if ("activerecordings" === section) loadLatestLiveTvRecordings(elem, !0, apiClient, userId); + else { + if ("nextup" !== section) return "onnow" === section || "livetv" === section ? loadOnNow(elem, apiClient, user) : (elem.innerHTML = "", Promise.resolve()); + loadNextUp(elem, apiClient, userId) + } + } + return Promise.resolve() + } + + function getUserViews(apiClient, userId) { + return apiClient.getUserViews({}, userId || apiClient.getCurrentUserId()).then(function(result) { + return result.Items + }) + } + + function enableScrollX() { + return !0 + } + + function getSquareShape() { + return enableScrollX() ? "overflowSquare" : "square" + } + + function getThumbShape() { + return enableScrollX() ? "overflowBackdrop" : "backdrop" + } + + function getPortraitShape() { + return enableScrollX() ? "autooverflow" : "auto" + } + + function getLibraryButtonsHtml(items) { + var html = ""; + html += '
', html += '
', html += '

' + globalize.translate("sharedcomponents#HeaderMyMedia") + "

", layoutManager.tv || (html += ''), html += "
", html += '
'; + for (var i = 0, length = items.length; i < length; i++) { + var icon, item = items[i]; + switch (item.CollectionType) { + case "movies": + icon = "local_movies"; + break; + case "music": + icon = "library_music"; + break; + case "photos": + icon = "photo"; + break; + case "livetv": + case "tvshows": + icon = "live_tv"; + break; + case "games": + icon = "folder"; + break; + case "trailers": + icon = "local_movies"; + break; + case "homevideos": + case "musicvideos": + icon = "video_library"; + break; + case "books": + case "channels": + case "playlists": + default: + icon = "folder" + } + html += '' + icon + "" + item.Name + "" + } + return html += "
", html += "
" + } + + function loadlibraryButtons(elem, apiClient, user, userSettings, userViews) { + return Promise.all([getAppInfo(apiClient), getDownloadsSectionHtml(apiClient, user, userSettings)]).then(function(responses) { + var infoHtml = responses[0], + downloadsHtml = responses[1]; + elem.classList.remove("verticalSection"); + var html = getLibraryButtonsHtml(userViews); + elem.innerHTML = html + downloadsHtml + infoHtml, bindHomeScreenSettingsIcon(elem, apiClient, user.Id, userSettings), infoHtml && bindAppInfoEvents(elem), imageLoader.lazyChildren(elem) + }) + } + + function bindAppInfoEvents(elem) { + elem.querySelector(".appInfoSection").addEventListener("click", function(e) { + dom.parentWithClass(e.target, "card") && registrationServices.showPremiereInfo() + }) + } + + function getRandomInt(min, max) { + return Math.floor(Math.random() * (max - min + 1)) + min + } + + function getAppInfo(apiClient) { + var cacheKey = "lastappinfopresent5", + lastDatePresented = parseInt(appSettings.get(cacheKey) || "0"); + return lastDatePresented ? (new Date).getTime() - lastDatePresented < 1728e5 ? Promise.resolve("") : registrationServices.validateFeature("dvr", { + showDialog: !1, + viewOnly: !0 + }).then(function() { + return appSettings.set(cacheKey, (new Date).getTime()), "" + }, function() { + appSettings.set(cacheKey, (new Date).getTime()); + var infos = [getPremiereInfo]; + return appHost.supports("otherapppromotions") && infos.push(getTheaterInfo), infos[getRandomInt(0, infos.length - 1)]() + }) : (appSettings.set(cacheKey, (new Date).getTime()), Promise.resolve("")) + } + + function getCard(img, shape) { + shape = shape || "backdropCard"; + var html = '
'; + return html += '
', html += '
', html += "
", html += "
" + } + + function getTheaterInfo() { + var html = ""; + html += '
', html += '
', html += '

Discover Emby Theater

', html += '', html += "
"; + return html += '
', html += '

A beautiful app for your TV and large screen tablet. Emby Theater runs on Windows, Xbox One, Raspberry Pi, Samsung Smart TVs, Sony PS4, Web Browsers, and more.

', html += '
', html += getCard("https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/apps/theater1.png"), html += getCard("https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/apps/theater2.png"), html += getCard("https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/apps/theater3.png"), html += "
", html += "
", html += "
" + } + + function getPremiereInfo() { + var html = ""; + return html += '
', html += '
', html += '

Discover Emby Premiere

', html += '', html += "
", html += '
', html += '

Enjoy Emby DVR, get free access to Emby apps, and more.

', html += '
', html += getCard("https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/apps/theater1.png"), html += getCard("https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/apps/theater2.png"), html += getCard("https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/apps/theater3.png"), html += "
", html += "
", html += "
" + } + + function getFetchLatestItemsFn(serverId, parentId, collectionType) { + return function() { + var apiClient = connectionManager.getApiClient(serverId), + limit = 16; + enableScrollX() ? "music" === collectionType && (limit = 30) : limit = "tvshows" === collectionType ? 5 : "music" === collectionType ? 9 : 8; + var options = { + Limit: limit, + Fields: "PrimaryImageAspectRatio,BasicSyncInfo", + ImageTypeLimit: 1, + EnableImageTypes: "Primary,Backdrop,Thumb", + ParentId: parentId + }; + return apiClient.getLatestItems(options) + } + } + + function getLatestItemsHtmlFn(itemType, viewType) { + return function(items) { + var shape = "Channel" === itemType || "movies" === viewType ? getPortraitShape() : "music" === viewType ? getSquareShape() : getThumbShape(); + return cardBuilder.getCardsHtml({ + items: items, + shape: shape, + preferThumb: "movies" !== viewType && "Channel" !== itemType && "music" !== viewType ? "auto" : null, + showUnplayedIndicator: !1, + showChildCountIndicator: !0, + context: "home", + overlayText: !1, + centerText: !0, + overlayPlayButton: "photos" !== viewType, + allowBottomPadding: !enableScrollX() && !0, + cardLayout: !1, + showTitle: "photos" !== viewType, + showYear: "movies" === viewType || "tvshows" === viewType || !viewType, + showParentTitle: "music" === viewType || "tvshows" === viewType || !viewType || !1, + lines: 2 + }) + } + } + + function renderLatestSection(elem, apiClient, user, parent) { + var html = ""; + html += '
', layoutManager.tv ? html += '

' + globalize.translate("sharedcomponents#LatestFromLibrary", parent.Name) + "

" : (html += '', html += '

', html += globalize.translate("sharedcomponents#LatestFromLibrary", parent.Name), html += "

", html += '', html += "
"), html += "
", enableScrollX() ? html += '
' : html += '
', enableScrollX() && (html += "
"), html += "
", elem.innerHTML = html; + var itemsContainer = elem.querySelector(".itemsContainer"); + itemsContainer.fetchData = getFetchLatestItemsFn(apiClient.serverId(), parent.Id, parent.CollectionType), itemsContainer.getItemsHtml = getLatestItemsHtmlFn(parent.Type, parent.CollectionType), itemsContainer.parentContainer = elem + } + + function loadRecentlyAdded(elem, apiClient, user, userViews) { + elem.classList.remove("verticalSection"); + for (var excludeViewTypes = ["playlists", "livetv", "boxsets", "channels"], i = 0, length = userViews.length; i < length; i++) { + var item = userViews[i]; + if (-1 === user.Configuration.LatestItemsExcludes.indexOf(item.Id) && -1 === excludeViewTypes.indexOf(item.CollectionType || [])) { + var frag = document.createElement("div"); + frag.classList.add("verticalSection"), frag.classList.add("hide"), elem.appendChild(frag), renderLatestSection(frag, apiClient, user, item) + } + } + } + + function getRequirePromise(deps) { + return new Promise(function(resolve, reject) { + require(deps, resolve) + }) + } + + function showHomeScreenSettings(elem, options) { + return getRequirePromise(["homescreenSettingsDialog"]).then(function(homescreenSettingsDialog) { + return homescreenSettingsDialog.show(options).then(function() { + dom.parentWithClass(elem, "homeSectionsContainer").dispatchEvent(new CustomEvent("settingschange", { + cancelable: !1 + })) + }) + }) + } + + function bindHomeScreenSettingsIcon(elem, apiClient, userId, userSettings) { + var btnHomeScreenSettings = elem.querySelector(".btnHomeScreenSettings"); + btnHomeScreenSettings && btnHomeScreenSettings.addEventListener("click", function() { + showHomeScreenSettings(elem, { + serverId: apiClient.serverId(), + userId: userId, + userSettings: userSettings + }) + }) + } + + function getDownloadsSectionHtml(apiClient, user, userSettings) { + return appHost.supports("sync") && user.Policy.EnableContentDownloading ? (apiClient.getLatestOfflineItems ? apiClient.getLatestOfflineItems({ + Limit: 20, + Filters: "IsNotFolder" + }) : Promise.resolve([])).then(function(items) { + var html = ""; + return html += '
', html += '
', layoutManager.tv ? html += '

' + globalize.translate("sharedcomponents#HeaderMyDownloads") + "

" : (html += '', html += '

', html += globalize.translate("sharedcomponents#HeaderMyDownloads"), html += "

", html += '', html += "
", html += ''), html += "
", html += '
', html += cardBuilder.getCardsHtml({ + items: items, + preferThumb: "auto", + shape: "autooverflow", + overlayText: !1, + showTitle: !0, + showParentTitle: !0, + lazy: !0, + showDetailsMenu: !0, + overlayPlayButton: !0, + context: "home", + centerText: !0, + allowBottomPadding: !1, + cardLayout: !1, + showYear: !0, + lines: 2 + }), html += "
", html += "
" + }) : Promise.resolve("") + } + + function loadLibraryTiles(elem, apiClient, user, userSettings, shape, userViews, allSections) { + elem.classList.remove("verticalSection"); + var html = "", + scrollX = !layoutManager.desktop; + return userViews.length && (html += '
', html += '
', html += '

' + globalize.translate("sharedcomponents#HeaderMyMedia") + "

", layoutManager.tv || (html += ''), html += "
", html += scrollX ? '
' : '
', html += cardBuilder.getCardsHtml({ + items: userViews, + shape: scrollX ? "overflowSmallBackdrop" : shape, + showTitle: !0, + centerText: !0, + overlayText: !1, + lazy: !0, + transition: !1, + allowBottomPadding: !scrollX + }), scrollX && (html += "
"), html += "
", html += "
"), Promise.all([getAppInfo(apiClient), getDownloadsSectionHtml(apiClient, user, userSettings)]).then(function(responses) { + var infoHtml = responses[0], + downloadsHtml = responses[1]; + elem.innerHTML = html + downloadsHtml + infoHtml, bindHomeScreenSettingsIcon(elem, apiClient, user.Id, userSettings), infoHtml && bindAppInfoEvents(elem), imageLoader.lazyChildren(elem) + }) + } + + function getContinueWatchingFetchFn(serverId) { + return function() { + var limit, apiClient = connectionManager.getApiClient(serverId), + screenWidth = dom.getWindowSize().innerWidth; + enableScrollX() ? limit = 12 : (limit = screenWidth >= 1920 ? 8 : screenWidth >= 1600 ? 8 : screenWidth >= 1200 ? 9 : 6, limit = Math.min(limit, 5)); + var options = { + Limit: limit, + Recursive: !0, + Fields: "PrimaryImageAspectRatio,BasicSyncInfo", + ImageTypeLimit: 1, + EnableImageTypes: "Primary,Backdrop,Thumb", + EnableTotalRecordCount: !1, + MediaTypes: "Video" + }; + return apiClient.getResumableItems(apiClient.getCurrentUserId(), options) + } + } + + function getContinueWatchingItemsHtml(items) { + return cardBuilder.getCardsHtml({ + items: items, + preferThumb: !0, + shape: getThumbShape(), + overlayText: !1, + showTitle: !0, + showParentTitle: !0, + lazy: !0, + showDetailsMenu: !0, + overlayPlayButton: !0, + context: "home", + centerText: !0, + allowBottomPadding: !1, + cardLayout: !1, + showYear: !0, + lines: 2 + }) + } + + function loadResumeVideo(elem, apiClient, userId) { + var html = ""; + html += '

' + globalize.translate("sharedcomponents#HeaderContinueWatching") + "

", enableScrollX() ? html += '
' : html += '
', enableScrollX() && (html += "
"), html += "
", elem.classList.add("hide"), elem.innerHTML = html; + var itemsContainer = elem.querySelector(".itemsContainer"); + itemsContainer.fetchData = getContinueWatchingFetchFn(apiClient.serverId()), itemsContainer.getItemsHtml = getContinueWatchingItemsHtml, itemsContainer.parentContainer = elem + } + + function getContinueListeningFetchFn(serverId) { + return function() { + var limit, apiClient = connectionManager.getApiClient(serverId), + screenWidth = dom.getWindowSize().innerWidth; + enableScrollX() ? limit = 12 : (limit = screenWidth >= 1920 ? 8 : screenWidth >= 1600 ? 8 : screenWidth >= 1200 ? 9 : 6, limit = Math.min(limit, 5)); + var options = { + Limit: limit, + Recursive: !0, + Fields: "PrimaryImageAspectRatio,BasicSyncInfo", + ImageTypeLimit: 1, + EnableImageTypes: "Primary,Backdrop,Thumb", + EnableTotalRecordCount: !1, + MediaTypes: "Audio" + }; + return apiClient.getResumableItems(apiClient.getCurrentUserId(), options) + } + } + + function getContinueListeningItemsHtml(items) { + return cardBuilder.getCardsHtml({ + items: items, + preferThumb: !0, + shape: getThumbShape(), + overlayText: !1, + showTitle: !0, + showParentTitle: !0, + lazy: !0, + showDetailsMenu: !0, + overlayPlayButton: !0, + context: "home", + centerText: !0, + allowBottomPadding: !1, + cardLayout: !1, + showYear: !0, + lines: 2 + }) + } + + function loadResumeAudio(elem, apiClient, userId) { + var html = ""; + html += '

' + globalize.translate("sharedcomponents#HeaderContinueWatching") + "

", enableScrollX() ? html += '
' : html += '
', enableScrollX() && (html += "
"), html += "
", elem.classList.add("hide"), elem.innerHTML = html; + var itemsContainer = elem.querySelector(".itemsContainer"); + itemsContainer.fetchData = getContinueListeningFetchFn(apiClient.serverId()), itemsContainer.getItemsHtml = getContinueListeningItemsHtml, itemsContainer.parentContainer = elem + } + + function bindUnlockClick(elem) { + var btnUnlock = elem.querySelector(".btnUnlock"); + btnUnlock && btnUnlock.addEventListener("click", function(e) { + registrationServices.validateFeature("livetv", { + viewOnly: !0 + }).then(function() { + dom.parentWithClass(elem, "homeSectionsContainer").dispatchEvent(new CustomEvent("settingschange", { + cancelable: !1 + })) + }) + }) + } + + function getOnNowFetchFn(serverId) { + return function() { + var apiClient = connectionManager.getApiClient(serverId); + return apiClient.getLiveTvRecommendedPrograms({ + userId: apiClient.getCurrentUserId(), + IsAiring: !0, + limit: 24, + ImageTypeLimit: 1, + EnableImageTypes: "Primary,Thumb,Backdrop", + EnableTotalRecordCount: !1, + Fields: "ChannelInfo,PrimaryImageAspectRatio" + }) + } + } + + function getOnNowItemsHtml(items) { + return cardBuilder.getCardsHtml({ + items: items, + preferThumb: "auto", + inheritThumb: !1, + shape: enableScrollX() ? "autooverflow" : "auto", + showParentTitleOrTitle: !0, + showTitle: !0, + centerText: !0, + coverImage: !0, + overlayText: !1, + allowBottomPadding: !enableScrollX(), + showAirTime: !0, + showChannelName: !1, + showAirDateTime: !1, + showAirEndTime: !0, + defaultShape: getThumbShape(), + lines: 3, + overlayPlayButton: !0 + }) + } + + function loadOnNow(elem, apiClient, user) { + if (!user.Policy.EnableLiveTvAccess) return Promise.resolve(); + var promises = []; + promises.push(registrationServices.validateFeature("livetv", { + viewOnly: !0, + showDialog: !1 + }).then(function() { + return !0 + }, function() { + return !1 + })); + user.Id; + return promises.push(apiClient.getLiveTvRecommendedPrograms({ + userId: apiClient.getCurrentUserId(), + IsAiring: !0, + limit: 1, + ImageTypeLimit: 1, + EnableImageTypes: "Primary,Thumb,Backdrop", + EnableTotalRecordCount: !1, + Fields: "ChannelInfo,PrimaryImageAspectRatio" + })), Promise.all(promises).then(function(responses) { + var registered = responses[0], + result = responses[1], + html = ""; + if (result.Items.length && registered) { + elem.classList.remove("padded-left"), elem.classList.remove("padded-right"), elem.classList.remove("padded-bottom"), elem.classList.remove("verticalSection"), html += '
', html += '
', html += '

' + globalize.translate("sharedcomponents#LiveTV") + "

", html += "
", enableScrollX() ? (html += '", html += "
", html += '
', html += '
', layoutManager.tv ? html += '

' + globalize.translate("sharedcomponents#HeaderOnNow") + "

" : (html += '', html += '

', html += globalize.translate("sharedcomponents#HeaderOnNow"), html += "

", html += '', html += "
"), html += "
", enableScrollX() ? html += '
' : html += '
', enableScrollX() && (html += "
"), html += "
", html += "
", elem.innerHTML = html; + var itemsContainer = elem.querySelector(".itemsContainer"); + itemsContainer.parentContainer = elem, itemsContainer.fetchData = getOnNowFetchFn(apiClient.serverId()), itemsContainer.getItemsHtml = getOnNowItemsHtml + } else result.Items.length && !registered && (elem.classList.add("padded-left"), elem.classList.add("padded-right"), elem.classList.add("padded-bottom"), html += '

' + globalize.translate("sharedcomponents#LiveTvRequiresUnlock") + "

", html += '", elem.innerHTML = html); + bindUnlockClick(elem) + }) + } + + function getNextUpFetchFn(serverId) { + return function() { + var apiClient = connectionManager.getApiClient(serverId); + return apiClient.getNextUpEpisodes({ + Limit: enableScrollX() ? 24 : 15, + Fields: "PrimaryImageAspectRatio,SeriesInfo,DateCreated,BasicSyncInfo", + UserId: apiClient.getCurrentUserId(), + ImageTypeLimit: 1, + EnableImageTypes: "Primary,Backdrop,Banner,Thumb", + EnableTotalRecordCount: !1 + }) + } + } + + function getNextUpItemsHtml(items) { + return cardBuilder.getCardsHtml({ + items: items, + preferThumb: !0, + shape: getThumbShape(), + overlayText: !1, + showTitle: !0, + showParentTitle: !0, + lazy: !0, + overlayPlayButton: !0, + context: "home", + centerText: !0, + allowBottomPadding: !enableScrollX(), + cardLayout: !1 + }) + } + + function loadNextUp(elem, apiClient, userId) { + var html = ""; + html += '
', layoutManager.tv ? html += '

' + globalize.translate("sharedcomponents#HeaderNextUp") + "

" : (html += '', html += '

', html += globalize.translate("sharedcomponents#HeaderNextUp"), html += "

", html += '', html += "
"), html += "
", enableScrollX() ? html += '
' : html += '
', enableScrollX() && (html += "
"), html += "
", elem.classList.add("hide"), elem.innerHTML = html; + var itemsContainer = elem.querySelector(".itemsContainer"); + itemsContainer.fetchData = getNextUpFetchFn(apiClient.serverId()), itemsContainer.getItemsHtml = getNextUpItemsHtml, itemsContainer.parentContainer = elem + } + + function getLatestRecordingsFetchFn(serverId, activeRecordingsOnly) { + return function() { + var apiClient = connectionManager.getApiClient(serverId); + return apiClient.getLiveTvRecordings({ + userId: apiClient.getCurrentUserId(), + Limit: enableScrollX() ? 12 : 5, + Fields: "PrimaryImageAspectRatio,BasicSyncInfo", + EnableTotalRecordCount: !1, + IsLibraryItem: !!activeRecordingsOnly && null, + IsInProgress: !!activeRecordingsOnly || null + }) + } + } + + function getLatestRecordingItemsHtml(activeRecordingsOnly) { + return function(items) { + return cardBuilder.getCardsHtml({ + items: items, + shape: enableScrollX() ? "autooverflow" : "auto", + showTitle: !0, + showParentTitle: !0, + coverImage: !0, + lazy: !0, + showDetailsMenu: !0, + centerText: !0, + overlayText: !1, + showYear: !0, + lines: 2, + overlayPlayButton: !activeRecordingsOnly, + allowBottomPadding: !enableScrollX(), + preferThumb: !0, + cardLayout: !1, + overlayMoreButton: activeRecordingsOnly, + action: activeRecordingsOnly ? "none" : null, + centerPlayButton: activeRecordingsOnly + }) + } + } + + function loadLatestLiveTvRecordings(elem, activeRecordingsOnly, apiClient, userId) { + var title = activeRecordingsOnly ? globalize.translate("sharedcomponents#HeaderActiveRecordings") : globalize.translate("sharedcomponents#HeaderLatestRecordings"), + html = ""; + html += '
', html += '

' + title + "

", layoutManager.tv, html += "
", enableScrollX() ? html += '
' : html += '
', enableScrollX() && (html += "
"), html += "
", elem.classList.add("hide"), elem.innerHTML = html; + var itemsContainer = elem.querySelector(".itemsContainer"); + itemsContainer.fetchData = getLatestRecordingsFetchFn(apiClient.serverId(), activeRecordingsOnly), itemsContainer.getItemsHtml = getLatestRecordingItemsHtml(activeRecordingsOnly), itemsContainer.parentContainer = elem + } + return { + loadLibraryTiles: loadLibraryTiles, + getDefaultSection: getDefaultSection, + loadSections: loadSections, + destroySections: destroySections, + pause: pause, + resume: resume + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/htmlaudioplayer/plugin.js b/dashboard-ui/bower_components/emby-webcomponents/htmlaudioplayer/plugin.js index 7ba843ad92..e36ac4d469 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/htmlaudioplayer/plugin.js +++ b/dashboard-ui/bower_components/emby-webcomponents/htmlaudioplayer/plugin.js @@ -1 +1,218 @@ -define(["events","browser","require","apphost","appSettings","htmlMediaHelper"],function(events,browser,require,appHost,appSettings,htmlMediaHelper){"use strict";function getDefaultProfile(){return new Promise(function(resolve,reject){require(["browserdeviceprofile"],function(profileBuilder){resolve(profileBuilder({}))})})}function fade(instance,elem,startingVolume){instance._isFadingOut=!0;var newVolume=Math.max(0,startingVolume-.15);return console.log("fading volume to "+newVolume),elem.volume=newVolume,newVolume<=0?(instance._isFadingOut=!1,Promise.resolve()):new Promise(function(resolve,reject){cancelFadeTimeout(),fadeTimeout=setTimeout(function(){fade(instance,elem,newVolume).then(resolve,reject)},100)})}function cancelFadeTimeout(){var timeout=fadeTimeout;timeout&&(clearTimeout(timeout),fadeTimeout=null)}function supportsFade(){return!browser.tv}function requireHlsPlayer(callback){require(["hlsjs"],function(hls){window.Hls=hls,callback()})}function enableHlsPlayer(url,item,mediaSource,mediaType){return htmlMediaHelper.enableHlsJsPlayer(mediaSource.RunTimeTicks,mediaType)?-1!==url.indexOf(".m3u8")?Promise.resolve():new Promise(function(resolve,reject){require(["fetchHelper"],function(fetchHelper){fetchHelper.ajax({url:url,type:"HEAD"}).then(function(response){"application/x-mpegurl"===(response.headers.get("Content-Type")||"").toLowerCase()?resolve():reject()},reject)})}):Promise.reject()}function HtmlAudioPlayer(){function setCurrentSrc(elem,options){elem.removeEventListener("error",onError),unBindEvents(elem),bindEvents(elem);var val=options.url;console.log("playing url: "+val);var seconds=(options.playerStartPositionTicks||0)/1e7;seconds&&(val+="#t="+seconds),htmlMediaHelper.destroyHlsPlayer(self),self._currentPlayOptions=options;var crossOrigin=htmlMediaHelper.getCrossOriginValue(options.mediaSource);return crossOrigin&&(elem.crossOrigin=crossOrigin),enableHlsPlayer(val,options.item,options.mediaSource,"Audio").then(function(){return new Promise(function(resolve,reject){requireHlsPlayer(function(){var hls=new Hls({manifestLoadingTimeOut:2e4});hls.loadSource(val),hls.attachMedia(elem),htmlMediaHelper.bindEventsToHlsPlayer(self,hls,elem,onError,resolve,reject),self._hlsPlayer=hls,self._currentSrc=val})})},function(){return elem.autoplay=!0,htmlMediaHelper.applySrc(elem,val,options).then(function(){return self._currentSrc=val,htmlMediaHelper.playWithPromise(elem,onError)})})}function bindEvents(elem){elem.addEventListener("timeupdate",onTimeUpdate),elem.addEventListener("ended",onEnded),elem.addEventListener("volumechange",onVolumeChange),elem.addEventListener("pause",onPause),elem.addEventListener("playing",onPlaying),elem.addEventListener("play",onPlay)}function unBindEvents(elem){elem.removeEventListener("timeupdate",onTimeUpdate),elem.removeEventListener("ended",onEnded),elem.removeEventListener("volumechange",onVolumeChange),elem.removeEventListener("pause",onPause),elem.removeEventListener("playing",onPlaying),elem.removeEventListener("play",onPlay)}function createMediaElement(){var elem=self._mediaElement;return elem||(elem=document.querySelector(".mediaPlayerAudio"),elem||(elem=document.createElement("audio"),elem.classList.add("mediaPlayerAudio"),elem.classList.add("hide"),document.body.appendChild(elem)),elem.volume=htmlMediaHelper.getSavedVolume(),self._mediaElement=elem,elem)}function onEnded(){htmlMediaHelper.onEndedInternal(self,this,onError)}function onTimeUpdate(){var time=this.currentTime;self._isFadingOut||(self._currentTime=time,events.trigger(self,"timeupdate"))}function onVolumeChange(){self._isFadingOut||(htmlMediaHelper.saveVolume(this.volume),events.trigger(self,"volumechange"))}function onPlaying(e){self._started||(self._started=!0,this.removeAttribute("controls"),htmlMediaHelper.seekOnPlaybackStart(self,e.target,self._currentPlayOptions.playerStartPositionTicks)),events.trigger(self,"playing")}function onPlay(e){events.trigger(self,"unpause")}function onPause(){events.trigger(self,"pause")}function onError(){var errorCode=this.error?this.error.code||0:0,errorMessage=this.error?this.error.message||"":"";console.log("Media element error: "+errorCode.toString()+" "+errorMessage);var type;switch(errorCode){case 1:return;case 2:type="network";break;case 3:if(self._hlsPlayer)return void htmlMediaHelper.handleHlsJsMediaError(self);type="mediadecodeerror";break;case 4:type="medianotsupported";break;default:return}htmlMediaHelper.onErrorInternal(self,type)}var self=this;self.name="Html Audio Player",self.type="mediaplayer",self.id="htmlaudioplayer",self.priority=1,self.play=function(options){return self._started=!1,self._timeUpdated=!1,self._currentTime=null,setCurrentSrc(createMediaElement(),options)},self.stop=function(destroyPlayer){cancelFadeTimeout();var elem=self._mediaElement,src=self._currentSrc;if(elem&&src){if(!destroyPlayer||!supportsFade())return elem.pause(),htmlMediaHelper.onEndedInternal(self,elem,onError),destroyPlayer&&self.destroy(),Promise.resolve();var originalVolume=elem.volume;return fade(self,elem,elem.volume).then(function(){elem.pause(),elem.volume=originalVolume,htmlMediaHelper.onEndedInternal(self,elem,onError),destroyPlayer&&self.destroy()})}return Promise.resolve()},self.destroy=function(){unBindEvents(self._mediaElement)}}var fadeTimeout;return HtmlAudioPlayer.prototype.currentSrc=function(){return this._currentSrc},HtmlAudioPlayer.prototype.canPlayMediaType=function(mediaType){return"audio"===(mediaType||"").toLowerCase()},HtmlAudioPlayer.prototype.getDeviceProfile=function(item){return appHost.getDeviceProfile?appHost.getDeviceProfile(item):getDefaultProfile()},HtmlAudioPlayer.prototype.currentTime=function(val){var mediaElement=this._mediaElement;if(mediaElement){if(null!=val)return void(mediaElement.currentTime=val/1e3);var currentTime=this._currentTime;return currentTime?1e3*currentTime:1e3*(mediaElement.currentTime||0)}},HtmlAudioPlayer.prototype.duration=function(val){var mediaElement=this._mediaElement;if(mediaElement){var duration=mediaElement.duration;if(htmlMediaHelper.isValidDuration(duration))return 1e3*duration}return null},HtmlAudioPlayer.prototype.seekable=function(){var mediaElement=this._mediaElement;if(mediaElement){var seekable=mediaElement.seekable;if(seekable&&seekable.length){var start=seekable.start(0),end=seekable.end(0);return htmlMediaHelper.isValidDuration(start)||(start=0),htmlMediaHelper.isValidDuration(end)||(end=0),end-start>0}return!1}},HtmlAudioPlayer.prototype.getBufferedRanges=function(){var mediaElement=this._mediaElement;return mediaElement?htmlMediaHelper.getBufferedRanges(this,mediaElement):[]},HtmlAudioPlayer.prototype.pause=function(){var mediaElement=this._mediaElement;mediaElement&&mediaElement.pause()},HtmlAudioPlayer.prototype.resume=function(){var mediaElement=this._mediaElement;mediaElement&&mediaElement.play()},HtmlAudioPlayer.prototype.unpause=function(){var mediaElement=this._mediaElement;mediaElement&&mediaElement.play()},HtmlAudioPlayer.prototype.paused=function(){var mediaElement=this._mediaElement;return!!mediaElement&&mediaElement.paused},HtmlAudioPlayer.prototype.setVolume=function(val){var mediaElement=this._mediaElement;mediaElement&&(mediaElement.volume=val/100)},HtmlAudioPlayer.prototype.getVolume=function(){var mediaElement=this._mediaElement;if(mediaElement)return Math.min(Math.round(100*mediaElement.volume),100)},HtmlAudioPlayer.prototype.volumeUp=function(){this.setVolume(Math.min(this.getVolume()+2,100))},HtmlAudioPlayer.prototype.volumeDown=function(){this.setVolume(Math.max(this.getVolume()-2,0))},HtmlAudioPlayer.prototype.setMute=function(mute){var mediaElement=this._mediaElement;mediaElement&&(mediaElement.muted=mute)},HtmlAudioPlayer.prototype.isMuted=function(){var mediaElement=this._mediaElement;return!!mediaElement&&mediaElement.muted},HtmlAudioPlayer.prototype.destroy=function(){},HtmlAudioPlayer}); \ No newline at end of file +define(["events", "browser", "require", "apphost", "appSettings", "htmlMediaHelper"], function(events, browser, require, appHost, appSettings, htmlMediaHelper) { + "use strict"; + + function getDefaultProfile() { + return new Promise(function(resolve, reject) { + require(["browserdeviceprofile"], function(profileBuilder) { + resolve(profileBuilder({})) + }) + }) + } + + function fade(instance, elem, startingVolume) { + instance._isFadingOut = !0; + var newVolume = Math.max(0, startingVolume - .15); + return console.log("fading volume to " + newVolume), elem.volume = newVolume, newVolume <= 0 ? (instance._isFadingOut = !1, Promise.resolve()) : new Promise(function(resolve, reject) { + cancelFadeTimeout(), fadeTimeout = setTimeout(function() { + fade(instance, elem, newVolume).then(resolve, reject) + }, 100) + }) + } + + function cancelFadeTimeout() { + var timeout = fadeTimeout; + timeout && (clearTimeout(timeout), fadeTimeout = null) + } + + function supportsFade() { + return !browser.tv + } + + function requireHlsPlayer(callback) { + require(["hlsjs"], function(hls) { + window.Hls = hls, callback() + }) + } + + function enableHlsPlayer(url, item, mediaSource, mediaType) { + return htmlMediaHelper.enableHlsJsPlayer(mediaSource.RunTimeTicks, mediaType) ? -1 !== url.indexOf(".m3u8") ? Promise.resolve() : new Promise(function(resolve, reject) { + require(["fetchHelper"], function(fetchHelper) { + fetchHelper.ajax({ + url: url, + type: "HEAD" + }).then(function(response) { + "application/x-mpegurl" === (response.headers.get("Content-Type") || "").toLowerCase() ? resolve() : reject() + }, reject) + }) + }) : Promise.reject() + } + + function HtmlAudioPlayer() { + function setCurrentSrc(elem, options) { + elem.removeEventListener("error", onError), unBindEvents(elem), bindEvents(elem); + var val = options.url; + console.log("playing url: " + val); + var seconds = (options.playerStartPositionTicks || 0) / 1e7; + seconds && (val += "#t=" + seconds), htmlMediaHelper.destroyHlsPlayer(self), self._currentPlayOptions = options; + var crossOrigin = htmlMediaHelper.getCrossOriginValue(options.mediaSource); + return crossOrigin && (elem.crossOrigin = crossOrigin), enableHlsPlayer(val, options.item, options.mediaSource, "Audio").then(function() { + return new Promise(function(resolve, reject) { + requireHlsPlayer(function() { + var hls = new Hls({ + manifestLoadingTimeOut: 2e4 + }); + hls.loadSource(val), hls.attachMedia(elem), htmlMediaHelper.bindEventsToHlsPlayer(self, hls, elem, onError, resolve, reject), self._hlsPlayer = hls, self._currentSrc = val + }) + }) + }, function() { + return elem.autoplay = !0, htmlMediaHelper.applySrc(elem, val, options).then(function() { + return self._currentSrc = val, htmlMediaHelper.playWithPromise(elem, onError) + }) + }) + } + + function bindEvents(elem) { + elem.addEventListener("timeupdate", onTimeUpdate), elem.addEventListener("ended", onEnded), elem.addEventListener("volumechange", onVolumeChange), elem.addEventListener("pause", onPause), elem.addEventListener("playing", onPlaying), elem.addEventListener("play", onPlay) + } + + function unBindEvents(elem) { + elem.removeEventListener("timeupdate", onTimeUpdate), elem.removeEventListener("ended", onEnded), elem.removeEventListener("volumechange", onVolumeChange), elem.removeEventListener("pause", onPause), elem.removeEventListener("playing", onPlaying), elem.removeEventListener("play", onPlay) + } + + function createMediaElement() { + var elem = self._mediaElement; + return elem || (elem = document.querySelector(".mediaPlayerAudio"), elem || (elem = document.createElement("audio"), elem.classList.add("mediaPlayerAudio"), elem.classList.add("hide"), document.body.appendChild(elem)), elem.volume = htmlMediaHelper.getSavedVolume(), self._mediaElement = elem, elem) + } + + function onEnded() { + htmlMediaHelper.onEndedInternal(self, this, onError) + } + + function onTimeUpdate() { + var time = this.currentTime; + self._isFadingOut || (self._currentTime = time, events.trigger(self, "timeupdate")) + } + + function onVolumeChange() { + self._isFadingOut || (htmlMediaHelper.saveVolume(this.volume), events.trigger(self, "volumechange")) + } + + function onPlaying(e) { + self._started || (self._started = !0, this.removeAttribute("controls"), htmlMediaHelper.seekOnPlaybackStart(self, e.target, self._currentPlayOptions.playerStartPositionTicks)), events.trigger(self, "playing") + } + + function onPlay(e) { + events.trigger(self, "unpause") + } + + function onPause() { + events.trigger(self, "pause") + } + + function onError() { + var errorCode = this.error ? this.error.code || 0 : 0, + errorMessage = this.error ? this.error.message || "" : ""; + console.log("Media element error: " + errorCode.toString() + " " + errorMessage); + var type; + switch (errorCode) { + case 1: + return; + case 2: + type = "network"; + break; + case 3: + if (self._hlsPlayer) return void htmlMediaHelper.handleHlsJsMediaError(self); + type = "mediadecodeerror"; + break; + case 4: + type = "medianotsupported"; + break; + default: + return + } + htmlMediaHelper.onErrorInternal(self, type) + } + var self = this; + self.name = "Html Audio Player", self.type = "mediaplayer", self.id = "htmlaudioplayer", self.priority = 1, self.play = function(options) { + return self._started = !1, self._timeUpdated = !1, self._currentTime = null, setCurrentSrc(createMediaElement(), options) + }, self.stop = function(destroyPlayer) { + cancelFadeTimeout(); + var elem = self._mediaElement, + src = self._currentSrc; + if (elem && src) { + if (!destroyPlayer || !supportsFade()) return elem.pause(), htmlMediaHelper.onEndedInternal(self, elem, onError), destroyPlayer && self.destroy(), Promise.resolve(); + var originalVolume = elem.volume; + return fade(self, elem, elem.volume).then(function() { + elem.pause(), elem.volume = originalVolume, htmlMediaHelper.onEndedInternal(self, elem, onError), destroyPlayer && self.destroy() + }) + } + return Promise.resolve() + }, self.destroy = function() { + unBindEvents(self._mediaElement) + } + } + var fadeTimeout; + return HtmlAudioPlayer.prototype.currentSrc = function() { + return this._currentSrc + }, HtmlAudioPlayer.prototype.canPlayMediaType = function(mediaType) { + return "audio" === (mediaType || "").toLowerCase() + }, HtmlAudioPlayer.prototype.getDeviceProfile = function(item) { + return appHost.getDeviceProfile ? appHost.getDeviceProfile(item) : getDefaultProfile() + }, HtmlAudioPlayer.prototype.currentTime = function(val) { + var mediaElement = this._mediaElement; + if (mediaElement) { + if (null != val) return void(mediaElement.currentTime = val / 1e3); + var currentTime = this._currentTime; + return currentTime ? 1e3 * currentTime : 1e3 * (mediaElement.currentTime || 0) + } + }, HtmlAudioPlayer.prototype.duration = function(val) { + var mediaElement = this._mediaElement; + if (mediaElement) { + var duration = mediaElement.duration; + if (htmlMediaHelper.isValidDuration(duration)) return 1e3 * duration + } + return null + }, HtmlAudioPlayer.prototype.seekable = function() { + var mediaElement = this._mediaElement; + if (mediaElement) { + var seekable = mediaElement.seekable; + if (seekable && seekable.length) { + var start = seekable.start(0), + end = seekable.end(0); + return htmlMediaHelper.isValidDuration(start) || (start = 0), htmlMediaHelper.isValidDuration(end) || (end = 0), end - start > 0 + } + return !1 + } + }, HtmlAudioPlayer.prototype.getBufferedRanges = function() { + var mediaElement = this._mediaElement; + return mediaElement ? htmlMediaHelper.getBufferedRanges(this, mediaElement) : [] + }, HtmlAudioPlayer.prototype.pause = function() { + var mediaElement = this._mediaElement; + mediaElement && mediaElement.pause() + }, HtmlAudioPlayer.prototype.resume = function() { + var mediaElement = this._mediaElement; + mediaElement && mediaElement.play() + }, HtmlAudioPlayer.prototype.unpause = function() { + var mediaElement = this._mediaElement; + mediaElement && mediaElement.play() + }, HtmlAudioPlayer.prototype.paused = function() { + var mediaElement = this._mediaElement; + return !!mediaElement && mediaElement.paused + }, HtmlAudioPlayer.prototype.setVolume = function(val) { + var mediaElement = this._mediaElement; + mediaElement && (mediaElement.volume = val / 100) + }, HtmlAudioPlayer.prototype.getVolume = function() { + var mediaElement = this._mediaElement; + if (mediaElement) return Math.min(Math.round(100 * mediaElement.volume), 100) + }, HtmlAudioPlayer.prototype.volumeUp = function() { + this.setVolume(Math.min(this.getVolume() + 2, 100)) + }, HtmlAudioPlayer.prototype.volumeDown = function() { + this.setVolume(Math.max(this.getVolume() - 2, 0)) + }, HtmlAudioPlayer.prototype.setMute = function(mute) { + var mediaElement = this._mediaElement; + mediaElement && (mediaElement.muted = mute) + }, HtmlAudioPlayer.prototype.isMuted = function() { + var mediaElement = this._mediaElement; + return !!mediaElement && mediaElement.muted + }, HtmlAudioPlayer.prototype.destroy = function() {}, HtmlAudioPlayer +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/htmlvideoplayer/htmlmediahelper.js b/dashboard-ui/bower_components/emby-webcomponents/htmlvideoplayer/htmlmediahelper.js index 06a04c64e3..68bc1ecded 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/htmlvideoplayer/htmlmediahelper.js +++ b/dashboard-ui/bower_components/emby-webcomponents/htmlvideoplayer/htmlmediahelper.js @@ -1 +1,218 @@ -define(["appSettings","browser","events"],function(appSettings,browser,events){"use strict";function getSavedVolume(){return appSettings.get("volume")||1}function saveVolume(value){value&&appSettings.set("volume",value)}function getCrossOriginValue(mediaSource){return mediaSource.IsRemote?null:"anonymous"}function canPlayNativeHls(){var media=document.createElement("video");return!(!media.canPlayType("application/x-mpegURL").replace(/no/,"")&&!media.canPlayType("application/vnd.apple.mpegURL").replace(/no/,""))}function enableHlsShakaPlayer(item,mediaSource,mediaType){if(window.MediaSource&&MediaSource.isTypeSupported){if(canPlayNativeHls()){if(browser.edge&&"Video"===mediaType)return!0;mediaSource.RunTimeTicks}return!0}return!1}function enableHlsJsPlayer(runTimeTicks,mediaType){if(null==window.MediaSource)return!1;if(browser.iOS)return!1;if(browser.tizen||browser.web0s)return!1;if(canPlayNativeHls()){if(browser.android&&"Audio"===mediaType)return!0;if(browser.edge,runTimeTicks)return!1}return!0}function handleHlsJsMediaError(instance,reject){var hlsPlayer=instance._hlsPlayer;if(hlsPlayer){var now=Date.now();window.performance&&window.performance.now&&(now=performance.now()),!recoverDecodingErrorDate||now-recoverDecodingErrorDate>3e3?(recoverDecodingErrorDate=now,console.log("try to recover media Error ..."),hlsPlayer.recoverMediaError()):!recoverSwapAudioCodecDate||now-recoverSwapAudioCodecDate>3e3?(recoverSwapAudioCodecDate=now,console.log("try to swap Audio Codec and recover media Error ..."),hlsPlayer.swapAudioCodec(),hlsPlayer.recoverMediaError()):(console.error("cannot recover, last media error recovery failed ..."),reject?reject():onErrorInternal(instance,"mediadecodeerror"))}}function onErrorInternal(instance,type){instance.destroyCustomTrack&&instance.destroyCustomTrack(instance._mediaElement),events.trigger(instance,"error",[{type:type}])}function isValidDuration(duration){return!(!duration||isNaN(duration)||duration===Number.POSITIVE_INFINITY||duration===Number.NEGATIVE_INFINITY)}function setCurrentTimeIfNeeded(element,seconds,allowance){Math.abs((element.currentTime||0)-seconds)>=allowance&&(element.currentTime=seconds)}function seekOnPlaybackStart(instance,element,ticks){var seconds=(ticks||0)/1e7;if(seconds){(instance.currentSrc()||"").toLowerCase();setCurrentTimeIfNeeded(element,seconds,5),setTimeout(function(){setCurrentTimeIfNeeded(element,seconds,10)},2500)}}function applySrc(elem,src,options){return window.Windows&&options.mediaSource&&options.mediaSource.IsLocal?Windows.Storage.StorageFile.getFileFromPathAsync(options.url).then(function(file){var playlist=new Windows.Media.Playback.MediaPlaybackList,source1=Windows.Media.Core.MediaSource.createFromStorageFile(file),startTime=(options.playerStartPositionTicks||0)/1e4;return playlist.items.append(new Windows.Media.Playback.MediaPlaybackItem(source1,startTime)),elem.src=URL.createObjectURL(playlist,{oneTimeOnly:!0}),Promise.resolve()}):(elem.src=src,Promise.resolve())}function onSuccessfulPlay(elem,onErrorFn){elem.addEventListener("error",onErrorFn)}function playWithPromise(elem,onErrorFn){try{var promise=elem.play();return promise&&promise.then?promise.catch(function(e){var errorName=(e.name||"").toLowerCase();return"notallowederror"===errorName||"aborterror"===errorName?(onSuccessfulPlay(elem,onErrorFn),Promise.resolve()):Promise.reject()}):(onSuccessfulPlay(elem,onErrorFn),Promise.resolve())}catch(err){return console.log("error calling video.play: "+err),Promise.reject()}}function destroyCastPlayer(instance){var player=instance._castPlayer;if(player){try{player.unload()}catch(err){console.log(err)}instance._castPlayer=null}}function destroyShakaPlayer(instance){var player=instance._shakaPlayer;if(player){try{player.destroy()}catch(err){console.log(err)}instance._shakaPlayer=null}}function destroyHlsPlayer(instance){var player=instance._hlsPlayer;if(player){try{player.destroy()}catch(err){console.log(err)}instance._hlsPlayer=null}}function destroyFlvPlayer(instance){var player=instance._flvPlayer;if(player){try{player.unload(),player.detachMediaElement(),player.destroy()}catch(err){console.log(err)}instance._flvPlayer=null}}function bindEventsToHlsPlayer(instance,hls,elem,onErrorFn,resolve,reject){hls.on(Hls.Events.MANIFEST_PARSED,function(){playWithPromise(elem,onErrorFn).then(resolve,function(){reject&&(reject(),reject=null)})}),hls.on(Hls.Events.ERROR,function(event,data){switch(console.log("HLS Error: Type: "+data.type+" Details: "+(data.details||"")+" Fatal: "+(data.fatal||!1)),data.type){case Hls.ErrorTypes.NETWORK_ERROR:if(data.response&&data.response.code&&data.response.code>=400)return console.log("hls.js response error code: "+data.response.code),hls.destroy(),void(reject?(reject("servererror"),reject=null):onErrorInternal(instance,"servererror"))}if(data.fatal)switch(data.type){case Hls.ErrorTypes.NETWORK_ERROR:data.response&&0===data.response.code?(console.log("hls.js response error code: "+data.response.code),hls.destroy(),reject?(reject("network"),reject=null):onErrorInternal(instance,"network")):(console.log("fatal network error encountered, try to recover"),hls.startLoad());break;case Hls.ErrorTypes.MEDIA_ERROR:console.log("fatal media error encountered, try to recover");var currentReject=reject;reject=null,handleHlsJsMediaError(instance,currentReject);break;default:console.log("Cannot recover from hls error - destroy and trigger error"),hls.destroy(),reject?(reject(),reject=null):onErrorInternal(instance,"mediadecodeerror")}})}function onEndedInternal(instance,elem,onErrorFn){elem.removeEventListener("error",onErrorFn),elem.src="",elem.innerHTML="",elem.removeAttribute("src"),destroyHlsPlayer(instance),destroyFlvPlayer(instance),destroyShakaPlayer(instance),destroyCastPlayer(instance);var stopInfo={src:instance._currentSrc};events.trigger(instance,"stopped",[stopInfo]),instance._currentTime=null,instance._currentSrc=null,instance._currentPlayOptions=null}function getBufferedRanges(instance,elem){var offset,ranges=[],seekable=elem.buffered||[],currentPlayOptions=instance._currentPlayOptions;currentPlayOptions&&(offset=currentPlayOptions.transcodingOffsetTicks),offset=offset||0;for(var i=0,length=seekable.length;i 3e3 ? (recoverDecodingErrorDate = now, console.log("try to recover media Error ..."), hlsPlayer.recoverMediaError()) : !recoverSwapAudioCodecDate || now - recoverSwapAudioCodecDate > 3e3 ? (recoverSwapAudioCodecDate = now, console.log("try to swap Audio Codec and recover media Error ..."), hlsPlayer.swapAudioCodec(), hlsPlayer.recoverMediaError()) : (console.error("cannot recover, last media error recovery failed ..."), reject ? reject() : onErrorInternal(instance, "mediadecodeerror")) + } + } + + function onErrorInternal(instance, type) { + instance.destroyCustomTrack && instance.destroyCustomTrack(instance._mediaElement), events.trigger(instance, "error", [{ + type: type + }]) + } + + function isValidDuration(duration) { + return !(!duration || isNaN(duration) || duration === Number.POSITIVE_INFINITY || duration === Number.NEGATIVE_INFINITY) + } + + function setCurrentTimeIfNeeded(element, seconds, allowance) { + Math.abs((element.currentTime || 0) - seconds) >= allowance && (element.currentTime = seconds) + } + + function seekOnPlaybackStart(instance, element, ticks) { + var seconds = (ticks || 0) / 1e7; + if (seconds) { + (instance.currentSrc() || "").toLowerCase(); + setCurrentTimeIfNeeded(element, seconds, 5), setTimeout(function() { + setCurrentTimeIfNeeded(element, seconds, 10) + }, 2500) + } + } + + function applySrc(elem, src, options) { + return window.Windows && options.mediaSource && options.mediaSource.IsLocal ? Windows.Storage.StorageFile.getFileFromPathAsync(options.url).then(function(file) { + var playlist = new Windows.Media.Playback.MediaPlaybackList, + source1 = Windows.Media.Core.MediaSource.createFromStorageFile(file), + startTime = (options.playerStartPositionTicks || 0) / 1e4; + return playlist.items.append(new Windows.Media.Playback.MediaPlaybackItem(source1, startTime)), elem.src = URL.createObjectURL(playlist, { + oneTimeOnly: !0 + }), Promise.resolve() + }) : (elem.src = src, Promise.resolve()) + } + + function onSuccessfulPlay(elem, onErrorFn) { + elem.addEventListener("error", onErrorFn) + } + + function playWithPromise(elem, onErrorFn) { + try { + var promise = elem.play(); + return promise && promise.then ? promise.catch(function(e) { + var errorName = (e.name || "").toLowerCase(); + return "notallowederror" === errorName || "aborterror" === errorName ? (onSuccessfulPlay(elem, onErrorFn), Promise.resolve()) : Promise.reject() + }) : (onSuccessfulPlay(elem, onErrorFn), Promise.resolve()) + } catch (err) { + return console.log("error calling video.play: " + err), Promise.reject() + } + } + + function destroyCastPlayer(instance) { + var player = instance._castPlayer; + if (player) { + try { + player.unload() + } catch (err) { + console.log(err) + } + instance._castPlayer = null + } + } + + function destroyShakaPlayer(instance) { + var player = instance._shakaPlayer; + if (player) { + try { + player.destroy() + } catch (err) { + console.log(err) + } + instance._shakaPlayer = null + } + } + + function destroyHlsPlayer(instance) { + var player = instance._hlsPlayer; + if (player) { + try { + player.destroy() + } catch (err) { + console.log(err) + } + instance._hlsPlayer = null + } + } + + function destroyFlvPlayer(instance) { + var player = instance._flvPlayer; + if (player) { + try { + player.unload(), player.detachMediaElement(), player.destroy() + } catch (err) { + console.log(err) + } + instance._flvPlayer = null + } + } + + function bindEventsToHlsPlayer(instance, hls, elem, onErrorFn, resolve, reject) { + hls.on(Hls.Events.MANIFEST_PARSED, function() { + playWithPromise(elem, onErrorFn).then(resolve, function() { + reject && (reject(), reject = null) + }) + }), hls.on(Hls.Events.ERROR, function(event, data) { + switch (console.log("HLS Error: Type: " + data.type + " Details: " + (data.details || "") + " Fatal: " + (data.fatal || !1)), data.type) { + case Hls.ErrorTypes.NETWORK_ERROR: + if (data.response && data.response.code && data.response.code >= 400) return console.log("hls.js response error code: " + data.response.code), hls.destroy(), void(reject ? (reject("servererror"), reject = null) : onErrorInternal(instance, "servererror")) + } + if (data.fatal) switch (data.type) { + case Hls.ErrorTypes.NETWORK_ERROR: + data.response && 0 === data.response.code ? (console.log("hls.js response error code: " + data.response.code), hls.destroy(), reject ? (reject("network"), reject = null) : onErrorInternal(instance, "network")) : (console.log("fatal network error encountered, try to recover"), hls.startLoad()); + break; + case Hls.ErrorTypes.MEDIA_ERROR: + console.log("fatal media error encountered, try to recover"); + var currentReject = reject; + reject = null, handleHlsJsMediaError(instance, currentReject); + break; + default: + console.log("Cannot recover from hls error - destroy and trigger error"), hls.destroy(), reject ? (reject(), reject = null) : onErrorInternal(instance, "mediadecodeerror") + } + }) + } + + function onEndedInternal(instance, elem, onErrorFn) { + elem.removeEventListener("error", onErrorFn), elem.src = "", elem.innerHTML = "", elem.removeAttribute("src"), destroyHlsPlayer(instance), destroyFlvPlayer(instance), destroyShakaPlayer(instance), destroyCastPlayer(instance); + var stopInfo = { + src: instance._currentSrc + }; + events.trigger(instance, "stopped", [stopInfo]), instance._currentTime = null, instance._currentSrc = null, instance._currentPlayOptions = null + } + + function getBufferedRanges(instance, elem) { + var offset, ranges = [], + seekable = elem.buffered || [], + currentPlayOptions = instance._currentPlayOptions; + currentPlayOptions && (offset = currentPlayOptions.transcodingOffsetTicks), offset = offset || 0; + for (var i = 0, length = seekable.length; i < length; i++) { + var start = seekable.start(i), + end = seekable.end(i); + isValidDuration(start) || (start = 0), isValidDuration(end) ? ranges.push({ + start: 1e7 * start + offset, + end: 1e7 * end + offset + }) : end = 0 + } + return ranges + } + var recoverDecodingErrorDate, recoverSwapAudioCodecDate; + return { + getSavedVolume: getSavedVolume, + saveVolume: saveVolume, + enableHlsJsPlayer: enableHlsJsPlayer, + enableHlsShakaPlayer: enableHlsShakaPlayer, + handleHlsJsMediaError: handleHlsJsMediaError, + isValidDuration: isValidDuration, + onErrorInternal: onErrorInternal, + seekOnPlaybackStart: seekOnPlaybackStart, + applySrc: applySrc, + playWithPromise: playWithPromise, + destroyHlsPlayer: destroyHlsPlayer, + destroyFlvPlayer: destroyFlvPlayer, + destroyCastPlayer: destroyCastPlayer, + bindEventsToHlsPlayer: bindEventsToHlsPlayer, + onEndedInternal: onEndedInternal, + getCrossOriginValue: getCrossOriginValue, + getBufferedRanges: getBufferedRanges + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/htmlvideoplayer/plugin.js b/dashboard-ui/bower_components/emby-webcomponents/htmlvideoplayer/plugin.js index 9552fb0725..35313d6782 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/htmlvideoplayer/plugin.js +++ b/dashboard-ui/bower_components/emby-webcomponents/htmlvideoplayer/plugin.js @@ -1 +1,699 @@ -define(["browser","require","events","apphost","loading","dom","playbackManager","appRouter","appSettings","connectionManager","htmlMediaHelper","itemHelper"],function(browser,require,events,appHost,loading,dom,playbackManager,appRouter,appSettings,connectionManager,htmlMediaHelper,itemHelper){"use strict";function tryRemoveElement(elem){var parentNode=elem.parentNode;if(parentNode)try{parentNode.removeChild(elem)}catch(err){console.log("Error removing dialog element: "+err)}}function enableNativeTrackSupport(currentSrc,track){if(track&&"Embed"===track.DeliveryMethod)return!0;if(browser.firefox&&-1!==(currentSrc||"").toLowerCase().indexOf(".m3u8"))return!1;if(browser.chromecast&&-1!==(currentSrc||"").toLowerCase().indexOf(".m3u8"))return!1;if(browser.ps4)return!1;if(browser.web0s)return!1;if(browser.edge)return!1;if(browser.iOS&&(browser.iosVersion||10)<10)return!1;if(track){var format=(track.Codec||"").toLowerCase();if("ssa"===format||"ass"===format)return!1}return!0}function requireHlsPlayer(callback){require(["hlsjs"],function(hls){window.Hls=hls,callback()})}function getMediaStreamAudioTracks(mediaSource){return mediaSource.MediaStreams.filter(function(s){return"Audio"===s.Type})}function getMediaStreamTextTracks(mediaSource){return mediaSource.MediaStreams.filter(function(s){return"Subtitle"===s.Type})}function zoomIn(elem){return new Promise(function(resolve,reject){elem.style.animation="htmlvideoplayer-zoomin 240ms ease-in normal",dom.addEventListener(elem,dom.whichAnimationEvent(),resolve,{once:!0})})}function normalizeTrackEventText(text){return text.replace(/\\N/gi,"\n")}function setTracks(elem,tracks,item,mediaSource){elem.innerHTML=getTracksHtml(tracks,item,mediaSource)}function getTextTrackUrl(track,item,format){if(itemHelper.isLocalItem(item)&&track.Path)return track.Path;var url=playbackManager.getSubtitleUrl(track,item.ServerId);return format&&(url=url.replace(".vtt",format)),url}function getTracksHtml(tracks,item,mediaSource){return tracks.map(function(t){if("External"!==t.DeliveryMethod)return"";var defaultAttribute=mediaSource.DefaultSubtitleStreamIndex===t.Index?" default":"",language=t.Language||"und",label=t.Language||"und";return'"}).join("")}function getDefaultProfile(){return new Promise(function(resolve,reject){require(["browserdeviceprofile"],function(profileBuilder){resolve(profileBuilder({}))})})}function HtmlVideoPlayer(){function updateVideoUrl(streamInfo){var isHls=-1!==streamInfo.url.toLowerCase().indexOf(".m3u8"),mediaSource=streamInfo.mediaSource,item=streamInfo.item;if(mediaSource&&item&&!mediaSource.RunTimeTicks&&isHls&&"Transcode"===streamInfo.playMethod&&(browser.iOS||browser.osx)){var hlsPlaylistUrl=streamInfo.url.replace("master.m3u8","live.m3u8");return loading.show(),console.log("prefetching hls playlist: "+hlsPlaylistUrl),connectionManager.getApiClient(item.ServerId).ajax({type:"GET",url:hlsPlaylistUrl}).then(function(){return console.log("completed prefetching hls playlist: "+hlsPlaylistUrl),loading.hide(),streamInfo.url=hlsPlaylistUrl,Promise.resolve()},function(){return console.log("error prefetching hls playlist: "+hlsPlaylistUrl),loading.hide(),Promise.resolve()})}return Promise.resolve()}function setSrcWithFlvJs(instance,elem,options,url){return new Promise(function(resolve,reject){require(["flvjs"],function(flvjs){var flvPlayer=flvjs.createPlayer({type:"flv",url:url},{seekType:"range",lazyLoad:!1});flvPlayer.attachMediaElement(elem),flvPlayer.load(),flvPlayer.play().then(resolve,reject),instance._flvPlayer=flvPlayer,self._currentSrc=url})})}function setSrcWithHlsJs(instance,elem,options,url){return new Promise(function(resolve,reject){requireHlsPlayer(function(){var hls=new Hls({manifestLoadingTimeOut:2e4});hls.loadSource(url),hls.attachMedia(elem),htmlMediaHelper.bindEventsToHlsPlayer(self,hls,elem,onError,resolve,reject),self._hlsPlayer=hls,self._currentSrc=url})})}function setCurrentSrcChromecast(instance,elem,options,url){elem.autoplay=!0;var lrd=new cast.receiver.MediaManager.LoadRequestData;lrd.currentTime=(options.playerStartPositionTicks||0)/1e7,lrd.autoplay=!0,lrd.media=new cast.receiver.media.MediaInformation,lrd.media.contentId=url,lrd.media.contentType=options.mimeType,lrd.media.streamType=cast.receiver.media.StreamType.OTHER,lrd.media.customData=options,console.log("loading media url into mediaManager");try{return mediaManager.load(lrd),self._currentSrc=url,Promise.resolve()}catch(err){return console.log("mediaManager error: "+err),Promise.reject()}}function onMediaManagerLoadMedia(event){self._castPlayer&&self._castPlayer.unload(),self._castPlayer=null;var protocol,data=event.data,media=event.data.media||{},url=media.contentId,contentType=media.contentType.toLowerCase(),mediaElement=(media.customData,self._mediaElement),host=new cast.player.api.Host({url:url,mediaElement:mediaElement});protocol=cast.player.api.CreateHlsStreamingProtocol(host),console.log("loading playback url: "+url),console.log("contentType: "+contentType),host.onError=function(errorCode){console.log("Fatal Error - "+errorCode)},mediaElement.autoplay=!1,self._castPlayer=new cast.player.api.Player(host),self._castPlayer.load(protocol,data.currentTime||0),self._castPlayer.playWhenHaveEnoughData()}function initMediaManager(){mediaManager.defaultOnLoad=mediaManager.onLoad.bind(mediaManager),mediaManager.onLoad=onMediaManagerLoadMedia.bind(self),mediaManager.defaultOnStop=mediaManager.onStop.bind(mediaManager),mediaManager.onStop=function(event){playbackManager.stop(),mediaManager.defaultOnStop(event)}}function setCurrentSrc(elem,options){elem.removeEventListener("error",onError);var val=options.url;console.log("playing url: "+val);var seconds=(options.playerStartPositionTicks||0)/1e7;seconds&&(val+="#t="+seconds),htmlMediaHelper.destroyHlsPlayer(self),htmlMediaHelper.destroyFlvPlayer(self),htmlMediaHelper.destroyCastPlayer(self);var tracks=getMediaStreamTextTracks(options.mediaSource);if(null!=(subtitleTrackIndexToSetOnPlaying=null==options.mediaSource.DefaultSubtitleStreamIndex?-1:options.mediaSource.DefaultSubtitleStreamIndex)&&subtitleTrackIndexToSetOnPlaying>=0){var initialSubtitleStream=options.mediaSource.MediaStreams[subtitleTrackIndexToSetOnPlaying];initialSubtitleStream&&"Encode"!==initialSubtitleStream.DeliveryMethod||(subtitleTrackIndexToSetOnPlaying=-1)}audioTrackIndexToSetOnPlaying="Transcode"===options.playMethod?null:options.mediaSource.DefaultAudioStreamIndex,self._currentPlayOptions=options;var crossOrigin=htmlMediaHelper.getCrossOriginValue(options.mediaSource);return crossOrigin&&(elem.crossOrigin=crossOrigin),browser.chromecast&&-1!==val.indexOf(".m3u8")&&options.mediaSource.RunTimeTicks?(setTracks(elem,tracks,options.item,options.mediaSource),setCurrentSrcChromecast(self,elem,options,val)):htmlMediaHelper.enableHlsJsPlayer(options.mediaSource.RunTimeTicks,"Video")&&-1!==val.indexOf(".m3u8")?(setTracks(elem,tracks,options.item,options.mediaSource),setSrcWithHlsJs(self,elem,options,val)):"Transcode"!==options.playMethod&&"flv"===options.mediaSource.Container?(setTracks(elem,tracks,options.item,options.mediaSource),setSrcWithFlvJs(self,elem,options,val)):(elem.autoplay=!0,htmlMediaHelper.applySrc(elem,val,options).then(function(){return setTracks(elem,tracks,options.item,options.mediaSource),self._currentSrc=val,htmlMediaHelper.playWithPromise(elem,onError)}))}function isAudioStreamSupported(stream,deviceProfile){var codec=(stream.Codec||"").toLowerCase();return!codec||(!deviceProfile||(deviceProfile.DirectPlayProfiles||[]).filter(function(p){return"Video"===p.Type&&(!p.AudioCodec||-1!==p.AudioCodec.toLowerCase().indexOf(codec))}).length>0)}function getSupportedAudioStreams(){var profile=self._lastProfile;return getMediaStreamAudioTracks(self._currentPlayOptions.mediaSource).filter(function(stream){return isAudioStreamSupported(stream,profile)})}function onEnded(){destroyCustomTrack(this),htmlMediaHelper.onEndedInternal(self,this,onError)}function onTimeUpdate(e){var time=this.currentTime;time&&!self._timeUpdated&&(self._timeUpdated=!0,ensureValidVideo(this)),self._currentTime=time;var currentPlayOptions=self._currentPlayOptions;if(currentPlayOptions){var timeMs=1e3*time;timeMs+=(currentPlayOptions.transcodingOffsetTicks||0)/1e4,updateSubtitleText(timeMs)}events.trigger(self,"timeupdate")}function onVolumeChange(){htmlMediaHelper.saveVolume(this.volume),events.trigger(self,"volumechange")}function onNavigatedToOsd(){var dlg=videoDialog;dlg&&(dlg.classList.remove("videoPlayerContainer-withBackdrop"),dlg.classList.remove("videoPlayerContainer-onTop"),onStartedAndNavigatedToOsd())}function onStartedAndNavigatedToOsd(){setCurrentTrackElement(subtitleTrackIndexToSetOnPlaying),null!=audioTrackIndexToSetOnPlaying&&self.canSetAudioStreamIndex()&&self.setAudioStreamIndex(audioTrackIndexToSetOnPlaying)}function onPlaying(e){self._started||(self._started=!0,this.removeAttribute("controls"),loading.hide(),htmlMediaHelper.seekOnPlaybackStart(self,e.target,self._currentPlayOptions.playerStartPositionTicks),self._currentPlayOptions.fullscreen?appRouter.showVideoOsd().then(onNavigatedToOsd):(appRouter.setTransparency("backdrop"),videoDialog.classList.remove("videoPlayerContainer-withBackdrop"),videoDialog.classList.remove("videoPlayerContainer-onTop"),onStartedAndNavigatedToOsd())),events.trigger(self,"playing")}function onPlay(e){events.trigger(self,"unpause")}function ensureValidVideo(elem){if(elem===self._mediaElement&&0===elem.videoWidth&&0===elem.videoHeight){var mediaSource=(self._currentPlayOptions||{}).mediaSource;if(!mediaSource||mediaSource.RunTimeTicks)return void htmlMediaHelper.onErrorInternal(self,"mediadecodeerror")}}function onClick(){events.trigger(self,"click")}function onDblClick(){events.trigger(self,"dblclick")}function onPause(){events.trigger(self,"pause")}function onError(){var errorCode=this.error?this.error.code||0:0,errorMessage=this.error?this.error.message||"":"";console.log("Media element error: "+errorCode.toString()+" "+errorMessage);var type;switch(errorCode){case 1:return;case 2:type="network";break;case 3:if(self._hlsPlayer)return void htmlMediaHelper.handleHlsJsMediaError(self);type="mediadecodeerror";break;case 4:type="medianotsupported";break;default:return}htmlMediaHelper.onErrorInternal(self,type)}function destroyCustomTrack(videoElement){if(self._resizeObserver&&(self._resizeObserver.disconnect(),self._resizeObserver=null),videoSubtitlesElem){var subtitlesContainer=videoSubtitlesElem.parentNode;subtitlesContainer&&tryRemoveElement(subtitlesContainer),videoSubtitlesElem=null}if(currentTrackEvents=null,videoElement)for(var allTracks=videoElement.textTracks||[],i=0;i
',videoSubtitlesElem=subtitlesContainer.querySelector(".videoSubtitlesInner"),setSubtitleAppearance(subtitlesContainer,videoSubtitlesElem),videoElement.parentNode.appendChild(subtitlesContainer),currentTrackEvents=data.TrackEvents}})}function setSubtitleAppearance(elem,innerElem){require(["userSettings","subtitleAppearanceHelper"],function(userSettings,subtitleAppearanceHelper){subtitleAppearanceHelper.applyStyles({text:innerElem,window:elem},userSettings.getSubtitleAppearanceSettings())})}function getCueCss(appearance,selector){var html=selector+"::cue {";return html+=appearance.text.map(function(s){return s.name+":"+s.value+"!important;"}).join(""),html+="}"}function setCueAppearance(){require(["userSettings","subtitleAppearanceHelper"],function(userSettings,subtitleAppearanceHelper){var elementId=self.id+"-cuestyle",styleElem=document.querySelector("#"+elementId);styleElem||(styleElem=document.createElement("style"),styleElem.id=elementId,styleElem.type="text/css",document.getElementsByTagName("head")[0].appendChild(styleElem)),styleElem.innerHTML=getCueCss(subtitleAppearanceHelper.getStyles(userSettings.getSubtitleAppearanceSettings(),!0),".htmlvideoplayer")})}function renderTracksEvents(videoElement,track,item){if(!itemHelper.isLocalItem(item)||track.IsExternal){var format=(track.Codec||"").toLowerCase();if("ssa"===format||"ass"===format)return void renderWithLibjass(videoElement,track,item);if(requiresCustomSubtitlesElement())return void renderSubtitlesWithCustomElement(videoElement,track,item)}for(var trackElement=null,expectedId="manualTrack"+track.Index,allTracks=videoElement.textTracks,i=0;i=ticks){selectedTrackEvent=currentTrackEvent;break}}selectedTrackEvent&&selectedTrackEvent.Text?(subtitleTextElement.innerHTML=normalizeTrackEventText(selectedTrackEvent.Text),subtitleTextElement.classList.remove("hide")):subtitleTextElement.classList.add("hide")}}}function setCurrentTrackElement(streamIndex){console.log("Setting new text track index to: "+streamIndex);var mediaStreamTextTracks=getMediaStreamTextTracks(self._currentPlayOptions.mediaSource),track=-1===streamIndex?null:mediaStreamTextTracks.filter(function(t){return t.Index===streamIndex})[0];enableNativeTrackSupport(self._currentSrc,track)?(setTrackForCustomDisplay(self._mediaElement,null),-1!==streamIndex&&setCueAppearance()):(setTrackForCustomDisplay(self._mediaElement,track),streamIndex=-1,track=null);for(var expectedId="textTrack"+streamIndex,trackIndex=-1!==streamIndex&&track?mediaStreamTextTracks.indexOf(track):-1,modes=["disabled","showing","hidden"],allTracks=self._mediaElement.textTracks,i=0;i':html+='",dlg.innerHTML=html;var videoElement=dlg.querySelector("video");videoElement.volume=htmlMediaHelper.getSavedVolume(),videoElement.addEventListener("timeupdate",onTimeUpdate),videoElement.addEventListener("ended",onEnded),videoElement.addEventListener("volumechange",onVolumeChange),videoElement.addEventListener("pause",onPause),videoElement.addEventListener("playing",onPlaying),videoElement.addEventListener("play",onPlay),videoElement.addEventListener("click",onClick),videoElement.addEventListener("dblclick",onDblClick),document.body.insertBefore(dlg,document.body.firstChild),videoDialog=dlg,self._mediaElement=videoElement,mediaManager&&(mediaManager.embyInit||(initMediaManager(),mediaManager.embyInit=!0),mediaManager.setMediaElement(videoElement)),options.fullscreen&&browser.supportsCssAnimation()&&!browser.slow?zoomIn(dlg).then(function(){resolve(videoElement)}):resolve(videoElement)})})}browser.edgeUwp?this.name="Windows Video Player":this.name="Html Video Player",this.type="mediaplayer",this.id="htmlvideoplayer",this.priority=1;var videoDialog,subtitleTrackIndexToSetOnPlaying,audioTrackIndexToSetOnPlaying,currentClock,currentAssRenderer,videoSubtitlesElem,currentTrackEvents,lastCustomTrackMs=0,customTrackIndex=-1,self=this;self.currentSrc=function(){return self._currentSrc},self.play=function(options){return browser.msie&&"Transcode"===options.playMethod&&!window.MediaSource?(alert("Playback of this content is not supported in Internet Explorer. For a better experience, try a modern browser such as Microsoft Edge, Google Chrome, Firefox or Opera."),Promise.reject()):(self._started=!1,self._timeUpdated=!1,self._currentTime=null,createMediaElement(options).then(function(elem){return updateVideoUrl(options,options.mediaSource).then(function(){return setCurrentSrc(elem,options)})}))},self.setSubtitleStreamIndex=function(index){setCurrentTrackElement(index)},self.setAudioStreamIndex=function(index){var streams=getSupportedAudioStreams();if(!(streams.length<2)){var i,length,stream,audioIndex=-1;for(i=0,length=streams.length;i=100?"none":rawValue/100;elem.style["-webkit-filter"]="brightness("+cssValue+");",elem.style.filter="brightness("+cssValue+")",elem.brightnessValue=val,events.trigger(this,"brightnesschange")}},HtmlVideoPlayer.prototype.getBrightness=function(){var elem=this._mediaElement;if(elem){var val=elem.brightnessValue;return null==val?100:val}},HtmlVideoPlayer.prototype.seekable=function(){var mediaElement=this._mediaElement;if(mediaElement){var seekable=mediaElement.seekable;if(seekable&&seekable.length){var start=seekable.start(0),end=seekable.end(0);return htmlMediaHelper.isValidDuration(start)||(start=0),htmlMediaHelper.isValidDuration(end)||(end=0),end-start>0}return!1}},HtmlVideoPlayer.prototype.pause=function(){var mediaElement=this._mediaElement;mediaElement&&mediaElement.pause()},HtmlVideoPlayer.prototype.resume=function(){var mediaElement=this._mediaElement;mediaElement&&mediaElement.play()},HtmlVideoPlayer.prototype.unpause=function(){var mediaElement=this._mediaElement;mediaElement&&mediaElement.play()},HtmlVideoPlayer.prototype.paused=function(){var mediaElement=this._mediaElement;return!!mediaElement&&mediaElement.paused},HtmlVideoPlayer.prototype.setVolume=function(val){var mediaElement=this._mediaElement;mediaElement&&(mediaElement.volume=val/100)},HtmlVideoPlayer.prototype.getVolume=function(){var mediaElement=this._mediaElement;if(mediaElement)return Math.min(Math.round(100*mediaElement.volume),100)},HtmlVideoPlayer.prototype.volumeUp=function(){this.setVolume(Math.min(this.getVolume()+2,100))},HtmlVideoPlayer.prototype.volumeDown=function(){this.setVolume(Math.max(this.getVolume()-2,0))},HtmlVideoPlayer.prototype.setMute=function(mute){var mediaElement=this._mediaElement;mediaElement&&(mediaElement.muted=mute)},HtmlVideoPlayer.prototype.isMuted=function(){var mediaElement=this._mediaElement;return!!mediaElement&&mediaElement.muted},HtmlVideoPlayer.prototype.setAspectRatio=function(val){},HtmlVideoPlayer.prototype.getAspectRatio=function(){return this._currentAspectRatio},HtmlVideoPlayer.prototype.getSupportedAspectRatios=function(){return[]},HtmlVideoPlayer.prototype.togglePictureInPicture=function(){return this.setPictureInPictureEnabled(!this.isPictureInPictureEnabled())},HtmlVideoPlayer.prototype.getBufferedRanges=function(){var mediaElement=this._mediaElement;return mediaElement?htmlMediaHelper.getBufferedRanges(this,mediaElement):[]},HtmlVideoPlayer.prototype.getStats=function(){var mediaElement=this._mediaElement,playOptions=this._currentPlayOptions||[],categories=[];if(!mediaElement)return Promise.resolve({categories:categories});var mediaCategory={stats:[],type:"media"};if(categories.push(mediaCategory),playOptions.url){var link=document.createElement("a");link.setAttribute("href",playOptions.url);var protocol=(link.protocol||"").replace(":","");protocol&&mediaCategory.stats.push({label:"Protocol:",value:protocol}),link=null}this._hlsPlayer||this._shakaPlayer?mediaCategory.stats.push({label:"Stream type:",value:"HLS"}):mediaCategory.stats.push({label:"Stream type:",value:"Video"});var videoCategory={stats:[],type:"video"};categories.push(videoCategory);var rect=mediaElement.getBoundingClientRect?mediaElement.getBoundingClientRect():{},height=rect.height,width=rect.width;if(width&&height&&!browser.tv&&videoCategory.stats.push({label:"Player dimensions:",value:width+"x"+height}),height=mediaElement.videoHeight,width=mediaElement.videoWidth,width&&height&&videoCategory.stats.push({label:"Video resolution:",value:width+"x"+height}),mediaElement.getVideoPlaybackQuality){var playbackQuality=mediaElement.getVideoPlaybackQuality(),droppedVideoFrames=playbackQuality.droppedVideoFrames||0;videoCategory.stats.push({label:"Dropped frames:",value:droppedVideoFrames});var corruptedVideoFrames=playbackQuality.corruptedVideoFrames||0;videoCategory.stats.push({label:"Corrupted frames:",value:corruptedVideoFrames})}var audioCategory={stats:[],type:"audio"};categories.push(audioCategory);var sinkId=mediaElement.sinkId;return sinkId&&audioCategory.stats.push({label:"Sink Id:",value:sinkId}),Promise.resolve({categories:categories})},browser.chromecast&&(mediaManager=new cast.receiver.MediaManager(document.createElement("video"))),HtmlVideoPlayer}); \ No newline at end of file +define(["browser", "require", "events", "apphost", "loading", "dom", "playbackManager", "appRouter", "appSettings", "connectionManager", "htmlMediaHelper", "itemHelper"], function(browser, require, events, appHost, loading, dom, playbackManager, appRouter, appSettings, connectionManager, htmlMediaHelper, itemHelper) { + "use strict"; + + function tryRemoveElement(elem) { + var parentNode = elem.parentNode; + if (parentNode) try { + parentNode.removeChild(elem) + } catch (err) { + console.log("Error removing dialog element: " + err) + } + } + + function enableNativeTrackSupport(currentSrc, track) { + if (track && "Embed" === track.DeliveryMethod) return !0; + if (browser.firefox && -1 !== (currentSrc || "").toLowerCase().indexOf(".m3u8")) return !1; + if (browser.chromecast && -1 !== (currentSrc || "").toLowerCase().indexOf(".m3u8")) return !1; + if (browser.ps4) return !1; + if (browser.web0s) return !1; + if (browser.edge) return !1; + if (browser.iOS && (browser.iosVersion || 10) < 10) return !1; + if (track) { + var format = (track.Codec || "").toLowerCase(); + if ("ssa" === format || "ass" === format) return !1 + } + return !0 + } + + function requireHlsPlayer(callback) { + require(["hlsjs"], function(hls) { + window.Hls = hls, callback() + }) + } + + function getMediaStreamAudioTracks(mediaSource) { + return mediaSource.MediaStreams.filter(function(s) { + return "Audio" === s.Type + }) + } + + function getMediaStreamTextTracks(mediaSource) { + return mediaSource.MediaStreams.filter(function(s) { + return "Subtitle" === s.Type + }) + } + + function zoomIn(elem) { + return new Promise(function(resolve, reject) { + elem.style.animation = "htmlvideoplayer-zoomin 240ms ease-in normal", dom.addEventListener(elem, dom.whichAnimationEvent(), resolve, { + once: !0 + }) + }) + } + + function normalizeTrackEventText(text) { + return text.replace(/\\N/gi, "\n") + } + + function setTracks(elem, tracks, item, mediaSource) { + elem.innerHTML = getTracksHtml(tracks, item, mediaSource) + } + + function getTextTrackUrl(track, item, format) { + if (itemHelper.isLocalItem(item) && track.Path) return track.Path; + var url = playbackManager.getSubtitleUrl(track, item.ServerId); + return format && (url = url.replace(".vtt", format)), url + } + + function getTracksHtml(tracks, item, mediaSource) { + return tracks.map(function(t) { + if ("External" !== t.DeliveryMethod) return ""; + var defaultAttribute = mediaSource.DefaultSubtitleStreamIndex === t.Index ? " default" : "", + language = t.Language || "und", + label = t.Language || "und"; + return '" + }).join("") + } + + function getDefaultProfile() { + return new Promise(function(resolve, reject) { + require(["browserdeviceprofile"], function(profileBuilder) { + resolve(profileBuilder({})) + }) + }) + } + + function HtmlVideoPlayer() { + function updateVideoUrl(streamInfo) { + var isHls = -1 !== streamInfo.url.toLowerCase().indexOf(".m3u8"), + mediaSource = streamInfo.mediaSource, + item = streamInfo.item; + if (mediaSource && item && !mediaSource.RunTimeTicks && isHls && "Transcode" === streamInfo.playMethod && (browser.iOS || browser.osx)) { + var hlsPlaylistUrl = streamInfo.url.replace("master.m3u8", "live.m3u8"); + return loading.show(), console.log("prefetching hls playlist: " + hlsPlaylistUrl), connectionManager.getApiClient(item.ServerId).ajax({ + type: "GET", + url: hlsPlaylistUrl + }).then(function() { + return console.log("completed prefetching hls playlist: " + hlsPlaylistUrl), loading.hide(), streamInfo.url = hlsPlaylistUrl, Promise.resolve() + }, function() { + return console.log("error prefetching hls playlist: " + hlsPlaylistUrl), loading.hide(), Promise.resolve() + }) + } + return Promise.resolve() + } + + function setSrcWithFlvJs(instance, elem, options, url) { + return new Promise(function(resolve, reject) { + require(["flvjs"], function(flvjs) { + var flvPlayer = flvjs.createPlayer({ + type: "flv", + url: url + }, { + seekType: "range", + lazyLoad: !1 + }); + flvPlayer.attachMediaElement(elem), flvPlayer.load(), flvPlayer.play().then(resolve, reject), instance._flvPlayer = flvPlayer, self._currentSrc = url + }) + }) + } + + function setSrcWithHlsJs(instance, elem, options, url) { + return new Promise(function(resolve, reject) { + requireHlsPlayer(function() { + var hls = new Hls({ + manifestLoadingTimeOut: 2e4 + }); + hls.loadSource(url), hls.attachMedia(elem), htmlMediaHelper.bindEventsToHlsPlayer(self, hls, elem, onError, resolve, reject), self._hlsPlayer = hls, self._currentSrc = url + }) + }) + } + + function setCurrentSrcChromecast(instance, elem, options, url) { + elem.autoplay = !0; + var lrd = new cast.receiver.MediaManager.LoadRequestData; + lrd.currentTime = (options.playerStartPositionTicks || 0) / 1e7, lrd.autoplay = !0, lrd.media = new cast.receiver.media.MediaInformation, lrd.media.contentId = url, lrd.media.contentType = options.mimeType, lrd.media.streamType = cast.receiver.media.StreamType.OTHER, lrd.media.customData = options, console.log("loading media url into mediaManager"); + try { + return mediaManager.load(lrd), self._currentSrc = url, Promise.resolve() + } catch (err) { + return console.log("mediaManager error: " + err), Promise.reject() + } + } + + function onMediaManagerLoadMedia(event) { + self._castPlayer && self._castPlayer.unload(), self._castPlayer = null; + var protocol, data = event.data, + media = event.data.media || {}, + url = media.contentId, + contentType = media.contentType.toLowerCase(), + mediaElement = (media.customData, self._mediaElement), + host = new cast.player.api.Host({ + url: url, + mediaElement: mediaElement + }); + protocol = cast.player.api.CreateHlsStreamingProtocol(host), console.log("loading playback url: " + url), console.log("contentType: " + contentType), host.onError = function(errorCode) { + console.log("Fatal Error - " + errorCode) + }, mediaElement.autoplay = !1, self._castPlayer = new cast.player.api.Player(host), self._castPlayer.load(protocol, data.currentTime || 0), self._castPlayer.playWhenHaveEnoughData() + } + + function initMediaManager() { + mediaManager.defaultOnLoad = mediaManager.onLoad.bind(mediaManager), mediaManager.onLoad = onMediaManagerLoadMedia.bind(self), mediaManager.defaultOnStop = mediaManager.onStop.bind(mediaManager), mediaManager.onStop = function(event) { + playbackManager.stop(), mediaManager.defaultOnStop(event) + } + } + + function setCurrentSrc(elem, options) { + elem.removeEventListener("error", onError); + var val = options.url; + console.log("playing url: " + val); + var seconds = (options.playerStartPositionTicks || 0) / 1e7; + seconds && (val += "#t=" + seconds), htmlMediaHelper.destroyHlsPlayer(self), htmlMediaHelper.destroyFlvPlayer(self), htmlMediaHelper.destroyCastPlayer(self); + var tracks = getMediaStreamTextTracks(options.mediaSource); + if (null != (subtitleTrackIndexToSetOnPlaying = null == options.mediaSource.DefaultSubtitleStreamIndex ? -1 : options.mediaSource.DefaultSubtitleStreamIndex) && subtitleTrackIndexToSetOnPlaying >= 0) { + var initialSubtitleStream = options.mediaSource.MediaStreams[subtitleTrackIndexToSetOnPlaying]; + initialSubtitleStream && "Encode" !== initialSubtitleStream.DeliveryMethod || (subtitleTrackIndexToSetOnPlaying = -1) + } + audioTrackIndexToSetOnPlaying = "Transcode" === options.playMethod ? null : options.mediaSource.DefaultAudioStreamIndex, self._currentPlayOptions = options; + var crossOrigin = htmlMediaHelper.getCrossOriginValue(options.mediaSource); + return crossOrigin && (elem.crossOrigin = crossOrigin), browser.chromecast && -1 !== val.indexOf(".m3u8") && options.mediaSource.RunTimeTicks ? (setTracks(elem, tracks, options.item, options.mediaSource), setCurrentSrcChromecast(self, elem, options, val)) : htmlMediaHelper.enableHlsJsPlayer(options.mediaSource.RunTimeTicks, "Video") && -1 !== val.indexOf(".m3u8") ? (setTracks(elem, tracks, options.item, options.mediaSource), setSrcWithHlsJs(self, elem, options, val)) : "Transcode" !== options.playMethod && "flv" === options.mediaSource.Container ? (setTracks(elem, tracks, options.item, options.mediaSource), setSrcWithFlvJs(self, elem, options, val)) : (elem.autoplay = !0, htmlMediaHelper.applySrc(elem, val, options).then(function() { + return setTracks(elem, tracks, options.item, options.mediaSource), self._currentSrc = val, htmlMediaHelper.playWithPromise(elem, onError) + })) + } + + function isAudioStreamSupported(stream, deviceProfile) { + var codec = (stream.Codec || "").toLowerCase(); + return !codec || (!deviceProfile || (deviceProfile.DirectPlayProfiles || []).filter(function(p) { + return "Video" === p.Type && (!p.AudioCodec || -1 !== p.AudioCodec.toLowerCase().indexOf(codec)) + }).length > 0) + } + + function getSupportedAudioStreams() { + var profile = self._lastProfile; + return getMediaStreamAudioTracks(self._currentPlayOptions.mediaSource).filter(function(stream) { + return isAudioStreamSupported(stream, profile) + }) + } + + function onEnded() { + destroyCustomTrack(this), htmlMediaHelper.onEndedInternal(self, this, onError) + } + + function onTimeUpdate(e) { + var time = this.currentTime; + time && !self._timeUpdated && (self._timeUpdated = !0, ensureValidVideo(this)), self._currentTime = time; + var currentPlayOptions = self._currentPlayOptions; + if (currentPlayOptions) { + var timeMs = 1e3 * time; + timeMs += (currentPlayOptions.transcodingOffsetTicks || 0) / 1e4, updateSubtitleText(timeMs) + } + events.trigger(self, "timeupdate") + } + + function onVolumeChange() { + htmlMediaHelper.saveVolume(this.volume), events.trigger(self, "volumechange") + } + + function onNavigatedToOsd() { + var dlg = videoDialog; + dlg && (dlg.classList.remove("videoPlayerContainer-withBackdrop"), dlg.classList.remove("videoPlayerContainer-onTop"), onStartedAndNavigatedToOsd()) + } + + function onStartedAndNavigatedToOsd() { + setCurrentTrackElement(subtitleTrackIndexToSetOnPlaying), null != audioTrackIndexToSetOnPlaying && self.canSetAudioStreamIndex() && self.setAudioStreamIndex(audioTrackIndexToSetOnPlaying) + } + + function onPlaying(e) { + self._started || (self._started = !0, this.removeAttribute("controls"), loading.hide(), htmlMediaHelper.seekOnPlaybackStart(self, e.target, self._currentPlayOptions.playerStartPositionTicks), self._currentPlayOptions.fullscreen ? appRouter.showVideoOsd().then(onNavigatedToOsd) : (appRouter.setTransparency("backdrop"), videoDialog.classList.remove("videoPlayerContainer-withBackdrop"), videoDialog.classList.remove("videoPlayerContainer-onTop"), onStartedAndNavigatedToOsd())), events.trigger(self, "playing") + } + + function onPlay(e) { + events.trigger(self, "unpause") + } + + function ensureValidVideo(elem) { + if (elem === self._mediaElement && 0 === elem.videoWidth && 0 === elem.videoHeight) { + var mediaSource = (self._currentPlayOptions || {}).mediaSource; + if (!mediaSource || mediaSource.RunTimeTicks) return void htmlMediaHelper.onErrorInternal(self, "mediadecodeerror") + } + } + + function onClick() { + events.trigger(self, "click") + } + + function onDblClick() { + events.trigger(self, "dblclick") + } + + function onPause() { + events.trigger(self, "pause") + } + + function onError() { + var errorCode = this.error ? this.error.code || 0 : 0, + errorMessage = this.error ? this.error.message || "" : ""; + console.log("Media element error: " + errorCode.toString() + " " + errorMessage); + var type; + switch (errorCode) { + case 1: + return; + case 2: + type = "network"; + break; + case 3: + if (self._hlsPlayer) return void htmlMediaHelper.handleHlsJsMediaError(self); + type = "mediadecodeerror"; + break; + case 4: + type = "medianotsupported"; + break; + default: + return + } + htmlMediaHelper.onErrorInternal(self, type) + } + + function destroyCustomTrack(videoElement) { + if (self._resizeObserver && (self._resizeObserver.disconnect(), self._resizeObserver = null), videoSubtitlesElem) { + var subtitlesContainer = videoSubtitlesElem.parentNode; + subtitlesContainer && tryRemoveElement(subtitlesContainer), videoSubtitlesElem = null + } + if (currentTrackEvents = null, videoElement) + for (var allTracks = videoElement.textTracks || [], i = 0; i < allTracks.length; i++) { + var currentTrack = allTracks[i]; - 1 !== currentTrack.label.indexOf("manualTrack") && (currentTrack.mode = "disabled") + } + customTrackIndex = -1, currentClock = null, self._currentAspectRatio = null; + var renderer = currentAssRenderer; + renderer && renderer.setEnabled(!1), currentAssRenderer = null + } + + function fetchSubtitlesUwp(track, item) { + return Windows.Storage.StorageFile.getFileFromPathAsync(track.Path).then(function(storageFile) { + return Windows.Storage.FileIO.readTextAsync(storageFile).then(function(text) { + return JSON.parse(text) + }) + }) + } + + function fetchSubtitles(track, item) { + return window.Windows && itemHelper.isLocalItem(item) ? fetchSubtitlesUwp(track, item) : new Promise(function(resolve, reject) { + var xhr = new XMLHttpRequest, + url = getTextTrackUrl(track, item, ".js"); + xhr.open("GET", url, !0), xhr.onload = function(e) { + resolve(JSON.parse(this.response)) + }, xhr.onerror = reject, xhr.send() + }) + } + + function setTrackForCustomDisplay(videoElement, track) { + if (!track) return void destroyCustomTrack(videoElement); + if (customTrackIndex !== track.Index) { + var item = self._currentPlayOptions.item; + destroyCustomTrack(videoElement), customTrackIndex = track.Index, renderTracksEvents(videoElement, track, item), lastCustomTrackMs = 0 + } + } + + function renderWithLibjass(videoElement, track, item) { + var rendererSettings = {}; + browser.ps4 ? rendererSettings.enableSvg = !1 : (browser.edge || browser.msie) && (rendererSettings.enableSvg = !1), rendererSettings.enableSvg = !1, require(["libjass", "ResizeObserver"], function(libjass, ResizeObserver) { + libjass.ASS.fromUrl(getTextTrackUrl(track, item)).then(function(ass) { + var clock = new libjass.renderers.ManualClock; + currentClock = clock; + var renderer = new libjass.renderers.WebRenderer(ass, clock, videoElement.parentNode, rendererSettings); + currentAssRenderer = renderer, renderer.addEventListener("ready", function() { + try { + renderer.resize(videoElement.offsetWidth, videoElement.offsetHeight, 0, 0), self._resizeObserver || (self._resizeObserver = new ResizeObserver(onVideoResize, {}), self._resizeObserver.observe(videoElement)) + } catch (ex) {} + }) + }, function() { + htmlMediaHelper.onErrorInternal(self, "mediadecodeerror") + }) + }) + } + + function onVideoResize() { + browser.iOS ? setTimeout(resetVideoRendererSize, 500) : resetVideoRendererSize() + } + + function resetVideoRendererSize() { + var renderer = currentAssRenderer; + if (renderer) { + var videoElement = self._mediaElement, + width = videoElement.offsetWidth, + height = videoElement.offsetHeight; + console.log("videoElement resized: " + width + "x" + height), renderer.resize(width, height, 0, 0) + } + } + + function requiresCustomSubtitlesElement() { + if (browser.ps4) return !0; + if (browser.firefox || browser.web0s) return !0; + if (browser.edge) return !0; + if (browser.iOS) { + var userAgent = navigator.userAgent.toLowerCase(); + if ((-1 !== userAgent.indexOf("os 9") || -1 !== userAgent.indexOf("os 8")) && -1 === userAgent.indexOf("safari")) return !0 + } + return !1 + } + + function renderSubtitlesWithCustomElement(videoElement, track, item) { + fetchSubtitles(track, item).then(function(data) { + if (!videoSubtitlesElem) { + var subtitlesContainer = document.createElement("div"); + subtitlesContainer.classList.add("videoSubtitles"), subtitlesContainer.innerHTML = '
', videoSubtitlesElem = subtitlesContainer.querySelector(".videoSubtitlesInner"), setSubtitleAppearance(subtitlesContainer, videoSubtitlesElem), videoElement.parentNode.appendChild(subtitlesContainer), currentTrackEvents = data.TrackEvents + } + }) + } + + function setSubtitleAppearance(elem, innerElem) { + require(["userSettings", "subtitleAppearanceHelper"], function(userSettings, subtitleAppearanceHelper) { + subtitleAppearanceHelper.applyStyles({ + text: innerElem, + window: elem + }, userSettings.getSubtitleAppearanceSettings()) + }) + } + + function getCueCss(appearance, selector) { + var html = selector + "::cue {"; + return html += appearance.text.map(function(s) { + return s.name + ":" + s.value + "!important;" + }).join(""), html += "}" + } + + function setCueAppearance() { + require(["userSettings", "subtitleAppearanceHelper"], function(userSettings, subtitleAppearanceHelper) { + var elementId = self.id + "-cuestyle", + styleElem = document.querySelector("#" + elementId); + styleElem || (styleElem = document.createElement("style"), styleElem.id = elementId, styleElem.type = "text/css", document.getElementsByTagName("head")[0].appendChild(styleElem)), styleElem.innerHTML = getCueCss(subtitleAppearanceHelper.getStyles(userSettings.getSubtitleAppearanceSettings(), !0), ".htmlvideoplayer") + }) + } + + function renderTracksEvents(videoElement, track, item) { + if (!itemHelper.isLocalItem(item) || track.IsExternal) { + var format = (track.Codec || "").toLowerCase(); + if ("ssa" === format || "ass" === format) return void renderWithLibjass(videoElement, track, item); + if (requiresCustomSubtitlesElement()) return void renderSubtitlesWithCustomElement(videoElement, track, item) + } + for (var trackElement = null, expectedId = "manualTrack" + track.Index, allTracks = videoElement.textTracks, i = 0; i < allTracks.length; i++) { + var currentTrack = allTracks[i]; + if (currentTrack.label === expectedId) { + trackElement = currentTrack; + break + } + currentTrack.mode = "disabled" + } + trackElement ? trackElement.mode = "showing" : (trackElement = videoElement.addTextTrack("subtitles", "manualTrack" + track.Index, track.Language || "und"), fetchSubtitles(track, item).then(function(data) { + console.log("downloaded " + data.TrackEvents.length + " track events"), data.TrackEvents.forEach(function(trackEvent) { + var trackCueObject = window.VTTCue || window.TextTrackCue, + cue = new trackCueObject(trackEvent.StartPositionTicks / 1e7, trackEvent.EndPositionTicks / 1e7, normalizeTrackEventText(trackEvent.Text)); + trackElement.addCue(cue) + }), trackElement.mode = "showing" + })) + } + + function updateSubtitleText(timeMs) { + var clock = currentClock; + if (clock) try { + clock.seek(timeMs / 1e3) + } catch (err) { + console.log("Error in libjass: " + err) + } else { + var trackEvents = currentTrackEvents, + subtitleTextElement = videoSubtitlesElem; + if (trackEvents && subtitleTextElement) { + for (var selectedTrackEvent, ticks = 1e4 * timeMs, i = 0; i < trackEvents.length; i++) { + var currentTrackEvent = trackEvents[i]; + if (currentTrackEvent.StartPositionTicks <= ticks && currentTrackEvent.EndPositionTicks >= ticks) { + selectedTrackEvent = currentTrackEvent; + break + } + } + selectedTrackEvent && selectedTrackEvent.Text ? (subtitleTextElement.innerHTML = normalizeTrackEventText(selectedTrackEvent.Text), subtitleTextElement.classList.remove("hide")) : subtitleTextElement.classList.add("hide") + } + } + } + + function setCurrentTrackElement(streamIndex) { + console.log("Setting new text track index to: " + streamIndex); + var mediaStreamTextTracks = getMediaStreamTextTracks(self._currentPlayOptions.mediaSource), + track = -1 === streamIndex ? null : mediaStreamTextTracks.filter(function(t) { + return t.Index === streamIndex + })[0]; + enableNativeTrackSupport(self._currentSrc, track) ? (setTrackForCustomDisplay(self._mediaElement, null), -1 !== streamIndex && setCueAppearance()) : (setTrackForCustomDisplay(self._mediaElement, track), streamIndex = -1, track = null); + for (var expectedId = "textTrack" + streamIndex, trackIndex = -1 !== streamIndex && track ? mediaStreamTextTracks.indexOf(track) : -1, modes = ["disabled", "showing", "hidden"], allTracks = self._mediaElement.textTracks, i = 0; i < allTracks.length; i++) { + var currentTrack = allTracks[i]; + console.log("currentTrack id: " + currentTrack.id); + var mode; + if (console.log("expectedId: " + expectedId + "--currentTrack.Id:" + currentTrack.id), browser.msie || browser.edge) mode = trackIndex === i ? 1 : 0; + else { + if (-1 !== currentTrack.label.indexOf("manualTrack")) continue; + mode = currentTrack.id === expectedId ? 1 : 0 + } + console.log("Setting track " + i + " mode to: " + mode), currentTrack.mode = modes[mode] + } + } + + function createMediaElement(options) { + return (browser.tv || browser.iOS || browser.mobile) && (options.backdropUrl = null), new Promise(function(resolve, reject) { + var dlg = document.querySelector(".videoPlayerContainer"); + dlg ? (options.backdropUrl && (dlg.classList.add("videoPlayerContainer-withBackdrop"), dlg.style.backgroundImage = "url('" + options.backdropUrl + "')"), resolve(dlg.querySelector("video"))) : require(["css!./style"], function() { + loading.show(); + var dlg = document.createElement("div"); + dlg.classList.add("videoPlayerContainer"), options.backdropUrl && (dlg.classList.add("videoPlayerContainer-withBackdrop"), dlg.style.backgroundImage = "url('" + options.backdropUrl + "')"), options.fullscreen && dlg.classList.add("videoPlayerContainer-onTop"); + var html = "", + cssClass = "htmlvideoplayer"; + browser.chromecast || (cssClass += " htmlvideoplayer-moveupsubtitles"), appHost.supports("htmlvideoautoplay") ? html += '
"),html+="
",html+="
",html+=""}function initEditor(page,apiClient){page.querySelector("#selectBrowsableImageType").addEventListener("change",function(){browsableImageType=this.value,browsableImageStartIndex=0,selectedProvider=null,reloadBrowsableImages(page,apiClient)}),page.querySelector("#selectImageProvider").addEventListener("change",function(){browsableImageStartIndex=0,selectedProvider=this.value,reloadBrowsableImages(page,apiClient)}),page.querySelector("#chkAllLanguages").addEventListener("change",function(){browsableImageStartIndex=0,reloadBrowsableImages(page,apiClient)}),page.addEventListener("click",function(e){var btnDownloadRemoteImage=parentWithClass(e.target,"btnDownloadRemoteImage");if(btnDownloadRemoteImage){var card=parentWithClass(btnDownloadRemoteImage,"card");return void downloadRemoteImage(page,apiClient,card.getAttribute("data-imageurl"),card.getAttribute("data-imagetype"),card.getAttribute("data-imageprovider"))}var btnImageCard=parentWithClass(e.target,"btnImageCard");btnImageCard&&downloadRemoteImage(page,apiClient,btnImageCard.getAttribute("data-imageurl"),btnImageCard.getAttribute("data-imagetype"),btnImageCard.getAttribute("data-imageprovider"))})}function showEditor(itemId,serverId,itemType){loading.show(),require(["text!./imagedownloader.template.html"],function(template){var apiClient=connectionManager.getApiClient(serverId);currentItemId=itemId,currentItemType=itemType;var dialogOptions={removeOnClose:!0};layoutManager.tv?dialogOptions.size="fullscreen":dialogOptions.size="fullscreen-border";var dlg=dialogHelper.createDialog(dialogOptions);dlg.innerHTML=globalize.translateDocument(template,"sharedcomponents"),layoutManager.tv&&scrollHelper.centerFocus.on(dlg,!1),dlg.addEventListener("close",onDialogClosed),dialogHelper.open(dlg);var editorContent=dlg.querySelector(".formDialogContent");initEditor(editorContent,apiClient),dlg.querySelector(".btnCancel").addEventListener("click",function(){dialogHelper.close(dlg)}),reloadBrowsableImages(editorContent,apiClient)})}function onDialogClosed(){var dlg=this;layoutManager.tv&&scrollHelper.centerFocus.off(dlg,!1),loading.hide(),hasChanges?currentResolve():currentReject()}var currentItemId,currentItemType,currentResolve,currentReject,selectedProvider,hasChanges=!1,browsableImagePageSize=browser.slow?6:30,browsableImageStartIndex=0,browsableImageType="Primary";return{show:function(itemId,serverId,itemType,imageType){return new Promise(function(resolve,reject){currentResolve=resolve,currentReject=reject,hasChanges=!1,browsableImageStartIndex=0,browsableImageType=imageType||"Primary",selectedProvider=null,showEditor(itemId,serverId,itemType)})}}}); \ No newline at end of file +define(["loading", "apphost", "dialogHelper", "connectionManager", "imageLoader", "browser", "layoutManager", "scrollHelper", "globalize", "require", "emby-checkbox", "emby-button", "paper-icon-button-light", "emby-linkbutton", "formDialogStyle", "cardStyle"], function(loading, appHost, dialogHelper, connectionManager, imageLoader, browser, layoutManager, scrollHelper, globalize, require) { + "use strict"; + + function getBaseRemoteOptions() { + var options = {}; + return options.itemId = currentItemId, options + } + + function reloadBrowsableImages(page, apiClient) { + loading.show(); + var options = getBaseRemoteOptions(); + options.type = browsableImageType, options.startIndex = browsableImageStartIndex, options.limit = browsableImagePageSize, options.IncludeAllLanguages = page.querySelector("#chkAllLanguages").checked; + var provider = selectedProvider || ""; + provider && (options.ProviderName = provider), apiClient.getAvailableRemoteImages(options).then(function(result) { + renderRemoteImages(page, apiClient, result, browsableImageType, options.startIndex, options.limit), page.querySelector("#selectBrowsableImageType").value = browsableImageType; + var providersHtml = result.Providers.map(function(p) { + return '" + }), + selectImageProvider = page.querySelector("#selectImageProvider"); + selectImageProvider.innerHTML = '" + providersHtml, selectImageProvider.value = provider, loading.hide() + }) + } + + function renderRemoteImages(page, apiClient, imagesResult, imageType, startIndex, limit) { + page.querySelector(".availableImagesPaging").innerHTML = getPagingHtml(startIndex, limit, imagesResult.TotalRecordCount); + for (var html = "", i = 0, length = imagesResult.Images.length; i < length; i++) html += getRemoteImageHtml(imagesResult.Images[i], imageType, apiClient); + var availableImagesList = page.querySelector(".availableImagesList"); + availableImagesList.innerHTML = html, imageLoader.lazyChildren(availableImagesList); + var btnNextPage = page.querySelector(".btnNextPage"), + btnPreviousPage = page.querySelector(".btnPreviousPage"); + btnNextPage && btnNextPage.addEventListener("click", function() { + browsableImageStartIndex += browsableImagePageSize, reloadBrowsableImages(page, apiClient) + }), btnPreviousPage && btnPreviousPage.addEventListener("click", function() { + browsableImageStartIndex -= browsableImagePageSize, reloadBrowsableImages(page, apiClient) + }) + } + + function getPagingHtml(startIndex, limit, totalRecordCount) { + var html = "", + recordsEnd = Math.min(startIndex + limit, totalRecordCount), + showControls = totalRecordCount > limit; + return html += '
', html += '', html += (totalRecordCount ? startIndex + 1 : 0) + "-" + recordsEnd + " of " + totalRecordCount, html += "", showControls && (html += '
', html += '', html += '', html += "
"), html += "
" + } + + function parentWithClass(elem, className) { + for (; !elem.classList || !elem.classList.contains(className);) + if (!(elem = elem.parentNode)) return null; + return elem + } + + function downloadRemoteImage(page, apiClient, url, type, provider) { + var options = getBaseRemoteOptions(); + options.Type = type, options.ImageUrl = url, options.ProviderName = provider, loading.show(), apiClient.downloadRemoteImage(options).then(function() { + hasChanges = !0; + var dlg = parentWithClass(page, "dialog"); + dialogHelper.close(dlg) + }) + } + + function getDisplayUrl(url, apiClient) { + return apiClient.getUrl("Images/Remote", { + imageUrl: url + }) + } + + function getRemoteImageHtml(image, imageType, apiClient) { + var tagName = layoutManager.tv ? "button" : "div", + enableFooterButtons = !layoutManager.tv, + html = "", + cssClass = "card scalableCard imageEditorCard", + cardBoxCssClass = "cardBox visualCardBox", + shape = "backdrop"; + return shape = "Backdrop" === imageType || "Art" === imageType || "Thumb" === imageType || "Logo" === imageType ? "backdrop" : "Banner" === imageType ? "banner" : "Disc" === imageType ? "square" : "Episode" === currentItemType ? "backdrop" : "MusicAlbum" === currentItemType || "MusicArtist" === currentItemType ? "square" : "portrait", cssClass += " " + shape + "Card " + shape + "Card-scalable", "button" === tagName ? (cssClass += " btnImageCard", layoutManager.tv && !browser.slow && (cardBoxCssClass += " cardBox-focustransform"), layoutManager.tv && (cardBoxCssClass += " card-focuscontent cardBox-withfocuscontent"), html += '', html += "
"), html += "
", html += "
", html += "" + } + + function initEditor(page, apiClient) { + page.querySelector("#selectBrowsableImageType").addEventListener("change", function() { + browsableImageType = this.value, browsableImageStartIndex = 0, selectedProvider = null, reloadBrowsableImages(page, apiClient) + }), page.querySelector("#selectImageProvider").addEventListener("change", function() { + browsableImageStartIndex = 0, selectedProvider = this.value, reloadBrowsableImages(page, apiClient) + }), page.querySelector("#chkAllLanguages").addEventListener("change", function() { + browsableImageStartIndex = 0, reloadBrowsableImages(page, apiClient) + }), page.addEventListener("click", function(e) { + var btnDownloadRemoteImage = parentWithClass(e.target, "btnDownloadRemoteImage"); + if (btnDownloadRemoteImage) { + var card = parentWithClass(btnDownloadRemoteImage, "card"); + return void downloadRemoteImage(page, apiClient, card.getAttribute("data-imageurl"), card.getAttribute("data-imagetype"), card.getAttribute("data-imageprovider")) + } + var btnImageCard = parentWithClass(e.target, "btnImageCard"); + btnImageCard && downloadRemoteImage(page, apiClient, btnImageCard.getAttribute("data-imageurl"), btnImageCard.getAttribute("data-imagetype"), btnImageCard.getAttribute("data-imageprovider")) + }) + } + + function showEditor(itemId, serverId, itemType) { + loading.show(), require(["text!./imagedownloader.template.html"], function(template) { + var apiClient = connectionManager.getApiClient(serverId); + currentItemId = itemId, currentItemType = itemType; + var dialogOptions = { + removeOnClose: !0 + }; + layoutManager.tv ? dialogOptions.size = "fullscreen" : dialogOptions.size = "fullscreen-border"; + var dlg = dialogHelper.createDialog(dialogOptions); + dlg.innerHTML = globalize.translateDocument(template, "sharedcomponents"), layoutManager.tv && scrollHelper.centerFocus.on(dlg, !1), dlg.addEventListener("close", onDialogClosed), dialogHelper.open(dlg); + var editorContent = dlg.querySelector(".formDialogContent"); + initEditor(editorContent, apiClient), dlg.querySelector(".btnCancel").addEventListener("click", function() { + dialogHelper.close(dlg) + }), reloadBrowsableImages(editorContent, apiClient) + }) + } + + function onDialogClosed() { + var dlg = this; + layoutManager.tv && scrollHelper.centerFocus.off(dlg, !1), loading.hide(), hasChanges ? currentResolve() : currentReject() + } + var currentItemId, currentItemType, currentResolve, currentReject, selectedProvider, hasChanges = !1, + browsableImagePageSize = browser.slow ? 6 : 30, + browsableImageStartIndex = 0, + browsableImageType = "Primary"; + return { + show: function(itemId, serverId, itemType, imageType) { + return new Promise(function(resolve, reject) { + currentResolve = resolve, currentReject = reject, hasChanges = !1, browsableImageStartIndex = 0, browsableImageType = imageType || "Primary", selectedProvider = null, showEditor(itemId, serverId, itemType) + }) + } + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/imageeditor/imageeditor.js b/dashboard-ui/bower_components/emby-webcomponents/imageeditor/imageeditor.js index 831082c8de..98f527901e 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/imageeditor/imageeditor.js +++ b/dashboard-ui/bower_components/emby-webcomponents/imageeditor/imageeditor.js @@ -1 +1,220 @@ -define(["dialogHelper","connectionManager","loading","dom","layoutManager","focusManager","globalize","scrollHelper","imageLoader","require","browser","apphost","cardStyle","formDialogStyle","emby-button","paper-icon-button-light","css!./imageeditor"],function(dialogHelper,connectionManager,loading,dom,layoutManager,focusManager,globalize,scrollHelper,imageLoader,require,browser,appHost){"use strict";function getBaseRemoteOptions(){var options={};return options.itemId=currentItem.Id,options}function reload(page,item,focusContext){loading.show();var apiClient;item?(apiClient=connectionManager.getApiClient(item.ServerId),reloadItem(page,item,apiClient,focusContext)):(apiClient=connectionManager.getApiClient(currentItem.ServerId),apiClient.getItem(apiClient.getCurrentUserId(),currentItem.Id).then(function(item){reloadItem(page,item,apiClient,focusContext)}))}function addListeners(container,className,eventName,fn){container.addEventListener(eventName,function(e){var elem=dom.parentWithClass(e.target,className);elem&&fn.call(elem,e)})}function reloadItem(page,item,apiClient,focusContext){currentItem=item,apiClient.getRemoteImageProviders(getBaseRemoteOptions()).then(function(providers){for(var btnBrowseAllImages=page.querySelectorAll(".btnBrowseAllImages"),i=0,length=btnBrowseAllImages.length;i',html+='
',html+='
',html+='
',html+='
",html+="
",html+="
",html+='
',html+='

'+globalize.translate("sharedcomponents#"+image.ImageType)+"

",html+='
',image.Width&&image.Height?html+=image.Width+" X "+image.Height:html+=" ",html+="
",enableFooterButtons&&(html+='
',"Backdrop"===image.ImageType||"Screenshot"===image.ImageType?(html+=index>0?'':'',html+=indexchevron_right':''):imageProviders.length&&(html+=''),html+='',html+="
"),html+="
",html+="
",html+=""}function deleteImage(context,itemId,type,index,apiClient,enableConfirmation){var afterConfirm=function(){apiClient.deleteItemImage(itemId,type,index).then(function(){hasChanges=!0,reload(context)})};if(!enableConfirmation)return void afterConfirm();require(["confirm"],function(confirm){confirm({text:globalize.translate("sharedcomponents#ConfirmDeleteImage"),confirmText:globalize.translate("sharedcomponents#Delete"),primary:"cancel"}).then(afterConfirm)})}function moveImage(context,apiClient,itemId,type,index,newIndex,focusContext){apiClient.updateItemImageIndex(itemId,type,index,newIndex).then(function(){hasChanges=!0,reload(context,null,focusContext)},function(){require(["alert"],function(alert){alert(globalize.translate("sharedcomponents#DefaultErrorMessage"))})})}function renderImages(page,item,apiClient,images,imageProviders,elem){var html="",imageSize=300,windowSize=dom.getWindowSize();windowSize.innerWidth>=1280&&(imageSize=Math.round(windowSize.innerWidth/4));for(var tagName=layoutManager.tv?"button":"div",enableFooterButtons=!layoutManager.tv,i=0,length=images.length;i0&&commands.push({name:globalize.translate("sharedcomponents#MoveLeft"),id:"moveleft"}),index', html += '
', html += '
', html += '
', html += '
", html += "
", html += "
", html += '
', html += '

' + globalize.translate("sharedcomponents#" + image.ImageType) + "

", html += '
', image.Width && image.Height ? html += image.Width + " X " + image.Height : html += " ", html += "
", enableFooterButtons && (html += '
', "Backdrop" === image.ImageType || "Screenshot" === image.ImageType ? (html += index > 0 ? '' : '', html += index < numImages - 1 ? '' : '') : imageProviders.length && (html += ''), html += '', html += "
"), html += "
", html += "
", html += "" + } + + function deleteImage(context, itemId, type, index, apiClient, enableConfirmation) { + var afterConfirm = function() { + apiClient.deleteItemImage(itemId, type, index).then(function() { + hasChanges = !0, reload(context) + }) + }; + if (!enableConfirmation) return void afterConfirm(); + require(["confirm"], function(confirm) { + confirm({ + text: globalize.translate("sharedcomponents#ConfirmDeleteImage"), + confirmText: globalize.translate("sharedcomponents#Delete"), + primary: "cancel" + }).then(afterConfirm) + }) + } + + function moveImage(context, apiClient, itemId, type, index, newIndex, focusContext) { + apiClient.updateItemImageIndex(itemId, type, index, newIndex).then(function() { + hasChanges = !0, reload(context, null, focusContext) + }, function() { + require(["alert"], function(alert) { + alert(globalize.translate("sharedcomponents#DefaultErrorMessage")) + }) + }) + } + + function renderImages(page, item, apiClient, images, imageProviders, elem) { + var html = "", + imageSize = 300, + windowSize = dom.getWindowSize(); + windowSize.innerWidth >= 1280 && (imageSize = Math.round(windowSize.innerWidth / 4)); + for (var tagName = layoutManager.tv ? "button" : "div", enableFooterButtons = !layoutManager.tv, i = 0, length = images.length; i < length; i++) { + html += getCardHtml(images[i], i, length, apiClient, imageProviders, imageSize, tagName, enableFooterButtons) + } + elem.innerHTML = html, imageLoader.lazyChildren(elem) + } + + function renderStandardImages(page, apiClient, item, imageInfos, imageProviders) { + renderImages(page, item, apiClient, imageInfos.filter(function(i) { + return "Screenshot" !== i.ImageType && "Backdrop" !== i.ImageType && "Chapter" !== i.ImageType + }), imageProviders, page.querySelector("#images")) + } + + function renderBackdrops(page, apiClient, item, imageInfos, imageProviders) { + var images = imageInfos.filter(function(i) { + return "Backdrop" === i.ImageType + }).sort(function(a, b) { + return a.ImageIndex - b.ImageIndex + }); + images.length ? (page.querySelector("#backdropsContainer", page).classList.remove("hide"), renderImages(page, item, apiClient, images, imageProviders, page.querySelector("#backdrops"))) : page.querySelector("#backdropsContainer", page).classList.add("hide") + } + + function renderScreenshots(page, apiClient, item, imageInfos, imageProviders) { + var images = imageInfos.filter(function(i) { + return "Screenshot" === i.ImageType + }).sort(function(a, b) { + return a.ImageIndex - b.ImageIndex + }); + images.length ? (page.querySelector("#screenshotsContainer", page).classList.remove("hide"), renderImages(page, item, apiClient, images, imageProviders, page.querySelector("#screenshots"))) : page.querySelector("#screenshotsContainer", page).classList.add("hide") + } + + function showImageDownloader(page, imageType) { + require(["imageDownloader"], function(ImageDownloader) { + ImageDownloader.show(currentItem.Id, currentItem.ServerId, currentItem.Type, imageType).then(function() { + hasChanges = !0, reload(page) + }) + }) + } + + function showActionSheet(context, imageCard) { + var itemId = imageCard.getAttribute("data-id"), + serverId = imageCard.getAttribute("data-serverid"), + apiClient = connectionManager.getApiClient(serverId), + type = imageCard.getAttribute("data-imagetype"), + index = parseInt(imageCard.getAttribute("data-index")), + providerCount = parseInt(imageCard.getAttribute("data-providers")), + numImages = parseInt(imageCard.getAttribute("data-numimages")); + require(["actionsheet"], function(actionSheet) { + var commands = []; + commands.push({ + name: globalize.translate("sharedcomponents#Delete"), + id: "delete" + }), "Backdrop" !== type && "Screenshot" !== type || (index > 0 && commands.push({ + name: globalize.translate("sharedcomponents#MoveLeft"), + id: "moveleft" + }), index < numImages - 1 && commands.push({ + name: globalize.translate("sharedcomponents#MoveRight"), + id: "moveright" + })), providerCount && commands.push({ + name: globalize.translate("sharedcomponents#Search"), + id: "search" + }), actionSheet.show({ + items: commands, + positionTo: imageCard + }).then(function(id) { + switch (id) { + case "delete": + deleteImage(context, itemId, type, index, apiClient, !1); + break; + case "search": + showImageDownloader(context, type); + break; + case "moveleft": + moveImage(context, apiClient, itemId, type, index, index - 1, dom.parentWithClass(imageCard, "itemsContainer")); + break; + case "moveright": + moveImage(context, apiClient, itemId, type, index, index + 1, dom.parentWithClass(imageCard, "itemsContainer")) + } + }) + }) + } + + function initEditor(context, options) { + for (var uploadButtons = context.querySelectorAll(".btnOpenUploadMenu"), isFileInputSupported = appHost.supports("fileinput"), i = 0, length = uploadButtons.length; i < length; i++) isFileInputSupported ? uploadButtons[i].classList.remove("hide") : uploadButtons[i].classList.add("hide"); + addListeners(context, "btnOpenUploadMenu", "click", function() { + var imageType = this.getAttribute("data-imagetype"); + require(["imageUploader"], function(imageUploader) { + imageUploader.show({ + theme: options.theme, + imageType: imageType, + itemId: currentItem.Id, + serverId: currentItem.ServerId + }).then(function(hasChanged) { + hasChanged && (hasChanges = !0, reload(context)) + }) + }) + }), addListeners(context, "btnSearchImages", "click", function() { + showImageDownloader(context, this.getAttribute("data-imagetype")) + }), addListeners(context, "btnBrowseAllImages", "click", function() { + showImageDownloader(context, this.getAttribute("data-imagetype") || "Primary") + }), addListeners(context, "btnImageCard", "click", function() { + showActionSheet(context, this) + }), addListeners(context, "btnDeleteImage", "click", function() { + var type = this.getAttribute("data-imagetype"), + index = this.getAttribute("data-index"); + index = "null" === index ? null : parseInt(index); + var apiClient = connectionManager.getApiClient(currentItem.ServerId); + deleteImage(context, currentItem.Id, type, index, apiClient, !0) + }), addListeners(context, "btnMoveImage", "click", function() { + var type = this.getAttribute("data-imagetype"), + index = this.getAttribute("data-index"), + newIndex = this.getAttribute("data-newindex"), + apiClient = connectionManager.getApiClient(currentItem.ServerId); + moveImage(context, apiClient, currentItem.Id, type, index, newIndex, dom.parentWithClass(this, "itemsContainer")) + }) + } + + function showEditor(options, resolve, reject) { + var itemId = options.itemId, + serverId = options.serverId; + loading.show(), require(["text!./imageeditor.template.html"], function(template) { + var apiClient = connectionManager.getApiClient(serverId); + apiClient.getItem(apiClient.getCurrentUserId(), itemId).then(function(item) { + var dialogOptions = { + removeOnClose: !0 + }; + layoutManager.tv ? dialogOptions.size = "fullscreen" : dialogOptions.size = "fullscreen-border"; + var dlg = dialogHelper.createDialog(dialogOptions); + dlg.classList.add("formDialog"), dlg.innerHTML = globalize.translateDocument(template, "sharedcomponents"), layoutManager.tv && scrollHelper.centerFocus.on(dlg, !1), initEditor(dlg, options), dlg.addEventListener("close", function() { + layoutManager.tv && scrollHelper.centerFocus.off(dlg, !1), loading.hide(), hasChanges ? resolve() : reject() + }), dialogHelper.open(dlg), reload(dlg, item), dlg.querySelector(".btnCancel").addEventListener("click", function() { + dialogHelper.close(dlg) + }) + }) + }) + } + var currentItem, hasChanges = !1; + return { + show: function(options) { + return new Promise(function(resolve, reject) { + hasChanges = !1, showEditor(options, resolve, reject) + }) + } + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/images/basicimagefetcher.js b/dashboard-ui/bower_components/emby-webcomponents/images/basicimagefetcher.js index 0438504782..7ba86474e0 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/images/basicimagefetcher.js +++ b/dashboard-ui/bower_components/emby-webcomponents/images/basicimagefetcher.js @@ -1 +1,18 @@ -define(["dom"],function(dom){"use strict";function loadImage(elem,url){return elem?"IMG"!==elem.tagName?(elem.style.backgroundImage="url('"+url+"')",Promise.resolve()):loadImageIntoImg(elem,url):Promise.reject("elem cannot be null")}function loadImageIntoImg(elem,url){return new Promise(function(resolve,reject){dom.addEventListener(elem,"load",resolve,{once:!0}),elem.setAttribute("src",url)})}return{loadImage:loadImage}}); \ No newline at end of file +define(["dom"], function(dom) { + "use strict"; + + function loadImage(elem, url) { + return elem ? "IMG" !== elem.tagName ? (elem.style.backgroundImage = "url('" + url + "')", Promise.resolve()) : loadImageIntoImg(elem, url) : Promise.reject("elem cannot be null") + } + + function loadImageIntoImg(elem, url) { + return new Promise(function(resolve, reject) { + dom.addEventListener(elem, "load", resolve, { + once: !0 + }), elem.setAttribute("src", url) + }) + } + return { + loadImage: loadImage + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/images/imagehelper.js b/dashboard-ui/bower_components/emby-webcomponents/images/imagehelper.js index e5b3d290d4..ddcf5b7ba7 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/images/imagehelper.js +++ b/dashboard-ui/bower_components/emby-webcomponents/images/imagehelper.js @@ -1 +1,82 @@ -define(["lazyLoader","imageFetcher","layoutManager","browser","appSettings","require","css!./style"],function(lazyLoader,imageFetcher,layoutManager,browser,appSettings,require){"use strict";function fillImage(elem,source,enableEffects){if(!elem)throw new Error("elem cannot be null");source||(source=elem.getAttribute("data-src")),source&&fillImageElement(elem,source,enableEffects)}function fillImageElement(elem,source,enableEffects){imageFetcher.loadImage(elem,source).then(function(){enableFade&&!1!==enableEffects&&fadeIn(elem),elem.removeAttribute("data-src")})}function getVibrantInfoFromElement(elem,url){return new Promise(function(resolve,reject){require(["vibrant"],function(){if("IMG"===elem.tagName)return void resolve(getVibrantInfo(elem,url));var img=new Image;img.onload=function(){resolve(getVibrantInfo(img,url))},img.src=url})})}function getSettingsKey(url){var parts=url.split("://");url=parts[parts.length-1],url=url.substring(url.indexOf("/")+1),url=url.split("?")[0];return"vibrant31"+url}function getCachedVibrantInfo(url){return appSettings.get(getSettingsKey(url))}function getVibrantInfo(img,url){var value=getCachedVibrantInfo(url);if(value)return value;var vibrant=new Vibrant(img),swatches=vibrant.swatches();return value="",value+=getSwatchString(swatches.DarkVibrant),appSettings.set(getSettingsKey(url),value),value}function getSwatchString(swatch){return swatch?swatch.getHex()+"|"+swatch.getBodyTextColor()+"|"+swatch.getTitleTextColor():"||"}function fadeIn(elem){elem.classList.add("lazy-image-fadein")}function lazyChildren(elem){lazyLoader.lazyChildren(elem,fillImage)}function getPrimaryImageAspectRatio(items){for(var values=[],i=0,length=items.length;i'].join("");page.querySelector("#imageOutput").innerHTML=html,page.querySelector("#fldUpload").classList.remove("hide")}}(file),reader.readAsDataURL(file)}function onSubmit(e){var file=currentFile;if(!file)return!1;if("image/png"!==file.type&&"image/jpeg"!==file.type&&"image/jpeg"!==file.type)return!1;loading.show();var dlg=dom.parentWithClass(this,"dialog"),imageType=dlg.querySelector("#selectImageType").value;return connectionManager.getApiClient(currentServerId).uploadItemImage(currentItemId,imageType,file).then(function(){dlg.querySelector("#uploadImage").value="",loading.hide(),hasChanges=!0,dialogHelper.close(dlg)}),e.preventDefault(),!1}function initEditor(page){page.querySelector("form").addEventListener("submit",onSubmit),page.querySelector("#uploadImage").addEventListener("change",function(){setFiles(page,this.files)}),page.querySelector(".btnBrowse").addEventListener("click",function(){page.querySelector("#uploadImage").click()})}function showEditor(options,resolve,reject){options=options||{},require(["text!./imageuploader.template.html"],function(template){currentItemId=options.itemId,currentServerId=options.serverId;var dialogOptions={removeOnClose:!0};layoutManager.tv?dialogOptions.size="fullscreen":dialogOptions.size="fullscreen-border";var dlg=dialogHelper.createDialog(dialogOptions);dlg.classList.add("formDialog"),dlg.innerHTML=globalize.translateDocument(template,"sharedcomponents"),layoutManager.tv&&scrollHelper.centerFocus.on(dlg,!1),dlg.addEventListener("close",function(){layoutManager.tv&&scrollHelper.centerFocus.off(dlg,!1),loading.hide(),resolve(hasChanges)}),dialogHelper.open(dlg),initEditor(dlg),dlg.querySelector("#selectImageType").value=options.imageType||"Primary",dlg.querySelector(".btnCancel").addEventListener("click",function(){dialogHelper.close(dlg)})})}var currentItemId,currentServerId,currentFile,hasChanges=!1;return{show:function(options){return new Promise(function(resolve,reject){hasChanges=!1,showEditor(options,resolve,reject)})}}}); \ No newline at end of file +define(["dialogHelper", "connectionManager", "dom", "loading", "scrollHelper", "layoutManager", "globalize", "require", "emby-button", "emby-select", "formDialogStyle", "css!./style"], function(dialogHelper, connectionManager, dom, loading, scrollHelper, layoutManager, globalize, require) { + "use strict"; + + function onFileReaderError(evt) { + switch (loading.hide(), evt.target.error.code) { + case evt.target.error.NOT_FOUND_ERR: + require(["toast"], function(toast) { + toast(globalize.translate("sharedcomponents#MessageFileReadError")) + }); + break; + case evt.target.error.ABORT_ERR: + break; + default: + require(["toast"], function(toast) { + toast(globalize.translate("sharedcomponents#MessageFileReadError")) + }) + } + } + + function setFiles(page, files) { + var file = files[0]; + if (!file || !file.type.match("image.*")) return page.querySelector("#imageOutput").innerHTML = "", page.querySelector("#fldUpload").classList.add("hide"), void(currentFile = null); + currentFile = file; + var reader = new FileReader; + reader.onerror = onFileReaderError, reader.onloadstart = function() { + page.querySelector("#fldUpload").classList.add("hide") + }, reader.onabort = function() { + loading.hide(), console.log("File read cancelled") + }, reader.onload = function(theFile) { + return function(e) { + var html = [''].join(""); + page.querySelector("#imageOutput").innerHTML = html, page.querySelector("#fldUpload").classList.remove("hide") + } + }(file), reader.readAsDataURL(file) + } + + function onSubmit(e) { + var file = currentFile; + if (!file) return !1; + if ("image/png" !== file.type && "image/jpeg" !== file.type && "image/jpeg" !== file.type) return !1; + loading.show(); + var dlg = dom.parentWithClass(this, "dialog"), + imageType = dlg.querySelector("#selectImageType").value; + return connectionManager.getApiClient(currentServerId).uploadItemImage(currentItemId, imageType, file).then(function() { + dlg.querySelector("#uploadImage").value = "", loading.hide(), hasChanges = !0, dialogHelper.close(dlg) + }), e.preventDefault(), !1 + } + + function initEditor(page) { + page.querySelector("form").addEventListener("submit", onSubmit), page.querySelector("#uploadImage").addEventListener("change", function() { + setFiles(page, this.files) + }), page.querySelector(".btnBrowse").addEventListener("click", function() { + page.querySelector("#uploadImage").click() + }) + } + + function showEditor(options, resolve, reject) { + options = options || {}, require(["text!./imageuploader.template.html"], function(template) { + currentItemId = options.itemId, currentServerId = options.serverId; + var dialogOptions = { + removeOnClose: !0 + }; + layoutManager.tv ? dialogOptions.size = "fullscreen" : dialogOptions.size = "fullscreen-border"; + var dlg = dialogHelper.createDialog(dialogOptions); + dlg.classList.add("formDialog"), dlg.innerHTML = globalize.translateDocument(template, "sharedcomponents"), layoutManager.tv && scrollHelper.centerFocus.on(dlg, !1), dlg.addEventListener("close", function() { + layoutManager.tv && scrollHelper.centerFocus.off(dlg, !1), loading.hide(), resolve(hasChanges) + }), dialogHelper.open(dlg), initEditor(dlg), dlg.querySelector("#selectImageType").value = options.imageType || "Primary", dlg.querySelector(".btnCancel").addEventListener("click", function() { + dialogHelper.close(dlg) + }) + }) + } + var currentItemId, currentServerId, currentFile, hasChanges = !1; + return { + show: function(options) { + return new Promise(function(resolve, reject) { + hasChanges = !1, showEditor(options, resolve, reject) + }) + } + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/indicators/indicators.js b/dashboard-ui/bower_components/emby-webcomponents/indicators/indicators.js index f1f7e1e883..41c3188aa2 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/indicators/indicators.js +++ b/dashboard-ui/bower_components/emby-webcomponents/indicators/indicators.js @@ -1 +1,120 @@ -define(["datetime","itemHelper","css!./indicators.css","material-icons"],function(datetime,itemHelper){"use strict";function enableProgressIndicator(item){return"Video"===item.MediaType&&"TvChannel"!==item.Type||("AudioBook"===item.Type||"AudioPodcast"===item.Type)}function getProgressHtml(pct,options){var containerClass="itemProgressBar";return options&&options.containerClass&&(containerClass+=" "+options.containerClass),'
'}function getAutoTimeProgressHtml(pct,options,isRecording,start,end){var containerClass="itemProgressBar";options&&options.containerClass&&(containerClass+=" "+options.containerClass);var foregroundClass="itemProgressBarForeground";return isRecording&&(foregroundClass+=" itemProgressBarForeground-recording"),'
'}function getProgressBarHtml(item,options){var pct;if(enableProgressIndicator(item)&&"Recording"!==item.Type){var userData=options?options.userData||item.UserData:item.UserData;if(userData&&(pct=userData.PlayedPercentage)&&pct<100)return getProgressHtml(pct,options)}if(("Program"===item.Type||"Timer"===item.Type||"Recording"===item.Type)&&item.StartDate&&item.EndDate){var startDate=0,endDate=1;try{startDate=datetime.parseISO8601Date(item.StartDate).getTime()}catch(err){}try{endDate=datetime.parseISO8601Date(item.EndDate).getTime()}catch(err){}if((pct=((new Date).getTime()-startDate)/(endDate-startDate)*100)>0&&pct<100){return getAutoTimeProgressHtml(pct,options,"Timer"===item.Type||"Recording"===item.Type||item.TimerId,startDate,endDate)}}return""}function enablePlayedIndicator(item){return itemHelper.canMarkPlayed(item)}function getPlayedIndicator(item){if(enablePlayedIndicator(item)){var userData=item.UserData||{};if(userData.UnplayedItemCount)return'
'+userData.UnplayedItemCount+"
";if(userData.PlayedPercentage&&userData.PlayedPercentage>=100||userData.Played)return'
'}return""}function getCountIndicatorHtml(count){return'
'+count+"
"}function getChildCountIndicatorHtml(item,options){var minCount=0;return options&&(minCount=options.minCount||minCount),item.ChildCount&&item.ChildCount>minCount?getCountIndicatorHtml(item.ChildCount):""}function getTimerIndicator(item){var status;if("SeriesTimer"===item.Type)return'';if(item.TimerId||item.SeriesTimerId)status=item.Status||"Cancelled";else{if("Timer"!==item.Type)return"";status=item.Status}return item.SeriesTimerId?"Cancelled"!==status?'':'':''}function getSyncIndicator(item){return 100===item.SyncPercent?'
':null!=item.SyncPercent?'
':""}function getTypeIndicator(item){return"Video"===item.Type?'
':"Folder"===item.Type||"PhotoAlbum"===item.Type?'
':"Photo"===item.Type?'
':""}function getMissingIndicator(item){if("Episode"===item.Type&&"Virtual"===item.LocationType){if(item.PremiereDate)try{if(datetime.parseISO8601Date(item.PremiereDate).getTime()>(new Date).getTime())return'
Unaired
'}catch(err){}return'
Missing
'}return""}function onAutoTimeProgress(){var start=parseInt(this.getAttribute("data-starttime")),end=parseInt(this.getAttribute("data-endtime")),now=(new Date).getTime(),total=end-start,pct=(now-start)/total*100;pct=Math.min(100,pct),pct=Math.max(0,pct),this.querySelector(".itemProgressBarForeground").style.width=pct+"%"}var ProgressBarPrototype=Object.create(HTMLDivElement.prototype);return ProgressBarPrototype.attachedCallback=function(){this.timeInterval&&clearInterval(this.timeInterval),"time"===this.getAttribute("data-automode")&&(this.timeInterval=setInterval(onAutoTimeProgress.bind(this),6e4))},ProgressBarPrototype.detachedCallback=function(){this.timeInterval&&(clearInterval(this.timeInterval),this.timeInterval=null)},document.registerElement("emby-progressbar",{prototype:ProgressBarPrototype,extends:"div"}),{getProgressBarHtml:getProgressBarHtml,getPlayedIndicatorHtml:getPlayedIndicator,getChildCountIndicatorHtml:getChildCountIndicatorHtml,enableProgressIndicator:enableProgressIndicator,getTimerIndicator:getTimerIndicator,enablePlayedIndicator:enablePlayedIndicator,getSyncIndicator:getSyncIndicator,getTypeIndicator:getTypeIndicator,getMissingIndicator:getMissingIndicator}}); \ No newline at end of file +define(["datetime", "itemHelper", "css!./indicators.css", "material-icons"], function(datetime, itemHelper) { + "use strict"; + + function enableProgressIndicator(item) { + return "Video" === item.MediaType && "TvChannel" !== item.Type || ("AudioBook" === item.Type || "AudioPodcast" === item.Type) + } + + function getProgressHtml(pct, options) { + var containerClass = "itemProgressBar"; + return options && options.containerClass && (containerClass += " " + options.containerClass), '
' + } + + function getAutoTimeProgressHtml(pct, options, isRecording, start, end) { + var containerClass = "itemProgressBar"; + options && options.containerClass && (containerClass += " " + options.containerClass); + var foregroundClass = "itemProgressBarForeground"; + return isRecording && (foregroundClass += " itemProgressBarForeground-recording"), '
' + } + + function getProgressBarHtml(item, options) { + var pct; + if (enableProgressIndicator(item) && "Recording" !== item.Type) { + var userData = options ? options.userData || item.UserData : item.UserData; + if (userData && (pct = userData.PlayedPercentage) && pct < 100) return getProgressHtml(pct, options) + } + if (("Program" === item.Type || "Timer" === item.Type || "Recording" === item.Type) && item.StartDate && item.EndDate) { + var startDate = 0, + endDate = 1; + try { + startDate = datetime.parseISO8601Date(item.StartDate).getTime() + } catch (err) {} + try { + endDate = datetime.parseISO8601Date(item.EndDate).getTime() + } catch (err) {} + if ((pct = ((new Date).getTime() - startDate) / (endDate - startDate) * 100) > 0 && pct < 100) { + return getAutoTimeProgressHtml(pct, options, "Timer" === item.Type || "Recording" === item.Type || item.TimerId, startDate, endDate) + } + } + return "" + } + + function enablePlayedIndicator(item) { + return itemHelper.canMarkPlayed(item) + } + + function getPlayedIndicator(item) { + if (enablePlayedIndicator(item)) { + var userData = item.UserData || {}; + if (userData.UnplayedItemCount) return '
' + userData.UnplayedItemCount + "
"; + if (userData.PlayedPercentage && userData.PlayedPercentage >= 100 || userData.Played) return '
' + } + return "" + } + + function getCountIndicatorHtml(count) { + return '
' + count + "
" + } + + function getChildCountIndicatorHtml(item, options) { + var minCount = 0; + return options && (minCount = options.minCount || minCount), item.ChildCount && item.ChildCount > minCount ? getCountIndicatorHtml(item.ChildCount) : "" + } + + function getTimerIndicator(item) { + var status; + if ("SeriesTimer" === item.Type) return ''; + if (item.TimerId || item.SeriesTimerId) status = item.Status || "Cancelled"; + else { + if ("Timer" !== item.Type) return ""; + status = item.Status + } + return item.SeriesTimerId ? "Cancelled" !== status ? '' : '' : '' + } + + function getSyncIndicator(item) { + return 100 === item.SyncPercent ? '
' : null != item.SyncPercent ? '
' : "" + } + + function getTypeIndicator(item) { + return "Video" === item.Type ? '
' : "Folder" === item.Type || "PhotoAlbum" === item.Type ? '
' : "Photo" === item.Type ? '
' : "" + } + + function getMissingIndicator(item) { + if ("Episode" === item.Type && "Virtual" === item.LocationType) { + if (item.PremiereDate) try { + if (datetime.parseISO8601Date(item.PremiereDate).getTime() > (new Date).getTime()) return '
Unaired
' + } catch (err) {} + return '
Missing
' + } + return "" + } + + function onAutoTimeProgress() { + var start = parseInt(this.getAttribute("data-starttime")), + end = parseInt(this.getAttribute("data-endtime")), + now = (new Date).getTime(), + total = end - start, + pct = (now - start) / total * 100; + pct = Math.min(100, pct), pct = Math.max(0, pct), this.querySelector(".itemProgressBarForeground").style.width = pct + "%" + } + var ProgressBarPrototype = Object.create(HTMLDivElement.prototype); + return ProgressBarPrototype.attachedCallback = function() { + this.timeInterval && clearInterval(this.timeInterval), "time" === this.getAttribute("data-automode") && (this.timeInterval = setInterval(onAutoTimeProgress.bind(this), 6e4)) + }, ProgressBarPrototype.detachedCallback = function() { + this.timeInterval && (clearInterval(this.timeInterval), this.timeInterval = null) + }, document.registerElement("emby-progressbar", { + prototype: ProgressBarPrototype, + extends: "div" + }), { + getProgressBarHtml: getProgressBarHtml, + getPlayedIndicatorHtml: getPlayedIndicator, + getChildCountIndicatorHtml: getChildCountIndicatorHtml, + enableProgressIndicator: enableProgressIndicator, + getTimerIndicator: getTimerIndicator, + enablePlayedIndicator: enablePlayedIndicator, + getSyncIndicator: getSyncIndicator, + getTypeIndicator: getTypeIndicator, + getMissingIndicator: getMissingIndicator + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/input/api.js b/dashboard-ui/bower_components/emby-webcomponents/input/api.js index c57e5a771b..13f0abc9ba 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/input/api.js +++ b/dashboard-ui/bower_components/emby-webcomponents/input/api.js @@ -1 +1,145 @@ -define(["connectionManager","playbackManager","events","inputManager","focusManager","appRouter"],function(connectionManager,playbackManager,events,inputManager,focusManager,appRouter){"use strict";function notifyApp(){inputManager.notify()}function displayMessage(cmd){var args=cmd.Arguments;args.TimeoutMs?require(["toast"],function(toast){toast({title:args.Header,text:args.Text})}):require(["alert"],function(alert){alert({title:args.Header,text:args.Text})})}function displayContent(cmd,apiClient){playbackManager.isPlayingLocally(["Video","Book","Game"])||appRouter.showItem(cmd.Arguments.ItemId,apiClient.serverId())}function playTrailers(apiClient,itemId){apiClient.getItem(apiClient.getCurrentUserId(),itemId).then(function(item){playbackManager.playTrailers(item)})}function processGeneralCommand(cmd,apiClient){switch(cmd.Name){case"Select":return void inputManager.trigger("select");case"Back":return void inputManager.trigger("back");case"MoveUp":return void inputManager.trigger("up");case"MoveDown":return void inputManager.trigger("down");case"MoveLeft":return void inputManager.trigger("left");case"MoveRight":return void inputManager.trigger("right");case"PageUp":return void inputManager.trigger("pageup");case"PageDown":return void inputManager.trigger("pagedown");case"PlayTrailers":playTrailers(apiClient,cmd.Arguments.ItemId);break;case"SetRepeatMode":playbackManager.setRepeatMode(cmd.Arguments.RepeatMode);break;case"VolumeUp":return void inputManager.trigger("volumeup");case"VolumeDown":return void inputManager.trigger("volumedown");case"ChannelUp":return void inputManager.trigger("channelup");case"ChannelDown":return void inputManager.trigger("channeldown");case"Mute":return void inputManager.trigger("mute");case"Unmute":return void inputManager.trigger("unmute");case"ToggleMute":return void inputManager.trigger("togglemute");case"SetVolume":notifyApp(),playbackManager.setVolume(cmd.Arguments.Volume);break;case"SetAudioStreamIndex":notifyApp(),playbackManager.setAudioStreamIndex(parseInt(cmd.Arguments.Index));break;case"SetSubtitleStreamIndex":notifyApp(),playbackManager.setSubtitleStreamIndex(parseInt(cmd.Arguments.Index));break;case"ToggleFullscreen":return void inputManager.trigger("togglefullscreen");case"GoHome":return void inputManager.trigger("home");case"GoToSettings":return void inputManager.trigger("settings");case"DisplayContent":displayContent(cmd,apiClient);break;case"GoToSearch":return void inputManager.trigger("search");case"DisplayMessage":displayMessage(cmd);break;case"ToggleOsd":case"ToggleContextMenu":case"TakeScreenShot":case"SendKey":break;case"SendString":focusManager.sendText(cmd.Arguments.String);break;default:console.log("processGeneralCommand does not recognize: "+cmd.Name)}notifyApp()}function onMessageReceived(e,msg){var apiClient=this;if("Play"===msg.MessageType){notifyApp();var serverId=apiClient.serverInfo().Id;"PlayNext"===msg.Data.PlayCommand?playbackManager.queueNext({ids:msg.Data.ItemIds,serverId:serverId}):"PlayLast"===msg.Data.PlayCommand?playbackManager.queue({ids:msg.Data.ItemIds,serverId:serverId}):playbackManager.play({ids:msg.Data.ItemIds,startPositionTicks:msg.Data.StartPositionTicks,mediaSourceId:msg.Data.MediaSourceId,audioStreamIndex:msg.Data.AudioStreamIndex,subtitleStreamIndex:msg.Data.SubtitleStreamIndex,startIndex:msg.Data.StartIndex,serverId:serverId})}else if("Playstate"===msg.MessageType)"Stop"===msg.Data.Command?inputManager.trigger("stop"):"Pause"===msg.Data.Command?inputManager.trigger("pause"):"Unpause"===msg.Data.Command?inputManager.trigger("play"):"PlayPause"===msg.Data.Command?inputManager.trigger("playpause"):"Seek"===msg.Data.Command?playbackManager.seek(msg.Data.SeekPositionTicks):"NextTrack"===msg.Data.Command?inputManager.trigger("next"):"PreviousTrack"===msg.Data.Command?inputManager.trigger("previous"):notifyApp();else if("GeneralCommand"===msg.MessageType){var cmd=msg.Data;processGeneralCommand(cmd,apiClient)}else if("UserDataChanged"===msg.MessageType){if(msg.Data.UserId===apiClient.getCurrentUserId())for(var i=0,length=msg.Data.UserDataList.length;i=200}function resetThrottle(key){times[key]=(new Date).getTime()}function allowInput(){return!(!isElectron&&document.hidden)&&"Minimized"!==appHost.getWindowState()}function raiseEvent(name,key,keyCode){if(allowInput()){var event=document.createEvent("Event");event.initEvent(name,!0,!0),event.key=key,event.keyCode=keyCode,(document.activeElement||document.body).dispatchEvent(event)}}function clickElement(elem){allowInput()&&elem.click()}function raiseKeyEvent(oldPressedState,newPressedState,key,keyCode,enableRepeatKeyDown,clickonKeyUp){if(!0===newPressedState){var fire=!1;!1===oldPressedState?(fire=!0,resetThrottle(key)):enableRepeatKeyDown&&(fire=throttle(key)),fire&&keyCode&&raiseEvent("keydown",key,keyCode)}else!1===newPressedState&&!0===oldPressedState&&(resetThrottle(key),keyCode&&raiseEvent("keyup",key,keyCode),clickonKeyUp&&clickElement(document.activeElement||window))}function runInputLoop(){var gamepads;navigator.getGamepads?gamepads=navigator.getGamepads():navigator.webkitGetGamepads&&(gamepads=navigator.webkitGetGamepads()),gamepads=gamepads||[];var i,j,len;for(i=0,len=gamepads.length;i_THUMB_STICK_THRESHOLD?_ButtonPressedState.setleftThumbstickRight(!0):leftStickX<-_THUMB_STICK_THRESHOLD?_ButtonPressedState.setleftThumbstickLeft(!0):leftStickY<-_THUMB_STICK_THRESHOLD?_ButtonPressedState.setleftThumbstickUp(!0):leftStickY>_THUMB_STICK_THRESHOLD?_ButtonPressedState.setleftThumbstickDown(!0):(_ButtonPressedState.setleftThumbstickLeft(!1),_ButtonPressedState.setleftThumbstickRight(!1),_ButtonPressedState.setleftThumbstickUp(!1),_ButtonPressedState.setleftThumbstickDown(!1));var buttons=gamepad.buttons;for(j=0,len=buttons.length;j= 200 + } + + function resetThrottle(key) { + times[key] = (new Date).getTime() + } + + function allowInput() { + return !(!isElectron && document.hidden) && "Minimized" !== appHost.getWindowState() + } + + function raiseEvent(name, key, keyCode) { + if (allowInput()) { + var event = document.createEvent("Event"); + event.initEvent(name, !0, !0), event.key = key, event.keyCode = keyCode, (document.activeElement || document.body).dispatchEvent(event) + } + } + + function clickElement(elem) { + allowInput() && elem.click() + } + + function raiseKeyEvent(oldPressedState, newPressedState, key, keyCode, enableRepeatKeyDown, clickonKeyUp) { + if (!0 === newPressedState) { + var fire = !1; + !1 === oldPressedState ? (fire = !0, resetThrottle(key)) : enableRepeatKeyDown && (fire = throttle(key)), fire && keyCode && raiseEvent("keydown", key, keyCode) + } else !1 === newPressedState && !0 === oldPressedState && (resetThrottle(key), keyCode && raiseEvent("keyup", key, keyCode), clickonKeyUp && clickElement(document.activeElement || window)) + } + + function runInputLoop() { + var gamepads; + navigator.getGamepads ? gamepads = navigator.getGamepads() : navigator.webkitGetGamepads && (gamepads = navigator.webkitGetGamepads()), gamepads = gamepads || []; + var i, j, len; + for (i = 0, len = gamepads.length; i < len; i++) { + var gamepad = gamepads[i]; + if (gamepad) { + var axes = gamepad.axes, + leftStickX = axes[0], + leftStickY = axes[1]; + leftStickX > _THUMB_STICK_THRESHOLD ? _ButtonPressedState.setleftThumbstickRight(!0) : leftStickX < -_THUMB_STICK_THRESHOLD ? _ButtonPressedState.setleftThumbstickLeft(!0) : leftStickY < -_THUMB_STICK_THRESHOLD ? _ButtonPressedState.setleftThumbstickUp(!0) : leftStickY > _THUMB_STICK_THRESHOLD ? _ButtonPressedState.setleftThumbstickDown(!0) : (_ButtonPressedState.setleftThumbstickLeft(!1), _ButtonPressedState.setleftThumbstickRight(!1), _ButtonPressedState.setleftThumbstickUp(!1), _ButtonPressedState.setleftThumbstickDown(!1)); + var buttons = gamepad.buttons; + for (j = 0, len = buttons.length; j < len; j++) + if (-1 !== ProcessedButtons.indexOf(j)) + if (buttons[j].pressed) switch (j) { + case _GAMEPAD_DPAD_UP_BUTTON_INDEX: + _ButtonPressedState.setdPadUp(!0); + break; + case _GAMEPAD_DPAD_DOWN_BUTTON_INDEX: + _ButtonPressedState.setdPadDown(!0); + break; + case _GAMEPAD_DPAD_LEFT_BUTTON_INDEX: + _ButtonPressedState.setdPadLeft(!0); + break; + case _GAMEPAD_DPAD_RIGHT_BUTTON_INDEX: + _ButtonPressedState.setdPadRight(!0); + break; + case _GAMEPAD_A_BUTTON_INDEX: + _ButtonPressedState.setgamepadA(!0); + break; + case _GAMEPAD_B_BUTTON_INDEX: + _ButtonPressedState.setgamepadB(!0) + } else switch (j) { + case _GAMEPAD_DPAD_UP_BUTTON_INDEX: + _ButtonPressedState.getdPadUp() && _ButtonPressedState.setdPadUp(!1); + break; + case _GAMEPAD_DPAD_DOWN_BUTTON_INDEX: + _ButtonPressedState.getdPadDown() && _ButtonPressedState.setdPadDown(!1); + break; + case _GAMEPAD_DPAD_LEFT_BUTTON_INDEX: + _ButtonPressedState.getdPadLeft() && _ButtonPressedState.setdPadLeft(!1); + break; + case _GAMEPAD_DPAD_RIGHT_BUTTON_INDEX: + _ButtonPressedState.getdPadRight() && _ButtonPressedState.setdPadRight(!1); + break; + case _GAMEPAD_A_BUTTON_INDEX: + _ButtonPressedState.getgamepadA() && _ButtonPressedState.setgamepadA(!1); + break; + case _GAMEPAD_B_BUTTON_INDEX: + _ButtonPressedState.getgamepadB() && _ButtonPressedState.setgamepadB(!1) + } + } + } + requestAnimationFrame(runInputLoop) + } + var _GAMEPAD_A_BUTTON_INDEX = 0, + _GAMEPAD_B_BUTTON_INDEX = 1, + _GAMEPAD_DPAD_UP_BUTTON_INDEX = 12, + _GAMEPAD_DPAD_DOWN_BUTTON_INDEX = 13, + _GAMEPAD_DPAD_LEFT_BUTTON_INDEX = 14, + _GAMEPAD_DPAD_RIGHT_BUTTON_INDEX = 15, + _THUMB_STICK_THRESHOLD = .75, + _leftThumbstickUpPressed = !1, + _leftThumbstickDownPressed = !1, + _leftThumbstickLeftPressed = !1, + _leftThumbstickRightPressed = !1, + _dPadUpPressed = !1, + _dPadDownPressed = !1, + _dPadLeftPressed = !1, + _dPadRightPressed = !1, + _gamepadAPressed = !1, + _gamepadBPressed = !1, + ProcessedButtons = [_GAMEPAD_DPAD_UP_BUTTON_INDEX, _GAMEPAD_DPAD_DOWN_BUTTON_INDEX, _GAMEPAD_DPAD_LEFT_BUTTON_INDEX, _GAMEPAD_DPAD_RIGHT_BUTTON_INDEX, _GAMEPAD_A_BUTTON_INDEX, _GAMEPAD_B_BUTTON_INDEX], + _ButtonPressedState = {}; + _ButtonPressedState.getgamepadA = function() { + return _gamepadAPressed + }, _ButtonPressedState.setgamepadA = function(newPressedState) { + raiseKeyEvent(_gamepadAPressed, newPressedState, "GamepadA", 0, !1, !0), _gamepadAPressed = newPressedState + }, _ButtonPressedState.getgamepadB = function() { + return _gamepadBPressed + }, _ButtonPressedState.setgamepadB = function(newPressedState) { + raiseKeyEvent(_gamepadBPressed, newPressedState, "GamepadB", 27), _gamepadBPressed = newPressedState + }, _ButtonPressedState.getleftThumbstickUp = function() { + return _leftThumbstickUpPressed + }, _ButtonPressedState.setleftThumbstickUp = function(newPressedState) { + raiseKeyEvent(_leftThumbstickUpPressed, newPressedState, "GamepadLeftThumbStickUp", 38, !0), _leftThumbstickUpPressed = newPressedState + }, _ButtonPressedState.getleftThumbstickDown = function() { + return _leftThumbstickDownPressed + }, _ButtonPressedState.setleftThumbstickDown = function(newPressedState) { + raiseKeyEvent(_leftThumbstickDownPressed, newPressedState, "GamepadLeftThumbStickDown", 40, !0), _leftThumbstickDownPressed = newPressedState + }, _ButtonPressedState.getleftThumbstickLeft = function() { + return _leftThumbstickLeftPressed + }, _ButtonPressedState.setleftThumbstickLeft = function(newPressedState) { + raiseKeyEvent(_leftThumbstickLeftPressed, newPressedState, "GamepadLeftThumbStickLeft", 37, !0), _leftThumbstickLeftPressed = newPressedState + }, _ButtonPressedState.getleftThumbstickRight = function() { + return _leftThumbstickRightPressed + }, _ButtonPressedState.setleftThumbstickRight = function(newPressedState) { + raiseKeyEvent(_leftThumbstickRightPressed, newPressedState, "GamepadLeftThumbStickRight", 39, !0), _leftThumbstickRightPressed = newPressedState + }, _ButtonPressedState.getdPadUp = function() { + return _dPadUpPressed + }, _ButtonPressedState.setdPadUp = function(newPressedState) { + raiseKeyEvent(_dPadUpPressed, newPressedState, "GamepadDPadUp", 38, !0), _dPadUpPressed = newPressedState + }, _ButtonPressedState.getdPadDown = function() { + return _dPadDownPressed + }, _ButtonPressedState.setdPadDown = function(newPressedState) { + raiseKeyEvent(_dPadDownPressed, newPressedState, "GamepadDPadDown", 40, !0), _dPadDownPressed = newPressedState + }, _ButtonPressedState.getdPadLeft = function() { + return _dPadLeftPressed + }, _ButtonPressedState.setdPadLeft = function(newPressedState) { + raiseKeyEvent(_dPadLeftPressed, newPressedState, "GamepadDPadLeft", 37, !0), _dPadLeftPressed = newPressedState + }, _ButtonPressedState.getdPadRight = function() { + return _dPadRightPressed + }, _ButtonPressedState.setdPadRight = function(newPressedState) { + raiseKeyEvent(_dPadRightPressed, newPressedState, "GamepadDPadRight", 39, !0), _dPadRightPressed = newPressedState + }; + var times = {}, + isElectron = -1 !== navigator.userAgent.toLowerCase().indexOf("electron"); + runInputLoop(), window.navigator && "string" == typeof window.navigator.gamepadInputEmulation && (window.navigator.gamepadInputEmulation = "gamepad") +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/input/mouse.js b/dashboard-ui/bower_components/emby-webcomponents/input/mouse.js index 12974e099e..56984561b0 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/input/mouse.js +++ b/dashboard-ui/bower_components/emby-webcomponents/input/mouse.js @@ -1 +1,75 @@ -define(["inputManager","focusManager","browser","layoutManager","events","dom"],function(inputmanager,focusManager,browser,layoutManager,events,dom){"use strict";function mouseIdleTime(){return(new Date).getTime()-lastMouseInputTime}function notifyApp(){inputmanager.notifyMouseMove()}function removeIdleClasses(){var classList=document.body.classList;classList.remove("mouseIdle"),classList.remove("mouseIdle-tv")}function addIdleClasses(){var classList=document.body.classList;classList.add("mouseIdle"),layoutManager.tv&&classList.add("mouseIdle-tv")}function onPointerMove(e){var eventX=e.screenX,eventY=e.screenY;if(void 0!==eventX||void 0!==eventY){var obj=lastPointerMoveData;if(!obj)return void(lastPointerMoveData={x:eventX,y:eventY});Math.abs(eventX-obj.x)<10&&Math.abs(eventY-obj.y)<10||(obj.x=eventX,obj.y=eventY,lastMouseInputTime=(new Date).getTime(),notifyApp(),isMouseIdle&&(isMouseIdle=!1,removeIdleClasses(),events.trigger(self,"mouseactive")))}}function onPointerEnter(e){if("mouse"===(e.pointerType||(layoutManager.mobile?"touch":"mouse"))&&!isMouseIdle){var parent=focusManager.focusableParent(e.target);parent&&focusManager.focus(parent)}}function enableFocusWithMouse(){return!!layoutManager.tv&&(!browser.web0s&&!!browser.tv)}function onMouseInterval(){!isMouseIdle&&mouseIdleTime()>=5e3&&(isMouseIdle=!0,addIdleClasses(),events.trigger(self,"mouseidle"))}function startMouseInterval(){mouseInterval||(mouseInterval=setInterval(onMouseInterval,5e3))}function stopMouseInterval(){var interval=mouseInterval;interval&&(clearInterval(interval),mouseInterval=null),removeIdleClasses()}function initMouse(){stopMouseInterval(),dom.removeEventListener(document,window.PointerEvent?"pointermove":"mousemove",onPointerMove,{passive:!0}),layoutManager.mobile||(startMouseInterval(),dom.addEventListener(document,window.PointerEvent?"pointermove":"mousemove",onPointerMove,{passive:!0})),dom.removeEventListener(document,window.PointerEvent?"pointerenter":"mouseenter",onPointerEnter,{capture:!0,passive:!0}),enableFocusWithMouse()&&dom.addEventListener(document,window.PointerEvent?"pointerenter":"mouseenter",onPointerEnter,{capture:!0,passive:!0})}var isMouseIdle,lastPointerMoveData,mouseInterval,self={},lastMouseInputTime=(new Date).getTime();return initMouse(),events.on(layoutManager,"modechange",initMouse),self}); \ No newline at end of file +define(["inputManager", "focusManager", "browser", "layoutManager", "events", "dom"], function(inputmanager, focusManager, browser, layoutManager, events, dom) { + "use strict"; + + function mouseIdleTime() { + return (new Date).getTime() - lastMouseInputTime + } + + function notifyApp() { + inputmanager.notifyMouseMove() + } + + function removeIdleClasses() { + var classList = document.body.classList; + classList.remove("mouseIdle"), classList.remove("mouseIdle-tv") + } + + function addIdleClasses() { + var classList = document.body.classList; + classList.add("mouseIdle"), layoutManager.tv && classList.add("mouseIdle-tv") + } + + function onPointerMove(e) { + var eventX = e.screenX, + eventY = e.screenY; + if (void 0 !== eventX || void 0 !== eventY) { + var obj = lastPointerMoveData; + if (!obj) return void(lastPointerMoveData = { + x: eventX, + y: eventY + }); + Math.abs(eventX - obj.x) < 10 && Math.abs(eventY - obj.y) < 10 || (obj.x = eventX, obj.y = eventY, lastMouseInputTime = (new Date).getTime(), notifyApp(), isMouseIdle && (isMouseIdle = !1, removeIdleClasses(), events.trigger(self, "mouseactive"))) + } + } + + function onPointerEnter(e) { + if ("mouse" === (e.pointerType || (layoutManager.mobile ? "touch" : "mouse")) && !isMouseIdle) { + var parent = focusManager.focusableParent(e.target); + parent && focusManager.focus(parent) + } + } + + function enableFocusWithMouse() { + return !!layoutManager.tv && (!browser.web0s && !!browser.tv) + } + + function onMouseInterval() { + !isMouseIdle && mouseIdleTime() >= 5e3 && (isMouseIdle = !0, addIdleClasses(), events.trigger(self, "mouseidle")) + } + + function startMouseInterval() { + mouseInterval || (mouseInterval = setInterval(onMouseInterval, 5e3)) + } + + function stopMouseInterval() { + var interval = mouseInterval; + interval && (clearInterval(interval), mouseInterval = null), removeIdleClasses() + } + + function initMouse() { + stopMouseInterval(), dom.removeEventListener(document, window.PointerEvent ? "pointermove" : "mousemove", onPointerMove, { + passive: !0 + }), layoutManager.mobile || (startMouseInterval(), dom.addEventListener(document, window.PointerEvent ? "pointermove" : "mousemove", onPointerMove, { + passive: !0 + })), dom.removeEventListener(document, window.PointerEvent ? "pointerenter" : "mouseenter", onPointerEnter, { + capture: !0, + passive: !0 + }), enableFocusWithMouse() && dom.addEventListener(document, window.PointerEvent ? "pointerenter" : "mouseenter", onPointerEnter, { + capture: !0, + passive: !0 + }) + } + var isMouseIdle, lastPointerMoveData, mouseInterval, self = {}, + lastMouseInputTime = (new Date).getTime(); + return initMouse(), events.on(layoutManager, "modechange", initMouse), self +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/inputmanager.js b/dashboard-ui/bower_components/emby-webcomponents/inputmanager.js index bd9b8062e0..2977f284e3 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/inputmanager.js +++ b/dashboard-ui/bower_components/emby-webcomponents/inputmanager.js @@ -1 +1,217 @@ -define(["playbackManager","focusManager","appRouter","dom"],function(playbackManager,focusManager,appRouter,dom){"use strict";function notify(){lastInputTime=(new Date).getTime(),handleCommand("unknown")}function notifyMouseMove(){lastInputTime=(new Date).getTime()}function idleTime(){return(new Date).getTime()-lastInputTime}function select(sourceElement){sourceElement.click()}function on(scope,fn){eventListenerCount++,dom.addEventListener(scope,"command",fn,{})}function off(scope,fn){eventListenerCount&&eventListenerCount--,dom.removeEventListener(scope,"command",fn,{})}function checkCommandTime(command){var last=commandTimes[command]||0,now=(new Date).getTime();return!(now-last<1e3)&&(commandTimes[command]=now,!0)}function handleCommand(name,options){lastInputTime=(new Date).getTime();var sourceElement=options?options.sourceElement:null;if(sourceElement&&(sourceElement=focusManager.focusableParent(sourceElement)),sourceElement=sourceElement||document.activeElement||window,eventListenerCount){var customEvent=new CustomEvent("command",{detail:{command:name},bubbles:!0,cancelable:!0});if(!sourceElement.dispatchEvent(customEvent))return}switch(name){case"up":focusManager.moveUp(sourceElement);break;case"down":focusManager.moveDown(sourceElement);break;case"left":focusManager.moveLeft(sourceElement);break;case"right":focusManager.moveRight(sourceElement);break;case"home":appRouter.goHome();break;case"settings":appRouter.showSettings();break;case"back":appRouter.back();break;case"forward":break;case"select":select(sourceElement);break;case"pageup":case"pagedown":case"end":break;case"menu":case"info":break;case"nextchapter":playbackManager.nextChapter();break;case"next":case"nexttrack":playbackManager.nextTrack();break;case"previous":case"previoustrack":playbackManager.previousTrack();break;case"previouschapter":playbackManager.previousChapter();break;case"guide":appRouter.showGuide();break;case"recordedtv":appRouter.showRecordedTV();break;case"record":break;case"livetv":appRouter.showLiveTV();break;case"mute":playbackManager.setMute(!0);break;case"unmute":playbackManager.setMute(!1);break;case"togglemute":playbackManager.toggleMute();break;case"channelup":playbackManager.channelUp();break;case"channeldown":playbackManager.channelDown();break;case"volumedown":playbackManager.volumeDown();break;case"volumeup":playbackManager.volumeUp();break;case"play":playbackManager.unpause();break;case"pause":playbackManager.pause();break;case"playpause":playbackManager.playPause();break;case"stop":checkCommandTime("stop")&&playbackManager.stop();break;case"changezoom":playbackManager.toggleAspectRatio();break;case"changeaudiotrack":playbackManager.changeAudioStream();break;case"changesubtitletrack":playbackManager.changeSubtitleStream();break;case"search":appRouter.showSearch();break;case"favorites":appRouter.showFavorites();break;case"fastforward":playbackManager.fastForward();break;case"rewind":playbackManager.rewind();break;case"togglefullscreen":playbackManager.toggleFullscreen();break;case"disabledisplaymirror":playbackManager.enableDisplayMirroring(!1);break;case"enabledisplaymirror":playbackManager.enableDisplayMirroring(!0);break;case"toggledisplaymirror":playbackManager.toggleDisplayMirroring();break;case"togglestats":break;case"movies":case"music":case"tv":appRouter.goHome();break;case"nowplaying":appRouter.showNowPlaying();break;case"save":case"screensaver":case"refresh":case"changebrightness":case"red":case"green":case"yellow":case"blue":case"grey":case"brown":break;case"repeatnone":playbackManager.setRepeatMode("RepeatNone");break;case"repeatall":playbackManager.setRepeatMode("RepeatAll");break;case"repeatone":playbackManager.setRepeatMode("RepeatOne")}}var lastInputTime=(new Date).getTime(),eventListenerCount=0,commandTimes={};return dom.addEventListener(document,"click",notify,{passive:!0}),{trigger:handleCommand,handle:handleCommand,notify:notify,notifyMouseMove:notifyMouseMove,idleTime:idleTime,on:on,off:off}}); \ No newline at end of file +define(["playbackManager", "focusManager", "appRouter", "dom"], function(playbackManager, focusManager, appRouter, dom) { + "use strict"; + + function notify() { + lastInputTime = (new Date).getTime(), handleCommand("unknown") + } + + function notifyMouseMove() { + lastInputTime = (new Date).getTime() + } + + function idleTime() { + return (new Date).getTime() - lastInputTime + } + + function select(sourceElement) { + sourceElement.click() + } + + function on(scope, fn) { + eventListenerCount++, dom.addEventListener(scope, "command", fn, {}) + } + + function off(scope, fn) { + eventListenerCount && eventListenerCount--, dom.removeEventListener(scope, "command", fn, {}) + } + + function checkCommandTime(command) { + var last = commandTimes[command] || 0, + now = (new Date).getTime(); + return !(now - last < 1e3) && (commandTimes[command] = now, !0) + } + + function handleCommand(name, options) { + lastInputTime = (new Date).getTime(); + var sourceElement = options ? options.sourceElement : null; + if (sourceElement && (sourceElement = focusManager.focusableParent(sourceElement)), sourceElement = sourceElement || document.activeElement || window, eventListenerCount) { + var customEvent = new CustomEvent("command", { + detail: { + command: name + }, + bubbles: !0, + cancelable: !0 + }); + if (!sourceElement.dispatchEvent(customEvent)) return + } + switch (name) { + case "up": + focusManager.moveUp(sourceElement); + break; + case "down": + focusManager.moveDown(sourceElement); + break; + case "left": + focusManager.moveLeft(sourceElement); + break; + case "right": + focusManager.moveRight(sourceElement); + break; + case "home": + appRouter.goHome(); + break; + case "settings": + appRouter.showSettings(); + break; + case "back": + appRouter.back(); + break; + case "forward": + break; + case "select": + select(sourceElement); + break; + case "pageup": + case "pagedown": + case "end": + break; + case "menu": + case "info": + break; + case "nextchapter": + playbackManager.nextChapter(); + break; + case "next": + case "nexttrack": + playbackManager.nextTrack(); + break; + case "previous": + case "previoustrack": + playbackManager.previousTrack(); + break; + case "previouschapter": + playbackManager.previousChapter(); + break; + case "guide": + appRouter.showGuide(); + break; + case "recordedtv": + appRouter.showRecordedTV(); + break; + case "record": + break; + case "livetv": + appRouter.showLiveTV(); + break; + case "mute": + playbackManager.setMute(!0); + break; + case "unmute": + playbackManager.setMute(!1); + break; + case "togglemute": + playbackManager.toggleMute(); + break; + case "channelup": + playbackManager.channelUp(); + break; + case "channeldown": + playbackManager.channelDown(); + break; + case "volumedown": + playbackManager.volumeDown(); + break; + case "volumeup": + playbackManager.volumeUp(); + break; + case "play": + playbackManager.unpause(); + break; + case "pause": + playbackManager.pause(); + break; + case "playpause": + playbackManager.playPause(); + break; + case "stop": + checkCommandTime("stop") && playbackManager.stop(); + break; + case "changezoom": + playbackManager.toggleAspectRatio(); + break; + case "changeaudiotrack": + playbackManager.changeAudioStream(); + break; + case "changesubtitletrack": + playbackManager.changeSubtitleStream(); + break; + case "search": + appRouter.showSearch(); + break; + case "favorites": + appRouter.showFavorites(); + break; + case "fastforward": + playbackManager.fastForward(); + break; + case "rewind": + playbackManager.rewind(); + break; + case "togglefullscreen": + playbackManager.toggleFullscreen(); + break; + case "disabledisplaymirror": + playbackManager.enableDisplayMirroring(!1); + break; + case "enabledisplaymirror": + playbackManager.enableDisplayMirroring(!0); + break; + case "toggledisplaymirror": + playbackManager.toggleDisplayMirroring(); + break; + case "togglestats": + break; + case "movies": + case "music": + case "tv": + appRouter.goHome(); + break; + case "nowplaying": + appRouter.showNowPlaying(); + break; + case "save": + case "screensaver": + case "refresh": + case "changebrightness": + case "red": + case "green": + case "yellow": + case "blue": + case "grey": + case "brown": + break; + case "repeatnone": + playbackManager.setRepeatMode("RepeatNone"); + break; + case "repeatall": + playbackManager.setRepeatMode("RepeatAll"); + break; + case "repeatone": + playbackManager.setRepeatMode("RepeatOne") + } + } + var lastInputTime = (new Date).getTime(), + eventListenerCount = 0, + commandTimes = {}; + return dom.addEventListener(document, "click", notify, { + passive: !0 + }), { + trigger: handleCommand, + handle: handleCommand, + notify: notify, + notifyMouseMove: notifyMouseMove, + idleTime: idleTime, + on: on, + off: off + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/itemcontextmenu.js b/dashboard-ui/bower_components/emby-webcomponents/itemcontextmenu.js index 04d17bfbcb..ff139c934e 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/itemcontextmenu.js +++ b/dashboard-ui/bower_components/emby-webcomponents/itemcontextmenu.js @@ -1 +1,359 @@ -define(["apphost","globalize","connectionManager","itemHelper","appRouter","playbackManager","loading","appSettings","browser","actionsheet"],function(appHost,globalize,connectionManager,itemHelper,appRouter,playbackManager,loading,appSettings,browser,actionsheet){"use strict";function getCommands(options){var item=options.item,canPlay=playbackManager.canPlay(item),commands=[],user=options.user,restrictOptions=(browser.operaTv||browser.web0s)&&!user.Policy.IsAdministrator;canPlay&&"Photo"!==item.MediaType&&(!1!==options.play&&commands.push({name:globalize.translate("sharedcomponents#Play"),id:"resume"}),options.playAllFromHere&&"Program"!==item.Type&&"TvChannel"!==item.Type&&commands.push({name:globalize.translate("sharedcomponents#PlayAllFromHere"),id:"playallfromhere"})),playbackManager.canQueue(item)&&(!1!==options.queue&&commands.push({name:globalize.translate("sharedcomponents#AddToPlayQueue"),id:"queue"}),!1!==options.queue&&commands.push({name:globalize.translate("sharedcomponents#PlayNext"),id:"queuenext"})),(item.IsFolder||"MusicArtist"===item.Type||"MusicGenre"===item.Type)&&"livetv"!==item.CollectionType&&!1!==options.shuffle&&commands.push({name:globalize.translate("sharedcomponents#Shuffle"),id:"shuffle"}),"Audio"!==item.MediaType&&"MusicAlbum"!==item.Type&&"MusicArtist"!==item.Type&&"MusicGenre"!==item.Type||!1===options.instantMix||itemHelper.isLocalItem(item)||commands.push({name:globalize.translate("sharedcomponents#InstantMix"),id:"instantmix"}),commands.length&&commands.push({divider:!0}),restrictOptions||(itemHelper.supportsAddingToCollection(item)&&commands.push({name:globalize.translate("sharedcomponents#AddToCollection"),id:"addtocollection"}),itemHelper.supportsAddingToPlaylist(item)&&commands.push({name:globalize.translate("sharedcomponents#AddToPlaylist"),id:"addtoplaylist"})),"Timer"===item.Type&&user.Policy.EnableLiveTvManagement&&!1!==options.cancelTimer&&commands.push({name:globalize.translate("sharedcomponents#CancelRecording"),id:"canceltimer"}),"Recording"===item.Type&&"InProgress"===item.Status&&user.Policy.EnableLiveTvManagement&&!1!==options.cancelTimer&&commands.push({name:globalize.translate("sharedcomponents#CancelRecording"),id:"canceltimer"}),"SeriesTimer"===item.Type&&user.Policy.EnableLiveTvManagement&&!1!==options.cancelTimer&&commands.push({name:globalize.translate("sharedcomponents#CancelSeries"),id:"cancelseriestimer"}),itemHelper.canConvert(item,user,connectionManager.getApiClient(item))&&commands.push({name:globalize.translate("sharedcomponents#Convert"),id:"convert"}),item.CanDelete&&!1!==options.deleteItem&&("Playlist"===item.Type||"BoxSet"===item.Type?commands.push({name:globalize.translate("sharedcomponents#Delete"),id:"delete"}):commands.push({name:globalize.translate("sharedcomponents#DeleteMedia"),id:"delete"})),item.CanDownload&&appHost.supports("filedownload")&&commands.push({name:globalize.translate("sharedcomponents#Download"),id:"download"}),appHost.supports("sync")&&!1!==options.syncLocal&&itemHelper.canSync(user,item)&&commands.push({name:globalize.translate("sharedcomponents#Download"),id:"synclocal"});var canEdit=itemHelper.canEdit(user,item);if(canEdit&&!1!==options.edit&&"SeriesTimer"!==item.Type){var text="Timer"===item.Type||"SeriesTimer"===item.Type?globalize.translate("sharedcomponents#Edit"):globalize.translate("sharedcomponents#EditMetadata");commands.push({name:text,id:"edit"})}return itemHelper.canEditImages(user,item)&&!1!==options.editImages&&commands.push({name:globalize.translate("sharedcomponents#EditImages"),id:"editimages"}),canEdit&&("Video"!==item.MediaType||"TvChannel"===item.Type||"Program"===item.Type||"Virtual"===item.LocationType||"Recording"===item.Type&&"Completed"!==item.Status||!1!==options.editSubtitles&&commands.push({name:globalize.translate("sharedcomponents#EditSubtitles"),id:"editsubtitles"})),!1!==options.identify&&itemHelper.canIdentify(user,item)&&commands.push({name:globalize.translate("sharedcomponents#Identify"),id:"identify"}),"Program"===item.Type&&!1!==options.record&&item.TimerId&&commands.push({name:Globalize.translate("sharedcomponents#ManageRecording"),id:"record"}),"Program"===item.Type&&!1!==options.record&&(item.TimerId||commands.push({name:Globalize.translate("sharedcomponents#Record"),id:"record"})),itemHelper.canRefreshMetadata(item,user)&&commands.push({name:globalize.translate("sharedcomponents#RefreshMetadata"),id:"refresh"}),item.PlaylistItemId&&options.playlistId&&commands.push({name:globalize.translate("sharedcomponents#RemoveFromPlaylist"),id:"removefromplaylist"}),options.collectionId&&commands.push({name:globalize.translate("sharedcomponents#RemoveFromCollection"),id:"removefromcollection"}),restrictOptions||!0===options.share&&itemHelper.canShare(item,user)&&commands.push({name:globalize.translate("sharedcomponents#Share"),id:"share"}),!1!==options.sync&&itemHelper.canSync(user,item)&&commands.push({name:globalize.translate("sharedcomponents#Sync"),id:"sync"}),!1!==options.openAlbum&&item.AlbumId&&"Photo"!==item.MediaType&&commands.push({name:Globalize.translate("sharedcomponents#ViewAlbum"),id:"album"}),!1!==options.openArtist&&item.ArtistItems&&item.ArtistItems.length&&commands.push({name:Globalize.translate("sharedcomponents#ViewArtist"),id:"artist"}),commands}function getResolveFunction(resolve,id,changed,deleted){return function(){resolve({command:id,updated:changed,deleted:deleted})}}function executeCommand(item,id,options){var itemId=item.Id,serverId=item.ServerId,apiClient=connectionManager.getApiClient(serverId);return new Promise(function(resolve,reject){switch(id){case"addtocollection":require(["collectionEditor"],function(collectionEditor){(new collectionEditor).show({items:[itemId],serverId:serverId}).then(getResolveFunction(resolve,id,!0),getResolveFunction(resolve,id))});break;case"addtoplaylist":require(["playlistEditor"],function(playlistEditor){(new playlistEditor).show({items:[itemId],serverId:serverId}).then(getResolveFunction(resolve,id,!0),getResolveFunction(resolve,id))});break;case"download":require(["fileDownloader"],function(fileDownloader){var downloadHref=apiClient.getItemDownloadUrl(itemId);fileDownloader.download([{url:downloadHref,itemId:itemId,serverId:serverId}]),getResolveFunction(getResolveFunction(resolve,id),id)()});break;case"editsubtitles":require(["subtitleEditor"],function(subtitleEditor){subtitleEditor.show(itemId,serverId).then(getResolveFunction(resolve,id,!0),getResolveFunction(resolve,id))});break;case"edit":editItem(apiClient,item).then(getResolveFunction(resolve,id,!0),getResolveFunction(resolve,id));break;case"editimages":require(["imageEditor"],function(imageEditor){imageEditor.show({itemId:itemId,serverId:serverId}).then(getResolveFunction(resolve,id,!0),getResolveFunction(resolve,id))});break;case"identify":require(["itemIdentifier"],function(itemIdentifier){itemIdentifier.show(itemId,serverId).then(getResolveFunction(resolve,id,!0),getResolveFunction(resolve,id))});break;case"refresh":refresh(apiClient,item),getResolveFunction(resolve,id)();break;case"open":appRouter.showItem(item),getResolveFunction(resolve,id)();break;case"play":play(item,!1),getResolveFunction(resolve,id)();break;case"resume":play(item,!0),getResolveFunction(resolve,id)();break;case"queue":play(item,!1,!0),getResolveFunction(resolve,id)();break;case"queuenext":play(item,!1,!0,!0),getResolveFunction(resolve,id)();break;case"record":require(["recordingCreator"],function(recordingCreator){recordingCreator.show(itemId,serverId).then(getResolveFunction(resolve,id,!0),getResolveFunction(resolve,id))});break;case"shuffle":playbackManager.shuffle(item),getResolveFunction(resolve,id)();break;case"instantmix":playbackManager.instantMix(item),getResolveFunction(resolve,id)();break;case"delete":deleteItem(apiClient,item).then(getResolveFunction(resolve,id,!0,!0),getResolveFunction(resolve,id));break;case"share":navigator.share({title:item.Name,text:item.Overview,url:"https://emby.media"});break;case"album":appRouter.showItem(item.AlbumId,item.ServerId),getResolveFunction(resolve,id)();break;case"artist":appRouter.showItem(item.ArtistItems[0].Id,item.ServerId),getResolveFunction(resolve,id)();break;case"playallfromhere":case"queueallfromhere":getResolveFunction(resolve,id)();break;case"convert":require(["syncDialog"],function(syncDialog){syncDialog.showMenu({items:[item],serverId:serverId,mode:"convert"})}),getResolveFunction(resolve,id)();break;case"sync":require(["syncDialog"],function(syncDialog){syncDialog.showMenu({items:[item],serverId:serverId,mode:"sync"})}),getResolveFunction(resolve,id)();break;case"synclocal":require(["syncDialog"],function(syncDialog){syncDialog.showMenu({items:[item],serverId:serverId,mode:"download"})}),getResolveFunction(resolve,id)();break;case"removefromplaylist":apiClient.ajax({url:apiClient.getUrl("Playlists/"+options.playlistId+"/Items",{EntryIds:[item.PlaylistItemId].join(",")}),type:"DELETE"}).then(function(){getResolveFunction(resolve,id,!0)()});break;case"removefromcollection":apiClient.ajax({type:"DELETE",url:apiClient.getUrl("Collections/"+options.collectionId+"/Items",{Ids:[item.Id].join(",")})}).then(function(){getResolveFunction(resolve,id,!0)()});break;case"canceltimer":deleteTimer(apiClient,item,resolve,id);break;case"cancelseriestimer":deleteSeriesTimer(apiClient,item,resolve,id);break;default:reject()}})}function deleteTimer(apiClient,item,resolve,command){require(["recordingHelper"],function(recordingHelper){var timerId=item.TimerId||item.Id;recordingHelper.cancelTimerWithConfirmation(timerId,item.ServerId).then(function(){getResolveFunction(resolve,command,!0)()})})}function deleteSeriesTimer(apiClient,item,resolve,command){require(["recordingHelper"],function(recordingHelper){recordingHelper.cancelSeriesTimerWithConfirmation(item.Id,item.ServerId).then(function(){getResolveFunction(resolve,command,!0)()})})}function play(item,resume,queue,queueNext){var method=queue?queueNext?"queueNext":"queue":"play",startPosition=0;resume&&item.UserData&&item.UserData.PlaybackPositionTicks&&(startPosition=item.UserData.PlaybackPositionTicks),"Program"===item.Type?playbackManager[method]({ids:[item.ChannelId],startPositionTicks:startPosition,serverId:item.ServerId}):playbackManager[method]({items:[item],startPositionTicks:startPosition})}function editItem(apiClient,item){return new Promise(function(resolve,reject){var serverId=apiClient.serverInfo().Id;"Timer"===item.Type?require(["recordingEditor"],function(recordingEditor){recordingEditor.show(item.Id,serverId).then(resolve,reject)}):"SeriesTimer"===item.Type?require(["seriesRecordingEditor"],function(recordingEditor){recordingEditor.show(item.Id,serverId).then(resolve,reject)}):require(["metadataEditor"],function(metadataEditor){metadataEditor.show(item.Id,serverId).then(resolve,reject)})})}function deleteItem(apiClient,item){return new Promise(function(resolve,reject){require(["deleteHelper"],function(deleteHelper){deleteHelper.deleteItem({item:item,navigate:!1}).then(function(){resolve(!0)},reject)})})}function refresh(apiClient,item){require(["refreshDialog"],function(refreshDialog){new refreshDialog({itemIds:[item.Id],serverId:apiClient.serverInfo().Id,mode:"CollectionFolder"===item.Type?"scan":null}).show()})}function show(options){var commands=getCommands(options);return commands.length?actionsheet.show({items:commands,positionTo:options.positionTo,resolveOnClick:["share"]}).then(function(id){return executeCommand(options.item,id,options)}):Promise.reject()}return{getCommands:getCommands,show:show}}); \ No newline at end of file +define(["apphost", "globalize", "connectionManager", "itemHelper", "appRouter", "playbackManager", "loading", "appSettings", "browser", "actionsheet"], function(appHost, globalize, connectionManager, itemHelper, appRouter, playbackManager, loading, appSettings, browser, actionsheet) { + "use strict"; + + function getCommands(options) { + var item = options.item, + canPlay = playbackManager.canPlay(item), + commands = [], + user = options.user, + restrictOptions = (browser.operaTv || browser.web0s) && !user.Policy.IsAdministrator; + canPlay && "Photo" !== item.MediaType && (!1 !== options.play && commands.push({ + name: globalize.translate("sharedcomponents#Play"), + id: "resume" + }), options.playAllFromHere && "Program" !== item.Type && "TvChannel" !== item.Type && commands.push({ + name: globalize.translate("sharedcomponents#PlayAllFromHere"), + id: "playallfromhere" + })), playbackManager.canQueue(item) && (!1 !== options.queue && commands.push({ + name: globalize.translate("sharedcomponents#AddToPlayQueue"), + id: "queue" + }), !1 !== options.queue && commands.push({ + name: globalize.translate("sharedcomponents#PlayNext"), + id: "queuenext" + })), (item.IsFolder || "MusicArtist" === item.Type || "MusicGenre" === item.Type) && "livetv" !== item.CollectionType && !1 !== options.shuffle && commands.push({ + name: globalize.translate("sharedcomponents#Shuffle"), + id: "shuffle" + }), "Audio" !== item.MediaType && "MusicAlbum" !== item.Type && "MusicArtist" !== item.Type && "MusicGenre" !== item.Type || !1 === options.instantMix || itemHelper.isLocalItem(item) || commands.push({ + name: globalize.translate("sharedcomponents#InstantMix"), + id: "instantmix" + }), commands.length && commands.push({ + divider: !0 + }), restrictOptions || (itemHelper.supportsAddingToCollection(item) && commands.push({ + name: globalize.translate("sharedcomponents#AddToCollection"), + id: "addtocollection" + }), itemHelper.supportsAddingToPlaylist(item) && commands.push({ + name: globalize.translate("sharedcomponents#AddToPlaylist"), + id: "addtoplaylist" + })), "Timer" === item.Type && user.Policy.EnableLiveTvManagement && !1 !== options.cancelTimer && commands.push({ + name: globalize.translate("sharedcomponents#CancelRecording"), + id: "canceltimer" + }), "Recording" === item.Type && "InProgress" === item.Status && user.Policy.EnableLiveTvManagement && !1 !== options.cancelTimer && commands.push({ + name: globalize.translate("sharedcomponents#CancelRecording"), + id: "canceltimer" + }), "SeriesTimer" === item.Type && user.Policy.EnableLiveTvManagement && !1 !== options.cancelTimer && commands.push({ + name: globalize.translate("sharedcomponents#CancelSeries"), + id: "cancelseriestimer" + }), itemHelper.canConvert(item, user, connectionManager.getApiClient(item)) && commands.push({ + name: globalize.translate("sharedcomponents#Convert"), + id: "convert" + }), item.CanDelete && !1 !== options.deleteItem && ("Playlist" === item.Type || "BoxSet" === item.Type ? commands.push({ + name: globalize.translate("sharedcomponents#Delete"), + id: "delete" + }) : commands.push({ + name: globalize.translate("sharedcomponents#DeleteMedia"), + id: "delete" + })), item.CanDownload && appHost.supports("filedownload") && commands.push({ + name: globalize.translate("sharedcomponents#Download"), + id: "download" + }), appHost.supports("sync") && !1 !== options.syncLocal && itemHelper.canSync(user, item) && commands.push({ + name: globalize.translate("sharedcomponents#Download"), + id: "synclocal" + }); + var canEdit = itemHelper.canEdit(user, item); + if (canEdit && !1 !== options.edit && "SeriesTimer" !== item.Type) { + var text = "Timer" === item.Type || "SeriesTimer" === item.Type ? globalize.translate("sharedcomponents#Edit") : globalize.translate("sharedcomponents#EditMetadata"); + commands.push({ + name: text, + id: "edit" + }) + } + return itemHelper.canEditImages(user, item) && !1 !== options.editImages && commands.push({ + name: globalize.translate("sharedcomponents#EditImages"), + id: "editimages" + }), canEdit && ("Video" !== item.MediaType || "TvChannel" === item.Type || "Program" === item.Type || "Virtual" === item.LocationType || "Recording" === item.Type && "Completed" !== item.Status || !1 !== options.editSubtitles && commands.push({ + name: globalize.translate("sharedcomponents#EditSubtitles"), + id: "editsubtitles" + })), !1 !== options.identify && itemHelper.canIdentify(user, item) && commands.push({ + name: globalize.translate("sharedcomponents#Identify"), + id: "identify" + }), "Program" === item.Type && !1 !== options.record && item.TimerId && commands.push({ + name: Globalize.translate("sharedcomponents#ManageRecording"), + id: "record" + }), "Program" === item.Type && !1 !== options.record && (item.TimerId || commands.push({ + name: Globalize.translate("sharedcomponents#Record"), + id: "record" + })), itemHelper.canRefreshMetadata(item, user) && commands.push({ + name: globalize.translate("sharedcomponents#RefreshMetadata"), + id: "refresh" + }), item.PlaylistItemId && options.playlistId && commands.push({ + name: globalize.translate("sharedcomponents#RemoveFromPlaylist"), + id: "removefromplaylist" + }), options.collectionId && commands.push({ + name: globalize.translate("sharedcomponents#RemoveFromCollection"), + id: "removefromcollection" + }), restrictOptions || !0 === options.share && itemHelper.canShare(item, user) && commands.push({ + name: globalize.translate("sharedcomponents#Share"), + id: "share" + }), !1 !== options.sync && itemHelper.canSync(user, item) && commands.push({ + name: globalize.translate("sharedcomponents#Sync"), + id: "sync" + }), !1 !== options.openAlbum && item.AlbumId && "Photo" !== item.MediaType && commands.push({ + name: Globalize.translate("sharedcomponents#ViewAlbum"), + id: "album" + }), !1 !== options.openArtist && item.ArtistItems && item.ArtistItems.length && commands.push({ + name: Globalize.translate("sharedcomponents#ViewArtist"), + id: "artist" + }), commands + } + + function getResolveFunction(resolve, id, changed, deleted) { + return function() { + resolve({ + command: id, + updated: changed, + deleted: deleted + }) + } + } + + function executeCommand(item, id, options) { + var itemId = item.Id, + serverId = item.ServerId, + apiClient = connectionManager.getApiClient(serverId); + return new Promise(function(resolve, reject) { + switch (id) { + case "addtocollection": + require(["collectionEditor"], function(collectionEditor) { + (new collectionEditor).show({ + items: [itemId], + serverId: serverId + }).then(getResolveFunction(resolve, id, !0), getResolveFunction(resolve, id)) + }); + break; + case "addtoplaylist": + require(["playlistEditor"], function(playlistEditor) { + (new playlistEditor).show({ + items: [itemId], + serverId: serverId + }).then(getResolveFunction(resolve, id, !0), getResolveFunction(resolve, id)) + }); + break; + case "download": + require(["fileDownloader"], function(fileDownloader) { + var downloadHref = apiClient.getItemDownloadUrl(itemId); + fileDownloader.download([{ + url: downloadHref, + itemId: itemId, + serverId: serverId + }]), getResolveFunction(getResolveFunction(resolve, id), id)() + }); + break; + case "editsubtitles": + require(["subtitleEditor"], function(subtitleEditor) { + subtitleEditor.show(itemId, serverId).then(getResolveFunction(resolve, id, !0), getResolveFunction(resolve, id)) + }); + break; + case "edit": + editItem(apiClient, item).then(getResolveFunction(resolve, id, !0), getResolveFunction(resolve, id)); + break; + case "editimages": + require(["imageEditor"], function(imageEditor) { + imageEditor.show({ + itemId: itemId, + serverId: serverId + }).then(getResolveFunction(resolve, id, !0), getResolveFunction(resolve, id)) + }); + break; + case "identify": + require(["itemIdentifier"], function(itemIdentifier) { + itemIdentifier.show(itemId, serverId).then(getResolveFunction(resolve, id, !0), getResolveFunction(resolve, id)) + }); + break; + case "refresh": + refresh(apiClient, item), getResolveFunction(resolve, id)(); + break; + case "open": + appRouter.showItem(item), getResolveFunction(resolve, id)(); + break; + case "play": + play(item, !1), getResolveFunction(resolve, id)(); + break; + case "resume": + play(item, !0), getResolveFunction(resolve, id)(); + break; + case "queue": + play(item, !1, !0), getResolveFunction(resolve, id)(); + break; + case "queuenext": + play(item, !1, !0, !0), getResolveFunction(resolve, id)(); + break; + case "record": + require(["recordingCreator"], function(recordingCreator) { + recordingCreator.show(itemId, serverId).then(getResolveFunction(resolve, id, !0), getResolveFunction(resolve, id)) + }); + break; + case "shuffle": + playbackManager.shuffle(item), getResolveFunction(resolve, id)(); + break; + case "instantmix": + playbackManager.instantMix(item), getResolveFunction(resolve, id)(); + break; + case "delete": + deleteItem(apiClient, item).then(getResolveFunction(resolve, id, !0, !0), getResolveFunction(resolve, id)); + break; + case "share": + navigator.share({ + title: item.Name, + text: item.Overview, + url: "https://emby.media" + }); + break; + case "album": + appRouter.showItem(item.AlbumId, item.ServerId), getResolveFunction(resolve, id)(); + break; + case "artist": + appRouter.showItem(item.ArtistItems[0].Id, item.ServerId), getResolveFunction(resolve, id)(); + break; + case "playallfromhere": + case "queueallfromhere": + getResolveFunction(resolve, id)(); + break; + case "convert": + require(["syncDialog"], function(syncDialog) { + syncDialog.showMenu({ + items: [item], + serverId: serverId, + mode: "convert" + }) + }), getResolveFunction(resolve, id)(); + break; + case "sync": + require(["syncDialog"], function(syncDialog) { + syncDialog.showMenu({ + items: [item], + serverId: serverId, + mode: "sync" + }) + }), getResolveFunction(resolve, id)(); + break; + case "synclocal": + require(["syncDialog"], function(syncDialog) { + syncDialog.showMenu({ + items: [item], + serverId: serverId, + mode: "download" + }) + }), getResolveFunction(resolve, id)(); + break; + case "removefromplaylist": + apiClient.ajax({ + url: apiClient.getUrl("Playlists/" + options.playlistId + "/Items", { + EntryIds: [item.PlaylistItemId].join(",") + }), + type: "DELETE" + }).then(function() { + getResolveFunction(resolve, id, !0)() + }); + break; + case "removefromcollection": + apiClient.ajax({ + type: "DELETE", + url: apiClient.getUrl("Collections/" + options.collectionId + "/Items", { + Ids: [item.Id].join(",") + }) + }).then(function() { + getResolveFunction(resolve, id, !0)() + }); + break; + case "canceltimer": + deleteTimer(apiClient, item, resolve, id); + break; + case "cancelseriestimer": + deleteSeriesTimer(apiClient, item, resolve, id); + break; + default: + reject() + } + }) + } + + function deleteTimer(apiClient, item, resolve, command) { + require(["recordingHelper"], function(recordingHelper) { + var timerId = item.TimerId || item.Id; + recordingHelper.cancelTimerWithConfirmation(timerId, item.ServerId).then(function() { + getResolveFunction(resolve, command, !0)() + }) + }) + } + + function deleteSeriesTimer(apiClient, item, resolve, command) { + require(["recordingHelper"], function(recordingHelper) { + recordingHelper.cancelSeriesTimerWithConfirmation(item.Id, item.ServerId).then(function() { + getResolveFunction(resolve, command, !0)() + }) + }) + } + + function play(item, resume, queue, queueNext) { + var method = queue ? queueNext ? "queueNext" : "queue" : "play", + startPosition = 0; + resume && item.UserData && item.UserData.PlaybackPositionTicks && (startPosition = item.UserData.PlaybackPositionTicks), "Program" === item.Type ? playbackManager[method]({ + ids: [item.ChannelId], + startPositionTicks: startPosition, + serverId: item.ServerId + }) : playbackManager[method]({ + items: [item], + startPositionTicks: startPosition + }) + } + + function editItem(apiClient, item) { + return new Promise(function(resolve, reject) { + var serverId = apiClient.serverInfo().Id; + "Timer" === item.Type ? require(["recordingEditor"], function(recordingEditor) { + recordingEditor.show(item.Id, serverId).then(resolve, reject) + }) : "SeriesTimer" === item.Type ? require(["seriesRecordingEditor"], function(recordingEditor) { + recordingEditor.show(item.Id, serverId).then(resolve, reject) + }) : require(["metadataEditor"], function(metadataEditor) { + metadataEditor.show(item.Id, serverId).then(resolve, reject) + }) + }) + } + + function deleteItem(apiClient, item) { + return new Promise(function(resolve, reject) { + require(["deleteHelper"], function(deleteHelper) { + deleteHelper.deleteItem({ + item: item, + navigate: !1 + }).then(function() { + resolve(!0) + }, reject) + }) + }) + } + + function refresh(apiClient, item) { + require(["refreshDialog"], function(refreshDialog) { + new refreshDialog({ + itemIds: [item.Id], + serverId: apiClient.serverInfo().Id, + mode: "CollectionFolder" === item.Type ? "scan" : null + }).show() + }) + } + + function show(options) { + var commands = getCommands(options); + return commands.length ? actionsheet.show({ + items: commands, + positionTo: options.positionTo, + resolveOnClick: ["share"] + }).then(function(id) { + return executeCommand(options.item, id, options) + }) : Promise.reject() + } + return { + getCommands: getCommands, + show: show + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/itemhelper.js b/dashboard-ui/bower_components/emby-webcomponents/itemhelper.js index 92bfb9d570..4dc99ca3c6 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/itemhelper.js +++ b/dashboard-ui/bower_components/emby-webcomponents/itemhelper.js @@ -1 +1,92 @@ -define(["apphost","globalize"],function(appHost,globalize){"use strict";function getDisplayName(item,options){if(!item)throw new Error("null item passed into getDisplayName");options=options||{},"Timer"===item.Type&&(item=item.ProgramInfo||item);var name=("Program"!==item.Type&&"Recording"!==item.Type||!item.IsSeries&&!item.EpisodeTitle?item.Name:item.EpisodeTitle)||"";if("TvChannel"===item.Type)return item.ChannelNumber?item.ChannelNumber+" "+name:name;if("Episode"===item.Type&&0===item.ParentIndexNumber)name=globalize.translate("sharedcomponents#ValueSpecialEpisodeName",name);else if(("Episode"===item.Type||"Program"===item.Type)&&null!=item.IndexNumber&&null!=item.ParentIndexNumber&&!1!==options.includeIndexNumber){var displayIndexNumber=item.IndexNumber,number=displayIndexNumber,nameSeparator=" - ";!1!==options.includeParentInfo?number="S"+item.ParentIndexNumber+":E"+number:nameSeparator=". ",item.IndexNumberEnd&&(displayIndexNumber=item.IndexNumberEnd,number+="-"+displayIndexNumber),number&&(name=name?number+nameSeparator+name:number)}return name}function supportsAddingToCollection(item){var invalidTypes=["Genre","MusicGenre","Studio","GameGenre","UserView","CollectionFolder","Audio","Program","Timer","SeriesTimer"];return("Recording"!==item.Type||"Completed"===item.Status)&&(!item.CollectionType&&-1===invalidTypes.indexOf(item.Type)&&"Photo"!==item.MediaType&&!isLocalItem(item))}function supportsAddingToPlaylist(item){return"Program"!==item.Type&&("TvChannel"!==item.Type&&("Timer"!==item.Type&&("SeriesTimer"!==item.Type&&("Photo"!==item.MediaType&&(("Recording"!==item.Type||"Completed"===item.Status)&&(!isLocalItem(item)&&("livetv"!==item.CollectionType&&(item.MediaType||item.IsFolder||"Genre"===item.Type||"MusicGenre"===item.Type||"MusicArtist"===item.Type))))))))}function canEdit(user,item){var itemType=item.Type;return"UserRootFolder"!==itemType&&"UserView"!==itemType&&("Program"!==itemType&&("Timer"!==itemType&&("SeriesTimer"!==itemType&&(("Recording"!==item.Type||"Completed"===item.Status)&&(!isLocalItem(item)&&user.Policy.IsAdministrator)))))}function isLocalItem(item){return!(!item||!item.Id||0!==item.Id.indexOf("local"))}return{getDisplayName:getDisplayName,supportsAddingToCollection:supportsAddingToCollection,supportsAddingToPlaylist:supportsAddingToPlaylist,isLocalItem:isLocalItem,canIdentify:function(user,item){var itemType=item.Type;return!("Movie"!==itemType&&"Trailer"!==itemType&&"Series"!==itemType&&"Game"!==itemType&&"BoxSet"!==itemType&&"Person"!==itemType&&"Book"!==itemType&&"MusicAlbum"!==itemType&&"MusicArtist"!==itemType&&"MusicVideo"!==itemType||!user.Policy.IsAdministrator||isLocalItem(item))},canEdit:canEdit,canEditImages:function(user,item){var itemType=item.Type;return"Photo"!==item.MediaType&&("UserView"===itemType?!!user.Policy.IsAdministrator:("Recording"!==item.Type||"Completed"===item.Status)&&("Timer"!==itemType&&"SeriesTimer"!==itemType&&canEdit(user,item)&&!isLocalItem(item)))},canSync:function(user,item){return!(user&&!user.Policy.EnableContentDownloading)&&(!isLocalItem(item)&&item.SupportsSync)},canShare:function(item,user){return"Program"!==item.Type&&("TvChannel"!==item.Type&&("Timer"!==item.Type&&("SeriesTimer"!==item.Type&&(("Recording"!==item.Type||"Completed"===item.Status)&&(!isLocalItem(item)&&(user.Policy.EnablePublicSharing&&appHost.supports("sharing")))))))},enableDateAddedDisplay:function(item){return!item.IsFolder&&item.MediaType&&"Program"!==item.Type&&"TvChannel"!==item.Type&&"Trailer"!==item.Type},canMarkPlayed:function(item){if("Program"===item.Type)return!1;if("Video"===item.MediaType){if("TvChannel"!==item.Type)return!0}else if("Audio"===item.MediaType){if("AudioPodcast"===item.Type)return!0;if("AudioBook"===item.Type)return!0}return"Series"===item.Type||"Season"===item.Type||"BoxSet"===item.Type||"Game"===item.MediaType||"Book"===item.MediaType||"Recording"===item.MediaType},canRate:function(item){return"Program"!==item.Type&&"Timer"!==item.Type&&"SeriesTimer"!==item.Type&&"CollectionFolder"!==item.Type&&"UserView"!==item.Type&&"Channel"!==item.Type&&"Season"!==item.Type&&"Studio"!==item.Type&&!!item.UserData},canConvert:function(item,user){if(!user.Policy.EnableMediaConversion)return!1;if(isLocalItem(item))return!1;var mediaType=item.MediaType;if("Book"===mediaType||"Photo"===mediaType||"Game"===mediaType||"Audio"===mediaType)return!1;if("livetv"===item.CollectionType)return!1;var type=item.Type;return"Channel"!==type&&"Person"!==type&&"Year"!==type&&"Program"!==type&&"Timer"!==type&&"SeriesTimer"!==type&&(!("Virtual"===item.LocationType&&!item.IsFolder)&&!item.IsPlaceHolder)},canRefreshMetadata:function(item,user){if(user.Policy.IsAdministrator){if("livetv"===item.CollectionType)return!1;if("Timer"!==item.Type&&"SeriesTimer"!==item.Type&&"Program"!==item.Type&&"TvChannel"!==item.Type&&("Recording"!==item.Type||"Completed"===item.Status)&&!isLocalItem(item))return!0}return!1},supportsMediaSourceSelection:function(item){return"Video"===item.MediaType&&("TvChannel"!==item.Type&&(!(!item.MediaSources||1===item.MediaSources.length&&"Placeholder"===item.MediaSources[0].Type)&&(!1!==item.EnableMediaSourceDisplay&&(null!=item.EnableMediaSourceDisplay||!item.SourceType||"Library"===item.SourceType))))}}}); \ No newline at end of file +define(["apphost", "globalize"], function(appHost, globalize) { + "use strict"; + + function getDisplayName(item, options) { + if (!item) throw new Error("null item passed into getDisplayName"); + options = options || {}, "Timer" === item.Type && (item = item.ProgramInfo || item); + var name = ("Program" !== item.Type && "Recording" !== item.Type || !item.IsSeries && !item.EpisodeTitle ? item.Name : item.EpisodeTitle) || ""; + if ("TvChannel" === item.Type) return item.ChannelNumber ? item.ChannelNumber + " " + name : name; + if ("Episode" === item.Type && 0 === item.ParentIndexNumber) name = globalize.translate("sharedcomponents#ValueSpecialEpisodeName", name); + else if (("Episode" === item.Type || "Program" === item.Type) && null != item.IndexNumber && null != item.ParentIndexNumber && !1 !== options.includeIndexNumber) { + var displayIndexNumber = item.IndexNumber, + number = displayIndexNumber, + nameSeparator = " - "; + !1 !== options.includeParentInfo ? number = "S" + item.ParentIndexNumber + ":E" + number : nameSeparator = ". ", item.IndexNumberEnd && (displayIndexNumber = item.IndexNumberEnd, number += "-" + displayIndexNumber), number && (name = name ? number + nameSeparator + name : number) + } + return name + } + + function supportsAddingToCollection(item) { + var invalidTypes = ["Genre", "MusicGenre", "Studio", "GameGenre", "UserView", "CollectionFolder", "Audio", "Program", "Timer", "SeriesTimer"]; + return ("Recording" !== item.Type || "Completed" === item.Status) && (!item.CollectionType && -1 === invalidTypes.indexOf(item.Type) && "Photo" !== item.MediaType && !isLocalItem(item)) + } + + function supportsAddingToPlaylist(item) { + return "Program" !== item.Type && ("TvChannel" !== item.Type && ("Timer" !== item.Type && ("SeriesTimer" !== item.Type && ("Photo" !== item.MediaType && (("Recording" !== item.Type || "Completed" === item.Status) && (!isLocalItem(item) && ("livetv" !== item.CollectionType && (item.MediaType || item.IsFolder || "Genre" === item.Type || "MusicGenre" === item.Type || "MusicArtist" === item.Type)))))))) + } + + function canEdit(user, item) { + var itemType = item.Type; + return "UserRootFolder" !== itemType && "UserView" !== itemType && ("Program" !== itemType && ("Timer" !== itemType && ("SeriesTimer" !== itemType && (("Recording" !== item.Type || "Completed" === item.Status) && (!isLocalItem(item) && user.Policy.IsAdministrator))))) + } + + function isLocalItem(item) { + return !(!item || !item.Id || 0 !== item.Id.indexOf("local")) + } + return { + getDisplayName: getDisplayName, + supportsAddingToCollection: supportsAddingToCollection, + supportsAddingToPlaylist: supportsAddingToPlaylist, + isLocalItem: isLocalItem, + canIdentify: function(user, item) { + var itemType = item.Type; + return !("Movie" !== itemType && "Trailer" !== itemType && "Series" !== itemType && "Game" !== itemType && "BoxSet" !== itemType && "Person" !== itemType && "Book" !== itemType && "MusicAlbum" !== itemType && "MusicArtist" !== itemType && "MusicVideo" !== itemType || !user.Policy.IsAdministrator || isLocalItem(item)) + }, + canEdit: canEdit, + canEditImages: function(user, item) { + var itemType = item.Type; + return "Photo" !== item.MediaType && ("UserView" === itemType ? !!user.Policy.IsAdministrator : ("Recording" !== item.Type || "Completed" === item.Status) && ("Timer" !== itemType && "SeriesTimer" !== itemType && canEdit(user, item) && !isLocalItem(item))) + }, + canSync: function(user, item) { + return !(user && !user.Policy.EnableContentDownloading) && (!isLocalItem(item) && item.SupportsSync) + }, + canShare: function(item, user) { + return "Program" !== item.Type && ("TvChannel" !== item.Type && ("Timer" !== item.Type && ("SeriesTimer" !== item.Type && (("Recording" !== item.Type || "Completed" === item.Status) && (!isLocalItem(item) && (user.Policy.EnablePublicSharing && appHost.supports("sharing"))))))) + }, + enableDateAddedDisplay: function(item) { + return !item.IsFolder && item.MediaType && "Program" !== item.Type && "TvChannel" !== item.Type && "Trailer" !== item.Type + }, + canMarkPlayed: function(item) { + if ("Program" === item.Type) return !1; + if ("Video" === item.MediaType) { + if ("TvChannel" !== item.Type) return !0 + } else if ("Audio" === item.MediaType) { + if ("AudioPodcast" === item.Type) return !0; + if ("AudioBook" === item.Type) return !0 + } + return "Series" === item.Type || "Season" === item.Type || "BoxSet" === item.Type || "Game" === item.MediaType || "Book" === item.MediaType || "Recording" === item.MediaType + }, + canRate: function(item) { + return "Program" !== item.Type && "Timer" !== item.Type && "SeriesTimer" !== item.Type && "CollectionFolder" !== item.Type && "UserView" !== item.Type && "Channel" !== item.Type && "Season" !== item.Type && "Studio" !== item.Type && !!item.UserData + }, + canConvert: function(item, user) { + if (!user.Policy.EnableMediaConversion) return !1; + if (isLocalItem(item)) return !1; + var mediaType = item.MediaType; + if ("Book" === mediaType || "Photo" === mediaType || "Game" === mediaType || "Audio" === mediaType) return !1; + if ("livetv" === item.CollectionType) return !1; + var type = item.Type; + return "Channel" !== type && "Person" !== type && "Year" !== type && "Program" !== type && "Timer" !== type && "SeriesTimer" !== type && (!("Virtual" === item.LocationType && !item.IsFolder) && !item.IsPlaceHolder) + }, + canRefreshMetadata: function(item, user) { + if (user.Policy.IsAdministrator) { + if ("livetv" === item.CollectionType) return !1; + if ("Timer" !== item.Type && "SeriesTimer" !== item.Type && "Program" !== item.Type && "TvChannel" !== item.Type && ("Recording" !== item.Type || "Completed" === item.Status) && !isLocalItem(item)) return !0 + } + return !1 + }, + supportsMediaSourceSelection: function(item) { + return "Video" === item.MediaType && ("TvChannel" !== item.Type && (!(!item.MediaSources || 1 === item.MediaSources.length && "Placeholder" === item.MediaSources[0].Type) && (!1 !== item.EnableMediaSourceDisplay && (null != item.EnableMediaSourceDisplay || !item.SourceType || "Library" === item.SourceType)))) + } + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/itemidentifier/itemidentifier.js b/dashboard-ui/bower_components/emby-webcomponents/itemidentifier/itemidentifier.js index fefded7f81..3024bee3d1 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/itemidentifier/itemidentifier.js +++ b/dashboard-ui/bower_components/emby-webcomponents/itemidentifier/itemidentifier.js @@ -1 +1,192 @@ -define(["dialogHelper","loading","connectionManager","require","globalize","scrollHelper","layoutManager","focusManager","browser","emby-input","emby-checkbox","paper-icon-button-light","css!./../formdialog","material-icons","cardStyle"],function(dialogHelper,loading,connectionManager,require,globalize,scrollHelper,layoutManager,focusManager,browser){"use strict";function getApiClient(){return connectionManager.getApiClient(currentServerId)}function searchForIdentificationResults(page){var i,length,value,lookupInfo={ProviderIds:{}},identifyField=page.querySelectorAll(".identifyField");for(i=0,length=identifyField.length;i");if(identifyResult.ImageUrl){resultHtml='
'+resultHtml+"
"}page.querySelector(".selectedSearchResult").innerHTML=resultHtml,focusManager.focus(identifyOptionsForm.querySelector(".btnSubmit"))}function getSearchResultHtml(result,index){var padderClass,html="",cssClass="card scalableCard",cardBoxCssClass="cardBox";if("Episode"===currentItemType?(cssClass+=" backdropCard backdropCard-scalable",padderClass="cardPadder-backdrop"):"MusicAlbum"===currentItemType||"MusicArtist"===currentItemType?(cssClass+=" squareCard squareCard-scalable",padderClass="cardPadder-square"):(cssClass+=" portraitCard portraitCard-scalable",padderClass="cardPadder-portrait"),layoutManager.tv&&!browser.slow&&(cardBoxCssClass+=" cardBox-focustransform"),cardBoxCssClass+=" cardBox-bottompadded",layoutManager.tv&&(cardBoxCssClass+=" card-focuscontent cardBox-withfocuscontent"),html+='"}function getSearchImageDisplayUrl(url,provider){return getApiClient().getUrl("Items/RemoteSearch/Image",{imageUrl:url,ProviderName:provider})}function submitIdentficationResult(page){loading.show();var options={ReplaceAllImages:page.querySelector("#chkIdentifyReplaceImages").checked},apiClient=getApiClient();apiClient.ajax({type:"POST",url:apiClient.getUrl("Items/RemoteSearch/Apply/"+currentItem.Id,options),data:JSON.stringify(currentSearchResult),contentType:"application/json"}).then(function(){hasChanges=!0,loading.hide(),dialogHelper.close(page)},function(){loading.hide(),dialogHelper.close(page)})}function showIdentificationForm(page,item){var apiClient=getApiClient();apiClient.getJSON(apiClient.getUrl("Items/"+item.Id+"/ExternalIdInfos")).then(function(idList){for(var html="",providerIds=item.ProviderIds||{},i=0,length=idList.length;i';var idLabel=globalize.translate("sharedcomponents#LabelDynamicExternalId").replace("{0}",idInfo.Name);idInfo.Key;html+='',html+="
"}page.querySelector("#txtLookupName").value="","Person"===item.Type||"BoxSet"===item.Type?(page.querySelector(".fldLookupYear").classList.add("hide"),page.querySelector("#txtLookupYear").value=""):(page.querySelector(".fldLookupYear").classList.remove("hide"),page.querySelector("#txtLookupYear").value=""),page.querySelector(".identifyProviderIds").innerHTML=html,page.querySelector(".formDialogHeaderTitle").innerHTML=globalize.translate("sharedcomponents#Identify")})}function showEditor(itemId){loading.show(),require(["text!./itemidentifier.template.html"],function(template){var apiClient=getApiClient();apiClient.getItem(apiClient.getCurrentUserId(),itemId).then(function(item){currentItem=item,currentItemType=currentItem.Type;var dialogOptions={size:"fullscreen-border",removeOnClose:!0,scrollY:!1};layoutManager.tv&&(dialogOptions.size="fullscreen");var dlg=dialogHelper.createDialog(dialogOptions);dlg.classList.add("formDialog"),dlg.classList.add("recordingDialog");var html="";html+=globalize.translateDocument(template,"sharedcomponents"),dlg.innerHTML=html,dlg.addEventListener("close",onDialogClosed),layoutManager.tv&&scrollHelper.centerFocus.on(dlg.querySelector(".formDialogContent"),!1),dialogHelper.open(dlg),dlg.querySelector(".popupIdentifyForm").addEventListener("submit",function(e){return e.preventDefault(),searchForIdentificationResults(dlg),!1}),dlg.querySelector(".identifyOptionsForm").addEventListener("submit",function(e){return e.preventDefault(),submitIdentficationResult(dlg),!1}),dlg.querySelector(".btnCancel").addEventListener("click",function(e){dialogHelper.close(dlg)}),dlg.classList.add("identifyDialog"),showIdentificationForm(dlg,item),loading.hide()})})}function onDialogClosed(){loading.hide(),hasChanges?currentResolve():currentReject()}function showEditorFindNew(itemName,itemYear,itemType,resolveFunc){currentItem=null,currentItemType=itemType,require(["text!./itemidentifier.template.html"],function(template){var dialogOptions={size:"fullscreen-border",removeOnClose:!0,scrollY:!1};layoutManager.tv&&(dialogOptions.size="fullscreen");var dlg=dialogHelper.createDialog(dialogOptions);dlg.classList.add("formDialog"),dlg.classList.add("recordingDialog");var html="";html+=globalize.translateDocument(template,"sharedcomponents"),dlg.innerHTML=html,layoutManager.tv&&scrollHelper.centerFocus.on(dlg.querySelector(".formDialogContent"),!1),dialogHelper.open(dlg),dlg.querySelector(".btnCancel").addEventListener("click",function(e){dialogHelper.close(dlg)}),dlg.querySelector(".popupIdentifyForm").addEventListener("submit",function(e){return e.preventDefault(),searchForIdentificationResults(dlg),!1}),dlg.addEventListener("close",function(){loading.hide(),resolveFunc(hasChanges?currentSearchResult:null)}),dlg.classList.add("identifyDialog"),showIdentificationFormFindNew(dlg,itemName,itemYear,itemType)})}function showIdentificationFormFindNew(dlg,itemName,itemYear,itemType){dlg.querySelector("#txtLookupName").value=itemName,"Person"===itemType||"BoxSet"===itemType?(dlg.querySelector(".fldLookupYear").classList.add("hide"),dlg.querySelector("#txtLookupYear").value=""):(dlg.querySelector(".fldLookupYear").classList.remove("hide"),dlg.querySelector("#txtLookupYear").value=itemYear),dlg.querySelector(".formDialogHeaderTitle").innerHTML=globalize.translate("sharedcomponents#Search")}var currentItem,currentItemType,currentServerId,currentResolve,currentReject,currentSearchResult,hasChanges=!1;return{show:function(itemId,serverId){return new Promise(function(resolve,reject){currentResolve=resolve,currentReject=reject,currentServerId=serverId,hasChanges=!1,showEditor(itemId)})},showFindNew:function(itemName,itemYear,itemType,serverId){return new Promise(function(resolve,reject){currentServerId=serverId,hasChanges=!1,showEditorFindNew(itemName,itemYear,itemType,resolve)})}}}); \ No newline at end of file +define(["dialogHelper", "loading", "connectionManager", "require", "globalize", "scrollHelper", "layoutManager", "focusManager", "browser", "emby-input", "emby-checkbox", "paper-icon-button-light", "css!./../formdialog", "material-icons", "cardStyle"], function(dialogHelper, loading, connectionManager, require, globalize, scrollHelper, layoutManager, focusManager, browser) { + "use strict"; + + function getApiClient() { + return connectionManager.getApiClient(currentServerId) + } + + function searchForIdentificationResults(page) { + var i, length, value, lookupInfo = { + ProviderIds: {} + }, + identifyField = page.querySelectorAll(".identifyField"); + for (i = 0, length = identifyField.length; i < length; i++)(value = identifyField[i].value) && ("number" === identifyField[i].type && (value = parseInt(value)), lookupInfo[identifyField[i].getAttribute("data-lookup")] = value); + var hasId = !1, + txtLookupId = page.querySelectorAll(".txtLookupId"); + for (i = 0, length = txtLookupId.length; i < length; i++) value = txtLookupId[i].value, value && (hasId = !0), lookupInfo.ProviderIds[txtLookupId[i].getAttribute("data-providerkey")] = value; + if (!hasId && !lookupInfo.Name) return void require(["toast"], function(toast) { + toast(globalize.translate("sharedcomponents#PleaseEnterNameOrId")) + }); + currentItem && currentItem.GameSystem && (lookupInfo.GameSystem = currentItem.GameSystem), lookupInfo = { + SearchInfo: lookupInfo + }, currentItem && currentItem.Id ? lookupInfo.ItemId = currentItem.Id : lookupInfo.IncludeDisabledProviders = !0, loading.show(); + var apiClient = getApiClient(); + apiClient.ajax({ + type: "POST", + url: apiClient.getUrl("Items/RemoteSearch/" + currentItemType), + data: JSON.stringify(lookupInfo), + contentType: "application/json", + dataType: "json" + }).then(function(results) { + loading.hide(), showIdentificationSearchResults(page, results) + }) + } + + function showIdentificationSearchResults(page, results) { + function onSearchImageClick() { + var index = parseInt(this.getAttribute("data-index")), + currentResult = results[index]; + null != currentItem ? showIdentifyOptions(page, currentResult) : finishFindNewDialog(page, currentResult) + } + var identificationSearchResults = page.querySelector(".identificationSearchResults"); + page.querySelector(".popupIdentifyForm").classList.add("hide"), identificationSearchResults.classList.remove("hide"), page.querySelector(".identifyOptionsForm").classList.add("hide"), page.querySelector(".dialogContentInner").classList.remove("dialog-content-centered"); + var i, length, html = ""; + for (i = 0, length = results.length; i < length; i++) { + html += getSearchResultHtml(results[i], i) + } + var elem = page.querySelector(".identificationSearchResultList"); + elem.innerHTML = html; + var searchImages = elem.querySelectorAll(".card"); + for (i = 0, length = searchImages.length; i < length; i++) searchImages[i].addEventListener("click", onSearchImageClick); + layoutManager.tv && focusManager.autoFocus(identificationSearchResults) + } + + function finishFindNewDialog(dlg, identifyResult) { + currentSearchResult = identifyResult, hasChanges = !0, loading.hide(), dialogHelper.close(dlg) + } + + function showIdentifyOptions(page, identifyResult) { + var identifyOptionsForm = page.querySelector(".identifyOptionsForm"); + page.querySelector(".popupIdentifyForm").classList.add("hide"), page.querySelector(".identificationSearchResults").classList.add("hide"), identifyOptionsForm.classList.remove("hide"), page.querySelector("#chkIdentifyReplaceImages").checked = !0, page.querySelector(".dialogContentInner").classList.add("dialog-content-centered"), currentSearchResult = identifyResult; + var lines = []; + lines.push(identifyResult.Name), identifyResult.ProductionYear && lines.push(identifyResult.ProductionYear), identifyResult.GameSystem && lines.push(identifyResult.GameSystem); + var resultHtml = lines.join("
"); + if (identifyResult.ImageUrl) { + resultHtml = '
' + resultHtml + "
" + } + page.querySelector(".selectedSearchResult").innerHTML = resultHtml, focusManager.focus(identifyOptionsForm.querySelector(".btnSubmit")) + } + + function getSearchResultHtml(result, index) { + var padderClass, html = "", + cssClass = "card scalableCard", + cardBoxCssClass = "cardBox"; + if ("Episode" === currentItemType ? (cssClass += " backdropCard backdropCard-scalable", padderClass = "cardPadder-backdrop") : "MusicAlbum" === currentItemType || "MusicArtist" === currentItemType ? (cssClass += " squareCard squareCard-scalable", padderClass = "cardPadder-square") : (cssClass += " portraitCard portraitCard-scalable", padderClass = "cardPadder-portrait"), layoutManager.tv && !browser.slow && (cardBoxCssClass += " cardBox-focustransform"), cardBoxCssClass += " cardBox-bottompadded", layoutManager.tv && (cardBoxCssClass += " card-focuscontent cardBox-withfocuscontent"), html += '" + } + + function getSearchImageDisplayUrl(url, provider) { + return getApiClient().getUrl("Items/RemoteSearch/Image", { + imageUrl: url, + ProviderName: provider + }) + } + + function submitIdentficationResult(page) { + loading.show(); + var options = { + ReplaceAllImages: page.querySelector("#chkIdentifyReplaceImages").checked + }, + apiClient = getApiClient(); + apiClient.ajax({ + type: "POST", + url: apiClient.getUrl("Items/RemoteSearch/Apply/" + currentItem.Id, options), + data: JSON.stringify(currentSearchResult), + contentType: "application/json" + }).then(function() { + hasChanges = !0, loading.hide(), dialogHelper.close(page) + }, function() { + loading.hide(), dialogHelper.close(page) + }) + } + + function showIdentificationForm(page, item) { + var apiClient = getApiClient(); + apiClient.getJSON(apiClient.getUrl("Items/" + item.Id + "/ExternalIdInfos")).then(function(idList) { + for (var html = "", providerIds = item.ProviderIds || {}, i = 0, length = idList.length; i < length; i++) { + var idInfo = idList[i], + id = "txtLookup" + idInfo.Key; + html += '
'; + var idLabel = globalize.translate("sharedcomponents#LabelDynamicExternalId").replace("{0}", idInfo.Name); + idInfo.Key; + html += '', html += "
" + } + page.querySelector("#txtLookupName").value = "", "Person" === item.Type || "BoxSet" === item.Type ? (page.querySelector(".fldLookupYear").classList.add("hide"), page.querySelector("#txtLookupYear").value = "") : (page.querySelector(".fldLookupYear").classList.remove("hide"), page.querySelector("#txtLookupYear").value = ""), page.querySelector(".identifyProviderIds").innerHTML = html, page.querySelector(".formDialogHeaderTitle").innerHTML = globalize.translate("sharedcomponents#Identify") + }) + } + + function showEditor(itemId) { + loading.show(), require(["text!./itemidentifier.template.html"], function(template) { + var apiClient = getApiClient(); + apiClient.getItem(apiClient.getCurrentUserId(), itemId).then(function(item) { + currentItem = item, currentItemType = currentItem.Type; + var dialogOptions = { + size: "fullscreen-border", + removeOnClose: !0, + scrollY: !1 + }; + layoutManager.tv && (dialogOptions.size = "fullscreen"); + var dlg = dialogHelper.createDialog(dialogOptions); + dlg.classList.add("formDialog"), dlg.classList.add("recordingDialog"); + var html = ""; + html += globalize.translateDocument(template, "sharedcomponents"), dlg.innerHTML = html, dlg.addEventListener("close", onDialogClosed), layoutManager.tv && scrollHelper.centerFocus.on(dlg.querySelector(".formDialogContent"), !1), dialogHelper.open(dlg), dlg.querySelector(".popupIdentifyForm").addEventListener("submit", function(e) { + return e.preventDefault(), searchForIdentificationResults(dlg), !1 + }), dlg.querySelector(".identifyOptionsForm").addEventListener("submit", function(e) { + return e.preventDefault(), submitIdentficationResult(dlg), !1 + }), dlg.querySelector(".btnCancel").addEventListener("click", function(e) { + dialogHelper.close(dlg) + }), dlg.classList.add("identifyDialog"), showIdentificationForm(dlg, item), loading.hide() + }) + }) + } + + function onDialogClosed() { + loading.hide(), hasChanges ? currentResolve() : currentReject() + } + + function showEditorFindNew(itemName, itemYear, itemType, resolveFunc) { + currentItem = null, currentItemType = itemType, require(["text!./itemidentifier.template.html"], function(template) { + var dialogOptions = { + size: "fullscreen-border", + removeOnClose: !0, + scrollY: !1 + }; + layoutManager.tv && (dialogOptions.size = "fullscreen"); + var dlg = dialogHelper.createDialog(dialogOptions); + dlg.classList.add("formDialog"), dlg.classList.add("recordingDialog"); + var html = ""; + html += globalize.translateDocument(template, "sharedcomponents"), dlg.innerHTML = html, layoutManager.tv && scrollHelper.centerFocus.on(dlg.querySelector(".formDialogContent"), !1), dialogHelper.open(dlg), dlg.querySelector(".btnCancel").addEventListener("click", function(e) { + dialogHelper.close(dlg) + }), dlg.querySelector(".popupIdentifyForm").addEventListener("submit", function(e) { + return e.preventDefault(), searchForIdentificationResults(dlg), !1 + }), dlg.addEventListener("close", function() { + loading.hide(), resolveFunc(hasChanges ? currentSearchResult : null) + }), dlg.classList.add("identifyDialog"), showIdentificationFormFindNew(dlg, itemName, itemYear, itemType) + }) + } + + function showIdentificationFormFindNew(dlg, itemName, itemYear, itemType) { + dlg.querySelector("#txtLookupName").value = itemName, "Person" === itemType || "BoxSet" === itemType ? (dlg.querySelector(".fldLookupYear").classList.add("hide"), dlg.querySelector("#txtLookupYear").value = "") : (dlg.querySelector(".fldLookupYear").classList.remove("hide"), dlg.querySelector("#txtLookupYear").value = itemYear), dlg.querySelector(".formDialogHeaderTitle").innerHTML = globalize.translate("sharedcomponents#Search") + } + var currentItem, currentItemType, currentServerId, currentResolve, currentReject, currentSearchResult, hasChanges = !1; + return { + show: function(itemId, serverId) { + return new Promise(function(resolve, reject) { + currentResolve = resolve, currentReject = reject, currentServerId = serverId, hasChanges = !1, showEditor(itemId) + }) + }, + showFindNew: function(itemName, itemYear, itemType, serverId) { + return new Promise(function(resolve, reject) { + currentServerId = serverId, hasChanges = !1, showEditorFindNew(itemName, itemYear, itemType, resolve) + }) + } + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/itemsrefresher.js b/dashboard-ui/bower_components/emby-webcomponents/itemsrefresher.js index 39eb3cca77..43a7a3213d 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/itemsrefresher.js +++ b/dashboard-ui/bower_components/emby-webcomponents/itemsrefresher.js @@ -1 +1,112 @@ -define(["playbackManager","serverNotifications","events"],function(playbackManager,serverNotifications,events){"use strict";function onUserDataChanged(e,apiClient,userData){var instance=this,eventsToMonitor=getEventsToMonitor(instance);-1!==eventsToMonitor.indexOf("markfavorite")?instance.notifyRefreshNeeded():-1!==eventsToMonitor.indexOf("markplayed")&&instance.notifyRefreshNeeded()}function getEventsToMonitor(instance){var options=instance.options,monitor=options?options.monitorEvents:null;return monitor?monitor.split(","):[]}function onTimerCreated(e,apiClient,data){var instance=this;if(-1!==getEventsToMonitor(instance).indexOf("timers"))return void instance.notifyRefreshNeeded()}function onSeriesTimerCreated(e,apiClient,data){var instance=this;if(-1!==getEventsToMonitor(instance).indexOf("seriestimers"))return void instance.notifyRefreshNeeded()}function onTimerCancelled(e,apiClient,data){var instance=this;if(-1!==getEventsToMonitor(instance).indexOf("timers"))return void instance.notifyRefreshNeeded()}function onSeriesTimerCancelled(e,apiClient,data){var instance=this;if(-1!==getEventsToMonitor(instance).indexOf("seriestimers"))return void instance.notifyRefreshNeeded()}function onLibraryChanged(e,apiClient,data){var instance=this,eventsToMonitor=getEventsToMonitor(instance);if(-1===eventsToMonitor.indexOf("seriestimers")&&-1===eventsToMonitor.indexOf("timers")){var itemsAdded=data.ItemsAdded||[],itemsRemoved=data.ItemsRemoved||[];if(itemsAdded.length||itemsRemoved.length){var options=instance.options||{},parentId=options.parentId;if(parentId){var foldersAddedTo=data.FoldersAddedTo||[],foldersRemovedFrom=data.FoldersRemovedFrom||[],collectionFolders=data.CollectionFolders||[];if(-1===foldersAddedTo.indexOf(parentId)&&-1===foldersRemovedFrom.indexOf(parentId)&&-1===collectionFolders.indexOf(parentId))return}instance.notifyRefreshNeeded()}}}function onPlaybackStopped(e,stopInfo){var instance=this,state=stopInfo.state,eventsToMonitor=getEventsToMonitor(instance);if(state.NowPlayingItem&&"Video"===state.NowPlayingItem.MediaType){if(-1!==eventsToMonitor.indexOf("videoplayback"))return void instance.notifyRefreshNeeded(!0)}else if(state.NowPlayingItem&&"Audio"===state.NowPlayingItem.MediaType&&-1!==eventsToMonitor.indexOf("audioplayback"))return void instance.notifyRefreshNeeded(!0)}function addNotificationEvent(instance,name,handler,owner){var localHandler=handler.bind(instance);owner=owner||serverNotifications,events.on(owner,name,localHandler),instance["event_"+name]=localHandler}function removeNotificationEvent(instance,name,owner){var handler=instance["event_"+name];handler&&(owner=owner||serverNotifications,events.off(owner,name,handler),instance["event_"+name]=null)}function ItemsRefresher(options){this.options=options||{},addNotificationEvent(this,"UserDataChanged",onUserDataChanged),addNotificationEvent(this,"TimerCreated",onTimerCreated),addNotificationEvent(this,"SeriesTimerCreated",onSeriesTimerCreated),addNotificationEvent(this,"TimerCancelled",onTimerCancelled),addNotificationEvent(this,"SeriesTimerCancelled",onSeriesTimerCancelled),addNotificationEvent(this,"LibraryChanged",onLibraryChanged),addNotificationEvent(this,"playbackstop",onPlaybackStopped,playbackManager)}function clearRefreshInterval(instance,isPausing){instance.refreshInterval&&(clearInterval(instance.refreshInterval),instance.refreshInterval=null,isPausing||(instance.refreshIntervalEndTime=null))}function resetRefreshInterval(instance,intervalMs){if(clearRefreshInterval(instance),!intervalMs){var options=instance.options;options&&(intervalMs=options.refreshIntervalMs)}intervalMs&&(instance.refreshInterval=setInterval(instance.notifyRefreshNeeded.bind(instance),intervalMs),instance.refreshIntervalEndTime=(new Date).getTime()+intervalMs)}function onDataFetched(result){resetRefreshInterval(this),this.afterRefresh&&this.afterRefresh(result)}return ItemsRefresher.prototype.pause=function(){clearRefreshInterval(this,!0),this.paused=!0},ItemsRefresher.prototype.resume=function(options){this.paused=!1;var refreshIntervalEndTime=this.refreshIntervalEndTime;if(refreshIntervalEndTime){var remainingMs=refreshIntervalEndTime-(new Date).getTime();remainingMs>0&&!this.needsRefresh?resetRefreshInterval(this,remainingMs):(this.needsRefresh=!0,this.refreshIntervalEndTime=null)}return this.needsRefresh||options&&options.refresh?this.refreshItems():Promise.resolve()},ItemsRefresher.prototype.refreshItems=function(){return this.fetchData?this.paused?(this.needsRefresh=!0,Promise.resolve()):(this.needsRefresh=!1,this.fetchData().then(onDataFetched.bind(this))):Promise.resolve()},ItemsRefresher.prototype.notifyRefreshNeeded=function(isInForeground){if(this.paused)return void(this.needsRefresh=!0);var timeout=this.refreshTimeout;timeout&&clearTimeout(timeout),!0===isInForeground?this.refreshItems():this.refreshTimeout=setTimeout(this.refreshItems.bind(this),1e4)},ItemsRefresher.prototype.destroy=function(){clearRefreshInterval(this),removeNotificationEvent(this,"UserDataChanged"),removeNotificationEvent(this,"TimerCreated"),removeNotificationEvent(this,"SeriesTimerCreated"),removeNotificationEvent(this,"TimerCancelled"),removeNotificationEvent(this,"SeriesTimerCancelled"),removeNotificationEvent(this,"LibraryChanged"),removeNotificationEvent(this,"playbackstop",playbackManager),this.fetchData=null,this.options=null},ItemsRefresher}); \ No newline at end of file +define(["playbackManager", "serverNotifications", "events"], function(playbackManager, serverNotifications, events) { + "use strict"; + + function onUserDataChanged(e, apiClient, userData) { + var instance = this, + eventsToMonitor = getEventsToMonitor(instance); - 1 !== eventsToMonitor.indexOf("markfavorite") ? instance.notifyRefreshNeeded() : -1 !== eventsToMonitor.indexOf("markplayed") && instance.notifyRefreshNeeded() + } + + function getEventsToMonitor(instance) { + var options = instance.options, + monitor = options ? options.monitorEvents : null; + return monitor ? monitor.split(",") : [] + } + + function onTimerCreated(e, apiClient, data) { + var instance = this; + if (-1 !== getEventsToMonitor(instance).indexOf("timers")) return void instance.notifyRefreshNeeded() + } + + function onSeriesTimerCreated(e, apiClient, data) { + var instance = this; + if (-1 !== getEventsToMonitor(instance).indexOf("seriestimers")) return void instance.notifyRefreshNeeded() + } + + function onTimerCancelled(e, apiClient, data) { + var instance = this; + if (-1 !== getEventsToMonitor(instance).indexOf("timers")) return void instance.notifyRefreshNeeded() + } + + function onSeriesTimerCancelled(e, apiClient, data) { + var instance = this; + if (-1 !== getEventsToMonitor(instance).indexOf("seriestimers")) return void instance.notifyRefreshNeeded() + } + + function onLibraryChanged(e, apiClient, data) { + var instance = this, + eventsToMonitor = getEventsToMonitor(instance); + if (-1 === eventsToMonitor.indexOf("seriestimers") && -1 === eventsToMonitor.indexOf("timers")) { + var itemsAdded = data.ItemsAdded || [], + itemsRemoved = data.ItemsRemoved || []; + if (itemsAdded.length || itemsRemoved.length) { + var options = instance.options || {}, + parentId = options.parentId; + if (parentId) { + var foldersAddedTo = data.FoldersAddedTo || [], + foldersRemovedFrom = data.FoldersRemovedFrom || [], + collectionFolders = data.CollectionFolders || []; + if (-1 === foldersAddedTo.indexOf(parentId) && -1 === foldersRemovedFrom.indexOf(parentId) && -1 === collectionFolders.indexOf(parentId)) return + } + instance.notifyRefreshNeeded() + } + } + } + + function onPlaybackStopped(e, stopInfo) { + var instance = this, + state = stopInfo.state, + eventsToMonitor = getEventsToMonitor(instance); + if (state.NowPlayingItem && "Video" === state.NowPlayingItem.MediaType) { + if (-1 !== eventsToMonitor.indexOf("videoplayback")) return void instance.notifyRefreshNeeded(!0) + } else if (state.NowPlayingItem && "Audio" === state.NowPlayingItem.MediaType && -1 !== eventsToMonitor.indexOf("audioplayback")) return void instance.notifyRefreshNeeded(!0) + } + + function addNotificationEvent(instance, name, handler, owner) { + var localHandler = handler.bind(instance); + owner = owner || serverNotifications, events.on(owner, name, localHandler), instance["event_" + name] = localHandler + } + + function removeNotificationEvent(instance, name, owner) { + var handler = instance["event_" + name]; + handler && (owner = owner || serverNotifications, events.off(owner, name, handler), instance["event_" + name] = null) + } + + function ItemsRefresher(options) { + this.options = options || {}, addNotificationEvent(this, "UserDataChanged", onUserDataChanged), addNotificationEvent(this, "TimerCreated", onTimerCreated), addNotificationEvent(this, "SeriesTimerCreated", onSeriesTimerCreated), addNotificationEvent(this, "TimerCancelled", onTimerCancelled), addNotificationEvent(this, "SeriesTimerCancelled", onSeriesTimerCancelled), addNotificationEvent(this, "LibraryChanged", onLibraryChanged), addNotificationEvent(this, "playbackstop", onPlaybackStopped, playbackManager) + } + + function clearRefreshInterval(instance, isPausing) { + instance.refreshInterval && (clearInterval(instance.refreshInterval), instance.refreshInterval = null, isPausing || (instance.refreshIntervalEndTime = null)) + } + + function resetRefreshInterval(instance, intervalMs) { + if (clearRefreshInterval(instance), !intervalMs) { + var options = instance.options; + options && (intervalMs = options.refreshIntervalMs) + } + intervalMs && (instance.refreshInterval = setInterval(instance.notifyRefreshNeeded.bind(instance), intervalMs), instance.refreshIntervalEndTime = (new Date).getTime() + intervalMs) + } + + function onDataFetched(result) { + resetRefreshInterval(this), this.afterRefresh && this.afterRefresh(result) + } + return ItemsRefresher.prototype.pause = function() { + clearRefreshInterval(this, !0), this.paused = !0 + }, ItemsRefresher.prototype.resume = function(options) { + this.paused = !1; + var refreshIntervalEndTime = this.refreshIntervalEndTime; + if (refreshIntervalEndTime) { + var remainingMs = refreshIntervalEndTime - (new Date).getTime(); + remainingMs > 0 && !this.needsRefresh ? resetRefreshInterval(this, remainingMs) : (this.needsRefresh = !0, this.refreshIntervalEndTime = null) + } + return this.needsRefresh || options && options.refresh ? this.refreshItems() : Promise.resolve() + }, ItemsRefresher.prototype.refreshItems = function() { + return this.fetchData ? this.paused ? (this.needsRefresh = !0, Promise.resolve()) : (this.needsRefresh = !1, this.fetchData().then(onDataFetched.bind(this))) : Promise.resolve() + }, ItemsRefresher.prototype.notifyRefreshNeeded = function(isInForeground) { + if (this.paused) return void(this.needsRefresh = !0); + var timeout = this.refreshTimeout; + timeout && clearTimeout(timeout), !0 === isInForeground ? this.refreshItems() : this.refreshTimeout = setTimeout(this.refreshItems.bind(this), 1e4) + }, ItemsRefresher.prototype.destroy = function() { + clearRefreshInterval(this), removeNotificationEvent(this, "UserDataChanged"), removeNotificationEvent(this, "TimerCreated"), removeNotificationEvent(this, "SeriesTimerCreated"), removeNotificationEvent(this, "TimerCancelled"), removeNotificationEvent(this, "SeriesTimerCancelled"), removeNotificationEvent(this, "LibraryChanged"), removeNotificationEvent(this, "playbackstop", playbackManager), this.fetchData = null, this.options = null + }, ItemsRefresher +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/layoutmanager.js b/dashboard-ui/bower_components/emby-webcomponents/layoutmanager.js index b7576ab69a..ae33babaa6 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/layoutmanager.js +++ b/dashboard-ui/bower_components/emby-webcomponents/layoutmanager.js @@ -1 +1,19 @@ -define(["browser","appSettings","events"],function(browser,appSettings,events){"use strict";function setLayout(instance,layout,selectedLayout){layout===selectedLayout?(instance[layout]=!0,document.documentElement.classList.add("layout-"+layout)):(instance[layout]=!1,document.documentElement.classList.remove("layout-"+layout))}function LayoutManager(){}return LayoutManager.prototype.setLayout=function(layout,save){layout&&"auto"!==layout?(setLayout(this,"mobile",layout),setLayout(this,"tv",layout),setLayout(this,"desktop",layout),!1!==save&&appSettings.set("layout",layout)):(this.autoLayout(),!1!==save&&appSettings.set("layout","")),events.trigger(this,"modechange")},LayoutManager.prototype.getSavedLayout=function(layout){return appSettings.get("layout")},LayoutManager.prototype.autoLayout=function(){browser.mobile?this.setLayout("mobile",!1):browser.tv||browser.xboxOne?this.setLayout("tv",!1):this.setLayout(this.defaultLayout||"tv",!1)},LayoutManager.prototype.init=function(){var saved=this.getSavedLayout();saved?this.setLayout(saved,!1):this.autoLayout()},new LayoutManager}); \ No newline at end of file +define(["browser", "appSettings", "events"], function(browser, appSettings, events) { + "use strict"; + + function setLayout(instance, layout, selectedLayout) { + layout === selectedLayout ? (instance[layout] = !0, document.documentElement.classList.add("layout-" + layout)) : (instance[layout] = !1, document.documentElement.classList.remove("layout-" + layout)) + } + + function LayoutManager() {} + return LayoutManager.prototype.setLayout = function(layout, save) { + layout && "auto" !== layout ? (setLayout(this, "mobile", layout), setLayout(this, "tv", layout), setLayout(this, "desktop", layout), !1 !== save && appSettings.set("layout", layout)) : (this.autoLayout(), !1 !== save && appSettings.set("layout", "")), events.trigger(this, "modechange") + }, LayoutManager.prototype.getSavedLayout = function(layout) { + return appSettings.get("layout") + }, LayoutManager.prototype.autoLayout = function() { + browser.mobile ? this.setLayout("mobile", !1) : browser.tv || browser.xboxOne ? this.setLayout("tv", !1) : this.setLayout(this.defaultLayout || "tv", !1) + }, LayoutManager.prototype.init = function() { + var saved = this.getSavedLayout(); + saved ? this.setLayout(saved, !1) : this.autoLayout() + }, new LayoutManager +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/lazyloader/lazyloader-intersectionobserver.js b/dashboard-ui/bower_components/emby-webcomponents/lazyloader/lazyloader-intersectionobserver.js index f31fe3d2a8..df4a2e12a2 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/lazyloader/lazyloader-intersectionobserver.js +++ b/dashboard-ui/bower_components/emby-webcomponents/lazyloader/lazyloader-intersectionobserver.js @@ -1 +1,45 @@ -define(["require","browser"],function(require,browser){"use strict";function LazyLoader(options){this.options=options}function unveilElements(elements,root,callback){if(elements.length){new LazyLoader({callback:callback}).addElements(elements)}}return browser.edge&&require(["css!./lazyedgehack"]),LazyLoader.prototype.createObserver=function(){var observerOptions={},options=this.options,loadedCount=0,callback=options.callback;observerOptions.rootMargin="50%";var observerId="obs"+(new Date).getTime(),self=this,observer=new IntersectionObserver(function(entries){for(var j=0,length2=entries.length;j0){var target=entry.target;observer.unobserve(target),target[observerId]||(target[observerId]=1,callback(target),++loadedCount>=self.elementCount&&self.destroyObserver())}}},observerOptions);this.observer=observer},LazyLoader.prototype.addElements=function(elements){var observer=this.observer;observer||(this.createObserver(),observer=this.observer),this.elementCount=(this.elementCount||0)+elements.length;for(var i=0,length=elements.length;i 0) { + var target = entry.target; + observer.unobserve(target), target[observerId] || (target[observerId] = 1, callback(target), ++loadedCount >= self.elementCount && self.destroyObserver()) + } + } + }, observerOptions); + this.observer = observer + }, LazyLoader.prototype.addElements = function(elements) { + var observer = this.observer; + observer || (this.createObserver(), observer = this.observer), this.elementCount = (this.elementCount || 0) + elements.length; + for (var i = 0, length = elements.length; i < length; i++) observer.observe(elements[i]) + }, LazyLoader.prototype.destroyObserver = function(elements) { + var observer = this.observer; + observer && (observer.disconnect(), this.observer = null) + }, LazyLoader.prototype.destroy = function(elements) { + this.destroyObserver(), this.options = null + }, LazyLoader.lazyChildren = function(elem, callback) { + unveilElements(elem.getElementsByClassName("lazy"), elem, callback) + }, LazyLoader +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/lazyloader/lazyloader-scroll.js b/dashboard-ui/bower_components/emby-webcomponents/lazyloader/lazyloader-scroll.js index 3ecf28e8a8..bab5cff978 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/lazyloader/lazyloader-scroll.js +++ b/dashboard-ui/bower_components/emby-webcomponents/lazyloader/lazyloader-scroll.js @@ -1 +1,103 @@ -define(["visibleinviewport","dom","browser"],function(visibleinviewport,dom,browser){"use strict";function resetThresholds(){thresholdX=.3*screen.availWidth,thresholdY=.3*screen.availHeight}function resetThresholdsOnTimer(){setTimeout(resetThresholds,500)}function isVisible(elem){return visibleinviewport(elem,!0,thresholdX,thresholdY)}function cancelAll(tokens){for(var i=0,length=tokens.length;i=elements.length&&(dom.removeEventListener(document,"focus",unveil,{capture:!0,passive:!0}),dom.removeEventListener(document,"scroll",unveil,{capture:!0,passive:!0}),dom.removeEventListener(document,wheelEvent,unveil,{capture:!0,passive:!0}),dom.removeEventListener(window,"resize",unveil,{capture:!0,passive:!0}))}function unveil(){cancelAll(cancellationTokens);var index=cancellationTokens.length;cancellationTokens.length++,setTimeout(function(){unveilInternal(index)},1)}var unveiledElements=[],cancellationTokens=[],loadedCount=0;dom.addEventListener(document,"focus",unveil,{capture:!0,passive:!0}),dom.addEventListener(document,"scroll",unveil,{capture:!0,passive:!0}),dom.addEventListener(document,wheelEvent,unveil,{capture:!0,passive:!0}),dom.addEventListener(window,"resize",unveil,{capture:!0,passive:!0}),unveil()}function LazyLoader(options){this.options=options}function unveilElements(elements,root,callback){if(elements.length){new LazyLoader({callback:callback}).addElements(elements)}}var thresholdX,thresholdY;window.requestIdleCallback;browser.iOS?(dom.addEventListener(window,"orientationchange",resetThresholdsOnTimer,{passive:!0}),dom.addEventListener(window,"resize",resetThresholdsOnTimer,{passive:!0})):(dom.addEventListener(window,"orientationchange",resetThresholds,{passive:!0}),dom.addEventListener(window,"resize",resetThresholds,{passive:!0})),resetThresholds();var wheelEvent=document.implementation.hasFeature("Event.wheel","3.0")?"wheel":"mousewheel";return LazyLoader.prototype.createObserver=function(){unveilElementsInternal(this,this.options.callback),this.observer=1},LazyLoader.prototype.addElements=function(elements){this.elements=this.elements||[];for(var i=0,length=elements.length;i= elements.length && (dom.removeEventListener(document, "focus", unveil, { + capture: !0, + passive: !0 + }), dom.removeEventListener(document, "scroll", unveil, { + capture: !0, + passive: !0 + }), dom.removeEventListener(document, wheelEvent, unveil, { + capture: !0, + passive: !0 + }), dom.removeEventListener(window, "resize", unveil, { + capture: !0, + passive: !0 + })) + } + + function unveil() { + cancelAll(cancellationTokens); + var index = cancellationTokens.length; + cancellationTokens.length++, setTimeout(function() { + unveilInternal(index) + }, 1) + } + var unveiledElements = [], + cancellationTokens = [], + loadedCount = 0; + dom.addEventListener(document, "focus", unveil, { + capture: !0, + passive: !0 + }), dom.addEventListener(document, "scroll", unveil, { + capture: !0, + passive: !0 + }), dom.addEventListener(document, wheelEvent, unveil, { + capture: !0, + passive: !0 + }), dom.addEventListener(window, "resize", unveil, { + capture: !0, + passive: !0 + }), unveil() + } + + function LazyLoader(options) { + this.options = options + } + + function unveilElements(elements, root, callback) { + if (elements.length) { + new LazyLoader({ + callback: callback + }).addElements(elements) + } + } + var thresholdX, thresholdY; + window.requestIdleCallback; + browser.iOS ? (dom.addEventListener(window, "orientationchange", resetThresholdsOnTimer, { + passive: !0 + }), dom.addEventListener(window, "resize", resetThresholdsOnTimer, { + passive: !0 + })) : (dom.addEventListener(window, "orientationchange", resetThresholds, { + passive: !0 + }), dom.addEventListener(window, "resize", resetThresholds, { + passive: !0 + })), resetThresholds(); + var wheelEvent = document.implementation.hasFeature("Event.wheel", "3.0") ? "wheel" : "mousewheel"; + return LazyLoader.prototype.createObserver = function() { + unveilElementsInternal(this, this.options.callback), this.observer = 1 + }, LazyLoader.prototype.addElements = function(elements) { + this.elements = this.elements || []; + for (var i = 0, length = elements.length; i < length; i++) this.elements.push(elements[i]); + this.observer || this.createObserver() + }, LazyLoader.prototype.destroyObserver = function(elements) {}, LazyLoader.prototype.destroy = function(elements) { + this.destroyObserver(), this.options = null + }, LazyLoader.lazyChildren = function(elem, callback) { + unveilElements(elem.getElementsByClassName("lazy"), elem, callback) + }, LazyLoader +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/listview/listview.js b/dashboard-ui/bower_components/emby-webcomponents/listview/listview.js index f3cb11f526..be183c9978 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/listview/listview.js +++ b/dashboard-ui/bower_components/emby-webcomponents/listview/listview.js @@ -1 +1,131 @@ -define(["itemHelper","mediaInfo","indicators","connectionManager","layoutManager","globalize","datetime","apphost","css!./listview","emby-ratingbutton","emby-playstatebutton"],function(itemHelper,mediaInfo,indicators,connectionManager,layoutManager,globalize,datetime,appHost){"use strict";function getIndex(item,options){if("disc"===options.index)return null==item.ParentIndexNumber?"":globalize.translate("sharedcomponents#ValueDiscNumber",item.ParentIndexNumber);var code,name,sortBy=(options.sortBy||"").toLowerCase();return 0===sortBy.indexOf("sortname")?"Episode"===item.Type?"":(name=(item.SortName||item.Name||"?")[0].toUpperCase(),code=name.charCodeAt(0),code<65||code>90?"#":name.toUpperCase()):0===sortBy.indexOf("officialrating")?item.OfficialRating||globalize.translate("sharedcomponents#Unrated"):0===sortBy.indexOf("communityrating")?null==item.CommunityRating?globalize.translate("sharedcomponents#Unrated"):Math.floor(item.CommunityRating):0===sortBy.indexOf("criticrating")?null==item.CriticRating?globalize.translate("sharedcomponents#Unrated"):Math.floor(item.CriticRating):0===sortBy.indexOf("albumartist")&&item.AlbumArtist?(name=item.AlbumArtist[0].toUpperCase(),code=name.charCodeAt(0),code<65||code>90?"#":name.toUpperCase()):""}function getImageUrl(item,width){var apiClient=connectionManager.getApiClient(item.ServerId),options={width:width,type:"Primary"};return item.ImageTags&&item.ImageTags.Primary?(options.tag=item.ImageTags.Primary,apiClient.getScaledImageUrl(item.Id,options)):item.AlbumId&&item.AlbumPrimaryImageTag?(options.tag=item.AlbumPrimaryImageTag,apiClient.getScaledImageUrl(item.AlbumId,options)):item.SeriesId&&item.SeriesPrimaryImageTag?(options.tag=item.SeriesPrimaryImageTag,apiClient.getScaledImageUrl(item.SeriesId,options)):item.ParentPrimaryImageTag?(options.tag=item.ParentPrimaryImageTag,apiClient.getScaledImageUrl(item.ParentPrimaryImageItemId,options)):null}function getChannelImageUrl(item,width){var apiClient=connectionManager.getApiClient(item.ServerId),options={width:width,type:"Primary"};return item.ChannelId&&item.ChannelPrimaryImageTag?(options.tag=item.ChannelPrimaryImageTag,apiClient.getScaledImageUrl(item.ChannelId,options)):null}function getTextLinesHtml(textlines,isLargeStyle){for(var html="",largeTitleTagName=layoutManager.tv?"h2":"div",i=0,length=textlines.length;i':'
':'
',html+=textlines[i]||" ",html+=0===i&&isLargeStyle?"":"
")}return html}function getRightButtonsHtml(options){for(var html="",i=0,length=options.rightButtons.length;i'+button.icon+""}return html}function getId(item){return item.Id}function getListViewHtml(options){for(var items=options.items,groupTitle="",action=options.action||"link",isLargeStyle="large"===options.imageSize,enableOverview=options.enableOverview,clickEntireItem=!!layoutManager.tv,outerTagName=clickEntireItem?"button":"div",enableSideMediaInfo=null==options.enableSideMediaInfo||options.enableSideMediaInfo,outerHtml="",enableContentWrapper=options.enableOverview&&!layoutManager.tv,containerAlbumArtistIds=(options.containerAlbumArtists||[]).map(getId),i=0,length=items.length;i"),html+=0===i?'

':'

',html+=itemGroupTitle,html+="

",html+="
",groupTitle=itemGroupTitle)}var cssClass="listItem";(options.border||!1!==options.highlight&&!layoutManager.tv)&&(cssClass+=" listItem-border"),clickEntireItem&&(cssClass+=" itemAction listItem-button"),layoutManager.tv&&(cssClass+=" listItem-focusscale");var downloadWidth=80;isLargeStyle&&(cssClass+=" listItem-largeImage",downloadWidth=500);var playlistItemId=item.PlaylistItemId?' data-playlistitemid="'+item.PlaylistItemId+'"':"",positionTicksData=item.UserData&&item.UserData.PlaybackPositionTicks?' data-positionticks="'+item.UserData.PlaybackPositionTicks+'"':"",collectionIdData=options.collectionId?' data-collectionid="'+options.collectionId+'"':"",playlistIdData=options.playlistId?' data-playlistid="'+options.playlistId+'"':"",mediaTypeData=item.MediaType?' data-mediatype="'+item.MediaType+'"':"",collectionTypeData=item.CollectionType?' data-collectiontype="'+item.CollectionType+'"':"",channelIdData=item.ChannelId?' data-channelid="'+item.ChannelId+'"':"";if(enableContentWrapper&&(cssClass+=" listItem-withContentWrapper"),html+="<"+outerTagName+' class="'+cssClass+'"'+playlistItemId+' data-action="'+action+'" data-isfolder="'+item.IsFolder+'" data-id="'+item.Id+'" data-serverid="'+item.ServerId+'" data-type="'+item.Type+'"'+mediaTypeData+collectionTypeData+channelIdData+positionTicksData+collectionIdData+playlistIdData+">",enableContentWrapper&&(html+='
'),!clickEntireItem&&options.dragHandle&&(html+=''),!1!==options.image){var imgUrl="channel"===options.imageSource?getChannelImageUrl(item,downloadWidth):getImageUrl(item,downloadWidth);console.log(imgUrl);var imageClass=isLargeStyle?"listItemImage listItemImage-large":"listItemImage";isLargeStyle&&layoutManager.tv&&(imageClass+=" listItemImage-large-tv");var playOnImageClick=options.imagePlayButton&&!layoutManager.tv;clickEntireItem||(imageClass+=" itemAction");var imageAction=playOnImageClick?"resume":action;html+=imgUrl?'
':'
';var indicatorsHtml="";indicatorsHtml+=indicators.getPlayedIndicatorHtml(item),indicatorsHtml&&(html+='
'+indicatorsHtml+"
"),playOnImageClick&&(html+='');var progressHtml=indicators.getProgressBarHtml(item,{containerClass:"listItemProgressBar"});progressHtml&&(html+=progressHtml),html+="
"}options.showIndexNumberLeft&&(html+='
',html+=item.IndexNumber||" ",html+="
");var textlines=[];options.showProgramDateTime&&textlines.push(datetime.toLocaleString(datetime.parseISO8601Date(item.StartDate),{weekday:"long",month:"short",day:"numeric",hour:"numeric",minute:"2-digit"})),options.showProgramTime&&textlines.push(datetime.getDisplayTime(datetime.parseISO8601Date(item.StartDate))),options.showChannel&&item.ChannelName&&textlines.push(item.ChannelName);var parentTitle=null;options.showParentTitle&&("Episode"===item.Type?parentTitle=item.SeriesName:(item.IsSeries||item.EpisodeTitle&&item.Name)&&(parentTitle=item.Name));var displayName=itemHelper.getDisplayName(item,{includeParentInfo:options.includeParentInfoInTitle});if(options.showIndexNumber&&null!=item.IndexNumber&&(displayName=item.IndexNumber+". "+displayName),options.showParentTitle&&options.parentTitleWithTitle?(displayName&&(parentTitle&&(parentTitle+=" - "),parentTitle=(parentTitle||"")+displayName),textlines.push(parentTitle||"")):options.showParentTitle&&textlines.push(parentTitle||""),displayName&&!options.parentTitleWithTitle&&textlines.push(displayName),item.IsFolder)!1!==options.artist&&item.AlbumArtist&&"MusicAlbum"===item.Type&&textlines.push(item.AlbumArtist);else{var showArtist=!0===options.artist,artistItems=item.ArtistItems;showArtist||!1===options.artist||(artistItems&&artistItems.length?(artistItems.length>1||-1===containerAlbumArtistIds.indexOf(artistItems[0].Id))&&(showArtist=!0):showArtist=!0),showArtist&&artistItems&&"MusicAlbum"!==item.Type&&textlines.push(artistItems.map(function(a){return a.Name}).join(", "))}"Game"===item.Type&&textlines.push(item.GameSystem),"TvChannel"===item.Type&&item.CurrentProgram&&textlines.push(itemHelper.getDisplayName(item.CurrentProgram)),cssClass="listItemBody",clickEntireItem||(cssClass+=" itemAction"),!1===options.image&&(cssClass+=" listItemBody-noleftpadding"),html+='
';if(html+=getTextLinesHtml(textlines,isLargeStyle),!1!==options.mediaInfo&&!enableSideMediaInfo){html+='
'+mediaInfo.getPrimaryMediaInfoHtml(item,{episodeTitle:!1,originalAirDate:!1,subtitles:!1})+"
"}if(enableOverview&&item.Overview&&(html+='
',html+=item.Overview,html+="
"),html+="
",!1!==options.mediaInfo&&enableSideMediaInfo&&(html+='
'+mediaInfo.getPrimaryMediaInfoHtml(item,{year:!1,container:!1,episodeTitle:!1,criticRating:!1,endsAt:!1})+"
"),options.recordButton||"Timer"!==item.Type&&"Program"!==item.Type||(html+=indicators.getTimerIndicator(item).replace("indicatorIcon","indicatorIcon listItemAside")),!clickEntireItem&&(options.addToListButton&&(html+=''),!1!==options.moreButton&&(html+=''),options.infoButton&&(html+=''),options.rightButtons&&(html+=getRightButtonsHtml(options)),!1!==options.enableUserDataButtons)){html+='';var userData=item.UserData||{},likes=null==userData.Likes?"":userData.Likes;itemHelper.canMarkPlayed(item)&&(html+=''),itemHelper.canRate(item)&&(html+=''),html+=""}enableContentWrapper&&(html+="
",enableOverview&&item.Overview&&(html+='
',html+=item.Overview,html+="
")),html+="",outerHtml+=html}return outerHtml}return{getListViewHtml:getListViewHtml}}); \ No newline at end of file +define(["itemHelper", "mediaInfo", "indicators", "connectionManager", "layoutManager", "globalize", "datetime", "apphost", "css!./listview", "emby-ratingbutton", "emby-playstatebutton"], function(itemHelper, mediaInfo, indicators, connectionManager, layoutManager, globalize, datetime, appHost) { + "use strict"; + + function getIndex(item, options) { + if ("disc" === options.index) return null == item.ParentIndexNumber ? "" : globalize.translate("sharedcomponents#ValueDiscNumber", item.ParentIndexNumber); + var code, name, sortBy = (options.sortBy || "").toLowerCase(); + return 0 === sortBy.indexOf("sortname") ? "Episode" === item.Type ? "" : (name = (item.SortName || item.Name || "?")[0].toUpperCase(), code = name.charCodeAt(0), code < 65 || code > 90 ? "#" : name.toUpperCase()) : 0 === sortBy.indexOf("officialrating") ? item.OfficialRating || globalize.translate("sharedcomponents#Unrated") : 0 === sortBy.indexOf("communityrating") ? null == item.CommunityRating ? globalize.translate("sharedcomponents#Unrated") : Math.floor(item.CommunityRating) : 0 === sortBy.indexOf("criticrating") ? null == item.CriticRating ? globalize.translate("sharedcomponents#Unrated") : Math.floor(item.CriticRating) : 0 === sortBy.indexOf("albumartist") && item.AlbumArtist ? (name = item.AlbumArtist[0].toUpperCase(), code = name.charCodeAt(0), code < 65 || code > 90 ? "#" : name.toUpperCase()) : "" + } + + function getImageUrl(item, width) { + var apiClient = connectionManager.getApiClient(item.ServerId), + options = { + width: width, + type: "Primary" + }; + return item.ImageTags && item.ImageTags.Primary ? (options.tag = item.ImageTags.Primary, apiClient.getScaledImageUrl(item.Id, options)) : item.AlbumId && item.AlbumPrimaryImageTag ? (options.tag = item.AlbumPrimaryImageTag, apiClient.getScaledImageUrl(item.AlbumId, options)) : item.SeriesId && item.SeriesPrimaryImageTag ? (options.tag = item.SeriesPrimaryImageTag, apiClient.getScaledImageUrl(item.SeriesId, options)) : item.ParentPrimaryImageTag ? (options.tag = item.ParentPrimaryImageTag, apiClient.getScaledImageUrl(item.ParentPrimaryImageItemId, options)) : null + } + + function getChannelImageUrl(item, width) { + var apiClient = connectionManager.getApiClient(item.ServerId), + options = { + width: width, + type: "Primary" + }; + return item.ChannelId && item.ChannelPrimaryImageTag ? (options.tag = item.ChannelPrimaryImageTag, apiClient.getScaledImageUrl(item.ChannelId, options)) : null + } + + function getTextLinesHtml(textlines, isLargeStyle) { + for (var html = "", largeTitleTagName = layoutManager.tv ? "h2" : "div", i = 0, length = textlines.length; i < length; i++) { + textlines[i] && (html += 0 === i ? isLargeStyle ? "<" + largeTitleTagName + ' class="listItemBodyText">' : '
' : '
', html += textlines[i] || " ", html += 0 === i && isLargeStyle ? "" : "
") + } + return html + } + + function getRightButtonsHtml(options) { + for (var html = "", i = 0, length = options.rightButtons.length; i < length; i++) { + var button = options.rightButtons[i]; + html += '" + } + return html + } + + function getId(item) { + return item.Id + } + + function getListViewHtml(options) { + for (var items = options.items, groupTitle = "", action = options.action || "link", isLargeStyle = "large" === options.imageSize, enableOverview = options.enableOverview, clickEntireItem = !!layoutManager.tv, outerTagName = clickEntireItem ? "button" : "div", enableSideMediaInfo = null == options.enableSideMediaInfo || options.enableSideMediaInfo, outerHtml = "", enableContentWrapper = options.enableOverview && !layoutManager.tv, containerAlbumArtistIds = (options.containerAlbumArtists || []).map(getId), i = 0, length = items.length; i < length; i++) { + var item = items[i], + html = ""; + if (options.showIndex) { + var itemGroupTitle = getIndex(item, options); + itemGroupTitle !== groupTitle && (html && (html += "
"), html += 0 === i ? '

' : '

', html += itemGroupTitle, html += "

", html += "
", groupTitle = itemGroupTitle) + } + var cssClass = "listItem"; + (options.border || !1 !== options.highlight && !layoutManager.tv) && (cssClass += " listItem-border"), clickEntireItem && (cssClass += " itemAction listItem-button"), layoutManager.tv && (cssClass += " listItem-focusscale"); + var downloadWidth = 80; + isLargeStyle && (cssClass += " listItem-largeImage", downloadWidth = 500); + var playlistItemId = item.PlaylistItemId ? ' data-playlistitemid="' + item.PlaylistItemId + '"' : "", + positionTicksData = item.UserData && item.UserData.PlaybackPositionTicks ? ' data-positionticks="' + item.UserData.PlaybackPositionTicks + '"' : "", + collectionIdData = options.collectionId ? ' data-collectionid="' + options.collectionId + '"' : "", + playlistIdData = options.playlistId ? ' data-playlistid="' + options.playlistId + '"' : "", + mediaTypeData = item.MediaType ? ' data-mediatype="' + item.MediaType + '"' : "", + collectionTypeData = item.CollectionType ? ' data-collectiontype="' + item.CollectionType + '"' : "", + channelIdData = item.ChannelId ? ' data-channelid="' + item.ChannelId + '"' : ""; + if (enableContentWrapper && (cssClass += " listItem-withContentWrapper"), html += "<" + outerTagName + ' class="' + cssClass + '"' + playlistItemId + ' data-action="' + action + '" data-isfolder="' + item.IsFolder + '" data-id="' + item.Id + '" data-serverid="' + item.ServerId + '" data-type="' + item.Type + '"' + mediaTypeData + collectionTypeData + channelIdData + positionTicksData + collectionIdData + playlistIdData + ">", enableContentWrapper && (html += '
'), !clickEntireItem && options.dragHandle && (html += ''), !1 !== options.image) { + var imgUrl = "channel" === options.imageSource ? getChannelImageUrl(item, downloadWidth) : getImageUrl(item, downloadWidth); + console.log(imgUrl); + var imageClass = isLargeStyle ? "listItemImage listItemImage-large" : "listItemImage"; + isLargeStyle && layoutManager.tv && (imageClass += " listItemImage-large-tv"); + var playOnImageClick = options.imagePlayButton && !layoutManager.tv; + clickEntireItem || (imageClass += " itemAction"); + var imageAction = playOnImageClick ? "resume" : action; + html += imgUrl ? '
' : '
'; + var indicatorsHtml = ""; + indicatorsHtml += indicators.getPlayedIndicatorHtml(item), indicatorsHtml && (html += '
' + indicatorsHtml + "
"), playOnImageClick && (html += ''); + var progressHtml = indicators.getProgressBarHtml(item, { + containerClass: "listItemProgressBar" + }); + progressHtml && (html += progressHtml), html += "
" + } + options.showIndexNumberLeft && (html += '
', html += item.IndexNumber || " ", html += "
"); + var textlines = []; + options.showProgramDateTime && textlines.push(datetime.toLocaleString(datetime.parseISO8601Date(item.StartDate), { + weekday: "long", + month: "short", + day: "numeric", + hour: "numeric", + minute: "2-digit" + })), options.showProgramTime && textlines.push(datetime.getDisplayTime(datetime.parseISO8601Date(item.StartDate))), options.showChannel && item.ChannelName && textlines.push(item.ChannelName); + var parentTitle = null; + options.showParentTitle && ("Episode" === item.Type ? parentTitle = item.SeriesName : (item.IsSeries || item.EpisodeTitle && item.Name) && (parentTitle = item.Name)); + var displayName = itemHelper.getDisplayName(item, { + includeParentInfo: options.includeParentInfoInTitle + }); + if (options.showIndexNumber && null != item.IndexNumber && (displayName = item.IndexNumber + ". " + displayName), options.showParentTitle && options.parentTitleWithTitle ? (displayName && (parentTitle && (parentTitle += " - "), parentTitle = (parentTitle || "") + displayName), textlines.push(parentTitle || "")) : options.showParentTitle && textlines.push(parentTitle || ""), displayName && !options.parentTitleWithTitle && textlines.push(displayName), item.IsFolder) !1 !== options.artist && item.AlbumArtist && "MusicAlbum" === item.Type && textlines.push(item.AlbumArtist); + else { + var showArtist = !0 === options.artist, + artistItems = item.ArtistItems; + showArtist || !1 === options.artist || (artistItems && artistItems.length ? (artistItems.length > 1 || -1 === containerAlbumArtistIds.indexOf(artistItems[0].Id)) && (showArtist = !0) : showArtist = !0), showArtist && artistItems && "MusicAlbum" !== item.Type && textlines.push(artistItems.map(function(a) { + return a.Name + }).join(", ")) + } + "Game" === item.Type && textlines.push(item.GameSystem), "TvChannel" === item.Type && item.CurrentProgram && textlines.push(itemHelper.getDisplayName(item.CurrentProgram)), cssClass = "listItemBody", clickEntireItem || (cssClass += " itemAction"), !1 === options.image && (cssClass += " listItemBody-noleftpadding"), html += '
'; + if (html += getTextLinesHtml(textlines, isLargeStyle), !1 !== options.mediaInfo && !enableSideMediaInfo) { + html += '
' + mediaInfo.getPrimaryMediaInfoHtml(item, { + episodeTitle: !1, + originalAirDate: !1, + subtitles: !1 + }) + "
" + } + if (enableOverview && item.Overview && (html += '
', html += item.Overview, html += "
"), html += "
", !1 !== options.mediaInfo && enableSideMediaInfo && (html += '
' + mediaInfo.getPrimaryMediaInfoHtml(item, { + year: !1, + container: !1, + episodeTitle: !1, + criticRating: !1, + endsAt: !1 + }) + "
"), options.recordButton || "Timer" !== item.Type && "Program" !== item.Type || (html += indicators.getTimerIndicator(item).replace("indicatorIcon", "indicatorIcon listItemAside")), !clickEntireItem && (options.addToListButton && (html += ''), !1 !== options.moreButton && (html += ''), options.infoButton && (html += ''), options.rightButtons && (html += getRightButtonsHtml(options)), !1 !== options.enableUserDataButtons)) { + html += ''; + var userData = item.UserData || {}, + likes = null == userData.Likes ? "" : userData.Likes; + itemHelper.canMarkPlayed(item) && (html += ''), itemHelper.canRate(item) && (html += ''), html += "" + } + enableContentWrapper && (html += "
", enableOverview && item.Overview && (html += '
', html += item.Overview, html += "
")), html += "", outerHtml += html + } + return outerHtml + } + return { + getListViewHtml: getListViewHtml + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/loading/loading-legacy.js b/dashboard-ui/bower_components/emby-webcomponents/loading/loading-legacy.js index c6cafa9af6..cd6620558f 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/loading/loading-legacy.js +++ b/dashboard-ui/bower_components/emby-webcomponents/loading/loading-legacy.js @@ -1 +1,14 @@ -define(["require","css!./loading-legacy"],function(require){"use strict";var loadingElem;return{show:function(){var elem=loadingElem;elem||(elem=document.createElement("img"),elem.src=require.toUrl(".").split("?")[0]+"/loader2.gif",loadingElem=elem,elem.classList.add("loading-spinner"),document.body.appendChild(elem)),elem.classList.remove("hide")},hide:function(){var elem=loadingElem;elem&&elem.classList.add("hide")}}}); \ No newline at end of file +define(["require", "css!./loading-legacy"], function(require) { + "use strict"; + var loadingElem; + return { + show: function() { + var elem = loadingElem; + elem || (elem = document.createElement("img"), elem.src = require.toUrl(".").split("?")[0] + "/loader2.gif", loadingElem = elem, elem.classList.add("loading-spinner"), document.body.appendChild(elem)), elem.classList.remove("hide") + }, + hide: function() { + var elem = loadingElem; + elem && elem.classList.add("hide") + } + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/loading/loading-lite.js b/dashboard-ui/bower_components/emby-webcomponents/loading/loading-lite.js index b9c6f2adfc..ecdfb255d8 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/loading/loading-lite.js +++ b/dashboard-ui/bower_components/emby-webcomponents/loading/loading-lite.js @@ -1 +1,22 @@ -define(["css!./loading-lite"],function(){"use strict";var loadingElem,layer1,layer2,layer3,layer4,circleLefts,circleRights;return{show:function(){var elem=loadingElem;elem||(elem=document.createElement("div"),loadingElem=elem,elem.classList.add("docspinner"),elem.classList.add("mdl-spinner"),elem.innerHTML='
',document.body.appendChild(elem),layer1=elem.querySelector(".mdl-spinner__layer-1"),layer2=elem.querySelector(".mdl-spinner__layer-2"),layer3=elem.querySelector(".mdl-spinner__layer-3"),layer4=elem.querySelector(".mdl-spinner__layer-4"),circleLefts=elem.querySelectorAll(".mdl-spinner__circleLeft"),circleRights=elem.querySelectorAll(".mdl-spinner__circleRight")),elem.classList.add("mdlSpinnerActive"),layer1.classList.add("mdl-spinner__layer-1-active"),layer2.classList.add("mdl-spinner__layer-2-active"),layer3.classList.add("mdl-spinner__layer-3-active"),layer4.classList.add("mdl-spinner__layer-4-active");var i,length;for(i=0,length=circleLefts.length;i
'+getTabsFn().map(function(t){var tabClass="emby-tab-button";!1===t.enabled&&(tabClass+=" hide");var tabHtml;return t.cssClass&&(tabClass+=" "+t.cssClass),tabHtml=t.href?'
'+t.name+"
":'",index++,tabHtml}).join("")+"
";return tabsContainerElem.innerHTML=tabsHtml,document.body.classList.add("withSectionTabs"),tabOwnerView=view,tabsElem=tabsContainerElem.querySelector('[is="emby-tabs"]'),configureSwipeTabs(view,tabsElem,getTabContainersFn),tabsElem.addEventListener("beforetabchange",function(e){var tabContainers=getTabContainersFn();if(null!=e.detail.previousIndex){var previousPanel=tabContainers[e.detail.previousIndex];previousPanel&&previousPanel.classList.remove("is-active")}var newPanel=tabContainers[e.detail.selectedTabIndex];newPanel&&newPanel.classList.add("is-active")}),onBeforeTabChange&&tabsElem.addEventListener("beforetabchange",onBeforeTabChange),onTabChange&&tabsElem.addEventListener("tabchange",onTabChange),!1!==setSelectedIndex&&(tabsElem.selectedIndex?tabsElem.selectedIndex(selectedIndex):(tabsElem.readySelectedIndex=selectedIndex,tabsElem.addEventListener("ready",onViewTabsReady))),{tabsContainer:tabsContainerElem,tabs:tabsContainerElem.querySelector('[is="emby-tabs"]'),replaced:!0}}return tabsElem||(tabsElem=tabsContainerElem.querySelector('[is="emby-tabs"]')),tabsElem.selectedIndex(selectedIndex),tabOwnerView=view,{tabsContainer:tabsContainerElem,tabs:tabsElem,replaced:!1}}function selectedTabIndex(index){var tabsContainerElem=headerTabsContainer;tabsElem||(tabsElem=tabsContainerElem.querySelector('[is="emby-tabs"]')),null!=index?tabsElem.selectedIndex(index):tabsElem.triggerTabChange()}function getTabsElement(){return document.querySelector(".tabs-viewmenubar")}var tabOwnerView,footerTabsContainer,headerTabsContainer,tabsElem,queryScope=document.querySelector(".skinHeader");return{setTabs:setTabs,getTabsElement:getTabsElement,selectedTabIndex:selectedTabIndex}}); \ No newline at end of file +define(["dom", "browser", "events", "emby-tabs", "emby-button", "emby-linkbutton"], function(dom, browser, events) { + "use strict"; + + function enableTabsInFooter() { + return !1 + } + + function ensureElements(enableInFooter) { + enableInFooter && (footerTabsContainer || (footerTabsContainer = document.createElement("div"), footerTabsContainer.classList.add("footerTabs"), footerTabsContainer.classList.add("sectionTabs"), footerTabsContainer.classList.add("hide"))), headerTabsContainer || (headerTabsContainer = queryScope.querySelector(".headerTabs")) + } + + function onViewTabsReady() { + this.selectedIndex(this.readySelectedIndex), this.readySelectedIndex = null + } + + function allowSwipe(target) { + for (var parent = target; null != parent;) { + if (! function(elem) { + if (dom.parentWithTag(elem, "input")) return !1; + var classList = elem.classList; + return !classList || !classList.contains("scrollX") && !classList.contains("animatedScrollX") + }(parent)) return !1; + parent = parent.parentNode + } + return !0 + } + + function configureSwipeTabs(view, tabsElem, getTabContainersFn) { + if (browser.touch) { + var onSwipeLeft = (getTabContainersFn().length, function(e, target) { + allowSwipe(target) && view.contains(target) && tabsElem.selectNext() + }), + onSwipeRight = function(e, target) { + allowSwipe(target) && view.contains(target) && tabsElem.selectPrevious() + }; + require(["touchHelper"], function(TouchHelper) { + var touchHelper = new TouchHelper(view.parentNode.parentNode); + events.on(touchHelper, "swipeleft", onSwipeLeft), events.on(touchHelper, "swiperight", onSwipeRight), view.addEventListener("viewdestroy", function() { + touchHelper.destroy() + }) + }) + } + } + + function setTabs(view, selectedIndex, getTabsFn, getTabContainersFn, onBeforeTabChange, onTabChange, setSelectedIndex) { + var enableInFooter = enableTabsInFooter(); + if (!view) return tabOwnerView && (headerTabsContainer || (headerTabsContainer = queryScope.querySelector(".headerTabs")), ensureElements(enableInFooter), document.body.classList.remove("withSectionTabs"), headerTabsContainer.innerHTML = "", headerTabsContainer.classList.add("hide"), footerTabsContainer && (footerTabsContainer.innerHTML = "", footerTabsContainer.classList.add("hide")), tabOwnerView = null), { + tabsContainer: headerTabsContainer, + replaced: !1 + }; + ensureElements(enableInFooter); + var tabsContainerElem = enableInFooter ? footerTabsContainer : headerTabsContainer; + if (tabOwnerView || tabsContainerElem.classList.remove("hide"), tabOwnerView !== view) { + var index = 0, + indexAttribute = null == selectedIndex ? "" : ' data-index="' + selectedIndex + '"', + tabsHtml = '
' + getTabsFn().map(function(t) { + var tabClass = "emby-tab-button"; + !1 === t.enabled && (tabClass += " hide"); + var tabHtml; + return t.cssClass && (tabClass += " " + t.cssClass), tabHtml = t.href ? '
' + t.name + "
" : '", index++, tabHtml + }).join("") + "
"; + return tabsContainerElem.innerHTML = tabsHtml, document.body.classList.add("withSectionTabs"), tabOwnerView = view, tabsElem = tabsContainerElem.querySelector('[is="emby-tabs"]'), configureSwipeTabs(view, tabsElem, getTabContainersFn), tabsElem.addEventListener("beforetabchange", function(e) { + var tabContainers = getTabContainersFn(); + if (null != e.detail.previousIndex) { + var previousPanel = tabContainers[e.detail.previousIndex]; + previousPanel && previousPanel.classList.remove("is-active") + } + var newPanel = tabContainers[e.detail.selectedTabIndex]; + newPanel && newPanel.classList.add("is-active") + }), onBeforeTabChange && tabsElem.addEventListener("beforetabchange", onBeforeTabChange), onTabChange && tabsElem.addEventListener("tabchange", onTabChange), !1 !== setSelectedIndex && (tabsElem.selectedIndex ? tabsElem.selectedIndex(selectedIndex) : (tabsElem.readySelectedIndex = selectedIndex, tabsElem.addEventListener("ready", onViewTabsReady))), { + tabsContainer: tabsContainerElem, + tabs: tabsContainerElem.querySelector('[is="emby-tabs"]'), + replaced: !0 + } + } + return tabsElem || (tabsElem = tabsContainerElem.querySelector('[is="emby-tabs"]')), tabsElem.selectedIndex(selectedIndex), tabOwnerView = view, { + tabsContainer: tabsContainerElem, + tabs: tabsElem, + replaced: !1 + } + } + + function selectedTabIndex(index) { + var tabsContainerElem = headerTabsContainer; + tabsElem || (tabsElem = tabsContainerElem.querySelector('[is="emby-tabs"]')), null != index ? tabsElem.selectedIndex(index) : tabsElem.triggerTabChange() + } + + function getTabsElement() { + return document.querySelector(".tabs-viewmenubar") + } + var tabOwnerView, footerTabsContainer, headerTabsContainer, tabsElem, queryScope = document.querySelector(".skinHeader"); + return { + setTabs: setTabs, + getTabsElement: getTabsElement, + selectedTabIndex: selectedTabIndex + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/mediainfo/mediainfo.js b/dashboard-ui/bower_components/emby-webcomponents/mediainfo/mediainfo.js index 550a347347..14f71ed273 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/mediainfo/mediainfo.js +++ b/dashboard-ui/bower_components/emby-webcomponents/mediainfo/mediainfo.js @@ -1 +1,258 @@ -define(["datetime","globalize","appRouter","itemHelper","indicators","material-icons","css!./mediainfo.css","programStyles","emby-linkbutton"],function(datetime,globalize,appRouter,itemHelper,indicators){"use strict";function getTimerIndicator(item){var status;if("SeriesTimer"===item.Type)return'';if(item.TimerId||item.SeriesTimerId)status=item.Status||"Cancelled";else{if("Timer"!==item.Type)return"";status=item.Status}return item.SeriesTimerId?"Cancelled"!==status?'':'':''}function getProgramInfoHtml(item,options){var text,date,html="",miscInfo=[];if(item.StartDate&&!1!==options.programTime)try{text="",date=datetime.parseISO8601Date(item.StartDate),!1!==options.startDate&&(text+=datetime.toLocaleDateString(date,{weekday:"short",month:"short",day:"numeric"})),text+=" "+datetime.getDisplayTime(date),item.EndDate&&(date=datetime.parseISO8601Date(item.EndDate),text+=" - "+datetime.getDisplayTime(date)),miscInfo.push(text)}catch(e){console.log("Error parsing date: "+item.StartDate)}if(item.ChannelNumber&&miscInfo.push("CH "+item.ChannelNumber),item.ChannelName&&(options.interactive&&item.ChannelId?miscInfo.push({html:''+item.ChannelName+""}):miscInfo.push(item.ChannelName)),!1!==options.timerIndicator){var timerHtml=getTimerIndicator(item);timerHtml&&miscInfo.push({html:timerHtml})}return html+=miscInfo.map(function(m){return getMediaInfoItem(m)}).join("")}function getMediaInfoHtml(item,options){var html="",miscInfo=[];options=options||{};var text,date,minutes,count,showFolderRuntime="MusicAlbum"===item.Type||"MusicArtist"===item.MediaType||"Playlist"===item.MediaType||"MusicGenre"===item.MediaType;if(showFolderRuntime?(count=item.SongCount||item.ChildCount,count&&miscInfo.push(globalize.translate("sharedcomponents#TrackCount",count)),item.RunTimeTicks&&miscInfo.push(datetime.getDisplayRunningTime(item.RunTimeTicks))):"PhotoAlbum"!==item.Type&&"BoxSet"!==item.Type||(count=item.ChildCount)&&miscInfo.push(globalize.translate("sharedcomponents#ItemCount",count)),("Episode"===item.Type||"Photo"===item.MediaType)&&!1!==options.originalAirDate&&item.PremiereDate)try{date=datetime.parseISO8601Date(item.PremiereDate),text=datetime.toLocaleDateString(date),miscInfo.push(text)}catch(e){console.log("Error parsing date: "+item.PremiereDate)}if("SeriesTimer"===item.Type&&(item.RecordAnyTime?miscInfo.push(globalize.translate("sharedcomponents#Anytime")):miscInfo.push(datetime.getDisplayTime(item.StartDate)),item.RecordAnyChannel?miscInfo.push(globalize.translate("sharedcomponents#AllChannels")):miscInfo.push(item.ChannelName||globalize.translate("sharedcomponents#OneChannel"))),item.StartDate&&"Program"!==item.Type&&"SeriesTimer"!==item.Type)try{date=datetime.parseISO8601Date(item.StartDate),text=datetime.toLocaleDateString(date),miscInfo.push(text),"Recording"!==item.Type&&(text=datetime.getDisplayTime(date),miscInfo.push(text))}catch(e){console.log("Error parsing date: "+item.StartDate)}if(!1!==options.year&&item.ProductionYear&&"Series"===item.Type)if("Continuing"===item.Status)miscInfo.push(globalize.translate("sharedcomponents#SeriesYearToPresent",item.ProductionYear));else if(item.ProductionYear){if(text=item.ProductionYear,item.EndDate)try{var endYear=datetime.parseISO8601Date(item.EndDate).getFullYear();endYear!==item.ProductionYear&&(text+="-"+datetime.parseISO8601Date(item.EndDate).getFullYear())}catch(e){console.log("Error parsing date: "+item.EndDate)}miscInfo.push(text)}if("Program"===item.Type)if(!1!==options.programIndicator&&(item.IsLive?miscInfo.push({html:'
'+globalize.translate("sharedcomponents#Live")+"
"}):item.IsPremiere?miscInfo.push({html:'
'+globalize.translate("sharedcomponents#Premiere")+"
"}):item.IsSeries&&!item.IsRepeat?miscInfo.push({html:'
'+globalize.translate("sharedcomponents#AttributeNew")+"
"}):item.IsSeries&&item.IsRepeat&&miscInfo.push({html:'
'+globalize.translate("sharedcomponents#Repeat")+"
"})),(item.IsSeries||item.EpisodeTitle)&&!1!==options.episodeTitle)(text=itemHelper.getDisplayName(item,{includeIndexNumber:options.episodeTitleIndexNumber}))&&miscInfo.push(text);else if(item.IsMovie&&item.ProductionYear&&!1!==options.originalAirDate)miscInfo.push(item.ProductionYear);else if(item.PremiereDate&&!1!==options.originalAirDate)try{date=datetime.parseISO8601Date(item.PremiereDate),text=globalize.translate("sharedcomponents#OriginalAirDateValue",datetime.toLocaleDateString(date)),miscInfo.push(text)}catch(e){console.log("Error parsing date: "+item.PremiereDate)}else item.ProductionYear&&miscInfo.push(item.ProductionYear);if(!1!==options.year&&"Series"!==item.Type&&"Episode"!==item.Type&&"Person"!==item.Type&&"Photo"!==item.MediaType&&"Program"!==item.Type&&"Season"!==item.Type)if(item.ProductionYear)miscInfo.push(item.ProductionYear);else if(item.PremiereDate)try{text=datetime.parseISO8601Date(item.PremiereDate).getFullYear(),miscInfo.push(text)}catch(e){console.log("Error parsing date: "+item.PremiereDate)}if(item.RunTimeTicks&&"Series"!==item.Type&&"Program"!==item.Type&&!showFolderRuntime&&!1!==options.runtime&&("Audio"===item.Type?miscInfo.push(datetime.getDisplayRunningTime(item.RunTimeTicks)):(minutes=item.RunTimeTicks/6e8,minutes=minutes||1,miscInfo.push(Math.round(minutes)+" mins"))),item.OfficialRating&&"Season"!==item.Type&&"Episode"!==item.Type&&miscInfo.push({text:item.OfficialRating,cssClass:"mediaInfoOfficialRating"}),item.Video3DFormat&&miscInfo.push("3D"),"Photo"===item.MediaType&&item.Width&&item.Height&&miscInfo.push(item.Width+"x"+item.Height),!1!==options.container&&"Audio"===item.Type&&item.Container&&miscInfo.push(item.Container),html+=miscInfo.map(function(m){return getMediaInfoItem(m)}).join(""),html+=getStarIconsHtml(item),item.HasSubtitles&&!1!==options.subtitles&&(html+='
CC
'),item.CriticRating&&!1!==options.criticRating&&(item.CriticRating>=60?html+='
'+item.CriticRating+"
":html+='
'+item.CriticRating+"
"),!1!==options.endsAt){var endsAt=getEndsAt(item);endsAt&&(html+=getMediaInfoItem(endsAt,"endsAt"))}return html+=indicators.getMissingIndicator(item)}function getEndsAt(item){if("Video"===item.MediaType&&item.RunTimeTicks&&!item.StartDate){var endDate=(new Date).getTime()+item.RunTimeTicks/1e4;endDate=new Date(endDate);var displayTime=datetime.getDisplayTime(endDate);return globalize.translate("sharedcomponents#EndsAtValue",displayTime)}return null}function getEndsAtFromPosition(runtimeTicks,positionTicks,includeText){var endDate=(new Date).getTime()+(runtimeTicks-(positionTicks||0))/1e4;endDate=new Date(endDate);var displayTime=datetime.getDisplayTime(endDate);return!1===includeText?displayTime:globalize.translate("sharedcomponents#EndsAtValue",displayTime)}function getMediaInfoItem(m,cssClass){cssClass=cssClass?cssClass+" mediaInfoItem":"mediaInfoItem";var mediaInfoText=m;if("string"!=typeof m&&"number"!=typeof m){if(m.html)return m.html;mediaInfoText=m.text,cssClass+=" "+m.cssClass}return'
'+mediaInfoText+"
"}function getStarIconsHtml(item){var html="",rating=item.CommunityRating;return rating&&(html+='
',html+='',html+=rating,html+="
"),html}function dynamicEndTime(elem,item){var interval=setInterval(function(){if(!document.body.contains(elem))return void clearInterval(interval);elem.innerHTML=getEndsAt(item)},6e4)}function fillPrimaryMediaInfo(elem,item,options){var html=getPrimaryMediaInfoHtml(item,options);elem.innerHTML=html,afterFill(elem,item,options)}function fillSecondaryMediaInfo(elem,item,options){var html=getSecondaryMediaInfoHtml(item,options);elem.innerHTML=html,afterFill(elem,item,options)}function afterFill(elem,item,options){if(!1!==options.endsAt){var endsAtElem=elem.querySelector(".endsAt");endsAtElem&&dynamicEndTime(endsAtElem,item)}var lnkChannel=elem.querySelector(".lnkChannel");lnkChannel&&lnkChannel.addEventListener("click",onChannelLinkClick)}function onChannelLinkClick(e){var channelId=this.getAttribute("data-id"),serverId=this.getAttribute("data-serverid");return appRouter.showItem(channelId,serverId),e.preventDefault(),!1}function getPrimaryMediaInfoHtml(item,options){return options=options||{},null==options.interactive&&(options.interactive=!1),getMediaInfoHtml(item,options)}function getSecondaryMediaInfoHtml(item,options){return options=options||{},null==options.interactive&&(options.interactive=!1),"Program"===item.Type?getProgramInfoHtml(item,options):""}function getResolutionText(i){var width=i.Width,height=i.Height;if(width&&height){if(width>=3800||height>=2e3)return"4K";if(width>=2500||height>=1400)return i.IsInterlaced?"1440i":"1440P";if(width>=1800||height>=1e3)return i.IsInterlaced?"1080i":"1080P";if(width>=1200||height>=700)return i.IsInterlaced?"720i":"720P";if(width>=700||height>=400)return i.IsInterlaced?"480i":"480P"}return null}function getAudioStreamForDisplay(item){if(!item.MediaSources)return null;var mediaSource=item.MediaSources[0];return mediaSource?(mediaSource.MediaStreams||[]).filter(function(i){return"Audio"===i.Type&&(i.Index===mediaSource.DefaultAudioStreamIndex||null==mediaSource.DefaultAudioStreamIndex)})[0]:null}function getMediaInfoStats(item,options){options=options||{};var list=[],mediaSource=(item.MediaSources||[])[0]||{},videoStream=(mediaSource.MediaStreams||[]).filter(function(i){return"Video"===i.Type})[0]||{},audioStream=getAudioStreamForDisplay(item)||{};"Dvd"===item.VideoType&&list.push({type:"mediainfo",text:"Dvd"}),"BluRay"===item.VideoType&&list.push({type:"mediainfo",text:"BluRay"});var resolutionText=getResolutionText(videoStream);resolutionText&&list.push({type:"mediainfo",text:resolutionText}),videoStream.Codec&&list.push({type:"mediainfo",text:videoStream.Codec});var channelText,channels=audioStream.Channels;8===channels?channelText="7.1":7===channels?channelText="6.1":6===channels?channelText="5.1":2===channels&&(channelText="2.0"),channelText&&list.push({type:"mediainfo",text:channelText});var audioCodec=(audioStream.Codec||"").toLowerCase();if("dca"!==audioCodec&&"dts"!==audioCodec||!audioStream.Profile?audioStream.Codec&&list.push({type:"mediainfo",text:audioStream.Codec}):list.push({type:"mediainfo",text:audioStream.Profile}),item.DateCreated&&itemHelper.enableDateAddedDisplay(item)){var dateCreated=datetime.parseISO8601Date(item.DateCreated);list.push({type:"added",text:globalize.translate("sharedcomponents#AddedOnValue",datetime.toLocaleDateString(dateCreated)+" "+datetime.getDisplayTime(dateCreated))})}return list}return{getMediaInfoHtml:getPrimaryMediaInfoHtml,fill:fillPrimaryMediaInfo,getEndsAt:getEndsAt,getEndsAtFromPosition:getEndsAtFromPosition,getPrimaryMediaInfoHtml:getPrimaryMediaInfoHtml,getSecondaryMediaInfoHtml:getSecondaryMediaInfoHtml,fillPrimaryMediaInfo:fillPrimaryMediaInfo,fillSecondaryMediaInfo:fillSecondaryMediaInfo,getMediaInfoStats:getMediaInfoStats,getResolutionText:getResolutionText}}); \ No newline at end of file +define(["datetime", "globalize", "appRouter", "itemHelper", "indicators", "material-icons", "css!./mediainfo.css", "programStyles", "emby-linkbutton"], function(datetime, globalize, appRouter, itemHelper, indicators) { + "use strict"; + + function getTimerIndicator(item) { + var status; + if ("SeriesTimer" === item.Type) return ''; + if (item.TimerId || item.SeriesTimerId) status = item.Status || "Cancelled"; + else { + if ("Timer" !== item.Type) return ""; + status = item.Status + } + return item.SeriesTimerId ? "Cancelled" !== status ? '' : '' : '' + } + + function getProgramInfoHtml(item, options) { + var text, date, html = "", + miscInfo = []; + if (item.StartDate && !1 !== options.programTime) try { + text = "", date = datetime.parseISO8601Date(item.StartDate), !1 !== options.startDate && (text += datetime.toLocaleDateString(date, { + weekday: "short", + month: "short", + day: "numeric" + })), text += " " + datetime.getDisplayTime(date), item.EndDate && (date = datetime.parseISO8601Date(item.EndDate), text += " - " + datetime.getDisplayTime(date)), miscInfo.push(text) + } catch (e) { + console.log("Error parsing date: " + item.StartDate) + } + if (item.ChannelNumber && miscInfo.push("CH " + item.ChannelNumber), item.ChannelName && (options.interactive && item.ChannelId ? miscInfo.push({ + html: '' + item.ChannelName + "" + }) : miscInfo.push(item.ChannelName)), !1 !== options.timerIndicator) { + var timerHtml = getTimerIndicator(item); + timerHtml && miscInfo.push({ + html: timerHtml + }) + } + return html += miscInfo.map(function(m) { + return getMediaInfoItem(m) + }).join("") + } + + function getMediaInfoHtml(item, options) { + var html = "", + miscInfo = []; + options = options || {}; + var text, date, minutes, count, showFolderRuntime = "MusicAlbum" === item.Type || "MusicArtist" === item.MediaType || "Playlist" === item.MediaType || "MusicGenre" === item.MediaType; + if (showFolderRuntime ? (count = item.SongCount || item.ChildCount, count && miscInfo.push(globalize.translate("sharedcomponents#TrackCount", count)), item.RunTimeTicks && miscInfo.push(datetime.getDisplayRunningTime(item.RunTimeTicks))) : "PhotoAlbum" !== item.Type && "BoxSet" !== item.Type || (count = item.ChildCount) && miscInfo.push(globalize.translate("sharedcomponents#ItemCount", count)), ("Episode" === item.Type || "Photo" === item.MediaType) && !1 !== options.originalAirDate && item.PremiereDate) try { + date = datetime.parseISO8601Date(item.PremiereDate), text = datetime.toLocaleDateString(date), miscInfo.push(text) + } catch (e) { + console.log("Error parsing date: " + item.PremiereDate) + } + if ("SeriesTimer" === item.Type && (item.RecordAnyTime ? miscInfo.push(globalize.translate("sharedcomponents#Anytime")) : miscInfo.push(datetime.getDisplayTime(item.StartDate)), item.RecordAnyChannel ? miscInfo.push(globalize.translate("sharedcomponents#AllChannels")) : miscInfo.push(item.ChannelName || globalize.translate("sharedcomponents#OneChannel"))), item.StartDate && "Program" !== item.Type && "SeriesTimer" !== item.Type) try { + date = datetime.parseISO8601Date(item.StartDate), text = datetime.toLocaleDateString(date), miscInfo.push(text), "Recording" !== item.Type && (text = datetime.getDisplayTime(date), miscInfo.push(text)) + } catch (e) { + console.log("Error parsing date: " + item.StartDate) + } + if (!1 !== options.year && item.ProductionYear && "Series" === item.Type) + if ("Continuing" === item.Status) miscInfo.push(globalize.translate("sharedcomponents#SeriesYearToPresent", item.ProductionYear)); + else if (item.ProductionYear) { + if (text = item.ProductionYear, item.EndDate) try { + var endYear = datetime.parseISO8601Date(item.EndDate).getFullYear(); + endYear !== item.ProductionYear && (text += "-" + datetime.parseISO8601Date(item.EndDate).getFullYear()) + } catch (e) { + console.log("Error parsing date: " + item.EndDate) + } + miscInfo.push(text) + } + if ("Program" === item.Type) + if (!1 !== options.programIndicator && (item.IsLive ? miscInfo.push({ + html: '
' + globalize.translate("sharedcomponents#Live") + "
" + }) : item.IsPremiere ? miscInfo.push({ + html: '
' + globalize.translate("sharedcomponents#Premiere") + "
" + }) : item.IsSeries && !item.IsRepeat ? miscInfo.push({ + html: '
' + globalize.translate("sharedcomponents#AttributeNew") + "
" + }) : item.IsSeries && item.IsRepeat && miscInfo.push({ + html: '
' + globalize.translate("sharedcomponents#Repeat") + "
" + })), (item.IsSeries || item.EpisodeTitle) && !1 !== options.episodeTitle)(text = itemHelper.getDisplayName(item, { + includeIndexNumber: options.episodeTitleIndexNumber + })) && miscInfo.push(text); + else if (item.IsMovie && item.ProductionYear && !1 !== options.originalAirDate) miscInfo.push(item.ProductionYear); + else if (item.PremiereDate && !1 !== options.originalAirDate) try { + date = datetime.parseISO8601Date(item.PremiereDate), text = globalize.translate("sharedcomponents#OriginalAirDateValue", datetime.toLocaleDateString(date)), miscInfo.push(text) + } catch (e) { + console.log("Error parsing date: " + item.PremiereDate) + } else item.ProductionYear && miscInfo.push(item.ProductionYear); + if (!1 !== options.year && "Series" !== item.Type && "Episode" !== item.Type && "Person" !== item.Type && "Photo" !== item.MediaType && "Program" !== item.Type && "Season" !== item.Type) + if (item.ProductionYear) miscInfo.push(item.ProductionYear); + else if (item.PremiereDate) try { + text = datetime.parseISO8601Date(item.PremiereDate).getFullYear(), miscInfo.push(text) + } catch (e) { + console.log("Error parsing date: " + item.PremiereDate) + } + if (item.RunTimeTicks && "Series" !== item.Type && "Program" !== item.Type && !showFolderRuntime && !1 !== options.runtime && ("Audio" === item.Type ? miscInfo.push(datetime.getDisplayRunningTime(item.RunTimeTicks)) : (minutes = item.RunTimeTicks / 6e8, minutes = minutes || 1, miscInfo.push(Math.round(minutes) + " mins"))), item.OfficialRating && "Season" !== item.Type && "Episode" !== item.Type && miscInfo.push({ + text: item.OfficialRating, + cssClass: "mediaInfoOfficialRating" + }), item.Video3DFormat && miscInfo.push("3D"), "Photo" === item.MediaType && item.Width && item.Height && miscInfo.push(item.Width + "x" + item.Height), !1 !== options.container && "Audio" === item.Type && item.Container && miscInfo.push(item.Container), html += miscInfo.map(function(m) { + return getMediaInfoItem(m) + }).join(""), html += getStarIconsHtml(item), item.HasSubtitles && !1 !== options.subtitles && (html += '
CC
'), item.CriticRating && !1 !== options.criticRating && (item.CriticRating >= 60 ? html += '
' + item.CriticRating + "
" : html += '
' + item.CriticRating + "
"), !1 !== options.endsAt) { + var endsAt = getEndsAt(item); + endsAt && (html += getMediaInfoItem(endsAt, "endsAt")) + } + return html += indicators.getMissingIndicator(item) + } + + function getEndsAt(item) { + if ("Video" === item.MediaType && item.RunTimeTicks && !item.StartDate) { + var endDate = (new Date).getTime() + item.RunTimeTicks / 1e4; + endDate = new Date(endDate); + var displayTime = datetime.getDisplayTime(endDate); + return globalize.translate("sharedcomponents#EndsAtValue", displayTime) + } + return null + } + + function getEndsAtFromPosition(runtimeTicks, positionTicks, includeText) { + var endDate = (new Date).getTime() + (runtimeTicks - (positionTicks || 0)) / 1e4; + endDate = new Date(endDate); + var displayTime = datetime.getDisplayTime(endDate); + return !1 === includeText ? displayTime : globalize.translate("sharedcomponents#EndsAtValue", displayTime) + } + + function getMediaInfoItem(m, cssClass) { + cssClass = cssClass ? cssClass + " mediaInfoItem" : "mediaInfoItem"; + var mediaInfoText = m; + if ("string" != typeof m && "number" != typeof m) { + if (m.html) return m.html; + mediaInfoText = m.text, cssClass += " " + m.cssClass + } + return '
' + mediaInfoText + "
" + } + + function getStarIconsHtml(item) { + var html = "", + rating = item.CommunityRating; + return rating && (html += '
', html += '', html += rating, html += "
"), html + } + + function dynamicEndTime(elem, item) { + var interval = setInterval(function() { + if (!document.body.contains(elem)) return void clearInterval(interval); + elem.innerHTML = getEndsAt(item) + }, 6e4) + } + + function fillPrimaryMediaInfo(elem, item, options) { + var html = getPrimaryMediaInfoHtml(item, options); + elem.innerHTML = html, afterFill(elem, item, options) + } + + function fillSecondaryMediaInfo(elem, item, options) { + var html = getSecondaryMediaInfoHtml(item, options); + elem.innerHTML = html, afterFill(elem, item, options) + } + + function afterFill(elem, item, options) { + if (!1 !== options.endsAt) { + var endsAtElem = elem.querySelector(".endsAt"); + endsAtElem && dynamicEndTime(endsAtElem, item) + } + var lnkChannel = elem.querySelector(".lnkChannel"); + lnkChannel && lnkChannel.addEventListener("click", onChannelLinkClick) + } + + function onChannelLinkClick(e) { + var channelId = this.getAttribute("data-id"), + serverId = this.getAttribute("data-serverid"); + return appRouter.showItem(channelId, serverId), e.preventDefault(), !1 + } + + function getPrimaryMediaInfoHtml(item, options) { + return options = options || {}, null == options.interactive && (options.interactive = !1), getMediaInfoHtml(item, options) + } + + function getSecondaryMediaInfoHtml(item, options) { + return options = options || {}, null == options.interactive && (options.interactive = !1), "Program" === item.Type ? getProgramInfoHtml(item, options) : "" + } + + function getResolutionText(i) { + var width = i.Width, + height = i.Height; + if (width && height) { + if (width >= 3800 || height >= 2e3) return "4K"; + if (width >= 2500 || height >= 1400) return i.IsInterlaced ? "1440i" : "1440P"; + if (width >= 1800 || height >= 1e3) return i.IsInterlaced ? "1080i" : "1080P"; + if (width >= 1200 || height >= 700) return i.IsInterlaced ? "720i" : "720P"; + if (width >= 700 || height >= 400) return i.IsInterlaced ? "480i" : "480P" + } + return null + } + + function getAudioStreamForDisplay(item) { + if (!item.MediaSources) return null; + var mediaSource = item.MediaSources[0]; + return mediaSource ? (mediaSource.MediaStreams || []).filter(function(i) { + return "Audio" === i.Type && (i.Index === mediaSource.DefaultAudioStreamIndex || null == mediaSource.DefaultAudioStreamIndex) + })[0] : null + } + + function getMediaInfoStats(item, options) { + options = options || {}; + var list = [], + mediaSource = (item.MediaSources || [])[0] || {}, + videoStream = (mediaSource.MediaStreams || []).filter(function(i) { + return "Video" === i.Type + })[0] || {}, + audioStream = getAudioStreamForDisplay(item) || {}; + "Dvd" === item.VideoType && list.push({ + type: "mediainfo", + text: "Dvd" + }), "BluRay" === item.VideoType && list.push({ + type: "mediainfo", + text: "BluRay" + }); + var resolutionText = getResolutionText(videoStream); + resolutionText && list.push({ + type: "mediainfo", + text: resolutionText + }), videoStream.Codec && list.push({ + type: "mediainfo", + text: videoStream.Codec + }); + var channelText, channels = audioStream.Channels; + 8 === channels ? channelText = "7.1" : 7 === channels ? channelText = "6.1" : 6 === channels ? channelText = "5.1" : 2 === channels && (channelText = "2.0"), channelText && list.push({ + type: "mediainfo", + text: channelText + }); + var audioCodec = (audioStream.Codec || "").toLowerCase(); + if ("dca" !== audioCodec && "dts" !== audioCodec || !audioStream.Profile ? audioStream.Codec && list.push({ + type: "mediainfo", + text: audioStream.Codec + }) : list.push({ + type: "mediainfo", + text: audioStream.Profile + }), item.DateCreated && itemHelper.enableDateAddedDisplay(item)) { + var dateCreated = datetime.parseISO8601Date(item.DateCreated); + list.push({ + type: "added", + text: globalize.translate("sharedcomponents#AddedOnValue", datetime.toLocaleDateString(dateCreated) + " " + datetime.getDisplayTime(dateCreated)) + }) + } + return list + } + return { + getMediaInfoHtml: getPrimaryMediaInfoHtml, + fill: fillPrimaryMediaInfo, + getEndsAt: getEndsAt, + getEndsAtFromPosition: getEndsAtFromPosition, + getPrimaryMediaInfoHtml: getPrimaryMediaInfoHtml, + getSecondaryMediaInfoHtml: getSecondaryMediaInfoHtml, + fillPrimaryMediaInfo: fillPrimaryMediaInfo, + fillSecondaryMediaInfo: fillSecondaryMediaInfo, + getMediaInfoStats: getMediaInfoStats, + getResolutionText: getResolutionText + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/metadataeditor/metadataeditor.js b/dashboard-ui/bower_components/emby-webcomponents/metadataeditor/metadataeditor.js index 3a9a948931..abf15cc882 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/metadataeditor/metadataeditor.js +++ b/dashboard-ui/bower_components/emby-webcomponents/metadataeditor/metadataeditor.js @@ -1 +1,482 @@ -define(["itemHelper","dom","layoutManager","dialogHelper","datetime","loading","focusManager","connectionManager","globalize","require","shell","emby-checkbox","emby-input","emby-select","listViewStyle","emby-textarea","emby-button","paper-icon-button-light","css!./../formdialog","clearButtonStyle","flexStyles"],function(itemHelper,dom,layoutManager,dialogHelper,datetime,loading,focusManager,connectionManager,globalize,require,shell){"use strict";function isDialog(){return currentContext.classList.contains("dialog")}function closeDialog(isSubmitted){isDialog()&&dialogHelper.close(currentContext)}function submitUpdatedItem(form,item){function afterContentTypeUpdated(){require(["toast"],function(toast){toast(globalize.translate("sharedcomponents#MessageItemSaved"))}),loading.hide(),closeDialog(!0)}var apiClient=getApiClient();apiClient.updateItem(item).then(function(){var newContentType=form.querySelector("#selectContentType").value||"";(metadataEditorInfo.ContentType||"")!==newContentType?apiClient.ajax({url:apiClient.getUrl("Items/"+item.Id+"/ContentType",{ContentType:newContentType}),type:"POST"}).then(function(){afterContentTypeUpdated()}):afterContentTypeUpdated()})}function getSelectedAirDays(form){var checkedItems=form.querySelectorAll(".chkAirDay:checked")||[];return Array.prototype.map.call(checkedItems,function(c){return c.getAttribute("data-day")})}function getAlbumArtists(form){return form.querySelector("#txtAlbumArtist").value.trim().split(";").filter(function(s){return s.length>0}).map(function(a){return{Name:a}})}function getArtists(form){return form.querySelector("#txtArtist").value.trim().split(";").filter(function(s){return s.length>0}).map(function(a){return{Name:a}})}function getDateValue(form,element,property){var val=form.querySelector(element).value;if(!val)return null;if(currentItem[property]){var date=datetime.parseISO8601Date(currentItem[property],!0),parts=date.toISOString().split("T");if(0===parts[0].indexOf(val)){val+="T"+parts[1]}}return val}function onSubmit(e){loading.show();var form=this,item={Id:currentItem.Id,Name:form.querySelector("#txtName").value,OriginalTitle:form.querySelector("#txtOriginalName").value,ForcedSortName:form.querySelector("#txtSortName").value,CommunityRating:form.querySelector("#txtCommunityRating").value,CriticRating:form.querySelector("#txtCriticRating").value,IndexNumber:form.querySelector("#txtIndexNumber").value||null,AirsBeforeSeasonNumber:form.querySelector("#txtAirsBeforeSeason").value,AirsAfterSeasonNumber:form.querySelector("#txtAirsAfterSeason").value,AirsBeforeEpisodeNumber:form.querySelector("#txtAirsBeforeEpisode").value,ParentIndexNumber:form.querySelector("#txtParentIndexNumber").value||null,DisplayOrder:form.querySelector("#selectDisplayOrder").value,Album:form.querySelector("#txtAlbum").value,AlbumArtists:getAlbumArtists(form),ArtistItems:getArtists(form),Overview:form.querySelector("#txtOverview").value,Status:form.querySelector("#selectStatus").value,AirDays:getSelectedAirDays(form),AirTime:form.querySelector("#txtAirTime").value,Genres:getListValues(form.querySelector("#listGenres")),Tags:getListValues(form.querySelector("#listTags")),Studios:getListValues(form.querySelector("#listStudios")).map(function(element){return{Name:element}}),PremiereDate:getDateValue(form,"#txtPremiereDate","PremiereDate"),DateCreated:getDateValue(form,"#txtDateAdded","DateCreated"),EndDate:getDateValue(form,"#txtEndDate","EndDate"),ProductionYear:form.querySelector("#txtProductionYear").value,AspectRatio:form.querySelector("#txtOriginalAspectRatio").value,Video3DFormat:form.querySelector("#select3dFormat").value,OfficialRating:form.querySelector("#selectOfficialRating").value,CustomRating:form.querySelector("#selectCustomRating").value,People:currentItem.People,LockData:form.querySelector("#chkLockData").checked,LockedFields:Array.prototype.filter.call(form.querySelectorAll(".selectLockedField"),function(c){return!c.checked}).map(function(c){return c.getAttribute("data-value")})};item.ProviderIds=Object.assign({},currentItem.ProviderIds);var idElements=form.querySelectorAll(".txtExternalId");if(Array.prototype.map.call(idElements,function(idElem){var providerKey=idElem.getAttribute("data-providerkey");item.ProviderIds[providerKey]=idElem.value}),item.PreferredMetadataLanguage=form.querySelector("#selectLanguage").value,item.PreferredMetadataCountryCode=form.querySelector("#selectCountry").value,"Person"===currentItem.Type){var placeOfBirth=form.querySelector("#txtPlaceOfBirth").value;item.ProductionLocations=placeOfBirth?[placeOfBirth]:[]}if("Series"===currentItem.Type){var seriesRuntime=form.querySelector("#txtSeriesRuntime").value;item.RunTimeTicks=seriesRuntime?6e8*seriesRuntime:null}var tagline=form.querySelector("#txtTagline").value;return item.Taglines=tagline?[tagline]:[],submitUpdatedItem(form,item),e.preventDefault(),e.stopPropagation(),!1}function getListValues(list){return Array.prototype.map.call(list.querySelectorAll(".textValue"),function(el){return el.textContent})}function addElementToList(source,sortCallback){require(["prompt"],function(prompt){prompt({label:"Value:"}).then(function(text){var list=dom.parentWithClass(source,"editableListviewContainer").querySelector(".paperList"),items=getListValues(list);items.push(text),populateListView(list,items,sortCallback)})})}function removeElementFromList(source){var el=dom.parentWithClass(source,"listItem");el.parentNode.removeChild(el)}function editPerson(context,person,index){require(["personEditor"],function(personEditor){personEditor.show(person).then(function(updatedPerson){-1===index&¤tItem.People.push(updatedPerson),populatePeople(context,currentItem.People)})})}function showMoreMenu(context,button,user){require(["itemContextMenu"],function(itemContextMenu){var item=currentItem;itemContextMenu.show({item:item,positionTo:button,edit:!1,editImages:!0,editSubtitles:!0,sync:!1,share:!1,play:!1,queue:!1,user:user}).then(function(result){result.deleted?afterDeleted(context,item):result.updated&&reload(context,item.Id,item.ServerId)})})}function afterDeleted(context,item){var parentId=item.ParentId||item.SeasonId||item.SeriesId;parentId?reload(context,parentId,item.ServerId):require(["appRouter"],function(appRouter){appRouter.goHome()})}function onEditorClick(e){var btnRemoveFromEditorList=dom.parentWithClass(e.target,"btnRemoveFromEditorList");if(btnRemoveFromEditorList)return void removeElementFromList(btnRemoveFromEditorList);var btnAddTextItem=dom.parentWithClass(e.target,"btnAddTextItem");btnAddTextItem&&addElementToList(btnAddTextItem)}function getApiClient(){return connectionManager.getApiClient(currentItem.ServerId)}function init(context,apiClient){context.querySelector(".externalIds").addEventListener("click",function(e){var btnOpenExternalId=dom.parentWithClass(e.target,"btnOpenExternalId");if(btnOpenExternalId){var field=context.querySelector("#"+btnOpenExternalId.getAttribute("data-fieldid")),formatString=field.getAttribute("data-formatstring");field.value&&shell.openUrl(formatString.replace("{0}",field.value))}}),context.querySelector(".btnCancel").addEventListener("click",function(){closeDialog(!1)}),context.querySelector(".btnMore").addEventListener("click",function(e){getApiClient().getCurrentUser().then(function(user){showMoreMenu(context,e.target,user)})}),context.querySelector(".btnHeaderSave").addEventListener("click",function(e){context.querySelector(".btnSave").click()}),context.querySelector("#chkLockData").addEventListener("click",function(e){e.target.checked?hideElement(".providerSettingsContainer"):showElement(".providerSettingsContainer")}),context.removeEventListener("click",onEditorClick),context.addEventListener("click",onEditorClick);var form=context.querySelector("form");form.removeEventListener("submit",onSubmit),form.addEventListener("submit",onSubmit),context.querySelector("#btnAddPerson").addEventListener("click",function(event,data){editPerson(context,{},-1)}),context.querySelector("#peopleList").addEventListener("click",function(e){var index,btnDeletePerson=dom.parentWithClass(e.target,"btnDeletePerson");btnDeletePerson&&(index=parseInt(btnDeletePerson.getAttribute("data-index")),currentItem.People.splice(index,1),populatePeople(context,currentItem.People));var btnEditPerson=dom.parentWithClass(e.target,"btnEditPerson");btnEditPerson&&(index=parseInt(btnEditPerson.getAttribute("data-index")),editPerson(context,currentItem.People[index],index))})}function getItem(itemId,serverId){var apiClient=connectionManager.getApiClient(serverId);return itemId?apiClient.getItem(apiClient.getCurrentUserId(),itemId):apiClient.getRootFolder(apiClient.getCurrentUserId())}function getEditorConfig(itemId,serverId){var apiClient=connectionManager.getApiClient(serverId);return itemId?apiClient.getJSON(apiClient.getUrl("Items/"+itemId+"/MetadataEditor")):Promise.resolve({})}function populateCountries(select,allCountries){var html="";html+="";for(var i=0,length=allCountries.length;i"+culture.DisplayName+""}select.innerHTML=html}function populateLanguages(select,languages){var html="";html+="";for(var i=0,length=languages.length;i"+culture.DisplayName+""}select.innerHTML=html}function renderContentTypeOptions(context,metadataInfo){metadataInfo.ContentTypeOptions.length?showElement("#fldContentType",context):hideElement("#fldContentType",context);var html=metadataInfo.ContentTypeOptions.map(function(i){return'"}).join(""),selectEl=context.querySelector("#selectContentType");selectEl.innerHTML=html,selectEl.value=metadataInfo.ContentType||""}function loadExternalIds(context,item,externalIds){for(var html="",providerIds=item.ProviderIds||{},i=0,length=externalIds.length;i',html+='
';var value=providerIds[idInfo.Key]||"";html+='
',html+='',html+="
",formatString&&(html+=''),html+="
",html+="
"}context.querySelector(".externalIds",context).innerHTML=html,externalIds.length?context.querySelector(".externalIdsSection").classList.remove("hide"):context.querySelector(".externalIdsSection").classList.add("hide")}function hideElement(selector,context,multiple){if(context=context||document,"string"==typeof selector){var elements=multiple?context.querySelectorAll(selector):[context.querySelector(selector)];Array.prototype.forEach.call(elements,function(el){el&&el.classList.add("hide")})}else selector.classList.add("hide")}function showElement(selector,context,multiple){if(context=context||document,"string"==typeof selector){var elements=multiple?context.querySelectorAll(selector):[context.querySelector(selector)];Array.prototype.forEach.call(elements,function(el){el&&el.classList.remove("hide")})}else selector.classList.remove("hide")}function setFieldVisibilities(context,item){item.Path&&!1!==item.EnableMediaSourceDisplay?showElement("#fldPath",context):hideElement("#fldPath",context),"Series"===item.Type||"Movie"===item.Type||"Trailer"===item.Type?showElement("#fldOriginalName",context):hideElement("#fldOriginalName",context),"Series"===item.Type?showElement("#fldSeriesRuntime",context):hideElement("#fldSeriesRuntime",context),"Series"===item.Type||"Person"===item.Type?showElement("#fldEndDate",context):hideElement("#fldEndDate",context),"MusicAlbum"===item.Type?showElement("#albumAssociationMessage",context):hideElement("#albumAssociationMessage",context),"Movie"===item.Type||"Trailer"===item.Type?showElement("#fldCriticRating",context):hideElement("#fldCriticRating",context),"Series"===item.Type?(showElement("#fldStatus",context),showElement("#fldAirDays",context),showElement("#fldAirTime",context)):(hideElement("#fldStatus",context),hideElement("#fldAirDays",context),hideElement("#fldAirTime",context)),"Video"===item.MediaType&&"TvChannel"!==item.Type?showElement("#fld3dFormat",context):hideElement("#fld3dFormat",context),"Audio"===item.Type?showElement("#fldAlbumArtist",context):hideElement("#fldAlbumArtist",context),"Audio"===item.Type||"MusicVideo"===item.Type?(showElement("#fldArtist",context),showElement("#fldAlbum",context)):(hideElement("#fldArtist",context),hideElement("#fldAlbum",context)),"Episode"===item.Type&&0===item.ParentIndexNumber?showElement("#collapsibleSpecialEpisodeInfo",context):hideElement("#collapsibleSpecialEpisodeInfo",context),"Person"===item.Type||"Genre"===item.Type||"Studio"===item.Type||"GameGenre"===item.Type||"MusicGenre"===item.Type||"TvChannel"===item.Type||"Book"===item.Type?hideElement("#peopleCollapsible",context):showElement("#peopleCollapsible",context),"Person"===item.Type||"Genre"===item.Type||"Studio"===item.Type||"GameGenre"===item.Type||"MusicGenre"===item.Type||"TvChannel"===item.Type?(hideElement("#fldCommunityRating",context),hideElement("#genresCollapsible",context),hideElement("#studiosCollapsible",context),"TvChannel"===item.Type?showElement("#fldOfficialRating",context):hideElement("#fldOfficialRating",context),hideElement("#fldCustomRating",context)):(showElement("#fldCommunityRating",context),showElement("#genresCollapsible",context),showElement("#studiosCollapsible",context),showElement("#fldOfficialRating",context),showElement("#fldCustomRating",context)),showElement("#tagsCollapsible",context),"TvChannel"===item.Type?(hideElement("#metadataSettingsCollapsible",context),hideElement("#fldPremiereDate",context),hideElement("#fldDateAdded",context),hideElement("#fldYear",context)):(showElement("#metadataSettingsCollapsible",context),showElement("#fldPremiereDate",context),showElement("#fldDateAdded",context),showElement("#fldYear",context)),"TvChannel"===item.Type?hideElement(".overviewContainer",context):showElement(".overviewContainer",context),"Person"===item.Type?(context.querySelector("#txtProductionYear").label(globalize.translate("sharedcomponents#LabelBirthYear")),context.querySelector("#txtPremiereDate").label(globalize.translate("sharedcomponents#LabelBirthDate")),context.querySelector("#txtEndDate").label(globalize.translate("sharedcomponents#LabelDeathDate")),showElement("#fldPlaceOfBirth")):(context.querySelector("#txtProductionYear").label(globalize.translate("sharedcomponents#LabelYear")),context.querySelector("#txtPremiereDate").label(globalize.translate("sharedcomponents#LabelReleaseDate")),context.querySelector("#txtEndDate").label(globalize.translate("sharedcomponents#LabelEndDate")),hideElement("#fldPlaceOfBirth")),"Video"===item.MediaType&&"TvChannel"!==item.Type?showElement("#fldOriginalAspectRatio"):hideElement("#fldOriginalAspectRatio"),"Audio"===item.Type||"Episode"===item.Type||"Season"===item.Type?(showElement("#fldIndexNumber"),"Episode"===item.Type?context.querySelector("#txtIndexNumber").label(globalize.translate("sharedcomponents#LabelEpisodeNumber")):"Season"===item.Type?context.querySelector("#txtIndexNumber").label(globalize.translate("sharedcomponents#LabelSeasonNumber")):"Audio"===item.Type?context.querySelector("#txtIndexNumber").label(globalize.translate("sharedcomponents#LabelTrackNumber")):context.querySelector("#txtIndexNumber").label(globalize.translate("sharedcomponents#LabelNumber"))):hideElement("#fldIndexNumber"),"Audio"===item.Type||"Episode"===item.Type?(showElement("#fldParentIndexNumber"),"Episode"===item.Type?context.querySelector("#txtParentIndexNumber").label(globalize.translate("sharedcomponents#LabelSeasonNumber")):"Audio"===item.Type?context.querySelector("#txtParentIndexNumber").label(globalize.translate("sharedcomponents#LabelDiscNumber")):context.querySelector("#txtParentIndexNumber").label(globalize.translate("sharedcomponents#LabelParentNumber"))):hideElement("#fldParentIndexNumber",context),"BoxSet"===item.Type?(showElement("#fldDisplayOrder",context),hideElement(".seriesDisplayOrderDescription",context),context.querySelector("#selectDisplayOrder").innerHTML='"):"Series"===item.Type?(showElement("#fldDisplayOrder",context),showElement(".seriesDisplayOrderDescription",context),context.querySelector("#selectDisplayOrder").innerHTML=''):(context.querySelector("#selectDisplayOrder").innerHTML="",hideElement("#fldDisplayOrder",context))}function fillItemInfo(context,item,parentalRatingOptions){var select=context.querySelector("#selectOfficialRating");populateRatings(parentalRatingOptions,select,item.OfficialRating),select.value=item.OfficialRating||"",select=context.querySelector("#selectCustomRating"),populateRatings(parentalRatingOptions,select,item.CustomRating),select.value=item.CustomRating||"";var selectStatus=context.querySelector("#selectStatus");populateStatus(selectStatus),selectStatus.value=item.Status||"",context.querySelector("#select3dFormat",context).value=item.Video3DFormat||"",Array.prototype.forEach.call(context.querySelectorAll(".chkAirDay",context),function(el){el.checked=-1!==(item.AirDays||[]).indexOf(el.getAttribute("data-day"))}),populateListView(context.querySelector("#listGenres"),item.Genres),populatePeople(context,item.People||[]),populateListView(context.querySelector("#listStudios"),(item.Studios||[]).map(function(element){return element.Name||""})),populateListView(context.querySelector("#listTags"),item.Tags);var lockData=item.LockData||!1,chkLockData=context.querySelector("#chkLockData");chkLockData.checked=lockData,chkLockData.checked?hideElement(".providerSettingsContainer",context):showElement(".providerSettingsContainer",context),fillMetadataSettings(context,item,item.LockedFields),context.querySelector("#txtPath").value=item.Path||"",context.querySelector("#txtName").value=item.Name||"",context.querySelector("#txtOriginalName").value=item.OriginalTitle||"",context.querySelector("#txtOverview").value=item.Overview||"",context.querySelector("#txtTagline").value=item.Taglines&&item.Taglines.length?item.Taglines[0]:"",context.querySelector("#txtSortName").value=item.ForcedSortName||"",context.querySelector("#txtCommunityRating").value=item.CommunityRating||"",context.querySelector("#txtCriticRating").value=item.CriticRating||"",context.querySelector("#txtIndexNumber").value=null==item.IndexNumber?"":item.IndexNumber,context.querySelector("#txtParentIndexNumber").value=null==item.ParentIndexNumber?"":item.ParentIndexNumber,context.querySelector("#txtAirsBeforeSeason").value="AirsBeforeSeasonNumber"in item?item.AirsBeforeSeasonNumber:"",context.querySelector("#txtAirsAfterSeason").value="AirsAfterSeasonNumber"in item?item.AirsAfterSeasonNumber:"",context.querySelector("#txtAirsBeforeEpisode").value="AirsBeforeEpisodeNumber"in item?item.AirsBeforeEpisodeNumber:"",context.querySelector("#txtAlbum").value=item.Album||"",context.querySelector("#txtAlbumArtist").value=(item.AlbumArtists||[]).map(function(a){return a.Name}).join(";"),item.Type,context.querySelector("#selectDisplayOrder").value=item.DisplayOrder||"",context.querySelector("#txtArtist").value=(item.ArtistItems||[]).map(function(a){return a.Name}).join(";");var date;if(item.DateCreated)try{date=datetime.parseISO8601Date(item.DateCreated,!0),context.querySelector("#txtDateAdded").value=date.toISOString().slice(0,10)}catch(e){context.querySelector("#txtDateAdded").value=""}else context.querySelector("#txtDateAdded").value="";if(item.PremiereDate)try{date=datetime.parseISO8601Date(item.PremiereDate,!0),context.querySelector("#txtPremiereDate").value=date.toISOString().slice(0,10)}catch(e){context.querySelector("#txtPremiereDate").value=""}else context.querySelector("#txtPremiereDate").value="";if(item.EndDate)try{date=datetime.parseISO8601Date(item.EndDate,!0),context.querySelector("#txtEndDate").value=date.toISOString().slice(0,10)}catch(e){context.querySelector("#txtEndDate").value=""}else context.querySelector("#txtEndDate").value="";context.querySelector("#txtProductionYear").value=item.ProductionYear||"",context.querySelector("#txtAirTime").value=item.AirTime||"";var placeofBirth=item.ProductionLocations&&item.ProductionLocations.length?item.ProductionLocations[0]:"";if(context.querySelector("#txtPlaceOfBirth").value=placeofBirth,context.querySelector("#txtOriginalAspectRatio").value=item.AspectRatio||"",context.querySelector("#selectLanguage").value=item.PreferredMetadataLanguage||"",context.querySelector("#selectCountry").value=item.PreferredMetadataCountryCode||"",item.RunTimeTicks){var minutes=item.RunTimeTicks/6e8;context.querySelector("#txtSeriesRuntime").value=Math.round(minutes)}else context.querySelector("#txtSeriesRuntime",context).value=""}function populateRatings(allParentalRatings,select,currentValue){var html="";html+="";var i,length,rating,ratings=[],currentValueFound=!1;for(i=0,length=allParentalRatings.length;i"+rating.Name+"";select.innerHTML=html}function populateStatus(select){var html="";html+="",html+="",html+="",select.innerHTML=html}function populateListView(list,items,sortCallback){items=items||[],void 0===sortCallback?items.sort(function(a,b){return a.toLowerCase().localeCompare(b.toLowerCase())}):items=sortCallback(items);for(var html="",i=0;i',html+='live_tv',html+='
',html+='
',html+=items[i],html+="
",html+="
",html+='',html+="
";list.innerHTML=html}function populatePeople(context,people){for(var html="",elem=context.querySelector("#peopleList"),i=0,length=people.length;i',html+='person',html+='
',html+='",html+="
",html+='',html+="
"}elem.innerHTML=html}function getLockedFieldsHtml(fields,currentFields){for(var html="",i=0;i",html+=""+name+"",html+=""}return html}function fillMetadataSettings(context,item,lockedFields){var container=context.querySelector(".providerSettingsContainer");lockedFields=lockedFields||[];var lockedFieldsList=[{name:globalize.translate("sharedcomponents#Name"),value:"Name"},{name:globalize.translate("sharedcomponents#Overview"),value:"Overview"},{name:globalize.translate("sharedcomponents#Genres"),value:"Genres"},{name:globalize.translate("sharedcomponents#ParentalRating"),value:"OfficialRating"},{name:globalize.translate("sharedcomponents#People"),value:"Cast"}];"Person"===item.Type?lockedFieldsList.push({name:globalize.translate("sharedcomponents#BirthLocation"),value:"ProductionLocations"}):lockedFieldsList.push({name:globalize.translate("sharedcomponents#ProductionLocations"),value:"ProductionLocations"}),"Series"===item.Type&&lockedFieldsList.push({name:globalize.translate("Runtime"),value:"Runtime"}),lockedFieldsList.push({name:globalize.translate("sharedcomponents#Studios"),value:"Studios"}),lockedFieldsList.push({name:globalize.translate("sharedcomponents#Tags"),value:"Tags"});var html="";html+="

"+globalize.translate("sharedcomponents#HeaderEnabledFields")+"

",html+="

"+globalize.translate("sharedcomponents#HeaderEnabledFieldsHelp")+"

",html+=getLockedFieldsHtml(lockedFieldsList,lockedFields),container.innerHTML=html}function reload(context,itemId,serverId){loading.show(),Promise.all([getItem(itemId,serverId),getEditorConfig(itemId,serverId)]).then(function(responses){var item=responses[0];metadataEditorInfo=responses[1],currentItem=item;var languages=metadataEditorInfo.Cultures,countries=metadataEditorInfo.Countries;renderContentTypeOptions(context,metadataEditorInfo),loadExternalIds(context,item,metadataEditorInfo.ExternalIdInfos),populateLanguages(context.querySelector("#selectLanguage"),languages),populateCountries(context.querySelector("#selectCountry"),countries),setFieldVisibilities(context,item),fillItemInfo(context,item,metadataEditorInfo.ParentalRatingOptions),"Video"===item.MediaType&&"Episode"!==item.Type&&"TvChannel"!==item.Type?showElement("#fldTagline",context):hideElement("#fldTagline",context),loading.hide()})}function centerFocus(elem,horiz,on){require(["scrollHelper"],function(scrollHelper){var fn=on?"on":"off";scrollHelper.centerFocus[fn](elem,horiz)})}function show(itemId,serverId,resolve,reject){loading.show(),require(["text!./metadataeditor.template.html"],function(template){var dialogOptions={removeOnClose:!0,scrollY:!1};layoutManager.tv?dialogOptions.size="fullscreen":dialogOptions.size="medium-tall";var dlg=dialogHelper.createDialog(dialogOptions);dlg.classList.add("formDialog");var html="";html+=globalize.translateDocument(template,"sharedcomponents"),dlg.innerHTML=html,layoutManager.tv&¢erFocus(dlg.querySelector(".formDialogContent"),!1,!0),dialogHelper.open(dlg),dlg.addEventListener("close",function(){layoutManager.tv&¢erFocus(dlg.querySelector(".formDialogContent"),!1,!1),resolve()}),currentContext=dlg,init(dlg,connectionManager.getApiClient(serverId)),reload(dlg,itemId,serverId)})}var currentContext,metadataEditorInfo,currentItem;return{show:function(itemId,serverId){return new Promise(function(resolve,reject){return show(itemId,serverId,resolve,reject)})},embed:function(elem,itemId,serverId){return new Promise(function(resolve,reject){loading.show(),require(["text!./metadataeditor.template.html"],function(template){elem.innerHTML=globalize.translateDocument(template,"sharedcomponents"),elem.querySelector(".formDialogFooter").classList.remove("formDialogFooter"),elem.querySelector(".btnHeaderSave").classList.remove("hide"),elem.querySelector(".btnCancel").classList.add("hide"),currentContext=elem,init(elem,connectionManager.getApiClient(serverId)),reload(elem,itemId,serverId),focusManager.autoFocus(elem)})})}}}); \ No newline at end of file +define(["itemHelper", "dom", "layoutManager", "dialogHelper", "datetime", "loading", "focusManager", "connectionManager", "globalize", "require", "shell", "emby-checkbox", "emby-input", "emby-select", "listViewStyle", "emby-textarea", "emby-button", "paper-icon-button-light", "css!./../formdialog", "clearButtonStyle", "flexStyles"], function(itemHelper, dom, layoutManager, dialogHelper, datetime, loading, focusManager, connectionManager, globalize, require, shell) { + "use strict"; + + function isDialog() { + return currentContext.classList.contains("dialog") + } + + function closeDialog(isSubmitted) { + isDialog() && dialogHelper.close(currentContext) + } + + function submitUpdatedItem(form, item) { + function afterContentTypeUpdated() { + require(["toast"], function(toast) { + toast(globalize.translate("sharedcomponents#MessageItemSaved")) + }), loading.hide(), closeDialog(!0) + } + var apiClient = getApiClient(); + apiClient.updateItem(item).then(function() { + var newContentType = form.querySelector("#selectContentType").value || ""; + (metadataEditorInfo.ContentType || "") !== newContentType ? apiClient.ajax({ + url: apiClient.getUrl("Items/" + item.Id + "/ContentType", { + ContentType: newContentType + }), + type: "POST" + }).then(function() { + afterContentTypeUpdated() + }) : afterContentTypeUpdated() + }) + } + + function getSelectedAirDays(form) { + var checkedItems = form.querySelectorAll(".chkAirDay:checked") || []; + return Array.prototype.map.call(checkedItems, function(c) { + return c.getAttribute("data-day") + }) + } + + function getAlbumArtists(form) { + return form.querySelector("#txtAlbumArtist").value.trim().split(";").filter(function(s) { + return s.length > 0 + }).map(function(a) { + return { + Name: a + } + }) + } + + function getArtists(form) { + return form.querySelector("#txtArtist").value.trim().split(";").filter(function(s) { + return s.length > 0 + }).map(function(a) { + return { + Name: a + } + }) + } + + function getDateValue(form, element, property) { + var val = form.querySelector(element).value; + if (!val) return null; + if (currentItem[property]) { + var date = datetime.parseISO8601Date(currentItem[property], !0), + parts = date.toISOString().split("T"); + if (0 === parts[0].indexOf(val)) { + val += "T" + parts[1] + } + } + return val + } + + function onSubmit(e) { + loading.show(); + var form = this, + item = { + Id: currentItem.Id, + Name: form.querySelector("#txtName").value, + OriginalTitle: form.querySelector("#txtOriginalName").value, + ForcedSortName: form.querySelector("#txtSortName").value, + CommunityRating: form.querySelector("#txtCommunityRating").value, + CriticRating: form.querySelector("#txtCriticRating").value, + IndexNumber: form.querySelector("#txtIndexNumber").value || null, + AirsBeforeSeasonNumber: form.querySelector("#txtAirsBeforeSeason").value, + AirsAfterSeasonNumber: form.querySelector("#txtAirsAfterSeason").value, + AirsBeforeEpisodeNumber: form.querySelector("#txtAirsBeforeEpisode").value, + ParentIndexNumber: form.querySelector("#txtParentIndexNumber").value || null, + DisplayOrder: form.querySelector("#selectDisplayOrder").value, + Album: form.querySelector("#txtAlbum").value, + AlbumArtists: getAlbumArtists(form), + ArtistItems: getArtists(form), + Overview: form.querySelector("#txtOverview").value, + Status: form.querySelector("#selectStatus").value, + AirDays: getSelectedAirDays(form), + AirTime: form.querySelector("#txtAirTime").value, + Genres: getListValues(form.querySelector("#listGenres")), + Tags: getListValues(form.querySelector("#listTags")), + Studios: getListValues(form.querySelector("#listStudios")).map(function(element) { + return { + Name: element + } + }), + PremiereDate: getDateValue(form, "#txtPremiereDate", "PremiereDate"), + DateCreated: getDateValue(form, "#txtDateAdded", "DateCreated"), + EndDate: getDateValue(form, "#txtEndDate", "EndDate"), + ProductionYear: form.querySelector("#txtProductionYear").value, + AspectRatio: form.querySelector("#txtOriginalAspectRatio").value, + Video3DFormat: form.querySelector("#select3dFormat").value, + OfficialRating: form.querySelector("#selectOfficialRating").value, + CustomRating: form.querySelector("#selectCustomRating").value, + People: currentItem.People, + LockData: form.querySelector("#chkLockData").checked, + LockedFields: Array.prototype.filter.call(form.querySelectorAll(".selectLockedField"), function(c) { + return !c.checked + }).map(function(c) { + return c.getAttribute("data-value") + }) + }; + item.ProviderIds = Object.assign({}, currentItem.ProviderIds); + var idElements = form.querySelectorAll(".txtExternalId"); + if (Array.prototype.map.call(idElements, function(idElem) { + var providerKey = idElem.getAttribute("data-providerkey"); + item.ProviderIds[providerKey] = idElem.value + }), item.PreferredMetadataLanguage = form.querySelector("#selectLanguage").value, item.PreferredMetadataCountryCode = form.querySelector("#selectCountry").value, "Person" === currentItem.Type) { + var placeOfBirth = form.querySelector("#txtPlaceOfBirth").value; + item.ProductionLocations = placeOfBirth ? [placeOfBirth] : [] + } + if ("Series" === currentItem.Type) { + var seriesRuntime = form.querySelector("#txtSeriesRuntime").value; + item.RunTimeTicks = seriesRuntime ? 6e8 * seriesRuntime : null + } + var tagline = form.querySelector("#txtTagline").value; + return item.Taglines = tagline ? [tagline] : [], submitUpdatedItem(form, item), e.preventDefault(), e.stopPropagation(), !1 + } + + function getListValues(list) { + return Array.prototype.map.call(list.querySelectorAll(".textValue"), function(el) { + return el.textContent + }) + } + + function addElementToList(source, sortCallback) { + require(["prompt"], function(prompt) { + prompt({ + label: "Value:" + }).then(function(text) { + var list = dom.parentWithClass(source, "editableListviewContainer").querySelector(".paperList"), + items = getListValues(list); + items.push(text), populateListView(list, items, sortCallback) + }) + }) + } + + function removeElementFromList(source) { + var el = dom.parentWithClass(source, "listItem"); + el.parentNode.removeChild(el) + } + + function editPerson(context, person, index) { + require(["personEditor"], function(personEditor) { + personEditor.show(person).then(function(updatedPerson) { + -1 === index && currentItem.People.push(updatedPerson), populatePeople(context, currentItem.People) + }) + }) + } + + function showMoreMenu(context, button, user) { + require(["itemContextMenu"], function(itemContextMenu) { + var item = currentItem; + itemContextMenu.show({ + item: item, + positionTo: button, + edit: !1, + editImages: !0, + editSubtitles: !0, + sync: !1, + share: !1, + play: !1, + queue: !1, + user: user + }).then(function(result) { + result.deleted ? afterDeleted(context, item) : result.updated && reload(context, item.Id, item.ServerId) + }) + }) + } + + function afterDeleted(context, item) { + var parentId = item.ParentId || item.SeasonId || item.SeriesId; + parentId ? reload(context, parentId, item.ServerId) : require(["appRouter"], function(appRouter) { + appRouter.goHome() + }) + } + + function onEditorClick(e) { + var btnRemoveFromEditorList = dom.parentWithClass(e.target, "btnRemoveFromEditorList"); + if (btnRemoveFromEditorList) return void removeElementFromList(btnRemoveFromEditorList); + var btnAddTextItem = dom.parentWithClass(e.target, "btnAddTextItem"); + btnAddTextItem && addElementToList(btnAddTextItem) + } + + function getApiClient() { + return connectionManager.getApiClient(currentItem.ServerId) + } + + function init(context, apiClient) { + context.querySelector(".externalIds").addEventListener("click", function(e) { + var btnOpenExternalId = dom.parentWithClass(e.target, "btnOpenExternalId"); + if (btnOpenExternalId) { + var field = context.querySelector("#" + btnOpenExternalId.getAttribute("data-fieldid")), + formatString = field.getAttribute("data-formatstring"); + field.value && shell.openUrl(formatString.replace("{0}", field.value)) + } + }), context.querySelector(".btnCancel").addEventListener("click", function() { + closeDialog(!1) + }), context.querySelector(".btnMore").addEventListener("click", function(e) { + getApiClient().getCurrentUser().then(function(user) { + showMoreMenu(context, e.target, user) + }) + }), context.querySelector(".btnHeaderSave").addEventListener("click", function(e) { + context.querySelector(".btnSave").click() + }), context.querySelector("#chkLockData").addEventListener("click", function(e) { + e.target.checked ? hideElement(".providerSettingsContainer") : showElement(".providerSettingsContainer") + }), context.removeEventListener("click", onEditorClick), context.addEventListener("click", onEditorClick); + var form = context.querySelector("form"); + form.removeEventListener("submit", onSubmit), form.addEventListener("submit", onSubmit), context.querySelector("#btnAddPerson").addEventListener("click", function(event, data) { + editPerson(context, {}, -1) + }), context.querySelector("#peopleList").addEventListener("click", function(e) { + var index, btnDeletePerson = dom.parentWithClass(e.target, "btnDeletePerson"); + btnDeletePerson && (index = parseInt(btnDeletePerson.getAttribute("data-index")), currentItem.People.splice(index, 1), populatePeople(context, currentItem.People)); + var btnEditPerson = dom.parentWithClass(e.target, "btnEditPerson"); + btnEditPerson && (index = parseInt(btnEditPerson.getAttribute("data-index")), editPerson(context, currentItem.People[index], index)) + }) + } + + function getItem(itemId, serverId) { + var apiClient = connectionManager.getApiClient(serverId); + return itemId ? apiClient.getItem(apiClient.getCurrentUserId(), itemId) : apiClient.getRootFolder(apiClient.getCurrentUserId()) + } + + function getEditorConfig(itemId, serverId) { + var apiClient = connectionManager.getApiClient(serverId); + return itemId ? apiClient.getJSON(apiClient.getUrl("Items/" + itemId + "/MetadataEditor")) : Promise.resolve({}) + } + + function populateCountries(select, allCountries) { + var html = ""; + html += ""; + for (var i = 0, length = allCountries.length; i < length; i++) { + var culture = allCountries[i]; + html += "" + } + select.innerHTML = html + } + + function populateLanguages(select, languages) { + var html = ""; + html += ""; + for (var i = 0, length = languages.length; i < length; i++) { + var culture = languages[i]; + html += "" + } + select.innerHTML = html + } + + function renderContentTypeOptions(context, metadataInfo) { + metadataInfo.ContentTypeOptions.length ? showElement("#fldContentType", context) : hideElement("#fldContentType", context); + var html = metadataInfo.ContentTypeOptions.map(function(i) { + return '" + }).join(""), + selectEl = context.querySelector("#selectContentType"); + selectEl.innerHTML = html, selectEl.value = metadataInfo.ContentType || "" + } + + function loadExternalIds(context, item, externalIds) { + for (var html = "", providerIds = item.ProviderIds || {}, i = 0, length = externalIds.length; i < length; i++) { + var idInfo = externalIds[i], + id = "txt1" + idInfo.Key, + formatString = idInfo.UrlFormatString || "", + labelText = globalize.translate("sharedcomponents#LabelDynamicExternalId").replace("{0}", idInfo.Name); + html += '
', html += '
'; + var value = providerIds[idInfo.Key] || ""; + html += '
', html += '', html += "
", formatString && (html += ''), html += "
", html += "
" + } + context.querySelector(".externalIds", context).innerHTML = html, externalIds.length ? context.querySelector(".externalIdsSection").classList.remove("hide") : context.querySelector(".externalIdsSection").classList.add("hide") + } + + function hideElement(selector, context, multiple) { + if (context = context || document, "string" == typeof selector) { + var elements = multiple ? context.querySelectorAll(selector) : [context.querySelector(selector)]; + Array.prototype.forEach.call(elements, function(el) { + el && el.classList.add("hide") + }) + } else selector.classList.add("hide") + } + + function showElement(selector, context, multiple) { + if (context = context || document, "string" == typeof selector) { + var elements = multiple ? context.querySelectorAll(selector) : [context.querySelector(selector)]; + Array.prototype.forEach.call(elements, function(el) { + el && el.classList.remove("hide") + }) + } else selector.classList.remove("hide") + } + + function setFieldVisibilities(context, item) { + item.Path && !1 !== item.EnableMediaSourceDisplay ? showElement("#fldPath", context) : hideElement("#fldPath", context), "Series" === item.Type || "Movie" === item.Type || "Trailer" === item.Type ? showElement("#fldOriginalName", context) : hideElement("#fldOriginalName", context), "Series" === item.Type ? showElement("#fldSeriesRuntime", context) : hideElement("#fldSeriesRuntime", context), "Series" === item.Type || "Person" === item.Type ? showElement("#fldEndDate", context) : hideElement("#fldEndDate", context), "MusicAlbum" === item.Type ? showElement("#albumAssociationMessage", context) : hideElement("#albumAssociationMessage", context), "Movie" === item.Type || "Trailer" === item.Type ? showElement("#fldCriticRating", context) : hideElement("#fldCriticRating", context), "Series" === item.Type ? (showElement("#fldStatus", context), showElement("#fldAirDays", context), showElement("#fldAirTime", context)) : (hideElement("#fldStatus", context), hideElement("#fldAirDays", context), hideElement("#fldAirTime", context)), "Video" === item.MediaType && "TvChannel" !== item.Type ? showElement("#fld3dFormat", context) : hideElement("#fld3dFormat", context), "Audio" === item.Type ? showElement("#fldAlbumArtist", context) : hideElement("#fldAlbumArtist", context), "Audio" === item.Type || "MusicVideo" === item.Type ? (showElement("#fldArtist", context), showElement("#fldAlbum", context)) : (hideElement("#fldArtist", context), hideElement("#fldAlbum", context)), "Episode" === item.Type && 0 === item.ParentIndexNumber ? showElement("#collapsibleSpecialEpisodeInfo", context) : hideElement("#collapsibleSpecialEpisodeInfo", context), "Person" === item.Type || "Genre" === item.Type || "Studio" === item.Type || "GameGenre" === item.Type || "MusicGenre" === item.Type || "TvChannel" === item.Type || "Book" === item.Type ? hideElement("#peopleCollapsible", context) : showElement("#peopleCollapsible", context), "Person" === item.Type || "Genre" === item.Type || "Studio" === item.Type || "GameGenre" === item.Type || "MusicGenre" === item.Type || "TvChannel" === item.Type ? (hideElement("#fldCommunityRating", context), hideElement("#genresCollapsible", context), hideElement("#studiosCollapsible", context), "TvChannel" === item.Type ? showElement("#fldOfficialRating", context) : hideElement("#fldOfficialRating", context), hideElement("#fldCustomRating", context)) : (showElement("#fldCommunityRating", context), showElement("#genresCollapsible", context), showElement("#studiosCollapsible", context), showElement("#fldOfficialRating", context), showElement("#fldCustomRating", context)), showElement("#tagsCollapsible", context), "TvChannel" === item.Type ? (hideElement("#metadataSettingsCollapsible", context), hideElement("#fldPremiereDate", context), hideElement("#fldDateAdded", context), hideElement("#fldYear", context)) : (showElement("#metadataSettingsCollapsible", context), showElement("#fldPremiereDate", context), showElement("#fldDateAdded", context), showElement("#fldYear", context)), "TvChannel" === item.Type ? hideElement(".overviewContainer", context) : showElement(".overviewContainer", context), "Person" === item.Type ? (context.querySelector("#txtProductionYear").label(globalize.translate("sharedcomponents#LabelBirthYear")), context.querySelector("#txtPremiereDate").label(globalize.translate("sharedcomponents#LabelBirthDate")), context.querySelector("#txtEndDate").label(globalize.translate("sharedcomponents#LabelDeathDate")), showElement("#fldPlaceOfBirth")) : (context.querySelector("#txtProductionYear").label(globalize.translate("sharedcomponents#LabelYear")), context.querySelector("#txtPremiereDate").label(globalize.translate("sharedcomponents#LabelReleaseDate")), context.querySelector("#txtEndDate").label(globalize.translate("sharedcomponents#LabelEndDate")), hideElement("#fldPlaceOfBirth")), "Video" === item.MediaType && "TvChannel" !== item.Type ? showElement("#fldOriginalAspectRatio") : hideElement("#fldOriginalAspectRatio"), "Audio" === item.Type || "Episode" === item.Type || "Season" === item.Type ? (showElement("#fldIndexNumber"), "Episode" === item.Type ? context.querySelector("#txtIndexNumber").label(globalize.translate("sharedcomponents#LabelEpisodeNumber")) : "Season" === item.Type ? context.querySelector("#txtIndexNumber").label(globalize.translate("sharedcomponents#LabelSeasonNumber")) : "Audio" === item.Type ? context.querySelector("#txtIndexNumber").label(globalize.translate("sharedcomponents#LabelTrackNumber")) : context.querySelector("#txtIndexNumber").label(globalize.translate("sharedcomponents#LabelNumber"))) : hideElement("#fldIndexNumber"), "Audio" === item.Type || "Episode" === item.Type ? (showElement("#fldParentIndexNumber"), "Episode" === item.Type ? context.querySelector("#txtParentIndexNumber").label(globalize.translate("sharedcomponents#LabelSeasonNumber")) : "Audio" === item.Type ? context.querySelector("#txtParentIndexNumber").label(globalize.translate("sharedcomponents#LabelDiscNumber")) : context.querySelector("#txtParentIndexNumber").label(globalize.translate("sharedcomponents#LabelParentNumber"))) : hideElement("#fldParentIndexNumber", context), "BoxSet" === item.Type ? (showElement("#fldDisplayOrder", context), hideElement(".seriesDisplayOrderDescription", context), context.querySelector("#selectDisplayOrder").innerHTML = '") : "Series" === item.Type ? (showElement("#fldDisplayOrder", context), showElement(".seriesDisplayOrderDescription", context), context.querySelector("#selectDisplayOrder").innerHTML = '') : (context.querySelector("#selectDisplayOrder").innerHTML = "", hideElement("#fldDisplayOrder", context)) + } + + function fillItemInfo(context, item, parentalRatingOptions) { + var select = context.querySelector("#selectOfficialRating"); + populateRatings(parentalRatingOptions, select, item.OfficialRating), select.value = item.OfficialRating || "", select = context.querySelector("#selectCustomRating"), populateRatings(parentalRatingOptions, select, item.CustomRating), select.value = item.CustomRating || ""; + var selectStatus = context.querySelector("#selectStatus"); + populateStatus(selectStatus), selectStatus.value = item.Status || "", context.querySelector("#select3dFormat", context).value = item.Video3DFormat || "", Array.prototype.forEach.call(context.querySelectorAll(".chkAirDay", context), function(el) { + el.checked = -1 !== (item.AirDays || []).indexOf(el.getAttribute("data-day")) + }), populateListView(context.querySelector("#listGenres"), item.Genres), populatePeople(context, item.People || []), populateListView(context.querySelector("#listStudios"), (item.Studios || []).map(function(element) { + return element.Name || "" + })), populateListView(context.querySelector("#listTags"), item.Tags); + var lockData = item.LockData || !1, + chkLockData = context.querySelector("#chkLockData"); + chkLockData.checked = lockData, chkLockData.checked ? hideElement(".providerSettingsContainer", context) : showElement(".providerSettingsContainer", context), fillMetadataSettings(context, item, item.LockedFields), context.querySelector("#txtPath").value = item.Path || "", context.querySelector("#txtName").value = item.Name || "", context.querySelector("#txtOriginalName").value = item.OriginalTitle || "", context.querySelector("#txtOverview").value = item.Overview || "", context.querySelector("#txtTagline").value = item.Taglines && item.Taglines.length ? item.Taglines[0] : "", context.querySelector("#txtSortName").value = item.ForcedSortName || "", context.querySelector("#txtCommunityRating").value = item.CommunityRating || "", context.querySelector("#txtCriticRating").value = item.CriticRating || "", context.querySelector("#txtIndexNumber").value = null == item.IndexNumber ? "" : item.IndexNumber, context.querySelector("#txtParentIndexNumber").value = null == item.ParentIndexNumber ? "" : item.ParentIndexNumber, context.querySelector("#txtAirsBeforeSeason").value = "AirsBeforeSeasonNumber" in item ? item.AirsBeforeSeasonNumber : "", context.querySelector("#txtAirsAfterSeason").value = "AirsAfterSeasonNumber" in item ? item.AirsAfterSeasonNumber : "", context.querySelector("#txtAirsBeforeEpisode").value = "AirsBeforeEpisodeNumber" in item ? item.AirsBeforeEpisodeNumber : "", context.querySelector("#txtAlbum").value = item.Album || "", context.querySelector("#txtAlbumArtist").value = (item.AlbumArtists || []).map(function(a) { + return a.Name + }).join(";"), item.Type, context.querySelector("#selectDisplayOrder").value = item.DisplayOrder || "", context.querySelector("#txtArtist").value = (item.ArtistItems || []).map(function(a) { + return a.Name + }).join(";"); + var date; + if (item.DateCreated) try { + date = datetime.parseISO8601Date(item.DateCreated, !0), context.querySelector("#txtDateAdded").value = date.toISOString().slice(0, 10) + } catch (e) { + context.querySelector("#txtDateAdded").value = "" + } else context.querySelector("#txtDateAdded").value = ""; + if (item.PremiereDate) try { + date = datetime.parseISO8601Date(item.PremiereDate, !0), context.querySelector("#txtPremiereDate").value = date.toISOString().slice(0, 10) + } catch (e) { + context.querySelector("#txtPremiereDate").value = "" + } else context.querySelector("#txtPremiereDate").value = ""; + if (item.EndDate) try { + date = datetime.parseISO8601Date(item.EndDate, !0), context.querySelector("#txtEndDate").value = date.toISOString().slice(0, 10) + } catch (e) { + context.querySelector("#txtEndDate").value = "" + } else context.querySelector("#txtEndDate").value = ""; + context.querySelector("#txtProductionYear").value = item.ProductionYear || "", context.querySelector("#txtAirTime").value = item.AirTime || ""; + var placeofBirth = item.ProductionLocations && item.ProductionLocations.length ? item.ProductionLocations[0] : ""; + if (context.querySelector("#txtPlaceOfBirth").value = placeofBirth, context.querySelector("#txtOriginalAspectRatio").value = item.AspectRatio || "", context.querySelector("#selectLanguage").value = item.PreferredMetadataLanguage || "", context.querySelector("#selectCountry").value = item.PreferredMetadataCountryCode || "", item.RunTimeTicks) { + var minutes = item.RunTimeTicks / 6e8; + context.querySelector("#txtSeriesRuntime").value = Math.round(minutes) + } else context.querySelector("#txtSeriesRuntime", context).value = "" + } + + function populateRatings(allParentalRatings, select, currentValue) { + var html = ""; + html += ""; + var i, length, rating, ratings = [], + currentValueFound = !1; + for (i = 0, length = allParentalRatings.length; i < length; i++) rating = allParentalRatings[i], ratings.push({ + Name: rating.Name, + Value: rating.Name + }), rating.Name === currentValue && (currentValueFound = !0); + for (currentValue && !currentValueFound && ratings.push({ + Name: currentValue, + Value: currentValue + }), i = 0, length = ratings.length; i < length; i++) rating = ratings[i], html += ""; + select.innerHTML = html + } + + function populateStatus(select) { + var html = ""; + html += "", html += "", html += "", select.innerHTML = html + } + + function populateListView(list, items, sortCallback) { + items = items || [], void 0 === sortCallback ? items.sort(function(a, b) { + return a.toLowerCase().localeCompare(b.toLowerCase()) + }) : items = sortCallback(items); + for (var html = "", i = 0; i < items.length; i++) html += '
', html += 'live_tv', html += '
', html += '
', html += items[i], html += "
", html += "
", html += '', html += "
"; + list.innerHTML = html + } + + function populatePeople(context, people) { + for (var html = "", elem = context.querySelector("#peopleList"), i = 0, length = people.length; i < length; i++) { + var person = people[i]; + html += '
', html += 'person', html += '
', html += '", html += "
", html += '', html += "
" + } + elem.innerHTML = html + } + + function getLockedFieldsHtml(fields, currentFields) { + for (var html = "", i = 0; i < fields.length; i++) { + var field = fields[i], + name = field.name, + value = field.value || field.name, + checkedHtml = -1 === currentFields.indexOf(value) ? " checked" : ""; + html += "" + } + return html + } + + function fillMetadataSettings(context, item, lockedFields) { + var container = context.querySelector(".providerSettingsContainer"); + lockedFields = lockedFields || []; + var lockedFieldsList = [{ + name: globalize.translate("sharedcomponents#Name"), + value: "Name" + }, { + name: globalize.translate("sharedcomponents#Overview"), + value: "Overview" + }, { + name: globalize.translate("sharedcomponents#Genres"), + value: "Genres" + }, { + name: globalize.translate("sharedcomponents#ParentalRating"), + value: "OfficialRating" + }, { + name: globalize.translate("sharedcomponents#People"), + value: "Cast" + }]; + "Person" === item.Type ? lockedFieldsList.push({ + name: globalize.translate("sharedcomponents#BirthLocation"), + value: "ProductionLocations" + }) : lockedFieldsList.push({ + name: globalize.translate("sharedcomponents#ProductionLocations"), + value: "ProductionLocations" + }), "Series" === item.Type && lockedFieldsList.push({ + name: globalize.translate("Runtime"), + value: "Runtime" + }), lockedFieldsList.push({ + name: globalize.translate("sharedcomponents#Studios"), + value: "Studios" + }), lockedFieldsList.push({ + name: globalize.translate("sharedcomponents#Tags"), + value: "Tags" + }); + var html = ""; + html += "

" + globalize.translate("sharedcomponents#HeaderEnabledFields") + "

", html += "

" + globalize.translate("sharedcomponents#HeaderEnabledFieldsHelp") + "

", html += getLockedFieldsHtml(lockedFieldsList, lockedFields), container.innerHTML = html + } + + function reload(context, itemId, serverId) { + loading.show(), Promise.all([getItem(itemId, serverId), getEditorConfig(itemId, serverId)]).then(function(responses) { + var item = responses[0]; + metadataEditorInfo = responses[1], currentItem = item; + var languages = metadataEditorInfo.Cultures, + countries = metadataEditorInfo.Countries; + renderContentTypeOptions(context, metadataEditorInfo), loadExternalIds(context, item, metadataEditorInfo.ExternalIdInfos), populateLanguages(context.querySelector("#selectLanguage"), languages), populateCountries(context.querySelector("#selectCountry"), countries), setFieldVisibilities(context, item), fillItemInfo(context, item, metadataEditorInfo.ParentalRatingOptions), "Video" === item.MediaType && "Episode" !== item.Type && "TvChannel" !== item.Type ? showElement("#fldTagline", context) : hideElement("#fldTagline", context), loading.hide() + }) + } + + function centerFocus(elem, horiz, on) { + require(["scrollHelper"], function(scrollHelper) { + var fn = on ? "on" : "off"; + scrollHelper.centerFocus[fn](elem, horiz) + }) + } + + function show(itemId, serverId, resolve, reject) { + loading.show(), require(["text!./metadataeditor.template.html"], function(template) { + var dialogOptions = { + removeOnClose: !0, + scrollY: !1 + }; + layoutManager.tv ? dialogOptions.size = "fullscreen" : dialogOptions.size = "medium-tall"; + var dlg = dialogHelper.createDialog(dialogOptions); + dlg.classList.add("formDialog"); + var html = ""; + html += globalize.translateDocument(template, "sharedcomponents"), dlg.innerHTML = html, layoutManager.tv && centerFocus(dlg.querySelector(".formDialogContent"), !1, !0), dialogHelper.open(dlg), dlg.addEventListener("close", function() { + layoutManager.tv && centerFocus(dlg.querySelector(".formDialogContent"), !1, !1), resolve() + }), currentContext = dlg, init(dlg, connectionManager.getApiClient(serverId)), reload(dlg, itemId, serverId) + }) + } + var currentContext, metadataEditorInfo, currentItem; + return { + show: function(itemId, serverId) { + return new Promise(function(resolve, reject) { + return show(itemId, serverId, resolve, reject) + }) + }, + embed: function(elem, itemId, serverId) { + return new Promise(function(resolve, reject) { + loading.show(), require(["text!./metadataeditor.template.html"], function(template) { + elem.innerHTML = globalize.translateDocument(template, "sharedcomponents"), elem.querySelector(".formDialogFooter").classList.remove("formDialogFooter"), elem.querySelector(".btnHeaderSave").classList.remove("hide"), elem.querySelector(".btnCancel").classList.add("hide"), currentContext = elem, init(elem, connectionManager.getApiClient(serverId)), reload(elem, itemId, serverId), focusManager.autoFocus(elem) + }) + }) + } + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/metadataeditor/personeditor.js b/dashboard-ui/bower_components/emby-webcomponents/metadataeditor/personeditor.js index a08ed639eb..4bca9a2adc 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/metadataeditor/personeditor.js +++ b/dashboard-ui/bower_components/emby-webcomponents/metadataeditor/personeditor.js @@ -1 +1,40 @@ -define(["dialogHelper","layoutManager","globalize","require","paper-icon-button-light","emby-input","emby-select","css!./../formdialog"],function(dialogHelper,layoutManager,globalize,require){"use strict";function centerFocus(elem,horiz,on){require(["scrollHelper"],function(scrollHelper){var fn=on?"on":"off";scrollHelper.centerFocus[fn](elem,horiz)})}function show(person){return new Promise(function(resolve,reject){require(["text!./personeditor.template.html"],function(template){var dialogOptions={removeOnClose:!0,scrollY:!1};layoutManager.tv?dialogOptions.size="fullscreen":dialogOptions.size="medium-tall";var dlg=dialogHelper.createDialog(dialogOptions);dlg.classList.add("formDialog");var html="",submitted=!1;html+=globalize.translateDocument(template,"sharedcomponents"),dlg.innerHTML=html,dlg.querySelector(".txtPersonName",dlg).value=person.Name||"",dlg.querySelector(".selectPersonType",dlg).value=person.Type||"",dlg.querySelector(".txtPersonRole",dlg).value=person.Role||"",layoutManager.tv&¢erFocus(dlg.querySelector(".formDialogContent"),!1,!0),dialogHelper.open(dlg),dlg.addEventListener("close",function(){layoutManager.tv&¢erFocus(dlg.querySelector(".formDialogContent"),!1,!1),submitted?resolve(person):reject()}),dlg.querySelector(".selectPersonType").addEventListener("change",function(e){"Actor"===this.value?dlg.querySelector(".fldRole").classList.remove("hide"):dlg.querySelector(".fldRole").classList.add("hide")}),dlg.querySelector(".btnCancel").addEventListener("click",function(e){dialogHelper.close(dlg)}),dlg.querySelector("form").addEventListener("submit",function(e){return submitted=!0,person.Name=dlg.querySelector(".txtPersonName",dlg).value,person.Type=dlg.querySelector(".selectPersonType",dlg).value,person.Role=dlg.querySelector(".txtPersonRole",dlg).value||null,dialogHelper.close(dlg),e.preventDefault(),!1}),dlg.querySelector(".selectPersonType").dispatchEvent(new CustomEvent("change",{bubbles:!0}))})})}return{show:show}}); \ No newline at end of file +define(["dialogHelper", "layoutManager", "globalize", "require", "paper-icon-button-light", "emby-input", "emby-select", "css!./../formdialog"], function(dialogHelper, layoutManager, globalize, require) { + "use strict"; + + function centerFocus(elem, horiz, on) { + require(["scrollHelper"], function(scrollHelper) { + var fn = on ? "on" : "off"; + scrollHelper.centerFocus[fn](elem, horiz) + }) + } + + function show(person) { + return new Promise(function(resolve, reject) { + require(["text!./personeditor.template.html"], function(template) { + var dialogOptions = { + removeOnClose: !0, + scrollY: !1 + }; + layoutManager.tv ? dialogOptions.size = "fullscreen" : dialogOptions.size = "medium-tall"; + var dlg = dialogHelper.createDialog(dialogOptions); + dlg.classList.add("formDialog"); + var html = "", + submitted = !1; + html += globalize.translateDocument(template, "sharedcomponents"), dlg.innerHTML = html, dlg.querySelector(".txtPersonName", dlg).value = person.Name || "", dlg.querySelector(".selectPersonType", dlg).value = person.Type || "", dlg.querySelector(".txtPersonRole", dlg).value = person.Role || "", layoutManager.tv && centerFocus(dlg.querySelector(".formDialogContent"), !1, !0), dialogHelper.open(dlg), dlg.addEventListener("close", function() { + layoutManager.tv && centerFocus(dlg.querySelector(".formDialogContent"), !1, !1), submitted ? resolve(person) : reject() + }), dlg.querySelector(".selectPersonType").addEventListener("change", function(e) { + "Actor" === this.value ? dlg.querySelector(".fldRole").classList.remove("hide") : dlg.querySelector(".fldRole").classList.add("hide") + }), dlg.querySelector(".btnCancel").addEventListener("click", function(e) { + dialogHelper.close(dlg) + }), dlg.querySelector("form").addEventListener("submit", function(e) { + return submitted = !0, person.Name = dlg.querySelector(".txtPersonName", dlg).value, person.Type = dlg.querySelector(".selectPersonType", dlg).value, person.Role = dlg.querySelector(".txtPersonRole", dlg).value || null, dialogHelper.close(dlg), e.preventDefault(), !1 + }), dlg.querySelector(".selectPersonType").dispatchEvent(new CustomEvent("change", { + bubbles: !0 + })) + }) + }) + } + return { + show: show + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/multidownload.js b/dashboard-ui/bower_components/emby-webcomponents/multidownload.js index f47128cdd2..c7554877ea 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/multidownload.js +++ b/dashboard-ui/bower_components/emby-webcomponents/multidownload.js @@ -1 +1,35 @@ -define(["browser"],function(browser){"use strict";function fallback(urls){var i=0;!function createIframe(){var frame=document.createElement("iframe");frame.style.display="none",frame.src=urls[i++],document.documentElement.appendChild(frame);var interval=setInterval(function(){"complete"!==frame.contentWindow.document.readyState&&"interactive"!==frame.contentWindow.document.readyState||(clearInterval(interval),setTimeout(function(){frame.parentNode.removeChild(frame)},1e3),i";itemSelectionPanel.querySelector(".chkItemSelect").addEventListener("change",onSelectionChange)}}function showSelectionCommands(){var selectionCommandsPanel=currentSelectionCommandsPanel;if(!selectionCommandsPanel){selectionCommandsPanel=document.createElement("div"),selectionCommandsPanel.classList.add("selectionCommandsPanel"),document.body.appendChild(selectionCommandsPanel),currentSelectionCommandsPanel=selectionCommandsPanel;var html="";html+='',html+='

';html+='',selectionCommandsPanel.innerHTML=html,selectionCommandsPanel.querySelector(".btnCloseSelectionPanel").addEventListener("click",hideSelections);var btnSelectionPanelOptions=selectionCommandsPanel.querySelector(".btnSelectionPanelOptions");dom.addEventListener(btnSelectionPanelOptions,"click",showMenuForSelectedItems,{passive:!0})}}function alertText(options){return new Promise(function(resolve,reject){require(["alert"],function(alert){alert(options).then(resolve,resolve)})})}function deleteItems(apiClient,itemIds){return new Promise(function(resolve,reject){var msg=globalize.translate("sharedcomponents#ConfirmDeleteItem"),title=globalize.translate("sharedcomponents#HeaderDeleteItem");itemIds.length>1&&(msg=globalize.translate("sharedcomponents#ConfirmDeleteItems"),title=globalize.translate("sharedcomponents#HeaderDeleteItems")),require(["confirm"],function(confirm){confirm(msg,title).then(function(){var promises=itemIds.map(function(itemId){apiClient.deleteItem(itemId)});Promise.all(promises).then(resolve,function(){alertText(globalize.translate("sharedcomponents#ErrorDeletingItem")).then(reject,reject)})},reject)})})}function showMenuForSelectedItems(e){var apiClient=connectionManager.currentApiClient();apiClient.getCurrentUser().then(function(user){var menuItems=[];menuItems.push({name:globalize.translate("sharedcomponents#AddToCollection"),id:"addtocollection",ironIcon:"add"}),menuItems.push({name:globalize.translate("sharedcomponents#AddToPlaylist"),id:"playlist",ironIcon:"playlist-add"}),user.Policy.EnableContentDeletion&&menuItems.push({name:globalize.translate("sharedcomponents#Delete"),id:"delete",ironIcon:"delete"}),user.Policy.EnableContentDownloading&&appHost.supports("filedownload"),user.Policy.EnableContentDownloading&&appHost.supports("sync")&&menuItems.push({name:globalize.translate("sharedcomponents#Download"),id:"synclocal"}),menuItems.push({name:globalize.translate("sharedcomponents#GroupVersions"),id:"groupvideos",ironIcon:"call-merge"}),menuItems.push({name:globalize.translate("sharedcomponents#MarkPlayed"),id:"markplayed"}),menuItems.push({name:globalize.translate("sharedcomponents#MarkUnplayed"),id:"markunplayed"}),menuItems.push({name:globalize.translate("sharedcomponents#RefreshMetadata"),id:"refresh"}),user.Policy.EnableContentDownloading&&menuItems.push({name:globalize.translate("sharedcomponents#Sync"),id:"sync"}),require(["actionsheet"],function(actionsheet){actionsheet.show({items:menuItems,positionTo:e.target,callback:function(id){var items=selectedItems.slice(0),serverId=apiClient.serverInfo().Id;switch(id){case"addtocollection":require(["collectionEditor"],function(collectionEditor){(new collectionEditor).show({items:items,serverId:serverId})}),hideSelections(),dispatchNeedsRefresh();break;case"playlist":require(["playlistEditor"],function(playlistEditor){(new playlistEditor).show({items:items,serverId:serverId})}),hideSelections(),dispatchNeedsRefresh();break;case"delete":deleteItems(apiClient,items).then(dispatchNeedsRefresh),hideSelections(),dispatchNeedsRefresh();break;case"groupvideos":combineVersions(apiClient,items);break;case"markplayed":items.forEach(function(itemId){apiClient.markPlayed(apiClient.getCurrentUserId(),itemId)}),hideSelections(),dispatchNeedsRefresh();break;case"markunplayed":items.forEach(function(itemId){apiClient.markUnplayed(apiClient.getCurrentUserId(),itemId)}),hideSelections(),dispatchNeedsRefresh();break;case"refresh":require(["refreshDialog"],function(refreshDialog){new refreshDialog({itemIds:items,serverId:serverId}).show()}),hideSelections(),dispatchNeedsRefresh();break;case"sync":require(["syncDialog"],function(syncDialog){syncDialog.showMenu({items:items.map(function(i){return{Id:i}}),serverId:serverId})}),hideSelections(),dispatchNeedsRefresh();break;case"synclocal":require(["syncDialog"],function(syncDialog){syncDialog.showMenu({items:items.map(function(i){return{Id:i}}),isLocalSync:!0,serverId:serverId})}),hideSelections(),dispatchNeedsRefresh()}}})})})}function dispatchNeedsRefresh(){var elems=[];[].forEach.call(selectedElements,function(i){var container=dom.parentWithAttribute(i,"is","emby-itemscontainer");container&&-1===elems.indexOf(container)&&elems.push(container)});for(var i=0,length=elems.length;i=5||deltaY>=5)&&onMouseOut(e)}}function onTouchEnd(e){onMouseOut(e)}function onMouseDown(e){touchStartTimeout&&(clearTimeout(touchStartTimeout),touchStartTimeout=null),touchTarget=e.target,touchStartTimeout=setTimeout(onTouchStartTimerFired,550)}function onMouseOut(e){touchStartTimeout&&(clearTimeout(touchStartTimeout),touchStartTimeout=null),touchTarget=null}function onTouchStartTimerFired(){if(touchTarget){var card=dom.parentWithClass(touchTarget,"card");touchTarget=null,card&&showSelections(card)}}var touchTarget,touchStartTimeout,touchStartX,touchStartY,self=this,container=options.container;!function(element){browser.touch&&!browser.safari?element.addEventListener("contextmenu",onTapHold):(dom.addEventListener(element,"touchstart",onTouchStart,{passive:!0}),dom.addEventListener(element,"touchmove",onTouchMove,{passive:!0}),dom.addEventListener(element,"touchend",onTouchEnd,{passive:!0}),dom.addEventListener(element,"touchcancel",onTouchEnd,{passive:!0}),dom.addEventListener(element,"mousedown",onMouseDown,{passive:!0}),dom.addEventListener(element,"mouseleave",onMouseOut,{passive:!0}),dom.addEventListener(element,"mouseup",onMouseOut,{passive:!0}))}(container),!1!==options.bindOnClick&&container.addEventListener("click",onContainerClick),self.onContainerClick=onContainerClick,self.destroy=function(){container.removeEventListener("click",onContainerClick),container.removeEventListener("contextmenu",onTapHold);var element=container;dom.removeEventListener(element,"touchstart",onTouchStart,{passive:!0}),dom.removeEventListener(element,"touchmove",onTouchMove,{passive:!0}),dom.removeEventListener(element,"touchend",onTouchEnd,{passive:!0}),dom.removeEventListener(element,"mousedown",onMouseDown,{passive:!0}),dom.removeEventListener(element,"mouseleave",onMouseOut,{passive:!0}),dom.removeEventListener(element,"mouseup",onMouseOut,{passive:!0})}}}); \ No newline at end of file +define(["browser", "appStorage", "apphost", "loading", "connectionManager", "globalize", "appRouter", "dom", "css!./multiselect"], function(browser, appStorage, appHost, loading, connectionManager, globalize, appRouter, dom) { + "use strict"; + + function hideSelections() { + var selectionCommandsPanel = currentSelectionCommandsPanel; + if (selectionCommandsPanel) { + selectionCommandsPanel.parentNode.removeChild(selectionCommandsPanel), currentSelectionCommandsPanel = null, selectedItems = [], selectedElements = []; + for (var elems = document.querySelectorAll(".itemSelectionPanel"), i = 0, length = elems.length; i < length; i++) { + var parent = elems[i].parentNode; + parent.removeChild(elems[i]), parent.classList.remove("withMultiSelect") + } + } + } + + function onItemSelectionPanelClick(e, itemSelectionPanel) { + if (!dom.parentWithClass(e.target, "chkItemSelect")) { + var chkItemSelect = itemSelectionPanel.querySelector(".chkItemSelect"); + if (chkItemSelect) + if (chkItemSelect.classList.contains("checkedInitial")) chkItemSelect.classList.remove("checkedInitial"); + else { + var newValue = !chkItemSelect.checked; + chkItemSelect.checked = newValue, updateItemSelection(chkItemSelect, newValue) + } + } + return e.preventDefault(), e.stopPropagation(), !1 + } + + function updateItemSelection(chkItemSelect, selected) { + var id = dom.parentWithAttribute(chkItemSelect, "data-id").getAttribute("data-id"); + if (selected) { + selectedItems.filter(function(i) { + return i === id + }).length || (selectedItems.push(id), selectedElements.push(chkItemSelect)) + } else selectedItems = selectedItems.filter(function(i) { + return i !== id + }), selectedElements = selectedElements.filter(function(i) { + return i !== chkItemSelect + }); + if (selectedItems.length) { + var itemSelectionCount = document.querySelector(".itemSelectionCount"); + itemSelectionCount && (itemSelectionCount.innerHTML = selectedItems.length) + } else hideSelections() + } + + function onSelectionChange(e) { + updateItemSelection(this, this.checked) + } + + function showSelection(item, isChecked) { + var itemSelectionPanel = item.querySelector(".itemSelectionPanel"); + if (!itemSelectionPanel) { + itemSelectionPanel = document.createElement("div"), itemSelectionPanel.classList.add("itemSelectionPanel"); + var parent = item.querySelector(".cardBox") || item.querySelector(".cardContent"); + parent.classList.add("withMultiSelect"), parent.appendChild(itemSelectionPanel); + var cssClass = "chkItemSelect"; + isChecked && !browser.firefox && (cssClass += " checkedInitial"); + var checkedAttribute = isChecked ? " checked" : ""; + itemSelectionPanel.innerHTML = '"; + itemSelectionPanel.querySelector(".chkItemSelect").addEventListener("change", onSelectionChange) + } + } + + function showSelectionCommands() { + var selectionCommandsPanel = currentSelectionCommandsPanel; + if (!selectionCommandsPanel) { + selectionCommandsPanel = document.createElement("div"), selectionCommandsPanel.classList.add("selectionCommandsPanel"), document.body.appendChild(selectionCommandsPanel), currentSelectionCommandsPanel = selectionCommandsPanel; + var html = ""; + html += '', html += '

'; + html += '', selectionCommandsPanel.innerHTML = html, selectionCommandsPanel.querySelector(".btnCloseSelectionPanel").addEventListener("click", hideSelections); + var btnSelectionPanelOptions = selectionCommandsPanel.querySelector(".btnSelectionPanelOptions"); + dom.addEventListener(btnSelectionPanelOptions, "click", showMenuForSelectedItems, { + passive: !0 + }) + } + } + + function alertText(options) { + return new Promise(function(resolve, reject) { + require(["alert"], function(alert) { + alert(options).then(resolve, resolve) + }) + }) + } + + function deleteItems(apiClient, itemIds) { + return new Promise(function(resolve, reject) { + var msg = globalize.translate("sharedcomponents#ConfirmDeleteItem"), + title = globalize.translate("sharedcomponents#HeaderDeleteItem"); + itemIds.length > 1 && (msg = globalize.translate("sharedcomponents#ConfirmDeleteItems"), title = globalize.translate("sharedcomponents#HeaderDeleteItems")), require(["confirm"], function(confirm) { + confirm(msg, title).then(function() { + var promises = itemIds.map(function(itemId) { + apiClient.deleteItem(itemId) + }); + Promise.all(promises).then(resolve, function() { + alertText(globalize.translate("sharedcomponents#ErrorDeletingItem")).then(reject, reject) + }) + }, reject) + }) + }) + } + + function showMenuForSelectedItems(e) { + var apiClient = connectionManager.currentApiClient(); + apiClient.getCurrentUser().then(function(user) { + var menuItems = []; + menuItems.push({ + name: globalize.translate("sharedcomponents#AddToCollection"), + id: "addtocollection", + ironIcon: "add" + }), menuItems.push({ + name: globalize.translate("sharedcomponents#AddToPlaylist"), + id: "playlist", + ironIcon: "playlist-add" + }), user.Policy.EnableContentDeletion && menuItems.push({ + name: globalize.translate("sharedcomponents#Delete"), + id: "delete", + ironIcon: "delete" + }), user.Policy.EnableContentDownloading && appHost.supports("filedownload"), user.Policy.EnableContentDownloading && appHost.supports("sync") && menuItems.push({ + name: globalize.translate("sharedcomponents#Download"), + id: "synclocal" + }), menuItems.push({ + name: globalize.translate("sharedcomponents#GroupVersions"), + id: "groupvideos", + ironIcon: "call-merge" + }), menuItems.push({ + name: globalize.translate("sharedcomponents#MarkPlayed"), + id: "markplayed" + }), menuItems.push({ + name: globalize.translate("sharedcomponents#MarkUnplayed"), + id: "markunplayed" + }), menuItems.push({ + name: globalize.translate("sharedcomponents#RefreshMetadata"), + id: "refresh" + }), user.Policy.EnableContentDownloading && menuItems.push({ + name: globalize.translate("sharedcomponents#Sync"), + id: "sync" + }), require(["actionsheet"], function(actionsheet) { + actionsheet.show({ + items: menuItems, + positionTo: e.target, + callback: function(id) { + var items = selectedItems.slice(0), + serverId = apiClient.serverInfo().Id; + switch (id) { + case "addtocollection": + require(["collectionEditor"], function(collectionEditor) { + (new collectionEditor).show({ + items: items, + serverId: serverId + }) + }), hideSelections(), dispatchNeedsRefresh(); + break; + case "playlist": + require(["playlistEditor"], function(playlistEditor) { + (new playlistEditor).show({ + items: items, + serverId: serverId + }) + }), hideSelections(), dispatchNeedsRefresh(); + break; + case "delete": + deleteItems(apiClient, items).then(dispatchNeedsRefresh), hideSelections(), dispatchNeedsRefresh(); + break; + case "groupvideos": + combineVersions(apiClient, items); + break; + case "markplayed": + items.forEach(function(itemId) { + apiClient.markPlayed(apiClient.getCurrentUserId(), itemId) + }), hideSelections(), dispatchNeedsRefresh(); + break; + case "markunplayed": + items.forEach(function(itemId) { + apiClient.markUnplayed(apiClient.getCurrentUserId(), itemId) + }), hideSelections(), dispatchNeedsRefresh(); + break; + case "refresh": + require(["refreshDialog"], function(refreshDialog) { + new refreshDialog({ + itemIds: items, + serverId: serverId + }).show() + }), hideSelections(), dispatchNeedsRefresh(); + break; + case "sync": + require(["syncDialog"], function(syncDialog) { + syncDialog.showMenu({ + items: items.map(function(i) { + return { + Id: i + } + }), + serverId: serverId + }) + }), hideSelections(), dispatchNeedsRefresh(); + break; + case "synclocal": + require(["syncDialog"], function(syncDialog) { + syncDialog.showMenu({ + items: items.map(function(i) { + return { + Id: i + } + }), + isLocalSync: !0, + serverId: serverId + }) + }), hideSelections(), dispatchNeedsRefresh() + } + } + }) + }) + }) + } + + function dispatchNeedsRefresh() { + var elems = []; + [].forEach.call(selectedElements, function(i) { + var container = dom.parentWithAttribute(i, "is", "emby-itemscontainer"); + container && -1 === elems.indexOf(container) && elems.push(container) + }); + for (var i = 0, length = elems.length; i < length; i++) elems[i].notifyRefreshNeeded(!0) + } + + function combineVersions(apiClient, selection) { + if (selection.length < 2) return void require(["alert"], function(alert) { + alert({ + text: globalize.translate("sharedcomponents#PleaseSelectTwoItems") + }) + }); + loading.show(), apiClient.ajax({ + type: "POST", + url: apiClient.getUrl("Videos/MergeVersions", { + Ids: selection.join(",") + }) + }).then(function() { + loading.hide(), hideSelections(), dispatchNeedsRefresh() + }) + } + + function showSelections(initialCard) { + require(["emby-checkbox"], function() { + for (var cards = document.querySelectorAll(".card"), i = 0, length = cards.length; i < length; i++) showSelection(cards[i], initialCard === cards[i]); + showSelectionCommands(), updateItemSelection(initialCard, !0) + }) + } + + function onContainerClick(e) { + var target = e.target; + if (selectedItems.length) { + var card = dom.parentWithClass(target, "card"); + if (card) { + var itemSelectionPanel = card.querySelector(".itemSelectionPanel"); + if (itemSelectionPanel) return onItemSelectionPanelClick(e, itemSelectionPanel) + } + return e.preventDefault(), e.stopPropagation(), !1 + } + } + var currentSelectionCommandsPanel, selectedItems = [], + selectedElements = []; + return document.addEventListener("viewbeforehide", hideSelections), + function(options) { + function onTapHold(e) { + var card = dom.parentWithClass(e.target, "card"); + return card && showSelections(card), e.preventDefault(), e.stopPropagation && e.stopPropagation(), !1 + } + + function getTouches(e) { + return e.changedTouches || e.targetTouches || e.touches + } + + function onTouchStart(e) { + var touch = getTouches(e)[0]; + if (touchTarget = null, touchStartX = 0, touchStartY = 0, touch) { + touchStartX = touch.clientX, touchStartY = touch.clientY; + var element = touch.target; + if (element) { + var card = dom.parentWithClass(element, "card"); + card && (touchStartTimeout && (clearTimeout(touchStartTimeout), touchStartTimeout = null), touchTarget = card, touchStartTimeout = setTimeout(onTouchStartTimerFired, 550)) + } + } + } + + function onTouchMove(e) { + if (touchTarget) { + var deltaX, deltaY, touch = getTouches(e)[0]; + if (touch) { + var touchEndX = touch.clientX || 0, + touchEndY = touch.clientY || 0; + deltaX = Math.abs(touchEndX - (touchStartX || 0)), deltaY = Math.abs(touchEndY - (touchStartY || 0)) + } else deltaX = 100, deltaY = 100; + (deltaX >= 5 || deltaY >= 5) && onMouseOut(e) + } + } + + function onTouchEnd(e) { + onMouseOut(e) + } + + function onMouseDown(e) { + touchStartTimeout && (clearTimeout(touchStartTimeout), touchStartTimeout = null), touchTarget = e.target, touchStartTimeout = setTimeout(onTouchStartTimerFired, 550) + } + + function onMouseOut(e) { + touchStartTimeout && (clearTimeout(touchStartTimeout), touchStartTimeout = null), touchTarget = null + } + + function onTouchStartTimerFired() { + if (touchTarget) { + var card = dom.parentWithClass(touchTarget, "card"); + touchTarget = null, card && showSelections(card) + } + } + var touchTarget, touchStartTimeout, touchStartX, touchStartY, self = this, + container = options.container; + ! function(element) { + browser.touch && !browser.safari ? element.addEventListener("contextmenu", onTapHold) : (dom.addEventListener(element, "touchstart", onTouchStart, { + passive: !0 + }), dom.addEventListener(element, "touchmove", onTouchMove, { + passive: !0 + }), dom.addEventListener(element, "touchend", onTouchEnd, { + passive: !0 + }), dom.addEventListener(element, "touchcancel", onTouchEnd, { + passive: !0 + }), dom.addEventListener(element, "mousedown", onMouseDown, { + passive: !0 + }), dom.addEventListener(element, "mouseleave", onMouseOut, { + passive: !0 + }), dom.addEventListener(element, "mouseup", onMouseOut, { + passive: !0 + })) + }(container), !1 !== options.bindOnClick && container.addEventListener("click", onContainerClick), self.onContainerClick = onContainerClick, self.destroy = function() { + container.removeEventListener("click", onContainerClick), container.removeEventListener("contextmenu", onTapHold); + var element = container; + dom.removeEventListener(element, "touchstart", onTouchStart, { + passive: !0 + }), dom.removeEventListener(element, "touchmove", onTouchMove, { + passive: !0 + }), dom.removeEventListener(element, "touchend", onTouchEnd, { + passive: !0 + }), dom.removeEventListener(element, "mousedown", onMouseDown, { + passive: !0 + }), dom.removeEventListener(element, "mouseleave", onMouseOut, { + passive: !0 + }), dom.removeEventListener(element, "mouseup", onMouseOut, { + passive: !0 + }) + } + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/native-promise-only/lib/npo.src.js b/dashboard-ui/bower_components/emby-webcomponents/native-promise-only/lib/npo.src.js index a0c48d0ece..888d602450 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/native-promise-only/lib/npo.src.js +++ b/dashboard-ui/bower_components/emby-webcomponents/native-promise-only/lib/npo.src.js @@ -1 +1,166 @@ -!function(name,context,definition){context[name]=definition(),"undefined"!=typeof module&&module.exports?module.exports=context[name]:"function"==typeof define&&define.amd&&define(function(){return context[name]})}("Promise","undefined"!=typeof global?global:this,function(){"use strict";function schedule(fn,self){scheduling_queue.add(fn,self),cycle||(cycle=timer(scheduling_queue.drain))}function isThenable(o){var _then,o_type=typeof o;return null==o||"object"!=o_type&&"function"!=o_type||(_then=o.then),"function"==typeof _then&&_then}function notify(){for(var i=0;i0&&schedule(notify,self))}catch(err){reject.call(new MakeDefWrapper(self),err)}}}function reject(msg){var self=this;self.triggered||(self.triggered=!0,self.def&&(self=self.def),self.msg=msg,self.state=2,self.chain.length>0&&schedule(notify,self))}function iteratePromises(Constructor,arr,resolver,rejecter){for(var idx=0;idx 0 && schedule(notify, self)) + } catch (err) { + reject.call(new MakeDefWrapper(self), err) + } + } + } + + function reject(msg) { + var self = this; + self.triggered || (self.triggered = !0, self.def && (self = self.def), self.msg = msg, self.state = 2, self.chain.length > 0 && schedule(notify, self)) + } + + function iteratePromises(Constructor, arr, resolver, rejecter) { + for (var idx = 0; idx < arr.length; idx++) ! function(idx) { + Constructor.resolve(arr[idx]).then(function(msg) { + resolver(idx, msg) + }, rejecter) + }(idx) + } + + function MakeDefWrapper(self) { + this.def = self, this.triggered = !1 + } + + function MakeDef(self) { + this.promise = self, this.state = 0, this.triggered = !1, this.chain = [], this.msg = void 0 + } + + function Promise(executor) { + if ("function" != typeof executor) throw TypeError("Not a function"); + if (0 !== this.__NPO__) throw TypeError("Not a promise"); + this.__NPO__ = 1; + var def = new MakeDef(this); + this.then = function(success, failure) { + var o = { + success: "function" != typeof success || success, + failure: "function" == typeof failure && failure + }; + return o.promise = new this.constructor(function(resolve, reject) { + if ("function" != typeof resolve || "function" != typeof reject) throw TypeError("Not a function"); + o.resolve = resolve, o.reject = reject + }), def.chain.push(o), 0 !== def.state && schedule(notify, def), o.promise + }, this.catch = function(failure) { + return this.then(void 0, failure) + }; + try { + executor.call(void 0, function(msg) { + resolve.call(def, msg) + }, function(msg) { + reject.call(def, msg) + }) + } catch (err) { + reject.call(def, err) + } + } + var builtInProp, cycle, scheduling_queue, ToString = Object.prototype.toString, + timer = "undefined" != typeof setImmediate ? function(fn) { + return setImmediate(fn) + } : setTimeout; + try { + Object.defineProperty({}, "x", {}), builtInProp = function(obj, name, val, config) { + return Object.defineProperty(obj, name, { + value: val, + writable: !0, + configurable: !1 !== config + }) + } + } catch (err) { + builtInProp = function(obj, name, val) { + return obj[name] = val, obj + } + } + scheduling_queue = function() { + function Item(fn, self) { + this.fn = fn, this.self = self, this.next = void 0 + } + var first, last, item; + return { + add: function(fn, self) { + item = new Item(fn, self), last ? last.next = item : first = item, last = item, item = void 0 + }, + drain: function() { + var f = first; + for (first = last = cycle = void 0; f;) f.fn.call(f.self), f = f.next + } + } + }(); + var PromisePrototype = builtInProp({}, "constructor", Promise, !1); + return Promise.prototype = PromisePrototype, builtInProp(PromisePrototype, "__NPO__", 0, !1), builtInProp(Promise, "resolve", function(msg) { + var Constructor = this; + return msg && "object" == typeof msg && 1 === msg.__NPO__ ? msg : new Constructor(function(resolve, reject) { + if ("function" != typeof resolve || "function" != typeof reject) throw TypeError("Not a function"); + resolve(msg) + }) + }), builtInProp(Promise, "reject", function(msg) { + return new this(function(resolve, reject) { + if ("function" != typeof resolve || "function" != typeof reject) throw TypeError("Not a function"); + reject(msg) + }) + }), builtInProp(Promise, "all", function(arr) { + var Constructor = this; + return "[object Array]" != ToString.call(arr) ? Constructor.reject(TypeError("Not an array")) : 0 === arr.length ? Constructor.resolve([]) : new Constructor(function(resolve, reject) { + if ("function" != typeof resolve || "function" != typeof reject) throw TypeError("Not a function"); + var len = arr.length, + msgs = Array(len), + count = 0; + iteratePromises(Constructor, arr, function(idx, msg) { + msgs[idx] = msg, ++count === len && resolve(msgs) + }, reject) + }) + }), builtInProp(Promise, "race", function(arr) { + var Constructor = this; + return "[object Array]" != ToString.call(arr) ? Constructor.reject(TypeError("Not an array")) : new Constructor(function(resolve, reject) { + if ("function" != typeof resolve || "function" != typeof reject) throw TypeError("Not a function"); + iteratePromises(Constructor, arr, function(idx, msg) { + resolve(msg) + }, reject) + }) + }), Promise +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/native-promise-only/test_adapter.js b/dashboard-ui/bower_components/emby-webcomponents/native-promise-only/test_adapter.js index 4b277d98ca..2bdfe7139f 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/native-promise-only/test_adapter.js +++ b/dashboard-ui/bower_components/emby-webcomponents/native-promise-only/test_adapter.js @@ -1 +1,12 @@ -var path=require("path"),Promise=require(path.join(__dirname,"lib","npo.src.js"));module.exports.deferred=function(){var o={};return o.promise=new Promise(function(resolve,reject){o.resolve=resolve,o.reject=reject}),o},module.exports.resolved=function(val){return Promise.resolve(val)},module.exports.rejected=function(reason){return Promise.reject(reason)}; \ No newline at end of file +var path = require("path"), + Promise = require(path.join(__dirname, "lib", "npo.src.js")); +module.exports.deferred = function() { + var o = {}; + return o.promise = new Promise(function(resolve, reject) { + o.resolve = resolve, o.reject = reject + }), o +}, module.exports.resolved = function(val) { + return Promise.resolve(val) +}, module.exports.rejected = function(reason) { + return Promise.reject(reason) +}; \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/notifications/notifications.js b/dashboard-ui/bower_components/emby-webcomponents/notifications/notifications.js index df4fa44ba3..08a4b7adf0 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/notifications/notifications.js +++ b/dashboard-ui/bower_components/emby-webcomponents/notifications/notifications.js @@ -1 +1,134 @@ -define(["serverNotifications","playbackManager","events","globalize","require"],function(serverNotifications,playbackManager,events,globalize,require){"use strict";function onOneDocumentClick(){document.removeEventListener("click",onOneDocumentClick),document.removeEventListener("keydown",onOneDocumentClick),window.Notification&&Notification.requestPermission()}function closeAfter(notification,timeoutMs){setTimeout(function(){notification.close?notification.close():notification.cancel&¬ification.cancel()},timeoutMs)}function resetRegistration(){var serviceWorker=navigator.serviceWorker;serviceWorker&&serviceWorker.ready.then(function(registration){serviceWorkerRegistration=registration})}function showPersistentNotification(title,options,timeoutMs){serviceWorkerRegistration.showNotification(title,options)}function showNonPersistentNotification(title,options,timeoutMs){try{var notif=new Notification(title,options);notif.show&¬if.show(),timeoutMs&&closeAfter(notif,timeoutMs)}catch(err){if(!options.actions)throw err;options.actions=[],showNonPersistentNotification(title,options,timeoutMs)}}function showNotification(options,timeoutMs,apiClient){var title=options.title;if(options.data=options.data||{},options.data.serverId=apiClient.serverInfo().Id,options.icon=options.icon||getIconUrl(),options.badge=options.badge||getIconUrl("badge.png"),resetRegistration(),serviceWorkerRegistration)return void showPersistentNotification(title,options,timeoutMs);showNonPersistentNotification(title,options,timeoutMs)}function showNewItemNotification(item,apiClient){if(!playbackManager.isPlayingLocally(["Video"])){var body=item.Name;item.SeriesName&&(body=item.SeriesName+" - "+body);var notification={title:"New "+item.Type,body:body,vibrate:!0,tag:"newItem"+item.Id,data:{}},imageTags=item.ImageTags||{};imageTags.Primary&&(notification.icon=apiClient.getScaledImageUrl(item.Id,{width:80,tag:imageTags.Primary,type:"Primary"})),showNotification(notification,15e3,apiClient)}}function onLibraryChanged(data,apiClient){var newItems=data.ItemsAdded;newItems.length&&(newItems.length>12&&(newItems.length=12),apiClient.getItems(apiClient.getCurrentUserId(),{Recursive:!0,Limit:3,Filters:"IsNotFolder",SortBy:"DateCreated",SortOrder:"Descending",Ids:newItems.join(","),MediaTypes:"Audio,Video",EnableTotalRecordCount:!1}).then(function(result){for(var items=result.Items,i=0,length=items.length;i 12 && (newItems.length = 12), apiClient.getItems(apiClient.getCurrentUserId(), { + Recursive: !0, + Limit: 3, + Filters: "IsNotFolder", + SortBy: "DateCreated", + SortOrder: "Descending", + Ids: newItems.join(","), + MediaTypes: "Audio,Video", + EnableTotalRecordCount: !1 + }).then(function(result) { + for (var items = result.Items, i = 0, length = items.length; i < length; i++) showNewItemNotification(items[i], apiClient) + })) + } + + function getIconUrl(name) { + return name = name || "notificationicon.png", require.toUrl(".").split("?")[0] + "/" + name + } + + function showPackageInstallNotification(apiClient, installation, status) { + apiClient.getCurrentUser().then(function(user) { + if (user.Policy.IsAdministrator) { + var notification = { + tag: "install" + installation.Id, + data: {} + }; + if ("completed" === status ? (notification.title = globalize.translate("sharedcomponents#PackageInstallCompleted").replace("{0}", installation.Name + " " + installation.Version), notification.vibrate = !0) : "cancelled" === status ? notification.title = globalize.translate("sharedcomponents#PackageInstallCancelled").replace("{0}", installation.Name + " " + installation.Version) : "failed" === status ? (notification.title = globalize.translate("sharedcomponents#PackageInstallFailed").replace("{0}", installation.Name + " " + installation.Version), notification.vibrate = !0) : "progress" === status && (notification.title = globalize.translate("sharedcomponents#InstallingPackage").replace("{0}", installation.Name + " " + installation.Version), notification.actions = [{ + action: "cancel-install", + title: globalize.translate("sharedcomponents#ButtonCancel"), + icon: getIconUrl() + }], notification.data.id = installation.id), "progress" === status) { + var percentComplete = Math.round(installation.PercentComplete || 0); + notification.body = percentComplete + "% complete." + } + showNotification(notification, "cancelled" === status ? 5e3 : 0, apiClient) + } + }) + } + document.addEventListener("click", onOneDocumentClick), document.addEventListener("keydown", onOneDocumentClick); + var serviceWorkerRegistration; + resetRegistration(), events.on(serverNotifications, "LibraryChanged", function(e, apiClient, data) { + onLibraryChanged(data, apiClient) + }), events.on(serverNotifications, "PackageInstallationCompleted", function(e, apiClient, data) { + showPackageInstallNotification(apiClient, data, "completed") + }), events.on(serverNotifications, "PackageInstallationFailed", function(e, apiClient, data) { + showPackageInstallNotification(apiClient, data, "failed") + }), events.on(serverNotifications, "PackageInstallationCancelled", function(e, apiClient, data) { + showPackageInstallNotification(apiClient, data, "cancelled") + }), events.on(serverNotifications, "PackageInstalling", function(e, apiClient, data) { + showPackageInstallNotification(apiClient, data, "progress") + }), events.on(serverNotifications, "ServerShuttingDown", function(e, apiClient, data) { + showNotification({ + tag: "restart" + apiClient.serverInfo().Id, + title: globalize.translate("sharedcomponents#ServerNameIsShuttingDown", apiClient.serverInfo().Name) + }, 0, apiClient) + }), events.on(serverNotifications, "ServerRestarting", function(e, apiClient, data) { + showNotification({ + tag: "restart" + apiClient.serverInfo().Id, + title: globalize.translate("sharedcomponents#ServerNameIsRestarting", apiClient.serverInfo().Name) + }, 0, apiClient) + }), events.on(serverNotifications, "RestartRequired", function(e, apiClient) { + var serverId = apiClient.serverInfo().Id, + notification = { + tag: "restart" + serverId, + title: globalize.translate("sharedcomponents#PleaseRestartServerName", apiClient.serverInfo().Name) + }; + notification.actions = [{ + action: "restart", + title: globalize.translate("sharedcomponents#ButtonRestart"), + icon: getIconUrl() + }], showNotification(notification, 0, apiClient) + }) +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/nowplayingbar/nowplayingbar.js b/dashboard-ui/bower_components/emby-webcomponents/nowplayingbar/nowplayingbar.js index 4c0062a417..feded12a2a 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/nowplayingbar/nowplayingbar.js +++ b/dashboard-ui/bower_components/emby-webcomponents/nowplayingbar/nowplayingbar.js @@ -1 +1,270 @@ -define(["require","datetime","itemHelper","events","browser","imageLoader","layoutManager","playbackManager","nowPlayingHelper","apphost","dom","connectionManager","paper-icon-button-light","emby-ratingbutton"],function(require,datetime,itemHelper,events,browser,imageLoader,layoutManager,playbackManager,nowPlayingHelper,appHost,dom,connectionManager){"use strict";function getNowPlayingBarHtml(){var html="";return html+='
',html+='
',html+='
',html+='',html+="
",html+='
',html+='
',html+='
',html+="
",html+='
',html+='',html+='',html+='',html+='',html+='
',html+="
",html+='
',html+='',html+='
',html+='',html+="
",html+='',html+='
',html+="
",html+='',html+='',html+="
",html+="
",html+="
"}function onSlideDownComplete(){this.classList.add("hide")}function slideDown(elem){elem.offsetWidth,elem.classList.add("nowPlayingBar-hidden"),dom.addEventListener(elem,dom.whichTransitionEvent(),onSlideDownComplete,{once:!0})}function slideUp(elem){dom.removeEventListener(elem,dom.whichTransitionEvent(),onSlideDownComplete,{once:!0}),elem.classList.remove("hide"),elem.offsetWidth,elem.classList.remove("nowPlayingBar-hidden")}function onPlayPauseClick(){playbackManager.playPause(currentPlayer)}function bindEvents(elem){currentTimeElement=elem.querySelector(".nowPlayingBarCurrentTime"),nowPlayingImageElement=elem.querySelector(".nowPlayingImage"),nowPlayingTextElement=elem.querySelector(".nowPlayingBarText"),nowPlayingUserData=elem.querySelector(".nowPlayingBarUserDataButtons"),muteButton=elem.querySelector(".muteButton"),muteButton.addEventListener("click",function(){currentPlayer&&playbackManager.toggleMute(currentPlayer)}),elem.querySelector(".stopButton").addEventListener("click",function(){currentPlayer&&playbackManager.stop(currentPlayer)});var i,length;for(playPauseButtons=elem.querySelectorAll(".playPauseButton"),i=0,length=playPauseButtons.length;i';return html+=text,html+=""}function seriesImageUrl(item,options){if(!item)throw new Error("item cannot be null!");if("Episode"!==item.Type)return null;if(options=options||{},options.type=options.type||"Primary","Primary"===options.type&&item.SeriesPrimaryImageTag)return options.tag=item.SeriesPrimaryImageTag,connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.SeriesId,options);if("Thumb"===options.type){if(item.SeriesThumbImageTag)return options.tag=item.SeriesThumbImageTag,connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.SeriesId,options);if(item.ParentThumbImageTag)return options.tag=item.ParentThumbImageTag,connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.ParentThumbItemId,options)}return null}function imageUrl(item,options){if(!item)throw new Error("item cannot be null!");return options=options||{},options.type=options.type||"Primary",item.ImageTags&&item.ImageTags[options.type]?(options.tag=item.ImageTags[options.type],connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.PrimaryImageItemId||item.Id,options)):item.AlbumId&&item.AlbumPrimaryImageTag?(options.tag=item.AlbumPrimaryImageTag,connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.AlbumId,options)):null}function updateNowPlayingInfo(state){var nowPlayingItem=state.NowPlayingItem,textLines=nowPlayingItem?nowPlayingHelper.getNowPlayingNames(nowPlayingItem):[];textLines.length>1&&(textLines[1].secondary=!0);var serverId=nowPlayingItem?nowPlayingItem.ServerId:null;nowPlayingTextElement.innerHTML=textLines.map(function(nowPlayingName){var cssClass=nowPlayingName.secondary?' class="nowPlayingBarSecondaryText"':"";return nowPlayingName.item?""+getTextActionButton(nowPlayingName.item,nowPlayingName.text,serverId)+"
":""+nowPlayingName.text+"
"}).join("");var url=nowPlayingItem?seriesImageUrl(nowPlayingItem,{height:70})||imageUrl(nowPlayingItem,{height:70}):null,isRefreshing=!1;if(url!==currentImgUrl&&(currentImgUrl=url,isRefreshing=!0,url?imageLoader.lazyImage(nowPlayingImageElement,url):nowPlayingImageElement.style.backgroundImage=""),nowPlayingItem.Id){if(isRefreshing){var apiClient=connectionManager.getApiClient(nowPlayingItem.ServerId);apiClient.getItem(apiClient.getCurrentUserId(),nowPlayingItem.Id).then(function(item){var userData=item.UserData||{},likes=null==userData.Likes?"":userData.Likes;nowPlayingUserData.innerHTML=''})}}else nowPlayingUserData.innerHTML=""}function onPlaybackStart(e,state){var player=this;onStateChanged.call(player,e,state)}function onRepeatModeChange(e){if(isEnabled){var player=this;updateRepeatModeDisplay(playbackManager.getRepeatMode(player))}}function showNowPlayingBar(){if(!isVisibilityAllowed)return void hideNowPlayingBar();getNowPlayingBar().then(slideUp)}function hideNowPlayingBar(){isEnabled=!1;var elem=document.getElementsByClassName("nowPlayingBar")[0];elem&&slideDown(elem)}function onPlaybackStopped(e,state){this.isLocalPlayer?"Audio"!==state.NextMediaType&&hideNowPlayingBar():state.NextMediaType||hideNowPlayingBar()}function onPlayPauseStateChanged(e){if(isEnabled){updatePlayPauseState(this.paused())}}function onStateChanged(event,state){var player=this;return!state.NowPlayingItem||layoutManager.tv?void hideNowPlayingBar():player.isLocalPlayer&&state.NowPlayingItem&&"Video"===state.NowPlayingItem.MediaType?void hideNowPlayingBar():(isEnabled=!0,nowPlayingBarElement?void updatePlayerStateInternal(event,state,player):void getNowPlayingBar().then(function(){updatePlayerStateInternal(event,state,player)}))}function onTimeUpdate(e){if(isEnabled){var now=(new Date).getTime();if(!(now-lastUpdateTime<700)){lastUpdateTime=now;var player=this;currentRuntimeTicks=playbackManager.duration(player),updateTimeDisplay(playbackManager.currentTime(player),currentRuntimeTicks,playbackManager.getBufferedRanges(player))}}}function releaseCurrentPlayer(){var player=currentPlayer;player&&(events.off(player,"playbackstart",onPlaybackStart),events.off(player,"statechange",onPlaybackStart),events.off(player,"repeatmodechange",onRepeatModeChange),events.off(player,"playbackstop",onPlaybackStopped),events.off(player,"volumechange",onVolumeChanged),events.off(player,"pause",onPlayPauseStateChanged),events.off(player,"unpause",onPlayPauseStateChanged),events.off(player,"timeupdate",onTimeUpdate),currentPlayer=null,hideNowPlayingBar())}function onVolumeChanged(e){if(isEnabled){var player=this;updatePlayerVolumeState(player.isMuted(),player.getVolume())}}function refreshFromPlayer(player){var state=playbackManager.getPlayerState(player);onStateChanged.call(player,{type:"init"},state)}function bindToPlayer(player){player!==currentPlayer&&(releaseCurrentPlayer(),currentPlayer=player,player&&(refreshFromPlayer(player),events.on(player,"playbackstart",onPlaybackStart),events.on(player,"statechange",onPlaybackStart),events.on(player,"repeatmodechange",onRepeatModeChange),events.on(player,"playbackstop",onPlaybackStopped),events.on(player,"volumechange",onVolumeChanged),events.on(player,"pause",onPlayPauseStateChanged),events.on(player,"unpause",onPlayPauseStateChanged),events.on(player,"timeupdate",onTimeUpdate)))}var currentPlayer,currentTimeElement,nowPlayingImageElement,nowPlayingTextElement,nowPlayingUserData,muteButton,volumeSlider,volumeSliderContainer,playPauseButtons,positionSlider,toggleRepeatButton,toggleRepeatButtonIcon,isEnabled,nowPlayingBarElement,currentImgUrl,currentPlayerSupportedCommands=[],lastUpdateTime=0,lastPlayerState={},currentRuntimeTicks=0,isVisibilityAllowed=!0;events.on(playbackManager,"playerchange",function(){bindToPlayer(playbackManager.getCurrentPlayer())}),bindToPlayer(playbackManager.getCurrentPlayer()),document.addEventListener("viewbeforeshow",function(e){e.detail.options.enableMediaControl?isVisibilityAllowed||(isVisibilityAllowed=!0,currentPlayer?refreshFromPlayer(currentPlayer):hideNowPlayingBar()):isVisibilityAllowed&&(isVisibilityAllowed=!1,hideNowPlayingBar())})}); \ No newline at end of file +define(["require", "datetime", "itemHelper", "events", "browser", "imageLoader", "layoutManager", "playbackManager", "nowPlayingHelper", "apphost", "dom", "connectionManager", "paper-icon-button-light", "emby-ratingbutton"], function(require, datetime, itemHelper, events, browser, imageLoader, layoutManager, playbackManager, nowPlayingHelper, appHost, dom, connectionManager) { + "use strict"; + + function getNowPlayingBarHtml() { + var html = ""; + return html += '
', html += '
', html += '
', html += '', html += "
", html += '
', html += '
', html += '
', html += "
", html += '
', html += '', html += '', html += '', html += '', html += '
', html += "
", html += '
', html += '', html += '
', html += '', html += "
", html += '', html += '
', html += "
", html += '', html += '', html += "
", html += "
", html += "
" + } + + function onSlideDownComplete() { + this.classList.add("hide") + } + + function slideDown(elem) { + elem.offsetWidth, elem.classList.add("nowPlayingBar-hidden"), dom.addEventListener(elem, dom.whichTransitionEvent(), onSlideDownComplete, { + once: !0 + }) + } + + function slideUp(elem) { + dom.removeEventListener(elem, dom.whichTransitionEvent(), onSlideDownComplete, { + once: !0 + }), elem.classList.remove("hide"), elem.offsetWidth, elem.classList.remove("nowPlayingBar-hidden") + } + + function onPlayPauseClick() { + playbackManager.playPause(currentPlayer) + } + + function bindEvents(elem) { + currentTimeElement = elem.querySelector(".nowPlayingBarCurrentTime"), nowPlayingImageElement = elem.querySelector(".nowPlayingImage"), nowPlayingTextElement = elem.querySelector(".nowPlayingBarText"), nowPlayingUserData = elem.querySelector(".nowPlayingBarUserDataButtons"), muteButton = elem.querySelector(".muteButton"), muteButton.addEventListener("click", function() { + currentPlayer && playbackManager.toggleMute(currentPlayer) + }), elem.querySelector(".stopButton").addEventListener("click", function() { + currentPlayer && playbackManager.stop(currentPlayer) + }); + var i, length; + for (playPauseButtons = elem.querySelectorAll(".playPauseButton"), i = 0, length = playPauseButtons.length; i < length; i++) playPauseButtons[i].addEventListener("click", onPlayPauseClick); + elem.querySelector(".nextTrackButton").addEventListener("click", function() { + currentPlayer && playbackManager.nextTrack(currentPlayer) + }), elem.querySelector(".previousTrackButton").addEventListener("click", function() { + currentPlayer && playbackManager.previousTrack(currentPlayer) + }), elem.querySelector(".remoteControlButton").addEventListener("click", showRemoteControl), toggleRepeatButton = elem.querySelector(".toggleRepeatButton"), toggleRepeatButton.addEventListener("click", function() { + if (currentPlayer) switch (playbackManager.getRepeatMode(currentPlayer)) { + case "RepeatAll": + playbackManager.setRepeatMode("RepeatOne", currentPlayer); + break; + case "RepeatOne": + playbackManager.setRepeatMode("RepeatNone", currentPlayer); + break; + default: + playbackManager.setRepeatMode("RepeatAll", currentPlayer) + } + }), toggleRepeatButtonIcon = toggleRepeatButton.querySelector("i"), volumeSlider = elem.querySelector(".nowPlayingBarVolumeSlider"), volumeSliderContainer = elem.querySelector(".nowPlayingBarVolumeSliderContainer"), appHost.supports("physicalvolumecontrol") ? volumeSliderContainer.classList.add("hide") : volumeSliderContainer.classList.remove("hide"), volumeSlider.addEventListener("change", function() { + currentPlayer && currentPlayer.setVolume(this.value) + }), positionSlider = elem.querySelector(".nowPlayingBarPositionSlider"), positionSlider.addEventListener("change", function() { + if (currentPlayer) { + var newPercent = parseFloat(this.value); + playbackManager.seekPercent(newPercent, currentPlayer) + } + }), positionSlider.getBubbleText = function(value) { + var state = lastPlayerState; + if (!state || !state.NowPlayingItem || !currentRuntimeTicks) return "--:--"; + var ticks = currentRuntimeTicks; + return ticks /= 100, ticks *= value, datetime.getDisplayRunningTime(ticks) + }, elem.addEventListener("click", function(e) { + dom.parentWithTag(e.target, ["BUTTON", "INPUT", "A"]) || showRemoteControl() + }) + } + + function showRemoteControl() { + require(["appRouter"], function(appRouter) { + appRouter.showNowPlaying() + }) + } + + function getNowPlayingBar() { + return nowPlayingBarElement ? Promise.resolve(nowPlayingBarElement) : new Promise(function(resolve, reject) { + require(["appFooter-shared", "itemShortcuts", "css!./nowplayingbar.css", "emby-slider"], function(appfooter, itemShortcuts) { + var parentContainer = appfooter.element; + if (nowPlayingBarElement = parentContainer.querySelector(".nowPlayingBar")) return void resolve(nowPlayingBarElement); + parentContainer.insertAdjacentHTML("afterbegin", getNowPlayingBarHtml()), nowPlayingBarElement = parentContainer.querySelector(".nowPlayingBar"), browser.safari && browser.slow && nowPlayingBarElement.classList.add("noMediaProgress"), itemShortcuts.on(nowPlayingBarElement), bindEvents(nowPlayingBarElement), resolve(nowPlayingBarElement) + }) + }) + } + + function showButton(button) { + button.classList.remove("hide") + } + + function hideButton(button) { + button.classList.add("hide") + } + + function updatePlayPauseState(isPaused) { + var i, length; + if (playPauseButtons) + if (isPaused) + for (i = 0, length = playPauseButtons.length; i < length; i++) playPauseButtons[i].querySelector("i").innerHTML = "play_arrow"; + else + for (i = 0, length = playPauseButtons.length; i < length; i++) playPauseButtons[i].querySelector("i").innerHTML = "pause" + } + + function updatePlayerStateInternal(event, state, player) { + showNowPlayingBar(), lastPlayerState = state; + var playerInfo = playbackManager.getPlayerInfo(), + playState = state.PlayState || {}; + updatePlayPauseState(playState.IsPaused); + var supportedCommands = playerInfo.supportedCommands; + if (currentPlayerSupportedCommands = supportedCommands, -1 === supportedCommands.indexOf("SetRepeatMode") ? toggleRepeatButton.classList.add("hide") : toggleRepeatButton.classList.remove("hide"), updateRepeatModeDisplay(playState.RepeatMode), updatePlayerVolumeState(playState.IsMuted, playState.VolumeLevel), positionSlider && !positionSlider.dragging) { + positionSlider.disabled = !playState.CanSeek; + var isProgressClear = state.MediaSource && null == state.MediaSource.RunTimeTicks; + positionSlider.setIsClear(isProgressClear) + } + updateTimeDisplay(playState.PositionTicks, (state.NowPlayingItem || {}).RunTimeTicks, playbackManager.getBufferedRanges(player)), updateNowPlayingInfo(state) + } + + function updateRepeatModeDisplay(repeatMode) { + "RepeatAll" === repeatMode ? (toggleRepeatButtonIcon.innerHTML = "repeat", toggleRepeatButton.classList.add("repeatButton-active")) : "RepeatOne" === repeatMode ? (toggleRepeatButtonIcon.innerHTML = "repeat_one", toggleRepeatButton.classList.add("repeatButton-active")) : (toggleRepeatButtonIcon.innerHTML = "repeat", toggleRepeatButton.classList.remove("repeatButton-active")) + } + + function updateTimeDisplay(positionTicks, runtimeTicks, bufferedRanges) { + if (positionSlider && !positionSlider.dragging) + if (runtimeTicks) { + var pct = positionTicks / runtimeTicks; + pct *= 100, positionSlider.value = pct + } else positionSlider.value = 0; + if (positionSlider && positionSlider.setBufferedRanges(bufferedRanges, runtimeTicks, positionTicks), currentTimeElement) { + var timeText = null == positionTicks ? "--:--" : datetime.getDisplayRunningTime(positionTicks); + runtimeTicks && (timeText += " / " + datetime.getDisplayRunningTime(runtimeTicks)), currentTimeElement.innerHTML = timeText + } + } + + function updatePlayerVolumeState(isMuted, volumeLevel) { + var supportedCommands = currentPlayerSupportedCommands, + showMuteButton = !0, + showVolumeSlider = !0; - 1 === supportedCommands.indexOf("ToggleMute") && (showMuteButton = !1), muteButton.querySelector("i").innerHTML = isMuted ? "" : "", -1 === supportedCommands.indexOf("SetVolume") && (showVolumeSlider = !1), currentPlayer.isLocalPlayer && appHost.supports("physicalvolumecontrol") && (showMuteButton = !1, showVolumeSlider = !1), showMuteButton ? showButton(muteButton) : hideButton(muteButton), volumeSlider && (showVolumeSlider ? volumeSliderContainer.classList.remove("hide") : volumeSliderContainer.classList.add("hide"), volumeSlider.dragging || (volumeSlider.value = volumeLevel || 0)) + } + + function getTextActionButton(item, text, serverId) { + text || (text = itemHelper.getDisplayName(item)); + var html = '" + } + + function seriesImageUrl(item, options) { + if (!item) throw new Error("item cannot be null!"); + if ("Episode" !== item.Type) return null; + if (options = options || {}, options.type = options.type || "Primary", "Primary" === options.type && item.SeriesPrimaryImageTag) return options.tag = item.SeriesPrimaryImageTag, connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.SeriesId, options); + if ("Thumb" === options.type) { + if (item.SeriesThumbImageTag) return options.tag = item.SeriesThumbImageTag, connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.SeriesId, options); + if (item.ParentThumbImageTag) return options.tag = item.ParentThumbImageTag, connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.ParentThumbItemId, options) + } + return null + } + + function imageUrl(item, options) { + if (!item) throw new Error("item cannot be null!"); + return options = options || {}, options.type = options.type || "Primary", item.ImageTags && item.ImageTags[options.type] ? (options.tag = item.ImageTags[options.type], connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.PrimaryImageItemId || item.Id, options)) : item.AlbumId && item.AlbumPrimaryImageTag ? (options.tag = item.AlbumPrimaryImageTag, connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.AlbumId, options)) : null + } + + function updateNowPlayingInfo(state) { + var nowPlayingItem = state.NowPlayingItem, + textLines = nowPlayingItem ? nowPlayingHelper.getNowPlayingNames(nowPlayingItem) : []; + textLines.length > 1 && (textLines[1].secondary = !0); + var serverId = nowPlayingItem ? nowPlayingItem.ServerId : null; + nowPlayingTextElement.innerHTML = textLines.map(function(nowPlayingName) { + var cssClass = nowPlayingName.secondary ? ' class="nowPlayingBarSecondaryText"' : ""; + return nowPlayingName.item ? "" + getTextActionButton(nowPlayingName.item, nowPlayingName.text, serverId) + "
" : "" + nowPlayingName.text + "
" + }).join(""); + var url = nowPlayingItem ? seriesImageUrl(nowPlayingItem, { + height: 70 + }) || imageUrl(nowPlayingItem, { + height: 70 + }) : null, + isRefreshing = !1; + if (url !== currentImgUrl && (currentImgUrl = url, isRefreshing = !0, url ? imageLoader.lazyImage(nowPlayingImageElement, url) : nowPlayingImageElement.style.backgroundImage = ""), nowPlayingItem.Id) { + if (isRefreshing) { + var apiClient = connectionManager.getApiClient(nowPlayingItem.ServerId); + apiClient.getItem(apiClient.getCurrentUserId(), nowPlayingItem.Id).then(function(item) { + var userData = item.UserData || {}, + likes = null == userData.Likes ? "" : userData.Likes; + nowPlayingUserData.innerHTML = '' + }) + } + } else nowPlayingUserData.innerHTML = "" + } + + function onPlaybackStart(e, state) { + var player = this; + onStateChanged.call(player, e, state) + } + + function onRepeatModeChange(e) { + if (isEnabled) { + var player = this; + updateRepeatModeDisplay(playbackManager.getRepeatMode(player)) + } + } + + function showNowPlayingBar() { + if (!isVisibilityAllowed) return void hideNowPlayingBar(); + getNowPlayingBar().then(slideUp) + } + + function hideNowPlayingBar() { + isEnabled = !1; + var elem = document.getElementsByClassName("nowPlayingBar")[0]; + elem && slideDown(elem) + } + + function onPlaybackStopped(e, state) { + this.isLocalPlayer ? "Audio" !== state.NextMediaType && hideNowPlayingBar() : state.NextMediaType || hideNowPlayingBar() + } + + function onPlayPauseStateChanged(e) { + if (isEnabled) { + updatePlayPauseState(this.paused()) + } + } + + function onStateChanged(event, state) { + var player = this; + return !state.NowPlayingItem || layoutManager.tv ? void hideNowPlayingBar() : player.isLocalPlayer && state.NowPlayingItem && "Video" === state.NowPlayingItem.MediaType ? void hideNowPlayingBar() : (isEnabled = !0, nowPlayingBarElement ? void updatePlayerStateInternal(event, state, player) : void getNowPlayingBar().then(function() { + updatePlayerStateInternal(event, state, player) + })) + } + + function onTimeUpdate(e) { + if (isEnabled) { + var now = (new Date).getTime(); + if (!(now - lastUpdateTime < 700)) { + lastUpdateTime = now; + var player = this; + currentRuntimeTicks = playbackManager.duration(player), updateTimeDisplay(playbackManager.currentTime(player), currentRuntimeTicks, playbackManager.getBufferedRanges(player)) + } + } + } + + function releaseCurrentPlayer() { + var player = currentPlayer; + player && (events.off(player, "playbackstart", onPlaybackStart), events.off(player, "statechange", onPlaybackStart), events.off(player, "repeatmodechange", onRepeatModeChange), events.off(player, "playbackstop", onPlaybackStopped), events.off(player, "volumechange", onVolumeChanged), events.off(player, "pause", onPlayPauseStateChanged), events.off(player, "unpause", onPlayPauseStateChanged), events.off(player, "timeupdate", onTimeUpdate), currentPlayer = null, hideNowPlayingBar()) + } + + function onVolumeChanged(e) { + if (isEnabled) { + var player = this; + updatePlayerVolumeState(player.isMuted(), player.getVolume()) + } + } + + function refreshFromPlayer(player) { + var state = playbackManager.getPlayerState(player); + onStateChanged.call(player, { + type: "init" + }, state) + } + + function bindToPlayer(player) { + player !== currentPlayer && (releaseCurrentPlayer(), currentPlayer = player, player && (refreshFromPlayer(player), events.on(player, "playbackstart", onPlaybackStart), events.on(player, "statechange", onPlaybackStart), events.on(player, "repeatmodechange", onRepeatModeChange), events.on(player, "playbackstop", onPlaybackStopped), events.on(player, "volumechange", onVolumeChanged), events.on(player, "pause", onPlayPauseStateChanged), events.on(player, "unpause", onPlayPauseStateChanged), events.on(player, "timeupdate", onTimeUpdate))) + } + var currentPlayer, currentTimeElement, nowPlayingImageElement, nowPlayingTextElement, nowPlayingUserData, muteButton, volumeSlider, volumeSliderContainer, playPauseButtons, positionSlider, toggleRepeatButton, toggleRepeatButtonIcon, isEnabled, nowPlayingBarElement, currentImgUrl, currentPlayerSupportedCommands = [], + lastUpdateTime = 0, + lastPlayerState = {}, + currentRuntimeTicks = 0, + isVisibilityAllowed = !0; + events.on(playbackManager, "playerchange", function() { + bindToPlayer(playbackManager.getCurrentPlayer()) + }), bindToPlayer(playbackManager.getCurrentPlayer()), document.addEventListener("viewbeforeshow", function(e) { + e.detail.options.enableMediaControl ? isVisibilityAllowed || (isVisibilityAllowed = !0, currentPlayer ? refreshFromPlayer(currentPlayer) : hideNowPlayingBar()) : isVisibilityAllowed && (isVisibilityAllowed = !1, hideNowPlayingBar()) + }) +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/packagemanager.js b/dashboard-ui/bower_components/emby-webcomponents/packagemanager.js index 9da2a3cddc..e697028f5c 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/packagemanager.js +++ b/dashboard-ui/bower_components/emby-webcomponents/packagemanager.js @@ -1 +1,74 @@ -define(["appSettings","pluginManager"],function(appSettings,pluginManager){"use strict";function addPackage(packageManager,pkg){packageManager.packagesList=packageManager.packagesList.filter(function(p){return p.name!==pkg.name}),packageManager.packagesList.push(pkg)}function removeUrl(url){var manifestUrls=JSON.parse(appSettings.get(settingsKey)||"[]");manifestUrls=manifestUrls.filter(function(i){return i!==url}),appSettings.set(settingsKey,JSON.stringify(manifestUrls))}function loadPackage(packageManager,url,throwError){return new Promise(function(resolve,reject){var xhr=new XMLHttpRequest,originalUrl=url;url+=-1===url.indexOf("?")?"?":"&",url+="t="+(new Date).getTime(),xhr.open("GET",url,!0);var onError=function(){!0===throwError?reject():(removeUrl(originalUrl),resolve())};xhr.onload=function(e){if(this.status<400){var pkg=JSON.parse(this.response);pkg.url=originalUrl,addPackage(packageManager,pkg);var plugins=pkg.plugins||[];pkg.plugin&&plugins.push(pkg.plugin);var promises=plugins.map(function(pluginUrl){return pluginManager.loadPlugin(packageManager.mapPath(pkg,pluginUrl))});Promise.all(promises).then(resolve,resolve)}else onError()},xhr.onerror=onError,xhr.send()})}function PackageManager(){this.packagesList=[]}var settingsKey="installedpackages1";return PackageManager.prototype.init=function(){var manifestUrls=JSON.parse(appSettings.get(settingsKey)||"[]"),instance=this;return Promise.all(manifestUrls.map(function(u){return loadPackage(instance,u)})).then(function(){return Promise.resolve()},function(){return Promise.resolve()})},PackageManager.prototype.packages=function(){return this.packagesList.slice(0)},PackageManager.prototype.install=function(url){return loadPackage(this,url,!0).then(function(pkg){var manifestUrls=JSON.parse(appSettings.get(settingsKey)||"[]");return-1===manifestUrls.indexOf(url)&&(manifestUrls.push(url),appSettings.set(settingsKey,JSON.stringify(manifestUrls))),pkg})},PackageManager.prototype.uninstall=function(name){var pkg=this.packagesList.filter(function(p){return p.name===name})[0];return pkg&&(this.packagesList=this.packagesList.filter(function(p){return p.name!==name}),removeUrl(pkg.url)),Promise.resolve()},PackageManager.prototype.mapPath=function(pkg,pluginUrl){var urlLower=pluginUrl.toLowerCase();if(0===urlLower.indexOf("http:")||0===urlLower.indexOf("https:")||0===urlLower.indexOf("file:"))return pluginUrl;var packageUrl=pkg.url;return packageUrl=packageUrl.substring(0,packageUrl.lastIndexOf("/")),packageUrl+="/",packageUrl+=pluginUrl},new PackageManager}); \ No newline at end of file +define(["appSettings", "pluginManager"], function(appSettings, pluginManager) { + "use strict"; + + function addPackage(packageManager, pkg) { + packageManager.packagesList = packageManager.packagesList.filter(function(p) { + return p.name !== pkg.name + }), packageManager.packagesList.push(pkg) + } + + function removeUrl(url) { + var manifestUrls = JSON.parse(appSettings.get(settingsKey) || "[]"); + manifestUrls = manifestUrls.filter(function(i) { + return i !== url + }), appSettings.set(settingsKey, JSON.stringify(manifestUrls)) + } + + function loadPackage(packageManager, url, throwError) { + return new Promise(function(resolve, reject) { + var xhr = new XMLHttpRequest, + originalUrl = url; + url += -1 === url.indexOf("?") ? "?" : "&", url += "t=" + (new Date).getTime(), xhr.open("GET", url, !0); + var onError = function() { + !0 === throwError ? reject() : (removeUrl(originalUrl), resolve()) + }; + xhr.onload = function(e) { + if (this.status < 400) { + var pkg = JSON.parse(this.response); + pkg.url = originalUrl, addPackage(packageManager, pkg); + var plugins = pkg.plugins || []; + pkg.plugin && plugins.push(pkg.plugin); + var promises = plugins.map(function(pluginUrl) { + return pluginManager.loadPlugin(packageManager.mapPath(pkg, pluginUrl)) + }); + Promise.all(promises).then(resolve, resolve) + } else onError() + }, xhr.onerror = onError, xhr.send() + }) + } + + function PackageManager() { + this.packagesList = [] + } + var settingsKey = "installedpackages1"; + return PackageManager.prototype.init = function() { + var manifestUrls = JSON.parse(appSettings.get(settingsKey) || "[]"), + instance = this; + return Promise.all(manifestUrls.map(function(u) { + return loadPackage(instance, u) + })).then(function() { + return Promise.resolve() + }, function() { + return Promise.resolve() + }) + }, PackageManager.prototype.packages = function() { + return this.packagesList.slice(0) + }, PackageManager.prototype.install = function(url) { + return loadPackage(this, url, !0).then(function(pkg) { + var manifestUrls = JSON.parse(appSettings.get(settingsKey) || "[]"); + return -1 === manifestUrls.indexOf(url) && (manifestUrls.push(url), appSettings.set(settingsKey, JSON.stringify(manifestUrls))), pkg + }) + }, PackageManager.prototype.uninstall = function(name) { + var pkg = this.packagesList.filter(function(p) { + return p.name === name + })[0]; + return pkg && (this.packagesList = this.packagesList.filter(function(p) { + return p.name !== name + }), removeUrl(pkg.url)), Promise.resolve() + }, PackageManager.prototype.mapPath = function(pkg, pluginUrl) { + var urlLower = pluginUrl.toLowerCase(); + if (0 === urlLower.indexOf("http:") || 0 === urlLower.indexOf("https:") || 0 === urlLower.indexOf("file:")) return pluginUrl; + var packageUrl = pkg.url; + return packageUrl = packageUrl.substring(0, packageUrl.lastIndexOf("/")), packageUrl += "/", packageUrl += pluginUrl + }, new PackageManager +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/pagejs/page.js b/dashboard-ui/bower_components/emby-webcomponents/pagejs/page.js index 79eff40df6..17b29a434a 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/pagejs/page.js +++ b/dashboard-ui/bower_components/emby-webcomponents/pagejs/page.js @@ -1 +1,288 @@ -define([],function(){"use strict";function page(path,fn){if("function"==typeof path)return page("*",path);if("function"==typeof fn)for(var route=new Route(path),i=1;i=href.indexOf("#!")&&(url+=location.search)}else url=location.pathname+location.search+location.hash;page.replace(url,null,!0,dispatch)}},page.stop=function(){running&&(page.current="",page.len=0,running=!1,document.removeEventListener(clickEvent,onclick,!1),window.removeEventListener("popstate",onpopstate,!1))},page.show=function(path,state,dispatch,push,isBack){var ctx=new Context(path,state);return ctx.isBack=isBack,page.current=ctx.path,!1!==dispatch&&page.dispatch(ctx),!1!==ctx.handled&&!1!==push&&ctx.pushState(),ctx},page.restorePreviousState=function(){prevContext=prevPageContext,page.show(prevContext.pathname,prevContext.state,!1,!0,!1)},page.back=function(path,state){if(enableHistory)return void history.back();if(page.len>0){if(enableHistory)history.back();else if(backStack.length>2){backStack.length--;var previousState=backStack[backStack.length-1];page.show(previousState.path,previousState.state,!0,!1,!0)}page.len--}else path?setTimeout(function(){page.show(path,state)}):setTimeout(function(){page.show(base,state)})},page.enableNativeHistory=function(){return enableHistory},page.canGoBack=function(){return enableHistory?history.length>1:(page.len||0)>0},page.redirect=function(from,to){"string"==typeof from&&"string"==typeof to&&page(from,function(e){setTimeout(function(){page.replace(to)},0)}),"string"==typeof from&&void 0===to&&setTimeout(function(){page.replace(from)},0)},page.replace=function(path,state,init,dispatch,isBack){var ctx=new Context(path,state);return ctx.isBack=isBack,page.current=ctx.path,ctx.init=init,ctx.save(),!1!==dispatch&&page.dispatch(ctx),ctx},page.dispatch=function(ctx){function nextExit(){var fn=page.exits[j++];if(!fn)return nextEnter();fn(prev,nextExit)}function nextEnter(){var fn=page.callbacks[i++];return ctx.path!==page.current?void(ctx.handled=!1):fn?void fn(ctx,nextEnter):unhandled(ctx)}var prev=prevContext,i=0,j=0;prevPageContext=prevContext,prevContext=ctx,prev?nextExit():nextEnter()},page.exit=function(path,fn){if("function"==typeof path)return page.exit("*",path);for(var route=new Route(path),i=1;i= href.indexOf("#!") && (url += location.search) + } else url = location.pathname + location.search + location.hash; + page.replace(url, null, !0, dispatch) + } + }, page.stop = function() { + running && (page.current = "", page.len = 0, running = !1, document.removeEventListener(clickEvent, onclick, !1), window.removeEventListener("popstate", onpopstate, !1)) + }, page.show = function(path, state, dispatch, push, isBack) { + var ctx = new Context(path, state); + return ctx.isBack = isBack, page.current = ctx.path, !1 !== dispatch && page.dispatch(ctx), !1 !== ctx.handled && !1 !== push && ctx.pushState(), ctx + }, page.restorePreviousState = function() { + prevContext = prevPageContext, page.show(prevContext.pathname, prevContext.state, !1, !0, !1) + }, page.back = function(path, state) { + if (enableHistory) return void history.back(); + if (page.len > 0) { + if (enableHistory) history.back(); + else if (backStack.length > 2) { + backStack.length--; + var previousState = backStack[backStack.length - 1]; + page.show(previousState.path, previousState.state, !0, !1, !0) + } + page.len-- + } else path ? setTimeout(function() { + page.show(path, state) + }) : setTimeout(function() { + page.show(base, state) + }) + }, page.enableNativeHistory = function() { + return enableHistory + }, page.canGoBack = function() { + return enableHistory ? history.length > 1 : (page.len || 0) > 0 + }, page.redirect = function(from, to) { + "string" == typeof from && "string" == typeof to && page(from, function(e) { + setTimeout(function() { + page.replace(to) + }, 0) + }), "string" == typeof from && void 0 === to && setTimeout(function() { + page.replace(from) + }, 0) + }, page.replace = function(path, state, init, dispatch, isBack) { + var ctx = new Context(path, state); + return ctx.isBack = isBack, page.current = ctx.path, ctx.init = init, ctx.save(), !1 !== dispatch && page.dispatch(ctx), ctx + }, page.dispatch = function(ctx) { + function nextExit() { + var fn = page.exits[j++]; + if (!fn) return nextEnter(); + fn(prev, nextExit) + } + + function nextEnter() { + var fn = page.callbacks[i++]; + return ctx.path !== page.current ? void(ctx.handled = !1) : fn ? void fn(ctx, nextEnter) : unhandled(ctx) + } + var prev = prevContext, + i = 0, + j = 0; + prevPageContext = prevContext, prevContext = ctx, prev ? nextExit() : nextEnter() + }, page.exit = function(path, fn) { + if ("function" == typeof path) return page.exit("*", path); + for (var route = new Route(path), i = 1; i < arguments.length; ++i) page.exits.push(route.middleware(arguments[i])) + }, page.Context = Context; + var backStack = []; + Context.prototype.pushState = function() { + page.len++, enableHistory ? history.pushState(this.state, this.title, hashbang && "/" !== this.path ? "#!" + this.path : this.canonicalPath) : backStack.push({ + state: this.state, + title: this.title, + url: hashbang && "/" !== this.path ? "#!" + this.path : this.canonicalPath, + path: this.path + }) + }, Context.prototype.save = function() { + enableHistory ? history.replaceState(this.state, this.title, hashbang && "/" !== this.path ? "#!" + this.path : this.canonicalPath) : backStack[page.len || 0] = { + state: this.state, + title: this.title, + url: hashbang && "/" !== this.path ? "#!" + this.path : this.canonicalPath, + path: this.path + } + }, page.Route = Route, Route.prototype.middleware = function(fn) { + var self = this; + return function(ctx, next) { + if (self.match(ctx.path, ctx.params)) return fn(ctx, next); + next() + } + }, Route.prototype.match = function(path, params) { + var keys = this.keys, + qsIndex = path.indexOf("?"), + pathname = ~qsIndex ? path.slice(0, qsIndex) : path, + m = this.regexp.exec(decodeURIComponent(pathname)); + if (!m) return !1; + for (var i = 1, len = m.length; i < len; ++i) { + var key = keys[i - 1], + val = decodeURLEncodedURIComponent(m[i]); + void 0 === val && hasOwnProperty.call(params, key.name) || (params[key.name] = val) + } + return !0 + }; + var previousPopState = {}; + page.pushState = function(state, title, url) { + hashbang && (url = "#!" + url), history.pushState(state, title, url), previousPopState = state + }; + var onpopstate = function() { + var loaded = !1; + if ("undefined" != typeof window) return "complete" === document.readyState ? loaded = !0 : window.addEventListener("load", function() { + setTimeout(function() { + loaded = !0 + }, 0) + }), + function(e) { + if (loaded && !ignorePopState(e)) + if (e.state) { + var path = e.state.path; + page.replace(path, e.state, null, null, !0) + } else page.show(location.pathname + location.hash, void 0, void 0, !1, !0) + } + }(); + page.handleAnchorClick = onclick, page.sameOrigin = sameOrigin; + var PATH_REGEXP = new RegExp(["(\\\\.)", "([\\/.])?(?:(?:\\:(\\w+)(?:\\(((?:\\\\.|[^()])+)\\))?|\\(((?:\\\\.|[^()])+)\\))([+*?])?|(\\*))"].join("|"), "g"), + isarray = Array.isArray || function(arr) { + return "[object Array]" === Object.prototype.toString.call(arr) + }; + return page +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/photoplayer/plugin.js b/dashboard-ui/bower_components/emby-webcomponents/photoplayer/plugin.js index aa2366f316..137a3520e1 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/photoplayer/plugin.js +++ b/dashboard-ui/bower_components/emby-webcomponents/photoplayer/plugin.js @@ -1 +1,25 @@ -define(["browser","require","events","apphost","loading","dom","playbackManager","appRouter","appSettings","connectionManager"],function(browser,require,events,appHost,loading,dom,playbackManager,appRouter,appSettings,connectionManager){"use strict";function PhotoPlayer(){var self=this;self.name="Photo Player",self.type="mediaplayer",self.id="photoplayer",self.priority=1}return PhotoPlayer.prototype.play=function(options){return new Promise(function(resolve,reject){require(["slideshow"],function(slideshow){var index=options.startIndex||0;new slideshow({showTitle:!1,cover:!1,items:options.items,startIndex:index,interval:11e3,interactive:!0}).show(),resolve()})})},PhotoPlayer.prototype.canPlayMediaType=function(mediaType){return"photo"===(mediaType||"").toLowerCase()},PhotoPlayer}); \ No newline at end of file +define(["browser", "require", "events", "apphost", "loading", "dom", "playbackManager", "appRouter", "appSettings", "connectionManager"], function(browser, require, events, appHost, loading, dom, playbackManager, appRouter, appSettings, connectionManager) { + "use strict"; + + function PhotoPlayer() { + var self = this; + self.name = "Photo Player", self.type = "mediaplayer", self.id = "photoplayer", self.priority = 1 + } + return PhotoPlayer.prototype.play = function(options) { + return new Promise(function(resolve, reject) { + require(["slideshow"], function(slideshow) { + var index = options.startIndex || 0; + new slideshow({ + showTitle: !1, + cover: !1, + items: options.items, + startIndex: index, + interval: 11e3, + interactive: !0 + }).show(), resolve() + }) + }) + }, PhotoPlayer.prototype.canPlayMediaType = function(mediaType) { + return "photo" === (mediaType || "").toLowerCase() + }, PhotoPlayer +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/playback/autoplaydetect.js b/dashboard-ui/bower_components/emby-webcomponents/playback/autoplaydetect.js index 93781cce4b..63b24cfeeb 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/playback/autoplaydetect.js +++ b/dashboard-ui/bower_components/emby-webcomponents/playback/autoplaydetect.js @@ -1 +1,28 @@ -define([],function(){"use strict";function supportsHtmlMediaAutoplay(){return new Promise(function(resolve,reject){var timeout,elem=document.createElement("video"),elemStyle=elem.style;if(!("autoplay"in elem))return void reject();elemStyle.position="absolute",elemStyle.height=0,elemStyle.width=0,elem.setAttribute("autoplay","autoplay"),elem.style.display="none",document.body.appendChild(elem);var testAutoplay=function(arg){clearTimeout(timeout),elem.removeEventListener("playing",testAutoplay),elem.removeEventListener("play",testAutoplay);var supported=arg&&"playing"===arg.type||arg&&"play"===arg.type||0!==elem.currentTime;elem.parentNode.removeChild(elem),supported?resolve():reject()};elem.addEventListener("play",testAutoplay),elem.addEventListener("playing",testAutoplay);try{elem.src="data:video/mp4;base64,AAAAHGZ0eXBtcDQyAAAAAG1wNDJpc29tYXZjMQAAAz5tb292AAAAbG12aGQAAAAAzaNacc2jWnEAAV+QAAFfkAABAAABAAAAAAAAAAAAAAAAAQAAAAAAAAAAAAAAAAAAAAEAAAAAAAAAAAAAAAAAAEAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAACAAAAGGlvZHMAAAAAEICAgAcAT////3//AAACQ3RyYWsAAABcdGtoZAAAAAHNo1pxzaNacQAAAAEAAAAAAAFfkAAAAAAAAAAAAAAAAAAAAAAAAQAAAAAAAAAAAAAAAAAAAAEAAAAAAAAAAAAAAAAAAEAAAAAAEAAAABAAAAAAAd9tZGlhAAAAIG1kaGQAAAAAzaNacc2jWnEAAV+QAAFfkFXEAAAAAAAhaGRscgAAAAAAAAAAdmlkZQAAAAAAAAAAAAAAAAAAAAGWbWluZgAAABR2bWhkAAAAAQAAAAAAAAAAAAAAJGRpbmYAAAAcZHJlZgAAAAAAAAABAAAADHVybCAAAAABAAABVnN0YmwAAACpc3RzZAAAAAAAAAABAAAAmWF2YzEAAAAAAAAAAQAAAAAAAAAAAAAAAAAAAAAAEAAQAEgAAABIAAAAAAAAAAEOSlZUL0FWQyBDb2RpbmcAAAAAAAAAAAAAAAAAAAAAAAAY//8AAAAxYXZjQwH0AAr/4QAZZ/QACq609NQYBBkAAAMAAQAAAwAKjxImoAEABWjOAa8gAAAAEmNvbHJuY2xjAAYAAQAGAAAAGHN0dHMAAAAAAAAAAQAAAAUAAEZQAAAAKHN0c3oAAAAAAAAAAAAAAAUAAAIqAAAACAAAAAgAAAAIAAAACAAAAChzdHNjAAAAAAAAAAIAAAABAAAABAAAAAEAAAACAAAAAQAAAAEAAAAYc3RjbwAAAAAAAAACAAADYgAABaQAAAAUc3RzcwAAAAAAAAABAAAAAQAAABFzZHRwAAAAAAREREREAAAAb3VkdGEAAABnbWV0YQAAAAAAAAAhaGRscgAAAAAAAAAAbWRpcgAAAAAAAAAAAAAAAAAAAAA6aWxzdAAAADKpdG9vAAAAKmRhdGEAAAABAAAAAEhhbmRCcmFrZSAwLjkuOCAyMDEyMDcxODAwAAACUm1kYXQAAAHkBgX/4NxF6b3m2Ui3lizYINkj7u94MjY0IC0gY29yZSAxMjAgLSBILjI2NC9NUEVHLTQgQVZDIGNvZGVjIC0gQ29weWxlZnQgMjAwMy0yMDExIC0gaHR0cDovL3d3dy52aWRlb2xhbi5vcmcveDI2NC5odG1sIC0gb3B0aW9uczogY2FiYWM9MCByZWY9MSBkZWJsb2NrPTE6MDowIGFuYWx5c2U9MHgxOjAgbWU9ZXNhIHN1Ym1lPTkgcHN5PTAgbWl4ZWRfcmVmPTAgbWVfcmFuZ2U9NCBjaHJvbWFfbWU9MSB0cmVsbGlzPTAgOHg4ZGN0PTAgY3FtPTAgZGVhZHpvbmU9MjEsMTEgZmFzdF9wc2tpcD0wIGNocm9tYV9xcF9vZmZzZXQ9MCB0aHJlYWRzPTYgc2xpY2VkX3RocmVhZHM9MCBucj0wIGRlY2ltYXRlPTEgaW50ZXJsYWNlZD0wIGJsdXJheV9jb21wYXQ9MCBjb25zdHJhaW5lZF9pbnRyYT0wIGJmcmFtZXM9MCB3ZWlnaHRwPTAga2V5aW50PTUwIGtleWludF9taW49NSBzY2VuZWN1dD00MCBpbnRyYV9yZWZyZXNoPTAgcmM9Y3FwIG1idHJlZT0wIHFwPTAAgAAAAD5liISscR8A+E4ACAACFoAAITAAAgsAAPgYCoKgoC+L4vi+KAvi+L4YfAEAACMzgABF9AAEUGUgABDJiXnf4AAAAARBmiKUAAAABEGaQpQAAAAEQZpilAAAAARBmoKU";var promise=elem.play();promise&&promise.catch&&promise.catch(reject),timeout=setTimeout(testAutoplay,500)}catch(e){return void reject()}})}return{supportsHtmlMediaAutoplay:supportsHtmlMediaAutoplay}}); \ No newline at end of file +define([], function() { + "use strict"; + + function supportsHtmlMediaAutoplay() { + return new Promise(function(resolve, reject) { + var timeout, elem = document.createElement("video"), + elemStyle = elem.style; + if (!("autoplay" in elem)) return void reject(); + elemStyle.position = "absolute", elemStyle.height = 0, elemStyle.width = 0, elem.setAttribute("autoplay", "autoplay"), elem.style.display = "none", document.body.appendChild(elem); + var testAutoplay = function(arg) { + clearTimeout(timeout), elem.removeEventListener("playing", testAutoplay), elem.removeEventListener("play", testAutoplay); + var supported = arg && "playing" === arg.type || arg && "play" === arg.type || 0 !== elem.currentTime; + elem.parentNode.removeChild(elem), supported ? resolve() : reject() + }; + elem.addEventListener("play", testAutoplay), elem.addEventListener("playing", testAutoplay); + try { + elem.src = "data:video/mp4;base64,AAAAHGZ0eXBtcDQyAAAAAG1wNDJpc29tYXZjMQAAAz5tb292AAAAbG12aGQAAAAAzaNacc2jWnEAAV+QAAFfkAABAAABAAAAAAAAAAAAAAAAAQAAAAAAAAAAAAAAAAAAAAEAAAAAAAAAAAAAAAAAAEAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAACAAAAGGlvZHMAAAAAEICAgAcAT////3//AAACQ3RyYWsAAABcdGtoZAAAAAHNo1pxzaNacQAAAAEAAAAAAAFfkAAAAAAAAAAAAAAAAAAAAAAAAQAAAAAAAAAAAAAAAAAAAAEAAAAAAAAAAAAAAAAAAEAAAAAAEAAAABAAAAAAAd9tZGlhAAAAIG1kaGQAAAAAzaNacc2jWnEAAV+QAAFfkFXEAAAAAAAhaGRscgAAAAAAAAAAdmlkZQAAAAAAAAAAAAAAAAAAAAGWbWluZgAAABR2bWhkAAAAAQAAAAAAAAAAAAAAJGRpbmYAAAAcZHJlZgAAAAAAAAABAAAADHVybCAAAAABAAABVnN0YmwAAACpc3RzZAAAAAAAAAABAAAAmWF2YzEAAAAAAAAAAQAAAAAAAAAAAAAAAAAAAAAAEAAQAEgAAABIAAAAAAAAAAEOSlZUL0FWQyBDb2RpbmcAAAAAAAAAAAAAAAAAAAAAAAAY//8AAAAxYXZjQwH0AAr/4QAZZ/QACq609NQYBBkAAAMAAQAAAwAKjxImoAEABWjOAa8gAAAAEmNvbHJuY2xjAAYAAQAGAAAAGHN0dHMAAAAAAAAAAQAAAAUAAEZQAAAAKHN0c3oAAAAAAAAAAAAAAAUAAAIqAAAACAAAAAgAAAAIAAAACAAAAChzdHNjAAAAAAAAAAIAAAABAAAABAAAAAEAAAACAAAAAQAAAAEAAAAYc3RjbwAAAAAAAAACAAADYgAABaQAAAAUc3RzcwAAAAAAAAABAAAAAQAAABFzZHRwAAAAAAREREREAAAAb3VkdGEAAABnbWV0YQAAAAAAAAAhaGRscgAAAAAAAAAAbWRpcgAAAAAAAAAAAAAAAAAAAAA6aWxzdAAAADKpdG9vAAAAKmRhdGEAAAABAAAAAEhhbmRCcmFrZSAwLjkuOCAyMDEyMDcxODAwAAACUm1kYXQAAAHkBgX/4NxF6b3m2Ui3lizYINkj7u94MjY0IC0gY29yZSAxMjAgLSBILjI2NC9NUEVHLTQgQVZDIGNvZGVjIC0gQ29weWxlZnQgMjAwMy0yMDExIC0gaHR0cDovL3d3dy52aWRlb2xhbi5vcmcveDI2NC5odG1sIC0gb3B0aW9uczogY2FiYWM9MCByZWY9MSBkZWJsb2NrPTE6MDowIGFuYWx5c2U9MHgxOjAgbWU9ZXNhIHN1Ym1lPTkgcHN5PTAgbWl4ZWRfcmVmPTAgbWVfcmFuZ2U9NCBjaHJvbWFfbWU9MSB0cmVsbGlzPTAgOHg4ZGN0PTAgY3FtPTAgZGVhZHpvbmU9MjEsMTEgZmFzdF9wc2tpcD0wIGNocm9tYV9xcF9vZmZzZXQ9MCB0aHJlYWRzPTYgc2xpY2VkX3RocmVhZHM9MCBucj0wIGRlY2ltYXRlPTEgaW50ZXJsYWNlZD0wIGJsdXJheV9jb21wYXQ9MCBjb25zdHJhaW5lZF9pbnRyYT0wIGJmcmFtZXM9MCB3ZWlnaHRwPTAga2V5aW50PTUwIGtleWludF9taW49NSBzY2VuZWN1dD00MCBpbnRyYV9yZWZyZXNoPTAgcmM9Y3FwIG1idHJlZT0wIHFwPTAAgAAAAD5liISscR8A+E4ACAACFoAAITAAAgsAAPgYCoKgoC+L4vi+KAvi+L4YfAEAACMzgABF9AAEUGUgABDJiXnf4AAAAARBmiKUAAAABEGaQpQAAAAEQZpilAAAAARBmoKU"; + var promise = elem.play(); + promise && promise.catch && promise.catch(reject), timeout = setTimeout(testAutoplay, 500) + } catch (e) { + return void reject() + } + }) + } + return { + supportsHtmlMediaAutoplay: supportsHtmlMediaAutoplay + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/playback/brightnessosd.js b/dashboard-ui/bower_components/emby-webcomponents/playback/brightnessosd.js index 7a2df23605..9b53743217 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/playback/brightnessosd.js +++ b/dashboard-ui/bower_components/emby-webcomponents/playback/brightnessosd.js @@ -1 +1,63 @@ -define(["events","playbackManager","dom","browser","css!./iconosd","material-icons"],function(events,playbackManager,dom,browser){"use strict";function getOsdElementHtml(){var html="";return html+='',html+='
'}function ensureOsdElement(){var elem=osdElement;elem||(enableAnimation=browser.supportsCssAnimation(),elem=document.createElement("div"),elem.classList.add("hide"),elem.classList.add("iconOsd"),elem.classList.add("iconOsd-hidden"),elem.classList.add("brightnessOsd"),elem.innerHTML=getOsdElementHtml(),iconElement=elem.querySelector("i"),progressElement=elem.querySelector(".iconOsdProgressInner"),document.body.appendChild(elem),osdElement=elem)}function onHideComplete(){this.classList.add("hide")}function showOsd(){clearHideTimeout();var elem=osdElement;dom.removeEventListener(elem,dom.whichTransitionEvent(),onHideComplete,{once:!0}),elem.classList.remove("hide"),elem.offsetWidth,requestAnimationFrame(function(){elem.classList.remove("iconOsd-hidden"),hideTimeout=setTimeout(hideOsd,3e3)})}function clearHideTimeout(){hideTimeout&&(clearTimeout(hideTimeout),hideTimeout=null)}function hideOsd(){clearHideTimeout();var elem=osdElement;elem&&(enableAnimation?(elem.offsetWidth,requestAnimationFrame(function(){elem.classList.add("iconOsd-hidden"),dom.addEventListener(elem,dom.whichTransitionEvent(),onHideComplete,{once:!0})})):onHideComplete.call(elem))}function updateElementsFromPlayer(brightness){iconElement&&(iconElement.innerHTML=brightness>=80?"":brightness>=20?"":""),progressElement&&(progressElement.style.width=(brightness||0)+"%")}function releaseCurrentPlayer(){var player=currentPlayer;player&&(events.off(player,"brightnesschange",onBrightnessChanged),events.off(player,"playbackstop",hideOsd),currentPlayer=null)}function onBrightnessChanged(e){var player=this;ensureOsdElement(),updateElementsFromPlayer(playbackManager.getBrightness(player)),showOsd()}function bindToPlayer(player){player!==currentPlayer&&(releaseCurrentPlayer(),currentPlayer=player,player&&(hideOsd(),events.on(player,"brightnesschange",onBrightnessChanged),events.on(player,"playbackstop",hideOsd)))}var currentPlayer,osdElement,iconElement,progressElement,enableAnimation,hideTimeout;events.on(playbackManager,"playerchange",function(){bindToPlayer(playbackManager.getCurrentPlayer())}),bindToPlayer(playbackManager.getCurrentPlayer())}); \ No newline at end of file +define(["events", "playbackManager", "dom", "browser", "css!./iconosd", "material-icons"], function(events, playbackManager, dom, browser) { + "use strict"; + + function getOsdElementHtml() { + var html = ""; + return html += '', html += '
' + } + + function ensureOsdElement() { + var elem = osdElement; + elem || (enableAnimation = browser.supportsCssAnimation(), elem = document.createElement("div"), elem.classList.add("hide"), elem.classList.add("iconOsd"), elem.classList.add("iconOsd-hidden"), elem.classList.add("brightnessOsd"), elem.innerHTML = getOsdElementHtml(), iconElement = elem.querySelector("i"), progressElement = elem.querySelector(".iconOsdProgressInner"), document.body.appendChild(elem), osdElement = elem) + } + + function onHideComplete() { + this.classList.add("hide") + } + + function showOsd() { + clearHideTimeout(); + var elem = osdElement; + dom.removeEventListener(elem, dom.whichTransitionEvent(), onHideComplete, { + once: !0 + }), elem.classList.remove("hide"), elem.offsetWidth, requestAnimationFrame(function() { + elem.classList.remove("iconOsd-hidden"), hideTimeout = setTimeout(hideOsd, 3e3) + }) + } + + function clearHideTimeout() { + hideTimeout && (clearTimeout(hideTimeout), hideTimeout = null) + } + + function hideOsd() { + clearHideTimeout(); + var elem = osdElement; + elem && (enableAnimation ? (elem.offsetWidth, requestAnimationFrame(function() { + elem.classList.add("iconOsd-hidden"), dom.addEventListener(elem, dom.whichTransitionEvent(), onHideComplete, { + once: !0 + }) + })) : onHideComplete.call(elem)) + } + + function updateElementsFromPlayer(brightness) { + iconElement && (iconElement.innerHTML = brightness >= 80 ? "" : brightness >= 20 ? "" : ""), progressElement && (progressElement.style.width = (brightness || 0) + "%") + } + + function releaseCurrentPlayer() { + var player = currentPlayer; + player && (events.off(player, "brightnesschange", onBrightnessChanged), events.off(player, "playbackstop", hideOsd), currentPlayer = null) + } + + function onBrightnessChanged(e) { + var player = this; + ensureOsdElement(), updateElementsFromPlayer(playbackManager.getBrightness(player)), showOsd() + } + + function bindToPlayer(player) { + player !== currentPlayer && (releaseCurrentPlayer(), currentPlayer = player, player && (hideOsd(), events.on(player, "brightnesschange", onBrightnessChanged), events.on(player, "playbackstop", hideOsd))) + } + var currentPlayer, osdElement, iconElement, progressElement, enableAnimation, hideTimeout; + events.on(playbackManager, "playerchange", function() { + bindToPlayer(playbackManager.getCurrentPlayer()) + }), bindToPlayer(playbackManager.getCurrentPlayer()) +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/playback/experimentalwarnings.js b/dashboard-ui/bower_components/emby-webcomponents/playback/experimentalwarnings.js index 4d0f61ad75..02c5c3b71a 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/playback/experimentalwarnings.js +++ b/dashboard-ui/bower_components/emby-webcomponents/playback/experimentalwarnings.js @@ -1 +1,41 @@ -define(["connectionManager","globalize","userSettings","apphost"],function(connectionManager,globalize,userSettings,appHost){"use strict";function getWeek(date){var d=new Date(Date.UTC(date.getFullYear(),date.getMonth(),date.getDate())),dayNum=d.getUTCDay()||7;d.setUTCDate(d.getUTCDate()+4-dayNum);var yearStart=new Date(Date.UTC(d.getUTCFullYear(),0,1));return Math.ceil(((d-yearStart)/864e5+1)/7)}function showMessage(text,userSettingsKey,appHostFeature){if(appHost.supports(appHostFeature))return Promise.resolve();var now=new Date;return userSettingsKey+=now.getFullYear()+"-w"+getWeek(now),"1"===userSettings.get(userSettingsKey,!1)?Promise.resolve():new Promise(function(resolve,reject){userSettings.set(userSettingsKey,"1",!1),require(["alert"],function(alert){return alert(text).then(resolve,resolve)})})}function showBlurayMessage(){return showMessage("Playback of Bluray folders in this app is experimental. Some titles may not work at all. For a better experience, consider converting to mkv video files, or use an Emby app with native Bluray folder support.","blurayexpirementalinfo","nativeblurayplayback")}function showDvdMessage(){return showMessage("Playback of Dvd folders in this app is experimental. Some titles may not work at all. For a better experience, consider converting to mkv video files, or use an Emby app with native Dvd folder support.","dvdexpirementalinfo","nativedvdplayback")}function showIsoMessage(){return showMessage("Playback of ISO files in this app is experimental. Some titles may not work at all. For a better experience, consider converting to mkv video files, or use an Emby app with native ISO support.","isoexpirementalinfo","nativeisoplayback")}function ExpirementalPlaybackWarnings(){this.name="Experimental playback warnings",this.type="preplayintercept",this.id="expirementalplaybackwarnings"}return ExpirementalPlaybackWarnings.prototype.intercept=function(options){var item=options.item;return item?"Iso"===item.VideoType?showIsoMessage():"BluRay"===item.VideoType?showBlurayMessage():"Dvd"===item.VideoType?showDvdMessage():Promise.resolve():Promise.resolve()},ExpirementalPlaybackWarnings}); \ No newline at end of file +define(["connectionManager", "globalize", "userSettings", "apphost"], function(connectionManager, globalize, userSettings, appHost) { + "use strict"; + + function getWeek(date) { + var d = new Date(Date.UTC(date.getFullYear(), date.getMonth(), date.getDate())), + dayNum = d.getUTCDay() || 7; + d.setUTCDate(d.getUTCDate() + 4 - dayNum); + var yearStart = new Date(Date.UTC(d.getUTCFullYear(), 0, 1)); + return Math.ceil(((d - yearStart) / 864e5 + 1) / 7) + } + + function showMessage(text, userSettingsKey, appHostFeature) { + if (appHost.supports(appHostFeature)) return Promise.resolve(); + var now = new Date; + return userSettingsKey += now.getFullYear() + "-w" + getWeek(now), "1" === userSettings.get(userSettingsKey, !1) ? Promise.resolve() : new Promise(function(resolve, reject) { + userSettings.set(userSettingsKey, "1", !1), require(["alert"], function(alert) { + return alert(text).then(resolve, resolve) + }) + }) + } + + function showBlurayMessage() { + return showMessage("Playback of Bluray folders in this app is experimental. Some titles may not work at all. For a better experience, consider converting to mkv video files, or use an Emby app with native Bluray folder support.", "blurayexpirementalinfo", "nativeblurayplayback") + } + + function showDvdMessage() { + return showMessage("Playback of Dvd folders in this app is experimental. Some titles may not work at all. For a better experience, consider converting to mkv video files, or use an Emby app with native Dvd folder support.", "dvdexpirementalinfo", "nativedvdplayback") + } + + function showIsoMessage() { + return showMessage("Playback of ISO files in this app is experimental. Some titles may not work at all. For a better experience, consider converting to mkv video files, or use an Emby app with native ISO support.", "isoexpirementalinfo", "nativeisoplayback") + } + + function ExpirementalPlaybackWarnings() { + this.name = "Experimental playback warnings", this.type = "preplayintercept", this.id = "expirementalplaybackwarnings" + } + return ExpirementalPlaybackWarnings.prototype.intercept = function(options) { + var item = options.item; + return item ? "Iso" === item.VideoType ? showIsoMessage() : "BluRay" === item.VideoType ? showBlurayMessage() : "Dvd" === item.VideoType ? showDvdMessage() : Promise.resolve() : Promise.resolve() + }, ExpirementalPlaybackWarnings +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/playback/mediasession.js b/dashboard-ui/bower_components/emby-webcomponents/playback/mediasession.js index e5df702922..15c6f9cc23 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/playback/mediasession.js +++ b/dashboard-ui/bower_components/emby-webcomponents/playback/mediasession.js @@ -1 +1,117 @@ -define(["playbackManager","nowPlayingHelper","events","connectionManager"],function(playbackManager,nowPlayingHelper,events,connectionManager){"use strict";function seriesImageUrl(item,options){if("Episode"!==item.Type)return null;if(options=options||{},options.type=options.type||"Primary","Primary"===options.type&&item.SeriesPrimaryImageTag)return options.tag=item.SeriesPrimaryImageTag,connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.SeriesId,options);if("Thumb"===options.type){if(item.SeriesThumbImageTag)return options.tag=item.SeriesThumbImageTag,connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.SeriesId,options);if(item.ParentThumbImageTag)return options.tag=item.ParentThumbImageTag,connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.ParentThumbItemId,options)}return null}function imageUrl(item,options){return options=options||{},options.type=options.type||"Primary",item.ImageTags&&item.ImageTags[options.type]?(options.tag=item.ImageTags[options.type],connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.Id,options)):item.AlbumId&&item.AlbumPrimaryImageTag?(options.tag=item.AlbumPrimaryImageTag,connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.AlbumId,options)):null}function pushImageUrl(item,height,list){var imageOptions={height:height},url=seriesImageUrl(item,imageOptions)||imageUrl(item,imageOptions);url&&list.push({src:url,sizes:height+"x"+height})}function getImageUrls(item){var list=[];return pushImageUrl(item,96,list),pushImageUrl(item,128,list),pushImageUrl(item,192,list),pushImageUrl(item,256,list),pushImageUrl(item,384,list),pushImageUrl(item,512,list),list}function updatePlayerState(player,state,eventName){var item=state.NowPlayingItem;if(!item)return void hideMediaControls();var playState=state.PlayState||{},parts=nowPlayingHelper.getNowPlayingNames(item),artist=1===parts.length?"":parts[0].text,title=parts[parts.length-1].text;if("Video"===item.MediaType&&parts.length>1){var temp=artist;artist=title,title=temp}var albumArtist;item.AlbumArtists&&item.AlbumArtists[0]&&(albumArtist=item.AlbumArtists[0].Name);var album=item.Album||"",itemId=item.Id,duration=parseInt(item.RunTimeTicks?item.RunTimeTicks/1e4:0),currentTime=parseInt(playState.PositionTicks?playState.PositionTicks/1e4:0),isPaused=playState.IsPaused||!1;navigator.mediaSession.metadata=new MediaMetadata({title:title,artist:artist,album:album,artwork:getImageUrls(item),albumArtist:albumArtist,currentTime:currentTime,duration:duration,paused:isPaused,itemId:itemId,mediaType:item.MediaType})}function onGeneralEvent(e){var player=this;updatePlayerState(player,playbackManager.getPlayerState(player),e.type)}function onStateChanged(e,state){updatePlayerState(this,state,"statechange")}function onPlaybackStart(e,state){updatePlayerState(this,state,e.type)}function onPlaybackStopped(e,state){hideMediaControls()}function releaseCurrentPlayer(){currentPlayer&&(events.off(currentPlayer,"playbackstart",onPlaybackStart),events.off(currentPlayer,"playbackstop",onPlaybackStopped),events.off(currentPlayer,"unpause",onGeneralEvent),events.off(currentPlayer,"pause",onGeneralEvent),events.off(currentPlayer,"statechange",onStateChanged),events.off(currentPlayer,"timeupdate",onGeneralEvent),currentPlayer=null,hideMediaControls())}function hideMediaControls(){navigator.mediaSession.metadata=null}function bindToPlayer(player){if(releaseCurrentPlayer(),player){currentPlayer=player;updatePlayerState(player,playbackManager.getPlayerState(player),"init"),events.on(currentPlayer,"playbackstart",onPlaybackStart),events.on(currentPlayer,"playbackstop",onPlaybackStopped),events.on(currentPlayer,"unpause",onGeneralEvent),events.on(currentPlayer,"pause",onGeneralEvent),events.on(currentPlayer,"statechange",onStateChanged),events.on(currentPlayer,"timeupdate",onGeneralEvent)}}function execute(name){playbackManager[name](currentPlayer)}var currentPlayer;navigator.mediaSession.setActionHandler("previoustrack",function(){execute("previousTrack")}),navigator.mediaSession.setActionHandler("nexttrack",function(){execute("nextTrack")}),navigator.mediaSession.setActionHandler("play",function(){execute("unpause")}),navigator.mediaSession.setActionHandler("pause",function(){execute("pause")}),navigator.mediaSession.setActionHandler("seekbackward",function(){execute("rewind")}),navigator.mediaSession.setActionHandler("seekforward",function(){execute("fastForward")}),events.on(playbackManager,"playerchange",function(){bindToPlayer(playbackManager.getCurrentPlayer())}),bindToPlayer(playbackManager.getCurrentPlayer())}); \ No newline at end of file +define(["playbackManager", "nowPlayingHelper", "events", "connectionManager"], function(playbackManager, nowPlayingHelper, events, connectionManager) { + "use strict"; + + function seriesImageUrl(item, options) { + if ("Episode" !== item.Type) return null; + if (options = options || {}, options.type = options.type || "Primary", "Primary" === options.type && item.SeriesPrimaryImageTag) return options.tag = item.SeriesPrimaryImageTag, connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.SeriesId, options); + if ("Thumb" === options.type) { + if (item.SeriesThumbImageTag) return options.tag = item.SeriesThumbImageTag, connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.SeriesId, options); + if (item.ParentThumbImageTag) return options.tag = item.ParentThumbImageTag, connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.ParentThumbItemId, options) + } + return null + } + + function imageUrl(item, options) { + return options = options || {}, options.type = options.type || "Primary", item.ImageTags && item.ImageTags[options.type] ? (options.tag = item.ImageTags[options.type], connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.Id, options)) : item.AlbumId && item.AlbumPrimaryImageTag ? (options.tag = item.AlbumPrimaryImageTag, connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.AlbumId, options)) : null + } + + function pushImageUrl(item, height, list) { + var imageOptions = { + height: height + }, + url = seriesImageUrl(item, imageOptions) || imageUrl(item, imageOptions); + url && list.push({ + src: url, + sizes: height + "x" + height + }) + } + + function getImageUrls(item) { + var list = []; + return pushImageUrl(item, 96, list), pushImageUrl(item, 128, list), pushImageUrl(item, 192, list), pushImageUrl(item, 256, list), pushImageUrl(item, 384, list), pushImageUrl(item, 512, list), list + } + + function updatePlayerState(player, state, eventName) { + var item = state.NowPlayingItem; + if (!item) return void hideMediaControls(); + var playState = state.PlayState || {}, + parts = nowPlayingHelper.getNowPlayingNames(item), + artist = 1 === parts.length ? "" : parts[0].text, + title = parts[parts.length - 1].text; + if ("Video" === item.MediaType && parts.length > 1) { + var temp = artist; + artist = title, title = temp + } + var albumArtist; + item.AlbumArtists && item.AlbumArtists[0] && (albumArtist = item.AlbumArtists[0].Name); + var album = item.Album || "", + itemId = item.Id, + duration = parseInt(item.RunTimeTicks ? item.RunTimeTicks / 1e4 : 0), + currentTime = parseInt(playState.PositionTicks ? playState.PositionTicks / 1e4 : 0), + isPaused = playState.IsPaused || !1; + navigator.mediaSession.metadata = new MediaMetadata({ + title: title, + artist: artist, + album: album, + artwork: getImageUrls(item), + albumArtist: albumArtist, + currentTime: currentTime, + duration: duration, + paused: isPaused, + itemId: itemId, + mediaType: item.MediaType + }) + } + + function onGeneralEvent(e) { + var player = this; + updatePlayerState(player, playbackManager.getPlayerState(player), e.type) + } + + function onStateChanged(e, state) { + updatePlayerState(this, state, "statechange") + } + + function onPlaybackStart(e, state) { + updatePlayerState(this, state, e.type) + } + + function onPlaybackStopped(e, state) { + hideMediaControls() + } + + function releaseCurrentPlayer() { + currentPlayer && (events.off(currentPlayer, "playbackstart", onPlaybackStart), events.off(currentPlayer, "playbackstop", onPlaybackStopped), events.off(currentPlayer, "unpause", onGeneralEvent), events.off(currentPlayer, "pause", onGeneralEvent), events.off(currentPlayer, "statechange", onStateChanged), events.off(currentPlayer, "timeupdate", onGeneralEvent), currentPlayer = null, hideMediaControls()) + } + + function hideMediaControls() { + navigator.mediaSession.metadata = null + } + + function bindToPlayer(player) { + if (releaseCurrentPlayer(), player) { + currentPlayer = player; + updatePlayerState(player, playbackManager.getPlayerState(player), "init"), events.on(currentPlayer, "playbackstart", onPlaybackStart), events.on(currentPlayer, "playbackstop", onPlaybackStopped), events.on(currentPlayer, "unpause", onGeneralEvent), events.on(currentPlayer, "pause", onGeneralEvent), events.on(currentPlayer, "statechange", onStateChanged), events.on(currentPlayer, "timeupdate", onGeneralEvent) + } + } + + function execute(name) { + playbackManager[name](currentPlayer) + } + var currentPlayer; + navigator.mediaSession.setActionHandler("previoustrack", function() { + execute("previousTrack") + }), navigator.mediaSession.setActionHandler("nexttrack", function() { + execute("nextTrack") + }), navigator.mediaSession.setActionHandler("play", function() { + execute("unpause") + }), navigator.mediaSession.setActionHandler("pause", function() { + execute("pause") + }), navigator.mediaSession.setActionHandler("seekbackward", function() { + execute("rewind") + }), navigator.mediaSession.setActionHandler("seekforward", function() { + execute("fastForward") + }), events.on(playbackManager, "playerchange", function() { + bindToPlayer(playbackManager.getCurrentPlayer()) + }), bindToPlayer(playbackManager.getCurrentPlayer()) +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/playback/nowplayinghelper.js b/dashboard-ui/bower_components/emby-webcomponents/playback/nowplayinghelper.js index 56781729c1..0e79788291 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/playback/nowplayinghelper.js +++ b/dashboard-ui/bower_components/emby-webcomponents/playback/nowplayinghelper.js @@ -1 +1,40 @@ -define([],function(){"use strict";function getNowPlayingNames(nowPlayingItem,includeNonNameInfo){var topItem=nowPlayingItem,bottomItem=null,topText=nowPlayingItem.Name;nowPlayingItem.AlbumId&&"Audio"===nowPlayingItem.MediaType&&(topItem={Id:nowPlayingItem.AlbumId,Name:nowPlayingItem.Album,Type:"MusicAlbum",IsFolder:!0}),"Video"===nowPlayingItem.MediaType&&(null!=nowPlayingItem.IndexNumber&&(topText=nowPlayingItem.IndexNumber+" - "+topText),null!=nowPlayingItem.ParentIndexNumber&&(topText=nowPlayingItem.ParentIndexNumber+"."+topText));var bottomText="";nowPlayingItem.ArtistItems&&nowPlayingItem.ArtistItems.length?(bottomItem={Id:nowPlayingItem.ArtistItems[0].Id,Name:nowPlayingItem.ArtistItems[0].Name,Type:"MusicArtist",IsFolder:!0},bottomText=nowPlayingItem.ArtistItems.map(function(a){return a.Name}).join(", ")):nowPlayingItem.Artists&&nowPlayingItem.Artists.length?bottomText=nowPlayingItem.Artists.join(", "):nowPlayingItem.SeriesName||nowPlayingItem.Album?(bottomText=topText,topText=nowPlayingItem.SeriesName||nowPlayingItem.Album,bottomItem=topItem,topItem=nowPlayingItem.SeriesId?{Id:nowPlayingItem.SeriesId,Name:nowPlayingItem.SeriesName,Type:"Series",IsFolder:!0}:null):nowPlayingItem.ProductionYear&&!1!==includeNonNameInfo&&(bottomText=nowPlayingItem.ProductionYear);var list=[];return list.push({text:topText,item:topItem}),bottomText&&list.push({text:bottomText,item:bottomItem}),list}return{getNowPlayingNames:getNowPlayingNames}}); \ No newline at end of file +define([], function() { + "use strict"; + + function getNowPlayingNames(nowPlayingItem, includeNonNameInfo) { + var topItem = nowPlayingItem, + bottomItem = null, + topText = nowPlayingItem.Name; + nowPlayingItem.AlbumId && "Audio" === nowPlayingItem.MediaType && (topItem = { + Id: nowPlayingItem.AlbumId, + Name: nowPlayingItem.Album, + Type: "MusicAlbum", + IsFolder: !0 + }), "Video" === nowPlayingItem.MediaType && (null != nowPlayingItem.IndexNumber && (topText = nowPlayingItem.IndexNumber + " - " + topText), null != nowPlayingItem.ParentIndexNumber && (topText = nowPlayingItem.ParentIndexNumber + "." + topText)); + var bottomText = ""; + nowPlayingItem.ArtistItems && nowPlayingItem.ArtistItems.length ? (bottomItem = { + Id: nowPlayingItem.ArtistItems[0].Id, + Name: nowPlayingItem.ArtistItems[0].Name, + Type: "MusicArtist", + IsFolder: !0 + }, bottomText = nowPlayingItem.ArtistItems.map(function(a) { + return a.Name + }).join(", ")) : nowPlayingItem.Artists && nowPlayingItem.Artists.length ? bottomText = nowPlayingItem.Artists.join(", ") : nowPlayingItem.SeriesName || nowPlayingItem.Album ? (bottomText = topText, topText = nowPlayingItem.SeriesName || nowPlayingItem.Album, bottomItem = topItem, topItem = nowPlayingItem.SeriesId ? { + Id: nowPlayingItem.SeriesId, + Name: nowPlayingItem.SeriesName, + Type: "Series", + IsFolder: !0 + } : null) : nowPlayingItem.ProductionYear && !1 !== includeNonNameInfo && (bottomText = nowPlayingItem.ProductionYear); + var list = []; + return list.push({ + text: topText, + item: topItem + }), bottomText && list.push({ + text: bottomText, + item: bottomItem + }), list + } + return { + getNowPlayingNames: getNowPlayingNames + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/playback/playaccessvalidation.js b/dashboard-ui/bower_components/emby-webcomponents/playback/playaccessvalidation.js index 3bff678e4c..30a687d771 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/playback/playaccessvalidation.js +++ b/dashboard-ui/bower_components/emby-webcomponents/playback/playaccessvalidation.js @@ -1 +1,29 @@ -define(["connectionManager","globalize"],function(connectionManager,globalize){"use strict";function getRequirePromise(deps){return new Promise(function(resolve,reject){require(deps,resolve)})}function showErrorMessage(){return getRequirePromise(["alert"]).then(function(alert){return alert(globalize.translate("sharedcomponents#MessagePlayAccessRestricted")).then(function(){return Promise.reject()})})}function PlayAccessValidation(){this.name="Playback validation",this.type="preplayintercept",this.id="playaccessvalidation",this.order=-2}return PlayAccessValidation.prototype.intercept=function(options){var item=options.item;if(!item)return Promise.resolve();var serverId=item.ServerId;return serverId?connectionManager.getApiClient(serverId).getCurrentUser().then(function(user){return user.Policy.EnableMediaPlayback?Promise.resolve():options.fullscreen?showErrorMessage():Promise.reject()}):Promise.resolve()},PlayAccessValidation}); \ No newline at end of file +define(["connectionManager", "globalize"], function(connectionManager, globalize) { + "use strict"; + + function getRequirePromise(deps) { + return new Promise(function(resolve, reject) { + require(deps, resolve) + }) + } + + function showErrorMessage() { + return getRequirePromise(["alert"]).then(function(alert) { + return alert(globalize.translate("sharedcomponents#MessagePlayAccessRestricted")).then(function() { + return Promise.reject() + }) + }) + } + + function PlayAccessValidation() { + this.name = "Playback validation", this.type = "preplayintercept", this.id = "playaccessvalidation", this.order = -2 + } + return PlayAccessValidation.prototype.intercept = function(options) { + var item = options.item; + if (!item) return Promise.resolve(); + var serverId = item.ServerId; + return serverId ? connectionManager.getApiClient(serverId).getCurrentUser().then(function(user) { + return user.Policy.EnableMediaPlayback ? Promise.resolve() : options.fullscreen ? showErrorMessage() : Promise.reject() + }) : Promise.resolve() + }, PlayAccessValidation +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/playback/playbackmanager.js b/dashboard-ui/bower_components/emby-webcomponents/playback/playbackmanager.js index 47731ed941..a321efc36b 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/playback/playbackmanager.js +++ b/dashboard-ui/bower_components/emby-webcomponents/playback/playbackmanager.js @@ -1,3 +1,1552 @@ -define(["events","datetime","appSettings","itemHelper","pluginManager","playQueueManager","userSettings","globalize","connectionManager","loading","apphost","fullscreenManager"],function(events,datetime,appSettings,itemHelper,pluginManager,PlayQueueManager,userSettings,globalize,connectionManager,loading,apphost,fullscreenManager){"use strict";function enableLocalPlaylistManagement(player){return!player.getPlaylist&&!!player.isLocalPlayer}function bindToFullscreenChange(player){events.on(fullscreenManager,"fullscreenchange",function(){events.trigger(player,"fullscreenchange")})}function triggerPlayerChange(playbackManagerInstance,newPlayer,newTarget,previousPlayer,previousTargetInfo){(newPlayer||previousPlayer)&&(newTarget&&previousTargetInfo&&newTarget.id===previousTargetInfo.id||events.trigger(playbackManagerInstance,"playerchange",[newPlayer,newTarget,previousPlayer]))}function reportPlayback(playbackManagerInstance,state,player,reportPlaylist,serverId,method,progressEventName){if(serverId){var info=Object.assign({},state.PlayState);info.ItemId=state.NowPlayingItem.Id,progressEventName&&(info.EventName=progressEventName),reportPlaylist&&addPlaylistToPlaybackReport(playbackManagerInstance,info,player,serverId);connectionManager.getApiClient(serverId)[method](info)}}function getPlaylistSync(playbackManagerInstance,player){return player=player||playbackManagerInstance._currentPlayer,player&&!enableLocalPlaylistManagement(player)?player.getPlaylistSync():playbackManagerInstance._playQueueManager.getPlaylist()}function addPlaylistToPlaybackReport(playbackManagerInstance,info,player,serverId){info.NowPlayingQueue=getPlaylistSync(playbackManagerInstance,player).map(function(i){var itemInfo={Id:i.Id,PlaylistItemId:i.PlaylistItemId};return i.ServerId!==serverId&&(itemInfo.ServerId=i.ServerId),itemInfo})}function normalizeName(t){return t.toLowerCase().replace(" ","")}function getItemsForPlayback(serverId,query){var apiClient=connectionManager.getApiClient(serverId);if(query.Ids&&1===query.Ids.split(",").length){var itemId=query.Ids.split(",");return apiClient.getItem(apiClient.getCurrentUserId(),itemId).then(function(item){return{Items:[item],TotalRecordCount:1}})}return query.Limit=query.Limit||300,query.Fields="Chapters",query.ExcludeLocationTypes="Virtual",query.EnableTotalRecordCount=!1,query.CollapseBoxSetItems=!1,apiClient.getItems(apiClient.getCurrentUserId(),query)}function createStreamInfoFromUrlItem(item){return{url:item.Url||item.Path,playMethod:"DirectPlay",item:item,textTracks:[],mediaType:item.MediaType}}function mergePlaybackQueries(obj1,obj2){var query=Object.assign(obj1,obj2),filters=query.Filters?query.Filters.split(","):[];return-1===filters.indexOf("IsNotFolder")&&filters.push("IsNotFolder"),query.Filters=filters.join(","),query}function backdropImageUrl(apiClient,item,options){return options=options||{},options.type=options.type||"Backdrop",options.maxWidth||options.width||options.maxHeight||options.height||(options.quality=100),item.BackdropImageTags&&item.BackdropImageTags.length?(options.tag=item.BackdropImageTags[0],apiClient.getScaledImageUrl(item.Id,options)):item.ParentBackdropImageTags&&item.ParentBackdropImageTags.length?(options.tag=item.ParentBackdropImageTags[0],apiClient.getScaledImageUrl(item.ParentBackdropItemId,options)):null}function getMimeType(type,container){if(container=(container||"").toLowerCase(),"audio"===type){if("opus"===container)return"audio/ogg";if("webma"===container)return"audio/webm";if("m4a"===container)return"audio/mp4"}else if("video"===type){if("mkv"===container)return"video/x-matroska";if("m4v"===container)return"video/mp4";if("mov"===container)return"video/quicktime";if("mpg"===container)return"video/mpeg";if("flv"===container)return"video/x-flv"}return type+"/"+container}function getParam(name,url){name=name.replace(/[\[]/,"\\[").replace(/[\]]/,"\\]");var regexS="[\\?&]"+name+"=([^&#]*)",regex=new RegExp(regexS,"i"),results=regex.exec(url);return null==results?"":decodeURIComponent(results[1].replace(/\+/g," "))}function isAutomaticPlayer(player){return!!player.isLocalPlayer}function getAutomaticPlayers(instance,forceLocalPlayer){if(!forceLocalPlayer){var player=instance._currentPlayer;if(player&&!isAutomaticPlayer(player))return[player]}return instance.getPlayers().filter(isAutomaticPlayer)}function isServerItem(item){return!!item.Id}function enableIntros(item){return"Video"===item.MediaType&&("TvChannel"!==item.Type&&("InProgress"!==item.Status&&isServerItem(item)))}function getIntros(firstItem,apiClient,options){return options.startPositionTicks||options.startIndex||!1===options.fullscreen||!enableIntros(firstItem)||!userSettings.enableCinemaMode()?Promise.resolve({Items:[]}):apiClient.getIntros(firstItem.Id).then(function(result){return result},function(err){return Promise.resolve({Items:[]})})}function getAudioMaxValues(deviceProfile){var maxAudioSampleRate=null,maxAudioBitDepth=null,maxAudioBitrate=null;return deviceProfile.CodecProfiles.map(function(codecProfile){"Audio"===codecProfile.Type&&(codecProfile.Conditions||[]).map(function(condition){"LessThanEqual"===condition.Condition&&"AudioBitDepth"===condition.Property&&(maxAudioBitDepth=condition.Value),"LessThanEqual"===condition.Condition&&"AudioSampleRate"===condition.Property&&(maxAudioSampleRate=condition.Value),"LessThanEqual"===condition.Condition&&"AudioBitrate"===condition.Property&&(maxAudioBitrate=condition.Value)})}),{maxAudioSampleRate:maxAudioSampleRate,maxAudioBitDepth:maxAudioBitDepth,maxAudioBitrate:maxAudioBitrate}}function getAudioStreamUrl(item,transcodingProfile,directPlayContainers,maxBitrate,apiClient,maxAudioSampleRate,maxAudioBitDepth,maxAudioBitrate,startPosition){var url="Audio/"+item.Id+"/universal";return startingPlaySession++,apiClient.getUrl(url,{UserId:apiClient.getCurrentUserId(),DeviceId:apiClient.deviceId(),MaxStreamingBitrate:maxAudioBitrate||maxBitrate,Container:directPlayContainers,TranscodingContainer:transcodingProfile.Container||null,TranscodingProtocol:transcodingProfile.Protocol||null,AudioCodec:transcodingProfile.AudioCodec,MaxAudioSampleRate:maxAudioSampleRate,MaxAudioBitDepth:maxAudioBitDepth,api_key:apiClient.accessToken(),PlaySessionId:startingPlaySession,StartTimeTicks:startPosition||0,EnableRedirection:!0,EnableRemoteMedia:apphost.supports("remoteaudio")})}function getAudioStreamUrlFromDeviceProfile(item,deviceProfile,maxBitrate,apiClient,startPosition){var transcodingProfile=deviceProfile.TranscodingProfiles.filter(function(p){return"Audio"===p.Type&&"Streaming"===p.Context})[0],directPlayContainers="";deviceProfile.DirectPlayProfiles.map(function(p){"Audio"===p.Type&&(directPlayContainers?directPlayContainers+=","+p.Container:directPlayContainers=p.Container,p.AudioCodec&&(directPlayContainers+="|"+p.AudioCodec))});var maxValues=getAudioMaxValues(deviceProfile);return getAudioStreamUrl(item,transcodingProfile,directPlayContainers,maxBitrate,apiClient,maxValues.maxAudioSampleRate,maxValues.maxAudioBitDepth,maxValues.maxAudioBitrate,startPosition)}function getStreamUrls(items,deviceProfile,maxBitrate,apiClient,startPosition){var audioTranscodingProfile=deviceProfile.TranscodingProfiles.filter(function(p){return"Audio"===p.Type&&"Streaming"===p.Context})[0],audioDirectPlayContainers="";deviceProfile.DirectPlayProfiles.map(function(p){"Audio"===p.Type&&(audioDirectPlayContainers?audioDirectPlayContainers+=","+p.Container:audioDirectPlayContainers=p.Container,p.AudioCodec&&(audioDirectPlayContainers+="|"+p.AudioCodec))});for(var maxValues=getAudioMaxValues(deviceProfile),streamUrls=[],i=0,length=items.length;i0}function getSavedMaxStreamingBitrate(apiClient,mediaType){apiClient||(apiClient=connectionManager.currentApiClient());var endpointInfo=apiClient.getSavedEndpointInfo()||{};return appSettings.maxStreamingBitrate(endpointInfo.IsInNetwork,mediaType)}function getDeliveryMethod(subtitleStream){return subtitleStream.DeliveryMethod?subtitleStream.DeliveryMethod:subtitleStream.IsExternal?"External":"Embed"}function canPlayerSeek(player){if(!player)throw new Error("player cannot be null");return-1!==(getPlayerData(player).streamInfo.url||"").toLowerCase().indexOf(".m3u8")||(player.seekable?player.seekable():!("Transcode"===self.playMethod(player))&&player.duration())}function changeStream(player,ticks,params){if(canPlayerSeek(player)&&null==params)return void player.currentTime(parseInt(ticks/1e4));params=params||{};var liveStreamId=getPlayerData(player).streamInfo.liveStreamId,lastMediaInfoQuery=getPlayerData(player).streamInfo.lastMediaInfoQuery,playSessionId=self.playSessionId(player),currentItem=self.currentItem(player);player.getDeviceProfile(currentItem,{isRetry:!1===params.EnableDirectPlay}).then(function(deviceProfile){var audioStreamIndex=null==params.AudioStreamIndex?getPlayerData(player).audioStreamIndex:params.AudioStreamIndex,subtitleStreamIndex=null==params.SubtitleStreamIndex?getPlayerData(player).subtitleStreamIndex:params.SubtitleStreamIndex,currentMediaSource=self.currentMediaSource(player),apiClient=connectionManager.getApiClient(currentItem.ServerId);ticks&&(ticks=parseInt(ticks));var maxBitrate=params.MaxStreamingBitrate||self.getMaxStreamingBitrate(player),currentPlayOptions=currentItem.playOptions||{};getPlaybackInfo(player,apiClient,currentItem,deviceProfile,maxBitrate,ticks,!0,currentMediaSource.Id,audioStreamIndex,subtitleStreamIndex,liveStreamId,params.EnableDirectPlay,params.EnableDirectStream,params.AllowVideoStreamCopy,params.AllowAudioStreamCopy).then(function(result){if(validatePlaybackInfoResult(self,result)){currentMediaSource=result.MediaSources[0];var streamInfo=createStreamInfo(apiClient,currentItem.MediaType,currentItem,currentMediaSource,ticks);if(streamInfo.fullscreen=currentPlayOptions.fullscreen,streamInfo.lastMediaInfoQuery=lastMediaInfoQuery,!streamInfo.url)return void showPlaybackInfoErrorMessage(self,"NoCompatibleStream",!0);getPlayerData(player).subtitleStreamIndex=subtitleStreamIndex,getPlayerData(player).audioStreamIndex=audioStreamIndex,getPlayerData(player).maxStreamingBitrate=maxBitrate,changeStreamToUrl(apiClient,player,playSessionId,streamInfo)}})})}function changeStreamToUrl(apiClient,player,playSessionId,streamInfo,newPositionTicks){var playerData=getPlayerData(player);playerData.isChangingStream=!0,playerData.streamInfo&&playSessionId?apiClient.stopActiveEncodings(playSessionId).then(function(){var afterSetSrc=function(){apiClient.stopActiveEncodings(playSessionId)};setSrcIntoPlayer(apiClient,player,streamInfo).then(afterSetSrc,afterSetSrc)}):setSrcIntoPlayer(apiClient,player,streamInfo)}function setSrcIntoPlayer(apiClient,player,streamInfo){return player.play(streamInfo).then(function(){var playerData=getPlayerData(player);playerData.isChangingStream=!1,playerData.streamInfo=streamInfo,streamInfo.started=!0,streamInfo.ended=!1,sendProgressUpdate(player,"timeupdate")},function(e){getPlayerData(player).isChangingStream=!1,onPlaybackError.call(player,e,{type:"mediadecodeerror",streamInfo:streamInfo})})}function translateItemsForPlayback(items,options){var promise,firstItem=items[0],serverId=firstItem.ServerId,queryOptions=options.queryOptions||{};return"Program"===firstItem.Type?promise=getItemsForPlayback(serverId,{Ids:firstItem.ChannelId}):"Playlist"===firstItem.Type?promise=getItemsForPlayback(serverId,{ParentId:firstItem.Id,SortBy:options.shuffle?"Random":null}):"MusicArtist"===firstItem.Type?promise=getItemsForPlayback(serverId,{ArtistIds:firstItem.Id,Filters:"IsNotFolder",Recursive:!0,SortBy:options.shuffle?"Random":"SortName",MediaTypes:"Audio"}):"Photo"===firstItem.MediaType?promise=getItemsForPlayback(serverId,{ParentId:firstItem.ParentId,Filters:"IsNotFolder",Recursive:!1,SortBy:options.shuffle?"Random":"SortName",MediaTypes:"Photo,Video",Limit:5e3}).then(function(result){var items=result.Items,index=items.map(function(i){return i.Id}).indexOf(firstItem.Id);return-1===index&&(index=0),options.startIndex=index,Promise.resolve(result)}):"PhotoAlbum"===firstItem.Type?promise=getItemsForPlayback(serverId,{ParentId:firstItem.Id,Filters:"IsNotFolder",Recursive:!1,SortBy:options.shuffle?"Random":"SortName",MediaTypes:"Photo,Video",Limit:1e3}):"MusicGenre"===firstItem.Type?promise=getItemsForPlayback(serverId,{GenreIds:firstItem.Id,Filters:"IsNotFolder",Recursive:!0,SortBy:options.shuffle?"Random":"SortName",MediaTypes:"Audio"}):firstItem.IsFolder?promise=getItemsForPlayback(serverId,mergePlaybackQueries({ParentId:firstItem.Id,Filters:"IsNotFolder",Recursive:!0,SortBy:options.shuffle?"Random":-1===["BoxSet"].indexOf(firstItem.Type)?"SortName":null,MediaTypes:"Audio,Video"},queryOptions)):"Episode"===firstItem.Type&&1===items.length&&!1!==getPlayer(firstItem,options).supportsProgress&&(promise=new Promise(function(resolve,reject){var apiClient=connectionManager.getApiClient(firstItem.ServerId);apiClient.getCurrentUser().then(function(user){if(!user.Configuration.EnableNextEpisodeAutoPlay||!firstItem.SeriesId)return void resolve(null);apiClient.getEpisodes(firstItem.SeriesId,{IsVirtualUnaired:!1,IsMissing:!1,UserId:apiClient.getCurrentUserId(),Fields:"Chapters"}).then(function(episodesResult){var foundItem=!1;episodesResult.Items=episodesResult.Items.filter(function(e){return!!foundItem||e.Id===firstItem.Id&&(foundItem=!0,!0)}),episodesResult.TotalRecordCount=episodesResult.Items.length,resolve(episodesResult)},reject)})})),promise?promise.then(function(result){return result?result.Items:items}):Promise.resolve(items)}function getPlayerData(player){if(!player)throw new Error("player cannot be null");if(!player.name)throw new Error("player name cannot be null");var state=playerStates[player.name];return state||(playerStates[player.name]={},state=playerStates[player.name]),player}function getCurrentTicks(player){if(!player)throw new Error("player cannot be null");var playerTime=Math.floor(1e4*(player||self._currentPlayer).currentTime());return getPlayerData(player).streamInfo&&(playerTime+=getPlayerData(player).streamInfo.transcodingOffsetTicks||0),playerTime}function playPhotos(items,options,user){var playStartIndex=options.startIndex||0,player=getPlayer(items[playStartIndex],options);return loading.hide(),options.items=items,player.play(options)}function playWithIntros(items,options,user){var playStartIndex=options.startIndex||0,firstItem=items[playStartIndex];if(firstItem||(playStartIndex=0,firstItem=items[playStartIndex]),!firstItem)return showPlaybackInfoErrorMessage(self,"NoCompatibleStream",!1),Promise.reject();if("Photo"===firstItem.MediaType)return playPhotos(items,options,user);var apiClient=connectionManager.getApiClient(firstItem.ServerId);return getIntros(firstItem,apiClient,options).then(function(introsResult){var introPlayOptions,introItems=introsResult.Items;return firstItem.playOptions=truncatePlayOptions(options),introPlayOptions=introItems.length?{fullscreen:firstItem.playOptions.fullscreen}:firstItem.playOptions,items=introItems.concat(items),introPlayOptions.items=items,introPlayOptions.startIndex=playStartIndex,playInternal(items[playStartIndex],introPlayOptions,function(){self._playQueueManager.setPlaylist(items),setPlaylistState(items[playStartIndex].PlaylistItemId,playStartIndex),loading.hide()})})}function setPlaylistState(playlistItemId,index){isNaN(index)||self._playQueueManager.setPlaylistState(playlistItemId,index)}function playInternal(item,playOptions,onPlaybackStartedFn){return item.IsPlaceHolder?(loading.hide(),showPlaybackInfoErrorMessage(self,"PlaceHolder",!0),Promise.reject()):(normalizePlayOptions(playOptions),playOptions.isFirstItem?playOptions.isFirstItem=!1:playOptions.isFirstItem=!0,runInterceptors(item,playOptions).then(function(){playOptions.fullscreen&&loading.show();var mediaType=item.MediaType,onBitrateDetectionFailure=function(){return playAfterBitrateDetect(getSavedMaxStreamingBitrate(connectionManager.getApiClient(item.ServerId),mediaType),item,playOptions,onPlaybackStartedFn)};if(!isServerItem(item)||itemHelper.isLocalItem(item))return onBitrateDetectionFailure();var apiClient=connectionManager.getApiClient(item.ServerId);apiClient.getEndpointInfo().then(function(endpointInfo){if(("Video"===mediaType||"Audio"===mediaType)&&appSettings.enableAutomaticBitrateDetection(endpointInfo.IsInNetwork,mediaType))return apiClient.detectBitrate().then(function(bitrate){return appSettings.maxStreamingBitrate(endpointInfo.IsInNetwork,mediaType,bitrate),playAfterBitrateDetect(bitrate,item,playOptions,onPlaybackStartedFn)},onBitrateDetectionFailure);onBitrateDetectionFailure()},onBitrateDetectionFailure)},onInterceptorRejection))}function onInterceptorRejection(){var player=self._currentPlayer;return player&&(destroyPlayer(player),removeCurrentPlayer(player)),events.trigger(self,"playbackcancelled"),Promise.reject()}function destroyPlayer(player){player.destroy()}function runInterceptors(item,playOptions){return new Promise(function(resolve,reject){var interceptors=pluginManager.ofType("preplayintercept");if(interceptors.sort(function(a,b){return(a.order||0)-(b.order||0)}),!interceptors.length)return void resolve();loading.hide();var options=Object.assign({},playOptions);options.mediaType=item.MediaType,options.item=item,runNextPrePlay(interceptors,0,options,resolve,reject)})}function runNextPrePlay(interceptors,index,options,resolve,reject){if(index>=interceptors.length)return void resolve();interceptors[index].intercept(options).then(function(){runNextPrePlay(interceptors,index+1,options,resolve,reject)},reject)}function sendPlaybackListToPlayer(player,items,deviceProfile,maxBitrate,apiClient,startPositionTicks,mediaSourceId,audioStreamIndex,subtitleStreamIndex,startIndex){return setStreamUrls(items,deviceProfile,maxBitrate,apiClient,startPositionTicks).then(function(){return loading.hide(),player.play({items:items,startPositionTicks:startPositionTicks||0,mediaSourceId:mediaSourceId,audioStreamIndex:audioStreamIndex,subtitleStreamIndex:subtitleStreamIndex,startIndex:startIndex})})}function playAfterBitrateDetect(maxBitrate,item,playOptions,onPlaybackStartedFn){var promise,startPosition=playOptions.startPositionTicks,player=getPlayer(item,playOptions),activePlayer=self._currentPlayer;return activePlayer?(self._playNextAfterEnded=!1,promise=onPlaybackChanging(activePlayer,player,item)):promise=Promise.resolve(),isServerItem(item)&&"Game"!==item.MediaType&&"Book"!==item.MediaType?Promise.all([promise,player.getDeviceProfile(item)]).then(function(responses){var deviceProfile=responses[1],apiClient=connectionManager.getApiClient(item.ServerId),mediaSourceId=playOptions.mediaSourceId,audioStreamIndex=playOptions.audioStreamIndex,subtitleStreamIndex=playOptions.subtitleStreamIndex;return player&&!enableLocalPlaylistManagement(player)?sendPlaybackListToPlayer(player,playOptions.items,deviceProfile,maxBitrate,apiClient,startPosition,mediaSourceId,audioStreamIndex,subtitleStreamIndex,playOptions.startIndex):(playOptions.items=null,getPlaybackMediaSource(player,apiClient,deviceProfile,maxBitrate,item,startPosition,mediaSourceId,audioStreamIndex,subtitleStreamIndex).then(function(mediaSource){var streamInfo=createStreamInfo(apiClient,item.MediaType,item,mediaSource,startPosition);return streamInfo.fullscreen=playOptions.fullscreen,getPlayerData(player).isChangingStream=!1,getPlayerData(player).maxStreamingBitrate=maxBitrate,player.play(streamInfo).then(function(){loading.hide(),onPlaybackStartedFn(),onPlaybackStarted(player,playOptions,streamInfo,mediaSource)},function(err){onPlaybackStartedFn(),onPlaybackStarted(player,playOptions,streamInfo,mediaSource),setTimeout(function(){onPlaybackError.call(player,err,{type:"mediadecodeerror",streamInfo:streamInfo})},100)})}))}):promise.then(function(){var streamInfo=createStreamInfoFromUrlItem(item);return streamInfo.fullscreen=playOptions.fullscreen,getPlayerData(player).isChangingStream=!1,player.play(streamInfo).then(function(){loading.hide(),onPlaybackStartedFn(),onPlaybackStarted(player,playOptions,streamInfo)},function(){self.stop(player)})})}function createStreamInfo(apiClient,type,item,mediaSource,startPosition){var mediaUrl,contentType,directOptions,transcodingOffsetTicks=0,playerStartPositionTicks=startPosition,liveStreamId=mediaSource.LiveStreamId,playMethod="Transcode",mediaSourceContainer=(mediaSource.Container||"").toLowerCase();if("Video"===type||"Audio"===type)if(contentType=getMimeType(type.toLowerCase(),mediaSourceContainer),mediaSource.enableDirectPlay)mediaUrl=mediaSource.Path,playMethod="DirectPlay";else if(mediaSource.StreamUrl)playMethod="Transcode",mediaUrl=mediaSource.StreamUrl;else if(mediaSource.SupportsDirectStream){directOptions={Static:!0,mediaSourceId:mediaSource.Id,deviceId:apiClient.deviceId(),api_key:apiClient.accessToken()},mediaSource.ETag&&(directOptions.Tag=mediaSource.ETag),mediaSource.LiveStreamId&&(directOptions.LiveStreamId=mediaSource.LiveStreamId);var prefix="Video"===type?"Videos":"Audio";mediaUrl=apiClient.getUrl(prefix+"/"+item.Id+"/stream."+mediaSourceContainer,directOptions),playMethod="DirectStream"}else mediaSource.SupportsTranscoding&&(mediaUrl=apiClient.getUrl(mediaSource.TranscodingUrl),"hls"===mediaSource.TranscodingSubProtocol?contentType="application/x-mpegURL":(playerStartPositionTicks=null,contentType=getMimeType(type.toLowerCase(),mediaSource.TranscodingContainer),-1===mediaUrl.toLowerCase().indexOf("copytimestamps=true")&&(transcodingOffsetTicks=startPosition||0)));else mediaUrl=mediaSource.Path,playMethod="DirectPlay";!mediaUrl&&mediaSource.SupportsDirectPlay&&(mediaUrl=mediaSource.Path,playMethod="DirectPlay");var resultInfo={url:mediaUrl,mimeType:contentType,transcodingOffsetTicks:transcodingOffsetTicks,playMethod:playMethod,playerStartPositionTicks:playerStartPositionTicks,item:item,mediaSource:mediaSource,textTracks:getTextTracks(apiClient,item,mediaSource),tracks:getTextTracks(apiClient,item,mediaSource),mediaType:type,liveStreamId:liveStreamId,playSessionId:getParam("playSessionId",mediaUrl),title:item.Name},backdropUrl=backdropImageUrl(apiClient,item,{});return backdropUrl&&(resultInfo.backdropUrl=backdropUrl),resultInfo}function getTextTracks(apiClient,item,mediaSource){for(var subtitleStreams=mediaSource.MediaStreams.filter(function(s){return"Subtitle"===s.Type}),textStreams=subtitleStreams.filter(function(s){return"External"===s.DeliveryMethod}),tracks=[],i=0,length=textStreams.length;i=6e5&&getLiveStreamMediaInfo(player,streamInfo,self.currentMediaSource(player),streamInfo.liveStreamId,serverId)}}function getLiveStreamMediaInfo(player,streamInfo,mediaSource,liveStreamId,serverId){console.log("getLiveStreamMediaInfo"),streamInfo.lastMediaInfoQuery=(new Date).getTime(),connectionManager.getApiClient(serverId).isMinServerVersion("3.2.70.7")&&connectionManager.getApiClient(serverId).getLiveStreamMediaInfo(liveStreamId).then(function(info){mediaSource.MediaStreams=info.MediaStreams,events.trigger(player,"mediastreamschange")},function(){})}var currentTargetInfo,lastLocalPlayer,self=this,players=[],currentPairingId=null;this._playNextAfterEnded=!0;var playerStates={};this._playQueueManager=new PlayQueueManager,self.currentItem=function(player){if(!player)throw new Error("player cannot be null");if(player.currentItem)return player.currentItem();var data=getPlayerData(player);return data.streamInfo?data.streamInfo.item:null},self.currentMediaSource=function(player){if(!player)throw new Error("player cannot be null");if(player.currentMediaSource)return player.currentMediaSource();var data=getPlayerData(player);return data.streamInfo?data.streamInfo.mediaSource:null},self.playMethod=function(player){if(!player)throw new Error("player cannot be null");if(player.playMethod)return player.playMethod();var data=getPlayerData(player);return data.streamInfo?data.streamInfo.playMethod:null},self.playSessionId=function(player){if(!player)throw new Error("player cannot be null");if(player.playSessionId)return player.playSessionId();var data=getPlayerData(player);return data.streamInfo?data.streamInfo.playSessionId:null},self.getPlayerInfo=function(){var player=self._currentPlayer;if(!player)return null;var target=currentTargetInfo||{};return{name:player.name,isLocalPlayer:player.isLocalPlayer,id:target.id,deviceName:target.deviceName,playableMediaTypes:target.playableMediaTypes,supportedCommands:target.supportedCommands}},self.setActivePlayer=function(player,targetInfo){if("localplayer"===player||"localplayer"===player.name){if(self._currentPlayer&&self._currentPlayer.isLocalPlayer)return;return void setCurrentPlayerInternal(null,null)}if("string"==typeof player&&(player=players.filter(function(p){return p.name===player})[0]),!player)throw new Error("null player");setCurrentPlayerInternal(player,targetInfo)},self.trySetActivePlayer=function(player,targetInfo){if("localplayer"===player||"localplayer"===player.name)return void(self._currentPlayer&&self._currentPlayer.isLocalPlayer);if("string"==typeof player&&(player=players.filter(function(p){return p.name===player})[0]),!player)throw new Error("null player");if(currentPairingId!==targetInfo.id){currentPairingId=targetInfo.id;var promise=player.tryPair?player.tryPair(targetInfo):Promise.resolve();events.trigger(self,"pairing"),promise.then(function(){events.trigger(self,"paired"),setCurrentPlayerInternal(player,targetInfo)},function(){events.trigger(self,"pairerror"),currentPairingId===targetInfo.id&&(currentPairingId=null)})}},self.getTargets=function(){var promises=players.filter(displayPlayerIndividually).map(getPlayerTargets);return Promise.all(promises).then(function(responses){return connectionManager.currentApiClient().getCurrentUser().then(function(user){var targets=[];targets.push({name:globalize.translate("sharedcomponents#HeaderMyDevice"),id:"localplayer",playerName:"localplayer",playableMediaTypes:["Audio","Video","Game","Photo","Book"],isLocalPlayer:!0,supportedCommands:self.getSupportedCommands({isLocalPlayer:!0}),user:user});for(var i=0;i0},self.isPlayingVideo=function(player){return self.isPlayingMediaType("Video",player)},self.isPlayingAudio=function(player){return self.isPlayingMediaType("Audio",player)},self.getPlayers=function(){return players},self.canPlay=function(item){var itemType=item.Type;if("PhotoAlbum"===itemType||"MusicGenre"===itemType||"Season"===itemType||"Series"===itemType||"BoxSet"===itemType||"MusicAlbum"===itemType||"MusicArtist"===itemType||"Playlist"===itemType)return!0;if("Virtual"===item.LocationType&&"Program"!==itemType)return!1;if("Program"===itemType){if(!item.EndDate||!item.StartDate)return!1;if((new Date).getTime()>datetime.parseISO8601Date(item.EndDate).getTime()||(new Date).getTime()=supported.length&&(index=0),self.setAspectRatio(supported[index].id,player)}},self.setAspectRatio=function(val,player){(player=player||self._currentPlayer)&&player.setAspectRatio&&player.setAspectRatio(val)},self.getSupportedAspectRatios=function(player){return player=player||self._currentPlayer,player&&player.getSupportedAspectRatios?player.getSupportedAspectRatios():[]},self.getAspectRatio=function(player){if((player=player||self._currentPlayer)&&player.getAspectRatio)return player.getAspectRatio()};var brightnessOsdLoaded;self.setBrightness=function(val,player){(player=player||self._currentPlayer)&&(brightnessOsdLoaded||(brightnessOsdLoaded=!0,require(["brightnessOsd"])),player.setBrightness(val))},self.getBrightness=function(player){if(player=player||self._currentPlayer)return player.getBrightness()},self.setVolume=function(val,player){(player=player||self._currentPlayer)&&player.setVolume(val)},self.getVolume=function(player){if(player=player||self._currentPlayer)return player.getVolume()},self.volumeUp=function(player){(player=player||self._currentPlayer)&&player.volumeUp()},self.volumeDown=function(player){(player=player||self._currentPlayer)&&player.volumeDown()},self.changeAudioStream=function(player){if((player=player||self._currentPlayer)&&!enableLocalPlaylistManagement(player))return player.changeAudioStream();if(player){var i,length,currentMediaSource=self.currentMediaSource(player),mediaStreams=[];for(i=0,length=currentMediaSource.MediaStreams.length;i=mediaStreams.length&&(nextIndex=0),nextIndex=-1===nextIndex?-1:mediaStreams[nextIndex].Index,self.setAudioStreamIndex(nextIndex,player)}}},self.changeSubtitleStream=function(player){if((player=player||self._currentPlayer)&&!enableLocalPlaylistManagement(player))return player.changeSubtitleStream();if(player){var i,length,currentMediaSource=self.currentMediaSource(player),mediaStreams=[];for(i=0,length=currentMediaSource.MediaStreams.length;i=mediaStreams.length&&(nextIndex=-1),nextIndex=-1===nextIndex?-1:mediaStreams[nextIndex].Index,self.setSubtitleStreamIndex(nextIndex,player)}}},self.getAudioStreamIndex=function(player){return player=player||self._currentPlayer,player&&!enableLocalPlaylistManagement(player)?player.getAudioStreamIndex():getPlayerData(player).audioStreamIndex},self.setAudioStreamIndex=function(index,player){if((player=player||self._currentPlayer)&&!enableLocalPlaylistManagement(player))return player.setAudioStreamIndex(index);"Transcode"!==self.playMethod(player)&&player.canSetAudioStreamIndex()?player.getDeviceProfile(self.currentItem(player)).then(function(profile){isAudioStreamSupported(self.currentMediaSource(player),index,profile)?(player.setAudioStreamIndex(index),getPlayerData(player).audioStreamIndex=index):(changeStream(player,getCurrentTicks(player),{AudioStreamIndex:index}),getPlayerData(player).audioStreamIndex=index)}):(changeStream(player,getCurrentTicks(player),{AudioStreamIndex:index}),getPlayerData(player).audioStreamIndex=index)},self.getMaxStreamingBitrate=function(player){if((player=player||self._currentPlayer)&&player.getMaxStreamingBitrate)return player.getMaxStreamingBitrate();var playerData=getPlayerData(player);if(playerData.maxStreamingBitrate)return playerData.maxStreamingBitrate;var mediaType=playerData.streamInfo?playerData.streamInfo.mediaType:null,currentItem=self.currentItem(player);return getSavedMaxStreamingBitrate(currentItem?connectionManager.getApiClient(currentItem.ServerId):connectionManager.currentApiClient(),mediaType)},self.enableAutomaticBitrateDetection=function(player){if((player=player||self._currentPlayer)&&player.enableAutomaticBitrateDetection)return player.enableAutomaticBitrateDetection();var playerData=getPlayerData(player),mediaType=playerData.streamInfo?playerData.streamInfo.mediaType:null,currentItem=self.currentItem(player),apiClient=currentItem?connectionManager.getApiClient(currentItem.ServerId):connectionManager.currentApiClient(),endpointInfo=apiClient.getSavedEndpointInfo()||{};return appSettings.enableAutomaticBitrateDetection(endpointInfo.IsInNetwork,mediaType)},self.setMaxStreamingBitrate=function(options,player){if((player=player||self._currentPlayer)&&player.setMaxStreamingBitrate)return player.setMaxStreamingBitrate(options);var apiClient=connectionManager.getApiClient(self.currentItem(player).ServerId);apiClient.getEndpointInfo().then(function(endpointInfo){var promise,playerData=getPlayerData(player),mediaType=playerData.streamInfo?playerData.streamInfo.mediaType:null;options.enableAutomaticBitrateDetection?(appSettings.enableAutomaticBitrateDetection(endpointInfo.IsInNetwork,mediaType,!0),promise=apiClient.detectBitrate(!0)):(appSettings.enableAutomaticBitrateDetection(endpointInfo.IsInNetwork,mediaType,!1),promise=Promise.resolve(options.maxBitrate)),promise.then(function(bitrate){appSettings.maxStreamingBitrate(endpointInfo.IsInNetwork,mediaType,bitrate),changeStream(player,getCurrentTicks(player),{MaxStreamingBitrate:bitrate})})})},self.isFullscreen=function(player){return player=player||self._currentPlayer,!player.isLocalPlayer||player.isFullscreen?player.isFullscreen():fullscreenManager.isFullScreen()},self.toggleFullscreen=function(player){if(player=player||self._currentPlayer,!player.isLocalPlayer||player.toggleFulscreen)return player.toggleFulscreen();fullscreenManager.isFullScreen()?fullscreenManager.exitFullscreen():fullscreenManager.requestFullscreen()},self.togglePictureInPicture=function(player){return player=player||self._currentPlayer,player.togglePictureInPicture()},self.getSubtitleStreamIndex=function(player){if((player=player||self._currentPlayer)&&!enableLocalPlaylistManagement(player))return player.getSubtitleStreamIndex();if(!player)throw new Error("player cannot be null");return getPlayerData(player).subtitleStreamIndex},self.setSubtitleStreamIndex=function(index,player){if((player=player||self._currentPlayer)&&!enableLocalPlaylistManagement(player))return player.setSubtitleStreamIndex(index);var currentStream=getCurrentSubtitleStream(player),newStream=getSubtitleStream(player,index);if(currentStream||newStream){var selectedTrackElementIndex=-1,currentPlayMethod=self.playMethod(player);currentStream&&!newStream?("Encode"===getDeliveryMethod(currentStream)||"Embed"===getDeliveryMethod(currentStream)&&"Transcode"===currentPlayMethod)&&changeStream(player,getCurrentTicks(player),{SubtitleStreamIndex:-1}):!currentStream&&newStream?"External"===getDeliveryMethod(newStream)?selectedTrackElementIndex=index:"Embed"===getDeliveryMethod(newStream)&&"Transcode"!==currentPlayMethod?selectedTrackElementIndex=index:changeStream(player,getCurrentTicks(player),{SubtitleStreamIndex:index}):currentStream&&newStream&&("External"===getDeliveryMethod(newStream)||"Embed"===getDeliveryMethod(newStream)&&"Transcode"!==currentPlayMethod?(selectedTrackElementIndex=index,"External"!==getDeliveryMethod(currentStream)&&"Embed"!==getDeliveryMethod(currentStream)&&changeStream(player,getCurrentTicks(player),{SubtitleStreamIndex:-1})):changeStream(player,getCurrentTicks(player),{SubtitleStreamIndex:index})),player.setSubtitleStreamIndex(selectedTrackElementIndex),getPlayerData(player).subtitleStreamIndex=index}},self.seek=function(ticks,player){if(ticks=Math.max(0,ticks),(player=player||self._currentPlayer)&&!enableLocalPlaylistManagement(player))return player.isLocalPlayer?player.seek((ticks||0)/1e4):player.seek(ticks);changeStream(player,ticks)},self.seekRelative=function(offsetTicks,player){if((player=player||self._currentPlayer)&&!enableLocalPlaylistManagement(player)&&player.seekRelative)return player.isLocalPlayer?player.seekRelative((ticks||0)/1e4):player.seekRelative(ticks);var ticks=getCurrentTicks(player)+offsetTicks;return this.seek(ticks,player)},self.play=function(options){if(normalizePlayOptions(options),self._currentPlayer){if(!1===options.enableRemotePlayers&&!self._currentPlayer.isLocalPlayer)return Promise.reject();if(!self._currentPlayer.isLocalPlayer)return self._currentPlayer.play(options)}if(options.fullscreen&&loading.show(),options.items)return translateItemsForPlayback(options.items,options).then(function(items){return playWithIntros(items,options)});if(!options.serverId)throw new Error("serverId required!");return getItemsForPlayback(options.serverId,{Ids:options.ids.join(",")}).then(function(result){return translateItemsForPlayback(result.Items,options).then(function(items){return playWithIntros(items,options)})})},self.getPlayerState=function(player,item,mediaSource){if(!(player=player||self._currentPlayer))throw new Error("player cannot be null");if(!enableLocalPlaylistManagement(player)&&player.getPlayerState)return player.getPlayerState();item=item||self.currentItem(player),mediaSource=mediaSource||self.currentMediaSource(player);var state={PlayState:{}};return player&&(state.PlayState.VolumeLevel=player.getVolume(),state.PlayState.IsMuted=player.isMuted(),state.PlayState.IsPaused=player.paused(),state.PlayState.RepeatMode=self.getRepeatMode(player),state.PlayState.MaxStreamingBitrate=self.getMaxStreamingBitrate(player),state.PlayState.PositionTicks=getCurrentTicks(player),state.PlayState.PlaybackStartTimeTicks=self.playbackStartTime(player),state.PlayState.SubtitleStreamIndex=self.getSubtitleStreamIndex(player),state.PlayState.AudioStreamIndex=self.getAudioStreamIndex(player),state.PlayState.BufferedRanges=self.getBufferedRanges(player),state.PlayState.PlayMethod=self.playMethod(player),mediaSource&&(state.PlayState.LiveStreamId=mediaSource.LiveStreamId),state.PlayState.PlaySessionId=self.playSessionId(player),state.PlayState.PlaylistItemId=self.getCurrentPlaylistItemId(player)),mediaSource&&(state.PlayState.MediaSourceId=mediaSource.Id,state.NowPlayingItem={RunTimeTicks:mediaSource.RunTimeTicks},state.PlayState.CanSeek=(mediaSource.RunTimeTicks||0)>0||canPlayerSeek(player)),item&&(state.NowPlayingItem=getNowPlayingItemForReporting(player,item,mediaSource)),state.MediaSource=mediaSource,state},self.duration=function(player){if((player=player||self._currentPlayer)&&!enableLocalPlaylistManagement(player)&&!player.isLocalPlayer)return player.duration();if(!player)throw new Error("player cannot be null");var mediaSource=self.currentMediaSource(player);if(mediaSource&&mediaSource.RunTimeTicks)return mediaSource.RunTimeTicks;var playerDuration=player.duration();return playerDuration&&(playerDuration*=1e4),playerDuration},self.getCurrentTicks=getCurrentTicks,self.getPlaybackInfo=function(item,options){options=options||{};var startPosition=options.startPositionTicks||0,mediaType=options.mediaType||item.MediaType,player=getPlayer(item,options),apiClient=connectionManager.getApiClient(item.ServerId);return apiClient.getEndpointInfo().then(function(){var maxBitrate=getSavedMaxStreamingBitrate(connectionManager.getApiClient(item.ServerId),mediaType);return player.getDeviceProfile(item).then(function(deviceProfile){return getPlaybackMediaSource(player,apiClient,deviceProfile,maxBitrate,item,startPosition,options.mediaSourceId,options.audioStreamIndex,options.subtitleStreamIndex).then(function(mediaSource){return createStreamInfo(apiClient,item.MediaType,item,mediaSource,startPosition)})})})},self.getPlaybackMediaSources=function(item,options){options=options||{};var startPosition=options.startPositionTicks||0,mediaType=options.mediaType||item.MediaType,player=getPlayer(item,options,!0),apiClient=connectionManager.getApiClient(item.ServerId);return apiClient.getEndpointInfo().then(function(){var maxBitrate=getSavedMaxStreamingBitrate(connectionManager.getApiClient(item.ServerId),mediaType);return player.getDeviceProfile(item).then(function(deviceProfile){return getPlaybackInfo(player,apiClient,item,deviceProfile,maxBitrate,startPosition,!1,null,null,null,null).then(function(playbackInfoResult){return playbackInfoResult.MediaSources})})})},self.setCurrentPlaylistItem=function(playlistItemId,player){if((player=player||self._currentPlayer)&&!enableLocalPlaylistManagement(player))return player.setCurrentPlaylistItem(playlistItemId);for(var newItem,newItemIndex,playlist=self._playQueueManager.getPlaylist(),i=0,length=playlist.length;i=0){var playlist=self._playQueueManager.getPlaylist(),newItem=playlist[newIndex];if(newItem){var newItemPlayOptions=newItem.playOptions||{};newItemPlayOptions.startPositionTicks=0,playInternal(newItem,newItemPlayOptions,function(){setPlaylistState(newItem.PlaylistItemId,newIndex)})}}},self.queue=function(options,player){queue(options,"",player)},self.queueNext=function(options,player){queue(options,"next",player)},events.on(pluginManager,"registered",function(e,plugin){"mediaplayer"===plugin.type&&initMediaPlayer(plugin)}),pluginManager.ofType("mediaplayer").map(initMediaPlayer),self.onAppClose=function(){var player=this._currentPlayer;player&&this.isPlaying(player)&&(this._playNextAfterEnded=!1,onPlaybackStopped.call(player))},self.playbackStartTime=function(player){if((player=player||this._currentPlayer)&&!enableLocalPlaylistManagement(player)&&!player.isLocalPlayer)return player.playbackStartTime();var streamInfo=getPlayerData(player).streamInfo;return streamInfo?streamInfo.playbackStartTimeTicks:null},apphost.supports("remotecontrol")&&require(["serverNotifications"],function(serverNotifications){events.on(serverNotifications,"ServerShuttingDown",self.setDefaultPlayerActive.bind(self)),events.on(serverNotifications,"ServerRestarting",self.setDefaultPlayerActive.bind(self))})}var startingPlaySession=(new Date).getTime();return PlaybackManager.prototype.getCurrentPlayer=function(){return this._currentPlayer},PlaybackManager.prototype.currentTime=function(player){return player=player||this._currentPlayer,!player||enableLocalPlaylistManagement(player)||player.isLocalPlayer?this.getCurrentTicks(player):player.currentTime()},PlaybackManager.prototype.nextItem=function(player){if((player=player||this._currentPlayer)&&!enableLocalPlaylistManagement(player))return player.nextItem();var nextItem=this._playQueueManager.getNextItemInfo();if(!nextItem||!nextItem.item)return Promise.reject();var apiClient=connectionManager.getApiClient(nextItem.item.ServerId);return apiClient.getItem(apiClient.getCurrentUserId(),nextItem.item.Id)},PlaybackManager.prototype.canQueue=function(item){return"MusicAlbum"===item.Type||"MusicArtist"===item.Type||"MusicGenre"===item.Type?this.canQueueMediaType("Audio"):this.canQueueMediaType(item.MediaType)},PlaybackManager.prototype.canQueueMediaType=function(mediaType){return!!this._currentPlayer&&this._currentPlayer.canPlayMediaType(mediaType)},PlaybackManager.prototype.isMuted=function(player){return!!(player=player||this._currentPlayer)&&player.isMuted()},PlaybackManager.prototype.setMute=function(mute,player){(player=player||this._currentPlayer)&&player.setMute(mute)},PlaybackManager.prototype.toggleMute=function(mute,player){(player=player||this._currentPlayer)&&(player.toggleMute?player.toggleMute():player.setMute(!player.isMuted()))},PlaybackManager.prototype.toggleDisplayMirroring=function(){this.enableDisplayMirroring(!this.enableDisplayMirroring())},PlaybackManager.prototype.enableDisplayMirroring=function(enabled){if(null!=enabled){var val=enabled?"1":"0";return void appSettings.set("displaymirror",val)}return"0"!==(appSettings.get("displaymirror")||"")},PlaybackManager.prototype.nextChapter=function(player){player=player||this._currentPlayer;var item=this.currentItem(player),ticks=this.getCurrentTicks(player),nextChapter=(item.Chapters||[]).filter(function(i){return i.StartPositionTicks>ticks})[0];nextChapter?this.seek(nextChapter.StartPositionTicks,player):this.nextTrack(player)},PlaybackManager.prototype.previousChapter=function(player){player=player||this._currentPlayer;var item=this.currentItem(player),ticks=this.getCurrentTicks(player);ticks-=1e8,0===this.getCurrentPlaylistIndex(player)&&(ticks=Math.max(ticks,0));var previousChapters=(item.Chapters||[]).filter(function(i){return i.StartPositionTicks<=ticks});previousChapters.length?this.seek(previousChapters[previousChapters.length-1].StartPositionTicks,player):this.previousTrack(player)},PlaybackManager.prototype.fastForward=function(player){if(player=player||this._currentPlayer,null!=player.fastForward)return void player.fastForward(userSettings.skipForwardLength());var offsetTicks=1e4*userSettings.skipForwardLength();this.seekRelative(offsetTicks,player)},PlaybackManager.prototype.rewind=function(player){if(player=player||this._currentPlayer,null!=player.rewind)return void player.rewind(userSettings.skipBackLength());var offsetTicks=0-1e4*userSettings.skipBackLength();this.seekRelative(offsetTicks,player)},PlaybackManager.prototype.seekPercent=function(percent,player){player=player||this._currentPlayer;var ticks=this.duration(player)||0;percent/=100,ticks*=percent,this.seek(parseInt(ticks),player)},PlaybackManager.prototype.playTrailers=function(item){var player=this._currentPlayer;if(player&&player.playTrailers)return player.playTrailers(item);var apiClient=connectionManager.getApiClient(item.ServerId),instance=this;if(item.LocalTrailerCount)return apiClient.getLocalTrailers(apiClient.getCurrentUserId(),item.Id).then(function(result){return instance.play({items:result})});var remoteTrailers=item.RemoteTrailers||[];return remoteTrailers.length?this.play({items:remoteTrailers.map(function(t){return{Name:t.Name||item.Name+" Trailer",Url:t.Url,MediaType:"Video",Type:"Trailer",ServerId:apiClient.serverId()}})}):Promise.reject()},PlaybackManager.prototype.getSubtitleUrl=function(textStream,serverId){var apiClient=connectionManager.getApiClient(serverId);return textStream.IsExternalUrl?textStream.DeliveryUrl:apiClient.getUrl(textStream.DeliveryUrl)},PlaybackManager.prototype.stop=function(player){return player=player||this._currentPlayer,player?(enableLocalPlaylistManagement(player)&&(this._playNextAfterEnded=!1),player.stop(!0,!0)):Promise.resolve()},PlaybackManager.prototype.getBufferedRanges=function(player){return player=player||this._currentPlayer,player&&player.getBufferedRanges?player.getBufferedRanges():[]},PlaybackManager.prototype.playPause=function(player){if(player=player||this._currentPlayer)return player.playPause?player.playPause():player.paused()?this.unpause(player):this.pause(player)},PlaybackManager.prototype.paused=function(player){if(player=player||this._currentPlayer)return player.paused()},PlaybackManager.prototype.pause=function(player){(player=player||this._currentPlayer)&&player.pause()},PlaybackManager.prototype.unpause=function(player){(player=player||this._currentPlayer)&&player.unpause()},PlaybackManager.prototype.instantMix=function(item,player){if((player=player||this._currentPlayer)&&player.instantMix)return player.instantMix(item);var apiClient=connectionManager.getApiClient(item.ServerId),options={};options.UserId=apiClient.getCurrentUserId(),options.Limit=200;var instance=this;apiClient.getInstantMixFromItem(item.Id,options).then(function(result){instance.play({items:result.Items})})},PlaybackManager.prototype.shuffle=function(shuffleItem,player,queryOptions){return player=player||this._currentPlayer,player&&player.shuffle?player.shuffle(shuffleItem):this.play({items:[shuffleItem],shuffle:!0})},PlaybackManager.prototype.audioTracks=function(player){if(player=player||this._currentPlayer,player.audioTracks){var result=player.audioTracks();if(result)return result}return((this.currentMediaSource(player)||{}).MediaStreams||[]).filter(function(s){return"Audio"===s.Type})},PlaybackManager.prototype.subtitleTracks=function(player){if(player=player||this._currentPlayer,player.subtitleTracks){var result=player.subtitleTracks();if(result)return result}return((this.currentMediaSource(player)||{}).MediaStreams||[]).filter(function(s){return"Subtitle"===s.Type})},PlaybackManager.prototype.getSupportedCommands=function(player){if(player=player||this._currentPlayer||{isLocalPlayer:!0},player.isLocalPlayer){var list=["GoHome","GoToSettings","VolumeUp","VolumeDown","Mute","Unmute","ToggleMute","SetVolume","SetAudioStreamIndex","SetSubtitleStreamIndex","SetMaxStreamingBitrate","DisplayContent","GoToSearch","DisplayMessage","SetRepeatMode","PlayMediaSource","PlayTrailers"];return apphost.supports("fullscreenchange")&&list.push("ToggleFullscreen"),player.supports&&(player.supports("PictureInPicture")&&list.push("PictureInPicture"),player.supports("SetBrightness")&&list.push("SetBrightness"),player.supports("SetAspectRatio")&&list.push("SetAspectRatio")),list}var info=this.getPlayerInfo();return info?info.supportedCommands:[]},PlaybackManager.prototype.setRepeatMode=function(value,player){if((player=player||this._currentPlayer)&&!enableLocalPlaylistManagement(player))return player.setRepeatMode(value);this._playQueueManager.setRepeatMode(value),events.trigger(player,"repeatmodechange")},PlaybackManager.prototype.getRepeatMode=function(player){return player=player||this._currentPlayer,player&&!enableLocalPlaylistManagement(player)?player.getRepeatMode():this._playQueueManager.getRepeatMode()},PlaybackManager.prototype.trySetActiveDeviceName=function(name){name=normalizeName(name);var instance=this;instance.getTargets().then(function(result){var target=result.filter(function(p){return normalizeName(p.name)===name})[0];target&&instance.trySetActivePlayer(target.playerName,target)})},PlaybackManager.prototype.displayContent=function(options,player){(player=player||this._currentPlayer)&&player.displayContent&&player.displayContent(options)},PlaybackManager.prototype.beginPlayerUpdates=function(player){player.beginPlayerUpdates&&player.beginPlayerUpdates()},PlaybackManager.prototype.endPlayerUpdates=function(player){player.endPlayerUpdates&&player.endPlayerUpdates()},PlaybackManager.prototype.setDefaultPlayerActive=function(){this.setActivePlayer("localplayer")},PlaybackManager.prototype.removeActivePlayer=function(name){var playerInfo=this.getPlayerInfo();playerInfo&&playerInfo.name===name&&this.setDefaultPlayerActive()},PlaybackManager.prototype.removeActiveTarget=function(id){var playerInfo=this.getPlayerInfo();playerInfo&&playerInfo.id===id&&this.setDefaultPlayerActive()},PlaybackManager.prototype.sendCommand=function(cmd,player){switch(console.log("MediaController received command: "+cmd.Name),cmd.Name){case"SetRepeatMode":this.setRepeatMode(cmd.Arguments.RepeatMode,player);break;case"VolumeUp":this.volumeUp(player);break;case"VolumeDown":this.volumeDown(player);break;case"Mute":this.setMute(!0,player);break;case"Unmute":this.setMute(!1,player);break;case"ToggleMute":this.toggleMute(player);break;case"SetVolume":this.setVolume(cmd.Arguments.Volume,player);break;case"SetAspectRatio":this.setAspectRatio(cmd.Arguments.AspectRatio,player);break;case"SetBrightness":this.setBrightness(cmd.Arguments.Brightness,player);break;case"SetAudioStreamIndex":this.setAudioStreamIndex(parseInt(cmd.Arguments.Index),player);break;case"SetSubtitleStreamIndex":this.setSubtitleStreamIndex(parseInt(cmd.Arguments.Index),player);break;case"SetMaxStreamingBitrate":break;case"ToggleFullscreen":this.toggleFullscreen(player);break;default:player.sendCommand&&player.sendCommand(cmd)}},new PlaybackManager}); \ No newline at end of file +define(["events", "datetime", "appSettings", "itemHelper", "pluginManager", "playQueueManager", "userSettings", "globalize", "connectionManager", "loading", "apphost", "fullscreenManager"], function(events, datetime, appSettings, itemHelper, pluginManager, PlayQueueManager, userSettings, globalize, connectionManager, loading, apphost, fullscreenManager) { + "use strict"; + + function enableLocalPlaylistManagement(player) { + return !player.getPlaylist && !!player.isLocalPlayer + } + + function bindToFullscreenChange(player) { + events.on(fullscreenManager, "fullscreenchange", function() { + events.trigger(player, "fullscreenchange") + }) + } + + function triggerPlayerChange(playbackManagerInstance, newPlayer, newTarget, previousPlayer, previousTargetInfo) { + (newPlayer || previousPlayer) && (newTarget && previousTargetInfo && newTarget.id === previousTargetInfo.id || events.trigger(playbackManagerInstance, "playerchange", [newPlayer, newTarget, previousPlayer])) + } + + function reportPlayback(playbackManagerInstance, state, player, reportPlaylist, serverId, method, progressEventName) { + if (serverId) { + var info = Object.assign({}, state.PlayState); + info.ItemId = state.NowPlayingItem.Id, progressEventName && (info.EventName = progressEventName), reportPlaylist && addPlaylistToPlaybackReport(playbackManagerInstance, info, player, serverId); + connectionManager.getApiClient(serverId)[method](info) + } + } + + function getPlaylistSync(playbackManagerInstance, player) { + return player = player || playbackManagerInstance._currentPlayer, player && !enableLocalPlaylistManagement(player) ? player.getPlaylistSync() : playbackManagerInstance._playQueueManager.getPlaylist() + } + + function addPlaylistToPlaybackReport(playbackManagerInstance, info, player, serverId) { + info.NowPlayingQueue = getPlaylistSync(playbackManagerInstance, player).map(function(i) { + var itemInfo = { + Id: i.Id, + PlaylistItemId: i.PlaylistItemId + }; + return i.ServerId !== serverId && (itemInfo.ServerId = i.ServerId), itemInfo + }) + } + + function normalizeName(t) { + return t.toLowerCase().replace(" ", "") + } + + function getItemsForPlayback(serverId, query) { + var apiClient = connectionManager.getApiClient(serverId); + if (query.Ids && 1 === query.Ids.split(",").length) { + var itemId = query.Ids.split(","); + return apiClient.getItem(apiClient.getCurrentUserId(), itemId).then(function(item) { + return { + Items: [item], + TotalRecordCount: 1 + } + }) + } + return query.Limit = query.Limit || 300, query.Fields = "Chapters", query.ExcludeLocationTypes = "Virtual", query.EnableTotalRecordCount = !1, query.CollapseBoxSetItems = !1, apiClient.getItems(apiClient.getCurrentUserId(), query) + } + + function createStreamInfoFromUrlItem(item) { + return { + url: item.Url || item.Path, + playMethod: "DirectPlay", + item: item, + textTracks: [], + mediaType: item.MediaType + } + } + + function mergePlaybackQueries(obj1, obj2) { + var query = Object.assign(obj1, obj2), + filters = query.Filters ? query.Filters.split(",") : []; + return -1 === filters.indexOf("IsNotFolder") && filters.push("IsNotFolder"), query.Filters = filters.join(","), query + } + + function backdropImageUrl(apiClient, item, options) { + return options = options || {}, options.type = options.type || "Backdrop", options.maxWidth || options.width || options.maxHeight || options.height || (options.quality = 100), item.BackdropImageTags && item.BackdropImageTags.length ? (options.tag = item.BackdropImageTags[0], apiClient.getScaledImageUrl(item.Id, options)) : item.ParentBackdropImageTags && item.ParentBackdropImageTags.length ? (options.tag = item.ParentBackdropImageTags[0], apiClient.getScaledImageUrl(item.ParentBackdropItemId, options)) : null + } + + function getMimeType(type, container) { + if (container = (container || "").toLowerCase(), "audio" === type) { + if ("opus" === container) return "audio/ogg"; + if ("webma" === container) return "audio/webm"; + if ("m4a" === container) return "audio/mp4" + } else if ("video" === type) { + if ("mkv" === container) return "video/x-matroska"; + if ("m4v" === container) return "video/mp4"; + if ("mov" === container) return "video/quicktime"; + if ("mpg" === container) return "video/mpeg"; + if ("flv" === container) return "video/x-flv" + } + return type + "/" + container + } + + function getParam(name, url) { + name = name.replace(/[\[]/, "\\[").replace(/[\]]/, "\\]"); + var regexS = "[\\?&]" + name + "=([^&#]*)", + regex = new RegExp(regexS, "i"), + results = regex.exec(url); + return null == results ? "" : decodeURIComponent(results[1].replace(/\+/g, " ")) + } + + function isAutomaticPlayer(player) { + return !!player.isLocalPlayer + } + + function getAutomaticPlayers(instance, forceLocalPlayer) { + if (!forceLocalPlayer) { + var player = instance._currentPlayer; + if (player && !isAutomaticPlayer(player)) return [player] + } + return instance.getPlayers().filter(isAutomaticPlayer) + } + + function isServerItem(item) { + return !!item.Id + } + + function enableIntros(item) { + return "Video" === item.MediaType && ("TvChannel" !== item.Type && ("InProgress" !== item.Status && isServerItem(item))) + } + + function getIntros(firstItem, apiClient, options) { + return options.startPositionTicks || options.startIndex || !1 === options.fullscreen || !enableIntros(firstItem) || !userSettings.enableCinemaMode() ? Promise.resolve({ + Items: [] + }) : apiClient.getIntros(firstItem.Id).then(function(result) { + return result + }, function(err) { + return Promise.resolve({ + Items: [] + }) + }) + } + + function getAudioMaxValues(deviceProfile) { + var maxAudioSampleRate = null, + maxAudioBitDepth = null, + maxAudioBitrate = null; + return deviceProfile.CodecProfiles.map(function(codecProfile) { + "Audio" === codecProfile.Type && (codecProfile.Conditions || []).map(function(condition) { + "LessThanEqual" === condition.Condition && "AudioBitDepth" === condition.Property && (maxAudioBitDepth = condition.Value), "LessThanEqual" === condition.Condition && "AudioSampleRate" === condition.Property && (maxAudioSampleRate = condition.Value), "LessThanEqual" === condition.Condition && "AudioBitrate" === condition.Property && (maxAudioBitrate = condition.Value) + }) + }), { + maxAudioSampleRate: maxAudioSampleRate, + maxAudioBitDepth: maxAudioBitDepth, + maxAudioBitrate: maxAudioBitrate + } + } + + function getAudioStreamUrl(item, transcodingProfile, directPlayContainers, maxBitrate, apiClient, maxAudioSampleRate, maxAudioBitDepth, maxAudioBitrate, startPosition) { + var url = "Audio/" + item.Id + "/universal"; + return startingPlaySession++, apiClient.getUrl(url, { + UserId: apiClient.getCurrentUserId(), + DeviceId: apiClient.deviceId(), + MaxStreamingBitrate: maxAudioBitrate || maxBitrate, + Container: directPlayContainers, + TranscodingContainer: transcodingProfile.Container || null, + TranscodingProtocol: transcodingProfile.Protocol || null, + AudioCodec: transcodingProfile.AudioCodec, + MaxAudioSampleRate: maxAudioSampleRate, + MaxAudioBitDepth: maxAudioBitDepth, + api_key: apiClient.accessToken(), + PlaySessionId: startingPlaySession, + StartTimeTicks: startPosition || 0, + EnableRedirection: !0, + EnableRemoteMedia: apphost.supports("remoteaudio") + }) + } + + function getAudioStreamUrlFromDeviceProfile(item, deviceProfile, maxBitrate, apiClient, startPosition) { + var transcodingProfile = deviceProfile.TranscodingProfiles.filter(function(p) { + return "Audio" === p.Type && "Streaming" === p.Context + })[0], + directPlayContainers = ""; + deviceProfile.DirectPlayProfiles.map(function(p) { + "Audio" === p.Type && (directPlayContainers ? directPlayContainers += "," + p.Container : directPlayContainers = p.Container, p.AudioCodec && (directPlayContainers += "|" + p.AudioCodec)) + }); + var maxValues = getAudioMaxValues(deviceProfile); + return getAudioStreamUrl(item, transcodingProfile, directPlayContainers, maxBitrate, apiClient, maxValues.maxAudioSampleRate, maxValues.maxAudioBitDepth, maxValues.maxAudioBitrate, startPosition) + } + + function getStreamUrls(items, deviceProfile, maxBitrate, apiClient, startPosition) { + var audioTranscodingProfile = deviceProfile.TranscodingProfiles.filter(function(p) { + return "Audio" === p.Type && "Streaming" === p.Context + })[0], + audioDirectPlayContainers = ""; + deviceProfile.DirectPlayProfiles.map(function(p) { + "Audio" === p.Type && (audioDirectPlayContainers ? audioDirectPlayContainers += "," + p.Container : audioDirectPlayContainers = p.Container, p.AudioCodec && (audioDirectPlayContainers += "|" + p.AudioCodec)) + }); + for (var maxValues = getAudioMaxValues(deviceProfile), streamUrls = [], i = 0, length = items.length; i < length; i++) { + var streamUrl, item = items[i]; + "Audio" !== item.MediaType || itemHelper.isLocalItem(item) || (streamUrl = getAudioStreamUrl(item, audioTranscodingProfile, audioDirectPlayContainers, maxBitrate, apiClient, maxValues.maxAudioSampleRate, maxValues.maxAudioBitDepth, maxValues.maxAudioBitrate, startPosition)), streamUrls.push(streamUrl || ""), 0 === i && (startPosition = 0) + } + return Promise.resolve(streamUrls) + } + + function setStreamUrls(items, deviceProfile, maxBitrate, apiClient, startPosition) { + return getStreamUrls(items, deviceProfile, maxBitrate, apiClient, startPosition).then(function(streamUrls) { + for (var i = 0, length = items.length; i < length; i++) { + var item = items[i], + streamUrl = streamUrls[i]; + streamUrl && (item.PresetMediaSource = { + StreamUrl: streamUrl, + Id: item.Id, + MediaStreams: [], + RunTimeTicks: item.RunTimeTicks + }) + } + }) + } + + function getPlaybackInfo(player, apiClient, item, deviceProfile, maxBitrate, startPosition, isPlayback, mediaSourceId, audioStreamIndex, subtitleStreamIndex, liveStreamId, enableDirectPlay, enableDirectStream, allowVideoStreamCopy, allowAudioStreamCopy) { + if (!itemHelper.isLocalItem(item) && "Audio" === item.MediaType) return Promise.resolve({ + MediaSources: [{ + StreamUrl: getAudioStreamUrlFromDeviceProfile(item, deviceProfile, maxBitrate, apiClient, startPosition), + Id: item.Id, + MediaStreams: [], + RunTimeTicks: item.RunTimeTicks + }] + }); + if (item.PresetMediaSource) return Promise.resolve({ + MediaSources: [item.PresetMediaSource] + }); + var itemId = item.Id, + query = { + UserId: apiClient.getCurrentUserId(), + StartTimeTicks: startPosition || 0 + }; + return isPlayback ? (query.IsPlayback = !0, query.AutoOpenLiveStream = !0) : (query.IsPlayback = !1, query.AutoOpenLiveStream = !1), null != audioStreamIndex && (query.AudioStreamIndex = audioStreamIndex), null != subtitleStreamIndex && (query.SubtitleStreamIndex = subtitleStreamIndex), null != enableDirectPlay && (query.EnableDirectPlay = enableDirectPlay), null != enableDirectStream && (query.EnableDirectStream = enableDirectStream), null != allowVideoStreamCopy && (query.AllowVideoStreamCopy = allowVideoStreamCopy), null != allowAudioStreamCopy && (query.AllowAudioStreamCopy = allowAudioStreamCopy), mediaSourceId && (query.MediaSourceId = mediaSourceId), liveStreamId && (query.LiveStreamId = liveStreamId), maxBitrate && (query.MaxStreamingBitrate = maxBitrate), player.enableMediaProbe && !player.enableMediaProbe(item) && (query.EnableMediaProbe = !1), !1 !== query.EnableDirectStream && player.supportsPlayMethod && !player.supportsPlayMethod("DirectStream", item) && (query.EnableDirectStream = !1), player.getDirectPlayProtocols && (query.DirectPlayProtocols = player.getDirectPlayProtocols()), apiClient.getPlaybackInfo(itemId, query, deviceProfile) + } + + function getOptimalMediaSource(apiClient, item, versions) { + var promises = versions.map(function(v) { + return supportsDirectPlay(apiClient, item, v) + }); + return promises.length ? Promise.all(promises).then(function(results) { + for (var i = 0, length = versions.length; i < length; i++) versions[i].enableDirectPlay = results[i] || !1; + var optimalVersion = versions.filter(function(v) { + return v.enableDirectPlay + })[0]; + return optimalVersion || (optimalVersion = versions.filter(function(v) { + return v.SupportsDirectStream + })[0]), (optimalVersion = optimalVersion || versions.filter(function(s) { + return s.SupportsTranscoding + })[0]) || versions[0] + }) : Promise.reject() + } + + function getLiveStream(player, apiClient, item, playSessionId, deviceProfile, maxBitrate, startPosition, mediaSource, audioStreamIndex, subtitleStreamIndex) { + var postData = { + DeviceProfile: deviceProfile, + OpenToken: mediaSource.OpenToken + }, + query = { + UserId: apiClient.getCurrentUserId(), + StartTimeTicks: startPosition || 0, + ItemId: item.Id, + PlaySessionId: playSessionId + }; + return maxBitrate && (query.MaxStreamingBitrate = maxBitrate), null != audioStreamIndex && (query.AudioStreamIndex = audioStreamIndex), null != subtitleStreamIndex && (query.SubtitleStreamIndex = subtitleStreamIndex), !1 !== query.EnableDirectStream && player.supportsPlayMethod && !player.supportsPlayMethod("DirectStream", item) && (query.EnableDirectStream = !1), apiClient.ajax({ + url: apiClient.getUrl("LiveStreams/Open", query), + type: "POST", + data: JSON.stringify(postData), + contentType: "application/json", + dataType: "json" + }) + } + + function isHostReachable(mediaSource, apiClient) { + return mediaSource.IsRemote ? Promise.resolve(!0) : apiClient.getEndpointInfo().then(function(endpointInfo) { + if (endpointInfo.IsInNetwork) { + if (!endpointInfo.IsLocal) { + var path = (mediaSource.Path || "").toLowerCase(); + if (-1 !== path.indexOf("localhost") || -1 !== path.indexOf("127.0.0.1")) return Promise.resolve(!1) + } + return Promise.resolve(!0) + } + return Promise.resolve(!1) + }) + } + + function supportsDirectPlay(apiClient, item, mediaSource) { + var isFolderRip = "BluRay" === mediaSource.VideoType || "Dvd" === mediaSource.VideoType || "HdDvd" === mediaSource.VideoType; + if (mediaSource.SupportsDirectPlay || isFolderRip) { + if (mediaSource.IsRemote && !apphost.supports("remotevideo")) return Promise.resolve(!1); + if ("Http" === mediaSource.Protocol && !mediaSource.RequiredHttpHeaders.length) return mediaSource.SupportsDirectStream || mediaSource.SupportsTranscoding ? isHostReachable(mediaSource, apiClient) : Promise.resolve(!0); + if ("File" === mediaSource.Protocol) return new Promise(function(resolve, reject) { + require(["filesystem"], function(filesystem) { + filesystem[isFolderRip ? "directoryExists" : "fileExists"](mediaSource.Path).then(function() { + resolve(!0) + }, function() { + resolve(!1) + }) + }) + }) + } + return Promise.resolve(!1) + } + + function validatePlaybackInfoResult(instance, result) { + return !result.ErrorCode || (showPlaybackInfoErrorMessage(instance, result.ErrorCode), !1) + } + + function showPlaybackInfoErrorMessage(instance, errorCode, playNextTrack) { + require(["alert"], function(alert) { + alert({ + text: globalize.translate("sharedcomponents#PlaybackError" + errorCode), + title: globalize.translate("sharedcomponents#HeaderPlaybackError") + }).then(function() { + playNextTrack && instance.nextTrack() + }) + }) + } + + function normalizePlayOptions(playOptions) { + playOptions.fullscreen = !1 !== playOptions.fullscreen + } + + function truncatePlayOptions(playOptions) { + return { + fullscreen: playOptions.fullscreen, + mediaSourceId: playOptions.mediaSourceId, + audioStreamIndex: playOptions.audioStreamIndex, + subtitleStreamIndex: playOptions.subtitleStreamIndex, + startPositionTicks: playOptions.startPositionTicks + } + } + + function getNowPlayingItemForReporting(player, item, mediaSource) { + var nowPlayingItem = Object.assign({}, item); + return mediaSource && (nowPlayingItem.RunTimeTicks = mediaSource.RunTimeTicks, nowPlayingItem.MediaStreams = mediaSource.MediaStreams, nowPlayingItem.MediaSources = null), nowPlayingItem.RunTimeTicks = nowPlayingItem.RunTimeTicks || 1e4 * player.duration(), nowPlayingItem + } + + function displayPlayerIndividually(player) { + return !player.isLocalPlayer + } + + function createTarget(instance, player) { + return { + name: player.name, + id: player.id, + playerName: player.name, + playableMediaTypes: ["Audio", "Video", "Game", "Photo", "Book"].map(player.canPlayMediaType), + isLocalPlayer: player.isLocalPlayer, + supportedCommands: instance.getSupportedCommands(player) + } + } + + function getPlayerTargets(player) { + return player.getTargets ? player.getTargets() : Promise.resolve([createTarget(player)]) + } + + function sortPlayerTargets(a, b) { + var aVal = a.isLocalPlayer ? 0 : 1, + bVal = b.isLocalPlayer ? 0 : 1; + return aVal = aVal.toString() + a.name, bVal = bVal.toString() + b.name, aVal.localeCompare(bVal) + } + + function PlaybackManager() { + function getCurrentSubtitleStream(player) { + if (!player) throw new Error("player cannot be null"); + var index = getPlayerData(player).subtitleStreamIndex; + return null == index || -1 === index ? null : getSubtitleStream(player, index) + } + + function getSubtitleStream(player, index) { + return self.subtitleTracks(player).filter(function(s) { + return "Subtitle" === s.Type && s.Index === index + })[0] + } + + function removeCurrentPlayer(player) { + var previousPlayer = self._currentPlayer; + previousPlayer && player.id !== previousPlayer.id || setCurrentPlayerInternal(null) + } + + function setCurrentPlayerInternal(player, targetInfo) { + var previousPlayer = self._currentPlayer, + previousTargetInfo = currentTargetInfo; + if (player && !targetInfo && player.isLocalPlayer && (targetInfo = createTarget(self, player)), player && !targetInfo) throw new Error("targetInfo cannot be null"); + currentPairingId = null, self._currentPlayer = player, currentTargetInfo = targetInfo, targetInfo && console.log("Active player: " + JSON.stringify(targetInfo)), player && player.isLocalPlayer && (lastLocalPlayer = player), previousPlayer && self.endPlayerUpdates(previousPlayer), player && self.beginPlayerUpdates(player), triggerPlayerChange(self, player, targetInfo, previousPlayer, previousTargetInfo) + } + + function getDefaultPlayOptions() { + return { + fullscreen: !0 + } + } + + function isAudioStreamSupported(mediaSource, index, deviceProfile) { + var mediaStream, i, length, mediaStreams = mediaSource.MediaStreams; + for (i = 0, length = mediaStreams.length; i < length; i++) + if ("Audio" === mediaStreams[i].Type && mediaStreams[i].Index === index) { + mediaStream = mediaStreams[i]; + break + } if (!mediaStream) return !1; + var codec = (mediaStream.Codec || "").toLowerCase(); + return !!codec && (deviceProfile.DirectPlayProfiles || []).filter(function(p) { + return "Video" === p.Type && (!p.AudioCodec || (0 === p.AudioCodec.indexOf("-") ? -1 === p.AudioCodec.toLowerCase().indexOf(codec) : -1 !== p.AudioCodec.toLowerCase().indexOf(codec))) + }).length > 0 + } + + function getSavedMaxStreamingBitrate(apiClient, mediaType) { + apiClient || (apiClient = connectionManager.currentApiClient()); + var endpointInfo = apiClient.getSavedEndpointInfo() || {}; + return appSettings.maxStreamingBitrate(endpointInfo.IsInNetwork, mediaType) + } + + function getDeliveryMethod(subtitleStream) { + return subtitleStream.DeliveryMethod ? subtitleStream.DeliveryMethod : subtitleStream.IsExternal ? "External" : "Embed" + } + + function canPlayerSeek(player) { + if (!player) throw new Error("player cannot be null"); + return -1 !== (getPlayerData(player).streamInfo.url || "").toLowerCase().indexOf(".m3u8") || (player.seekable ? player.seekable() : !("Transcode" === self.playMethod(player)) && player.duration()) + } + + function changeStream(player, ticks, params) { + if (canPlayerSeek(player) && null == params) return void player.currentTime(parseInt(ticks / 1e4)); + params = params || {}; + var liveStreamId = getPlayerData(player).streamInfo.liveStreamId, + lastMediaInfoQuery = getPlayerData(player).streamInfo.lastMediaInfoQuery, + playSessionId = self.playSessionId(player), + currentItem = self.currentItem(player); + player.getDeviceProfile(currentItem, { + isRetry: !1 === params.EnableDirectPlay + }).then(function(deviceProfile) { + var audioStreamIndex = null == params.AudioStreamIndex ? getPlayerData(player).audioStreamIndex : params.AudioStreamIndex, + subtitleStreamIndex = null == params.SubtitleStreamIndex ? getPlayerData(player).subtitleStreamIndex : params.SubtitleStreamIndex, + currentMediaSource = self.currentMediaSource(player), + apiClient = connectionManager.getApiClient(currentItem.ServerId); + ticks && (ticks = parseInt(ticks)); + var maxBitrate = params.MaxStreamingBitrate || self.getMaxStreamingBitrate(player), + currentPlayOptions = currentItem.playOptions || {}; + getPlaybackInfo(player, apiClient, currentItem, deviceProfile, maxBitrate, ticks, !0, currentMediaSource.Id, audioStreamIndex, subtitleStreamIndex, liveStreamId, params.EnableDirectPlay, params.EnableDirectStream, params.AllowVideoStreamCopy, params.AllowAudioStreamCopy).then(function(result) { + if (validatePlaybackInfoResult(self, result)) { + currentMediaSource = result.MediaSources[0]; + var streamInfo = createStreamInfo(apiClient, currentItem.MediaType, currentItem, currentMediaSource, ticks); + if (streamInfo.fullscreen = currentPlayOptions.fullscreen, streamInfo.lastMediaInfoQuery = lastMediaInfoQuery, !streamInfo.url) return void showPlaybackInfoErrorMessage(self, "NoCompatibleStream", !0); + getPlayerData(player).subtitleStreamIndex = subtitleStreamIndex, getPlayerData(player).audioStreamIndex = audioStreamIndex, getPlayerData(player).maxStreamingBitrate = maxBitrate, changeStreamToUrl(apiClient, player, playSessionId, streamInfo) + } + }) + }) + } + + function changeStreamToUrl(apiClient, player, playSessionId, streamInfo, newPositionTicks) { + var playerData = getPlayerData(player); + playerData.isChangingStream = !0, playerData.streamInfo && playSessionId ? apiClient.stopActiveEncodings(playSessionId).then(function() { + var afterSetSrc = function() { + apiClient.stopActiveEncodings(playSessionId) + }; + setSrcIntoPlayer(apiClient, player, streamInfo).then(afterSetSrc, afterSetSrc) + }) : setSrcIntoPlayer(apiClient, player, streamInfo) + } + + function setSrcIntoPlayer(apiClient, player, streamInfo) { + return player.play(streamInfo).then(function() { + var playerData = getPlayerData(player); + playerData.isChangingStream = !1, playerData.streamInfo = streamInfo, streamInfo.started = !0, streamInfo.ended = !1, sendProgressUpdate(player, "timeupdate") + }, function(e) { + getPlayerData(player).isChangingStream = !1, onPlaybackError.call(player, e, { + type: "mediadecodeerror", + streamInfo: streamInfo + }) + }) + } + + function translateItemsForPlayback(items, options) { + var promise, firstItem = items[0], + serverId = firstItem.ServerId, + queryOptions = options.queryOptions || {}; + return "Program" === firstItem.Type ? promise = getItemsForPlayback(serverId, { + Ids: firstItem.ChannelId + }) : "Playlist" === firstItem.Type ? promise = getItemsForPlayback(serverId, { + ParentId: firstItem.Id, + SortBy: options.shuffle ? "Random" : null + }) : "MusicArtist" === firstItem.Type ? promise = getItemsForPlayback(serverId, { + ArtistIds: firstItem.Id, + Filters: "IsNotFolder", + Recursive: !0, + SortBy: options.shuffle ? "Random" : "SortName", + MediaTypes: "Audio" + }) : "Photo" === firstItem.MediaType ? promise = getItemsForPlayback(serverId, { + ParentId: firstItem.ParentId, + Filters: "IsNotFolder", + Recursive: !1, + SortBy: options.shuffle ? "Random" : "SortName", + MediaTypes: "Photo,Video", + Limit: 5e3 + }).then(function(result) { + var items = result.Items, + index = items.map(function(i) { + return i.Id + }).indexOf(firstItem.Id); + return -1 === index && (index = 0), options.startIndex = index, Promise.resolve(result) + }) : "PhotoAlbum" === firstItem.Type ? promise = getItemsForPlayback(serverId, { + ParentId: firstItem.Id, + Filters: "IsNotFolder", + Recursive: !1, + SortBy: options.shuffle ? "Random" : "SortName", + MediaTypes: "Photo,Video", + Limit: 1e3 + }) : "MusicGenre" === firstItem.Type ? promise = getItemsForPlayback(serverId, { + GenreIds: firstItem.Id, + Filters: "IsNotFolder", + Recursive: !0, + SortBy: options.shuffle ? "Random" : "SortName", + MediaTypes: "Audio" + }) : firstItem.IsFolder ? promise = getItemsForPlayback(serverId, mergePlaybackQueries({ + ParentId: firstItem.Id, + Filters: "IsNotFolder", + Recursive: !0, + SortBy: options.shuffle ? "Random" : -1 === ["BoxSet"].indexOf(firstItem.Type) ? "SortName" : null, + MediaTypes: "Audio,Video" + }, queryOptions)) : "Episode" === firstItem.Type && 1 === items.length && !1 !== getPlayer(firstItem, options).supportsProgress && (promise = new Promise(function(resolve, reject) { + var apiClient = connectionManager.getApiClient(firstItem.ServerId); + apiClient.getCurrentUser().then(function(user) { + if (!user.Configuration.EnableNextEpisodeAutoPlay || !firstItem.SeriesId) return void resolve(null); + apiClient.getEpisodes(firstItem.SeriesId, { + IsVirtualUnaired: !1, + IsMissing: !1, + UserId: apiClient.getCurrentUserId(), + Fields: "Chapters" + }).then(function(episodesResult) { + var foundItem = !1; + episodesResult.Items = episodesResult.Items.filter(function(e) { + return !!foundItem || e.Id === firstItem.Id && (foundItem = !0, !0) + }), episodesResult.TotalRecordCount = episodesResult.Items.length, resolve(episodesResult) + }, reject) + }) + })), promise ? promise.then(function(result) { + return result ? result.Items : items + }) : Promise.resolve(items) + } + + function getPlayerData(player) { + if (!player) throw new Error("player cannot be null"); + if (!player.name) throw new Error("player name cannot be null"); + var state = playerStates[player.name]; + return state || (playerStates[player.name] = {}, state = playerStates[player.name]), player + } + + function getCurrentTicks(player) { + if (!player) throw new Error("player cannot be null"); + var playerTime = Math.floor(1e4 * (player || self._currentPlayer).currentTime()); + return getPlayerData(player).streamInfo && (playerTime += getPlayerData(player).streamInfo.transcodingOffsetTicks || 0), playerTime + } + + function playPhotos(items, options, user) { + var playStartIndex = options.startIndex || 0, + player = getPlayer(items[playStartIndex], options); + return loading.hide(), options.items = items, player.play(options) + } + + function playWithIntros(items, options, user) { + var playStartIndex = options.startIndex || 0, + firstItem = items[playStartIndex]; + if (firstItem || (playStartIndex = 0, firstItem = items[playStartIndex]), !firstItem) return showPlaybackInfoErrorMessage(self, "NoCompatibleStream", !1), Promise.reject(); + if ("Photo" === firstItem.MediaType) return playPhotos(items, options, user); + var apiClient = connectionManager.getApiClient(firstItem.ServerId); + return getIntros(firstItem, apiClient, options).then(function(introsResult) { + var introPlayOptions, introItems = introsResult.Items; + return firstItem.playOptions = truncatePlayOptions(options), introPlayOptions = introItems.length ? { + fullscreen: firstItem.playOptions.fullscreen + } : firstItem.playOptions, items = introItems.concat(items), introPlayOptions.items = items, introPlayOptions.startIndex = playStartIndex, playInternal(items[playStartIndex], introPlayOptions, function() { + self._playQueueManager.setPlaylist(items), setPlaylistState(items[playStartIndex].PlaylistItemId, playStartIndex), loading.hide() + }) + }) + } + + function setPlaylistState(playlistItemId, index) { + isNaN(index) || self._playQueueManager.setPlaylistState(playlistItemId, index) + } + + function playInternal(item, playOptions, onPlaybackStartedFn) { + return item.IsPlaceHolder ? (loading.hide(), showPlaybackInfoErrorMessage(self, "PlaceHolder", !0), Promise.reject()) : (normalizePlayOptions(playOptions), playOptions.isFirstItem ? playOptions.isFirstItem = !1 : playOptions.isFirstItem = !0, runInterceptors(item, playOptions).then(function() { + playOptions.fullscreen && loading.show(); + var mediaType = item.MediaType, + onBitrateDetectionFailure = function() { + return playAfterBitrateDetect(getSavedMaxStreamingBitrate(connectionManager.getApiClient(item.ServerId), mediaType), item, playOptions, onPlaybackStartedFn) + }; + if (!isServerItem(item) || itemHelper.isLocalItem(item)) return onBitrateDetectionFailure(); + var apiClient = connectionManager.getApiClient(item.ServerId); + apiClient.getEndpointInfo().then(function(endpointInfo) { + if (("Video" === mediaType || "Audio" === mediaType) && appSettings.enableAutomaticBitrateDetection(endpointInfo.IsInNetwork, mediaType)) return apiClient.detectBitrate().then(function(bitrate) { + return appSettings.maxStreamingBitrate(endpointInfo.IsInNetwork, mediaType, bitrate), playAfterBitrateDetect(bitrate, item, playOptions, onPlaybackStartedFn) + }, onBitrateDetectionFailure); + onBitrateDetectionFailure() + }, onBitrateDetectionFailure) + }, onInterceptorRejection)) + } + + function onInterceptorRejection() { + var player = self._currentPlayer; + return player && (destroyPlayer(player), removeCurrentPlayer(player)), events.trigger(self, "playbackcancelled"), Promise.reject() + } + + function destroyPlayer(player) { + player.destroy() + } + + function runInterceptors(item, playOptions) { + return new Promise(function(resolve, reject) { + var interceptors = pluginManager.ofType("preplayintercept"); + if (interceptors.sort(function(a, b) { + return (a.order || 0) - (b.order || 0) + }), !interceptors.length) return void resolve(); + loading.hide(); + var options = Object.assign({}, playOptions); + options.mediaType = item.MediaType, options.item = item, runNextPrePlay(interceptors, 0, options, resolve, reject) + }) + } + + function runNextPrePlay(interceptors, index, options, resolve, reject) { + if (index >= interceptors.length) return void resolve(); + interceptors[index].intercept(options).then(function() { + runNextPrePlay(interceptors, index + 1, options, resolve, reject) + }, reject) + } + + function sendPlaybackListToPlayer(player, items, deviceProfile, maxBitrate, apiClient, startPositionTicks, mediaSourceId, audioStreamIndex, subtitleStreamIndex, startIndex) { + return setStreamUrls(items, deviceProfile, maxBitrate, apiClient, startPositionTicks).then(function() { + return loading.hide(), player.play({ + items: items, + startPositionTicks: startPositionTicks || 0, + mediaSourceId: mediaSourceId, + audioStreamIndex: audioStreamIndex, + subtitleStreamIndex: subtitleStreamIndex, + startIndex: startIndex + }) + }) + } + + function playAfterBitrateDetect(maxBitrate, item, playOptions, onPlaybackStartedFn) { + var promise, startPosition = playOptions.startPositionTicks, + player = getPlayer(item, playOptions), + activePlayer = self._currentPlayer; + return activePlayer ? (self._playNextAfterEnded = !1, promise = onPlaybackChanging(activePlayer, player, item)) : promise = Promise.resolve(), isServerItem(item) && "Game" !== item.MediaType && "Book" !== item.MediaType ? Promise.all([promise, player.getDeviceProfile(item)]).then(function(responses) { + var deviceProfile = responses[1], + apiClient = connectionManager.getApiClient(item.ServerId), + mediaSourceId = playOptions.mediaSourceId, + audioStreamIndex = playOptions.audioStreamIndex, + subtitleStreamIndex = playOptions.subtitleStreamIndex; + return player && !enableLocalPlaylistManagement(player) ? sendPlaybackListToPlayer(player, playOptions.items, deviceProfile, maxBitrate, apiClient, startPosition, mediaSourceId, audioStreamIndex, subtitleStreamIndex, playOptions.startIndex) : (playOptions.items = null, getPlaybackMediaSource(player, apiClient, deviceProfile, maxBitrate, item, startPosition, mediaSourceId, audioStreamIndex, subtitleStreamIndex).then(function(mediaSource) { + var streamInfo = createStreamInfo(apiClient, item.MediaType, item, mediaSource, startPosition); + return streamInfo.fullscreen = playOptions.fullscreen, getPlayerData(player).isChangingStream = !1, getPlayerData(player).maxStreamingBitrate = maxBitrate, player.play(streamInfo).then(function() { + loading.hide(), onPlaybackStartedFn(), onPlaybackStarted(player, playOptions, streamInfo, mediaSource) + }, function(err) { + onPlaybackStartedFn(), onPlaybackStarted(player, playOptions, streamInfo, mediaSource), setTimeout(function() { + onPlaybackError.call(player, err, { + type: "mediadecodeerror", + streamInfo: streamInfo + }) + }, 100) + }) + })) + }) : promise.then(function() { + var streamInfo = createStreamInfoFromUrlItem(item); + return streamInfo.fullscreen = playOptions.fullscreen, getPlayerData(player).isChangingStream = !1, player.play(streamInfo).then(function() { + loading.hide(), onPlaybackStartedFn(), onPlaybackStarted(player, playOptions, streamInfo) + }, function() { + self.stop(player) + }) + }) + } + + function createStreamInfo(apiClient, type, item, mediaSource, startPosition) { + var mediaUrl, contentType, directOptions, transcodingOffsetTicks = 0, + playerStartPositionTicks = startPosition, + liveStreamId = mediaSource.LiveStreamId, + playMethod = "Transcode", + mediaSourceContainer = (mediaSource.Container || "").toLowerCase(); + if ("Video" === type || "Audio" === type) + if (contentType = getMimeType(type.toLowerCase(), mediaSourceContainer), mediaSource.enableDirectPlay) mediaUrl = mediaSource.Path, playMethod = "DirectPlay"; + else if (mediaSource.StreamUrl) playMethod = "Transcode", mediaUrl = mediaSource.StreamUrl; + else if (mediaSource.SupportsDirectStream) { + directOptions = { + Static: !0, + mediaSourceId: mediaSource.Id, + deviceId: apiClient.deviceId(), + api_key: apiClient.accessToken() + }, mediaSource.ETag && (directOptions.Tag = mediaSource.ETag), mediaSource.LiveStreamId && (directOptions.LiveStreamId = mediaSource.LiveStreamId); + var prefix = "Video" === type ? "Videos" : "Audio"; + mediaUrl = apiClient.getUrl(prefix + "/" + item.Id + "/stream." + mediaSourceContainer, directOptions), playMethod = "DirectStream" + } else mediaSource.SupportsTranscoding && (mediaUrl = apiClient.getUrl(mediaSource.TranscodingUrl), "hls" === mediaSource.TranscodingSubProtocol ? contentType = "application/x-mpegURL" : (playerStartPositionTicks = null, contentType = getMimeType(type.toLowerCase(), mediaSource.TranscodingContainer), -1 === mediaUrl.toLowerCase().indexOf("copytimestamps=true") && (transcodingOffsetTicks = startPosition || 0))); + else mediaUrl = mediaSource.Path, playMethod = "DirectPlay"; + !mediaUrl && mediaSource.SupportsDirectPlay && (mediaUrl = mediaSource.Path, playMethod = "DirectPlay"); + var resultInfo = { + url: mediaUrl, + mimeType: contentType, + transcodingOffsetTicks: transcodingOffsetTicks, + playMethod: playMethod, + playerStartPositionTicks: playerStartPositionTicks, + item: item, + mediaSource: mediaSource, + textTracks: getTextTracks(apiClient, item, mediaSource), + tracks: getTextTracks(apiClient, item, mediaSource), + mediaType: type, + liveStreamId: liveStreamId, + playSessionId: getParam("playSessionId", mediaUrl), + title: item.Name + }, + backdropUrl = backdropImageUrl(apiClient, item, {}); + return backdropUrl && (resultInfo.backdropUrl = backdropUrl), resultInfo + } + + function getTextTracks(apiClient, item, mediaSource) { + for (var subtitleStreams = mediaSource.MediaStreams.filter(function(s) { + return "Subtitle" === s.Type + }), textStreams = subtitleStreams.filter(function(s) { + return "External" === s.DeliveryMethod + }), tracks = [], i = 0, length = textStreams.length; i < length; i++) { + var textStreamUrl, textStream = textStreams[i]; + textStreamUrl = itemHelper.isLocalItem(item) ? textStream.Path : textStream.IsExternalUrl ? textStream.DeliveryUrl : apiClient.getUrl(textStream.DeliveryUrl), tracks.push({ + url: textStreamUrl, + language: textStream.Language || "und", + isDefault: textStream.Index === mediaSource.DefaultSubtitleStreamIndex, + index: textStream.Index, + format: textStream.Codec + }) + } + return tracks + } + + function getPlaybackMediaSource(player, apiClient, deviceProfile, maxBitrate, item, startPosition, mediaSourceId, audioStreamIndex, subtitleStreamIndex) { + return getPlaybackInfo(player, apiClient, item, deviceProfile, maxBitrate, startPosition, !0, mediaSourceId, audioStreamIndex, subtitleStreamIndex, null).then(function(playbackInfoResult) { + return validatePlaybackInfoResult(self, playbackInfoResult) ? getOptimalMediaSource(apiClient, item, playbackInfoResult.MediaSources).then(function(mediaSource) { + return mediaSource ? mediaSource.RequiresOpening && !mediaSource.LiveStreamId ? getLiveStream(player, apiClient, item, playbackInfoResult.PlaySessionId, deviceProfile, maxBitrate, startPosition, mediaSource, null, null).then(function(openLiveStreamResult) { + return supportsDirectPlay(apiClient, item, openLiveStreamResult.MediaSource).then(function(result) { + return openLiveStreamResult.MediaSource.enableDirectPlay = result, openLiveStreamResult.MediaSource + }) + }) : mediaSource : (showPlaybackInfoErrorMessage(self, "NoCompatibleStream"), Promise.reject()) + }) : Promise.reject() + }) + } + + function getPlayer(item, playOptions, forceLocalPlayers) { + var serverItem = isServerItem(item); + return getAutomaticPlayers(self, forceLocalPlayers).filter(function(p) { + if (p.canPlayMediaType(item.MediaType)) { + if (serverItem) return !p.canPlayItem || p.canPlayItem(item, playOptions); + if (item.Url && p.canPlayUrl) return p.canPlayUrl(item.Url) + } + return !1 + })[0] + } + + function queue(options, mode, player) { + if (!(player = player || self._currentPlayer)) return self.play(options); + if (options.items) return translateItemsForPlayback(options.items, options).then(function(items) { + queueAll(items, mode, player) + }); + if (!options.serverId) throw new Error("serverId required!"); + return getItemsForPlayback(options.serverId, { + Ids: options.ids.join(",") + }).then(function(result) { + return translateItemsForPlayback(result.Items, options).then(function(items) { + queueAll(items, mode, player) + }) + }) + } + + function queueAll(items, mode, player) { + if (items.length) { + if (!player.isLocalPlayer) return void("next" === mode ? player.queueNext({ + items: items + }) : player.queue({ + items: items + })); + if (player && !enableLocalPlaylistManagement(player)) { + var apiClient = connectionManager.getApiClient(items[0].ServerId); + return void player.getDeviceProfile(items[0]).then(function(profile) { + setStreamUrls(items, profile, self.getMaxStreamingBitrate(player), apiClient, 0).then(function() { + "next" === mode ? player.queueNext(items) : player.queue(items) + }) + }) + } + "next" === mode ? self._playQueueManager.queueNext(items) : self._playQueueManager.queue(items) + } + } + + function onPlayerProgressInterval() { + sendProgressUpdate(this, "timeupdate") + } + + function startPlaybackProgressTimer(player) { + stopPlaybackProgressTimer(player), player._progressInterval = setInterval(onPlayerProgressInterval.bind(player), 1e4) + } + + function stopPlaybackProgressTimer(player) { + player._progressInterval && (clearInterval(player._progressInterval), player._progressInterval = null) + } + + function onPlaybackStarted(player, playOptions, streamInfo, mediaSource) { + if (!player) throw new Error("player cannot be null"); + setCurrentPlayerInternal(player); + var playerData = getPlayerData(player); + playerData.streamInfo = streamInfo, streamInfo.playbackStartTimeTicks = 1e4 * (new Date).getTime(), mediaSource ? (playerData.audioStreamIndex = mediaSource.DefaultAudioStreamIndex, playerData.subtitleStreamIndex = mediaSource.DefaultSubtitleStreamIndex) : (playerData.audioStreamIndex = null, playerData.subtitleStreamIndex = null), self._playNextAfterEnded = !0; + var isFirstItem = playOptions.isFirstItem, + fullscreen = playOptions.fullscreen, + state = self.getPlayerState(player, streamInfo.item, streamInfo.mediaSource); + reportPlayback(self, state, player, !0, state.NowPlayingItem.ServerId, "reportPlaybackStart"), state.IsFirstItem = isFirstItem, state.IsFullscreen = fullscreen, events.trigger(player, "playbackstart", [state]), events.trigger(self, "playbackstart", [player, state]), streamInfo.started = !0, startPlaybackProgressTimer(player) + } + + function onPlaybackStartedFromSelfManagingPlayer(e, item, mediaSource) { + var player = this; + setCurrentPlayerInternal(player); + var playOptions = item.playOptions || {}, + isFirstItem = playOptions.isFirstItem, + fullscreen = playOptions.fullscreen; + playOptions.isFirstItem = !1; + var playerData = getPlayerData(player); + playerData.streamInfo = {}; + var streamInfo = playerData.streamInfo; + streamInfo.playbackStartTimeTicks = 1e4 * (new Date).getTime(); + var state = self.getPlayerState(player, item, mediaSource); + reportPlayback(self, state, player, !0, state.NowPlayingItem.ServerId, "reportPlaybackStart"), state.IsFirstItem = isFirstItem, state.IsFullscreen = fullscreen, events.trigger(player, "playbackstart", [state]), events.trigger(self, "playbackstart", [player, state]), streamInfo.started = !0, startPlaybackProgressTimer(player) + } + + function onPlaybackStoppedFromSelfManagingPlayer(e, playerStopInfo) { + var player = this; + stopPlaybackProgressTimer(player); + var state = self.getPlayerState(player, playerStopInfo.item, playerStopInfo.mediaSource), + nextItem = playerStopInfo.nextItem, + nextMediaType = playerStopInfo.nextMediaType, + playbackStopInfo = { + player: player, + state: state, + nextItem: nextItem ? nextItem.item : null, + nextMediaType: nextMediaType + }; + state.NextMediaType = nextMediaType, getPlayerData(player).streamInfo.ended = !0, isServerItem(playerStopInfo.item) && (state.PlayState.PositionTicks = 1e4 * (playerStopInfo.positionMs || 0), reportPlayback(self, state, player, !0, playerStopInfo.item.ServerId, "reportPlaybackStopped")), state.NextItem = playbackStopInfo.nextItem, events.trigger(player, "playbackstop", [state]), events.trigger(self, "playbackstop", [playbackStopInfo]); + var nextItemPlayOptions = nextItem ? nextItem.item.playOptions || getDefaultPlayOptions() : getDefaultPlayOptions(); + (nextItem ? getPlayer(nextItem.item, nextItemPlayOptions) : null) !== player && (destroyPlayer(player), removeCurrentPlayer(player)) + } + + function enablePlaybackRetryWithTranscoding(streamInfo, errorType, currentlyPreventsVideoStreamCopy, currentlyPreventsAudioStreamCopy) { + return !(!streamInfo.mediaSource.SupportsTranscoding || currentlyPreventsVideoStreamCopy && currentlyPreventsAudioStreamCopy) + } + + function onPlaybackError(e, error) { + var player = this; + error = error || {}; + var errorType = error.type; + console.log("playbackmanager playback error type: " + (errorType || "")); + var streamInfo = error.streamInfo || getPlayerData(player).streamInfo; + if (streamInfo) { + var currentlyPreventsVideoStreamCopy = -1 !== streamInfo.url.toLowerCase().indexOf("allowvideostreamcopy=false"), + currentlyPreventsAudioStreamCopy = -1 !== streamInfo.url.toLowerCase().indexOf("allowaudiostreamcopy=false"); + if (enablePlaybackRetryWithTranscoding(streamInfo, errorType, currentlyPreventsVideoStreamCopy, currentlyPreventsAudioStreamCopy)) { + return void changeStream(player, getCurrentTicks(player) || streamInfo.playerStartPositionTicks, { + EnableDirectPlay: !1, + EnableDirectStream: !1, + AllowVideoStreamCopy: !1, + AllowAudioStreamCopy: !currentlyPreventsAudioStreamCopy && !currentlyPreventsVideoStreamCopy && null + }, !0) + } + } + onPlaybackStopped.call(player, e, "NoCompatibleStream") + } + + function onPlaybackStopped(e, displayErrorCode) { + var player = this; + if (!getPlayerData(player).isChangingStream) { + stopPlaybackProgressTimer(player); + var state = self.getPlayerState(player), + streamInfo = getPlayerData(player).streamInfo, + nextItem = self._playNextAfterEnded ? self._playQueueManager.getNextItemInfo() : null, + nextMediaType = nextItem ? nextItem.item.MediaType : null, + playbackStopInfo = { + player: player, + state: state, + nextItem: nextItem ? nextItem.item : null, + nextMediaType: nextMediaType + }; + state.NextMediaType = nextMediaType, isServerItem(streamInfo.item) && (!1 === player.supportsProgress && state.PlayState && !state.PlayState.PositionTicks && (state.PlayState.PositionTicks = streamInfo.item.RunTimeTicks), streamInfo.ended = !0, reportPlayback(self, state, player, !0, streamInfo.item.ServerId, "reportPlaybackStopped")), state.NextItem = playbackStopInfo.nextItem, nextItem || self._playQueueManager.reset(), events.trigger(player, "playbackstop", [state]), events.trigger(self, "playbackstop", [playbackStopInfo]); + var nextItemPlayOptions = nextItem ? nextItem.item.playOptions || getDefaultPlayOptions() : getDefaultPlayOptions(); + (nextItem ? getPlayer(nextItem.item, nextItemPlayOptions) : null) !== player && (destroyPlayer(player), removeCurrentPlayer(player)), displayErrorCode && "string" == typeof displayErrorCode ? showPlaybackInfoErrorMessage(self, displayErrorCode, nextItem) : nextItem && self.nextTrack() + } + } + + function onPlaybackChanging(activePlayer, newPlayer, newItem) { + var promise, state = self.getPlayerState(activePlayer), + serverId = self.currentItem(activePlayer).ServerId; + return stopPlaybackProgressTimer(activePlayer), unbindStopped(activePlayer), promise = activePlayer === newPlayer ? activePlayer.stop(!1) : activePlayer.stop(!0), promise.then(function() { + bindStopped(activePlayer), enableLocalPlaylistManagement(activePlayer) && reportPlayback(self, state, activePlayer, !0, serverId, "reportPlaybackStopped"), events.trigger(self, "playbackstop", [{ + player: activePlayer, + state: state, + nextItem: newItem, + nextMediaType: newItem.MediaType + }]) + }) + } + + function bindStopped(player) { + enableLocalPlaylistManagement(player) && (events.off(player, "stopped", onPlaybackStopped), events.on(player, "stopped", onPlaybackStopped)) + } + + function onPlaybackTimeUpdate(e) { + sendProgressUpdate(this, "timeupdate") + } + + function onPlaybackPause(e) { + sendProgressUpdate(this, "pause") + } + + function onPlaybackUnpause(e) { + sendProgressUpdate(this, "unpause") + } + + function onPlaybackVolumeChange(e) { + sendProgressUpdate(this, "volumechange") + } + + function onRepeatModeChange(e) { + sendProgressUpdate(this, "repeatmodechange") + } + + function onPlaylistItemMove(e) { + sendProgressUpdate(this, "playlistitemmove", !0) + } + + function onPlaylistItemRemove(e) { + sendProgressUpdate(this, "playlistitemremove", !0) + } + + function onPlaylistItemAdd(e) { + sendProgressUpdate(this, "playlistitemadd", !0) + } + + function unbindStopped(player) { + events.off(player, "stopped", onPlaybackStopped) + } + + function initLegacyVolumeMethods(player) { + player.getVolume = function() { + return player.volume() + }, player.setVolume = function(val) { + return player.volume(val) + } + } + + function initMediaPlayer(player) { + players.push(player), players.sort(function(a, b) { + return (a.priority || 0) - (b.priority || 0) + }), !1 !== player.isLocalPlayer && (player.isLocalPlayer = !0), player.currentState = {}, player.getVolume && player.setVolume || initLegacyVolumeMethods(player), enableLocalPlaylistManagement(player) ? (events.on(player, "error", onPlaybackError), events.on(player, "timeupdate", onPlaybackTimeUpdate), events.on(player, "pause", onPlaybackPause), events.on(player, "unpause", onPlaybackUnpause), events.on(player, "volumechange", onPlaybackVolumeChange), events.on(player, "repeatmodechange", onRepeatModeChange), events.on(player, "playlistitemmove", onPlaylistItemMove), events.on(player, "playlistitemremove", onPlaylistItemRemove), events.on(player, "playlistitemadd", onPlaylistItemAdd)) : player.isLocalPlayer && (events.on(player, "itemstarted", onPlaybackStartedFromSelfManagingPlayer), events.on(player, "itemstopped", onPlaybackStoppedFromSelfManagingPlayer), events.on(player, "timeupdate", onPlaybackTimeUpdate), events.on(player, "pause", onPlaybackPause), events.on(player, "unpause", onPlaybackUnpause), events.on(player, "volumechange", onPlaybackVolumeChange), events.on(player, "repeatmodechange", onRepeatModeChange), events.on(player, "playlistitemmove", onPlaylistItemMove), events.on(player, "playlistitemremove", onPlaylistItemRemove), events.on(player, "playlistitemadd", onPlaylistItemAdd)), player.isLocalPlayer && bindToFullscreenChange(player), bindStopped(player) + } + + function sendProgressUpdate(player, progressEventName, reportPlaylist) { + if (!player) throw new Error("player cannot be null"); + var state = self.getPlayerState(player); + if (state.NowPlayingItem) { + var serverId = state.NowPlayingItem.ServerId, + streamInfo = getPlayerData(player).streamInfo; + streamInfo && streamInfo.started && !streamInfo.ended && reportPlayback(self, state, player, reportPlaylist, serverId, "reportPlaybackProgress", progressEventName), streamInfo && streamInfo.liveStreamId && (new Date).getTime() - (streamInfo.lastMediaInfoQuery || 0) >= 6e5 && getLiveStreamMediaInfo(player, streamInfo, self.currentMediaSource(player), streamInfo.liveStreamId, serverId) + } + } + + function getLiveStreamMediaInfo(player, streamInfo, mediaSource, liveStreamId, serverId) { + console.log("getLiveStreamMediaInfo"), streamInfo.lastMediaInfoQuery = (new Date).getTime(), connectionManager.getApiClient(serverId).isMinServerVersion("3.2.70.7") && connectionManager.getApiClient(serverId).getLiveStreamMediaInfo(liveStreamId).then(function(info) { + mediaSource.MediaStreams = info.MediaStreams, events.trigger(player, "mediastreamschange") + }, function() {}) + } + var currentTargetInfo, lastLocalPlayer, self = this, + players = [], + currentPairingId = null; + this._playNextAfterEnded = !0; + var playerStates = {}; + this._playQueueManager = new PlayQueueManager, self.currentItem = function(player) { + if (!player) throw new Error("player cannot be null"); + if (player.currentItem) return player.currentItem(); + var data = getPlayerData(player); + return data.streamInfo ? data.streamInfo.item : null + }, self.currentMediaSource = function(player) { + if (!player) throw new Error("player cannot be null"); + if (player.currentMediaSource) return player.currentMediaSource(); + var data = getPlayerData(player); + return data.streamInfo ? data.streamInfo.mediaSource : null + }, self.playMethod = function(player) { + if (!player) throw new Error("player cannot be null"); + if (player.playMethod) return player.playMethod(); + var data = getPlayerData(player); + return data.streamInfo ? data.streamInfo.playMethod : null + }, self.playSessionId = function(player) { + if (!player) throw new Error("player cannot be null"); + if (player.playSessionId) return player.playSessionId(); + var data = getPlayerData(player); + return data.streamInfo ? data.streamInfo.playSessionId : null + }, self.getPlayerInfo = function() { + var player = self._currentPlayer; + if (!player) return null; + var target = currentTargetInfo || {}; + return { + name: player.name, + isLocalPlayer: player.isLocalPlayer, + id: target.id, + deviceName: target.deviceName, + playableMediaTypes: target.playableMediaTypes, + supportedCommands: target.supportedCommands + } + }, self.setActivePlayer = function(player, targetInfo) { + if ("localplayer" === player || "localplayer" === player.name) { + if (self._currentPlayer && self._currentPlayer.isLocalPlayer) return; + return void setCurrentPlayerInternal(null, null) + } + if ("string" == typeof player && (player = players.filter(function(p) { + return p.name === player + })[0]), !player) throw new Error("null player"); + setCurrentPlayerInternal(player, targetInfo) + }, self.trySetActivePlayer = function(player, targetInfo) { + if ("localplayer" === player || "localplayer" === player.name) return void(self._currentPlayer && self._currentPlayer.isLocalPlayer); + if ("string" == typeof player && (player = players.filter(function(p) { + return p.name === player + })[0]), !player) throw new Error("null player"); + if (currentPairingId !== targetInfo.id) { + currentPairingId = targetInfo.id; + var promise = player.tryPair ? player.tryPair(targetInfo) : Promise.resolve(); + events.trigger(self, "pairing"), promise.then(function() { + events.trigger(self, "paired"), setCurrentPlayerInternal(player, targetInfo) + }, function() { + events.trigger(self, "pairerror"), currentPairingId === targetInfo.id && (currentPairingId = null) + }) + } + }, self.getTargets = function() { + var promises = players.filter(displayPlayerIndividually).map(getPlayerTargets); + return Promise.all(promises).then(function(responses) { + return connectionManager.currentApiClient().getCurrentUser().then(function(user) { + var targets = []; + targets.push({ + name: globalize.translate("sharedcomponents#HeaderMyDevice"), + id: "localplayer", + playerName: "localplayer", + playableMediaTypes: ["Audio", "Video", "Game", "Photo", "Book"], + isLocalPlayer: !0, + supportedCommands: self.getSupportedCommands({ + isLocalPlayer: !0 + }), + user: user + }); + for (var i = 0; i < responses.length; i++) + for (var subTargets = responses[i], j = 0; j < subTargets.length; j++) targets.push(subTargets[j]); + return targets = targets.sort(sortPlayerTargets) + }) + }) + }, self.getPlaylist = function(player) { + return player = player || self._currentPlayer, player && !enableLocalPlaylistManagement(player) ? player.getPlaylistSync ? Promise.resolve(player.getPlaylistSync()) : player.getPlaylist() : Promise.resolve(self._playQueueManager.getPlaylist()) + }, self.isPlaying = function(player) { + return player = player || self._currentPlayer, player && player.isPlaying ? player.isPlaying() : null != player && null != player.currentSrc() + }, self.isPlayingMediaType = function(mediaType, player) { + if ((player = player || self._currentPlayer) && player.isPlaying) return player.isPlaying(mediaType); + if (self.isPlaying(player)) { + return getPlayerData(player).streamInfo.mediaType === mediaType + } + return !1 + }, self.isPlayingLocally = function(mediaTypes, player) { + return !(!(player = player || self._currentPlayer) || !player.isLocalPlayer) && mediaTypes.filter(function(mediaType) { + return self.isPlayingMediaType(mediaType, player) + }).length > 0 + }, self.isPlayingVideo = function(player) { + return self.isPlayingMediaType("Video", player) + }, self.isPlayingAudio = function(player) { + return self.isPlayingMediaType("Audio", player) + }, self.getPlayers = function() { + return players + }, self.canPlay = function(item) { + var itemType = item.Type; + if ("PhotoAlbum" === itemType || "MusicGenre" === itemType || "Season" === itemType || "Series" === itemType || "BoxSet" === itemType || "MusicAlbum" === itemType || "MusicArtist" === itemType || "Playlist" === itemType) return !0; + if ("Virtual" === item.LocationType && "Program" !== itemType) return !1; + if ("Program" === itemType) { + if (!item.EndDate || !item.StartDate) return !1; + if ((new Date).getTime() > datetime.parseISO8601Date(item.EndDate).getTime() || (new Date).getTime() < datetime.parseISO8601Date(item.StartDate).getTime()) return !1 + } + return null != getPlayer(item, getDefaultPlayOptions()) + }, self.toggleAspectRatio = function(player) { + if (player = player || self._currentPlayer) { + for (var current = self.getAspectRatio(player), supported = self.getSupportedAspectRatios(player), index = -1, i = 0, length = supported.length; i < length; i++) + if (supported[i].id === current) { + index = i; + break + } index++, index >= supported.length && (index = 0), self.setAspectRatio(supported[index].id, player) + } + }, self.setAspectRatio = function(val, player) { + (player = player || self._currentPlayer) && player.setAspectRatio && player.setAspectRatio(val) + }, self.getSupportedAspectRatios = function(player) { + return player = player || self._currentPlayer, player && player.getSupportedAspectRatios ? player.getSupportedAspectRatios() : [] + }, self.getAspectRatio = function(player) { + if ((player = player || self._currentPlayer) && player.getAspectRatio) return player.getAspectRatio() + }; + var brightnessOsdLoaded; + self.setBrightness = function(val, player) { + (player = player || self._currentPlayer) && (brightnessOsdLoaded || (brightnessOsdLoaded = !0, require(["brightnessOsd"])), player.setBrightness(val)) + }, self.getBrightness = function(player) { + if (player = player || self._currentPlayer) return player.getBrightness() + }, self.setVolume = function(val, player) { + (player = player || self._currentPlayer) && player.setVolume(val) + }, self.getVolume = function(player) { + if (player = player || self._currentPlayer) return player.getVolume() + }, self.volumeUp = function(player) { + (player = player || self._currentPlayer) && player.volumeUp() + }, self.volumeDown = function(player) { + (player = player || self._currentPlayer) && player.volumeDown() + }, self.changeAudioStream = function(player) { + if ((player = player || self._currentPlayer) && !enableLocalPlaylistManagement(player)) return player.changeAudioStream(); + if (player) { + var i, length, currentMediaSource = self.currentMediaSource(player), + mediaStreams = []; + for (i = 0, length = currentMediaSource.MediaStreams.length; i < length; i++) "Audio" === currentMediaSource.MediaStreams[i].Type && mediaStreams.push(currentMediaSource.MediaStreams[i]); + if (!(mediaStreams.length <= 1)) { + var currentStreamIndex = self.getAudioStreamIndex(player), + indexInList = -1; + for (i = 0, length = mediaStreams.length; i < length; i++) + if (mediaStreams[i].Index === currentStreamIndex) { + indexInList = i; + break + } var nextIndex = indexInList + 1; + nextIndex >= mediaStreams.length && (nextIndex = 0), nextIndex = -1 === nextIndex ? -1 : mediaStreams[nextIndex].Index, self.setAudioStreamIndex(nextIndex, player) + } + } + }, self.changeSubtitleStream = function(player) { + if ((player = player || self._currentPlayer) && !enableLocalPlaylistManagement(player)) return player.changeSubtitleStream(); + if (player) { + var i, length, currentMediaSource = self.currentMediaSource(player), + mediaStreams = []; + for (i = 0, length = currentMediaSource.MediaStreams.length; i < length; i++) "Subtitle" === currentMediaSource.MediaStreams[i].Type && mediaStreams.push(currentMediaSource.MediaStreams[i]); + if (mediaStreams.length) { + var currentStreamIndex = self.getSubtitleStreamIndex(player), + indexInList = -1; + for (i = 0, length = mediaStreams.length; i < length; i++) + if (mediaStreams[i].Index === currentStreamIndex) { + indexInList = i; + break + } var nextIndex = indexInList + 1; + nextIndex >= mediaStreams.length && (nextIndex = -1), nextIndex = -1 === nextIndex ? -1 : mediaStreams[nextIndex].Index, self.setSubtitleStreamIndex(nextIndex, player) + } + } + }, self.getAudioStreamIndex = function(player) { + return player = player || self._currentPlayer, player && !enableLocalPlaylistManagement(player) ? player.getAudioStreamIndex() : getPlayerData(player).audioStreamIndex + }, self.setAudioStreamIndex = function(index, player) { + if ((player = player || self._currentPlayer) && !enableLocalPlaylistManagement(player)) return player.setAudioStreamIndex(index); + "Transcode" !== self.playMethod(player) && player.canSetAudioStreamIndex() ? player.getDeviceProfile(self.currentItem(player)).then(function(profile) { + isAudioStreamSupported(self.currentMediaSource(player), index, profile) ? (player.setAudioStreamIndex(index), getPlayerData(player).audioStreamIndex = index) : (changeStream(player, getCurrentTicks(player), { + AudioStreamIndex: index + }), getPlayerData(player).audioStreamIndex = index) + }) : (changeStream(player, getCurrentTicks(player), { + AudioStreamIndex: index + }), getPlayerData(player).audioStreamIndex = index) + }, self.getMaxStreamingBitrate = function(player) { + if ((player = player || self._currentPlayer) && player.getMaxStreamingBitrate) return player.getMaxStreamingBitrate(); + var playerData = getPlayerData(player); + if (playerData.maxStreamingBitrate) return playerData.maxStreamingBitrate; + var mediaType = playerData.streamInfo ? playerData.streamInfo.mediaType : null, + currentItem = self.currentItem(player); + return getSavedMaxStreamingBitrate(currentItem ? connectionManager.getApiClient(currentItem.ServerId) : connectionManager.currentApiClient(), mediaType) + }, self.enableAutomaticBitrateDetection = function(player) { + if ((player = player || self._currentPlayer) && player.enableAutomaticBitrateDetection) return player.enableAutomaticBitrateDetection(); + var playerData = getPlayerData(player), + mediaType = playerData.streamInfo ? playerData.streamInfo.mediaType : null, + currentItem = self.currentItem(player), + apiClient = currentItem ? connectionManager.getApiClient(currentItem.ServerId) : connectionManager.currentApiClient(), + endpointInfo = apiClient.getSavedEndpointInfo() || {}; + return appSettings.enableAutomaticBitrateDetection(endpointInfo.IsInNetwork, mediaType) + }, self.setMaxStreamingBitrate = function(options, player) { + if ((player = player || self._currentPlayer) && player.setMaxStreamingBitrate) return player.setMaxStreamingBitrate(options); + var apiClient = connectionManager.getApiClient(self.currentItem(player).ServerId); + apiClient.getEndpointInfo().then(function(endpointInfo) { + var promise, playerData = getPlayerData(player), + mediaType = playerData.streamInfo ? playerData.streamInfo.mediaType : null; + options.enableAutomaticBitrateDetection ? (appSettings.enableAutomaticBitrateDetection(endpointInfo.IsInNetwork, mediaType, !0), promise = apiClient.detectBitrate(!0)) : (appSettings.enableAutomaticBitrateDetection(endpointInfo.IsInNetwork, mediaType, !1), promise = Promise.resolve(options.maxBitrate)), promise.then(function(bitrate) { + appSettings.maxStreamingBitrate(endpointInfo.IsInNetwork, mediaType, bitrate), changeStream(player, getCurrentTicks(player), { + MaxStreamingBitrate: bitrate + }) + }) + }) + }, self.isFullscreen = function(player) { + return player = player || self._currentPlayer, !player.isLocalPlayer || player.isFullscreen ? player.isFullscreen() : fullscreenManager.isFullScreen() + }, self.toggleFullscreen = function(player) { + if (player = player || self._currentPlayer, !player.isLocalPlayer || player.toggleFulscreen) return player.toggleFulscreen(); + fullscreenManager.isFullScreen() ? fullscreenManager.exitFullscreen() : fullscreenManager.requestFullscreen() + }, self.togglePictureInPicture = function(player) { + return player = player || self._currentPlayer, player.togglePictureInPicture() + }, self.getSubtitleStreamIndex = function(player) { + if ((player = player || self._currentPlayer) && !enableLocalPlaylistManagement(player)) return player.getSubtitleStreamIndex(); + if (!player) throw new Error("player cannot be null"); + return getPlayerData(player).subtitleStreamIndex + }, self.setSubtitleStreamIndex = function(index, player) { + if ((player = player || self._currentPlayer) && !enableLocalPlaylistManagement(player)) return player.setSubtitleStreamIndex(index); + var currentStream = getCurrentSubtitleStream(player), + newStream = getSubtitleStream(player, index); + if (currentStream || newStream) { + var selectedTrackElementIndex = -1, + currentPlayMethod = self.playMethod(player); + currentStream && !newStream ? ("Encode" === getDeliveryMethod(currentStream) || "Embed" === getDeliveryMethod(currentStream) && "Transcode" === currentPlayMethod) && changeStream(player, getCurrentTicks(player), { + SubtitleStreamIndex: -1 + }) : !currentStream && newStream ? "External" === getDeliveryMethod(newStream) ? selectedTrackElementIndex = index : "Embed" === getDeliveryMethod(newStream) && "Transcode" !== currentPlayMethod ? selectedTrackElementIndex = index : changeStream(player, getCurrentTicks(player), { + SubtitleStreamIndex: index + }) : currentStream && newStream && ("External" === getDeliveryMethod(newStream) || "Embed" === getDeliveryMethod(newStream) && "Transcode" !== currentPlayMethod ? (selectedTrackElementIndex = index, "External" !== getDeliveryMethod(currentStream) && "Embed" !== getDeliveryMethod(currentStream) && changeStream(player, getCurrentTicks(player), { + SubtitleStreamIndex: -1 + })) : changeStream(player, getCurrentTicks(player), { + SubtitleStreamIndex: index + })), player.setSubtitleStreamIndex(selectedTrackElementIndex), getPlayerData(player).subtitleStreamIndex = index + } + }, self.seek = function(ticks, player) { + if (ticks = Math.max(0, ticks), (player = player || self._currentPlayer) && !enableLocalPlaylistManagement(player)) return player.isLocalPlayer ? player.seek((ticks || 0) / 1e4) : player.seek(ticks); + changeStream(player, ticks) + }, self.seekRelative = function(offsetTicks, player) { + if ((player = player || self._currentPlayer) && !enableLocalPlaylistManagement(player) && player.seekRelative) return player.isLocalPlayer ? player.seekRelative((ticks || 0) / 1e4) : player.seekRelative(ticks); + var ticks = getCurrentTicks(player) + offsetTicks; + return this.seek(ticks, player) + }, self.play = function(options) { + if (normalizePlayOptions(options), self._currentPlayer) { + if (!1 === options.enableRemotePlayers && !self._currentPlayer.isLocalPlayer) return Promise.reject(); + if (!self._currentPlayer.isLocalPlayer) return self._currentPlayer.play(options) + } + if (options.fullscreen && loading.show(), options.items) return translateItemsForPlayback(options.items, options).then(function(items) { + return playWithIntros(items, options) + }); + if (!options.serverId) throw new Error("serverId required!"); + return getItemsForPlayback(options.serverId, { + Ids: options.ids.join(",") + }).then(function(result) { + return translateItemsForPlayback(result.Items, options).then(function(items) { + return playWithIntros(items, options) + }) + }) + }, self.getPlayerState = function(player, item, mediaSource) { + if (!(player = player || self._currentPlayer)) throw new Error("player cannot be null"); + if (!enableLocalPlaylistManagement(player) && player.getPlayerState) return player.getPlayerState(); + item = item || self.currentItem(player), mediaSource = mediaSource || self.currentMediaSource(player); + var state = { + PlayState: {} + }; + return player && (state.PlayState.VolumeLevel = player.getVolume(), state.PlayState.IsMuted = player.isMuted(), state.PlayState.IsPaused = player.paused(), state.PlayState.RepeatMode = self.getRepeatMode(player), state.PlayState.MaxStreamingBitrate = self.getMaxStreamingBitrate(player), state.PlayState.PositionTicks = getCurrentTicks(player), state.PlayState.PlaybackStartTimeTicks = self.playbackStartTime(player), state.PlayState.SubtitleStreamIndex = self.getSubtitleStreamIndex(player), state.PlayState.AudioStreamIndex = self.getAudioStreamIndex(player), state.PlayState.BufferedRanges = self.getBufferedRanges(player), state.PlayState.PlayMethod = self.playMethod(player), mediaSource && (state.PlayState.LiveStreamId = mediaSource.LiveStreamId), state.PlayState.PlaySessionId = self.playSessionId(player), state.PlayState.PlaylistItemId = self.getCurrentPlaylistItemId(player)), mediaSource && (state.PlayState.MediaSourceId = mediaSource.Id, state.NowPlayingItem = { + RunTimeTicks: mediaSource.RunTimeTicks + }, state.PlayState.CanSeek = (mediaSource.RunTimeTicks || 0) > 0 || canPlayerSeek(player)), item && (state.NowPlayingItem = getNowPlayingItemForReporting(player, item, mediaSource)), state.MediaSource = mediaSource, state + }, self.duration = function(player) { + if ((player = player || self._currentPlayer) && !enableLocalPlaylistManagement(player) && !player.isLocalPlayer) return player.duration(); + if (!player) throw new Error("player cannot be null"); + var mediaSource = self.currentMediaSource(player); + if (mediaSource && mediaSource.RunTimeTicks) return mediaSource.RunTimeTicks; + var playerDuration = player.duration(); + return playerDuration && (playerDuration *= 1e4), playerDuration + }, self.getCurrentTicks = getCurrentTicks, self.getPlaybackInfo = function(item, options) { + options = options || {}; + var startPosition = options.startPositionTicks || 0, + mediaType = options.mediaType || item.MediaType, + player = getPlayer(item, options), + apiClient = connectionManager.getApiClient(item.ServerId); + return apiClient.getEndpointInfo().then(function() { + var maxBitrate = getSavedMaxStreamingBitrate(connectionManager.getApiClient(item.ServerId), mediaType); + return player.getDeviceProfile(item).then(function(deviceProfile) { + return getPlaybackMediaSource(player, apiClient, deviceProfile, maxBitrate, item, startPosition, options.mediaSourceId, options.audioStreamIndex, options.subtitleStreamIndex).then(function(mediaSource) { + return createStreamInfo(apiClient, item.MediaType, item, mediaSource, startPosition) + }) + }) + }) + }, self.getPlaybackMediaSources = function(item, options) { + options = options || {}; + var startPosition = options.startPositionTicks || 0, + mediaType = options.mediaType || item.MediaType, + player = getPlayer(item, options, !0), + apiClient = connectionManager.getApiClient(item.ServerId); + return apiClient.getEndpointInfo().then(function() { + var maxBitrate = getSavedMaxStreamingBitrate(connectionManager.getApiClient(item.ServerId), mediaType); + return player.getDeviceProfile(item).then(function(deviceProfile) { + return getPlaybackInfo(player, apiClient, item, deviceProfile, maxBitrate, startPosition, !1, null, null, null, null).then(function(playbackInfoResult) { + return playbackInfoResult.MediaSources + }) + }) + }) + }, self.setCurrentPlaylistItem = function(playlistItemId, player) { + if ((player = player || self._currentPlayer) && !enableLocalPlaylistManagement(player)) return player.setCurrentPlaylistItem(playlistItemId); + for (var newItem, newItemIndex, playlist = self._playQueueManager.getPlaylist(), i = 0, length = playlist.length; i < length; i++) + if (playlist[i].PlaylistItemId === playlistItemId) { + newItem = playlist[i], newItemIndex = i; + break + } if (newItem) { + var newItemPlayOptions = newItem.playOptions || {}; + playInternal(newItem, newItemPlayOptions, function() { + setPlaylistState(newItem.PlaylistItemId, newItemIndex) + }) + } + }, self.removeFromPlaylist = function(playlistItemIds, player) { + if (!playlistItemIds) throw new Error("Invalid playlistItemIds"); + if ((player = player || self._currentPlayer) && !enableLocalPlaylistManagement(player)) return player.removeFromPlaylist(playlistItemIds); + var removeResult = self._playQueueManager.removeFromPlaylist(playlistItemIds); + if ("empty" === removeResult.result) return self.stop(player); + var isCurrentIndex = removeResult.isCurrentIndex; + return events.trigger(player, "playlistitemremove", [{ + playlistItemIds: playlistItemIds + }]), isCurrentIndex ? self.setCurrentPlaylistItem(self._playQueueManager.getPlaylist()[0].PlaylistItemId, player) : Promise.resolve() + }, self.movePlaylistItem = function(playlistItemId, newIndex, player) { + if ((player = player || self._currentPlayer) && !enableLocalPlaylistManagement(player)) return player.movePlaylistItem(playlistItemId, newIndex); + var moveResult = self._playQueueManager.movePlaylistItem(playlistItemId, newIndex); + "noop" !== moveResult.result && events.trigger(player, "playlistitemmove", [{ + playlistItemId: moveResult.playlistItemId, + newIndex: moveResult.newIndex + }]) + }, self.getCurrentPlaylistIndex = function(player) { + return player = player || self._currentPlayer, player && !enableLocalPlaylistManagement(player) ? player.getCurrentPlaylistIndex() : self._playQueueManager.getCurrentPlaylistIndex() + }, self.getCurrentPlaylistItemId = function(player) { + return player = player || self._currentPlayer, player && !enableLocalPlaylistManagement(player) ? player.getCurrentPlaylistItemId() : self._playQueueManager.getCurrentPlaylistItemId() + }, self.channelUp = function(player) { + return player = player || self._currentPlayer, self.nextTrack(player) + }, self.channelDown = function(player) { + return player = player || self._currentPlayer, self.previousTrack(player) + }, self.nextTrack = function(player) { + if ((player = player || self._currentPlayer) && !enableLocalPlaylistManagement(player)) return player.nextTrack(); + var newItemInfo = self._playQueueManager.getNextItemInfo(); + if (newItemInfo) { + console.log("playing next track"); + var newItemPlayOptions = newItemInfo.item.playOptions || {}; + playInternal(newItemInfo.item, newItemPlayOptions, function() { + setPlaylistState(newItemInfo.item.PlaylistItemId, newItemInfo.index) + }) + } + }, self.previousTrack = function(player) { + if ((player = player || self._currentPlayer) && !enableLocalPlaylistManagement(player)) return player.previousTrack(); + var newIndex = self.getCurrentPlaylistIndex(player) - 1; + if (newIndex >= 0) { + var playlist = self._playQueueManager.getPlaylist(), + newItem = playlist[newIndex]; + if (newItem) { + var newItemPlayOptions = newItem.playOptions || {}; + newItemPlayOptions.startPositionTicks = 0, playInternal(newItem, newItemPlayOptions, function() { + setPlaylistState(newItem.PlaylistItemId, newIndex) + }) + } + } + }, self.queue = function(options, player) { + queue(options, "", player) + }, self.queueNext = function(options, player) { + queue(options, "next", player) + }, events.on(pluginManager, "registered", function(e, plugin) { + "mediaplayer" === plugin.type && initMediaPlayer(plugin) + }), pluginManager.ofType("mediaplayer").map(initMediaPlayer), self.onAppClose = function() { + var player = this._currentPlayer; + player && this.isPlaying(player) && (this._playNextAfterEnded = !1, onPlaybackStopped.call(player)) + }, self.playbackStartTime = function(player) { + if ((player = player || this._currentPlayer) && !enableLocalPlaylistManagement(player) && !player.isLocalPlayer) return player.playbackStartTime(); + var streamInfo = getPlayerData(player).streamInfo; + return streamInfo ? streamInfo.playbackStartTimeTicks : null + }, apphost.supports("remotecontrol") && require(["serverNotifications"], function(serverNotifications) { + events.on(serverNotifications, "ServerShuttingDown", self.setDefaultPlayerActive.bind(self)), events.on(serverNotifications, "ServerRestarting", self.setDefaultPlayerActive.bind(self)) + }) + } + var startingPlaySession = (new Date).getTime(); + return PlaybackManager.prototype.getCurrentPlayer = function() { + return this._currentPlayer + }, PlaybackManager.prototype.currentTime = function(player) { + return player = player || this._currentPlayer, !player || enableLocalPlaylistManagement(player) || player.isLocalPlayer ? this.getCurrentTicks(player) : player.currentTime() + }, PlaybackManager.prototype.nextItem = function(player) { + if ((player = player || this._currentPlayer) && !enableLocalPlaylistManagement(player)) return player.nextItem(); + var nextItem = this._playQueueManager.getNextItemInfo(); + if (!nextItem || !nextItem.item) return Promise.reject(); + var apiClient = connectionManager.getApiClient(nextItem.item.ServerId); + return apiClient.getItem(apiClient.getCurrentUserId(), nextItem.item.Id) + }, PlaybackManager.prototype.canQueue = function(item) { + return "MusicAlbum" === item.Type || "MusicArtist" === item.Type || "MusicGenre" === item.Type ? this.canQueueMediaType("Audio") : this.canQueueMediaType(item.MediaType) + }, PlaybackManager.prototype.canQueueMediaType = function(mediaType) { + return !!this._currentPlayer && this._currentPlayer.canPlayMediaType(mediaType) + }, PlaybackManager.prototype.isMuted = function(player) { + return !!(player = player || this._currentPlayer) && player.isMuted() + }, PlaybackManager.prototype.setMute = function(mute, player) { + (player = player || this._currentPlayer) && player.setMute(mute) + }, PlaybackManager.prototype.toggleMute = function(mute, player) { + (player = player || this._currentPlayer) && (player.toggleMute ? player.toggleMute() : player.setMute(!player.isMuted())) + }, PlaybackManager.prototype.toggleDisplayMirroring = function() { + this.enableDisplayMirroring(!this.enableDisplayMirroring()) + }, PlaybackManager.prototype.enableDisplayMirroring = function(enabled) { + if (null != enabled) { + var val = enabled ? "1" : "0"; + return void appSettings.set("displaymirror", val) + } + return "0" !== (appSettings.get("displaymirror") || "") + }, PlaybackManager.prototype.nextChapter = function(player) { + player = player || this._currentPlayer; + var item = this.currentItem(player), + ticks = this.getCurrentTicks(player), + nextChapter = (item.Chapters || []).filter(function(i) { + return i.StartPositionTicks > ticks + })[0]; + nextChapter ? this.seek(nextChapter.StartPositionTicks, player) : this.nextTrack(player) + }, PlaybackManager.prototype.previousChapter = function(player) { + player = player || this._currentPlayer; + var item = this.currentItem(player), + ticks = this.getCurrentTicks(player); + ticks -= 1e8, 0 === this.getCurrentPlaylistIndex(player) && (ticks = Math.max(ticks, 0)); + var previousChapters = (item.Chapters || []).filter(function(i) { + return i.StartPositionTicks <= ticks + }); + previousChapters.length ? this.seek(previousChapters[previousChapters.length - 1].StartPositionTicks, player) : this.previousTrack(player) + }, PlaybackManager.prototype.fastForward = function(player) { + if (player = player || this._currentPlayer, null != player.fastForward) return void player.fastForward(userSettings.skipForwardLength()); + var offsetTicks = 1e4 * userSettings.skipForwardLength(); + this.seekRelative(offsetTicks, player) + }, PlaybackManager.prototype.rewind = function(player) { + if (player = player || this._currentPlayer, null != player.rewind) return void player.rewind(userSettings.skipBackLength()); + var offsetTicks = 0 - 1e4 * userSettings.skipBackLength(); + this.seekRelative(offsetTicks, player) + }, PlaybackManager.prototype.seekPercent = function(percent, player) { + player = player || this._currentPlayer; + var ticks = this.duration(player) || 0; + percent /= 100, ticks *= percent, this.seek(parseInt(ticks), player) + }, PlaybackManager.prototype.playTrailers = function(item) { + var player = this._currentPlayer; + if (player && player.playTrailers) return player.playTrailers(item); + var apiClient = connectionManager.getApiClient(item.ServerId), + instance = this; + if (item.LocalTrailerCount) return apiClient.getLocalTrailers(apiClient.getCurrentUserId(), item.Id).then(function(result) { + return instance.play({ + items: result + }) + }); + var remoteTrailers = item.RemoteTrailers || []; + return remoteTrailers.length ? this.play({ + items: remoteTrailers.map(function(t) { + return { + Name: t.Name || item.Name + " Trailer", + Url: t.Url, + MediaType: "Video", + Type: "Trailer", + ServerId: apiClient.serverId() + } + }) + }) : Promise.reject() + }, PlaybackManager.prototype.getSubtitleUrl = function(textStream, serverId) { + var apiClient = connectionManager.getApiClient(serverId); + return textStream.IsExternalUrl ? textStream.DeliveryUrl : apiClient.getUrl(textStream.DeliveryUrl) + }, PlaybackManager.prototype.stop = function(player) { + return player = player || this._currentPlayer, player ? (enableLocalPlaylistManagement(player) && (this._playNextAfterEnded = !1), player.stop(!0, !0)) : Promise.resolve() + }, PlaybackManager.prototype.getBufferedRanges = function(player) { + return player = player || this._currentPlayer, player && player.getBufferedRanges ? player.getBufferedRanges() : [] + }, PlaybackManager.prototype.playPause = function(player) { + if (player = player || this._currentPlayer) return player.playPause ? player.playPause() : player.paused() ? this.unpause(player) : this.pause(player) + }, PlaybackManager.prototype.paused = function(player) { + if (player = player || this._currentPlayer) return player.paused() + }, PlaybackManager.prototype.pause = function(player) { + (player = player || this._currentPlayer) && player.pause() + }, PlaybackManager.prototype.unpause = function(player) { + (player = player || this._currentPlayer) && player.unpause() + }, PlaybackManager.prototype.instantMix = function(item, player) { + if ((player = player || this._currentPlayer) && player.instantMix) return player.instantMix(item); + var apiClient = connectionManager.getApiClient(item.ServerId), + options = {}; + options.UserId = apiClient.getCurrentUserId(), options.Limit = 200; + var instance = this; + apiClient.getInstantMixFromItem(item.Id, options).then(function(result) { + instance.play({ + items: result.Items + }) + }) + }, PlaybackManager.prototype.shuffle = function(shuffleItem, player, queryOptions) { + return player = player || this._currentPlayer, player && player.shuffle ? player.shuffle(shuffleItem) : this.play({ + items: [shuffleItem], + shuffle: !0 + }) + }, PlaybackManager.prototype.audioTracks = function(player) { + if (player = player || this._currentPlayer, player.audioTracks) { + var result = player.audioTracks(); + if (result) return result + } + return ((this.currentMediaSource(player) || {}).MediaStreams || []).filter(function(s) { + return "Audio" === s.Type + }) + }, PlaybackManager.prototype.subtitleTracks = function(player) { + if (player = player || this._currentPlayer, player.subtitleTracks) { + var result = player.subtitleTracks(); + if (result) return result + } + return ((this.currentMediaSource(player) || {}).MediaStreams || []).filter(function(s) { + return "Subtitle" === s.Type + }) + }, PlaybackManager.prototype.getSupportedCommands = function(player) { + if (player = player || this._currentPlayer || { + isLocalPlayer: !0 + }, player.isLocalPlayer) { + var list = ["GoHome", "GoToSettings", "VolumeUp", "VolumeDown", "Mute", "Unmute", "ToggleMute", "SetVolume", "SetAudioStreamIndex", "SetSubtitleStreamIndex", "SetMaxStreamingBitrate", "DisplayContent", "GoToSearch", "DisplayMessage", "SetRepeatMode", "PlayMediaSource", "PlayTrailers"]; + return apphost.supports("fullscreenchange") && list.push("ToggleFullscreen"), player.supports && (player.supports("PictureInPicture") && list.push("PictureInPicture"), player.supports("SetBrightness") && list.push("SetBrightness"), player.supports("SetAspectRatio") && list.push("SetAspectRatio")), list + } + var info = this.getPlayerInfo(); + return info ? info.supportedCommands : [] + }, PlaybackManager.prototype.setRepeatMode = function(value, player) { + if ((player = player || this._currentPlayer) && !enableLocalPlaylistManagement(player)) return player.setRepeatMode(value); + this._playQueueManager.setRepeatMode(value), events.trigger(player, "repeatmodechange") + }, PlaybackManager.prototype.getRepeatMode = function(player) { + return player = player || this._currentPlayer, player && !enableLocalPlaylistManagement(player) ? player.getRepeatMode() : this._playQueueManager.getRepeatMode() + }, PlaybackManager.prototype.trySetActiveDeviceName = function(name) { + name = normalizeName(name); + var instance = this; + instance.getTargets().then(function(result) { + var target = result.filter(function(p) { + return normalizeName(p.name) === name + })[0]; + target && instance.trySetActivePlayer(target.playerName, target) + }) + }, PlaybackManager.prototype.displayContent = function(options, player) { + (player = player || this._currentPlayer) && player.displayContent && player.displayContent(options) + }, PlaybackManager.prototype.beginPlayerUpdates = function(player) { + player.beginPlayerUpdates && player.beginPlayerUpdates() + }, PlaybackManager.prototype.endPlayerUpdates = function(player) { + player.endPlayerUpdates && player.endPlayerUpdates() + }, PlaybackManager.prototype.setDefaultPlayerActive = function() { + this.setActivePlayer("localplayer") + }, PlaybackManager.prototype.removeActivePlayer = function(name) { + var playerInfo = this.getPlayerInfo(); + playerInfo && playerInfo.name === name && this.setDefaultPlayerActive() + }, PlaybackManager.prototype.removeActiveTarget = function(id) { + var playerInfo = this.getPlayerInfo(); + playerInfo && playerInfo.id === id && this.setDefaultPlayerActive() + }, PlaybackManager.prototype.sendCommand = function(cmd, player) { + switch (console.log("MediaController received command: " + cmd.Name), cmd.Name) { + case "SetRepeatMode": + this.setRepeatMode(cmd.Arguments.RepeatMode, player); + break; + case "VolumeUp": + this.volumeUp(player); + break; + case "VolumeDown": + this.volumeDown(player); + break; + case "Mute": + this.setMute(!0, player); + break; + case "Unmute": + this.setMute(!1, player); + break; + case "ToggleMute": + this.toggleMute(player); + break; + case "SetVolume": + this.setVolume(cmd.Arguments.Volume, player); + break; + case "SetAspectRatio": + this.setAspectRatio(cmd.Arguments.AspectRatio, player); + break; + case "SetBrightness": + this.setBrightness(cmd.Arguments.Brightness, player); + break; + case "SetAudioStreamIndex": + this.setAudioStreamIndex(parseInt(cmd.Arguments.Index), player); + break; + case "SetSubtitleStreamIndex": + this.setSubtitleStreamIndex(parseInt(cmd.Arguments.Index), player); + break; + case "SetMaxStreamingBitrate": + break; + case "ToggleFullscreen": + this.toggleFullscreen(player); + break; + default: + player.sendCommand && player.sendCommand(cmd) + } + }, new PlaybackManager +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/playback/playbackorientation.js b/dashboard-ui/bower_components/emby-webcomponents/playback/playbackorientation.js index 9eced4dc0c..b682f7c564 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/playback/playbackorientation.js +++ b/dashboard-ui/bower_components/emby-webcomponents/playback/playbackorientation.js @@ -1 +1,35 @@ -define(["playbackManager","layoutManager","events"],function(playbackManager,layoutManager,events){"use strict";function onOrientationChangeSuccess(){orientationLocked=!0}function onOrientationChangeError(err){orientationLocked=!1,console.log("error locking orientation: "+err)}var orientationLocked;events.on(playbackManager,"playbackstart",function(e,player,state){if(player.isLocalPlayer&&!player.isExternalPlayer&&playbackManager.isPlayingVideo(player)&&layoutManager.mobile){var lockOrientation=screen.lockOrientation||screen.mozLockOrientation||screen.msLockOrientation||screen.orientation&&screen.orientation.lock;if(lockOrientation)try{var promise=lockOrientation("landscape");promise.then?promise.then(onOrientationChangeSuccess,onOrientationChangeError):orientationLocked=promise}catch(err){onOrientationChangeError(err)}}}),events.on(playbackManager,"playbackstop",function(e,playbackStopInfo){if(orientationLocked&&!playbackStopInfo.nextMediaType){var unlockOrientation=screen.unlockOrientation||screen.mozUnlockOrientation||screen.msUnlockOrientation||screen.orientation&&screen.orientation.unlock;if(unlockOrientation){try{unlockOrientation()}catch(err){console.log("error unlocking orientation: "+err)}orientationLocked=!1}}})}); \ No newline at end of file +define(["playbackManager", "layoutManager", "events"], function(playbackManager, layoutManager, events) { + "use strict"; + + function onOrientationChangeSuccess() { + orientationLocked = !0 + } + + function onOrientationChangeError(err) { + orientationLocked = !1, console.log("error locking orientation: " + err) + } + var orientationLocked; + events.on(playbackManager, "playbackstart", function(e, player, state) { + if (player.isLocalPlayer && !player.isExternalPlayer && playbackManager.isPlayingVideo(player) && layoutManager.mobile) { + var lockOrientation = screen.lockOrientation || screen.mozLockOrientation || screen.msLockOrientation || screen.orientation && screen.orientation.lock; + if (lockOrientation) try { + var promise = lockOrientation("landscape"); + promise.then ? promise.then(onOrientationChangeSuccess, onOrientationChangeError) : orientationLocked = promise + } catch (err) { + onOrientationChangeError(err) + } + } + }), events.on(playbackManager, "playbackstop", function(e, playbackStopInfo) { + if (orientationLocked && !playbackStopInfo.nextMediaType) { + var unlockOrientation = screen.unlockOrientation || screen.mozUnlockOrientation || screen.msUnlockOrientation || screen.orientation && screen.orientation.unlock; + if (unlockOrientation) { + try { + unlockOrientation() + } catch (err) { + console.log("error unlocking orientation: " + err) + } + orientationLocked = !1 + } + } + }) +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/playback/playbackvalidation.js b/dashboard-ui/bower_components/emby-webcomponents/playback/playbackvalidation.js index 046b6d5e70..6fa070ab3b 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/playback/playbackvalidation.js +++ b/dashboard-ui/bower_components/emby-webcomponents/playback/playbackvalidation.js @@ -1 +1,43 @@ -define(["playbackManager","itemHelper"],function(playbackManager,itemHelper){"use strict";function getRequirePromise(deps){return new Promise(function(resolve,reject){require(deps,resolve)})}function validatePlayback(options){var feature="playback";if(!options.item||"TvChannel"!==options.item.Type&&"Recording"!==options.item.Type||(feature="livetv"),"playback"===feature){var player=playbackManager.getCurrentPlayer();if(player&&!player.isLocalPlayer)return Promise.resolve()}return getRequirePromise(["registrationServices"]).then(function(registrationServices){return registrationServices.validateFeature(feature,options).then(function(result){result&&result.enableTimeLimit&&startAutoStopTimer()})})}function startAutoStopTimer(){stopAutoStopTimer(),autoStopTimeout=setTimeout(onAutoStopTimeout,63e3)}function onAutoStopTimeout(){stopAutoStopTimer(),playbackManager.stop()}function stopAutoStopTimer(){var timeout=autoStopTimeout;timeout&&(clearTimeout(timeout),autoStopTimeout=null)}function PlaybackValidation(){this.name="Playback validation",this.type="preplayintercept",this.id="playbackvalidation",this.order=-1}var autoStopTimeout;return PlaybackValidation.prototype.intercept=function(options){return options.fullscreen?options.item&&itemHelper.isLocalItem(options.item)?Promise.resolve():validatePlayback(options):Promise.resolve()},PlaybackValidation}); \ No newline at end of file +define(["playbackManager", "itemHelper"], function(playbackManager, itemHelper) { + "use strict"; + + function getRequirePromise(deps) { + return new Promise(function(resolve, reject) { + require(deps, resolve) + }) + } + + function validatePlayback(options) { + var feature = "playback"; + if (!options.item || "TvChannel" !== options.item.Type && "Recording" !== options.item.Type || (feature = "livetv"), "playback" === feature) { + var player = playbackManager.getCurrentPlayer(); + if (player && !player.isLocalPlayer) return Promise.resolve() + } + return getRequirePromise(["registrationServices"]).then(function(registrationServices) { + return registrationServices.validateFeature(feature, options).then(function(result) { + result && result.enableTimeLimit && startAutoStopTimer() + }) + }) + } + + function startAutoStopTimer() { + stopAutoStopTimer(), autoStopTimeout = setTimeout(onAutoStopTimeout, 63e3) + } + + function onAutoStopTimeout() { + stopAutoStopTimer(), playbackManager.stop() + } + + function stopAutoStopTimer() { + var timeout = autoStopTimeout; + timeout && (clearTimeout(timeout), autoStopTimeout = null) + } + + function PlaybackValidation() { + this.name = "Playback validation", this.type = "preplayintercept", this.id = "playbackvalidation", this.order = -1 + } + var autoStopTimeout; + return PlaybackValidation.prototype.intercept = function(options) { + return options.fullscreen ? options.item && itemHelper.isLocalItem(options.item) ? Promise.resolve() : validatePlayback(options) : Promise.resolve() + }, PlaybackValidation +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/playback/playerselection.js b/dashboard-ui/bower_components/emby-webcomponents/playback/playerselection.js index 6d0bba55cc..0a2445f676 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/playback/playerselection.js +++ b/dashboard-ui/bower_components/emby-webcomponents/playback/playerselection.js @@ -1 +1,158 @@ -define(["appSettings","events","browser","loading","playbackManager","appRouter","globalize","apphost"],function(appSettings,events,browser,loading,playbackManager,appRouter,globalize,appHost){"use strict";function mirrorItem(info,player){var item=info.item;playbackManager.displayContent({ItemName:item.Name,ItemId:item.Id,ItemType:item.Type,Context:info.context},player)}function mirrorIfEnabled(info){if(info&&playbackManager.enableDisplayMirroring()){var getPlayerInfo=playbackManager.getPlayerInfo();getPlayerInfo&&(getPlayerInfo.isLocalPlayer||-1===getPlayerInfo.supportedCommands.indexOf("DisplayContent")||mirrorItem(info,playbackManager.getCurrentPlayer()))}}function emptyCallback(){}function getTargetSecondaryText(target){return target.user?target.user.Name:null}function getIcon(target){var deviceType=target.deviceType;switch(!deviceType&&target.isLocalPlayer&&(deviceType=browser.tv?"tv":browser.mobile?"smartphone":"desktop"),deviceType||(deviceType="tv"),deviceType){case"smartphone":return"";case"tablet":return"";case"tv":return"";case"cast":return"";case"desktop":return"";default:return""}}function showPlayerSelection(button){var currentPlayerInfo=playbackManager.getPlayerInfo();if(currentPlayerInfo&&!currentPlayerInfo.isLocalPlayer)return void showActivePlayerMenu(currentPlayerInfo);var currentPlayerId=currentPlayerInfo?currentPlayerInfo.id:null;loading.show(),playbackManager.getTargets().then(function(targets){var menuItems=targets.map(function(t){var name=t.name;return t.appName&&t.appName!==t.name&&(name+=" - "+t.appName),{name:name,id:t.id,selected:currentPlayerId===t.id,secondaryText:getTargetSecondaryText(t),icon:getIcon(t)}});require(["actionsheet"],function(actionsheet){loading.hide();var menuOptions={title:globalize.translate("sharedcomponents#HeaderPlayOn"),items:menuItems,positionTo:button,resolveOnClick:!0,border:!0};browser.chrome&&!appHost.supports("castmenuhashchange")&&(menuOptions.enableHistory=!1),actionsheet.show(menuOptions).then(function(id){var target=targets.filter(function(t){return t.id===id})[0];playbackManager.trySetActivePlayer(target.playerName,target),mirrorIfEnabled()},emptyCallback)})})}function showActivePlayerMenu(playerInfo){require(["dialogHelper","dialog","emby-checkbox","emby-button"],function(dialogHelper){showActivePlayerMenuInternal(dialogHelper,playerInfo)})}function disconnectFromPlayer(currentDeviceName){-1!==playbackManager.getSupportedCommands().indexOf("EndSession")?require(["dialog"],function(dialog){var menuItems=[];menuItems.push({name:globalize.translate("sharedcomponents#Yes"),id:"yes"}),menuItems.push({name:globalize.translate("sharedcomponents#No"),id:"no"}),dialog({buttons:menuItems,text:globalize.translate("sharedcomponents#ConfirmEndPlayerSession",currentDeviceName)}).then(function(id){switch(id){case"yes":playbackManager.getCurrentPlayer().endSession(),playbackManager.setDefaultPlayerActive();break;case"no":playbackManager.setDefaultPlayerActive()}})}):playbackManager.setDefaultPlayerActive()}function showActivePlayerMenuInternal(dialogHelper,playerInfo){var html="",dialogOptions={removeOnClose:!0};dialogOptions.modal=!1,dialogOptions.entryAnimationDuration=160,dialogOptions.exitAnimationDuration=160,dialogOptions.autoFocus=!1;var dlg=dialogHelper.createDialog(dialogOptions);dlg.classList.add("promptDialog");var currentDeviceName=playerInfo.deviceName||playerInfo.name;if(html+='
',html+='

',html+=currentDeviceName,html+="

",html+="
",-1!==playerInfo.supportedCommands.indexOf("DisplayContent")){html+='"}html+="
",html+='
',html+='",html+='",html+='",html+="
",html+="
",dlg.innerHTML=html;var chkMirror=dlg.querySelector(".chkMirror");chkMirror&&chkMirror.addEventListener("change",onMirrorChange);var destination="",btnRemoteControl=dlg.querySelector(".btnRemoteControl");btnRemoteControl&&btnRemoteControl.addEventListener("click",function(){destination="nowplaying",dialogHelper.close(dlg)}),dlg.querySelector(".btnDisconnect").addEventListener("click",function(){destination="disconnectFromPlayer",dialogHelper.close(dlg)}),dlg.querySelector(".btnCancel").addEventListener("click",function(){dialogHelper.close(dlg)}),dialogHelper.open(dlg).then(function(){"nowplaying"===destination?appRouter.showNowPlaying():"disconnectFromPlayer"===destination&&disconnectFromPlayer(currentDeviceName)},emptyCallback)}function onMirrorChange(){playbackManager.enableDisplayMirroring(this.checked)}return document.addEventListener("viewshow",function(e){var state=e.detail.state||{},item=state.item;if(item&&item.ServerId)return void mirrorIfEnabled({item:item})}),events.on(appSettings,"change",function(e,name){"displaymirror"===name&&mirrorIfEnabled()}),events.on(playbackManager,"pairing",function(e){loading.show()}),events.on(playbackManager,"paired",function(e){loading.hide()}),events.on(playbackManager,"pairerror",function(e){loading.hide()}),{show:showPlayerSelection}}); \ No newline at end of file +define(["appSettings", "events", "browser", "loading", "playbackManager", "appRouter", "globalize", "apphost"], function(appSettings, events, browser, loading, playbackManager, appRouter, globalize, appHost) { + "use strict"; + + function mirrorItem(info, player) { + var item = info.item; + playbackManager.displayContent({ + ItemName: item.Name, + ItemId: item.Id, + ItemType: item.Type, + Context: info.context + }, player) + } + + function mirrorIfEnabled(info) { + if (info && playbackManager.enableDisplayMirroring()) { + var getPlayerInfo = playbackManager.getPlayerInfo(); + getPlayerInfo && (getPlayerInfo.isLocalPlayer || -1 === getPlayerInfo.supportedCommands.indexOf("DisplayContent") || mirrorItem(info, playbackManager.getCurrentPlayer())) + } + } + + function emptyCallback() {} + + function getTargetSecondaryText(target) { + return target.user ? target.user.Name : null + } + + function getIcon(target) { + var deviceType = target.deviceType; + switch (!deviceType && target.isLocalPlayer && (deviceType = browser.tv ? "tv" : browser.mobile ? "smartphone" : "desktop"), deviceType || (deviceType = "tv"), deviceType) { + case "smartphone": + return ""; + case "tablet": + return ""; + case "tv": + return ""; + case "cast": + return ""; + case "desktop": + return ""; + default: + return "" + } + } + + function showPlayerSelection(button) { + var currentPlayerInfo = playbackManager.getPlayerInfo(); + if (currentPlayerInfo && !currentPlayerInfo.isLocalPlayer) return void showActivePlayerMenu(currentPlayerInfo); + var currentPlayerId = currentPlayerInfo ? currentPlayerInfo.id : null; + loading.show(), playbackManager.getTargets().then(function(targets) { + var menuItems = targets.map(function(t) { + var name = t.name; + return t.appName && t.appName !== t.name && (name += " - " + t.appName), { + name: name, + id: t.id, + selected: currentPlayerId === t.id, + secondaryText: getTargetSecondaryText(t), + icon: getIcon(t) + } + }); + require(["actionsheet"], function(actionsheet) { + loading.hide(); + var menuOptions = { + title: globalize.translate("sharedcomponents#HeaderPlayOn"), + items: menuItems, + positionTo: button, + resolveOnClick: !0, + border: !0 + }; + browser.chrome && !appHost.supports("castmenuhashchange") && (menuOptions.enableHistory = !1), actionsheet.show(menuOptions).then(function(id) { + var target = targets.filter(function(t) { + return t.id === id + })[0]; + playbackManager.trySetActivePlayer(target.playerName, target), mirrorIfEnabled() + }, emptyCallback) + }) + }) + } + + function showActivePlayerMenu(playerInfo) { + require(["dialogHelper", "dialog", "emby-checkbox", "emby-button"], function(dialogHelper) { + showActivePlayerMenuInternal(dialogHelper, playerInfo) + }) + } + + function disconnectFromPlayer(currentDeviceName) { + -1 !== playbackManager.getSupportedCommands().indexOf("EndSession") ? require(["dialog"], function(dialog) { + var menuItems = []; + menuItems.push({ + name: globalize.translate("sharedcomponents#Yes"), + id: "yes" + }), menuItems.push({ + name: globalize.translate("sharedcomponents#No"), + id: "no" + }), dialog({ + buttons: menuItems, + text: globalize.translate("sharedcomponents#ConfirmEndPlayerSession", currentDeviceName) + }).then(function(id) { + switch (id) { + case "yes": + playbackManager.getCurrentPlayer().endSession(), playbackManager.setDefaultPlayerActive(); + break; + case "no": + playbackManager.setDefaultPlayerActive() + } + }) + }) : playbackManager.setDefaultPlayerActive() + } + + function showActivePlayerMenuInternal(dialogHelper, playerInfo) { + var html = "", + dialogOptions = { + removeOnClose: !0 + }; + dialogOptions.modal = !1, dialogOptions.entryAnimationDuration = 160, dialogOptions.exitAnimationDuration = 160, dialogOptions.autoFocus = !1; + var dlg = dialogHelper.createDialog(dialogOptions); + dlg.classList.add("promptDialog"); + var currentDeviceName = playerInfo.deviceName || playerInfo.name; + if (html += '
', html += '

', html += currentDeviceName, html += "

", html += "
", -1 !== playerInfo.supportedCommands.indexOf("DisplayContent")) { + html += '" + } + html += "
", html += '
', html += '", html += '", html += '", html += "
", html += "
", dlg.innerHTML = html; + var chkMirror = dlg.querySelector(".chkMirror"); + chkMirror && chkMirror.addEventListener("change", onMirrorChange); + var destination = "", + btnRemoteControl = dlg.querySelector(".btnRemoteControl"); + btnRemoteControl && btnRemoteControl.addEventListener("click", function() { + destination = "nowplaying", dialogHelper.close(dlg) + }), dlg.querySelector(".btnDisconnect").addEventListener("click", function() { + destination = "disconnectFromPlayer", dialogHelper.close(dlg) + }), dlg.querySelector(".btnCancel").addEventListener("click", function() { + dialogHelper.close(dlg) + }), dialogHelper.open(dlg).then(function() { + "nowplaying" === destination ? appRouter.showNowPlaying() : "disconnectFromPlayer" === destination && disconnectFromPlayer(currentDeviceName) + }, emptyCallback) + } + + function onMirrorChange() { + playbackManager.enableDisplayMirroring(this.checked) + } + return document.addEventListener("viewshow", function(e) { + var state = e.detail.state || {}, + item = state.item; + if (item && item.ServerId) return void mirrorIfEnabled({ + item: item + }) + }), events.on(appSettings, "change", function(e, name) { + "displaymirror" === name && mirrorIfEnabled() + }), events.on(playbackManager, "pairing", function(e) { + loading.show() + }), events.on(playbackManager, "paired", function(e) { + loading.hide() + }), events.on(playbackManager, "pairerror", function(e) { + loading.hide() + }), { + show: showPlayerSelection + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/playback/playersettingsmenu.js b/dashboard-ui/bower_components/emby-webcomponents/playback/playersettingsmenu.js index 3cae0391ac..f75ad2a65b 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/playback/playersettingsmenu.js +++ b/dashboard-ui/bower_components/emby-webcomponents/playback/playersettingsmenu.js @@ -1 +1,195 @@ -define(["connectionManager","actionsheet","datetime","playbackManager","globalize","appSettings","qualityoptions"],function(connectionManager,actionsheet,datetime,playbackManager,globalize,appSettings,qualityoptions){"use strict";function showQualityMenu(player,btn){var videoStream=playbackManager.currentMediaSource(player).MediaStreams.filter(function(stream){return"Video"===stream.Type})[0],videoWidth=videoStream?videoStream.Width:null,options=qualityoptions.getVideoQualityOptions({currentMaxBitrate:playbackManager.getMaxStreamingBitrate(player),isAutomaticBitrateEnabled:playbackManager.enableAutomaticBitrateDetection(player),videoWidth:videoWidth,enableAuto:!0}),menuItems=options.map(function(o){var opt={name:o.name,id:o.bitrate,asideText:o.secondaryText};return o.selected&&(opt.selected=!0),opt}),selectedId=options.filter(function(o){return o.selected});return selectedId=selectedId.length?selectedId[0].bitrate:null,actionsheet.show({items:menuItems,positionTo:btn}).then(function(id){var bitrate=parseInt(id);bitrate!==selectedId&&playbackManager.setMaxStreamingBitrate({enableAutomaticBitrateDetection:!bitrate,maxBitrate:bitrate},player)})}function showRepeatModeMenu(player,btn){var menuItems=[],currentValue=playbackManager.getRepeatMode(player);return menuItems.push({name:globalize.translate("sharedcomponents#RepeatAll"),id:"RepeatAll",selected:"RepeatAll"===currentValue}),menuItems.push({name:globalize.translate("sharedcomponents#RepeatOne"),id:"RepeatOne",selected:"RepeatOne"===currentValue}),menuItems.push({name:globalize.translate("sharedcomponents#None"),id:"RepeatNone",selected:"RepeatNone"===currentValue}),actionsheet.show({items:menuItems,positionTo:btn}).then(function(mode){mode&&playbackManager.setRepeatMode(mode,player)})}function getQualitySecondaryText(player){var state=playbackManager.getPlayerState(player),videoStream=(playbackManager.enableAutomaticBitrateDetection(player),playbackManager.getMaxStreamingBitrate(player),playbackManager.currentMediaSource(player).MediaStreams.filter(function(stream){return"Video"===stream.Type})[0]),videoWidth=videoStream?videoStream.Width:null,options=qualityoptions.getVideoQualityOptions({currentMaxBitrate:playbackManager.getMaxStreamingBitrate(player),isAutomaticBitrateEnabled:playbackManager.enableAutomaticBitrateDetection(player),videoWidth:videoWidth,enableAuto:!0}),selectedOption=(options.map(function(o){var opt={name:o.name,id:o.bitrate,asideText:o.secondaryText};return o.selected&&(opt.selected=!0),opt}),options.filter(function(o){return o.selected}));if(!selectedOption.length)return null;selectedOption=selectedOption[0];var text=selectedOption.name;return selectedOption.autoText&&(state.PlayState&&"Transcode"!==state.PlayState.PlayMethod?text+=" - Direct":text+=" "+selectedOption.autoText),text}function showAspectRatioMenu(player,btn){var currentId=playbackManager.getAspectRatio(player),menuItems=playbackManager.getSupportedAspectRatios(player).map(function(i){return{id:i.id,name:i.name,selected:i.id===currentId}});return actionsheet.show({items:menuItems,positionTo:btn}).then(function(id){return id?(playbackManager.setAspectRatio(id,player),Promise.resolve()):Promise.reject()})}function showWithUser(options,player,user){var supportedCommands=playbackManager.getSupportedCommands(player),menuItems=(options.mediaType,[]);if(-1!==supportedCommands.indexOf("SetAspectRatio")){var currentAspectRatioId=playbackManager.getAspectRatio(player),currentAspectRatio=playbackManager.getSupportedAspectRatios(player).filter(function(i){return i.id===currentAspectRatioId})[0];menuItems.push({name:globalize.translate("sharedcomponents#AspectRatio"),id:"aspectratio",asideText:currentAspectRatio?currentAspectRatio.name:null})}if(menuItems.push({name:globalize.translate("sharedcomponents#PlaybackSettings"),id:"playbacksettings"}),user&&user.Policy.EnableVideoPlaybackTranscoding){var secondaryQualityText=getQualitySecondaryText(player);menuItems.push({name:globalize.translate("sharedcomponents#Quality"),id:"quality",asideText:secondaryQualityText})}var repeatMode=playbackManager.getRepeatMode(player);return-1!==supportedCommands.indexOf("SetRepeatMode")&&playbackManager.currentMediaSource(player).RunTimeTicks&&menuItems.push({name:globalize.translate("sharedcomponents#RepeatMode"),id:"repeatmode",asideText:"RepeatNone"===repeatMode?globalize.translate("sharedcomponents#None"):globalize.translate("sharedcomponents#"+repeatMode)}),options.stats&&menuItems.push({name:globalize.translate("sharedcomponents#StatsForNerds"),id:"stats",asideText:null}),menuItems.push({name:globalize.translate("sharedcomponents#SubtitleSettings"),id:"subtitlesettings"}),actionsheet.show({items:menuItems,positionTo:options.positionTo}).then(function(id){return handleSelectedOption(id,options,player)})}function show(options){var player=options.player,currentItem=playbackManager.currentItem(player);return currentItem&¤tItem.ServerId?connectionManager.getApiClient(currentItem.ServerId).getCurrentUser().then(function(user){return showWithUser(options,player,user)}):showWithUser(options,player,null)}function alertText(text){return new Promise(function(resolve,reject){require(["alert"],function(alert){alert(text).then(resolve)})})}function showSubtitleSettings(player,btn){return alertText(globalize.translate("sharedcomponents#SubtitleSettingsIntro"))}function showPlaybackSettings(player,btn){return alertText(globalize.translate("sharedcomponents#PlaybackSettingsIntro"))}function handleSelectedOption(id,options,player){switch(id){case"quality":return showQualityMenu(player,options.positionTo);case"aspectratio":return showAspectRatioMenu(player,options.positionTo);case"repeatmode":return showRepeatModeMenu(player,options.positionTo);case"subtitlesettings":return showSubtitleSettings(player,options.positionTo);case"playbacksettings":return showPlaybackSettings(player,options.positionTo);case"stats":return options.onOption&&options.onOption("stats"),Promise.resolve()}return Promise.reject()}return{show:show}}); \ No newline at end of file +define(["connectionManager", "actionsheet", "datetime", "playbackManager", "globalize", "appSettings", "qualityoptions"], function(connectionManager, actionsheet, datetime, playbackManager, globalize, appSettings, qualityoptions) { + "use strict"; + + function showQualityMenu(player, btn) { + var videoStream = playbackManager.currentMediaSource(player).MediaStreams.filter(function(stream) { + return "Video" === stream.Type + })[0], + videoWidth = videoStream ? videoStream.Width : null, + options = qualityoptions.getVideoQualityOptions({ + currentMaxBitrate: playbackManager.getMaxStreamingBitrate(player), + isAutomaticBitrateEnabled: playbackManager.enableAutomaticBitrateDetection(player), + videoWidth: videoWidth, + enableAuto: !0 + }), + menuItems = options.map(function(o) { + var opt = { + name: o.name, + id: o.bitrate, + asideText: o.secondaryText + }; + return o.selected && (opt.selected = !0), opt + }), + selectedId = options.filter(function(o) { + return o.selected + }); + return selectedId = selectedId.length ? selectedId[0].bitrate : null, actionsheet.show({ + items: menuItems, + positionTo: btn + }).then(function(id) { + var bitrate = parseInt(id); + bitrate !== selectedId && playbackManager.setMaxStreamingBitrate({ + enableAutomaticBitrateDetection: !bitrate, + maxBitrate: bitrate + }, player) + }) + } + + function showRepeatModeMenu(player, btn) { + var menuItems = [], + currentValue = playbackManager.getRepeatMode(player); + return menuItems.push({ + name: globalize.translate("sharedcomponents#RepeatAll"), + id: "RepeatAll", + selected: "RepeatAll" === currentValue + }), menuItems.push({ + name: globalize.translate("sharedcomponents#RepeatOne"), + id: "RepeatOne", + selected: "RepeatOne" === currentValue + }), menuItems.push({ + name: globalize.translate("sharedcomponents#None"), + id: "RepeatNone", + selected: "RepeatNone" === currentValue + }), actionsheet.show({ + items: menuItems, + positionTo: btn + }).then(function(mode) { + mode && playbackManager.setRepeatMode(mode, player) + }) + } + + function getQualitySecondaryText(player) { + var state = playbackManager.getPlayerState(player), + videoStream = (playbackManager.enableAutomaticBitrateDetection(player), playbackManager.getMaxStreamingBitrate(player), playbackManager.currentMediaSource(player).MediaStreams.filter(function(stream) { + return "Video" === stream.Type + })[0]), + videoWidth = videoStream ? videoStream.Width : null, + options = qualityoptions.getVideoQualityOptions({ + currentMaxBitrate: playbackManager.getMaxStreamingBitrate(player), + isAutomaticBitrateEnabled: playbackManager.enableAutomaticBitrateDetection(player), + videoWidth: videoWidth, + enableAuto: !0 + }), + selectedOption = (options.map(function(o) { + var opt = { + name: o.name, + id: o.bitrate, + asideText: o.secondaryText + }; + return o.selected && (opt.selected = !0), opt + }), options.filter(function(o) { + return o.selected + })); + if (!selectedOption.length) return null; + selectedOption = selectedOption[0]; + var text = selectedOption.name; + return selectedOption.autoText && (state.PlayState && "Transcode" !== state.PlayState.PlayMethod ? text += " - Direct" : text += " " + selectedOption.autoText), text + } + + function showAspectRatioMenu(player, btn) { + var currentId = playbackManager.getAspectRatio(player), + menuItems = playbackManager.getSupportedAspectRatios(player).map(function(i) { + return { + id: i.id, + name: i.name, + selected: i.id === currentId + } + }); + return actionsheet.show({ + items: menuItems, + positionTo: btn + }).then(function(id) { + return id ? (playbackManager.setAspectRatio(id, player), Promise.resolve()) : Promise.reject() + }) + } + + function showWithUser(options, player, user) { + var supportedCommands = playbackManager.getSupportedCommands(player), + menuItems = (options.mediaType, []); + if (-1 !== supportedCommands.indexOf("SetAspectRatio")) { + var currentAspectRatioId = playbackManager.getAspectRatio(player), + currentAspectRatio = playbackManager.getSupportedAspectRatios(player).filter(function(i) { + return i.id === currentAspectRatioId + })[0]; + menuItems.push({ + name: globalize.translate("sharedcomponents#AspectRatio"), + id: "aspectratio", + asideText: currentAspectRatio ? currentAspectRatio.name : null + }) + } + if (menuItems.push({ + name: globalize.translate("sharedcomponents#PlaybackSettings"), + id: "playbacksettings" + }), user && user.Policy.EnableVideoPlaybackTranscoding) { + var secondaryQualityText = getQualitySecondaryText(player); + menuItems.push({ + name: globalize.translate("sharedcomponents#Quality"), + id: "quality", + asideText: secondaryQualityText + }) + } + var repeatMode = playbackManager.getRepeatMode(player); + return -1 !== supportedCommands.indexOf("SetRepeatMode") && playbackManager.currentMediaSource(player).RunTimeTicks && menuItems.push({ + name: globalize.translate("sharedcomponents#RepeatMode"), + id: "repeatmode", + asideText: "RepeatNone" === repeatMode ? globalize.translate("sharedcomponents#None") : globalize.translate("sharedcomponents#" + repeatMode) + }), options.stats && menuItems.push({ + name: globalize.translate("sharedcomponents#StatsForNerds"), + id: "stats", + asideText: null + }), menuItems.push({ + name: globalize.translate("sharedcomponents#SubtitleSettings"), + id: "subtitlesettings" + }), actionsheet.show({ + items: menuItems, + positionTo: options.positionTo + }).then(function(id) { + return handleSelectedOption(id, options, player) + }) + } + + function show(options) { + var player = options.player, + currentItem = playbackManager.currentItem(player); + return currentItem && currentItem.ServerId ? connectionManager.getApiClient(currentItem.ServerId).getCurrentUser().then(function(user) { + return showWithUser(options, player, user) + }) : showWithUser(options, player, null) + } + + function alertText(text) { + return new Promise(function(resolve, reject) { + require(["alert"], function(alert) { + alert(text).then(resolve) + }) + }) + } + + function showSubtitleSettings(player, btn) { + return alertText(globalize.translate("sharedcomponents#SubtitleSettingsIntro")) + } + + function showPlaybackSettings(player, btn) { + return alertText(globalize.translate("sharedcomponents#PlaybackSettingsIntro")) + } + + function handleSelectedOption(id, options, player) { + switch (id) { + case "quality": + return showQualityMenu(player, options.positionTo); + case "aspectratio": + return showAspectRatioMenu(player, options.positionTo); + case "repeatmode": + return showRepeatModeMenu(player, options.positionTo); + case "subtitlesettings": + return showSubtitleSettings(player, options.positionTo); + case "playbacksettings": + return showPlaybackSettings(player, options.positionTo); + case "stats": + return options.onOption && options.onOption("stats"), Promise.resolve() + } + return Promise.reject() + } + return { + show: show + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/playback/playmethodhelper.js b/dashboard-ui/bower_components/emby-webcomponents/playback/playmethodhelper.js index a2d05f8096..56e5f45dfa 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/playback/playmethodhelper.js +++ b/dashboard-ui/bower_components/emby-webcomponents/playback/playmethodhelper.js @@ -1 +1,10 @@ -define([],function(){"use strict";function getDisplayPlayMethod(session){return session.NowPlayingItem?session.TranscodingInfo&&session.TranscodingInfo.IsVideoDirect?"DirectStream":"Transcode"===session.PlayState.PlayMethod?"Transcode":"DirectStream"===session.PlayState.PlayMethod?"DirectPlay":"DirectPlay"===session.PlayState.PlayMethod?"DirectPlay":void 0:null}return{getDisplayPlayMethod:getDisplayPlayMethod}}); \ No newline at end of file +define([], function() { + "use strict"; + + function getDisplayPlayMethod(session) { + return session.NowPlayingItem ? session.TranscodingInfo && session.TranscodingInfo.IsVideoDirect ? "DirectStream" : "Transcode" === session.PlayState.PlayMethod ? "Transcode" : "DirectStream" === session.PlayState.PlayMethod ? "DirectPlay" : "DirectPlay" === session.PlayState.PlayMethod ? "DirectPlay" : void 0 : null + } + return { + getDisplayPlayMethod: getDisplayPlayMethod + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/playback/playqueuemanager.js b/dashboard-ui/bower_components/emby-webcomponents/playback/playqueuemanager.js index 36375c225d..0962bfc4b0 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/playback/playqueuemanager.js +++ b/dashboard-ui/bower_components/emby-webcomponents/playback/playqueuemanager.js @@ -1 +1,103 @@ -define([],function(){"use strict";function addUniquePlaylistItemId(item){item.PlaylistItemId||(item.PlaylistItemId="playlistItem"+currentId,currentId++)}function findPlaylistIndex(playlistItemId,list){for(var i=0,length=list.length;i=playlist.length)throw new Error("newIndex out of bounds");return moveInArray(playlist,oldIndex,newIndex),this._playlist=playlist,{result:"moved",playlistItemId:playlistItemId,newIndex:newIndex}},PlayQueueManager.prototype.reset=function(){this._playlist=[],this._currentPlaylistItemId=null,this._repeatMode="RepeatNone"},PlayQueueManager.prototype.setRepeatMode=function(value){this._repeatMode=value},PlayQueueManager.prototype.getRepeatMode=function(){return this._repeatMode},PlayQueueManager.prototype.getNextItemInfo=function(){var newIndex,playlist=this.getPlaylist(),playlistLength=playlist.length;switch(this.getRepeatMode()){case"RepeatOne":newIndex=this.getCurrentPlaylistIndex();break;case"RepeatAll":newIndex=this.getCurrentPlaylistIndex()+1,newIndex>=playlistLength&&(newIndex=0);break;default:newIndex=this.getCurrentPlaylistIndex()+1}if(newIndex<0||newIndex>=playlistLength)return null;var item=playlist[newIndex];return item?{item:item,index:newIndex}:null},PlayQueueManager}); \ No newline at end of file +define([], function() { + "use strict"; + + function addUniquePlaylistItemId(item) { + item.PlaylistItemId || (item.PlaylistItemId = "playlistItem" + currentId, currentId++) + } + + function findPlaylistIndex(playlistItemId, list) { + for (var i = 0, length = list.length; i < length; i++) + if (list[i].PlaylistItemId === playlistItemId) return i; + return -1 + } + + function PlayQueueManager() { + this._playlist = [], this._repeatMode = "RepeatNone" + } + + function arrayInsertAt(destArray, pos, arrayToInsert) { + var args = []; + args.push(pos), args.push(0), args = args.concat(arrayToInsert), destArray.splice.apply(destArray, args) + } + + function moveInArray(array, from, to) { + array.splice(to, 0, array.splice(from, 1)[0]) + } + var currentId = 0; + return PlayQueueManager.prototype.getPlaylist = function() { + return this._playlist.slice(0) + }, PlayQueueManager.prototype.setPlaylist = function(items) { + items = items.slice(0); + for (var i = 0, length = items.length; i < length; i++) addUniquePlaylistItemId(items[i]); + this._currentPlaylistItemId = null, this._playlist = items, this._repeatMode = "RepeatNone" + }, PlayQueueManager.prototype.queue = function(items) { + for (var i = 0, length = items.length; i < length; i++) addUniquePlaylistItemId(items[i]), this._playlist.push(items[i]) + }, PlayQueueManager.prototype.queueNext = function(items) { + var i, length; + for (i = 0, length = items.length; i < length; i++) addUniquePlaylistItemId(items[i]); + var currentIndex = this.getCurrentPlaylistIndex(); - 1 === currentIndex ? currentIndex = this._playlist.length : currentIndex++, arrayInsertAt(this._playlist, currentIndex, items) + }, PlayQueueManager.prototype.getCurrentPlaylistIndex = function() { + return findPlaylistIndex(this.getCurrentPlaylistItemId(), this._playlist) + }, PlayQueueManager.prototype.getCurrentItem = function() { + var index = findPlaylistIndex(this.getCurrentPlaylistItemId(), this._playlist); + return -1 === index ? null : this._playlist[index] + }, PlayQueueManager.prototype.getCurrentPlaylistItemId = function() { + return this._currentPlaylistItemId + }, PlayQueueManager.prototype.setPlaylistState = function(playlistItemId, playlistIndex) { + this._currentPlaylistItemId = playlistItemId + }, PlayQueueManager.prototype.setPlaylistIndex = function(playlistIndex) { + playlistIndex < 0 ? this.setPlaylistState(null) : this.setPlaylistState(this._playlist[playlistIndex].PlaylistItemId) + }, PlayQueueManager.prototype.removeFromPlaylist = function(playlistItemIds) { + var playlist = this.getPlaylist(); + if (playlist.length <= playlistItemIds.length) return { + result: "empty" + }; + var currentPlaylistItemId = this.getCurrentPlaylistItemId(), + isCurrentIndex = -1 !== playlistItemIds.indexOf(currentPlaylistItemId); + return this._playlist = playlist.filter(function(item) { + return -1 === playlistItemIds.indexOf(item.PlaylistItemId) + }), { + result: "removed", + isCurrentIndex: isCurrentIndex + } + }, PlayQueueManager.prototype.movePlaylistItem = function(playlistItemId, newIndex) { + for (var oldIndex, playlist = this.getPlaylist(), i = 0, length = playlist.length; i < length; i++) + if (playlist[i].PlaylistItemId === playlistItemId) { + oldIndex = i; + break + } if (-1 === oldIndex || oldIndex === newIndex) return { + result: "noop" + }; + if (newIndex >= playlist.length) throw new Error("newIndex out of bounds"); + return moveInArray(playlist, oldIndex, newIndex), this._playlist = playlist, { + result: "moved", + playlistItemId: playlistItemId, + newIndex: newIndex + } + }, PlayQueueManager.prototype.reset = function() { + this._playlist = [], this._currentPlaylistItemId = null, this._repeatMode = "RepeatNone" + }, PlayQueueManager.prototype.setRepeatMode = function(value) { + this._repeatMode = value + }, PlayQueueManager.prototype.getRepeatMode = function() { + return this._repeatMode + }, PlayQueueManager.prototype.getNextItemInfo = function() { + var newIndex, playlist = this.getPlaylist(), + playlistLength = playlist.length; + switch (this.getRepeatMode()) { + case "RepeatOne": + newIndex = this.getCurrentPlaylistIndex(); + break; + case "RepeatAll": + newIndex = this.getCurrentPlaylistIndex() + 1, newIndex >= playlistLength && (newIndex = 0); + break; + default: + newIndex = this.getCurrentPlaylistIndex() + 1 + } + if (newIndex < 0 || newIndex >= playlistLength) return null; + var item = playlist[newIndex]; + return item ? { + item: item, + index: newIndex + } : null + }, PlayQueueManager +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/playback/remotecontrolautoplay.js b/dashboard-ui/bower_components/emby-webcomponents/playback/remotecontrolautoplay.js index bbe8735f9a..6cc1929497 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/playback/remotecontrolautoplay.js +++ b/dashboard-ui/bower_components/emby-webcomponents/playback/remotecontrolautoplay.js @@ -1 +1,22 @@ -define(["events","playbackManager"],function(events,playbackManager){"use strict";function transferPlayback(oldPlayer,newPlayer){var state=playbackManager.getPlayerState(oldPlayer),item=state.NowPlayingItem;if(item){var playState=state.PlayState||{},resumePositionTicks=playState.PositionTicks||0;playbackManager.stop(oldPlayer).then(function(){playbackManager.play({ids:[item.Id],serverId:item.ServerId,startPositionTicks:resumePositionTicks},newPlayer)})}}events.on(playbackManager,"playerchange",function(e,newPlayer,newTarget,oldPlayer){if(oldPlayer&&newPlayer)return oldPlayer.isLocalPlayer?newPlayer.isLocalPlayer?void console.log("Skipping remote control autoplay because newPlayer is a local player"):void transferPlayback(oldPlayer,newPlayer):void console.log("Skipping remote control autoplay because oldPlayer is not a local player")})}); \ No newline at end of file +define(["events", "playbackManager"], function(events, playbackManager) { + "use strict"; + + function transferPlayback(oldPlayer, newPlayer) { + var state = playbackManager.getPlayerState(oldPlayer), + item = state.NowPlayingItem; + if (item) { + var playState = state.PlayState || {}, + resumePositionTicks = playState.PositionTicks || 0; + playbackManager.stop(oldPlayer).then(function() { + playbackManager.play({ + ids: [item.Id], + serverId: item.ServerId, + startPositionTicks: resumePositionTicks + }, newPlayer) + }) + } + } + events.on(playbackManager, "playerchange", function(e, newPlayer, newTarget, oldPlayer) { + if (oldPlayer && newPlayer) return oldPlayer.isLocalPlayer ? newPlayer.isLocalPlayer ? void console.log("Skipping remote control autoplay because newPlayer is a local player") : void transferPlayback(oldPlayer, newPlayer) : void console.log("Skipping remote control autoplay because oldPlayer is not a local player") + }) +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/playback/volumeosd.js b/dashboard-ui/bower_components/emby-webcomponents/playback/volumeosd.js index b33ed54cd1..0987947f6f 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/playback/volumeosd.js +++ b/dashboard-ui/bower_components/emby-webcomponents/playback/volumeosd.js @@ -1 +1,63 @@ -define(["events","playbackManager","dom","browser","css!./iconosd","material-icons"],function(events,playbackManager,dom,browser){"use strict";function getOsdElementHtml(){var html="";return html+='',html+='
'}function ensureOsdElement(){var elem=osdElement;elem||(enableAnimation=browser.supportsCssAnimation(),elem=document.createElement("div"),elem.classList.add("hide"),elem.classList.add("iconOsd"),elem.classList.add("iconOsd-hidden"),elem.classList.add("volumeOsd"),elem.innerHTML=getOsdElementHtml(),iconElement=elem.querySelector("i"),progressElement=elem.querySelector(".iconOsdProgressInner"),document.body.appendChild(elem),osdElement=elem)}function onHideComplete(){this.classList.add("hide")}function showOsd(){clearHideTimeout();var elem=osdElement;dom.removeEventListener(elem,dom.whichTransitionEvent(),onHideComplete,{once:!0}),elem.classList.remove("hide"),elem.offsetWidth,requestAnimationFrame(function(){elem.classList.remove("iconOsd-hidden"),hideTimeout=setTimeout(hideOsd,3e3)})}function clearHideTimeout(){hideTimeout&&(clearTimeout(hideTimeout),hideTimeout=null)}function hideOsd(){clearHideTimeout();var elem=osdElement;elem&&(enableAnimation?(elem.offsetWidth,requestAnimationFrame(function(){elem.classList.add("iconOsd-hidden"),dom.addEventListener(elem,dom.whichTransitionEvent(),onHideComplete,{once:!0})})):onHideComplete.call(elem))}function updatePlayerVolumeState(isMuted,volume){iconElement&&(iconElement.innerHTML=isMuted?"":""),progressElement&&(progressElement.style.width=(volume||0)+"%")}function releaseCurrentPlayer(){var player=currentPlayer;player&&(events.off(player,"volumechange",onVolumeChanged),events.off(player,"playbackstop",hideOsd),currentPlayer=null)}function onVolumeChanged(e){var player=this;ensureOsdElement(),updatePlayerVolumeState(player.isMuted(),player.getVolume()),showOsd()}function bindToPlayer(player){player!==currentPlayer&&(releaseCurrentPlayer(),currentPlayer=player,player&&(hideOsd(),events.on(player,"volumechange",onVolumeChanged),events.on(player,"playbackstop",hideOsd)))}var currentPlayer,osdElement,iconElement,progressElement,enableAnimation,hideTimeout;events.on(playbackManager,"playerchange",function(){bindToPlayer(playbackManager.getCurrentPlayer())}),bindToPlayer(playbackManager.getCurrentPlayer())}); \ No newline at end of file +define(["events", "playbackManager", "dom", "browser", "css!./iconosd", "material-icons"], function(events, playbackManager, dom, browser) { + "use strict"; + + function getOsdElementHtml() { + var html = ""; + return html += '', html += '
' + } + + function ensureOsdElement() { + var elem = osdElement; + elem || (enableAnimation = browser.supportsCssAnimation(), elem = document.createElement("div"), elem.classList.add("hide"), elem.classList.add("iconOsd"), elem.classList.add("iconOsd-hidden"), elem.classList.add("volumeOsd"), elem.innerHTML = getOsdElementHtml(), iconElement = elem.querySelector("i"), progressElement = elem.querySelector(".iconOsdProgressInner"), document.body.appendChild(elem), osdElement = elem) + } + + function onHideComplete() { + this.classList.add("hide") + } + + function showOsd() { + clearHideTimeout(); + var elem = osdElement; + dom.removeEventListener(elem, dom.whichTransitionEvent(), onHideComplete, { + once: !0 + }), elem.classList.remove("hide"), elem.offsetWidth, requestAnimationFrame(function() { + elem.classList.remove("iconOsd-hidden"), hideTimeout = setTimeout(hideOsd, 3e3) + }) + } + + function clearHideTimeout() { + hideTimeout && (clearTimeout(hideTimeout), hideTimeout = null) + } + + function hideOsd() { + clearHideTimeout(); + var elem = osdElement; + elem && (enableAnimation ? (elem.offsetWidth, requestAnimationFrame(function() { + elem.classList.add("iconOsd-hidden"), dom.addEventListener(elem, dom.whichTransitionEvent(), onHideComplete, { + once: !0 + }) + })) : onHideComplete.call(elem)) + } + + function updatePlayerVolumeState(isMuted, volume) { + iconElement && (iconElement.innerHTML = isMuted ? "" : ""), progressElement && (progressElement.style.width = (volume || 0) + "%") + } + + function releaseCurrentPlayer() { + var player = currentPlayer; + player && (events.off(player, "volumechange", onVolumeChanged), events.off(player, "playbackstop", hideOsd), currentPlayer = null) + } + + function onVolumeChanged(e) { + var player = this; + ensureOsdElement(), updatePlayerVolumeState(player.isMuted(), player.getVolume()), showOsd() + } + + function bindToPlayer(player) { + player !== currentPlayer && (releaseCurrentPlayer(), currentPlayer = player, player && (hideOsd(), events.on(player, "volumechange", onVolumeChanged), events.on(player, "playbackstop", hideOsd))) + } + var currentPlayer, osdElement, iconElement, progressElement, enableAnimation, hideTimeout; + events.on(playbackManager, "playerchange", function() { + bindToPlayer(playbackManager.getCurrentPlayer()) + }), bindToPlayer(playbackManager.getCurrentPlayer()) +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/playbacksettings/playbacksettings.js b/dashboard-ui/bower_components/emby-webcomponents/playbacksettings/playbacksettings.js index 0999d1db89..bb74207382 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/playbacksettings/playbacksettings.js +++ b/dashboard-ui/bower_components/emby-webcomponents/playbacksettings/playbacksettings.js @@ -1 +1,135 @@ -define(["require","browser","appSettings","apphost","focusManager","qualityoptions","globalize","loading","connectionManager","dom","events","emby-select","emby-checkbox"],function(require,browser,appSettings,appHost,focusManager,qualityoptions,globalize,loading,connectionManager,dom,events){"use strict";function fillSkipLengths(select){var options=[5,10,15,20,25,30];select.innerHTML=options.map(function(option){return{name:globalize.translate("sharedcomponents#ValueSeconds",option),value:1e3*option}}).map(function(o){return'"}).join("")}function populateLanguages(select,languages){var html="";html+="";for(var i=0,length=languages.length;i"+culture.DisplayName+""}select.innerHTML=html}function setMaxBitrateIntoField(select,isInNetwork,mediatype){var options="Audio"===mediatype?qualityoptions.getAudioQualityOptions({currentMaxBitrate:appSettings.maxStreamingBitrate(isInNetwork,mediatype),isAutomaticBitrateEnabled:appSettings.enableAutomaticBitrateDetection(isInNetwork,mediatype),enableAuto:!0}):qualityoptions.getVideoQualityOptions({currentMaxBitrate:appSettings.maxStreamingBitrate(isInNetwork,mediatype),isAutomaticBitrateEnabled:appSettings.enableAutomaticBitrateDetection(isInNetwork,mediatype),enableAuto:!0});select.innerHTML=options.map(function(i){return'"}).join(""),appSettings.enableAutomaticBitrateDetection(isInNetwork,mediatype)?select.value="":select.value=appSettings.maxStreamingBitrate(isInNetwork,mediatype)}function fillChromecastQuality(select){var options=qualityoptions.getVideoQualityOptions({currentMaxBitrate:appSettings.maxChromecastBitrate(),isAutomaticBitrateEnabled:!appSettings.maxChromecastBitrate(),enableAuto:!0});select.innerHTML=options.map(function(i){return'"}).join(""),select.value=appSettings.maxChromecastBitrate()||""}function setMaxBitrateFromField(select,isInNetwork,mediatype,value){select.value?(appSettings.maxStreamingBitrate(isInNetwork,mediatype,select.value),appSettings.enableAutomaticBitrateDetection(isInNetwork,mediatype,!1)):appSettings.enableAutomaticBitrateDetection(isInNetwork,mediatype,!0)}function showHideQualityFields(context,user,apiClient){if(user.Policy.EnableVideoPlaybackTranscoding?context.querySelector(".videoQualitySection").classList.remove("hide"):context.querySelector(".videoQualitySection").classList.add("hide"),appHost.supports("multiserver"))return context.querySelector(".fldVideoInNetworkQuality").classList.remove("hide"),context.querySelector(".fldVideoInternetQuality").classList.remove("hide"),void(user.Policy.EnableAudioPlaybackTranscoding?context.querySelector(".musicQualitySection").classList.remove("hide"):context.querySelector(".musicQualitySection").classList.add("hide"));apiClient.getEndpointInfo().then(function(endpointInfo){endpointInfo.IsInNetwork?(context.querySelector(".fldVideoInNetworkQuality").classList.remove("hide"),context.querySelector(".fldVideoInternetQuality").classList.add("hide"),context.querySelector(".musicQualitySection").classList.add("hide")):(context.querySelector(".fldVideoInNetworkQuality").classList.add("hide"),context.querySelector(".fldVideoInternetQuality").classList.remove("hide"),user.Policy.EnableAudioPlaybackTranscoding?context.querySelector(".musicQualitySection").classList.remove("hide"):context.querySelector(".musicQualitySection").classList.add("hide"))})}function showOrHideEpisodesField(context,user,apiClient){if(browser.tizen||browser.web0s)return void context.querySelector(".fldEpisodeAutoPlay").classList.add("hide");context.querySelector(".fldEpisodeAutoPlay").classList.remove("hide")}function loadForm(context,user,userSettings,apiClient){var loggedInUserId=apiClient.getCurrentUserId(),userId=user.Id;showHideQualityFields(context,user,apiClient),apiClient.getCultures().then(function(allCultures){populateLanguages(context.querySelector("#selectAudioLanguage"),allCultures),context.querySelector("#selectAudioLanguage",context).value=user.Configuration.AudioLanguagePreference||"",context.querySelector(".chkEpisodeAutoPlay").checked=user.Configuration.EnableNextEpisodeAutoPlay||!1}),apiClient.getNamedConfiguration("cinemamode").then(function(cinemaConfig){cinemaConfig.EnableIntrosForMovies||cinemaConfig.EnableIntrosForEpisodes?context.querySelector(".cinemaModeOptions").classList.remove("hide"):context.querySelector(".cinemaModeOptions").classList.add("hide")}),appHost.supports("externalplayerintent")&&userId===loggedInUserId?context.querySelector(".fldExternalPlayer").classList.remove("hide"):context.querySelector(".fldExternalPlayer").classList.add("hide"),userId===loggedInUserId&&(user.Policy.EnableVideoPlaybackTranscoding||user.Policy.EnableAudioPlaybackTranscoding)?(context.querySelector(".qualitySections").classList.remove("hide"),appHost.supports("chromecast")&&user.Policy.EnableVideoPlaybackTranscoding?context.querySelector(".fldChromecastQuality").classList.remove("hide"):context.querySelector(".fldChromecastQuality").classList.add("hide")):(context.querySelector(".qualitySections").classList.add("hide"),context.querySelector(".fldChromecastQuality").classList.add("hide")),browser.tizen||browser.web0s?context.querySelector(".fldEnableNextVideoOverlay").classList.add("hide"):context.querySelector(".fldEnableNextVideoOverlay").classList.remove("hide"),context.querySelector(".chkPlayDefaultAudioTrack").checked=user.Configuration.PlayDefaultAudioTrack||!1,context.querySelector(".chkEnableCinemaMode").checked=userSettings.enableCinemaMode(),context.querySelector(".chkEnableNextVideoOverlay").checked=userSettings.enableNextVideoInfoOverlay(),context.querySelector(".chkExternalVideoPlayer").checked=appSettings.enableSystemExternalPlayers(),setMaxBitrateIntoField(context.querySelector(".selectVideoInNetworkQuality"),!0,"Video"),setMaxBitrateIntoField(context.querySelector(".selectVideoInternetQuality"),!1,"Video"),setMaxBitrateIntoField(context.querySelector(".selectMusicInternetQuality"),!1,"Audio"),fillChromecastQuality(context.querySelector(".selectChromecastVideoQuality"));var selectSkipForwardLength=context.querySelector(".selectSkipForwardLength");fillSkipLengths(selectSkipForwardLength),selectSkipForwardLength.value=userSettings.skipForwardLength();var selectSkipBackLength=context.querySelector(".selectSkipBackLength");fillSkipLengths(selectSkipBackLength),selectSkipBackLength.value=userSettings.skipBackLength(),showOrHideEpisodesField(context,user,apiClient),loading.hide()}function saveUser(context,user,userSettingsInstance,apiClient){return appSettings.enableSystemExternalPlayers(context.querySelector(".chkExternalVideoPlayer").checked),appSettings.maxChromecastBitrate(context.querySelector(".selectChromecastVideoQuality").value),setMaxBitrateFromField(context.querySelector(".selectVideoInNetworkQuality"),!0,"Video"),setMaxBitrateFromField(context.querySelector(".selectVideoInternetQuality"),!1,"Video"),setMaxBitrateFromField(context.querySelector(".selectMusicInternetQuality"),!1,"Audio"),user.Configuration.AudioLanguagePreference=context.querySelector("#selectAudioLanguage").value,user.Configuration.PlayDefaultAudioTrack=context.querySelector(".chkPlayDefaultAudioTrack").checked,user.Configuration.EnableNextEpisodeAutoPlay=context.querySelector(".chkEpisodeAutoPlay").checked,userSettingsInstance.enableCinemaMode(context.querySelector(".chkEnableCinemaMode").checked),userSettingsInstance.enableNextVideoInfoOverlay(context.querySelector(".chkEnableNextVideoOverlay").checked),userSettingsInstance.skipForwardLength(context.querySelector(".selectSkipForwardLength").value),userSettingsInstance.skipBackLength(context.querySelector(".selectSkipBackLength").value),apiClient.updateUserConfiguration(user.Id,user.Configuration)}function save(instance,context,userId,userSettings,apiClient,enableSaveConfirmation){loading.show(),apiClient.getUser(userId).then(function(user){saveUser(context,user,userSettings,apiClient).then(function(){loading.hide(),enableSaveConfirmation&&require(["toast"],function(toast){toast(globalize.translate("sharedcomponents#SettingsSaved"))}),events.trigger(instance,"saved")},function(){loading.hide()})})}function onSubmit(e){var self=this,apiClient=connectionManager.getApiClient(self.options.serverId),userId=self.options.userId,userSettings=self.options.userSettings;return userSettings.setUserInfo(userId,apiClient).then(function(){var enableSaveConfirmation=self.options.enableSaveConfirmation;save(self,self.options.element,userId,userSettings,apiClient,enableSaveConfirmation)}),e&&e.preventDefault(),!1}function embed(options,self){require(["text!./playbacksettings.template.html"],function(template){options.element.innerHTML=globalize.translateDocument(template,"sharedcomponents"),options.element.querySelector("form").addEventListener("submit",onSubmit.bind(self)),options.enableSaveButton&&options.element.querySelector(".btnSave").classList.remove("hide"),self.loadData(),options.autoFocus&&focusManager.autoFocus(options.element)})}function PlaybackSettings(options){this.options=options,embed(options,this)}return PlaybackSettings.prototype.loadData=function(){var self=this,context=self.options.element;loading.show();var userId=self.options.userId,apiClient=connectionManager.getApiClient(self.options.serverId),userSettings=self.options.userSettings;apiClient.getUser(userId).then(function(user){userSettings.setUserInfo(userId,apiClient).then(function(){self.dataLoaded=!0,loadForm(context,user,userSettings,apiClient)})})},PlaybackSettings.prototype.submit=function(){onSubmit.call(this)},PlaybackSettings.prototype.destroy=function(){this.options=null},PlaybackSettings}); \ No newline at end of file +define(["require", "browser", "appSettings", "apphost", "focusManager", "qualityoptions", "globalize", "loading", "connectionManager", "dom", "events", "emby-select", "emby-checkbox"], function(require, browser, appSettings, appHost, focusManager, qualityoptions, globalize, loading, connectionManager, dom, events) { + "use strict"; + + function fillSkipLengths(select) { + var options = [5, 10, 15, 20, 25, 30]; + select.innerHTML = options.map(function(option) { + return { + name: globalize.translate("sharedcomponents#ValueSeconds", option), + value: 1e3 * option + } + }).map(function(o) { + return '" + }).join("") + } + + function populateLanguages(select, languages) { + var html = ""; + html += ""; + for (var i = 0, length = languages.length; i < length; i++) { + var culture = languages[i]; + html += "" + } + select.innerHTML = html + } + + function setMaxBitrateIntoField(select, isInNetwork, mediatype) { + var options = "Audio" === mediatype ? qualityoptions.getAudioQualityOptions({ + currentMaxBitrate: appSettings.maxStreamingBitrate(isInNetwork, mediatype), + isAutomaticBitrateEnabled: appSettings.enableAutomaticBitrateDetection(isInNetwork, mediatype), + enableAuto: !0 + }) : qualityoptions.getVideoQualityOptions({ + currentMaxBitrate: appSettings.maxStreamingBitrate(isInNetwork, mediatype), + isAutomaticBitrateEnabled: appSettings.enableAutomaticBitrateDetection(isInNetwork, mediatype), + enableAuto: !0 + }); + select.innerHTML = options.map(function(i) { + return '" + }).join(""), appSettings.enableAutomaticBitrateDetection(isInNetwork, mediatype) ? select.value = "" : select.value = appSettings.maxStreamingBitrate(isInNetwork, mediatype) + } + + function fillChromecastQuality(select) { + var options = qualityoptions.getVideoQualityOptions({ + currentMaxBitrate: appSettings.maxChromecastBitrate(), + isAutomaticBitrateEnabled: !appSettings.maxChromecastBitrate(), + enableAuto: !0 + }); + select.innerHTML = options.map(function(i) { + return '" + }).join(""), select.value = appSettings.maxChromecastBitrate() || "" + } + + function setMaxBitrateFromField(select, isInNetwork, mediatype, value) { + select.value ? (appSettings.maxStreamingBitrate(isInNetwork, mediatype, select.value), appSettings.enableAutomaticBitrateDetection(isInNetwork, mediatype, !1)) : appSettings.enableAutomaticBitrateDetection(isInNetwork, mediatype, !0) + } + + function showHideQualityFields(context, user, apiClient) { + if (user.Policy.EnableVideoPlaybackTranscoding ? context.querySelector(".videoQualitySection").classList.remove("hide") : context.querySelector(".videoQualitySection").classList.add("hide"), appHost.supports("multiserver")) return context.querySelector(".fldVideoInNetworkQuality").classList.remove("hide"), context.querySelector(".fldVideoInternetQuality").classList.remove("hide"), void(user.Policy.EnableAudioPlaybackTranscoding ? context.querySelector(".musicQualitySection").classList.remove("hide") : context.querySelector(".musicQualitySection").classList.add("hide")); + apiClient.getEndpointInfo().then(function(endpointInfo) { + endpointInfo.IsInNetwork ? (context.querySelector(".fldVideoInNetworkQuality").classList.remove("hide"), context.querySelector(".fldVideoInternetQuality").classList.add("hide"), context.querySelector(".musicQualitySection").classList.add("hide")) : (context.querySelector(".fldVideoInNetworkQuality").classList.add("hide"), context.querySelector(".fldVideoInternetQuality").classList.remove("hide"), user.Policy.EnableAudioPlaybackTranscoding ? context.querySelector(".musicQualitySection").classList.remove("hide") : context.querySelector(".musicQualitySection").classList.add("hide")) + }) + } + + function showOrHideEpisodesField(context, user, apiClient) { + if (browser.tizen || browser.web0s) return void context.querySelector(".fldEpisodeAutoPlay").classList.add("hide"); + context.querySelector(".fldEpisodeAutoPlay").classList.remove("hide") + } + + function loadForm(context, user, userSettings, apiClient) { + var loggedInUserId = apiClient.getCurrentUserId(), + userId = user.Id; + showHideQualityFields(context, user, apiClient), apiClient.getCultures().then(function(allCultures) { + populateLanguages(context.querySelector("#selectAudioLanguage"), allCultures), context.querySelector("#selectAudioLanguage", context).value = user.Configuration.AudioLanguagePreference || "", context.querySelector(".chkEpisodeAutoPlay").checked = user.Configuration.EnableNextEpisodeAutoPlay || !1 + }), apiClient.getNamedConfiguration("cinemamode").then(function(cinemaConfig) { + cinemaConfig.EnableIntrosForMovies || cinemaConfig.EnableIntrosForEpisodes ? context.querySelector(".cinemaModeOptions").classList.remove("hide") : context.querySelector(".cinemaModeOptions").classList.add("hide") + }), appHost.supports("externalplayerintent") && userId === loggedInUserId ? context.querySelector(".fldExternalPlayer").classList.remove("hide") : context.querySelector(".fldExternalPlayer").classList.add("hide"), userId === loggedInUserId && (user.Policy.EnableVideoPlaybackTranscoding || user.Policy.EnableAudioPlaybackTranscoding) ? (context.querySelector(".qualitySections").classList.remove("hide"), appHost.supports("chromecast") && user.Policy.EnableVideoPlaybackTranscoding ? context.querySelector(".fldChromecastQuality").classList.remove("hide") : context.querySelector(".fldChromecastQuality").classList.add("hide")) : (context.querySelector(".qualitySections").classList.add("hide"), context.querySelector(".fldChromecastQuality").classList.add("hide")), browser.tizen || browser.web0s ? context.querySelector(".fldEnableNextVideoOverlay").classList.add("hide") : context.querySelector(".fldEnableNextVideoOverlay").classList.remove("hide"), context.querySelector(".chkPlayDefaultAudioTrack").checked = user.Configuration.PlayDefaultAudioTrack || !1, context.querySelector(".chkEnableCinemaMode").checked = userSettings.enableCinemaMode(), context.querySelector(".chkEnableNextVideoOverlay").checked = userSettings.enableNextVideoInfoOverlay(), context.querySelector(".chkExternalVideoPlayer").checked = appSettings.enableSystemExternalPlayers(), setMaxBitrateIntoField(context.querySelector(".selectVideoInNetworkQuality"), !0, "Video"), setMaxBitrateIntoField(context.querySelector(".selectVideoInternetQuality"), !1, "Video"), setMaxBitrateIntoField(context.querySelector(".selectMusicInternetQuality"), !1, "Audio"), fillChromecastQuality(context.querySelector(".selectChromecastVideoQuality")); + var selectSkipForwardLength = context.querySelector(".selectSkipForwardLength"); + fillSkipLengths(selectSkipForwardLength), selectSkipForwardLength.value = userSettings.skipForwardLength(); + var selectSkipBackLength = context.querySelector(".selectSkipBackLength"); + fillSkipLengths(selectSkipBackLength), selectSkipBackLength.value = userSettings.skipBackLength(), showOrHideEpisodesField(context, user, apiClient), loading.hide() + } + + function saveUser(context, user, userSettingsInstance, apiClient) { + return appSettings.enableSystemExternalPlayers(context.querySelector(".chkExternalVideoPlayer").checked), appSettings.maxChromecastBitrate(context.querySelector(".selectChromecastVideoQuality").value), setMaxBitrateFromField(context.querySelector(".selectVideoInNetworkQuality"), !0, "Video"), setMaxBitrateFromField(context.querySelector(".selectVideoInternetQuality"), !1, "Video"), setMaxBitrateFromField(context.querySelector(".selectMusicInternetQuality"), !1, "Audio"), user.Configuration.AudioLanguagePreference = context.querySelector("#selectAudioLanguage").value, user.Configuration.PlayDefaultAudioTrack = context.querySelector(".chkPlayDefaultAudioTrack").checked, user.Configuration.EnableNextEpisodeAutoPlay = context.querySelector(".chkEpisodeAutoPlay").checked, userSettingsInstance.enableCinemaMode(context.querySelector(".chkEnableCinemaMode").checked), userSettingsInstance.enableNextVideoInfoOverlay(context.querySelector(".chkEnableNextVideoOverlay").checked), userSettingsInstance.skipForwardLength(context.querySelector(".selectSkipForwardLength").value), userSettingsInstance.skipBackLength(context.querySelector(".selectSkipBackLength").value), apiClient.updateUserConfiguration(user.Id, user.Configuration) + } + + function save(instance, context, userId, userSettings, apiClient, enableSaveConfirmation) { + loading.show(), apiClient.getUser(userId).then(function(user) { + saveUser(context, user, userSettings, apiClient).then(function() { + loading.hide(), enableSaveConfirmation && require(["toast"], function(toast) { + toast(globalize.translate("sharedcomponents#SettingsSaved")) + }), events.trigger(instance, "saved") + }, function() { + loading.hide() + }) + }) + } + + function onSubmit(e) { + var self = this, + apiClient = connectionManager.getApiClient(self.options.serverId), + userId = self.options.userId, + userSettings = self.options.userSettings; + return userSettings.setUserInfo(userId, apiClient).then(function() { + var enableSaveConfirmation = self.options.enableSaveConfirmation; + save(self, self.options.element, userId, userSettings, apiClient, enableSaveConfirmation) + }), e && e.preventDefault(), !1 + } + + function embed(options, self) { + require(["text!./playbacksettings.template.html"], function(template) { + options.element.innerHTML = globalize.translateDocument(template, "sharedcomponents"), options.element.querySelector("form").addEventListener("submit", onSubmit.bind(self)), options.enableSaveButton && options.element.querySelector(".btnSave").classList.remove("hide"), self.loadData(), options.autoFocus && focusManager.autoFocus(options.element) + }) + } + + function PlaybackSettings(options) { + this.options = options, embed(options, this) + } + return PlaybackSettings.prototype.loadData = function() { + var self = this, + context = self.options.element; + loading.show(); + var userId = self.options.userId, + apiClient = connectionManager.getApiClient(self.options.serverId), + userSettings = self.options.userSettings; + apiClient.getUser(userId).then(function(user) { + userSettings.setUserInfo(userId, apiClient).then(function() { + self.dataLoaded = !0, loadForm(context, user, userSettings, apiClient) + }) + }) + }, PlaybackSettings.prototype.submit = function() { + onSubmit.call(this) + }, PlaybackSettings.prototype.destroy = function() { + this.options = null + }, PlaybackSettings +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/playerstats/playerstats.js b/dashboard-ui/bower_components/emby-webcomponents/playerstats/playerstats.js index d9a2b5440e..a089690aa0 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/playerstats/playerstats.js +++ b/dashboard-ui/bower_components/emby-webcomponents/playerstats/playerstats.js @@ -1 +1,193 @@ -define(["events","globalize","playbackManager","connectionManager","playMethodHelper","layoutManager","serverNotifications","paper-icon-button-light","css!./playerstats"],function(events,globalize,playbackManager,connectionManager,playMethodHelper,layoutManager,serverNotifications){"use strict";function init(instance){var parent=document.createElement("div");parent.classList.add("playerStats"),layoutManager.tv&&parent.classList.add("playerStats-tv"),parent.classList.add("hide");var button;button=layoutManager.tv?"":'';var contentClass=layoutManager.tv?"playerStats-content playerStats-content-tv":"playerStats-content";parent.innerHTML='
'+button+'
',button=parent.querySelector(".playerStats-closeButton"),button&&button.addEventListener("click",onCloseButtonClick.bind(instance)),document.body.appendChild(parent),instance.element=parent}function onCloseButtonClick(){this.enabled(!1)}function renderStats(elem,categories){elem.querySelector(".playerStats-stats").innerHTML=categories.map(function(category){var categoryHtml="",stats=category.stats;stats.length&&category.name&&(categoryHtml+='
',categoryHtml+='
',categoryHtml+=category.name,categoryHtml+="
",categoryHtml+='
',categoryHtml+=category.subText||"",categoryHtml+="
",categoryHtml+="
");for(var i=0,length=stats.length;i';var stat=stats[i];categoryHtml+='
',categoryHtml+=stat.label,categoryHtml+="
",categoryHtml+='
',categoryHtml+=stat.value,categoryHtml+="
",categoryHtml+="
"}return categoryHtml}).join("")}function getSession(instance,player){if((new Date).getTime()-(instance.lastSessionTime||0)<1e4)return Promise.resolve(instance.lastSession);var apiClient=connectionManager.getApiClient(playbackManager.currentItem(player).ServerId);return apiClient.getSessions({deviceId:apiClient.deviceId()}).then(function(sessions){return instance.lastSession=sessions[0]||{},instance.lastSessionTime=(new Date).getTime(),Promise.resolve(instance.lastSession)},function(){return Promise.resolve({})})}function translateReason(reason){return globalize.translate("sharedcomponents#"+reason)}function getTranscodingStats(session,player,displayPlayMethod){var videoCodec,audioCodec,totalBitrate,sessionStats=[];return session.TranscodingInfo&&(videoCodec=session.TranscodingInfo.VideoCodec,audioCodec=session.TranscodingInfo.AudioCodec,totalBitrate=session.TranscodingInfo.Bitrate,session.TranscodingInfo.AudioChannels),videoCodec&&sessionStats.push({label:"Video codec:",value:session.TranscodingInfo.IsVideoDirect?videoCodec.toUpperCase()+" (direct)":videoCodec.toUpperCase()}),audioCodec&&sessionStats.push({label:"Audio codec:",value:session.TranscodingInfo.IsAudioDirect?audioCodec.toUpperCase()+" (direct)":audioCodec.toUpperCase()}),"Transcode"===displayPlayMethod&&(totalBitrate&&sessionStats.push({label:"Bitrate:",value:getDisplayBitrate(totalBitrate)}),session.TranscodingInfo.CompletionPercentage&&sessionStats.push({label:"Transcoding progress:",value:session.TranscodingInfo.CompletionPercentage.toFixed(1)+"%"}),session.TranscodingInfo.Framerate&&sessionStats.push({label:"Transcoding framerate:",value:session.TranscodingInfo.Framerate+" fps"}),session.TranscodingInfo.TranscodeReasons&&session.TranscodingInfo.TranscodeReasons.length&&sessionStats.push({label:"Reason for transcoding:",value:session.TranscodingInfo.TranscodeReasons.map(translateReason).join("
")})),sessionStats}function getDisplayBitrate(bitrate){return bitrate>1e6?(bitrate/1e6).toFixed(1)+" Mbps":Math.floor(bitrate/1e3)+" kbps"}function getMediaSourceStats(session,player,displayPlayMethod){var sessionStats=[],mediaSource=playbackManager.currentMediaSource(player)||{},totalBitrate=mediaSource.Bitrate;mediaSource.Container&&sessionStats.push({label:"Container:",value:mediaSource.Container}),totalBitrate&&sessionStats.push({label:"Bitrate:",value:getDisplayBitrate(totalBitrate)});var mediaStreams=mediaSource.MediaStreams||[],videoStream=mediaStreams.filter(function(s){return"Video"===s.Type})[0]||{},videoCodec=videoStream.Codec,audioStreamIndex=playbackManager.getAudioStreamIndex(player),audioStream=playbackManager.audioTracks(player).filter(function(s){return"Audio"===s.Type&&s.Index===audioStreamIndex})[0]||{},audioCodec=audioStream.Codec,audioChannels=audioStream.Channels,videoInfos=[];videoCodec&&videoInfos.push(videoCodec.toUpperCase()),videoStream.Profile&&videoInfos.push(videoStream.Profile),videoInfos.length&&sessionStats.push({label:"Video codec:",value:videoInfos.join(" ")}),videoStream.BitRate&&sessionStats.push({label:"Video bitrate:",value:getDisplayBitrate(videoStream.BitRate)});var audioInfos=[];return audioCodec&&audioInfos.push(audioCodec.toUpperCase()),audioStream.Profile&&audioInfos.push(audioStream.Profile),audioInfos.length&&sessionStats.push({label:"Audio codec:",value:audioInfos.join(" ")}),audioStream.BitRate&&sessionStats.push({label:"Audio bitrate:",value:getDisplayBitrate(audioStream.BitRate)}),audioChannels&&sessionStats.push({label:"Audio channels:",value:audioChannels}),audioStream.SampleRate&&sessionStats.push({label:"Audio sample rate:",value:audioStream.SampleRate+" Hz"}),audioStream.BitDepth&&sessionStats.push({label:"Audio bit depth:",value:audioStream.BitDepth}),sessionStats}function getStats(instance,player){var statsPromise=player.getStats?player.getStats():Promise.resolve({}),sessionPromise=getSession(instance,player);return Promise.all([statsPromise,sessionPromise]).then(function(responses){var playerStatsResult=responses[0],playerStats=playerStatsResult.categories||[],session=responses[1],displayPlayMethod=playMethodHelper.getDisplayPlayMethod(session),baseCategory={stats:[],name:"Playback Info"};baseCategory.stats.unshift({label:"Play method:",value:displayPlayMethod}),baseCategory.stats.unshift({label:"Player:",value:player.name});var categories=[];categories.push(baseCategory);for(var i=0,length=playerStats.length;iclose'; + var contentClass = layoutManager.tv ? "playerStats-content playerStats-content-tv" : "playerStats-content"; + parent.innerHTML = '
' + button + '
', button = parent.querySelector(".playerStats-closeButton"), button && button.addEventListener("click", onCloseButtonClick.bind(instance)), document.body.appendChild(parent), instance.element = parent + } + + function onCloseButtonClick() { + this.enabled(!1) + } + + function renderStats(elem, categories) { + elem.querySelector(".playerStats-stats").innerHTML = categories.map(function(category) { + var categoryHtml = "", + stats = category.stats; + stats.length && category.name && (categoryHtml += '
', categoryHtml += '
', categoryHtml += category.name, categoryHtml += "
", categoryHtml += '
', categoryHtml += category.subText || "", categoryHtml += "
", categoryHtml += "
"); + for (var i = 0, length = stats.length; i < length; i++) { + categoryHtml += '
'; + var stat = stats[i]; + categoryHtml += '
', categoryHtml += stat.label, categoryHtml += "
", categoryHtml += '
', categoryHtml += stat.value, categoryHtml += "
", categoryHtml += "
" + } + return categoryHtml + }).join("") + } + + function getSession(instance, player) { + if ((new Date).getTime() - (instance.lastSessionTime || 0) < 1e4) return Promise.resolve(instance.lastSession); + var apiClient = connectionManager.getApiClient(playbackManager.currentItem(player).ServerId); + return apiClient.getSessions({ + deviceId: apiClient.deviceId() + }).then(function(sessions) { + return instance.lastSession = sessions[0] || {}, instance.lastSessionTime = (new Date).getTime(), Promise.resolve(instance.lastSession) + }, function() { + return Promise.resolve({}) + }) + } + + function translateReason(reason) { + return globalize.translate("sharedcomponents#" + reason) + } + + function getTranscodingStats(session, player, displayPlayMethod) { + var videoCodec, audioCodec, totalBitrate, sessionStats = []; + return session.TranscodingInfo && (videoCodec = session.TranscodingInfo.VideoCodec, audioCodec = session.TranscodingInfo.AudioCodec, totalBitrate = session.TranscodingInfo.Bitrate, session.TranscodingInfo.AudioChannels), videoCodec && sessionStats.push({ + label: "Video codec:", + value: session.TranscodingInfo.IsVideoDirect ? videoCodec.toUpperCase() + " (direct)" : videoCodec.toUpperCase() + }), audioCodec && sessionStats.push({ + label: "Audio codec:", + value: session.TranscodingInfo.IsAudioDirect ? audioCodec.toUpperCase() + " (direct)" : audioCodec.toUpperCase() + }), "Transcode" === displayPlayMethod && (totalBitrate && sessionStats.push({ + label: "Bitrate:", + value: getDisplayBitrate(totalBitrate) + }), session.TranscodingInfo.CompletionPercentage && sessionStats.push({ + label: "Transcoding progress:", + value: session.TranscodingInfo.CompletionPercentage.toFixed(1) + "%" + }), session.TranscodingInfo.Framerate && sessionStats.push({ + label: "Transcoding framerate:", + value: session.TranscodingInfo.Framerate + " fps" + }), session.TranscodingInfo.TranscodeReasons && session.TranscodingInfo.TranscodeReasons.length && sessionStats.push({ + label: "Reason for transcoding:", + value: session.TranscodingInfo.TranscodeReasons.map(translateReason).join("
") + })), sessionStats + } + + function getDisplayBitrate(bitrate) { + return bitrate > 1e6 ? (bitrate / 1e6).toFixed(1) + " Mbps" : Math.floor(bitrate / 1e3) + " kbps" + } + + function getMediaSourceStats(session, player, displayPlayMethod) { + var sessionStats = [], + mediaSource = playbackManager.currentMediaSource(player) || {}, + totalBitrate = mediaSource.Bitrate; + mediaSource.Container && sessionStats.push({ + label: "Container:", + value: mediaSource.Container + }), totalBitrate && sessionStats.push({ + label: "Bitrate:", + value: getDisplayBitrate(totalBitrate) + }); + var mediaStreams = mediaSource.MediaStreams || [], + videoStream = mediaStreams.filter(function(s) { + return "Video" === s.Type + })[0] || {}, + videoCodec = videoStream.Codec, + audioStreamIndex = playbackManager.getAudioStreamIndex(player), + audioStream = playbackManager.audioTracks(player).filter(function(s) { + return "Audio" === s.Type && s.Index === audioStreamIndex + })[0] || {}, + audioCodec = audioStream.Codec, + audioChannels = audioStream.Channels, + videoInfos = []; + videoCodec && videoInfos.push(videoCodec.toUpperCase()), videoStream.Profile && videoInfos.push(videoStream.Profile), videoInfos.length && sessionStats.push({ + label: "Video codec:", + value: videoInfos.join(" ") + }), videoStream.BitRate && sessionStats.push({ + label: "Video bitrate:", + value: getDisplayBitrate(videoStream.BitRate) + }); + var audioInfos = []; + return audioCodec && audioInfos.push(audioCodec.toUpperCase()), audioStream.Profile && audioInfos.push(audioStream.Profile), audioInfos.length && sessionStats.push({ + label: "Audio codec:", + value: audioInfos.join(" ") + }), audioStream.BitRate && sessionStats.push({ + label: "Audio bitrate:", + value: getDisplayBitrate(audioStream.BitRate) + }), audioChannels && sessionStats.push({ + label: "Audio channels:", + value: audioChannels + }), audioStream.SampleRate && sessionStats.push({ + label: "Audio sample rate:", + value: audioStream.SampleRate + " Hz" + }), audioStream.BitDepth && sessionStats.push({ + label: "Audio bit depth:", + value: audioStream.BitDepth + }), sessionStats + } + + function getStats(instance, player) { + var statsPromise = player.getStats ? player.getStats() : Promise.resolve({}), + sessionPromise = getSession(instance, player); + return Promise.all([statsPromise, sessionPromise]).then(function(responses) { + var playerStatsResult = responses[0], + playerStats = playerStatsResult.categories || [], + session = responses[1], + displayPlayMethod = playMethodHelper.getDisplayPlayMethod(session), + baseCategory = { + stats: [], + name: "Playback Info" + }; + baseCategory.stats.unshift({ + label: "Play method:", + value: displayPlayMethod + }), baseCategory.stats.unshift({ + label: "Player:", + value: player.name + }); + var categories = []; + categories.push(baseCategory); + for (var i = 0, length = playerStats.length; i < length; i++) { + var category = playerStats[i]; + "audio" === category.type ? category.name = "Audio Info" : "video" === category.type && (category.name = "Video Info"), categories.push(category) + } + return session.TranscodingInfo && categories.push({ + stats: getTranscodingStats(session, player, displayPlayMethod), + name: "Transcode" === displayPlayMethod ? "Transcoding Info" : "Direct Stream Info" + }), categories.push({ + stats: getMediaSourceStats(session, player), + name: "Original Media Info" + }), Promise.resolve(categories) + }) + } + + function renderPlayerStats(instance, player) { + var now = (new Date).getTime(); + now - (instance.lastRender || 0) < 700 || (instance.lastRender = now, getStats(instance, player).then(function(stats) { + var elem = instance.element; + elem && renderStats(elem, stats) + })) + } + + function bindEvents(instance, player) { + var localOnTimeUpdate = function() { + renderPlayerStats(instance, player) + }; + instance.onTimeUpdate = localOnTimeUpdate, events.on(player, "timeupdate", localOnTimeUpdate) + } + + function unbindEvents(instance, player) { + var localOnTimeUpdate = instance.onTimeUpdate; + localOnTimeUpdate && events.off(player, "timeupdate", localOnTimeUpdate) + } + + function PlayerStats(options) { + this.options = options, init(this), this.enabled(!0) + } + return PlayerStats.prototype.enabled = function(enabled) { + if (null == enabled) return this._enabled; + var options = this.options; + options && (this._enabled = enabled, enabled ? (this.element.classList.remove("hide"), bindEvents(this, options.player)) : (this.element.classList.add("hide"), unbindEvents(this, options.player))) + }, PlayerStats.prototype.toggle = function() { + this.enabled(!this.enabled()) + }, PlayerStats.prototype.destroy = function() { + var options = this.options; + options && (this.options = null, unbindEvents(this, options.player)); + var elem = this.element; + elem && (elem.parentNode.removeChild(elem), this.element = null) + }, PlayerStats +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/playlisteditor/playlisteditor.js b/dashboard-ui/bower_components/emby-webcomponents/playlisteditor/playlisteditor.js index b58c5fe569..22a5c180d8 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/playlisteditor/playlisteditor.js +++ b/dashboard-ui/bower_components/emby-webcomponents/playlisteditor/playlisteditor.js @@ -1 +1,127 @@ -define(["shell","dialogHelper","loading","layoutManager","playbackManager","connectionManager","userSettings","appRouter","globalize","emby-input","paper-icon-button-light","emby-select","material-icons","css!./../formdialog","emby-button"],function(shell,dialogHelper,loading,layoutManager,playbackManager,connectionManager,userSettings,appRouter,globalize){"use strict";function parentWithClass(elem,className){for(;!elem.classList||!elem.classList.contains(className);)if(!(elem=elem.parentNode))return null;return elem}function onSubmit(e){var panel=parentWithClass(this,"dialog"),playlistId=panel.querySelector("#selectPlaylistToAddTo").value,apiClient=connectionManager.getApiClient(currentServerId);return playlistId?(userSettings.set("playlisteditor-lastplaylistid",playlistId),addToPlaylist(apiClient,panel,playlistId)):createPlaylist(apiClient,panel),e.preventDefault(),!1}function createPlaylist(apiClient,dlg){loading.show();var url=apiClient.getUrl("Playlists",{Name:dlg.querySelector("#txtNewPlaylistName").value,Ids:dlg.querySelector(".fldSelectedItemIds").value||"",userId:apiClient.getCurrentUserId()});apiClient.ajax({type:"POST",url:url,dataType:"json"}).then(function(result){loading.hide();var id=result.Id;dlg.submitted=!0,dialogHelper.close(dlg),redirectToPlaylist(apiClient,id)})}function redirectToPlaylist(apiClient,id){appRouter.showItem(id,apiClient.serverId())}function addToPlaylist(apiClient,dlg,id){var itemIds=dlg.querySelector(".fldSelectedItemIds").value||"";if("queue"===id)return playbackManager.queue({serverId:apiClient.serverId(),ids:itemIds.split(",")}),dlg.submitted=!0,void dialogHelper.close(dlg);loading.show();var url=apiClient.getUrl("Playlists/"+id+"/Items",{Ids:itemIds,userId:apiClient.getCurrentUserId()});apiClient.ajax({type:"POST",url:url}).then(function(){loading.hide(),dlg.submitted=!0,dialogHelper.close(dlg)})}function triggerChange(select){select.dispatchEvent(new CustomEvent("change",{}))}function populatePlaylists(editorOptions,panel){var select=panel.querySelector("#selectPlaylistToAddTo");loading.hide(),panel.querySelector(".newPlaylistInfo").classList.add("hide");var options={Recursive:!0,IncludeItemTypes:"Playlist",SortBy:"SortName",EnableTotalRecordCount:!1},apiClient=connectionManager.getApiClient(currentServerId);apiClient.getItems(apiClient.getCurrentUserId(),options).then(function(result){var html="";!1!==editorOptions.enableAddToPlayQueue&&playbackManager.isPlaying()&&(html+='"),html+='",html+=result.Items.map(function(i){return'"}),select.innerHTML=html;var defaultValue=editorOptions.defaultValue;defaultValue||(defaultValue=userSettings.get("playlisteditor-lastplaylistid")||""),select.value="new"===defaultValue?"":defaultValue,select.value||(select.value=""),triggerChange(select),loading.hide()})}function getEditorHtml(items){var html="";html+='
',html+='
',html+='
',html+='
';var autoFocus=items.length?" autofocus":"";return html+='",html+="
",html+='
',html+='
',autoFocus=items.length?"":" autofocus",html+='",html+="
",html+="
",html+='
',html+='",html+="
",html+='',html+="
",html+="
",html+="
"}function initEditor(content,options,items){if(content.querySelector("#selectPlaylistToAddTo").addEventListener("change",function(){this.value?(content.querySelector(".newPlaylistInfo").classList.add("hide"),content.querySelector("#txtNewPlaylistName").removeAttribute("required")):(content.querySelector(".newPlaylistInfo").classList.remove("hide"),content.querySelector("#txtNewPlaylistName").setAttribute("required","required"))}),content.querySelector("form").addEventListener("submit",onSubmit),content.querySelector(".fldSelectedItemIds",content).value=items.join(","),items.length)content.querySelector(".fldSelectPlaylist").classList.remove("hide"),populatePlaylists(options,content);else{content.querySelector(".fldSelectPlaylist").classList.add("hide");var selectPlaylistToAddTo=content.querySelector("#selectPlaylistToAddTo");selectPlaylistToAddTo.innerHTML="",selectPlaylistToAddTo.value="",triggerChange(selectPlaylistToAddTo)}}function centerFocus(elem,horiz,on){require(["scrollHelper"],function(scrollHelper){var fn=on?"on":"off";scrollHelper.centerFocus[fn](elem,horiz)})}function PlaylistEditor(){}var currentServerId;return PlaylistEditor.prototype.show=function(options){var items=options.items||{};currentServerId=options.serverId;var dialogOptions={removeOnClose:!0,scrollY:!1};layoutManager.tv?dialogOptions.size="fullscreen":dialogOptions.size="small";var dlg=dialogHelper.createDialog(dialogOptions);dlg.classList.add("formDialog");var html="",title=globalize.translate("sharedcomponents#HeaderAddToPlaylist");return html+='
',html+='',html+='

',html+=title,html+="

",html+="
",html+=getEditorHtml(items),dlg.innerHTML=html,initEditor(dlg,options,items),dlg.querySelector(".btnCancel").addEventListener("click",function(){dialogHelper.close(dlg)}),layoutManager.tv&¢erFocus(dlg.querySelector(".formDialogContent"),!1,!0),dialogHelper.open(dlg).then(function(){return layoutManager.tv&¢erFocus(dlg.querySelector(".formDialogContent"),!1,!1),dlg.submitted?Promise.resolve():Promise.reject()})},PlaylistEditor}); \ No newline at end of file +define(["shell", "dialogHelper", "loading", "layoutManager", "playbackManager", "connectionManager", "userSettings", "appRouter", "globalize", "emby-input", "paper-icon-button-light", "emby-select", "material-icons", "css!./../formdialog", "emby-button"], function(shell, dialogHelper, loading, layoutManager, playbackManager, connectionManager, userSettings, appRouter, globalize) { + "use strict"; + + function parentWithClass(elem, className) { + for (; !elem.classList || !elem.classList.contains(className);) + if (!(elem = elem.parentNode)) return null; + return elem + } + + function onSubmit(e) { + var panel = parentWithClass(this, "dialog"), + playlistId = panel.querySelector("#selectPlaylistToAddTo").value, + apiClient = connectionManager.getApiClient(currentServerId); + return playlistId ? (userSettings.set("playlisteditor-lastplaylistid", playlistId), addToPlaylist(apiClient, panel, playlistId)) : createPlaylist(apiClient, panel), e.preventDefault(), !1 + } + + function createPlaylist(apiClient, dlg) { + loading.show(); + var url = apiClient.getUrl("Playlists", { + Name: dlg.querySelector("#txtNewPlaylistName").value, + Ids: dlg.querySelector(".fldSelectedItemIds").value || "", + userId: apiClient.getCurrentUserId() + }); + apiClient.ajax({ + type: "POST", + url: url, + dataType: "json" + }).then(function(result) { + loading.hide(); + var id = result.Id; + dlg.submitted = !0, dialogHelper.close(dlg), redirectToPlaylist(apiClient, id) + }) + } + + function redirectToPlaylist(apiClient, id) { + appRouter.showItem(id, apiClient.serverId()) + } + + function addToPlaylist(apiClient, dlg, id) { + var itemIds = dlg.querySelector(".fldSelectedItemIds").value || ""; + if ("queue" === id) return playbackManager.queue({ + serverId: apiClient.serverId(), + ids: itemIds.split(",") + }), dlg.submitted = !0, void dialogHelper.close(dlg); + loading.show(); + var url = apiClient.getUrl("Playlists/" + id + "/Items", { + Ids: itemIds, + userId: apiClient.getCurrentUserId() + }); + apiClient.ajax({ + type: "POST", + url: url + }).then(function() { + loading.hide(), dlg.submitted = !0, dialogHelper.close(dlg) + }) + } + + function triggerChange(select) { + select.dispatchEvent(new CustomEvent("change", {})) + } + + function populatePlaylists(editorOptions, panel) { + var select = panel.querySelector("#selectPlaylistToAddTo"); + loading.hide(), panel.querySelector(".newPlaylistInfo").classList.add("hide"); + var options = { + Recursive: !0, + IncludeItemTypes: "Playlist", + SortBy: "SortName", + EnableTotalRecordCount: !1 + }, + apiClient = connectionManager.getApiClient(currentServerId); + apiClient.getItems(apiClient.getCurrentUserId(), options).then(function(result) { + var html = ""; + !1 !== editorOptions.enableAddToPlayQueue && playbackManager.isPlaying() && (html += '"), html += '", html += result.Items.map(function(i) { + return '" + }), select.innerHTML = html; + var defaultValue = editorOptions.defaultValue; + defaultValue || (defaultValue = userSettings.get("playlisteditor-lastplaylistid") || ""), select.value = "new" === defaultValue ? "" : defaultValue, select.value || (select.value = ""), triggerChange(select), loading.hide() + }) + } + + function getEditorHtml(items) { + var html = ""; + html += '
', html += '
', html += '
', html += '
'; + var autoFocus = items.length ? " autofocus" : ""; + return html += '", html += "
", html += '
', html += '
', autoFocus = items.length ? "" : " autofocus", html += '", html += "
", html += "
", html += '
', html += '", html += "
", html += '', html += "
", html += "
", html += "
" + } + + function initEditor(content, options, items) { + if (content.querySelector("#selectPlaylistToAddTo").addEventListener("change", function() { + this.value ? (content.querySelector(".newPlaylistInfo").classList.add("hide"), content.querySelector("#txtNewPlaylistName").removeAttribute("required")) : (content.querySelector(".newPlaylistInfo").classList.remove("hide"), content.querySelector("#txtNewPlaylistName").setAttribute("required", "required")) + }), content.querySelector("form").addEventListener("submit", onSubmit), content.querySelector(".fldSelectedItemIds", content).value = items.join(","), items.length) content.querySelector(".fldSelectPlaylist").classList.remove("hide"), populatePlaylists(options, content); + else { + content.querySelector(".fldSelectPlaylist").classList.add("hide"); + var selectPlaylistToAddTo = content.querySelector("#selectPlaylistToAddTo"); + selectPlaylistToAddTo.innerHTML = "", selectPlaylistToAddTo.value = "", triggerChange(selectPlaylistToAddTo) + } + } + + function centerFocus(elem, horiz, on) { + require(["scrollHelper"], function(scrollHelper) { + var fn = on ? "on" : "off"; + scrollHelper.centerFocus[fn](elem, horiz) + }) + } + + function PlaylistEditor() {} + var currentServerId; + return PlaylistEditor.prototype.show = function(options) { + var items = options.items || {}; + currentServerId = options.serverId; + var dialogOptions = { + removeOnClose: !0, + scrollY: !1 + }; + layoutManager.tv ? dialogOptions.size = "fullscreen" : dialogOptions.size = "small"; + var dlg = dialogHelper.createDialog(dialogOptions); + dlg.classList.add("formDialog"); + var html = "", + title = globalize.translate("sharedcomponents#HeaderAddToPlaylist"); + return html += '
', html += '', html += '

', html += title, html += "

", html += "
", html += getEditorHtml(items), dlg.innerHTML = html, initEditor(dlg, options, items), dlg.querySelector(".btnCancel").addEventListener("click", function() { + dialogHelper.close(dlg) + }), layoutManager.tv && centerFocus(dlg.querySelector(".formDialogContent"), !1, !0), dialogHelper.open(dlg).then(function() { + return layoutManager.tv && centerFocus(dlg.querySelector(".formDialogContent"), !1, !1), dlg.submitted ? Promise.resolve() : Promise.reject() + }) + }, PlaylistEditor +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/playmenu.js b/dashboard-ui/bower_components/emby-webcomponents/playmenu.js index dc159c6c04..acdf9e8f7e 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/playmenu.js +++ b/dashboard-ui/bower_components/emby-webcomponents/playmenu.js @@ -1 +1,55 @@ -define(["actionsheet","datetime","playbackManager","globalize","appSettings"],function(actionsheet,datetime,playbackManager,globalize,appSettings){"use strict";function show(options){var item=options.item,itemType=item.Type,isFolder=item.IsFolder,itemId=item.Id,channelId=item.ChannelId,serverId=item.ServerId,resumePositionTicks=item.UserData?item.UserData.PlaybackPositionTicks:null,playableItemId="Program"===itemType?channelId:itemId;if(!resumePositionTicks||isFolder)return void playbackManager.play({ids:[playableItemId],serverId:serverId});var menuItems=[];menuItems.push({name:globalize.translate("sharedcomponents#ResumeAt",datetime.getDisplayRunningTime(resumePositionTicks)),id:"resume"}),menuItems.push({name:globalize.translate("sharedcomponents#PlayFromBeginning"),id:"play"}),actionsheet.show({items:menuItems,positionTo:options.positionTo}).then(function(id){switch(id){case"play":playbackManager.play({ids:[playableItemId],serverId:serverId});break;case"resume":playbackManager.play({ids:[playableItemId],startPositionTicks:resumePositionTicks,serverId:serverId});break;case"queue":playbackManager.queue({items:[item]});break;case"shuffle":playbackManager.shuffle(item)}})}return{show:show}}); \ No newline at end of file +define(["actionsheet", "datetime", "playbackManager", "globalize", "appSettings"], function(actionsheet, datetime, playbackManager, globalize, appSettings) { + "use strict"; + + function show(options) { + var item = options.item, + itemType = item.Type, + isFolder = item.IsFolder, + itemId = item.Id, + channelId = item.ChannelId, + serverId = item.ServerId, + resumePositionTicks = item.UserData ? item.UserData.PlaybackPositionTicks : null, + playableItemId = "Program" === itemType ? channelId : itemId; + if (!resumePositionTicks || isFolder) return void playbackManager.play({ + ids: [playableItemId], + serverId: serverId + }); + var menuItems = []; + menuItems.push({ + name: globalize.translate("sharedcomponents#ResumeAt", datetime.getDisplayRunningTime(resumePositionTicks)), + id: "resume" + }), menuItems.push({ + name: globalize.translate("sharedcomponents#PlayFromBeginning"), + id: "play" + }), actionsheet.show({ + items: menuItems, + positionTo: options.positionTo + }).then(function(id) { + switch (id) { + case "play": + playbackManager.play({ + ids: [playableItemId], + serverId: serverId + }); + break; + case "resume": + playbackManager.play({ + ids: [playableItemId], + startPositionTicks: resumePositionTicks, + serverId: serverId + }); + break; + case "queue": + playbackManager.queue({ + items: [item] + }); + break; + case "shuffle": + playbackManager.shuffle(item) + } + }) + } + return { + show: show + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/pluginmanager.js b/dashboard-ui/bower_components/emby-webcomponents/pluginmanager.js index a4674d541e..57da495a42 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/pluginmanager.js +++ b/dashboard-ui/bower_components/emby-webcomponents/pluginmanager.js @@ -1 +1,63 @@ -define(["events"],function(events){"use strict";function loadStrings(plugin,globalize){var strings=plugin.getTranslations?plugin.getTranslations():[];return globalize.loadStrings({name:plugin.id||plugin.packageName,strings:strings})}function definePluginRoute(pluginManager,route,plugin){route.contentPath=pluginManager.mapPath(plugin,route.path),route.path=pluginManager.mapRoute(plugin,route),Emby.App.defineRoute(route,plugin.id)}function PluginManager(){this.pluginsList=[]}var cacheParam=(new Date).getTime();return PluginManager.prototype.loadPlugin=function(url){console.log("Loading plugin: "+url);var instance=this;return new Promise(function(resolve,reject){require([url,"globalize","appRouter"],function(pluginFactory,globalize,appRouter){var plugin=new pluginFactory;if(instance.pluginsList.filter(function(p){return p.id===plugin.id})[0])return void resolve(url);plugin.installUrl=url;var urlLower=url.toLowerCase();-1===urlLower.indexOf("http:")&&-1===urlLower.indexOf("https:")&&-1===urlLower.indexOf("file:")&&0!==url.indexOf(appRouter.baseUrl())&&(url=appRouter.baseUrl()+"/"+url);var separatorIndex=Math.max(url.lastIndexOf("/"),url.lastIndexOf("\\"));plugin.baseUrl=url.substring(0,separatorIndex);var paths={};paths[plugin.id]=plugin.baseUrl,requirejs.config({waitSeconds:0,paths:paths}),instance.register(plugin),plugin.getRoutes&&plugin.getRoutes().forEach(function(route){definePluginRoute(instance,route,plugin)}),"skin"===plugin.type?resolve(plugin):loadStrings(plugin,globalize).then(function(){resolve(plugin)},reject)})})},PluginManager.prototype.register=function(obj){this.pluginsList.push(obj),events.trigger(this,"registered",[obj])},PluginManager.prototype.ofType=function(type){return this.pluginsList.filter(function(o){return o.type===type})},PluginManager.prototype.plugins=function(){return this.pluginsList},PluginManager.prototype.mapRoute=function(plugin,route){return"string"==typeof plugin&&(plugin=this.pluginsList.filter(function(p){return(p.id||p.packageName)===plugin})[0]),route=route.path||route,0===route.toLowerCase().indexOf("http")?route:"/plugins/"+plugin.id+"/"+route},PluginManager.prototype.mapPath=function(plugin,path,addCacheParam){"string"==typeof plugin&&(plugin=this.pluginsList.filter(function(p){return(p.id||p.packageName)===plugin})[0]);var url=plugin.baseUrl+"/"+path;return addCacheParam&&(url+=-1===url.indexOf("?")?"?":"&",url+="v="+cacheParam),url},new PluginManager}); \ No newline at end of file +define(["events"], function(events) { + "use strict"; + + function loadStrings(plugin, globalize) { + var strings = plugin.getTranslations ? plugin.getTranslations() : []; + return globalize.loadStrings({ + name: plugin.id || plugin.packageName, + strings: strings + }) + } + + function definePluginRoute(pluginManager, route, plugin) { + route.contentPath = pluginManager.mapPath(plugin, route.path), route.path = pluginManager.mapRoute(plugin, route), Emby.App.defineRoute(route, plugin.id) + } + + function PluginManager() { + this.pluginsList = [] + } + var cacheParam = (new Date).getTime(); + return PluginManager.prototype.loadPlugin = function(url) { + console.log("Loading plugin: " + url); + var instance = this; + return new Promise(function(resolve, reject) { + require([url, "globalize", "appRouter"], function(pluginFactory, globalize, appRouter) { + var plugin = new pluginFactory; + if (instance.pluginsList.filter(function(p) { + return p.id === plugin.id + })[0]) return void resolve(url); + plugin.installUrl = url; + var urlLower = url.toLowerCase(); - 1 === urlLower.indexOf("http:") && -1 === urlLower.indexOf("https:") && -1 === urlLower.indexOf("file:") && 0 !== url.indexOf(appRouter.baseUrl()) && (url = appRouter.baseUrl() + "/" + url); + var separatorIndex = Math.max(url.lastIndexOf("/"), url.lastIndexOf("\\")); + plugin.baseUrl = url.substring(0, separatorIndex); + var paths = {}; + paths[plugin.id] = plugin.baseUrl, requirejs.config({ + waitSeconds: 0, + paths: paths + }), instance.register(plugin), plugin.getRoutes && plugin.getRoutes().forEach(function(route) { + definePluginRoute(instance, route, plugin) + }), "skin" === plugin.type ? resolve(plugin) : loadStrings(plugin, globalize).then(function() { + resolve(plugin) + }, reject) + }) + }) + }, PluginManager.prototype.register = function(obj) { + this.pluginsList.push(obj), events.trigger(this, "registered", [obj]) + }, PluginManager.prototype.ofType = function(type) { + return this.pluginsList.filter(function(o) { + return o.type === type + }) + }, PluginManager.prototype.plugins = function() { + return this.pluginsList + }, PluginManager.prototype.mapRoute = function(plugin, route) { + return "string" == typeof plugin && (plugin = this.pluginsList.filter(function(p) { + return (p.id || p.packageName) === plugin + })[0]), route = route.path || route, 0 === route.toLowerCase().indexOf("http") ? route : "/plugins/" + plugin.id + "/" + route + }, PluginManager.prototype.mapPath = function(plugin, path, addCacheParam) { + "string" == typeof plugin && (plugin = this.pluginsList.filter(function(p) { + return (p.id || p.packageName) === plugin + })[0]); + var url = plugin.baseUrl + "/" + path; + return addCacheParam && (url += -1 === url.indexOf("?") ? "?" : "&", url += "v=" + cacheParam), url + }, new PluginManager +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/polyfills/array.js b/dashboard-ui/bower_components/emby-webcomponents/polyfills/array.js index 93cd413780..e32a7d9562 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/polyfills/array.js +++ b/dashboard-ui/bower_components/emby-webcomponents/polyfills/array.js @@ -1 +1,12 @@ -Array.prototype.filter||(Array.prototype.filter=function(fun){"use strict";if(null==this)throw new TypeError;var t=Object(this),len=t.length>>>0;if("function"!=typeof fun)throw new TypeError;for(var res=[],thisp=arguments[1],i=0;i>> 0; + if ("function" != typeof fun) throw new TypeError; + for (var res = [], thisp = arguments[1], i = 0; i < len; i++) + if (i in t) { + var val = t[i]; + fun.call(thisp, val, i, t) && res.push(val) + } return res +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/polyfills/bind.js b/dashboard-ui/bower_components/emby-webcomponents/polyfills/bind.js index 12c23d8b1f..27b00f6eae 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/polyfills/bind.js +++ b/dashboard-ui/bower_components/emby-webcomponents/polyfills/bind.js @@ -1 +1,10 @@ -Function.prototype.bind||(Function.prototype.bind=function(oThis){if("function"!=typeof this)throw new TypeError("Function.prototype.bind - what is trying to be bound is not callable");var aArgs=Array.prototype.slice.call(arguments,1),fToBind=this,fNOP=function(){},fBound=function(){return fToBind.apply(this instanceof fNOP?this:oThis,aArgs.concat(Array.prototype.slice.call(arguments)))};return this.prototype&&(fNOP.prototype=this.prototype),fBound.prototype=new fNOP,fBound}); \ No newline at end of file +Function.prototype.bind || (Function.prototype.bind = function(oThis) { + if ("function" != typeof this) throw new TypeError("Function.prototype.bind - what is trying to be bound is not callable"); + var aArgs = Array.prototype.slice.call(arguments, 1), + fToBind = this, + fNOP = function() {}, + fBound = function() { + return fToBind.apply(this instanceof fNOP ? this : oThis, aArgs.concat(Array.prototype.slice.call(arguments))) + }; + return this.prototype && (fNOP.prototype = this.prototype), fBound.prototype = new fNOP, fBound +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/polyfills/objectassign.js b/dashboard-ui/bower_components/emby-webcomponents/polyfills/objectassign.js index 468eda183e..7883d26563 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/polyfills/objectassign.js +++ b/dashboard-ui/bower_components/emby-webcomponents/polyfills/objectassign.js @@ -1 +1,12 @@ -"function"!=typeof Object.assign&&function(){Object.assign=function(target){"use strict";if(void 0===target||null===target)throw new TypeError("Cannot convert undefined or null to object");for(var output=Object(target),index=1;index","\n"),result=prompt(label,options.text||"");return result?Promise.resolve(result):Promise.reject(result)}}); \ No newline at end of file +define([], function() { + "use strict"; + + function replaceAll(str, find, replace) { + return str.split(find).join(replace) + } + return function(options) { + "string" == typeof options && (options = { + label: "", + text: options + }); + var label = replaceAll(options.label || "", "
", "\n"), + result = prompt(label, options.text || ""); + return result ? Promise.resolve(result) : Promise.reject(result) + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/prompt/prompt.js b/dashboard-ui/bower_components/emby-webcomponents/prompt/prompt.js index 51737fae59..d70ed5d6bc 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/prompt/prompt.js +++ b/dashboard-ui/bower_components/emby-webcomponents/prompt/prompt.js @@ -1 +1,40 @@ -define(["dialogHelper","layoutManager","scrollHelper","globalize","dom","require","material-icons","emby-button","paper-icon-button-light","emby-input","formDialogStyle"],function(dialogHelper,layoutManager,scrollHelper,globalize,dom,require){"use strict";function setInputProperties(dlg,options){var txtInput=dlg.querySelector("#txtInput");txtInput.label?txtInput.label(options.label||""):txtInput.setAttribute("label",options.label||""),txtInput.value=options.value||""}function showDialog(options,template){var dialogOptions={removeOnClose:!0,scrollY:!1};layoutManager.tv&&(dialogOptions.size="fullscreen");var dlg=dialogHelper.createDialog(dialogOptions);dlg.classList.add("formDialog"),dlg.innerHTML=globalize.translateHtml(template,"sharedcomponents"),layoutManager.tv?scrollHelper.centerFocus.on(dlg.querySelector(".formDialogContent"),!1):(dlg.querySelector(".dialogContentInner").classList.add("dialogContentInner-mini"),dlg.classList.add("dialog-fullscreen-lowres")),dlg.querySelector(".btnCancel").addEventListener("click",function(e){dialogHelper.close(dlg)}),dlg.querySelector(".formDialogHeaderTitle").innerHTML=options.title||"",options.description?dlg.querySelector(".fieldDescription").innerHTML=options.description:dlg.querySelector(".fieldDescription").classList.add("hide"),setInputProperties(dlg,options);var submitValue;return dlg.querySelector("form").addEventListener("submit",function(e){return submitValue=dlg.querySelector("#txtInput").value,e.preventDefault(),e.stopPropagation(),setTimeout(function(){dialogHelper.close(dlg)},300),!1}),dlg.querySelector(".submitText").innerHTML=options.confirmText||globalize.translate("sharedcomponents#ButtonOk"),dlg.style.minWidth=Math.min(400,dom.getWindowSize().innerWidth-50)+"px",dialogHelper.open(dlg).then(function(){layoutManager.tv&&scrollHelper.centerFocus.off(dlg.querySelector(".formDialogContent"),!1);var value=submitValue;return value||Promise.reject()})}return function(options){return new Promise(function(resolve,reject){require(["text!./prompt.template.html"],function(template){"string"==typeof options&&(options={title:"",text:options}),showDialog(options,template).then(resolve,reject)})})}}); \ No newline at end of file +define(["dialogHelper", "layoutManager", "scrollHelper", "globalize", "dom", "require", "material-icons", "emby-button", "paper-icon-button-light", "emby-input", "formDialogStyle"], function(dialogHelper, layoutManager, scrollHelper, globalize, dom, require) { + "use strict"; + + function setInputProperties(dlg, options) { + var txtInput = dlg.querySelector("#txtInput"); + txtInput.label ? txtInput.label(options.label || "") : txtInput.setAttribute("label", options.label || ""), txtInput.value = options.value || "" + } + + function showDialog(options, template) { + var dialogOptions = { + removeOnClose: !0, + scrollY: !1 + }; + layoutManager.tv && (dialogOptions.size = "fullscreen"); + var dlg = dialogHelper.createDialog(dialogOptions); + dlg.classList.add("formDialog"), dlg.innerHTML = globalize.translateHtml(template, "sharedcomponents"), layoutManager.tv ? scrollHelper.centerFocus.on(dlg.querySelector(".formDialogContent"), !1) : (dlg.querySelector(".dialogContentInner").classList.add("dialogContentInner-mini"), dlg.classList.add("dialog-fullscreen-lowres")), dlg.querySelector(".btnCancel").addEventListener("click", function(e) { + dialogHelper.close(dlg) + }), dlg.querySelector(".formDialogHeaderTitle").innerHTML = options.title || "", options.description ? dlg.querySelector(".fieldDescription").innerHTML = options.description : dlg.querySelector(".fieldDescription").classList.add("hide"), setInputProperties(dlg, options); + var submitValue; + return dlg.querySelector("form").addEventListener("submit", function(e) { + return submitValue = dlg.querySelector("#txtInput").value, e.preventDefault(), e.stopPropagation(), setTimeout(function() { + dialogHelper.close(dlg) + }, 300), !1 + }), dlg.querySelector(".submitText").innerHTML = options.confirmText || globalize.translate("sharedcomponents#ButtonOk"), dlg.style.minWidth = Math.min(400, dom.getWindowSize().innerWidth - 50) + "px", dialogHelper.open(dlg).then(function() { + layoutManager.tv && scrollHelper.centerFocus.off(dlg.querySelector(".formDialogContent"), !1); + var value = submitValue; + return value || Promise.reject() + }) + } + return function(options) { + return new Promise(function(resolve, reject) { + require(["text!./prompt.template.html"], function(template) { + "string" == typeof options && (options = { + title: "", + text: options + }), showDialog(options, template).then(resolve, reject) + }) + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/qualityoptions.js b/dashboard-ui/bower_components/emby-webcomponents/qualityoptions.js index e6523379e7..d0d7bae88c 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/qualityoptions.js +++ b/dashboard-ui/bower_components/emby-webcomponents/qualityoptions.js @@ -1 +1,214 @@ -define(["globalize"],function(globalize){"use strict";function getVideoQualityOptions(options){var maxStreamingBitrate=options.currentMaxBitrate,videoWidth=options.videoWidth,maxAllowedWidth=videoWidth||4096,qualityOptions=[];maxAllowedWidth>=3800&&(qualityOptions.push({name:"4K - 120 Mbps",maxHeight:2160,bitrate:12e7}),qualityOptions.push({name:"4K - 100 Mbps",maxHeight:2160,bitrate:1e8}),qualityOptions.push({name:"4K - 80 Mbps",maxHeight:2160,bitrate:8e7})),maxAllowedWidth>=1900?(qualityOptions.push({name:"1080p - 60 Mbps",maxHeight:1080,bitrate:6e7}),qualityOptions.push({name:"1080p - 50 Mbps",maxHeight:1080,bitrate:5e7}),qualityOptions.push({name:"1080p - 40 Mbps",maxHeight:1080,bitrate:4e7}),qualityOptions.push({name:"1080p - 30 Mbps",maxHeight:1080,bitrate:3e7}),qualityOptions.push({name:"1080p - 25 Mbps",maxHeight:1080,bitrate:25e6}),qualityOptions.push({name:"1080p - 20 Mbps",maxHeight:1080,bitrate:2e7}),qualityOptions.push({name:"1080p - 15 Mbps",maxHeight:1080,bitrate:15e6}),qualityOptions.push({name:"1080p - 10 Mbps",maxHeight:1080,bitrate:10000001}),qualityOptions.push({name:"1080p - 8 Mbps",maxHeight:1080,bitrate:8000001}),qualityOptions.push({name:"1080p - 6 Mbps",maxHeight:1080,bitrate:6000001}),qualityOptions.push({name:"1080p - 5 Mbps",maxHeight:1080,bitrate:5000001}),qualityOptions.push({name:"1080p - 4 Mbps",maxHeight:1080,bitrate:4000002})):maxAllowedWidth>=1260?(qualityOptions.push({name:"720p - 10 Mbps",maxHeight:720,bitrate:1e7}),qualityOptions.push({name:"720p - 8 Mbps",maxHeight:720,bitrate:8e6}),qualityOptions.push({name:"720p - 6 Mbps",maxHeight:720,bitrate:6e6}),qualityOptions.push({name:"720p - 5 Mbps",maxHeight:720,bitrate:5e6})):maxAllowedWidth>=620&&(qualityOptions.push({name:"480p - 4 Mbps",maxHeight:480,bitrate:4000001}),qualityOptions.push({name:"480p - 3 Mbps",maxHeight:480,bitrate:3000001}),qualityOptions.push({name:"480p - 2.5 Mbps",maxHeight:480,bitrate:25e5}),qualityOptions.push({name:"480p - 2 Mbps",maxHeight:480,bitrate:2000001}),qualityOptions.push({name:"480p - 1.5 Mbps",maxHeight:480,bitrate:1500001})),maxAllowedWidth>=1260&&(qualityOptions.push({name:"720p - 4 Mbps",maxHeight:720,bitrate:4e6}),qualityOptions.push({name:"720p - 3 Mbps",maxHeight:720,bitrate:3e6}),qualityOptions.push({name:"720p - 2 Mbps",maxHeight:720,bitrate:2e6}),qualityOptions.push({name:"720p - 1.5 Mbps",maxHeight:720,bitrate:15e5}),qualityOptions.push({name:"720p - 1 Mbps",maxHeight:720,bitrate:1000001})),qualityOptions.push({name:"480p - 1 Mbps",maxHeight:480,bitrate:1e6}),qualityOptions.push({name:"480p - 720 kbps",maxHeight:480,bitrate:72e4}),qualityOptions.push({name:"480p - 420 kbps",maxHeight:480,bitrate:42e4}),qualityOptions.push({name:"360p",maxHeight:360,bitrate:4e5}),qualityOptions.push({name:"240p",maxHeight:240,bitrate:32e4}),qualityOptions.push({name:"144p",maxHeight:144,bitrate:192e3});var autoQualityOption={name:globalize.translate("sharedcomponents#Auto"),bitrate:0,selected:options.isAutomaticBitrateEnabled};if(options.enableAuto&&qualityOptions.push(autoQualityOption),maxStreamingBitrate){for(var selectedIndex=-1,i=0,length=qualityOptions.length;i= 3800 && (qualityOptions.push({ + name: "4K - 120 Mbps", + maxHeight: 2160, + bitrate: 12e7 + }), qualityOptions.push({ + name: "4K - 100 Mbps", + maxHeight: 2160, + bitrate: 1e8 + }), qualityOptions.push({ + name: "4K - 80 Mbps", + maxHeight: 2160, + bitrate: 8e7 + })), maxAllowedWidth >= 1900 ? (qualityOptions.push({ + name: "1080p - 60 Mbps", + maxHeight: 1080, + bitrate: 6e7 + }), qualityOptions.push({ + name: "1080p - 50 Mbps", + maxHeight: 1080, + bitrate: 5e7 + }), qualityOptions.push({ + name: "1080p - 40 Mbps", + maxHeight: 1080, + bitrate: 4e7 + }), qualityOptions.push({ + name: "1080p - 30 Mbps", + maxHeight: 1080, + bitrate: 3e7 + }), qualityOptions.push({ + name: "1080p - 25 Mbps", + maxHeight: 1080, + bitrate: 25e6 + }), qualityOptions.push({ + name: "1080p - 20 Mbps", + maxHeight: 1080, + bitrate: 2e7 + }), qualityOptions.push({ + name: "1080p - 15 Mbps", + maxHeight: 1080, + bitrate: 15e6 + }), qualityOptions.push({ + name: "1080p - 10 Mbps", + maxHeight: 1080, + bitrate: 10000001 + }), qualityOptions.push({ + name: "1080p - 8 Mbps", + maxHeight: 1080, + bitrate: 8000001 + }), qualityOptions.push({ + name: "1080p - 6 Mbps", + maxHeight: 1080, + bitrate: 6000001 + }), qualityOptions.push({ + name: "1080p - 5 Mbps", + maxHeight: 1080, + bitrate: 5000001 + }), qualityOptions.push({ + name: "1080p - 4 Mbps", + maxHeight: 1080, + bitrate: 4000002 + })) : maxAllowedWidth >= 1260 ? (qualityOptions.push({ + name: "720p - 10 Mbps", + maxHeight: 720, + bitrate: 1e7 + }), qualityOptions.push({ + name: "720p - 8 Mbps", + maxHeight: 720, + bitrate: 8e6 + }), qualityOptions.push({ + name: "720p - 6 Mbps", + maxHeight: 720, + bitrate: 6e6 + }), qualityOptions.push({ + name: "720p - 5 Mbps", + maxHeight: 720, + bitrate: 5e6 + })) : maxAllowedWidth >= 620 && (qualityOptions.push({ + name: "480p - 4 Mbps", + maxHeight: 480, + bitrate: 4000001 + }), qualityOptions.push({ + name: "480p - 3 Mbps", + maxHeight: 480, + bitrate: 3000001 + }), qualityOptions.push({ + name: "480p - 2.5 Mbps", + maxHeight: 480, + bitrate: 25e5 + }), qualityOptions.push({ + name: "480p - 2 Mbps", + maxHeight: 480, + bitrate: 2000001 + }), qualityOptions.push({ + name: "480p - 1.5 Mbps", + maxHeight: 480, + bitrate: 1500001 + })), maxAllowedWidth >= 1260 && (qualityOptions.push({ + name: "720p - 4 Mbps", + maxHeight: 720, + bitrate: 4e6 + }), qualityOptions.push({ + name: "720p - 3 Mbps", + maxHeight: 720, + bitrate: 3e6 + }), qualityOptions.push({ + name: "720p - 2 Mbps", + maxHeight: 720, + bitrate: 2e6 + }), qualityOptions.push({ + name: "720p - 1.5 Mbps", + maxHeight: 720, + bitrate: 15e5 + }), qualityOptions.push({ + name: "720p - 1 Mbps", + maxHeight: 720, + bitrate: 1000001 + })), qualityOptions.push({ + name: "480p - 1 Mbps", + maxHeight: 480, + bitrate: 1e6 + }), qualityOptions.push({ + name: "480p - 720 kbps", + maxHeight: 480, + bitrate: 72e4 + }), qualityOptions.push({ + name: "480p - 420 kbps", + maxHeight: 480, + bitrate: 42e4 + }), qualityOptions.push({ + name: "360p", + maxHeight: 360, + bitrate: 4e5 + }), qualityOptions.push({ + name: "240p", + maxHeight: 240, + bitrate: 32e4 + }), qualityOptions.push({ + name: "144p", + maxHeight: 144, + bitrate: 192e3 + }); + var autoQualityOption = { + name: globalize.translate("sharedcomponents#Auto"), + bitrate: 0, + selected: options.isAutomaticBitrateEnabled + }; + if (options.enableAuto && qualityOptions.push(autoQualityOption), maxStreamingBitrate) { + for (var selectedIndex = -1, i = 0, length = qualityOptions.length; i < length; i++) { + var option = qualityOptions[i]; - 1 === selectedIndex && option.bitrate <= maxStreamingBitrate && (selectedIndex = i) + } - 1 === selectedIndex && (selectedIndex = qualityOptions.length - 1); + var currentQualityOption = qualityOptions[selectedIndex]; + options.isAutomaticBitrateEnabled ? autoQualityOption.autoText = currentQualityOption.name : currentQualityOption.selected = !0 + } + return qualityOptions + } + + function getAudioQualityOptions(options) { + var maxStreamingBitrate = options.currentMaxBitrate, + qualityOptions = []; + qualityOptions.push({ + name: "2 Mbps", + bitrate: 2e6 + }), qualityOptions.push({ + name: "1.5 Mbps", + bitrate: 15e5 + }), qualityOptions.push({ + name: "1 Mbps", + bitrate: 1e6 + }), qualityOptions.push({ + name: "320 kbps", + bitrate: 32e4 + }), qualityOptions.push({ + name: "256 kbps", + bitrate: 256e3 + }), qualityOptions.push({ + name: "192 kbps", + bitrate: 192e3 + }), qualityOptions.push({ + name: "128 kbps", + bitrate: 128e3 + }), qualityOptions.push({ + name: "96 kbps", + bitrate: 96e3 + }), qualityOptions.push({ + name: "64 kbps", + bitrate: 64e3 + }); + var autoQualityOption = { + name: globalize.translate("sharedcomponents#Auto"), + bitrate: 0, + selected: options.isAutomaticBitrateEnabled + }; + if (options.enableAuto && qualityOptions.push(autoQualityOption), maxStreamingBitrate) { + for (var selectedIndex = -1, i = 0, length = qualityOptions.length; i < length; i++) { + var option = qualityOptions[i]; - 1 === selectedIndex && option.bitrate <= maxStreamingBitrate && (selectedIndex = i) + } - 1 === selectedIndex && (selectedIndex = qualityOptions.length - 1); + var currentQualityOption = qualityOptions[selectedIndex]; + options.isAutomaticBitrateEnabled ? autoQualityOption.autoText = currentQualityOption.name : currentQualityOption.selected = !0 + } + return qualityOptions + } + return { + getVideoQualityOptions: getVideoQualityOptions, + getAudioQualityOptions: getAudioQualityOptions + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/recordingcreator/recordingbutton.js b/dashboard-ui/bower_components/emby-webcomponents/recordingcreator/recordingbutton.js index 506f5e734f..a5b085284c 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/recordingcreator/recordingbutton.js +++ b/dashboard-ui/bower_components/emby-webcomponents/recordingcreator/recordingbutton.js @@ -1 +1,60 @@ -define(["globalize","connectionManager","require","loading","apphost","dom","recordingHelper","events","registrationServices","paper-icon-button-light","emby-button","css!./recordingfields"],function(globalize,connectionManager,require,loading,appHost,dom,recordingHelper,events,registrationServices){"use strict";function onRecordingButtonClick(e){var item=this.item;if(item){var serverId=item.ServerId,programId=item.Id,timerId=item.TimerId,timerStatus=item.Status,seriesTimerId=item.SeriesTimerId,instance=this;recordingHelper.toggleRecording(serverId,programId,timerId,timerStatus,seriesTimerId).then(function(){instance.refresh(serverId,programId)})}}function RecordingButton(options){this.options=options,options.item?this.refreshItem(options.item):options.itemId&&options.serverId&&this.refresh(options.itemId,options.serverId);var button=options.button;button.querySelector("i").innerHTML="";var clickFn=onRecordingButtonClick.bind(this);this.clickFn=clickFn,dom.addEventListener(button,"click",clickFn,{passive:!0})}function getIndicatorIcon(item){var status;if("SeriesTimer"===item.Type)return"";if(item.TimerId||item.SeriesTimerId)status=item.Status||"Cancelled";else{if("Timer"!==item.Type)return"";status=item.Status}return item.SeriesTimerId&&"Cancelled"!==status?"":""}return RecordingButton.prototype.refresh=function(serverId,itemId){var apiClient=connectionManager.getApiClient(serverId),self=this;apiClient.getItem(apiClient.getCurrentUserId(),itemId).then(function(item){self.refreshItem(item)})},RecordingButton.prototype.refreshItem=function(item){var options=this.options,button=options.button;this.item=item,button.querySelector("i").innerHTML=getIndicatorIcon(item),item.TimerId&&"Cancelled"!==(item.Status||"Cancelled")?button.classList.add("recordingIcon-active"):button.classList.remove("recordingIcon-active")},RecordingButton.prototype.destroy=function(){var options=this.options;if(options){var button=options.button,clickFn=this.clickFn;clickFn&&dom.removeEventListener(button,"click",clickFn,{passive:!0})}this.options=null,this.item=null},RecordingButton}); \ No newline at end of file +define(["globalize", "connectionManager", "require", "loading", "apphost", "dom", "recordingHelper", "events", "registrationServices", "paper-icon-button-light", "emby-button", "css!./recordingfields"], function(globalize, connectionManager, require, loading, appHost, dom, recordingHelper, events, registrationServices) { + "use strict"; + + function onRecordingButtonClick(e) { + var item = this.item; + if (item) { + var serverId = item.ServerId, + programId = item.Id, + timerId = item.TimerId, + timerStatus = item.Status, + seriesTimerId = item.SeriesTimerId, + instance = this; + recordingHelper.toggleRecording(serverId, programId, timerId, timerStatus, seriesTimerId).then(function() { + instance.refresh(serverId, programId) + }) + } + } + + function RecordingButton(options) { + this.options = options, options.item ? this.refreshItem(options.item) : options.itemId && options.serverId && this.refresh(options.itemId, options.serverId); + var button = options.button; + button.querySelector("i").innerHTML = ""; + var clickFn = onRecordingButtonClick.bind(this); + this.clickFn = clickFn, dom.addEventListener(button, "click", clickFn, { + passive: !0 + }) + } + + function getIndicatorIcon(item) { + var status; + if ("SeriesTimer" === item.Type) return ""; + if (item.TimerId || item.SeriesTimerId) status = item.Status || "Cancelled"; + else { + if ("Timer" !== item.Type) return ""; + status = item.Status + } + return item.SeriesTimerId && "Cancelled" !== status ? "" : "" + } + return RecordingButton.prototype.refresh = function(serverId, itemId) { + var apiClient = connectionManager.getApiClient(serverId), + self = this; + apiClient.getItem(apiClient.getCurrentUserId(), itemId).then(function(item) { + self.refreshItem(item) + }) + }, RecordingButton.prototype.refreshItem = function(item) { + var options = this.options, + button = options.button; + this.item = item, button.querySelector("i").innerHTML = getIndicatorIcon(item), item.TimerId && "Cancelled" !== (item.Status || "Cancelled") ? button.classList.add("recordingIcon-active") : button.classList.remove("recordingIcon-active") + }, RecordingButton.prototype.destroy = function() { + var options = this.options; + if (options) { + var button = options.button, + clickFn = this.clickFn; + clickFn && dom.removeEventListener(button, "click", clickFn, { + passive: !0 + }) + } + this.options = null, this.item = null + }, RecordingButton +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/recordingcreator/recordingcreator.js b/dashboard-ui/bower_components/emby-webcomponents/recordingcreator/recordingcreator.js index 7d3b4d0180..760cfdc3a9 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/recordingcreator/recordingcreator.js +++ b/dashboard-ui/bower_components/emby-webcomponents/recordingcreator/recordingcreator.js @@ -1 +1,95 @@ -define(["dialogHelper","globalize","layoutManager","mediaInfo","apphost","connectionManager","require","loading","scrollHelper","datetime","imageLoader","recordingFields","events","emby-checkbox","emby-button","emby-collapse","emby-input","paper-icon-button-light","css!./../formdialog","css!./recordingcreator","material-icons"],function(dialogHelper,globalize,layoutManager,mediaInfo,appHost,connectionManager,require,loading,scrollHelper,datetime,imageLoader,recordingFields,events){"use strict";function closeDialog(){dialogHelper.close(currentDialog)}function init(context){context.querySelector(".btnPlay").addEventListener("click",function(){closeAction="play",closeDialog()}),context.querySelector(".btnCancel").addEventListener("click",function(){closeAction=null,closeDialog()})}function getImageUrl(item,apiClient,imageHeight){var imageTags=item.ImageTags||{};return item.PrimaryImageTag&&(imageTags.Primary=item.PrimaryImageTag),imageTags.Primary?apiClient.getScaledImageUrl(item.Id,{type:"Primary",maxHeight:imageHeight,tag:item.ImageTags.Primary}):imageTags.Thumb?apiClient.getScaledImageUrl(item.Id,{type:"Thumb",maxHeight:imageHeight,tag:item.ImageTags.Thumb}):null}function renderRecording(context,defaultTimer,program,apiClient,refreshRecordingStateOnly){if(!refreshRecordingStateOnly){var imgUrl=getImageUrl(program,apiClient,200),imageContainer=context.querySelector(".recordingDialog-imageContainer");imgUrl?(imageContainer.innerHTML='',imageContainer.classList.remove("hide"),imageLoader.lazyChildren(imageContainer)):(imageContainer.innerHTML="",imageContainer.classList.add("hide")),context.querySelector(".recordingDialog-itemName").innerHTML=program.Name,context.querySelector(".formDialogHeaderTitle").innerHTML=program.Name,context.querySelector(".itemGenres").innerHTML=(program.Genres||[]).join(" / "),context.querySelector(".itemOverview").innerHTML=program.Overview||"";var formDialogFooter=context.querySelector(".formDialogFooter"),now=new Date;now>=datetime.parseISO8601Date(program.StartDate,!0)&&now', imageContainer.classList.remove("hide"), imageLoader.lazyChildren(imageContainer)) : (imageContainer.innerHTML = "", imageContainer.classList.add("hide")), context.querySelector(".recordingDialog-itemName").innerHTML = program.Name, context.querySelector(".formDialogHeaderTitle").innerHTML = program.Name, context.querySelector(".itemGenres").innerHTML = (program.Genres || []).join(" / "), context.querySelector(".itemOverview").innerHTML = program.Overview || ""; + var formDialogFooter = context.querySelector(".formDialogFooter"), + now = new Date; + now >= datetime.parseISO8601Date(program.StartDate, !0) && now < datetime.parseISO8601Date(program.EndDate, !0) ? formDialogFooter.classList.remove("hide") : formDialogFooter.classList.add("hide"), context.querySelector(".itemMiscInfoPrimary").innerHTML = mediaInfo.getPrimaryMediaInfoHtml(program) + } + context.querySelector(".itemMiscInfoSecondary").innerHTML = mediaInfo.getSecondaryMediaInfoHtml(program, {}), loading.hide() + } + + function reload(context, programId, serverId, refreshRecordingStateOnly) { + loading.show(); + var apiClient = connectionManager.getApiClient(serverId), + promise1 = apiClient.getNewLiveTvTimerDefaults({ + programId: programId + }), + promise2 = apiClient.getLiveTvProgram(programId, apiClient.getCurrentUserId()); + Promise.all([promise1, promise2]).then(function(responses) { + var defaults = responses[0], + program = responses[1]; + renderRecording(context, defaults, program, apiClient, refreshRecordingStateOnly) + }) + } + + function executeCloseAction(action, programId, serverId) { + if ("play" === action) return void require(["playbackManager"], function(playbackManager) { + var apiClient = connectionManager.getApiClient(serverId); + apiClient.getLiveTvProgram(programId, apiClient.getCurrentUserId()).then(function(item) { + playbackManager.play({ + ids: [item.ChannelId], + serverId: serverId + }) + }) + }) + } + + function showEditor(itemId, serverId) { + return new Promise(function(resolve, reject) { + closeAction = null, loading.show(), require(["text!./recordingcreator.template.html"], function(template) { + function onRecordingChanged() { + reload(dlg, itemId, serverId, !0) + } + var dialogOptions = { + removeOnClose: !0, + scrollY: !1 + }; + layoutManager.tv ? dialogOptions.size = "fullscreen" : dialogOptions.size = "small"; + var dlg = dialogHelper.createDialog(dialogOptions); + dlg.classList.add("formDialog"), dlg.classList.add("recordingDialog"); + var html = ""; + html += globalize.translateDocument(template, "sharedcomponents"), dlg.innerHTML = html, currentDialog = dlg, dlg.addEventListener("close", function() { + events.off(currentRecordingFields, "recordingchanged", onRecordingChanged), executeCloseAction(closeAction, itemId, serverId), currentRecordingFields && currentRecordingFields.hasChanged() ? resolve() : reject() + }), layoutManager.tv && scrollHelper.centerFocus.on(dlg.querySelector(".formDialogContent"), !1), init(dlg), reload(dlg, itemId, serverId), currentRecordingFields = new recordingFields({ + parent: dlg.querySelector(".recordingFields"), + programId: itemId, + serverId: serverId + }), events.on(currentRecordingFields, "recordingchanged", onRecordingChanged), dialogHelper.open(dlg) + }) + }) + } + var currentDialog, closeAction, currentRecordingFields; + return { + show: showEditor + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/recordingcreator/recordingeditor.js b/dashboard-ui/bower_components/emby-webcomponents/recordingcreator/recordingeditor.js index 7b7decf768..bcc900e918 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/recordingcreator/recordingeditor.js +++ b/dashboard-ui/bower_components/emby-webcomponents/recordingcreator/recordingeditor.js @@ -1 +1,73 @@ -define(["dialogHelper","globalize","layoutManager","mediaInfo","apphost","connectionManager","require","loading","scrollHelper","imageLoader","scrollStyles","emby-button","emby-collapse","emby-input","paper-icon-button-light","css!./../formdialog","css!./recordingcreator","material-icons","flexStyles"],function(dialogHelper,globalize,layoutManager,mediaInfo,appHost,connectionManager,require,loading,scrollHelper,imageLoader){"use strict";function deleteTimer(apiClient,timerId){return new Promise(function(resolve,reject){require(["recordingHelper"],function(recordingHelper){recordingHelper.cancelTimerWithConfirmation(timerId,apiClient.serverId()).then(resolve,reject)})})}function renderTimer(context,item,apiClient){item.ProgramInfo;context.querySelector("#txtPrePaddingMinutes").value=item.PrePaddingSeconds/60,context.querySelector("#txtPostPaddingMinutes").value=item.PostPaddingSeconds/60,loading.hide()}function closeDialog(isDeleted){recordingDeleted=isDeleted,dialogHelper.close(currentDialog)}function onSubmit(e){var form=this,apiClient=connectionManager.getApiClient(currentServerId);return apiClient.getLiveTvTimer(currentItemId).then(function(item){item.PrePaddingSeconds=60*form.querySelector("#txtPrePaddingMinutes").value,item.PostPaddingSeconds=60*form.querySelector("#txtPostPaddingMinutes").value,apiClient.updateLiveTvTimer(item).then(currentResolve)}),e.preventDefault(),!1}function init(context){context.querySelector(".btnCancel").addEventListener("click",function(){closeDialog(!1)}),context.querySelector(".btnCancelRecording").addEventListener("click",function(){deleteTimer(connectionManager.getApiClient(currentServerId),currentItemId).then(function(){closeDialog(!0)})}),context.querySelector("form").addEventListener("submit",onSubmit)}function reload(context,id){loading.show(),currentItemId=id;var apiClient=connectionManager.getApiClient(currentServerId);apiClient.getLiveTvTimer(id).then(function(result){renderTimer(context,result,apiClient),loading.hide()})}function showEditor(itemId,serverId,options){return new Promise(function(resolve,reject){recordingDeleted=!1,currentServerId=serverId,loading.show(),options=options||{},currentResolve=resolve,require(["text!./recordingeditor.template.html"],function(template){var dialogOptions={removeOnClose:!0,scrollY:!1};layoutManager.tv&&(dialogOptions.size="fullscreen");var dlg=dialogHelper.createDialog(dialogOptions);dlg.classList.add("formDialog"),dlg.classList.add("recordingDialog"),layoutManager.tv||(dlg.style["min-width"]="20%",dlg.classList.add("dialog-fullscreen-lowres"));var html="";html+=globalize.translateDocument(template,"sharedcomponents"),dlg.innerHTML=html,!1===options.enableCancel&&dlg.querySelector(".formDialogFooter").classList.add("hide"),currentDialog=dlg,dlg.addEventListener("closing",function(){recordingDeleted||dlg.querySelector(".btnSubmit").click()}),dlg.addEventListener("close",function(){recordingDeleted&&resolve({updated:!0,deleted:!0})}),layoutManager.tv&&scrollHelper.centerFocus.on(dlg.querySelector(".formDialogContent"),!1),init(dlg),reload(dlg,itemId),dialogHelper.open(dlg)})})}var currentDialog,currentItemId,currentServerId,currentResolve,recordingDeleted=!1;return{show:showEditor}}); \ No newline at end of file +define(["dialogHelper", "globalize", "layoutManager", "mediaInfo", "apphost", "connectionManager", "require", "loading", "scrollHelper", "imageLoader", "scrollStyles", "emby-button", "emby-collapse", "emby-input", "paper-icon-button-light", "css!./../formdialog", "css!./recordingcreator", "material-icons", "flexStyles"], function(dialogHelper, globalize, layoutManager, mediaInfo, appHost, connectionManager, require, loading, scrollHelper, imageLoader) { + "use strict"; + + function deleteTimer(apiClient, timerId) { + return new Promise(function(resolve, reject) { + require(["recordingHelper"], function(recordingHelper) { + recordingHelper.cancelTimerWithConfirmation(timerId, apiClient.serverId()).then(resolve, reject) + }) + }) + } + + function renderTimer(context, item, apiClient) { + item.ProgramInfo; + context.querySelector("#txtPrePaddingMinutes").value = item.PrePaddingSeconds / 60, context.querySelector("#txtPostPaddingMinutes").value = item.PostPaddingSeconds / 60, loading.hide() + } + + function closeDialog(isDeleted) { + recordingDeleted = isDeleted, dialogHelper.close(currentDialog) + } + + function onSubmit(e) { + var form = this, + apiClient = connectionManager.getApiClient(currentServerId); + return apiClient.getLiveTvTimer(currentItemId).then(function(item) { + item.PrePaddingSeconds = 60 * form.querySelector("#txtPrePaddingMinutes").value, item.PostPaddingSeconds = 60 * form.querySelector("#txtPostPaddingMinutes").value, apiClient.updateLiveTvTimer(item).then(currentResolve) + }), e.preventDefault(), !1 + } + + function init(context) { + context.querySelector(".btnCancel").addEventListener("click", function() { + closeDialog(!1) + }), context.querySelector(".btnCancelRecording").addEventListener("click", function() { + deleteTimer(connectionManager.getApiClient(currentServerId), currentItemId).then(function() { + closeDialog(!0) + }) + }), context.querySelector("form").addEventListener("submit", onSubmit) + } + + function reload(context, id) { + loading.show(), currentItemId = id; + var apiClient = connectionManager.getApiClient(currentServerId); + apiClient.getLiveTvTimer(id).then(function(result) { + renderTimer(context, result, apiClient), loading.hide() + }) + } + + function showEditor(itemId, serverId, options) { + return new Promise(function(resolve, reject) { + recordingDeleted = !1, currentServerId = serverId, loading.show(), options = options || {}, currentResolve = resolve, require(["text!./recordingeditor.template.html"], function(template) { + var dialogOptions = { + removeOnClose: !0, + scrollY: !1 + }; + layoutManager.tv && (dialogOptions.size = "fullscreen"); + var dlg = dialogHelper.createDialog(dialogOptions); + dlg.classList.add("formDialog"), dlg.classList.add("recordingDialog"), layoutManager.tv || (dlg.style["min-width"] = "20%", dlg.classList.add("dialog-fullscreen-lowres")); + var html = ""; + html += globalize.translateDocument(template, "sharedcomponents"), dlg.innerHTML = html, !1 === options.enableCancel && dlg.querySelector(".formDialogFooter").classList.add("hide"), currentDialog = dlg, dlg.addEventListener("closing", function() { + recordingDeleted || dlg.querySelector(".btnSubmit").click() + }), dlg.addEventListener("close", function() { + recordingDeleted && resolve({ + updated: !0, + deleted: !0 + }) + }), layoutManager.tv && scrollHelper.centerFocus.on(dlg.querySelector(".formDialogContent"), !1), init(dlg), reload(dlg, itemId), dialogHelper.open(dlg) + }) + }) + } + var currentDialog, currentItemId, currentServerId, currentResolve, recordingDeleted = !1; + return { + show: showEditor + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/recordingcreator/recordingfields.js b/dashboard-ui/bower_components/emby-webcomponents/recordingcreator/recordingfields.js index 6098673c76..735951b300 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/recordingcreator/recordingfields.js +++ b/dashboard-ui/bower_components/emby-webcomponents/recordingcreator/recordingfields.js @@ -1 +1,168 @@ -define(["globalize","connectionManager","serverNotifications","require","loading","apphost","dom","recordingHelper","events","registrationServices","paper-icon-button-light","emby-button","css!./recordingfields","flexStyles"],function(globalize,connectionManager,serverNotifications,require,loading,appHost,dom,recordingHelper,events,registrationServices){"use strict";function getRegistration(apiClient,feature){return registrationServices.validateFeature(feature,{showDialog:!1,viewOnly:!0})}function showConvertRecordingsUnlockMessage(context,apiClient){getRegistration(apiClient,getDvrFeatureCode()).then(function(){context.querySelector(".convertRecordingsContainer").classList.add("hide")},function(){context.querySelector(".convertRecordingsContainer").classList.remove("hide")})}function showSeriesRecordingFields(context,programId,apiClient){getRegistration(apiClient,getDvrFeatureCode()).then(function(){context.querySelector(".supporterContainer").classList.add("hide"),context.querySelector(".convertRecordingsContainer").classList.add("hide"),context.querySelector(".recordSeriesContainer").classList.remove("hide")},function(){context.querySelector(".supporterContainerText").innerHTML=globalize.translate("sharedcomponents#MessageActiveSubscriptionRequiredSeriesRecordings"),context.querySelector(".supporterContainer").classList.remove("hide"),context.querySelector(".recordSeriesContainer").classList.add("hide"),context.querySelector(".convertRecordingsContainer").classList.add("hide")})}function getDvrFeatureCode(){return"dvr"}function showSingleRecordingFields(context,programId,apiClient){getRegistration(apiClient,getDvrFeatureCode()).then(function(){context.querySelector(".supporterContainer").classList.add("hide"),showConvertRecordingsUnlockMessage(context,apiClient)},function(){context.querySelector(".supporterContainerText").innerHTML=globalize.translate("sharedcomponents#DvrSubscriptionRequired"),context.querySelector(".supporterContainer").classList.remove("hide"),context.querySelector(".convertRecordingsContainer").classList.add("hide")})}function showRecordingFieldsContainer(context,programId,apiClient){getRegistration(apiClient,getDvrFeatureCode()).then(function(){context.querySelector(".recordingFields").classList.remove("hide")},function(){context.querySelector(".recordingFields").classList.add("hide")})}function loadData(parent,program,apiClient){program.IsSeries?(parent.querySelector(".recordSeriesContainer").classList.remove("hide"),showSeriesRecordingFields(parent,program.Id,apiClient)):(parent.querySelector(".recordSeriesContainer").classList.add("hide"),showSingleRecordingFields(parent,program.Id,apiClient)),program.SeriesTimerId?(parent.querySelector(".btnManageSeriesRecording").classList.remove("hide"),parent.querySelector(".seriesRecordingButton .recordingIcon").classList.add("recordingIcon-active"),parent.querySelector(".seriesRecordingButton .buttonText").innerHTML=globalize.translate("sharedcomponents#CancelSeries")):(parent.querySelector(".btnManageSeriesRecording").classList.add("hide"),parent.querySelector(".seriesRecordingButton .recordingIcon").classList.remove("recordingIcon-active"),parent.querySelector(".seriesRecordingButton .buttonText").innerHTML=globalize.translate("sharedcomponents#RecordSeries")),program.TimerId&&"Cancelled"!==program.Status?(parent.querySelector(".btnManageRecording").classList.remove("hide"),parent.querySelector(".singleRecordingButton .recordingIcon").classList.add("recordingIcon-active"),"InProgress"===program.Status?parent.querySelector(".singleRecordingButton .buttonText").innerHTML=globalize.translate("sharedcomponents#StopRecording"):parent.querySelector(".singleRecordingButton .buttonText").innerHTML=globalize.translate("sharedcomponents#DoNotRecord")):(parent.querySelector(".btnManageRecording").classList.add("hide"),parent.querySelector(".singleRecordingButton .recordingIcon").classList.remove("recordingIcon-active"),parent.querySelector(".singleRecordingButton .buttonText").innerHTML=globalize.translate("sharedcomponents#Record"))}function fetchData(instance){var options=instance.options,apiClient=connectionManager.getApiClient(options.serverId);return showRecordingFieldsContainer(options.parent,options.programId,apiClient),apiClient.getLiveTvProgram(options.programId,apiClient.getCurrentUserId()).then(function(program){instance.TimerId=program.TimerId,instance.Status=program.Status,instance.SeriesTimerId=program.SeriesTimerId,loadData(options.parent,program,apiClient)})}function onTimerChangedExternally(e,apiClient,data){var options=this.options,refresh=!1;data.Id&&this.TimerId===data.Id&&(refresh=!0),data.ProgramId&&options&&options.programId===data.ProgramId&&(refresh=!0),refresh&&this.refresh()}function onSeriesTimerChangedExternally(e,apiClient,data){var options=this.options,refresh=!1;data.Id&&this.SeriesTimerId===data.Id&&(refresh=!0),data.ProgramId&&options&&options.programId===data.ProgramId&&(refresh=!0),refresh&&this.refresh()}function RecordingEditor(options){this.options=options,this.embed();var timerChangedHandler=onTimerChangedExternally.bind(this);this.timerChangedHandler=timerChangedHandler,events.on(serverNotifications,"TimerCreated",timerChangedHandler),events.on(serverNotifications,"TimerCancelled",timerChangedHandler);var seriesTimerChangedHandler=onSeriesTimerChangedExternally.bind(this);this.seriesTimerChangedHandler=seriesTimerChangedHandler,events.on(serverNotifications,"SeriesTimerCreated",seriesTimerChangedHandler),events.on(serverNotifications,"SeriesTimerCancelled",seriesTimerChangedHandler)}function onSupporterButtonClick(){registrationServices.showPremiereInfo()}function onManageRecordingClick(e){var options=this.options;if(this.TimerId&&"Cancelled"!==this.Status){var self=this;require(["recordingEditor"],function(recordingEditor){recordingEditor.show(self.TimerId,options.serverId,{enableCancel:!1}).then(function(){self.changed=!0})})}}function onManageSeriesRecordingClick(e){var options=this.options;if(this.SeriesTimerId){var self=this;require(["seriesRecordingEditor"],function(seriesRecordingEditor){seriesRecordingEditor.show(self.SeriesTimerId,options.serverId,{enableCancel:!1}).then(function(){self.changed=!0})})}}function onRecordChange(e){this.changed=!0;var self=this,options=this.options,apiClient=connectionManager.getApiClient(options.serverId),button=dom.parentWithTag(e.target,"BUTTON"),isChecked=!button.querySelector("i").classList.contains("recordingIcon-active"),hasEnabledTimer=this.TimerId&&"Cancelled"!==this.Status;isChecked?hasEnabledTimer||(loading.show(),recordingHelper.createRecording(apiClient,options.programId,!1).then(function(){events.trigger(self,"recordingchanged"),fetchData(self),loading.hide()})):hasEnabledTimer&&(loading.show(),recordingHelper.cancelTimer(apiClient,this.TimerId,!0).then(function(){events.trigger(self,"recordingchanged"),fetchData(self),loading.hide()}))}function sendToast(msg){require(["toast"],function(toast){toast(msg)})}function onRecordSeriesChange(e){this.changed=!0;var self=this,options=this.options,apiClient=connectionManager.getApiClient(options.serverId);if(dom.parentWithTag(e.target,"BUTTON").querySelector("i").classList.contains("recordingIcon-active"))showSingleRecordingFields(options.parent,options.programId,apiClient),this.SeriesTimerId&&apiClient.cancelLiveTvSeriesTimer(this.SeriesTimerId).then(function(){sendToast(globalize.translate("sharedcomponents#RecordingCancelled")),fetchData(self)});else if(showSeriesRecordingFields(options.parent,options.programId,apiClient),!this.SeriesTimerId){var promise=this.TimerId?recordingHelper.changeRecordingToSeries(apiClient,this.TimerId,options.programId):recordingHelper.createRecording(apiClient,options.programId,!0);promise.then(function(){fetchData(self)})}}return RecordingEditor.prototype.embed=function(){var self=this;return new Promise(function(resolve,reject){require(["text!./recordingfields.template.html"],function(template){var options=self.options,context=options.parent;context.innerHTML=globalize.translateDocument(template,"sharedcomponents");for(var supporterButtons=context.querySelectorAll(".btnSupporter"),i=0,length=supporterButtons.length;i'+text+""}context.querySelector(".selectKeepUpTo").innerHTML=html}function onFieldChange(e){this.querySelector(".btnSubmit").click()}function embed(itemId,serverId,options){recordingUpdated=!1,recordingDeleted=!1,currentServerId=serverId,loading.show(),options=options||{},require(["text!./seriesrecordingeditor.template.html"],function(template){var dialogOptions={removeOnClose:!0,scrollY:!1};layoutManager.tv?dialogOptions.size="fullscreen":dialogOptions.size="small";var dlg=options.context;dlg.classList.add("hide"),dlg.innerHTML=globalize.translateDocument(template,"sharedcomponents"),dlg.querySelector(".formDialogHeader").classList.add("hide"),dlg.querySelector(".formDialogFooter").classList.add("hide"),dlg.querySelector(".formDialogContent").className="",dlg.querySelector(".dialogContentInner").className="",dlg.classList.remove("hide"),dlg.removeEventListener("change",onFieldChange),dlg.addEventListener("change",onFieldChange),currentDialog=dlg,init(dlg),reload(dlg,itemId)})}function showEditor(itemId,serverId,options){return new Promise(function(resolve,reject){recordingUpdated=!1,recordingDeleted=!1,currentServerId=serverId,loading.show(),options=options||{},require(["text!./seriesrecordingeditor.template.html"],function(template){var dialogOptions={removeOnClose:!0,scrollY:!1};layoutManager.tv?dialogOptions.size="fullscreen":dialogOptions.size="small";var dlg=dialogHelper.createDialog(dialogOptions);dlg.classList.add("formDialog"),dlg.classList.add("recordingDialog"),layoutManager.tv||(dlg.style["min-width"]="20%");var html="";html+=globalize.translateDocument(template,"sharedcomponents"),dlg.innerHTML=html,!1===options.enableCancel&&dlg.querySelector(".formDialogFooter").classList.add("hide"),currentDialog=dlg,dlg.addEventListener("closing",function(){recordingDeleted||this.querySelector(".btnSubmit").click()}),dlg.addEventListener("close",function(){recordingUpdated?resolve({updated:!0,deleted:recordingDeleted}):reject()}),layoutManager.tv&&scrollHelper.centerFocus.on(dlg.querySelector(".formDialogContent"),!1),init(dlg),reload(dlg,itemId),dialogHelper.open(dlg)})})}var currentDialog,currentItemId,currentServerId,recordingUpdated=!1,recordingDeleted=!1;return{show:showEditor,embed:embed}}); \ No newline at end of file +define(["dialogHelper", "globalize", "layoutManager", "mediaInfo", "apphost", "connectionManager", "require", "loading", "scrollHelper", "imageLoader", "datetime", "scrollStyles", "emby-button", "emby-checkbox", "emby-input", "emby-select", "paper-icon-button-light", "css!./../formdialog", "css!./recordingcreator", "material-icons", "flexStyles"], function(dialogHelper, globalize, layoutManager, mediaInfo, appHost, connectionManager, require, loading, scrollHelper, imageLoader, datetime) { + "use strict"; + + function deleteTimer(apiClient, timerId) { + return new Promise(function(resolve, reject) { + require(["recordingHelper"], function(recordingHelper) { + recordingHelper.cancelSeriesTimerWithConfirmation(timerId, apiClient.serverId()).then(resolve, reject) + }) + }) + } + + function renderTimer(context, item, apiClient) { + item.ProgramInfo; + context.querySelector("#txtPrePaddingMinutes").value = item.PrePaddingSeconds / 60, context.querySelector("#txtPostPaddingMinutes").value = item.PostPaddingSeconds / 60, context.querySelector(".selectChannels").value = item.RecordAnyChannel ? "all" : "one", context.querySelector(".selectAirTime").value = item.RecordAnyTime ? "any" : "original", context.querySelector(".selectShowType").value = item.RecordNewOnly ? "new" : "all", context.querySelector(".chkSkipEpisodesInLibrary").checked = item.SkipEpisodesInLibrary, context.querySelector(".selectKeepUpTo").value = item.KeepUpTo || 0, item.ChannelName || item.ChannelNumber ? context.querySelector(".optionChannelOnly").innerHTML = globalize.translate("sharedcomponents#ChannelNameOnly", item.ChannelName || item.ChannelNumber) : context.querySelector(".optionChannelOnly").innerHTML = globalize.translate("sharedcomponents#OneChannel"), context.querySelector(".optionAroundTime").innerHTML = globalize.translate("sharedcomponents#AroundTime", datetime.getDisplayTime(datetime.parseISO8601Date(item.StartDate))), loading.hide() + } + + function closeDialog(isDeleted) { + recordingUpdated = !0, recordingDeleted = isDeleted, dialogHelper.close(currentDialog) + } + + function onSubmit(e) { + var form = this, + apiClient = connectionManager.getApiClient(currentServerId); + return apiClient.getLiveTvSeriesTimer(currentItemId).then(function(item) { + item.PrePaddingSeconds = 60 * form.querySelector("#txtPrePaddingMinutes").value, item.PostPaddingSeconds = 60 * form.querySelector("#txtPostPaddingMinutes").value, item.RecordAnyChannel = "all" === form.querySelector(".selectChannels").value, item.RecordAnyTime = "any" === form.querySelector(".selectAirTime").value, item.RecordNewOnly = "new" === form.querySelector(".selectShowType").value, item.SkipEpisodesInLibrary = form.querySelector(".chkSkipEpisodesInLibrary").checked, item.KeepUpTo = form.querySelector(".selectKeepUpTo").value, apiClient.updateLiveTvSeriesTimer(item) + }), e.preventDefault(), !1 + } + + function init(context) { + fillKeepUpTo(context), context.querySelector(".btnCancel").addEventListener("click", function() { + closeDialog(!1) + }), context.querySelector(".btnCancelRecording").addEventListener("click", function() { + deleteTimer(connectionManager.getApiClient(currentServerId), currentItemId).then(function() { + closeDialog(!0) + }) + }), context.querySelector("form").addEventListener("submit", onSubmit) + } + + function reload(context, id) { + var apiClient = connectionManager.getApiClient(currentServerId); + loading.show(), "string" == typeof id ? (currentItemId = id, apiClient.getLiveTvSeriesTimer(id).then(function(result) { + renderTimer(context, result, apiClient), loading.hide() + })) : id && (currentItemId = id.Id, renderTimer(context, id, apiClient), loading.hide()) + } + + function fillKeepUpTo(context) { + for (var html = "", i = 0; i <= 50; i++) { + var text; + text = 0 === i ? globalize.translate("sharedcomponents#AsManyAsPossible") : 1 === i ? globalize.translate("sharedcomponents#ValueOneEpisode") : globalize.translate("sharedcomponents#ValueEpisodeCount", i), html += '" + } + context.querySelector(".selectKeepUpTo").innerHTML = html + } + + function onFieldChange(e) { + this.querySelector(".btnSubmit").click() + } + + function embed(itemId, serverId, options) { + recordingUpdated = !1, recordingDeleted = !1, currentServerId = serverId, loading.show(), options = options || {}, require(["text!./seriesrecordingeditor.template.html"], function(template) { + var dialogOptions = { + removeOnClose: !0, + scrollY: !1 + }; + layoutManager.tv ? dialogOptions.size = "fullscreen" : dialogOptions.size = "small"; + var dlg = options.context; + dlg.classList.add("hide"), dlg.innerHTML = globalize.translateDocument(template, "sharedcomponents"), dlg.querySelector(".formDialogHeader").classList.add("hide"), dlg.querySelector(".formDialogFooter").classList.add("hide"), dlg.querySelector(".formDialogContent").className = "", dlg.querySelector(".dialogContentInner").className = "", dlg.classList.remove("hide"), dlg.removeEventListener("change", onFieldChange), dlg.addEventListener("change", onFieldChange), currentDialog = dlg, init(dlg), reload(dlg, itemId) + }) + } + + function showEditor(itemId, serverId, options) { + return new Promise(function(resolve, reject) { + recordingUpdated = !1, recordingDeleted = !1, currentServerId = serverId, loading.show(), options = options || {}, require(["text!./seriesrecordingeditor.template.html"], function(template) { + var dialogOptions = { + removeOnClose: !0, + scrollY: !1 + }; + layoutManager.tv ? dialogOptions.size = "fullscreen" : dialogOptions.size = "small"; + var dlg = dialogHelper.createDialog(dialogOptions); + dlg.classList.add("formDialog"), dlg.classList.add("recordingDialog"), layoutManager.tv || (dlg.style["min-width"] = "20%"); + var html = ""; + html += globalize.translateDocument(template, "sharedcomponents"), dlg.innerHTML = html, !1 === options.enableCancel && dlg.querySelector(".formDialogFooter").classList.add("hide"), currentDialog = dlg, dlg.addEventListener("closing", function() { + recordingDeleted || this.querySelector(".btnSubmit").click() + }), dlg.addEventListener("close", function() { + recordingUpdated ? resolve({ + updated: !0, + deleted: recordingDeleted + }) : reject() + }), layoutManager.tv && scrollHelper.centerFocus.on(dlg.querySelector(".formDialogContent"), !1), init(dlg), reload(dlg, itemId), dialogHelper.open(dlg) + }) + }) + } + var currentDialog, currentItemId, currentServerId, recordingUpdated = !1, + recordingDeleted = !1; + return { + show: showEditor, + embed: embed + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/refreshdialog/refreshdialog.js b/dashboard-ui/bower_components/emby-webcomponents/refreshdialog/refreshdialog.js index d2ccd47197..1b35092781 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/refreshdialog/refreshdialog.js +++ b/dashboard-ui/bower_components/emby-webcomponents/refreshdialog/refreshdialog.js @@ -1 +1,65 @@ -define(["shell","dialogHelper","loading","layoutManager","connectionManager","appRouter","globalize","emby-input","emby-checkbox","paper-icon-button-light","emby-select","material-icons","css!./../formdialog","emby-button"],function(shell,dialogHelper,loading,layoutManager,connectionManager,appRouter,globalize){"use strict";function parentWithClass(elem,className){for(;!elem.classList||!elem.classList.contains(className);)if(!(elem=elem.parentNode))return null;return elem}function getEditorHtml(){var html="";return html+='
',html+='
',html+='
',html+='
',html+='",html+="
",html+='",html+='
',html+=globalize.translate("sharedcomponents#RefreshDialogHelp"),html+="
",html+='',html+="
",html+='
',html+='",html+="
",html+="
",html+="
",html+="
"}function centerFocus(elem,horiz,on){require(["scrollHelper"],function(scrollHelper){var fn=on?"on":"off";scrollHelper.centerFocus[fn](elem,horiz)})}function onSubmit(e){loading.show();var instance=this,dlg=parentWithClass(e.target,"dialog"),options=instance.options,apiClient=connectionManager.getApiClient(options.serverId),replaceAllMetadata="all"===dlg.querySelector("#selectMetadataRefreshMode").value,mode="scan"===dlg.querySelector("#selectMetadataRefreshMode").value?"Default":"FullRefresh",replaceAllImages="FullRefresh"===mode&&dlg.querySelector(".chkReplaceImages").checked;return options.itemIds.forEach(function(itemId){apiClient.refreshItem(itemId,{Recursive:!0,ImageRefreshMode:mode,MetadataRefreshMode:mode,ReplaceAllImages:replaceAllImages,ReplaceAllMetadata:replaceAllMetadata})}),dialogHelper.close(dlg),require(["toast"],function(toast){toast(globalize.translate("sharedcomponents#RefreshQueued"))}),loading.hide(),e.preventDefault(),!1}function RefreshDialog(options){this.options=options}return RefreshDialog.prototype.show=function(){var dialogOptions={removeOnClose:!0,scrollY:!1};layoutManager.tv?dialogOptions.size="fullscreen":dialogOptions.size="small";var dlg=dialogHelper.createDialog(dialogOptions);dlg.classList.add("formDialog");var html="",title=globalize.translate("sharedcomponents#RefreshMetadata");return html+='
',html+='',html+='

',html+=title,html+="

",html+="
",html+=getEditorHtml(),dlg.innerHTML=html,dlg.querySelector("form").addEventListener("submit",onSubmit.bind(this)),dlg.querySelector("#selectMetadataRefreshMode").addEventListener("change",function(){"scan"===this.value?dlg.querySelector(".fldReplaceExistingImages").classList.add("hide"):dlg.querySelector(".fldReplaceExistingImages").classList.remove("hide")}),this.options.mode&&(dlg.querySelector("#selectMetadataRefreshMode").value=this.options.mode),dlg.querySelector("#selectMetadataRefreshMode").dispatchEvent(new CustomEvent("change")),dlg.querySelector(".btnCancel").addEventListener("click",function(){dialogHelper.close(dlg)}),layoutManager.tv&¢erFocus(dlg.querySelector(".formDialogContent"),!1,!0),new Promise(function(resolve,reject){layoutManager.tv&¢erFocus(dlg.querySelector(".formDialogContent"),!1,!1),dlg.addEventListener("close",resolve),dialogHelper.open(dlg)})},RefreshDialog}); \ No newline at end of file +define(["shell", "dialogHelper", "loading", "layoutManager", "connectionManager", "appRouter", "globalize", "emby-input", "emby-checkbox", "paper-icon-button-light", "emby-select", "material-icons", "css!./../formdialog", "emby-button"], function(shell, dialogHelper, loading, layoutManager, connectionManager, appRouter, globalize) { + "use strict"; + + function parentWithClass(elem, className) { + for (; !elem.classList || !elem.classList.contains(className);) + if (!(elem = elem.parentNode)) return null; + return elem + } + + function getEditorHtml() { + var html = ""; + return html += '
', html += '
', html += '
', html += '
', html += '", html += "
", html += '", html += '
', html += globalize.translate("sharedcomponents#RefreshDialogHelp"), html += "
", html += '', html += "
", html += '
', html += '", html += "
", html += "
", html += "
", html += "
" + } + + function centerFocus(elem, horiz, on) { + require(["scrollHelper"], function(scrollHelper) { + var fn = on ? "on" : "off"; + scrollHelper.centerFocus[fn](elem, horiz) + }) + } + + function onSubmit(e) { + loading.show(); + var instance = this, + dlg = parentWithClass(e.target, "dialog"), + options = instance.options, + apiClient = connectionManager.getApiClient(options.serverId), + replaceAllMetadata = "all" === dlg.querySelector("#selectMetadataRefreshMode").value, + mode = "scan" === dlg.querySelector("#selectMetadataRefreshMode").value ? "Default" : "FullRefresh", + replaceAllImages = "FullRefresh" === mode && dlg.querySelector(".chkReplaceImages").checked; + return options.itemIds.forEach(function(itemId) { + apiClient.refreshItem(itemId, { + Recursive: !0, + ImageRefreshMode: mode, + MetadataRefreshMode: mode, + ReplaceAllImages: replaceAllImages, + ReplaceAllMetadata: replaceAllMetadata + }) + }), dialogHelper.close(dlg), require(["toast"], function(toast) { + toast(globalize.translate("sharedcomponents#RefreshQueued")) + }), loading.hide(), e.preventDefault(), !1 + } + + function RefreshDialog(options) { + this.options = options + } + return RefreshDialog.prototype.show = function() { + var dialogOptions = { + removeOnClose: !0, + scrollY: !1 + }; + layoutManager.tv ? dialogOptions.size = "fullscreen" : dialogOptions.size = "small"; + var dlg = dialogHelper.createDialog(dialogOptions); + dlg.classList.add("formDialog"); + var html = "", + title = globalize.translate("sharedcomponents#RefreshMetadata"); + return html += '
', html += '', html += '

', html += title, html += "

", html += "
", html += getEditorHtml(), dlg.innerHTML = html, dlg.querySelector("form").addEventListener("submit", onSubmit.bind(this)), dlg.querySelector("#selectMetadataRefreshMode").addEventListener("change", function() { + "scan" === this.value ? dlg.querySelector(".fldReplaceExistingImages").classList.add("hide") : dlg.querySelector(".fldReplaceExistingImages").classList.remove("hide") + }), this.options.mode && (dlg.querySelector("#selectMetadataRefreshMode").value = this.options.mode), dlg.querySelector("#selectMetadataRefreshMode").dispatchEvent(new CustomEvent("change")), dlg.querySelector(".btnCancel").addEventListener("click", function() { + dialogHelper.close(dlg) + }), layoutManager.tv && centerFocus(dlg.querySelector(".formDialogContent"), !1, !0), new Promise(function(resolve, reject) { + layoutManager.tv && centerFocus(dlg.querySelector(".formDialogContent"), !1, !1), dlg.addEventListener("close", resolve), dialogHelper.open(dlg) + }) + }, RefreshDialog +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/registrationservices/registrationservices.js b/dashboard-ui/bower_components/emby-webcomponents/registrationservices/registrationservices.js index 1daf465c83..ee034150a2 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/registrationservices/registrationservices.js +++ b/dashboard-ui/bower_components/emby-webcomponents/registrationservices/registrationservices.js @@ -1 +1,302 @@ -define(["appSettings","loading","apphost","iapManager","events","shell","globalize","dialogHelper","connectionManager","layoutManager","emby-button","emby-linkbutton"],function(appSettings,loading,appHost,iapManager,events,shell,globalize,dialogHelper,connectionManager,layoutManager){"use strict";function alertText(options){return new Promise(function(resolve,reject){require(["alert"],function(alert){alert(options).then(resolve,reject)})})}function showInAppPurchaseInfo(subscriptionOptions,unlockableProductInfo,dialogOptions){return new Promise(function(resolve,reject){require(["listViewStyle","formDialogStyle"],function(){showInAppPurchaseElement(subscriptionOptions,unlockableProductInfo,dialogOptions,resolve,reject),currentDisplayingResolve=resolve})})}function showPeriodicMessage(feature,settingsKey){return new Promise(function(resolve,reject){require(["listViewStyle","emby-button","formDialogStyle"],function(){var dlg=dialogHelper.createDialog({size:layoutManager.tv?"fullscreen":"fullscreen-border",removeOnClose:!0,scrollY:!1});dlg.classList.add("formDialog");var html="";html+='
',html+='',html+='

Emby Premiere',html+="

",html+="
",html+='
',html+='
',html+="

"+globalize.translate("sharedcomponents#HeaderDiscoverEmbyPremiere")+"

",html+="

"+globalize.translate("sharedcomponents#MessageDidYouKnowCinemaMode")+"

",html+="

"+globalize.translate("sharedcomponents#MessageDidYouKnowCinemaMode2")+"

",html+='

'+globalize.translate("sharedcomponents#HeaderBenefitsEmbyPremiere")+"

",html+='
',html+=getSubscriptionBenefits().map(getSubscriptionBenefitHtml).join(""),html+="
",html+="
",html+='
',html+='";var seconds=11;html+='
'+globalize.translate("sharedcomponents#ContinueInSecondsValue",seconds)+"
",html+='",html+="
",html+="
",html+="
",dlg.innerHTML=html;var i,length,isRejected=!0,timeTextInterval=setInterval(function(){seconds-=1,seconds<=0?(dlg.querySelector(".continueTimeText").classList.add("hide"),dlg.querySelector(".btnContinue").classList.remove("hide")):dlg.querySelector(".continueTimeText").innerHTML=globalize.translate("sharedcomponents#ContinueInSecondsValue",seconds)},1e3),btnPurchases=dlg.querySelectorAll(".buttonPremiereInfo");for(i=0,length=btnPurchases.length;iintervalMs){var apiClient=connectionManager.currentApiClient();if("6da60dd6edfc4508bca2c434d4400816"===apiClient.serverId())return Promise.resolve();var registrationOptions={viewOnly:!0};return connectionManager.getRegistrationInfo(iapManager.getAdminFeatureName(feature),apiClient,registrationOptions).catch(function(errorResult){return"overlimit"===errorResult?(appSettings.set(settingsKey,(new Date).getTime()),Promise.resolve()):showPeriodicMessage(feature,settingsKey)})}return Promise.resolve()}function validateFeature(feature,options){return options=options||{},console.log("validateFeature: "+feature),iapManager.isUnlockedByDefault(feature,options).then(function(){return showPeriodicMessageIfNeeded(feature)},function(){var unlockableFeatureCacheKey="featurepurchased-"+feature;if("1"===appSettings.get(unlockableFeatureCacheKey))return showPeriodicMessageIfNeeded(feature);var unlockableProduct=iapManager.getProductInfo(feature);if(unlockableProduct){var unlockableCacheKey="productpurchased-"+unlockableProduct.id;if(unlockableProduct.owned)return appSettings.set(unlockableFeatureCacheKey,"1"),appSettings.set(unlockableCacheKey,"1"),showPeriodicMessageIfNeeded(feature);if("1"===appSettings.get(unlockableCacheKey))return showPeriodicMessageIfNeeded(feature)}var unlockableProductInfo=unlockableProduct?{enableAppUnlock:!0,id:unlockableProduct.id,price:unlockableProduct.price,feature:feature}:null;return iapManager.getSubscriptionOptions().then(function(subscriptionOptions){if(subscriptionOptions.filter(function(p){return p.owned}).length>0)return Promise.resolve();var registrationOptions={viewOnly:options.viewOnly};return connectionManager.getRegistrationInfo(iapManager.getAdminFeatureName(feature),connectionManager.currentApiClient(),registrationOptions).catch(function(errorResult){if(!1===options.showDialog)return Promise.reject();var alertPromise;return"overlimit"===errorResult&&(alertPromise=showOverLimitAlert()),alertPromise||(alertPromise=Promise.resolve()),alertPromise.then(function(){var dialogOptions={title:globalize.translate("sharedcomponents#HeaderUnlockFeature"),feature:feature};return currentValidatingFeature=feature,showInAppPurchaseInfo(subscriptionOptions,unlockableProductInfo,dialogOptions)})})})})}function showOverLimitAlert(){return alertText("Your Emby Premiere device limit has been exceeded. Please check with the owner of your Emby Server and have them contact Emby support at apps@emby.media if necessary.").catch(function(){return Promise.resolve()})}function cancelInAppPurchase(){var elem=document.querySelector(".inAppPurchaseOverlay");elem&&dialogHelper.close(elem)}function clearCurrentDisplayingInfo(){currentDisplayingProductInfos=[],currentDisplayingResolve=null,currentValidatingFeature=null,isCurrentDialogRejected=null}function showExternalPremiereInfo(){shell.openUrl(iapManager.getPremiumInfoUrl())}function centerFocus(elem,horiz,on){require(["scrollHelper"],function(scrollHelper){var fn=on?"on":"off";scrollHelper.centerFocus[fn](elem,horiz)})}function getPurchaseTermHtml(term){return"
  • "+term+"
  • "}function getTermsOfPurchaseHtml(){var html="",termsOfPurchase=iapManager.getTermsOfPurchase?iapManager.getTermsOfPurchase():[];return termsOfPurchase.length?(html+="

    "+globalize.translate("sharedcomponents#HeaderTermsOfPurchase")+"

    ",termsOfPurchase.push(''+globalize.translate("sharedcomponents#PrivacyPolicy")+""),termsOfPurchase.push(''+globalize.translate("sharedcomponents#TermsOfUse")+""),html+="
      ",html+=termsOfPurchase.map(getPurchaseTermHtml).join(""),html+="
    "):html}function showInAppPurchaseElement(subscriptionOptions,unlockableProductInfo,dialogOptions,resolve,reject){function onCloseButtonClick(){dialogHelper.close(dlg)}cancelInAppPurchase(),currentDisplayingProductInfos=subscriptionOptions.slice(0),unlockableProductInfo&¤tDisplayingProductInfos.push(unlockableProductInfo);var dlg=dialogHelper.createDialog({size:layoutManager.tv?"fullscreen":"fullscreen-border",removeOnClose:!0,scrollY:!1});dlg.classList.add("formDialog");var html="";html+='
    ',html+='',html+='

    ',html+=dialogOptions.title||"",html+="

    ",html+="
    ",html+='
    ',html+='
    ',html+='
    ',html+='

    ',html+=unlockableProductInfo?globalize.translate("sharedcomponents#MessageUnlockAppWithPurchaseOrSupporter"):globalize.translate("sharedcomponents#MessageUnlockAppWithSupporter"),html+="

    ",html+='

    ',html+=globalize.translate("sharedcomponents#MessageToValidateSupporter"),html+="

    ";var i,length;for(i=0,length=subscriptionOptions.length;i",html+='",html+="

    ";if(unlockableProductInfo){!0;var unlockText=globalize.translate("sharedcomponents#ButtonUnlockWithPurchase");unlockableProductInfo.price&&(unlockText=globalize.translate("sharedcomponents#ButtonUnlockPrice",unlockableProductInfo.price)),html+="

    ",html+='",html+="

    "}html+="

    ",html+='",html+="

    ",subscriptionOptions.length&&(html+='

    '+globalize.translate("sharedcomponents#HeaderBenefitsEmbyPremiere")+"

    ",html+='
    ',html+=getSubscriptionBenefits().map(getSubscriptionBenefitHtml).join(""),html+="
    "),"playback"===dialogOptions.feature&&(html+="

    ",html+='",html+="

    "),html+=getTermsOfPurchaseHtml(),html+="",html+="
    ",html+="
    ",dlg.innerHTML=html,document.body.appendChild(dlg);var btnPurchases=dlg.querySelectorAll(".btnPurchase");for(i=0,length=btnPurchases.length;i'):html+='
    ',html+=''+item.icon+"",html+='
    ',html+='

    ',html+=item.name,html+="

    ",html+='
    ',html+=item.text,html+="
    ",html+="
    ",html+=enableLink?"":"
    "}function onPurchaseButtonClick(){var featureId=this.getAttribute("data-featureid");"true"===this.getAttribute("data-email")?getUserEmail().then(function(email){iapManager.beginPurchase(featureId,email)}):iapManager.beginPurchase(featureId)}function restorePurchase(unlockableProductInfo){var dlg=dialogHelper.createDialog({size:layoutManager.tv?"fullscreen":"fullscreen-border",removeOnClose:!0,scrollY:!1});dlg.classList.add("formDialog");var html="";html+='
    ',html+='',html+='

    ',html+=iapManager.getRestoreButtonText(),html+="

    ",html+="
    ",html+='
    ',html+='
    ',html+='

    ',html+=globalize.translate("sharedcomponents#HowDidYouPay"),html+="

    ",html+="

    ",html+='",html+="

    ",unlockableProductInfo&&(html+="

    ",html+='",html+="

    "),html+="
    ",html+="
    ",dlg.innerHTML=html,document.body.appendChild(dlg),loading.hide(),layoutManager.tv&¢erFocus(dlg.querySelector(".formDialogContent"),!1,!0),dlg.querySelector(".btnCloseDialog").addEventListener("click",function(){dialogHelper.close(dlg)}),dlg.querySelector(".btnRestoreSub").addEventListener("click",function(){dialogHelper.close(dlg),alertText({text:globalize.translate("sharedcomponents#MessageToValidateSupporter"),title:"Emby Premiere"})});var btnRestoreUnlock=dlg.querySelector(".btnRestoreUnlock");btnRestoreUnlock&&btnRestoreUnlock.addEventListener("click",function(){dialogHelper.close(dlg),iapManager.restorePurchase()}),dialogHelper.open(dlg).then(function(){layoutManager.tv&¢erFocus(dlg.querySelector(".formDialogContent"),!1,!1)})}function getUserEmail(){if(connectionManager.isLoggedIntoConnect()){var connectUser=connectionManager.connectUser();if(connectUser&&connectUser.Email)return Promise.resolve(connectUser.Email)}return new Promise(function(resolve,reject){require(["prompt"],function(prompt){prompt({label:globalize.translate("sharedcomponents#LabelEmailAddress")}).then(resolve,reject)})})}function onProductUpdated(e,product){if(product.owned){var resolve=currentDisplayingResolve;if(resolve&¤tDisplayingProductInfos.filter(function(p){return product.id===p.id}).length)return isCurrentDialogRejected=!1,cancelInAppPurchase(),void resolve()}var feature=currentValidatingFeature;feature&&iapManager.isUnlockedByDefault(feature).then(function(){isCurrentDialogRejected=!1,cancelInAppPurchase(),resolve()})}function showPremiereInfo(){return appHost.supports("externalpremium")?(showExternalPremiereInfo(),Promise.resolve()):iapManager.getSubscriptionOptions().then(function(subscriptionOptions){return showInAppPurchaseInfo(subscriptionOptions,null,{title:"Emby Premiere",feature:"sync"})})}var currentDisplayingProductInfos=[],currentDisplayingResolve=null,currentValidatingFeature=null,isCurrentDialogRejected=null;return events.on(iapManager,"productupdated",onProductUpdated),{validateFeature:validateFeature,showPremiereInfo:showPremiereInfo}}); \ No newline at end of file +define(["appSettings", "loading", "apphost", "iapManager", "events", "shell", "globalize", "dialogHelper", "connectionManager", "layoutManager", "emby-button", "emby-linkbutton"], function(appSettings, loading, appHost, iapManager, events, shell, globalize, dialogHelper, connectionManager, layoutManager) { + "use strict"; + + function alertText(options) { + return new Promise(function(resolve, reject) { + require(["alert"], function(alert) { + alert(options).then(resolve, reject) + }) + }) + } + + function showInAppPurchaseInfo(subscriptionOptions, unlockableProductInfo, dialogOptions) { + return new Promise(function(resolve, reject) { + require(["listViewStyle", "formDialogStyle"], function() { + showInAppPurchaseElement(subscriptionOptions, unlockableProductInfo, dialogOptions, resolve, reject), currentDisplayingResolve = resolve + }) + }) + } + + function showPeriodicMessage(feature, settingsKey) { + return new Promise(function(resolve, reject) { + require(["listViewStyle", "emby-button", "formDialogStyle"], function() { + var dlg = dialogHelper.createDialog({ + size: layoutManager.tv ? "fullscreen" : "fullscreen-border", + removeOnClose: !0, + scrollY: !1 + }); + dlg.classList.add("formDialog"); + var html = ""; + html += '
    ', html += '', html += '

    Emby Premiere', html += "

    ", html += "
    ", html += '
    ', html += '
    ', html += "

    " + globalize.translate("sharedcomponents#HeaderDiscoverEmbyPremiere") + "

    ", html += "

    " + globalize.translate("sharedcomponents#MessageDidYouKnowCinemaMode") + "

    ", html += "

    " + globalize.translate("sharedcomponents#MessageDidYouKnowCinemaMode2") + "

    ", html += '

    ' + globalize.translate("sharedcomponents#HeaderBenefitsEmbyPremiere") + "

    ", html += '
    ', html += getSubscriptionBenefits().map(getSubscriptionBenefitHtml).join(""), html += "
    ", html += "
    ", html += '
    ', html += '"; + var seconds = 11; + html += '
    ' + globalize.translate("sharedcomponents#ContinueInSecondsValue", seconds) + "
    ", html += '", html += "
    ", html += "
    ", html += "
    ", dlg.innerHTML = html; + var i, length, isRejected = !0, + timeTextInterval = setInterval(function() { + seconds -= 1, seconds <= 0 ? (dlg.querySelector(".continueTimeText").classList.add("hide"), dlg.querySelector(".btnContinue").classList.remove("hide")) : dlg.querySelector(".continueTimeText").innerHTML = globalize.translate("sharedcomponents#ContinueInSecondsValue", seconds) + }, 1e3), + btnPurchases = dlg.querySelectorAll(".buttonPremiereInfo"); + for (i = 0, length = btnPurchases.length; i < length; i++) btnPurchases[i].addEventListener("click", showExternalPremiereInfo); + layoutManager.tv && centerFocus(dlg.querySelector(".formDialogContent"), !1, !0), dlg.addEventListener("close", function(e) { + clearInterval(timeTextInterval), layoutManager.tv && centerFocus(dlg.querySelector(".formDialogContent"), !1, !1), isRejected ? reject() : (appSettings.set(settingsKey, (new Date).getTime()), resolve()) + }), dlg.querySelector(".btnContinue").addEventListener("click", function() { + isRejected = !1, dialogHelper.close(dlg) + }), dlg.querySelector(".btnGetPremiere").addEventListener("click", showPremiereInfo), dialogHelper.open(dlg); + var onCancelClick = function() { + dialogHelper.close(dlg) + }, + elems = dlg.querySelectorAll(".btnCancelSupporterInfo"); + for (i = 0, length = elems.length; i < length; i++) elems[i].addEventListener("click", onCancelClick) + }) + }) + } + + function showPeriodicMessageIfNeeded(feature) { + if ("playback" !== feature) return Promise.resolve(); + var intervalMs = iapManager.getPeriodicMessageIntervalMs(feature); + if (intervalMs <= 0) return Promise.resolve(); + var settingsKey = "periodicmessage11-" + feature, + lastMessage = parseInt(appSettings.get(settingsKey) || "0"); + if (!lastMessage) return appSettings.set(settingsKey, (new Date).getTime()), Promise.resolve(); + if ((new Date).getTime() - lastMessage > intervalMs) { + var apiClient = connectionManager.currentApiClient(); + if ("6da60dd6edfc4508bca2c434d4400816" === apiClient.serverId()) return Promise.resolve(); + var registrationOptions = { + viewOnly: !0 + }; + return connectionManager.getRegistrationInfo(iapManager.getAdminFeatureName(feature), apiClient, registrationOptions).catch(function(errorResult) { + return "overlimit" === errorResult ? (appSettings.set(settingsKey, (new Date).getTime()), Promise.resolve()) : showPeriodicMessage(feature, settingsKey) + }) + } + return Promise.resolve() + } + + function validateFeature(feature, options) { + return options = options || {}, console.log("validateFeature: " + feature), iapManager.isUnlockedByDefault(feature, options).then(function() { + return showPeriodicMessageIfNeeded(feature) + }, function() { + var unlockableFeatureCacheKey = "featurepurchased-" + feature; + if ("1" === appSettings.get(unlockableFeatureCacheKey)) return showPeriodicMessageIfNeeded(feature); + var unlockableProduct = iapManager.getProductInfo(feature); + if (unlockableProduct) { + var unlockableCacheKey = "productpurchased-" + unlockableProduct.id; + if (unlockableProduct.owned) return appSettings.set(unlockableFeatureCacheKey, "1"), appSettings.set(unlockableCacheKey, "1"), showPeriodicMessageIfNeeded(feature); + if ("1" === appSettings.get(unlockableCacheKey)) return showPeriodicMessageIfNeeded(feature) + } + var unlockableProductInfo = unlockableProduct ? { + enableAppUnlock: !0, + id: unlockableProduct.id, + price: unlockableProduct.price, + feature: feature + } : null; + return iapManager.getSubscriptionOptions().then(function(subscriptionOptions) { + if (subscriptionOptions.filter(function(p) { + return p.owned + }).length > 0) return Promise.resolve(); + var registrationOptions = { + viewOnly: options.viewOnly + }; + return connectionManager.getRegistrationInfo(iapManager.getAdminFeatureName(feature), connectionManager.currentApiClient(), registrationOptions).catch(function(errorResult) { + if (!1 === options.showDialog) return Promise.reject(); + var alertPromise; + return "overlimit" === errorResult && (alertPromise = showOverLimitAlert()), alertPromise || (alertPromise = Promise.resolve()), alertPromise.then(function() { + var dialogOptions = { + title: globalize.translate("sharedcomponents#HeaderUnlockFeature"), + feature: feature + }; + return currentValidatingFeature = feature, showInAppPurchaseInfo(subscriptionOptions, unlockableProductInfo, dialogOptions) + }) + }) + }) + }) + } + + function showOverLimitAlert() { + return alertText("Your Emby Premiere device limit has been exceeded. Please check with the owner of your Emby Server and have them contact Emby support at apps@emby.media if necessary.").catch(function() { + return Promise.resolve() + }) + } + + function cancelInAppPurchase() { + var elem = document.querySelector(".inAppPurchaseOverlay"); + elem && dialogHelper.close(elem) + } + + function clearCurrentDisplayingInfo() { + currentDisplayingProductInfos = [], currentDisplayingResolve = null, currentValidatingFeature = null, isCurrentDialogRejected = null + } + + function showExternalPremiereInfo() { + shell.openUrl(iapManager.getPremiumInfoUrl()) + } + + function centerFocus(elem, horiz, on) { + require(["scrollHelper"], function(scrollHelper) { + var fn = on ? "on" : "off"; + scrollHelper.centerFocus[fn](elem, horiz) + }) + } + + function getPurchaseTermHtml(term) { + return "
  • " + term + "
  • " + } + + function getTermsOfPurchaseHtml() { + var html = "", + termsOfPurchase = iapManager.getTermsOfPurchase ? iapManager.getTermsOfPurchase() : []; + return termsOfPurchase.length ? (html += "

    " + globalize.translate("sharedcomponents#HeaderTermsOfPurchase") + "

    ", termsOfPurchase.push('' + globalize.translate("sharedcomponents#PrivacyPolicy") + ""), termsOfPurchase.push('' + globalize.translate("sharedcomponents#TermsOfUse") + ""), html += "
      ", html += termsOfPurchase.map(getPurchaseTermHtml).join(""), html += "
    ") : html + } + + function showInAppPurchaseElement(subscriptionOptions, unlockableProductInfo, dialogOptions, resolve, reject) { + function onCloseButtonClick() { + dialogHelper.close(dlg) + } + cancelInAppPurchase(), currentDisplayingProductInfos = subscriptionOptions.slice(0), unlockableProductInfo && currentDisplayingProductInfos.push(unlockableProductInfo); + var dlg = dialogHelper.createDialog({ + size: layoutManager.tv ? "fullscreen" : "fullscreen-border", + removeOnClose: !0, + scrollY: !1 + }); + dlg.classList.add("formDialog"); + var html = ""; + html += '
    ', html += '', html += '

    ', html += dialogOptions.title || "", html += "

    ", html += "
    ", html += '
    ', html += '
    ', html += '
    ', html += '

    ', html += unlockableProductInfo ? globalize.translate("sharedcomponents#MessageUnlockAppWithPurchaseOrSupporter") : globalize.translate("sharedcomponents#MessageUnlockAppWithSupporter"), html += "

    ", html += '

    ', html += globalize.translate("sharedcomponents#MessageToValidateSupporter"), html += "

    "; + var i, length; + for (i = 0, length = subscriptionOptions.length; i < length; i++) !0, html += "

    ", html += '", html += "

    "; + if (unlockableProductInfo) { + !0; + var unlockText = globalize.translate("sharedcomponents#ButtonUnlockWithPurchase"); + unlockableProductInfo.price && (unlockText = globalize.translate("sharedcomponents#ButtonUnlockPrice", unlockableProductInfo.price)), html += "

    ", html += '", html += "

    " + } + html += "

    ", html += '", html += "

    ", subscriptionOptions.length && (html += '

    ' + globalize.translate("sharedcomponents#HeaderBenefitsEmbyPremiere") + "

    ", html += '
    ', html += getSubscriptionBenefits().map(getSubscriptionBenefitHtml).join(""), html += "
    "), "playback" === dialogOptions.feature && (html += "

    ", html += '", html += "

    "), html += getTermsOfPurchaseHtml(), html += "
    ", html += "
    ", html += "
    ", dlg.innerHTML = html, document.body.appendChild(dlg); + var btnPurchases = dlg.querySelectorAll(".btnPurchase"); + for (i = 0, length = btnPurchases.length; i < length; i++) btnPurchases[i].addEventListener("click", onPurchaseButtonClick); + for (btnPurchases = dlg.querySelectorAll(".buttonPremiereInfo"), i = 0, length = btnPurchases.length; i < length; i++) btnPurchases[i].addEventListener("click", showExternalPremiereInfo); + isCurrentDialogRejected = !0; + var resolveWithTimeLimit = !1, + btnPlayMinute = dlg.querySelector(".btnPlayMinute"); + btnPlayMinute && btnPlayMinute.addEventListener("click", function() { + resolveWithTimeLimit = !0, isCurrentDialogRejected = !1, dialogHelper.close(dlg) + }), dlg.querySelector(".btnRestorePurchase").addEventListener("click", function() { + restorePurchase(unlockableProductInfo) + }), loading.hide(); + var btnCloseDialogs = dlg.querySelectorAll(".btnCloseDialog"); + for (i = 0, length = btnCloseDialogs.length; i < length; i++) btnCloseDialogs[i].addEventListener("click", onCloseButtonClick); + dlg.classList.add("inAppPurchaseOverlay"), layoutManager.tv && centerFocus(dlg.querySelector(".formDialogContent"), !1, !0), dialogHelper.open(dlg).then(function() { + layoutManager.tv && centerFocus(dlg.querySelector(".formDialogContent"), !1, !1); + var rejected = isCurrentDialogRejected; + clearCurrentDisplayingInfo(), rejected ? reject() : resolveWithTimeLimit && resolve({ + enableTimeLimit: !0 + }) + }) + } + + function getSubscriptionBenefits() { + var list = []; + return list.push({ + name: globalize.translate("sharedcomponents#HeaderFreeApps"), + icon: "", + text: globalize.translate("sharedcomponents#FreeAppsFeatureDescription") + }), appHost.supports("sync") && list.push({ + name: globalize.translate("sharedcomponents#HeaderOfflineDownloads"), + icon: "", + text: globalize.translate("sharedcomponents#HeaderOfflineDownloadsDescription") + }), list.push({ + name: globalize.translate("sharedcomponents#LiveTV"), + icon: "", + text: globalize.translate("sharedcomponents#LiveTvFeatureDescription") + }), list.push({ + name: "Emby DVR", + icon: "", + text: globalize.translate("sharedcomponents#DvrFeatureDescription") + }), list.push({ + name: globalize.translate("sharedcomponents#HeaderCinemaMode"), + icon: "", + text: globalize.translate("sharedcomponents#CinemaModeFeatureDescription") + }), list.push({ + name: globalize.translate("sharedcomponents#HeaderCloudSync"), + icon: "", + text: globalize.translate("sharedcomponents#CloudSyncFeatureDescription") + }), list + } + + function getSubscriptionBenefitHtml(item) { + var enableLink = appHost.supports("externalpremium"), + html = "", + cssClass = "listItem"; + return layoutManager.tv && (cssClass += " listItem-focusscale"), enableLink ? (cssClass += " listItem-button", html += '" : "
    " + } + + function onPurchaseButtonClick() { + var featureId = this.getAttribute("data-featureid"); + "true" === this.getAttribute("data-email") ? getUserEmail().then(function(email) { + iapManager.beginPurchase(featureId, email) + }) : iapManager.beginPurchase(featureId) + } + + function restorePurchase(unlockableProductInfo) { + var dlg = dialogHelper.createDialog({ + size: layoutManager.tv ? "fullscreen" : "fullscreen-border", + removeOnClose: !0, + scrollY: !1 + }); + dlg.classList.add("formDialog"); + var html = ""; + html += '
    ', html += '', html += '

    ', html += iapManager.getRestoreButtonText(), html += "

    ", html += "
    ", html += '
    ', html += '
    ', html += '

    ', html += globalize.translate("sharedcomponents#HowDidYouPay"), html += "

    ", html += "

    ", html += '", html += "

    ", unlockableProductInfo && (html += "

    ", html += '", html += "

    "), html += "
    ", html += "
    ", dlg.innerHTML = html, document.body.appendChild(dlg), loading.hide(), layoutManager.tv && centerFocus(dlg.querySelector(".formDialogContent"), !1, !0), dlg.querySelector(".btnCloseDialog").addEventListener("click", function() { + dialogHelper.close(dlg) + }), dlg.querySelector(".btnRestoreSub").addEventListener("click", function() { + dialogHelper.close(dlg), alertText({ + text: globalize.translate("sharedcomponents#MessageToValidateSupporter"), + title: "Emby Premiere" + }) + }); + var btnRestoreUnlock = dlg.querySelector(".btnRestoreUnlock"); + btnRestoreUnlock && btnRestoreUnlock.addEventListener("click", function() { + dialogHelper.close(dlg), iapManager.restorePurchase() + }), dialogHelper.open(dlg).then(function() { + layoutManager.tv && centerFocus(dlg.querySelector(".formDialogContent"), !1, !1) + }) + } + + function getUserEmail() { + if (connectionManager.isLoggedIntoConnect()) { + var connectUser = connectionManager.connectUser(); + if (connectUser && connectUser.Email) return Promise.resolve(connectUser.Email) + } + return new Promise(function(resolve, reject) { + require(["prompt"], function(prompt) { + prompt({ + label: globalize.translate("sharedcomponents#LabelEmailAddress") + }).then(resolve, reject) + }) + }) + } + + function onProductUpdated(e, product) { + if (product.owned) { + var resolve = currentDisplayingResolve; + if (resolve && currentDisplayingProductInfos.filter(function(p) { + return product.id === p.id + }).length) return isCurrentDialogRejected = !1, cancelInAppPurchase(), void resolve() + } + var feature = currentValidatingFeature; + feature && iapManager.isUnlockedByDefault(feature).then(function() { + isCurrentDialogRejected = !1, cancelInAppPurchase(), resolve() + }) + } + + function showPremiereInfo() { + return appHost.supports("externalpremium") ? (showExternalPremiereInfo(), Promise.resolve()) : iapManager.getSubscriptionOptions().then(function(subscriptionOptions) { + return showInAppPurchaseInfo(subscriptionOptions, null, { + title: "Emby Premiere", + feature: "sync" + }) + }) + } + var currentDisplayingProductInfos = [], + currentDisplayingResolve = null, + currentValidatingFeature = null, + isCurrentDialogRejected = null; + return events.on(iapManager, "productupdated", onProductUpdated), { + validateFeature: validateFeature, + showPremiereInfo: showPremiereInfo + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/require/requirecss.js b/dashboard-ui/bower_components/emby-webcomponents/require/requirecss.js index 1448c6fa8e..5e158496cf 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/require/requirecss.js +++ b/dashboard-ui/bower_components/emby-webcomponents/require/requirecss.js @@ -1 +1,35 @@ -define(function(){"use strict";function isLoaded(url){return-1!==importedCss.indexOf(url)}function removeFromLoadHistory(url){url=url.toLowerCase(),importedCss=importedCss.filter(function(c){return-1===url.indexOf(c.toLowerCase())})}var requireCss={};requireCss.normalize=function(name,normalize){return".css"===name.substr(name.length-4,4)&&(name=name.substr(0,name.length-4)),normalize(name)};var importedCss=[];return requireCss.load=function(cssId,req,load,config){var srch="/emby-webcomponents/require/requirecss",index=cssId.indexOf(srch);-1!==index&&(cssId="css"+cssId.substring(index+srch.length));var url=cssId+".css";if(-1===url.indexOf("://")&&(url=config.baseUrl+url),isLoaded(url))load();else{importedCss.push(url);var link=document.createElement("link");link.setAttribute("rel","stylesheet"),link.setAttribute("type","text/css"),link.onload=load;var linkUrl=url;config.urlArgs&&(linkUrl+=config.urlArgs(cssId,url)),link.setAttribute("href",linkUrl),document.head.appendChild(link)}},window.requireCss={removeStylesheet:function(stylesheet){stylesheet.parentNode.removeChild(stylesheet),removeFromLoadHistory(stylesheet.href)}},requireCss}); \ No newline at end of file +define(function() { + "use strict"; + + function isLoaded(url) { + return -1 !== importedCss.indexOf(url) + } + + function removeFromLoadHistory(url) { + url = url.toLowerCase(), importedCss = importedCss.filter(function(c) { + return -1 === url.indexOf(c.toLowerCase()) + }) + } + var requireCss = {}; + requireCss.normalize = function(name, normalize) { + return ".css" === name.substr(name.length - 4, 4) && (name = name.substr(0, name.length - 4)), normalize(name) + }; + var importedCss = []; + return requireCss.load = function(cssId, req, load, config) { + var srch = "/emby-webcomponents/require/requirecss", + index = cssId.indexOf(srch); - 1 !== index && (cssId = "css" + cssId.substring(index + srch.length)); + var url = cssId + ".css"; + if (-1 === url.indexOf("://") && (url = config.baseUrl + url), isLoaded(url)) load(); + else { + importedCss.push(url); + var link = document.createElement("link"); + link.setAttribute("rel", "stylesheet"), link.setAttribute("type", "text/css"), link.onload = load; + var linkUrl = url; + config.urlArgs && (linkUrl += config.urlArgs(cssId, url)), link.setAttribute("href", linkUrl), document.head.appendChild(link) + } + }, window.requireCss = { + removeStylesheet: function(stylesheet) { + stylesheet.parentNode.removeChild(stylesheet), removeFromLoadHistory(stylesheet.href) + } + }, requireCss +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/require/requiretext.js b/dashboard-ui/bower_components/emby-webcomponents/require/requiretext.js index 5e950f1d13..cea971a3cb 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/require/requiretext.js +++ b/dashboard-ui/bower_components/emby-webcomponents/require/requiretext.js @@ -1 +1,16 @@ -define(function(){"use strict";var addRedirectPrevention=null!=self.dashboardVersion&&self.Dashboard&&!self.Dashboard.isConnectMode();return{load:function(url,req,load,config){-1===url.indexOf("://")&&(url=config.baseUrl+url),config.urlArgs&&(url+=config.urlArgs(url,url)),addRedirectPrevention&&(-1===url.indexOf("?")?url+="?":url+="&",url+="r=0");var xhr=new XMLHttpRequest;xhr.open("GET",url,!0),xhr.onload=function(e){load(this.response)},xhr.send()},normalize:function(name,normalize){return normalize(name)}}}); \ No newline at end of file +define(function() { + "use strict"; + var addRedirectPrevention = null != self.dashboardVersion && self.Dashboard && !self.Dashboard.isConnectMode(); + return { + load: function(url, req, load, config) { + -1 === url.indexOf("://") && (url = config.baseUrl + url), config.urlArgs && (url += config.urlArgs(url, url)), addRedirectPrevention && (-1 === url.indexOf("?") ? url += "?" : url += "&", url += "r=0"); + var xhr = new XMLHttpRequest; + xhr.open("GET", url, !0), xhr.onload = function(e) { + load(this.response) + }, xhr.send() + }, + normalize: function(name, normalize) { + return normalize(name) + } + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/resize-observer-polyfill/ResizeObserver.js b/dashboard-ui/bower_components/emby-webcomponents/resize-observer-polyfill/ResizeObserver.js index 51fedf6e2c..4b7687b2f4 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/resize-observer-polyfill/ResizeObserver.js +++ b/dashboard-ui/bower_components/emby-webcomponents/resize-observer-polyfill/ResizeObserver.js @@ -1 +1,244 @@ -!function(global,factory){"object"==typeof exports&&"undefined"!=typeof module?module.exports=factory():"function"==typeof define&&define.amd?define(factory):global.ResizeObserver=factory()}(this,function(){"use strict";function getHTMLElementContentRect(target){var rect=target.getBoundingClientRect();return createRectInit(rect.left,rect.top,rect.width,rect.height)}function getContentRect(target){return isBrowser?getHTMLElementContentRect(target):emptyRect}function createReadOnlyRect(ref){var x=ref.x,y=ref.y,width=ref.width,height=ref.height,Constr="undefined"!=typeof DOMRectReadOnly?DOMRectReadOnly:Object,rect=Object.create(Constr.prototype);return defineConfigurable(rect,{x:x,y:y,width:width,height:height,top:y,right:x+width,bottom:height+y,left:x}),rect}function createRectInit(x,y,width,height){return{x:x,y:y,width:width,height:height}}var MapShim=function(){function getIndex(arr,key){var result=-1;return arr.some(function(entry,index){return entry[0]===key&&(result=index,!0)}),result}return"undefined"!=typeof Map?Map:function(){function anonymous(){this.__entries__=[]}var prototypeAccessors={size:{configurable:!0}};return prototypeAccessors.size.get=function(){return this.__entries__.length},anonymous.prototype.get=function(key){var index=getIndex(this.__entries__,key),entry=this.__entries__[index];return entry&&entry[1]},anonymous.prototype.set=function(key,value){var index=getIndex(this.__entries__,key);~index?this.__entries__[index][1]=value:this.__entries__.push([key,value])},anonymous.prototype.delete=function(key){var entries=this.__entries__,index=getIndex(entries,key);~index&&entries.splice(index,1)},anonymous.prototype.has=function(key){return!!~getIndex(this.__entries__,key)},anonymous.prototype.clear=function(){this.__entries__.splice(0)},anonymous.prototype.forEach=function(callback,ctx){var this$1=this;void 0===ctx&&(ctx=null);for(var i=0,list=this$1.__entries__;i0},ResizeObserverController.prototype.connect_=function(){isBrowser&&!this.connected_&&(document.addEventListener("transitionend",this.onTransitionEnd_),window.addEventListener("resize",this.refresh),window.addEventListener("orientationchange",this.refresh),mutationObserverSupported?(this.mutationsObserver_=new MutationObserver(this.refresh),this.mutationsObserver_.observe(document,{attributes:!0,childList:!0,characterData:!0,subtree:!0})):(document.addEventListener("DOMSubtreeModified",this.refresh),this.mutationEventsAdded_=!0),this.connected_=!0)},ResizeObserverController.prototype.disconnect_=function(){isBrowser&&this.connected_&&(document.removeEventListener("transitionend",this.onTransitionEnd_),window.removeEventListener("resize",this.refresh),window.removeEventListener("orientationchange",this.refresh),this.mutationsObserver_&&this.mutationsObserver_.disconnect(),this.mutationEventsAdded_&&document.removeEventListener("DOMSubtreeModified",this.refresh),this.mutationsObserver_=null,this.mutationEventsAdded_=!1,this.connected_=!1)},ResizeObserverController.prototype.onTransitionEnd_=function(ref){var propertyName=ref.propertyName;void 0===propertyName&&(propertyName=""),transitionKeys.some(function(key){return!!~propertyName.indexOf(key)})&&this.refresh()},ResizeObserverController.getInstance=function(){return this.instance_||(this.instance_=new ResizeObserverController),this.instance_},ResizeObserverController.instance_=null;var defineConfigurable=function(target,props){for(var i=0,list=Object.keys(props);i0};var observers="undefined"!=typeof WeakMap?new WeakMap:new MapShim,ResizeObserver=function(callback){if(!(this instanceof ResizeObserver))throw new TypeError("Cannot call a class as a function.");if(!arguments.length)throw new TypeError("1 argument required, but only 0 present.");var controller=ResizeObserverController.getInstance(),observer=new ResizeObserverSPI(callback,controller,this);observers.set(this,observer)};return["observe","unobserve","disconnect"].forEach(function(method){ResizeObserver.prototype[method]=function(){return(ref=observers.get(this))[method].apply(ref,arguments);var ref}}),function(){return void 0!==global$1.ResizeObserver?global$1.ResizeObserver:ResizeObserver}()}); \ No newline at end of file +! function(global, factory) { + "object" == typeof exports && "undefined" != typeof module ? module.exports = factory() : "function" == typeof define && define.amd ? define(factory) : global.ResizeObserver = factory() +}(this, function() { + "use strict"; + + function getHTMLElementContentRect(target) { + var rect = target.getBoundingClientRect(); + return createRectInit(rect.left, rect.top, rect.width, rect.height) + } + + function getContentRect(target) { + return isBrowser ? getHTMLElementContentRect(target) : emptyRect + } + + function createReadOnlyRect(ref) { + var x = ref.x, + y = ref.y, + width = ref.width, + height = ref.height, + Constr = "undefined" != typeof DOMRectReadOnly ? DOMRectReadOnly : Object, + rect = Object.create(Constr.prototype); + return defineConfigurable(rect, { + x: x, + y: y, + width: width, + height: height, + top: y, + right: x + width, + bottom: height + y, + left: x + }), rect + } + + function createRectInit(x, y, width, height) { + return { + x: x, + y: y, + width: width, + height: height + } + } + var MapShim = function() { + function getIndex(arr, key) { + var result = -1; + return arr.some(function(entry, index) { + return entry[0] === key && (result = index, !0) + }), result + } + return "undefined" != typeof Map ? Map : function() { + function anonymous() { + this.__entries__ = [] + } + var prototypeAccessors = { + size: { + configurable: !0 + } + }; + return prototypeAccessors.size.get = function() { + return this.__entries__.length + }, anonymous.prototype.get = function(key) { + var index = getIndex(this.__entries__, key), + entry = this.__entries__[index]; + return entry && entry[1] + }, anonymous.prototype.set = function(key, value) { + var index = getIndex(this.__entries__, key); + ~index ? this.__entries__[index][1] = value : this.__entries__.push([key, value]) + }, anonymous.prototype.delete = function(key) { + var entries = this.__entries__, + index = getIndex(entries, key); + ~index && entries.splice(index, 1) + }, anonymous.prototype.has = function(key) { + return !!~getIndex(this.__entries__, key) + }, anonymous.prototype.clear = function() { + this.__entries__.splice(0) + }, anonymous.prototype.forEach = function(callback, ctx) { + var this$1 = this; + void 0 === ctx && (ctx = null); + for (var i = 0, list = this$1.__entries__; i < list.length; i += 1) { + var entry = list[i]; + callback.call(ctx, entry[1], entry[0]) + } + }, Object.defineProperties(anonymous.prototype, prototypeAccessors), anonymous + }() + }(), + isBrowser = "undefined" != typeof window && "undefined" != typeof document && window.document === document, + global$1 = function() { + return "undefined" != typeof global && global.Math === Math ? global : "undefined" != typeof self && self.Math === Math ? self : "undefined" != typeof window && window.Math === Math ? window : Function("return this")() + }(), + requestAnimationFrame$1 = function() { + return "function" == typeof requestAnimationFrame ? requestAnimationFrame.bind(global$1) : function(callback) { + return setTimeout(function() { + return callback(Date.now()) + }, 1e3 / 60) + } + }(), + trailingTimeout = 2, + throttle = function(callback, delay) { + function resolvePending() { + leadingCall && (leadingCall = !1, callback()), trailingCall && proxy() + } + + function timeoutCallback() { + requestAnimationFrame$1(resolvePending) + } + + function proxy() { + var timeStamp = Date.now(); + if (leadingCall) { + if (timeStamp - lastCallTime < trailingTimeout) return; + trailingCall = !0 + } else leadingCall = !0, trailingCall = !1, setTimeout(timeoutCallback, delay); + lastCallTime = timeStamp + } + var leadingCall = !1, + trailingCall = !1, + lastCallTime = 0; + return proxy + }, + transitionKeys = ["top", "right", "bottom", "left", "width", "height", "size", "weight"], + mutationObserverSupported = "undefined" != typeof MutationObserver, + ResizeObserverController = function() { + this.connected_ = !1, this.mutationEventsAdded_ = !1, this.mutationsObserver_ = null, this.observers_ = [], this.onTransitionEnd_ = this.onTransitionEnd_.bind(this), this.refresh = throttle(this.refresh.bind(this), 20) + }; + ResizeObserverController.prototype.addObserver = function(observer) { + ~this.observers_.indexOf(observer) || this.observers_.push(observer), this.connected_ || this.connect_() + }, ResizeObserverController.prototype.removeObserver = function(observer) { + var observers = this.observers_, + index = observers.indexOf(observer); + ~index && observers.splice(index, 1), !observers.length && this.connected_ && this.disconnect_() + }, ResizeObserverController.prototype.refresh = function() { + this.updateObservers_() && this.refresh() + }, ResizeObserverController.prototype.updateObservers_ = function() { + var activeObservers = this.observers_.filter(function(observer) { + return observer.gatherActive(), observer.hasActive() + }); + return activeObservers.forEach(function(observer) { + return observer.broadcastActive() + }), activeObservers.length > 0 + }, ResizeObserverController.prototype.connect_ = function() { + isBrowser && !this.connected_ && (document.addEventListener("transitionend", this.onTransitionEnd_), window.addEventListener("resize", this.refresh), window.addEventListener("orientationchange", this.refresh), mutationObserverSupported ? (this.mutationsObserver_ = new MutationObserver(this.refresh), this.mutationsObserver_.observe(document, { + attributes: !0, + childList: !0, + characterData: !0, + subtree: !0 + })) : (document.addEventListener("DOMSubtreeModified", this.refresh), this.mutationEventsAdded_ = !0), this.connected_ = !0) + }, ResizeObserverController.prototype.disconnect_ = function() { + isBrowser && this.connected_ && (document.removeEventListener("transitionend", this.onTransitionEnd_), window.removeEventListener("resize", this.refresh), window.removeEventListener("orientationchange", this.refresh), this.mutationsObserver_ && this.mutationsObserver_.disconnect(), this.mutationEventsAdded_ && document.removeEventListener("DOMSubtreeModified", this.refresh), this.mutationsObserver_ = null, this.mutationEventsAdded_ = !1, this.connected_ = !1) + }, ResizeObserverController.prototype.onTransitionEnd_ = function(ref) { + var propertyName = ref.propertyName; + void 0 === propertyName && (propertyName = ""), transitionKeys.some(function(key) { + return !!~propertyName.indexOf(key) + }) && this.refresh() + }, ResizeObserverController.getInstance = function() { + return this.instance_ || (this.instance_ = new ResizeObserverController), this.instance_ + }, ResizeObserverController.instance_ = null; + var defineConfigurable = function(target, props) { + for (var i = 0, list = Object.keys(props); i < list.length; i += 1) { + var key = list[i]; + Object.defineProperty(target, key, { + value: props[key], + enumerable: !1, + writable: !1, + configurable: !0 + }) + } + return target + }, + getWindowOf = function(target) { + return target && target.ownerDocument && target.ownerDocument.defaultView || global$1 + }, + emptyRect = createRectInit(0, 0, 0, 0), + ResizeObservation = function(target) { + this.broadcastWidth = 0, this.broadcastHeight = 0, this.contentRect_ = createRectInit(0, 0, 0, 0), this.target = target + }; + ResizeObservation.prototype.isActive = function() { + var rect = getContentRect(this.target); + return this.contentRect_ = rect, rect.width !== this.broadcastWidth || rect.height !== this.broadcastHeight + }, ResizeObservation.prototype.broadcastRect = function() { + var rect = this.contentRect_; + return this.broadcastWidth = rect.width, this.broadcastHeight = rect.height, rect + }; + var ResizeObserverEntry = function(target, rectInit) { + var contentRect = createReadOnlyRect(rectInit); + defineConfigurable(this, { + target: target, + contentRect: contentRect + }) + }, + ResizeObserverSPI = function(callback, controller, callbackCtx) { + if (this.activeObservations_ = [], this.observations_ = new MapShim, "function" != typeof callback) throw new TypeError("The callback provided as parameter 1 is not a function."); + this.callback_ = callback, this.controller_ = controller, this.callbackCtx_ = callbackCtx + }; + ResizeObserverSPI.prototype.observe = function(target) { + if (!arguments.length) throw new TypeError("1 argument required, but only 0 present."); + if ("undefined" != typeof Element && Element instanceof Object) { + if (!(target instanceof getWindowOf(target).Element)) throw new TypeError('parameter 1 is not of type "Element".'); + var observations = this.observations_; + observations.has(target) || (observations.set(target, new ResizeObservation(target)), this.controller_.addObserver(this), this.controller_.refresh()) + } + }, ResizeObserverSPI.prototype.unobserve = function(target) { + if (!arguments.length) throw new TypeError("1 argument required, but only 0 present."); + if ("undefined" != typeof Element && Element instanceof Object) { + if (!(target instanceof getWindowOf(target).Element)) throw new TypeError('parameter 1 is not of type "Element".'); + var observations = this.observations_; + observations.has(target) && (observations.delete(target), observations.size || this.controller_.removeObserver(this)) + } + }, ResizeObserverSPI.prototype.disconnect = function() { + this.clearActive(), this.observations_.clear(), this.controller_.removeObserver(this) + }, ResizeObserverSPI.prototype.gatherActive = function() { + var this$1 = this; + this.clearActive(), this.observations_.forEach(function(observation) { + observation.isActive() && this$1.activeObservations_.push(observation) + }) + }, ResizeObserverSPI.prototype.broadcastActive = function() { + if (this.hasActive()) { + var ctx = this.callbackCtx_, + entries = this.activeObservations_.map(function(observation) { + return new ResizeObserverEntry(observation.target, observation.broadcastRect()) + }); + this.callback_.call(ctx, entries, ctx), this.clearActive() + } + }, ResizeObserverSPI.prototype.clearActive = function() { + this.activeObservations_.splice(0) + }, ResizeObserverSPI.prototype.hasActive = function() { + return this.activeObservations_.length > 0 + }; + var observers = "undefined" != typeof WeakMap ? new WeakMap : new MapShim, + ResizeObserver = function(callback) { + if (!(this instanceof ResizeObserver)) throw new TypeError("Cannot call a class as a function."); + if (!arguments.length) throw new TypeError("1 argument required, but only 0 present."); + var controller = ResizeObserverController.getInstance(), + observer = new ResizeObserverSPI(callback, controller, this); + observers.set(this, observer) + }; + return ["observe", "unobserve", "disconnect"].forEach(function(method) { + ResizeObserver.prototype[method] = function() { + return (ref = observers.get(this))[method].apply(ref, arguments); + var ref + } + }), + function() { + return void 0 !== global$1.ResizeObserver ? global$1.ResizeObserver : ResizeObserver + }() +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/router.js b/dashboard-ui/bower_components/emby-webcomponents/router.js index 4d41c0dd43..1effed01d8 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/router.js +++ b/dashboard-ui/bower_components/emby-webcomponents/router.js @@ -1 +1,416 @@ -define(["loading","globalize","events","viewManager","layoutManager","skinManager","pluginManager","backdrop","browser","pageJs","appSettings","apphost","connectionManager"],function(loading,globalize,events,viewManager,layoutManager,skinManager,pluginManager,backdrop,browser,page,appSettings,appHost,connectionManager){"use strict";function beginConnectionWizard(){backdrop.clear(),loading.show(),connectionManager.connect({enableAutoLogin:appSettings.enableAutoLogin()}).then(function(result){handleConnectionResult(result,loading)})}function handleConnectionResult(result,loading){switch(result.State){case"SignedIn":loading.hide(),skinManager.loadUserSkin();break;case"ServerSignIn":result.ApiClient.getPublicUsers().then(function(users){users.length?appRouter.showLocalLogin(result.Servers[0].Id):appRouter.showLocalLogin(result.Servers[0].Id,!0)});break;case"ServerSelection":appRouter.showSelectServer();break;case"ConnectSignIn":appRouter.showWelcome();break;case"ServerUpdateNeeded":require(["alert"],function(alert){alert({text:globalize.translate("sharedcomponents#ServerUpdateNeeded","https://emby.media"),html:globalize.translate("sharedcomponents#ServerUpdateNeeded",'https://emby.media')}).then(function(){appRouter.showSelectServer()})})}}function loadContentUrl(ctx,next,route,request){var url;url=route.contentPath&&"function"==typeof route.contentPath?route.contentPath(ctx.querystring):route.contentPath||route.path,-1===url.indexOf("://")&&(0!==url.indexOf("/")&&(url="/"+url),url=baseUrl()+url),ctx.querystring&&route.enableContentQueryString&&(url+="?"+ctx.querystring),require(["text!"+url],function(html){loadContent(ctx,route,html,request)})}function handleRoute(ctx,next,route){authenticate(ctx,route,function(){initRoute(ctx,next,route)})}function initRoute(ctx,next,route){var onInitComplete=function(controllerFactory){sendRouteToViewManager(ctx,next,route,controllerFactory)};require(route.dependencies||[],function(){route.controller?require([route.controller],onInitComplete):onInitComplete()})}function cancelCurrentLoadRequest(){var currentRequest=currentViewLoadRequest;currentRequest&&(currentRequest.cancel=!0)}function sendRouteToViewManager(ctx,next,route,controllerFactory){if(isDummyBackToHome&&"home"===route.type)return void(isDummyBackToHome=!1);cancelCurrentLoadRequest();var isBackNav=ctx.isBack,currentRequest={url:baseUrl()+ctx.path,transition:route.transition,isBack:isBackNav,state:ctx.state,type:route.type,fullscreen:route.fullscreen,controllerFactory:controllerFactory,options:{supportsThemeMedia:route.supportsThemeMedia||!1,enableMediaControl:!1!==route.enableMediaControl},autoFocus:route.autoFocus};currentViewLoadRequest=currentRequest;var onNewViewNeeded=function(){"string"==typeof route.path?loadContentUrl(ctx,next,route,currentRequest):next()};if(!isBackNav)return void onNewViewNeeded();viewManager.tryRestoreView(currentRequest,function(){currentRouteInfo={route:route,path:ctx.path}}).catch(function(result){result&&result.cancelled||onNewViewNeeded()})}function onForcedLogoutMessageTimeout(){var msg=forcedLogoutMsg;forcedLogoutMsg=null,msg&&require(["alert"],function(alert){alert(msg)})}function showForcedLogoutMessage(msg){forcedLogoutMsg=msg,msgTimeout&&clearTimeout(msgTimeout),msgTimeout=setTimeout(onForcedLogoutMessageTimeout,100)}function onRequestFail(e,data){var apiClient=this;if(401===data.status&&"ParentalControl"===data.errorCode){!currentRouteInfo||(currentRouteInfo.route.anonymous||currentRouteInfo.route.startup)||(showForcedLogoutMessage(globalize.translate("sharedcomponents#AccessRestrictedTryAgainLater")),connectionManager.isLoggedIntoConnect()?appRouter.showConnectLogin():appRouter.showLocalLogin(apiClient.serverId()))}}function onBeforeExit(e){browser.web0s&&page.restorePreviousState()}function normalizeImageOptions(options){var setQuality,scaleFactor=browser.tv?.8:1;if(options.maxWidth&&(options.maxWidth=Math.round(options.maxWidth*scaleFactor),setQuality=!0),options.width&&(options.width=Math.round(options.width*scaleFactor),setQuality=!0),options.maxHeight&&(options.maxHeight=Math.round(options.maxHeight*scaleFactor),setQuality=!0),options.height&&(options.height=Math.round(options.height*scaleFactor),setQuality=!0),setQuality){var quality=100,type=options.type||"Primary";quality=browser.tv||browser.slow?browser.chrome?"Primary"===type?40:50:"Backdrop"===type?60:50:"Backdrop"===type?70:90,options.quality=quality}}function getMaxBandwidth(){if(navigator.connection){var max=navigator.connection.downlinkMax;if(max&&max>0&&maxhttps://emby.media') + }).then(function() { + appRouter.showSelectServer() + }) + }) + } + } + + function loadContentUrl(ctx, next, route, request) { + var url; + url = route.contentPath && "function" == typeof route.contentPath ? route.contentPath(ctx.querystring) : route.contentPath || route.path, -1 === url.indexOf("://") && (0 !== url.indexOf("/") && (url = "/" + url), url = baseUrl() + url), ctx.querystring && route.enableContentQueryString && (url += "?" + ctx.querystring), require(["text!" + url], function(html) { + loadContent(ctx, route, html, request) + }) + } + + function handleRoute(ctx, next, route) { + authenticate(ctx, route, function() { + initRoute(ctx, next, route) + }) + } + + function initRoute(ctx, next, route) { + var onInitComplete = function(controllerFactory) { + sendRouteToViewManager(ctx, next, route, controllerFactory) + }; + require(route.dependencies || [], function() { + route.controller ? require([route.controller], onInitComplete) : onInitComplete() + }) + } + + function cancelCurrentLoadRequest() { + var currentRequest = currentViewLoadRequest; + currentRequest && (currentRequest.cancel = !0) + } + + function sendRouteToViewManager(ctx, next, route, controllerFactory) { + if (isDummyBackToHome && "home" === route.type) return void(isDummyBackToHome = !1); + cancelCurrentLoadRequest(); + var isBackNav = ctx.isBack, + currentRequest = { + url: baseUrl() + ctx.path, + transition: route.transition, + isBack: isBackNav, + state: ctx.state, + type: route.type, + fullscreen: route.fullscreen, + controllerFactory: controllerFactory, + options: { + supportsThemeMedia: route.supportsThemeMedia || !1, + enableMediaControl: !1 !== route.enableMediaControl + }, + autoFocus: route.autoFocus + }; + currentViewLoadRequest = currentRequest; + var onNewViewNeeded = function() { + "string" == typeof route.path ? loadContentUrl(ctx, next, route, currentRequest) : next() + }; + if (!isBackNav) return void onNewViewNeeded(); + viewManager.tryRestoreView(currentRequest, function() { + currentRouteInfo = { + route: route, + path: ctx.path + } + }).catch(function(result) { + result && result.cancelled || onNewViewNeeded() + }) + } + + function onForcedLogoutMessageTimeout() { + var msg = forcedLogoutMsg; + forcedLogoutMsg = null, msg && require(["alert"], function(alert) { + alert(msg) + }) + } + + function showForcedLogoutMessage(msg) { + forcedLogoutMsg = msg, msgTimeout && clearTimeout(msgTimeout), msgTimeout = setTimeout(onForcedLogoutMessageTimeout, 100) + } + + function onRequestFail(e, data) { + var apiClient = this; + if (401 === data.status && "ParentalControl" === data.errorCode) { + !currentRouteInfo || (currentRouteInfo.route.anonymous || currentRouteInfo.route.startup) || (showForcedLogoutMessage(globalize.translate("sharedcomponents#AccessRestrictedTryAgainLater")), connectionManager.isLoggedIntoConnect() ? appRouter.showConnectLogin() : appRouter.showLocalLogin(apiClient.serverId())) + } + } + + function onBeforeExit(e) { + browser.web0s && page.restorePreviousState() + } + + function normalizeImageOptions(options) { + var setQuality, scaleFactor = browser.tv ? .8 : 1; + if (options.maxWidth && (options.maxWidth = Math.round(options.maxWidth * scaleFactor), setQuality = !0), options.width && (options.width = Math.round(options.width * scaleFactor), setQuality = !0), options.maxHeight && (options.maxHeight = Math.round(options.maxHeight * scaleFactor), setQuality = !0), options.height && (options.height = Math.round(options.height * scaleFactor), setQuality = !0), setQuality) { + var quality = 100, + type = options.type || "Primary"; + quality = browser.tv || browser.slow ? browser.chrome ? "Primary" === type ? 40 : 50 : "Backdrop" === type ? 60 : 50 : "Backdrop" === type ? 70 : 90, options.quality = quality + } + } + + function getMaxBandwidth() { + if (navigator.connection) { + var max = navigator.connection.downlinkMax; + if (max && max > 0 && max < Number.POSITIVE_INFINITY) return max /= 8, max *= 1e6, max *= .7, max = parseInt(max) + } + return null + } + + function getMaxBandwidthIOS() { + return 8e5 + } + + function onApiClientCreated(e, newApiClient) { + newApiClient.normalizeImageOptions = normalizeImageOptions, browser.iOS ? newApiClient.getMaxBandwidth = getMaxBandwidthIOS : newApiClient.getMaxBandwidth = getMaxBandwidth, events.off(newApiClient, "requestfail", onRequestFail), events.on(newApiClient, "requestfail", onRequestFail) + } + + function initApiClient(apiClient) { + onApiClientCreated({}, apiClient) + } + + function initApiClients() { + connectionManager.getApiClients().forEach(initApiClient), events.on(connectionManager, "apiclientcreated", onApiClientCreated) + } + + function onAppResume() { + var apiClient = connectionManager.currentApiClient(); + apiClient && apiClient.ensureWebSocket() + } + + function start(options) { + loading.show(), initApiClients(), events.on(appHost, "beforeexit", onBeforeExit), events.on(appHost, "resume", onAppResume), connectionManager.connect({ + enableAutoLogin: appSettings.enableAutoLogin() + }).then(function(result) { + firstConnectionResult = result, loading.hide(), options = options || {}, page({ + click: !1 !== options.click, + hashbang: !1 !== options.hashbang, + enableHistory: enableHistory() + }) + }) + } + + function enableHistory() { + return !browser.xboxOne && !browser.orsay + } + + function enableNativeHistory() { + return page.enableNativeHistory() + } + + function authenticate(ctx, route, callback) { + var firstResult = firstConnectionResult; + if (firstResult && (firstConnectionResult = null, "SignedIn" !== firstResult.State && !route.anonymous)) return void handleConnectionResult(firstResult, loading); + var apiClient = connectionManager.currentApiClient(), + pathname = ctx.pathname.toLowerCase(); + console.log("appRouter - processing path request " + pathname); + var isCurrentRouteStartup = !currentRouteInfo || currentRouteInfo.route.startup, + shouldExitApp = ctx.isBack && route.isDefaultRoute && isCurrentRouteStartup; + if (!(shouldExitApp || apiClient && apiClient.isLoggedIn() || route.anonymous)) return console.log("appRouter - route does not allow anonymous access, redirecting to login"), void beginConnectionWizard(); + if (shouldExitApp) { + if (appHost.supports("exit")) return void appHost.exit() + } else { + if (apiClient && apiClient.isLoggedIn()) { + if (console.log("appRouter - user is authenticated"), ctx.isBack && (route.isDefaultRoute || route.startup) && !isCurrentRouteStartup) return void handleBackToDefault(); + if (route.isDefaultRoute) return console.log("appRouter - loading skin home page"), void loadUserSkinWithOptions(ctx); + if (route.roles) return void validateRoles(apiClient, route.roles).then(function() { + callback() + }, beginConnectionWizard) + } + console.log("appRouter - proceeding to " + pathname), callback() + } + } + + function loadUserSkinWithOptions(ctx) { + require(["queryString"], function(queryString) { + var params = queryString.parse(ctx.querystring); + skinManager.loadUserSkin({ + start: params.start + }) + }) + } + + function validateRoles(apiClient, roles) { + return Promise.all(roles.split(",").map(function(role) { + return validateRole(apiClient, role) + })) + } + + function validateRole(apiClient, role) { + return "admin" === role ? apiClient.getCurrentUser().then(function(user) { + return user.Policy.IsAdministrator ? Promise.resolve() : Promise.reject() + }) : Promise.resolve() + } + + function handleBackToDefault() { + if (!appHost.supports("exitmenu") && appHost.supports("exit")) return void appHost.exit(); + isDummyBackToHome = !0, skinManager.loadUserSkin(), isHandlingBackToDefault || skinManager.getCurrentSkin().showBackMenu().then(function() { + isHandlingBackToDefault = !1 + }) + } + + function loadContent(ctx, route, html, request) { + html = globalize.translateDocument(html, route.dictionary), request.view = html, viewManager.loadView(request), currentRouteInfo = { + route: route, + path: ctx.path + }, ctx.handled = !0 + } + + function getRequestFile() { + var path = self.location.pathname || "", + index = path.lastIndexOf("/"); + return path = -1 !== index ? path.substring(index) : "/" + path, path && "/" !== path || (path = "/index.html"), path + } + + function endsWith(str, srch) { + return str.lastIndexOf(srch) === srch.length - 1 + } + + function baseUrl() { + return baseRoute + } + + function getHandler(route) { + return function(ctx, next) { + handleRoute(ctx, next, route) + } + } + + function getWindowLocationSearch(win) { + var currentPath = currentRouteInfo ? currentRouteInfo.path || "" : "", + index = currentPath.indexOf("?"), + search = ""; + return -1 !== index && (search = currentPath.substring(index)), search || "" + } + + function param(name, url) { + name = name.replace(/[\[]/, "\\[").replace(/[\]]/, "\\]"); + var regexS = "[\\?&]" + name + "=([^&#]*)", + regex = new RegExp(regexS, "i"), + results = regex.exec(url || getWindowLocationSearch()); + return null == results ? "" : decodeURIComponent(results[1].replace(/\+/g, " ")) + } + + function back() { + page.back() + } + + function canGoBack() { + var curr = current(); + return !!curr && ("home" !== curr.type && page.canGoBack()) + } + + function show(path, options) { + 0 !== path.indexOf("/") && -1 === path.indexOf("://") && (path = "/" + path); + var baseRoute = baseUrl(); + return path = path.replace(baseRoute, ""), currentRouteInfo && currentRouteInfo.path === path && "home" !== currentRouteInfo.route.type ? (loading.hide(), Promise.resolve()) : new Promise(function(resolve, reject) { + resolveOnNextShow = resolve, page.show(path, options) + }) + } + + function current() { + return currentRouteInfo ? currentRouteInfo.route : null + } + + function goHome() { + var skin = skinManager.getCurrentSkin(); + if (skin.getHomeRoute) { + var homePath = skin.getHomeRoute(); + return show(pluginManager.mapRoute(skin, homePath)) + } + var homeRoute = skin.getRoutes().filter(function(r) { + return "home" === r.type + })[0]; + return show(pluginManager.mapRoute(skin, homeRoute)) + } + + function getRouteUrl(item, options) { + return "downloads" === item ? "offline/offline.html" : "managedownloads" === item ? "offline/managedownloads.html" : "settings" === item ? "settings/settings.html" : skinManager.getCurrentSkin().getRouteUrl(item, options) + } + + function showItem(item, serverId, options) { + if ("string" == typeof item) { + var apiClient = serverId ? connectionManager.getApiClient(serverId) : connectionManager.currentApiClient(); + apiClient.getItem(apiClient.getCurrentUserId(), item).then(function(item) { + appRouter.showItem(item, options) + }) + } else { + 2 === arguments.length && (options = arguments[1]); + var url = appRouter.getRouteUrl(item, options); + appRouter.show(url, { + item: item + }) + } + } + + function setTitle(title) { + skinManager.getCurrentSkin().setTitle(title) + } + + function showVideoOsd() { + var skin = skinManager.getCurrentSkin(), + homeRoute = skin.getRoutes().filter(function(r) { + return "video-osd" === r.type + })[0]; + return show(pluginManager.mapRoute(skin, homeRoute)) + } + + function addRoute(path, newRoute) { + page(path, getHandler(newRoute)), allRoutes.push(newRoute) + } + + function getRoutes() { + return allRoutes + } + + function setTransparency(level) { + backdropContainer || (backdropContainer = document.querySelector(".backdropContainer")), backgroundContainer || (backgroundContainer = document.querySelector(".backgroundContainer")), "full" === level || 2 === level ? (backdrop.clear(!0), document.documentElement.classList.add("transparentDocument"), backgroundContainer.classList.add("backgroundContainer-transparent"), backdropContainer.classList.add("hide")) : "backdrop" === level || 1 === level ? (backdrop.externalBackdrop(!0), document.documentElement.classList.add("transparentDocument"), backgroundContainer.classList.add("backgroundContainer-transparent"), backdropContainer.classList.add("hide")) : (backdrop.externalBackdrop(!1), document.documentElement.classList.remove("transparentDocument"), backgroundContainer.classList.remove("backgroundContainer-transparent"), backdropContainer.classList.remove("hide")) + } + + function pushState(state, title, url) { + state.navigate = !1, page.pushState(state, title, url) + } + + function invokeShortcut(id) { + 0 === id.indexOf("library-") ? (id = id.replace("library-", ""), id = id.split("_"), appRouter.showItem(id[0], id[1])) : 0 === id.indexOf("item-") ? (id = id.replace("item-", ""), id = id.split("_"), appRouter.showItem(id[0], id[1])) : (id = id.split("_"), appRouter.show(appRouter.getRouteUrl(id[0], { + serverId: id[1] + }))) + } + var currentViewLoadRequest, msgTimeout, forcedLogoutMsg, firstConnectionResult, isHandlingBackToDefault, isDummyBackToHome, appRouter = { + showLocalLogin: function(serverId, manualLogin) { + show("/startup/" + (manualLogin ? "manuallogin" : "login") + ".html?serverid=" + serverId) + }, + showSelectServer: function() { + show("/startup/selectserver.html") + }, + showWelcome: function() { + show("/startup/welcome.html") + }, + showConnectLogin: function() { + show("/startup/connectlogin.html") + }, + showSettings: function() { + show("/settings/settings.html") + }, + showSearch: function() { + skinManager.getCurrentSkin().search() + }, + showGenre: function(options) { + skinManager.getCurrentSkin().showGenre(options) + }, + showGuide: function() { + skinManager.getCurrentSkin().showGuide({ + serverId: connectionManager.currentApiClient().serverId() + }) + }, + showLiveTV: function() { + skinManager.getCurrentSkin().showLiveTV({ + serverId: connectionManager.currentApiClient().serverId() + }) + }, + showRecordedTV: function() { + skinManager.getCurrentSkin().showRecordedTV() + }, + showFavorites: function() { + skinManager.getCurrentSkin().showFavorites() + }, + showNowPlaying: function() { + skinManager.getCurrentSkin().showNowPlaying() + } + }, + baseRoute = self.location.href.split("?")[0].replace(getRequestFile(), ""); + baseRoute = baseRoute.split("#")[0], endsWith(baseRoute, "/") && !endsWith(baseRoute, "://") && (baseRoute = baseRoute.substring(0, baseRoute.length - 1)); + var resolveOnNextShow; + document.addEventListener("viewshow", function() { + var resolve = resolveOnNextShow; + resolve && (resolveOnNextShow = null, resolve()) + }); + var currentRouteInfo, backdropContainer, backgroundContainer, allRoutes = []; + return function() { + var baseRoute = self.location.pathname.replace(getRequestFile(), ""); + baseRoute.lastIndexOf("/") === baseRoute.length - 1 && (baseRoute = baseRoute.substring(0, baseRoute.length - 1)), console.log("Setting page base to " + baseRoute), page.base(baseRoute) + }(), appRouter.addRoute = addRoute, appRouter.param = param, appRouter.back = back, appRouter.show = show, appRouter.start = start, appRouter.baseUrl = baseUrl, appRouter.canGoBack = canGoBack, appRouter.current = current, appRouter.beginConnectionWizard = beginConnectionWizard, appRouter.goHome = goHome, appRouter.showItem = showItem, appRouter.setTitle = setTitle, appRouter.setTransparency = setTransparency, appRouter.getRoutes = getRoutes, appRouter.getRouteUrl = getRouteUrl, appRouter.pushState = pushState, appRouter.enableNativeHistory = enableNativeHistory, appRouter.showVideoOsd = showVideoOsd, appRouter.handleAnchorClick = page.handleAnchorClick, appRouter.TransparencyLevel = { + None: 0, + Backdrop: 1, + Full: 2 + }, appRouter.invokeShortcut = invokeShortcut, appRouter +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/sanitizefilename.js b/dashboard-ui/bower_components/emby-webcomponents/sanitizefilename.js index 08b4a82cbc..fc8e3a8a64 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/sanitizefilename.js +++ b/dashboard-ui/bower_components/emby-webcomponents/sanitizefilename.js @@ -1 +1,36 @@ -define([],function(){"use strict";function isHighSurrogate(codePoint){return codePoint>=55296&&codePoint<=56319}function isLowSurrogate(codePoint){return codePoint>=56320&&codePoint<=57343}function getByteLength(string){if("string"!=typeof string)throw new Error("Input must be string");for(var charLength=string.length,byteLength=0,codePoint=null,prevCodePoint=null,i=0;i=128&&codePoint<=2047?byteLength+=2:codePoint>=2048&&codePoint<=65535&&(byteLength+=3),prevCodePoint=codePoint;return byteLength}function truncate(string,byteLength){if("string"!=typeof string)throw new Error("Input must be string");for(var codePoint,segment,charLength=string.length,curByteLength=0,i=0;ibyteLength)return string.slice(0,i-segment.length+1)}return string}var illegalRe=/[\/\?<>\\:\*\|":]/g,controlRe=/[\x00-\x1f\x80-\x9f]/g,reservedRe=/^\.+$/,windowsReservedRe=/^(con|prn|aux|nul|com[0-9]|lpt[0-9])(\..*)?$/i,windowsTrailingRe=/[\. ]+$/;return{sanitize:function(input,replacement){return truncate(input.replace(illegalRe,replacement).replace(controlRe,replacement).replace(reservedRe,replacement).replace(windowsReservedRe,replacement).replace(windowsTrailingRe,replacement),255)}}}); \ No newline at end of file +define([], function() { + "use strict"; + + function isHighSurrogate(codePoint) { + return codePoint >= 55296 && codePoint <= 56319 + } + + function isLowSurrogate(codePoint) { + return codePoint >= 56320 && codePoint <= 57343 + } + + function getByteLength(string) { + if ("string" != typeof string) throw new Error("Input must be string"); + for (var charLength = string.length, byteLength = 0, codePoint = null, prevCodePoint = null, i = 0; i < charLength; i++) codePoint = string.charCodeAt(i), isLowSurrogate(codePoint) ? null != prevCodePoint && isHighSurrogate(prevCodePoint) ? byteLength += 1 : byteLength += 3 : codePoint <= 127 ? byteLength += 1 : codePoint >= 128 && codePoint <= 2047 ? byteLength += 2 : codePoint >= 2048 && codePoint <= 65535 && (byteLength += 3), prevCodePoint = codePoint; + return byteLength + } + + function truncate(string, byteLength) { + if ("string" != typeof string) throw new Error("Input must be string"); + for (var codePoint, segment, charLength = string.length, curByteLength = 0, i = 0; i < charLength; i += 1) { + if (codePoint = string.charCodeAt(i), segment = string[i], isHighSurrogate(codePoint) && isLowSurrogate(string.charCodeAt(i + 1)) && (i += 1, segment += string[i]), (curByteLength += getByteLength(segment)) === byteLength) return string.slice(0, i + 1); + if (curByteLength > byteLength) return string.slice(0, i - segment.length + 1) + } + return string + } + var illegalRe = /[\/\?<>\\:\*\|":]/g, + controlRe = /[\x00-\x1f\x80-\x9f]/g, + reservedRe = /^\.+$/, + windowsReservedRe = /^(con|prn|aux|nul|com[0-9]|lpt[0-9])(\..*)?$/i, + windowsTrailingRe = /[\. ]+$/; + return { + sanitize: function(input, replacement) { + return truncate(input.replace(illegalRe, replacement).replace(controlRe, replacement).replace(reservedRe, replacement).replace(windowsReservedRe, replacement).replace(windowsTrailingRe, replacement), 255) + } + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/scroller/smoothscroller.js b/dashboard-ui/bower_components/emby-webcomponents/scroller/smoothscroller.js index 2ab1136203..dabd776911 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/scroller/smoothscroller.js +++ b/dashboard-ui/bower_components/emby-webcomponents/scroller/smoothscroller.js @@ -1 +1,292 @@ -define(["browser","layoutManager","dom","focusManager","ResizeObserver","scrollStyles"],function(browser,layoutManager,dom,focusManager,ResizeObserver){"use strict";function type(value){return null==value?String(value):"object"==typeof value||"function"==typeof value?Object.prototype.toString.call(value).match(/\s([a-z]+)/i)[1].toLowerCase()||"object":typeof value}function disableOneEvent(event){event.preventDefault(),event.stopPropagation(),this.removeEventListener(event.type,disableOneEvent)}function within(number,min,max){return numbermax?max:number}var dragMouseEvents=["mousemove","mouseup"],dragTouchEvents=["touchmove","touchend"],wheelEvent=document.implementation.hasFeature("Event.wheel","3.0")?"wheel":"mousewheel",interactiveElements=["INPUT","SELECT","TEXTAREA"],abs=Math.abs,sqrt=Math.sqrt,pow=Math.pow,round=Math.round,max=Math.max,scrollerFactory=(Math.min,function(frame,options){function ensureSizeInfo(){requiresReflow&&(requiresReflow=!1,frameSize=o.horizontal?frame.offsetWidth:frame.offsetHeight,slideeSize=o.scrollWidth||Math.max(slideeElement[o.horizontal?"offsetWidth":"offsetHeight"],slideeElement[o.horizontal?"scrollWidth":"scrollHeight"]),self._pos.end=max(slideeSize-frameSize,0))}function load(isInit){if(requiresReflow=!0,!isInit){ensureSizeInfo();var pos=self._pos;self.slideTo(within(pos.dest,pos.start,pos.end))}}function initFrameResizeObserver(){var observerOptions={};self.frameResizeObserver=new ResizeObserver(onResize,observerOptions),self.frameResizeObserver.observe(frame)}function nativeScrollTo(container,pos,immediate){container.scroll?o.horizontal?container.scroll({left:pos,behavior:immediate?"instant":"smooth"}):container.scroll({top:pos,behavior:immediate?"instant":"smooth"}):!immediate&&container.scrollTo?o.horizontal?container.scrollTo(Math.round(pos),0):container.scrollTo(0,Math.round(pos)):o.horizontal?container.scrollLeft=Math.round(pos):container.scrollTop=Math.round(pos)}function setStyleProperty(elem,name,value,speed,resetTransition){var style=elem.style;(resetTransition||browser.edge)&&(style.transition="none",elem.offsetWidth),style.transition="transform "+speed+"ms ease-out",style[name]=value}function dispatchScrollEventIfNeeded(){o.dispatchScrollEvent&&frame.dispatchEvent(new CustomEvent(self.getScrollEventName(),{bubbles:!0,cancelable:!1}))}function renderAnimateWithTransform(fromPosition,toPosition,immediate){var speed=o.speed;immediate&&(speed=o.immediateSpeed||50),o.horizontal?setStyleProperty(slideeElement,"transform","translateX("+-round(toPosition)+"px)",speed):setStyleProperty(slideeElement,"transform","translateY("+-round(toPosition)+"px)",speed),self._pos.cur=toPosition,dispatchScrollEventIfNeeded()}function getBoundingClientRect(elem){return elem.getBoundingClientRect?elem.getBoundingClientRect():{top:0,left:0}}function dragInitSlidee(event){var isTouch="touchstart"===event.type;if(!(dragging.init||!isTouch&&isInteractive(event.target))&&(isTouch?o.touchDragging:o.mouseDragging&&event.which<2)){isTouch||event.preventDefault(),dragging.released=0,dragging.init=0,dragging.source=event.target,dragging.touch=isTouch;var pointer=isTouch?event.touches[0]:event;dragging.initX=pointer.pageX,dragging.initY=pointer.pageY,dragging.initPos=self._pos.cur,dragging.start=+new Date,dragging.time=0,dragging.path=0,dragging.delta=0,dragging.locked=0,dragging.pathToLock=isTouch?30:10,transform&&(isTouch?dragTouchEvents.forEach(function(eventName){dom.addEventListener(document,eventName,dragHandler,{passive:!0})}):dragMouseEvents.forEach(function(eventName){dom.addEventListener(document,eventName,dragHandler,{passive:!0})}))}}function dragHandler(event){dragging.released="mouseup"===event.type||"touchend"===event.type;var pointer=dragging.touch?event[dragging.released?"changedTouches":"touches"][0]:event;if(dragging.pathX=pointer.pageX-dragging.initX,dragging.pathY=pointer.pageY-dragging.initY,dragging.path=sqrt(pow(dragging.pathX,2)+pow(dragging.pathY,2)),dragging.delta=o.horizontal?dragging.pathX:dragging.pathY,dragging.released||!(dragging.path<1)){if(!dragging.init){if(dragging.pathabs(dragging.pathY):abs(dragging.pathX)dragging.pathToLock&&(dragging.locked=1,dragging.source.addEventListener("click",disableOneEvent)),dragging.released&&dragEnd(),self.slideTo(round(dragging.initPos-dragging.delta))}}function dragEnd(){dragging.released=!0,dragTouchEvents.forEach(function(eventName){dom.removeEventListener(document,eventName,dragHandler,{passive:!0})}),dragMouseEvents.forEach(function(eventName){dom.removeEventListener(document,eventName,dragHandler,{passive:!0})}),setTimeout(function(){dragging.source.removeEventListener("click",disableOneEvent)}),dragging.init=0}function isInteractive(element){for(;element;){if(-1!==interactiveElements.indexOf(element.tagName))return!0;element=element.parentNode}return!1}function normalizeWheelDelta(event){return scrolling.curDelta=(o.horizontal?event.deltaY||event.deltaX:event.deltaY)||-event.wheelDelta,transform&&(scrolling.curDelta/=1===event.deltaMode?3:100),scrolling.curDelta}function scrollHandler(event){ensureSizeInfo();var pos=self._pos;if(o.scrollBy&&pos.start!==pos.end){var delta=normalizeWheelDelta(event);transform?(delta>0&&pos.dest=currentStart&&offset+size<=currentEnd}},self.getCenterPosition=function(item){ensureSizeInfo();var pos=self.getPos(item);return within(pos.center,pos.start,pos.end)},self.destroy=function(){return self.frameResizeObserver&&(self.frameResizeObserver.disconnect(),self.frameResizeObserver=null),dom.removeEventListener(frame,"scroll",resetScroll,{passive:!0}),dom.removeEventListener(scrollSource,wheelEvent,scrollHandler,{passive:!0}),dom.removeEventListener(dragSourceElement,"touchstart",dragInitSlidee,{passive:!0}),dom.removeEventListener(frame,"click",onFrameClick,{passive:!0,capture:!0}),dom.removeEventListener(dragSourceElement,"mousedown",dragInitSlidee,{}),self.initialized=0,self};var contentRect={};self.getScrollPosition=function(){return transform?self._pos.cur:o.horizontal?nativeScrollElement.scrollLeft:nativeScrollElement.scrollTop},self.getScrollSize=function(){return transform?slideeSize:o.horizontal?nativeScrollElement.scrollWidth:nativeScrollElement.scrollHeight},self.init=function(){if(!self.initialized)return transform?(frame.style.overflow="hidden",slideeElement.style["will-change"]="transform",slideeElement.style.transition="transform "+o.speed+"ms ease-out",o.horizontal?slideeElement.classList.add("animatedScrollX"):slideeElement.classList.add("animatedScrollY")):o.horizontal?(layoutManager.desktop&&!o.hideScrollbar?nativeScrollElement.classList.add("scrollX"):(nativeScrollElement.classList.add("scrollX"),nativeScrollElement.classList.add("hiddenScrollX"),layoutManager.tv&&!1!==o.allowNativeSmoothScroll&&nativeScrollElement.classList.add("smoothScrollX")),o.forceHideScrollbars&&nativeScrollElement.classList.add("hiddenScrollX-forced")):(layoutManager.desktop&&!o.hideScrollbar?nativeScrollElement.classList.add("scrollY"):(nativeScrollElement.classList.add("scrollY"),nativeScrollElement.classList.add("hiddenScrollY"),layoutManager.tv&&!1!==o.allowNativeSmoothScroll&&nativeScrollElement.classList.add("smoothScrollY")),o.forceHideScrollbars&&nativeScrollElement.classList.add("hiddenScrollY-forced")),(transform||layoutManager.tv)&&dom.addEventListener(dragSourceElement,"mousedown",dragInitSlidee,{}),initFrameResizeObserver(),transform?(dom.addEventListener(dragSourceElement,"touchstart",dragInitSlidee,{passive:!0}),o.horizontal||dom.addEventListener(frame,"scroll",resetScroll,{passive:!0}),o.mouseWheel&&dom.addEventListener(scrollSource,wheelEvent,scrollHandler,{passive:!0})):o.horizontal&&o.mouseWheel&&dom.addEventListener(scrollSource,wheelEvent,scrollHandler,{passive:!0}),dom.addEventListener(frame,"click",onFrameClick,{passive:!0,capture:!0}),self.initialized=1,load(!0),self}});return scrollerFactory.prototype.slideBy=function(delta,immediate){delta&&this.slideTo(this._pos.dest+delta,immediate)},scrollerFactory.prototype.to=function(location,item,immediate){if("boolean"===type(item)&&(immediate=item,item=void 0),void 0===item)this.slideTo(this._pos[location],immediate);else{var itemPos=this.getPos(item);itemPos&&this.slideTo(itemPos[location],immediate,itemPos)}},scrollerFactory.prototype.toStart=function(item,immediate){this.to("start",item,immediate)},scrollerFactory.prototype.toEnd=function(item,immediate){this.to("end",item,immediate)},scrollerFactory.prototype.toCenter=function(item,immediate){this.to("center",item,immediate)},scrollerFactory.create=function(frame,options){var instance=new scrollerFactory(frame,options);return Promise.resolve(instance)},scrollerFactory}); \ No newline at end of file +define(["browser", "layoutManager", "dom", "focusManager", "ResizeObserver", "scrollStyles"], function(browser, layoutManager, dom, focusManager, ResizeObserver) { + "use strict"; + + function type(value) { + return null == value ? String(value) : "object" == typeof value || "function" == typeof value ? Object.prototype.toString.call(value).match(/\s([a-z]+)/i)[1].toLowerCase() || "object" : typeof value + } + + function disableOneEvent(event) { + event.preventDefault(), event.stopPropagation(), this.removeEventListener(event.type, disableOneEvent) + } + + function within(number, min, max) { + return number < min ? min : number > max ? max : number + } + var dragMouseEvents = ["mousemove", "mouseup"], + dragTouchEvents = ["touchmove", "touchend"], + wheelEvent = document.implementation.hasFeature("Event.wheel", "3.0") ? "wheel" : "mousewheel", + interactiveElements = ["INPUT", "SELECT", "TEXTAREA"], + abs = Math.abs, + sqrt = Math.sqrt, + pow = Math.pow, + round = Math.round, + max = Math.max, + scrollerFactory = (Math.min, function(frame, options) { + function ensureSizeInfo() { + requiresReflow && (requiresReflow = !1, frameSize = o.horizontal ? frame.offsetWidth : frame.offsetHeight, slideeSize = o.scrollWidth || Math.max(slideeElement[o.horizontal ? "offsetWidth" : "offsetHeight"], slideeElement[o.horizontal ? "scrollWidth" : "scrollHeight"]), self._pos.end = max(slideeSize - frameSize, 0)) + } + + function load(isInit) { + if (requiresReflow = !0, !isInit) { + ensureSizeInfo(); + var pos = self._pos; + self.slideTo(within(pos.dest, pos.start, pos.end)) + } + } + + function initFrameResizeObserver() { + var observerOptions = {}; + self.frameResizeObserver = new ResizeObserver(onResize, observerOptions), self.frameResizeObserver.observe(frame) + } + + function nativeScrollTo(container, pos, immediate) { + container.scroll ? o.horizontal ? container.scroll({ + left: pos, + behavior: immediate ? "instant" : "smooth" + }) : container.scroll({ + top: pos, + behavior: immediate ? "instant" : "smooth" + }) : !immediate && container.scrollTo ? o.horizontal ? container.scrollTo(Math.round(pos), 0) : container.scrollTo(0, Math.round(pos)) : o.horizontal ? container.scrollLeft = Math.round(pos) : container.scrollTop = Math.round(pos) + } + + function setStyleProperty(elem, name, value, speed, resetTransition) { + var style = elem.style; + (resetTransition || browser.edge) && (style.transition = "none", elem.offsetWidth), style.transition = "transform " + speed + "ms ease-out", style[name] = value + } + + function dispatchScrollEventIfNeeded() { + o.dispatchScrollEvent && frame.dispatchEvent(new CustomEvent(self.getScrollEventName(), { + bubbles: !0, + cancelable: !1 + })) + } + + function renderAnimateWithTransform(fromPosition, toPosition, immediate) { + var speed = o.speed; + immediate && (speed = o.immediateSpeed || 50), o.horizontal ? setStyleProperty(slideeElement, "transform", "translateX(" + -round(toPosition) + "px)", speed) : setStyleProperty(slideeElement, "transform", "translateY(" + -round(toPosition) + "px)", speed), self._pos.cur = toPosition, dispatchScrollEventIfNeeded() + } + + function getBoundingClientRect(elem) { + return elem.getBoundingClientRect ? elem.getBoundingClientRect() : { + top: 0, + left: 0 + } + } + + function dragInitSlidee(event) { + var isTouch = "touchstart" === event.type; + if (!(dragging.init || !isTouch && isInteractive(event.target)) && (isTouch ? o.touchDragging : o.mouseDragging && event.which < 2)) { + isTouch || event.preventDefault(), dragging.released = 0, dragging.init = 0, dragging.source = event.target, dragging.touch = isTouch; + var pointer = isTouch ? event.touches[0] : event; + dragging.initX = pointer.pageX, dragging.initY = pointer.pageY, dragging.initPos = self._pos.cur, dragging.start = +new Date, dragging.time = 0, dragging.path = 0, dragging.delta = 0, dragging.locked = 0, dragging.pathToLock = isTouch ? 30 : 10, transform && (isTouch ? dragTouchEvents.forEach(function(eventName) { + dom.addEventListener(document, eventName, dragHandler, { + passive: !0 + }) + }) : dragMouseEvents.forEach(function(eventName) { + dom.addEventListener(document, eventName, dragHandler, { + passive: !0 + }) + })) + } + } + + function dragHandler(event) { + dragging.released = "mouseup" === event.type || "touchend" === event.type; + var pointer = dragging.touch ? event[dragging.released ? "changedTouches" : "touches"][0] : event; + if (dragging.pathX = pointer.pageX - dragging.initX, dragging.pathY = pointer.pageY - dragging.initY, dragging.path = sqrt(pow(dragging.pathX, 2) + pow(dragging.pathY, 2)), dragging.delta = o.horizontal ? dragging.pathX : dragging.pathY, dragging.released || !(dragging.path < 1)) { + if (!dragging.init) { + if (dragging.path < o.dragThreshold) return dragging.released ? dragEnd() : void 0; + if (!(o.horizontal ? abs(dragging.pathX) > abs(dragging.pathY) : abs(dragging.pathX) < abs(dragging.pathY))) return dragEnd(); + dragging.init = 1 + }!dragging.locked && dragging.path > dragging.pathToLock && (dragging.locked = 1, dragging.source.addEventListener("click", disableOneEvent)), dragging.released && dragEnd(), self.slideTo(round(dragging.initPos - dragging.delta)) + } + } + + function dragEnd() { + dragging.released = !0, dragTouchEvents.forEach(function(eventName) { + dom.removeEventListener(document, eventName, dragHandler, { + passive: !0 + }) + }), dragMouseEvents.forEach(function(eventName) { + dom.removeEventListener(document, eventName, dragHandler, { + passive: !0 + }) + }), setTimeout(function() { + dragging.source.removeEventListener("click", disableOneEvent) + }), dragging.init = 0 + } + + function isInteractive(element) { + for (; element;) { + if (-1 !== interactiveElements.indexOf(element.tagName)) return !0; + element = element.parentNode + } + return !1 + } + + function normalizeWheelDelta(event) { + return scrolling.curDelta = (o.horizontal ? event.deltaY || event.deltaX : event.deltaY) || -event.wheelDelta, transform && (scrolling.curDelta /= 1 === event.deltaMode ? 3 : 100), scrolling.curDelta + } + + function scrollHandler(event) { + ensureSizeInfo(); + var pos = self._pos; + if (o.scrollBy && pos.start !== pos.end) { + var delta = normalizeWheelDelta(event); + transform ? (delta > 0 && pos.dest < pos.end || delta < 0 && (pos.dest, pos.start), self.slideBy(o.scrollBy * delta)) : (isSmoothScrollSupported && (delta *= 12), o.horizontal ? nativeScrollElement.scrollLeft += delta : nativeScrollElement.scrollTop += delta) + } + } + + function onResize(entries) { + var entry = entries[0]; + if (entry) { + var newRect = entry.contentRect; + if (0 === newRect.width || 0 === newRect.height) return; + newRect.width === contentRect.width && newRect.height === contentRect.height || (contentRect = newRect, load(!1)) + } + } + + function resetScroll() { + o.horizontal ? this.scrollLeft = 0 : this.scrollTop = 0 + } + + function onFrameClick(e) { + if (1 === e.which) { + var focusableParent = focusManager.focusableParent(e.target); + focusableParent && focusableParent !== document.activeElement && focusableParent.focus() + } + } + var o = Object.assign({}, { + slidee: null, + horizontal: !1, + mouseWheel: !0, + scrollBy: 0, + dragSource: null, + mouseDragging: 1, + touchDragging: 1, + dragThreshold: 3, + intervactive: null, + speed: 0 + }, options), + isSmoothScrollSupported = "scrollBehavior" in document.documentElement.style; + !1 === options.allowNativeScroll ? options.enableNativeScroll = !1 : isSmoothScrollSupported && (browser.firefox && !layoutManager.tv || options.allowNativeSmoothScroll) ? options.enableNativeScroll = !0 : options.requireAnimation && (browser.animate || browser.supportsCssAnimation()) ? options.enableNativeScroll = !1 : layoutManager.tv && browser.animate || (options.enableNativeScroll = !0), browser.web0s && (options.enableNativeScroll = !0); + var self = this; + self.options = o; + var slideeElement = o.slidee ? o.slidee : function(n, elem) { + for (var matched = []; n; n = n.nextSibling) 1 === n.nodeType && n !== elem && matched.push(n); + return matched + }(frame.firstChild)[0]; + self._pos = { + start: 0, + center: 0, + end: 0, + cur: 0, + dest: 0 + }; + var transform = !options.enableNativeScroll, + scrollSource = frame, + dragSourceElement = o.dragSource ? o.dragSource : frame, + dragging = { + released: 1 + }, + scrolling = { + last: 0, + delta: 0, + resetTime: 200 + }; + self.initialized = 0, self.slidee = slideeElement, self.options = o, self.dragging = dragging; + var nativeScrollElement = frame, + requiresReflow = !0, + frameSize = 0, + slideeSize = 0; + self.reload = function() { + load() + }, self.getScrollEventName = function() { + return transform ? "scrollanimate" : "scroll" + }, self.getScrollSlider = function() { + return slideeElement + }, self.getScrollFrame = function() { + return frame + }; + var lastAnimate; + self.slideTo = function(newPos, immediate, fullItemPos) { + ensureSizeInfo(); + var pos = self._pos; + if (newPos = within(newPos, pos.start, pos.end), !transform) return void nativeScrollTo(nativeScrollElement, newPos, immediate); + var from = pos.cur; + immediate = immediate || dragging.init || !o.speed; + var now = (new Date).getTime(); + o.autoImmediate && !immediate && now - (lastAnimate || 0) <= 50 && (immediate = !0), !immediate && o.skipSlideToWhenVisible && fullItemPos && fullItemPos.isVisible || newPos !== pos.dest && (pos.dest = newPos, renderAnimateWithTransform(from, newPos, immediate), lastAnimate = now) + }, self.getPos = function(item) { + var scrollElement = transform ? slideeElement : nativeScrollElement, + slideeOffset = getBoundingClientRect(scrollElement), + itemOffset = getBoundingClientRect(item), + offset = (o.horizontal ? slideeOffset.left : slideeOffset.top, o.horizontal ? slideeOffset.right : slideeOffset.bottom, o.horizontal ? itemOffset.left - slideeOffset.left : itemOffset.top - slideeOffset.top), + size = o.horizontal ? itemOffset.width : itemOffset.height; + size || 0 === size || (size = item[o.horizontal ? "offsetWidth" : "offsetHeight"]); + var centerOffset = o.centerOffset || 0; + transform || (centerOffset = 0, o.horizontal ? offset += nativeScrollElement.scrollLeft : offset += nativeScrollElement.scrollTop), ensureSizeInfo(); + var currentStart = self._pos.cur, + currentEnd = currentStart + frameSize; + return { + start: offset, + center: offset + centerOffset - frameSize / 2 + size / 2, + end: offset - frameSize + size, + size: size, + isVisible: offset >= currentStart && offset + size <= currentEnd + } + }, self.getCenterPosition = function(item) { + ensureSizeInfo(); + var pos = self.getPos(item); + return within(pos.center, pos.start, pos.end) + }, self.destroy = function() { + return self.frameResizeObserver && (self.frameResizeObserver.disconnect(), self.frameResizeObserver = null), dom.removeEventListener(frame, "scroll", resetScroll, { + passive: !0 + }), dom.removeEventListener(scrollSource, wheelEvent, scrollHandler, { + passive: !0 + }), dom.removeEventListener(dragSourceElement, "touchstart", dragInitSlidee, { + passive: !0 + }), dom.removeEventListener(frame, "click", onFrameClick, { + passive: !0, + capture: !0 + }), dom.removeEventListener(dragSourceElement, "mousedown", dragInitSlidee, {}), self.initialized = 0, self + }; + var contentRect = {}; + self.getScrollPosition = function() { + return transform ? self._pos.cur : o.horizontal ? nativeScrollElement.scrollLeft : nativeScrollElement.scrollTop + }, self.getScrollSize = function() { + return transform ? slideeSize : o.horizontal ? nativeScrollElement.scrollWidth : nativeScrollElement.scrollHeight + }, self.init = function() { + if (!self.initialized) return transform ? (frame.style.overflow = "hidden", slideeElement.style["will-change"] = "transform", slideeElement.style.transition = "transform " + o.speed + "ms ease-out", o.horizontal ? slideeElement.classList.add("animatedScrollX") : slideeElement.classList.add("animatedScrollY")) : o.horizontal ? (layoutManager.desktop && !o.hideScrollbar ? nativeScrollElement.classList.add("scrollX") : (nativeScrollElement.classList.add("scrollX"), nativeScrollElement.classList.add("hiddenScrollX"), layoutManager.tv && !1 !== o.allowNativeSmoothScroll && nativeScrollElement.classList.add("smoothScrollX")), o.forceHideScrollbars && nativeScrollElement.classList.add("hiddenScrollX-forced")) : (layoutManager.desktop && !o.hideScrollbar ? nativeScrollElement.classList.add("scrollY") : (nativeScrollElement.classList.add("scrollY"), nativeScrollElement.classList.add("hiddenScrollY"), layoutManager.tv && !1 !== o.allowNativeSmoothScroll && nativeScrollElement.classList.add("smoothScrollY")), o.forceHideScrollbars && nativeScrollElement.classList.add("hiddenScrollY-forced")), (transform || layoutManager.tv) && dom.addEventListener(dragSourceElement, "mousedown", dragInitSlidee, {}), initFrameResizeObserver(), transform ? (dom.addEventListener(dragSourceElement, "touchstart", dragInitSlidee, { + passive: !0 + }), o.horizontal || dom.addEventListener(frame, "scroll", resetScroll, { + passive: !0 + }), o.mouseWheel && dom.addEventListener(scrollSource, wheelEvent, scrollHandler, { + passive: !0 + })) : o.horizontal && o.mouseWheel && dom.addEventListener(scrollSource, wheelEvent, scrollHandler, { + passive: !0 + }), dom.addEventListener(frame, "click", onFrameClick, { + passive: !0, + capture: !0 + }), self.initialized = 1, load(!0), self + } + }); + return scrollerFactory.prototype.slideBy = function(delta, immediate) { + delta && this.slideTo(this._pos.dest + delta, immediate) + }, scrollerFactory.prototype.to = function(location, item, immediate) { + if ("boolean" === type(item) && (immediate = item, item = void 0), void 0 === item) this.slideTo(this._pos[location], immediate); + else { + var itemPos = this.getPos(item); + itemPos && this.slideTo(itemPos[location], immediate, itemPos) + } + }, scrollerFactory.prototype.toStart = function(item, immediate) { + this.to("start", item, immediate) + }, scrollerFactory.prototype.toEnd = function(item, immediate) { + this.to("end", item, immediate) + }, scrollerFactory.prototype.toCenter = function(item, immediate) { + this.to("center", item, immediate) + }, scrollerFactory.create = function(frame, options) { + var instance = new scrollerFactory(frame, options); + return Promise.resolve(instance) + }, scrollerFactory +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/scrollhelper.js b/dashboard-ui/bower_components/emby-webcomponents/scrollhelper.js index 6e397f060f..4ae5262ec4 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/scrollhelper.js +++ b/dashboard-ui/bower_components/emby-webcomponents/scrollhelper.js @@ -1 +1,77 @@ -define(["focusManager","dom","scrollStyles"],function(focusManager,dom){"use strict";function getBoundingClientRect(elem){return elem.getBoundingClientRect?elem.getBoundingClientRect():{top:0,left:0}}function getPosition(scrollContainer,item,horizontal){var slideeOffset=getBoundingClientRect(scrollContainer),itemOffset=getBoundingClientRect(item),offset=horizontal?itemOffset.left-slideeOffset.left:itemOffset.top-slideeOffset.top,size=horizontal?itemOffset.width:itemOffset.height;size||0===size||(size=item[horizontal?"offsetWidth":"offsetHeight"]);var currentStart=horizontal?scrollContainer.scrollLeft:scrollContainer.scrollTop;offset+=currentStart;var frameSize=horizontal?scrollContainer.offsetWidth:scrollContainer.offsetHeight,currentEnd=currentStart+frameSize;return{start:offset,center:offset-frameSize/2+size/2,end:offset-frameSize+size,size:size,isVisible:offset>=currentStart&&offset+size<=currentEnd}}function toCenter(container,elem,horizontal,skipWhenVisible){var pos=getPosition(container,elem,horizontal);skipWhenVisible&&pos.isVisible||(container.scrollTo?horizontal?container.scrollTo(pos.center,0):container.scrollTo(0,pos.center):horizontal?container.scrollLeft=Math.round(pos.center):container.scrollTop=Math.round(pos.center))}function toStart(container,elem,horizontal,skipWhenVisible){var pos=getPosition(container,elem,horizontal);skipWhenVisible&&pos.isVisible||(container.scrollTo?horizontal?container.scrollTo(pos.start,0):container.scrollTo(0,pos.start):horizontal?container.scrollLeft=Math.round(pos.start):container.scrollTop=Math.round(pos.start))}function centerOnFocus(e,scrollSlider,horizontal){var focused=focusManager.focusableParent(e.target);focused&&toCenter(scrollSlider,focused,horizontal)}function centerOnFocusHorizontal(e){centerOnFocus(e,this,!0)}function centerOnFocusVertical(e){centerOnFocus(e,this,!1)}return{getPosition:getPosition,centerFocus:{on:function(element,horizontal){horizontal?dom.addEventListener(element,"focus",centerOnFocusHorizontal,{capture:!0,passive:!0}):dom.addEventListener(element,"focus",centerOnFocusVertical,{capture:!0,passive:!0})},off:function(element,horizontal){horizontal?dom.removeEventListener(element,"focus",centerOnFocusHorizontal,{capture:!0,passive:!0}):dom.removeEventListener(element,"focus",centerOnFocusVertical,{capture:!0,passive:!0})}},toCenter:toCenter,toStart:toStart}}); \ No newline at end of file +define(["focusManager", "dom", "scrollStyles"], function(focusManager, dom) { + "use strict"; + + function getBoundingClientRect(elem) { + return elem.getBoundingClientRect ? elem.getBoundingClientRect() : { + top: 0, + left: 0 + } + } + + function getPosition(scrollContainer, item, horizontal) { + var slideeOffset = getBoundingClientRect(scrollContainer), + itemOffset = getBoundingClientRect(item), + offset = horizontal ? itemOffset.left - slideeOffset.left : itemOffset.top - slideeOffset.top, + size = horizontal ? itemOffset.width : itemOffset.height; + size || 0 === size || (size = item[horizontal ? "offsetWidth" : "offsetHeight"]); + var currentStart = horizontal ? scrollContainer.scrollLeft : scrollContainer.scrollTop; + offset += currentStart; + var frameSize = horizontal ? scrollContainer.offsetWidth : scrollContainer.offsetHeight, + currentEnd = currentStart + frameSize; + return { + start: offset, + center: offset - frameSize / 2 + size / 2, + end: offset - frameSize + size, + size: size, + isVisible: offset >= currentStart && offset + size <= currentEnd + } + } + + function toCenter(container, elem, horizontal, skipWhenVisible) { + var pos = getPosition(container, elem, horizontal); + skipWhenVisible && pos.isVisible || (container.scrollTo ? horizontal ? container.scrollTo(pos.center, 0) : container.scrollTo(0, pos.center) : horizontal ? container.scrollLeft = Math.round(pos.center) : container.scrollTop = Math.round(pos.center)) + } + + function toStart(container, elem, horizontal, skipWhenVisible) { + var pos = getPosition(container, elem, horizontal); + skipWhenVisible && pos.isVisible || (container.scrollTo ? horizontal ? container.scrollTo(pos.start, 0) : container.scrollTo(0, pos.start) : horizontal ? container.scrollLeft = Math.round(pos.start) : container.scrollTop = Math.round(pos.start)) + } + + function centerOnFocus(e, scrollSlider, horizontal) { + var focused = focusManager.focusableParent(e.target); + focused && toCenter(scrollSlider, focused, horizontal) + } + + function centerOnFocusHorizontal(e) { + centerOnFocus(e, this, !0) + } + + function centerOnFocusVertical(e) { + centerOnFocus(e, this, !1) + } + return { + getPosition: getPosition, + centerFocus: { + on: function(element, horizontal) { + horizontal ? dom.addEventListener(element, "focus", centerOnFocusHorizontal, { + capture: !0, + passive: !0 + }) : dom.addEventListener(element, "focus", centerOnFocusVertical, { + capture: !0, + passive: !0 + }) + }, + off: function(element, horizontal) { + horizontal ? dom.removeEventListener(element, "focus", centerOnFocusHorizontal, { + capture: !0, + passive: !0 + }) : dom.removeEventListener(element, "focus", centerOnFocusVertical, { + capture: !0, + passive: !0 + }) + } + }, + toCenter: toCenter, + toStart: toStart + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/search/searchfields.js b/dashboard-ui/bower_components/emby-webcomponents/search/searchfields.js index 2af72fd678..e52fd7ef24 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/search/searchfields.js +++ b/dashboard-ui/bower_components/emby-webcomponents/search/searchfields.js @@ -1 +1,64 @@ -define(["layoutManager","globalize","require","events","browser","alphaPicker","emby-input","flexStyles","material-icons","css!./searchfields"],function(layoutManager,globalize,require,events,browser,AlphaPicker){"use strict";function onSearchTimeout(){var instance=this,value=instance.nextSearchValue;value=(value||"").trim(),events.trigger(instance,"search",[value])}function triggerSearch(instance,value){instance.searchTimeout&&clearTimeout(instance.searchTimeout),instance.nextSearchValue=value,instance.searchTimeout=setTimeout(onSearchTimeout.bind(instance),400)}function onAlphaValueClicked(e){var value=e.detail.value,searchFieldsInstance=this,txtSearch=searchFieldsInstance.options.element.querySelector(".searchfields-txtSearch");if("backspace"===value){var val=txtSearch.value;txtSearch.value=val.length?val.substring(0,val.length-1):""}else txtSearch.value+=value;txtSearch.dispatchEvent(new CustomEvent("input",{bubbles:!0}))}function initAlphaPicker(alphaPickerElement,instance){instance.alphaPicker=new AlphaPicker({element:alphaPickerElement,mode:"keyboard"}),alphaPickerElement.addEventListener("alphavalueclicked",onAlphaValueClicked.bind(instance))}function onSearchInput(e){triggerSearch(this,e.target.value)}function embed(elem,instance,options){require(["text!./searchfields.template.html"],function(template){var html=globalize.translateDocument(template,"sharedcomponents");(browser.tizen||browser.orsay)&&(html=html.replace("';return itemHtml+=i.Name,itemHtml+="
    "}).join(""),searchSuggestions=context.querySelector(".searchSuggestions");searchSuggestions.querySelector(".searchSuggestionsList").innerHTML=html,result.Items.length&&searchSuggestions.classList.remove("hide")})}function getSearchHints(instance,apiClient,query){if(!query.searchTerm)return Promise.resolve({SearchHints:[]});var allowSearch=!0,queryIncludeItemTypes=query.IncludeItemTypes;if("tvshows"===instance.options.collectionType?query.IncludeArtists?allowSearch=!1:"Movie"!==queryIncludeItemTypes&&"LiveTvProgram"!==queryIncludeItemTypes&&"MusicAlbum"!==queryIncludeItemTypes&&"Audio"!==queryIncludeItemTypes&&"Book"!==queryIncludeItemTypes&&"AudioBook"!==queryIncludeItemTypes&&"Playlist"!==queryIncludeItemTypes&&"PhotoAlbum"!==queryIncludeItemTypes&&"Video"!==query.MediaTypes&&"Photo"!==query.MediaTypes||(allowSearch=!1):"movies"===instance.options.collectionType?query.IncludeArtists?allowSearch=!1:"Series"!==queryIncludeItemTypes&&"Episode"!==queryIncludeItemTypes&&"LiveTvProgram"!==queryIncludeItemTypes&&"MusicAlbum"!==queryIncludeItemTypes&&"Audio"!==queryIncludeItemTypes&&"Book"!==queryIncludeItemTypes&&"AudioBook"!==queryIncludeItemTypes&&"Playlist"!==queryIncludeItemTypes&&"PhotoAlbum"!==queryIncludeItemTypes&&"Video"!==query.MediaTypes&&"Photo"!==query.MediaTypes||(allowSearch=!1):"music"===instance.options.collectionType?query.People?allowSearch=!1:"Series"!==queryIncludeItemTypes&&"Episode"!==queryIncludeItemTypes&&"LiveTvProgram"!==queryIncludeItemTypes&&"Movie"!==queryIncludeItemTypes||(allowSearch=!1):"livetv"===instance.options.collectionType&&(query.IncludeArtists||query.IncludePeople?allowSearch=!1:"Series"!==queryIncludeItemTypes&&"Episode"!==queryIncludeItemTypes&&"MusicAlbum"!==queryIncludeItemTypes&&"Audio"!==queryIncludeItemTypes&&"Book"!==queryIncludeItemTypes&&"AudioBook"!==queryIncludeItemTypes&&"PhotoAlbum"!==queryIncludeItemTypes&&"Movie"!==queryIncludeItemTypes&&"Video"!==query.MediaTypes&&"Photo"!==query.MediaTypes||(allowSearch=!1)),"NullType"===queryIncludeItemTypes&&(allowSearch=!1),!allowSearch)return Promise.resolve({SearchHints:[]});if(apiClient.isMinServerVersion("3.4.1.31")){query.Fields="PrimaryImageAspectRatio,CanDelete,BasicSyncInfo,MediaSourceCount",query.Recursive=!0,query.EnableTotalRecordCount=!1,query.ImageTypeLimit=1;var methodName="getItems";return query.IncludeMedia||(query.IncludePeople?methodName="getPeople":query.IncludeArtists&&(methodName="getArtists")),apiClient[methodName](apiClient.getCurrentUserId(),query)}return query.UserId=apiClient.getCurrentUserId(),apiClient.getSearchHints(query)}function search(instance,apiClient,context,value){value||layoutManager.tv?(instance.mode="search",context.querySelector(".searchSuggestions").classList.add("hide")):(instance.mode="suggestions",loadSuggestions(instance,context,apiClient)),"livetv"===instance.options.collectionType?searchType(instance,apiClient,{searchTerm:value,IncludePeople:!1,IncludeMedia:!0,IncludeGenres:!1,IncludeStudios:!1,IncludeArtists:!1,IncludeItemTypes:"LiveTvProgram",IsMovie:!0,IsKids:!1,IsNews:!1},context,".movieResults",{preferThumb:!0,inheritThumb:!1,shape:enableScrollX()?"overflowPortrait":"portrait",showParentTitleOrTitle:!0,showTitle:!1,centerText:!0,coverImage:!0,overlayText:!1,overlayMoreButton:!0,showAirTime:!0,showAirDateTime:!0,showChannelName:!0}):searchType(instance,apiClient,{searchTerm:value,IncludePeople:!1,IncludeMedia:!0,IncludeGenres:!1,IncludeStudios:!1,IncludeArtists:!1,IncludeItemTypes:"Movie"},context,".movieResults",{showTitle:!0,overlayText:!1,centerText:!0,showYear:!0}),searchType(instance,apiClient,{searchTerm:value,IncludePeople:!1,IncludeMedia:!0,IncludeGenres:!1,IncludeStudios:!1,IncludeArtists:!1,IncludeItemTypes:"Series"},context,".seriesResults",{showTitle:!0,overlayText:!1,centerText:!0,showYear:!0}),"livetv"===instance.options.collectionType?searchType(instance,apiClient,{searchTerm:value,IncludePeople:!1,IncludeMedia:!0,IncludeGenres:!1,IncludeStudios:!1,IncludeArtists:!1,IncludeItemTypes:"LiveTvProgram",IsSeries:!0,IsSports:!1,IsKids:!1,IsNews:!1},context,".episodeResults",{preferThumb:!0,inheritThumb:!1,shape:enableScrollX()?"overflowBackdrop":"backdrop",showParentTitleOrTitle:!0,showTitle:!1,centerText:!0,coverImage:!0,overlayText:!1,overlayMoreButton:!0,showAirTime:!0,showAirDateTime:!0,showChannelName:!0}):searchType(instance,apiClient,{searchTerm:value,IncludePeople:!1,IncludeMedia:!0,IncludeGenres:!1,IncludeStudios:!1,IncludeArtists:!1,IncludeItemTypes:"Episode"},context,".episodeResults",{coverImage:!0,showTitle:!0,showParentTitle:!0}),searchType(instance,apiClient,{searchTerm:value,IncludePeople:!1,IncludeMedia:!0,IncludeGenres:!1,IncludeStudios:!1,IncludeArtists:!1,IncludeItemTypes:"livetv"===instance.options.collectionType?"LiveTvProgram":"NullType",IsSports:!0},context,".sportsResults",{preferThumb:!0,inheritThumb:!1,shape:enableScrollX()?"overflowBackdrop":"backdrop",showParentTitleOrTitle:!0,showTitle:!1,centerText:!0,coverImage:!0,overlayText:!1,overlayMoreButton:!0,showAirTime:!0,showAirDateTime:!0,showChannelName:!0}),searchType(instance,apiClient,{searchTerm:value,IncludePeople:!1,IncludeMedia:!0,IncludeGenres:!1,IncludeStudios:!1,IncludeArtists:!1,IncludeItemTypes:"livetv"===instance.options.collectionType?"LiveTvProgram":"NullType",IsKids:!0},context,".kidsResults",{preferThumb:!0,inheritThumb:!1,shape:enableScrollX()?"overflowBackdrop":"backdrop",showParentTitleOrTitle:!0,showTitle:!1,centerText:!0,coverImage:!0,overlayText:!1,overlayMoreButton:!0,showAirTime:!0,showAirDateTime:!0,showChannelName:!0}),searchType(instance,apiClient,{searchTerm:value,IncludePeople:!1,IncludeMedia:!0,IncludeGenres:!1,IncludeStudios:!1,IncludeArtists:!1,IncludeItemTypes:"livetv"===instance.options.collectionType?"LiveTvProgram":"NullType",IsNews:!0},context,".newsResults",{preferThumb:!0,inheritThumb:!1,shape:enableScrollX()?"overflowBackdrop":"backdrop",showParentTitleOrTitle:!0,showTitle:!1,centerText:!0,coverImage:!0,overlayText:!1,overlayMoreButton:!0,showAirTime:!0,showAirDateTime:!0,showChannelName:!0}),searchType(instance,apiClient,{searchTerm:value,IncludePeople:!1,IncludeMedia:!0,IncludeGenres:!1,IncludeStudios:!1,IncludeArtists:!1,IncludeItemTypes:"LiveTvProgram",IsMovie:"livetv"!==instance.options.collectionType&&null,IsSeries:"livetv"!==instance.options.collectionType&&null,IsSports:"livetv"!==instance.options.collectionType&&null,IsKids:"livetv"!==instance.options.collectionType&&null,IsNews:"livetv"!==instance.options.collectionType&&null},context,".programResults",{preferThumb:!0,inheritThumb:!1,shape:enableScrollX()?"overflowBackdrop":"backdrop",showParentTitleOrTitle:!0,showTitle:!1,centerText:!0,coverImage:!0,overlayText:!1,overlayMoreButton:!0,showAirTime:!0,showAirDateTime:!0,showChannelName:!0}),searchType(instance,apiClient,{searchTerm:value,IncludePeople:!1,IncludeMedia:!0,IncludeGenres:!1,IncludeStudios:!1,IncludeArtists:!1,MediaTypes:"Video",ExcludeItemTypes:"Movie,Episode"},context,".videoResults",{showParentTitle:!0,showTitle:!0,overlayText:!1,centerText:!0}),searchType(instance,apiClient,{searchTerm:value,IncludePeople:!0,IncludeMedia:!1,IncludeGenres:!1,IncludeStudios:!1,IncludeArtists:!1},context,".peopleResults",{coverImage:!0,showTitle:!0}),searchType(instance,apiClient,{searchTerm:value,IncludePeople:!1,IncludeMedia:!1,IncludeGenres:!1,IncludeStudios:!1,IncludeArtists:!0},context,".artistResults",{coverImage:!0,showTitle:!0}),searchType(instance,apiClient,{searchTerm:value,IncludePeople:!1,IncludeMedia:!0,IncludeGenres:!1,IncludeStudios:!1,IncludeArtists:!1,IncludeItemTypes:"MusicAlbum"},context,".albumResults",{showParentTitle:!0,showTitle:!0,overlayText:!1,centerText:!0}),searchType(instance,apiClient,{searchTerm:value,IncludePeople:!1,IncludeMedia:!0,IncludeGenres:!1,IncludeStudios:!1,IncludeArtists:!1,IncludeItemTypes:"Audio"},context,".songResults",{showParentTitle:!0,showTitle:!0,overlayText:!1,centerText:!0,action:"play"}),searchType(instance,apiClient,{searchTerm:value,IncludePeople:!1,IncludeMedia:!0,IncludeGenres:!1,IncludeStudios:!1,IncludeArtists:!1,MediaTypes:"Photo"},context,".photoResults",{showParentTitle:!1,showTitle:!0,overlayText:!1,centerText:!0}),searchType(instance,apiClient,{searchTerm:value,IncludePeople:!1,IncludeMedia:!0,IncludeGenres:!1,IncludeStudios:!1,IncludeArtists:!1,IncludeItemTypes:"PhotoAlbum"},context,".photoAlbumResults",{showTitle:!0,overlayText:!1,centerText:!0}),searchType(instance,apiClient,{searchTerm:value,IncludePeople:!1,IncludeMedia:!0,IncludeGenres:!1,IncludeStudios:!1,IncludeArtists:!1,IncludeItemTypes:"Book"},context,".bookResults",{showTitle:!0,overlayText:!1,centerText:!0}),searchType(instance,apiClient,{searchTerm:value,IncludePeople:!1,IncludeMedia:!0,IncludeGenres:!1,IncludeStudios:!1,IncludeArtists:!1,IncludeItemTypes:"AudioBook"},context,".audioBookResults",{showTitle:!0,overlayText:!1,centerText:!0}),searchType(instance,apiClient,{searchTerm:value,IncludePeople:!1,IncludeMedia:!0,IncludeGenres:!1,IncludeStudios:!1,IncludeArtists:!1,IncludeItemTypes:"Playlist"},context,".playlistResults",{showTitle:!0,overlayText:!1,centerText:!0})}function searchType(instance,apiClient,query,context,section,cardOptions){query.Limit=enableScrollX()?24:16,query.ParentId=instance.options.parentId,getSearchHints(instance,apiClient,query).then(function(result){populateResults(result,context,section,cardOptions)})}function populateResults(result,context,section,cardOptions){section=context.querySelector(section);var items=result.Items||result.SearchHints,itemsContainer=section.querySelector(".itemsContainer");cardBuilder.buildCards(items,Object.assign({itemsContainer:itemsContainer,parentContainer:section,shape:enableScrollX()?"autooverflow":"auto",scalable:!0,overlayText:!1,centerText:!0,allowBottomPadding:!enableScrollX()},cardOptions||{})),section.querySelector(".emby-scroller").scrollToBeginning(!0)}function enableScrollX(){return!0}function replaceAll(originalString,strReplace,strWith){var reg=new RegExp(strReplace,"ig");return originalString.replace(reg,strWith)}function embed(elem,instance,options){require(["text!./searchresults.template.html"],function(template){enableScrollX()||(template=replaceAll(template,'data-horizontal="true"','data-horizontal="false"'),template=replaceAll(template,"itemsContainer scrollSlider","itemsContainer scrollSlider vertical-wrap"));var html=globalize.translateDocument(template,"sharedcomponents");elem.innerHTML=html,elem.classList.add("searchResults"),instance.search("")})}function SearchResults(options){this.options=options,embed(options.element,this,options)}return SearchResults.prototype.search=function(value){search(this,connectionManager.getApiClient(this.options.serverId),this.options.element,value)},SearchResults.prototype.destroy=function(){var options=this.options;options&&options.element.classList.remove("searchFields"),this.options=null},SearchResults}); \ No newline at end of file +define(["layoutManager", "globalize", "require", "events", "connectionManager", "cardBuilder", "appRouter", "emby-scroller", "emby-itemscontainer", "emby-linkbutton"], function(layoutManager, globalize, require, events, connectionManager, cardBuilder, appRouter) { + "use strict"; + + function loadSuggestions(instance, context, apiClient) { + var options = { + SortBy: "IsFavoriteOrLiked,Random", + IncludeItemTypes: "Movie,Series,MusicArtist", + Limit: 20, + Recursive: !0, + ImageTypeLimit: 0, + EnableImages: !1, + ParentId: instance.options.parentId, + EnableTotalRecordCount: !1 + }; + apiClient.getItems(apiClient.getCurrentUserId(), options).then(function(result) { + "suggestions" !== instance.mode && (result.Items = []); + var html = result.Items.map(function(i) { + var href = appRouter.getRouteUrl(i), + itemHtml = '" + }).join(""), + searchSuggestions = context.querySelector(".searchSuggestions"); + searchSuggestions.querySelector(".searchSuggestionsList").innerHTML = html, result.Items.length && searchSuggestions.classList.remove("hide") + }) + } + + function getSearchHints(instance, apiClient, query) { + if (!query.searchTerm) return Promise.resolve({ + SearchHints: [] + }); + var allowSearch = !0, + queryIncludeItemTypes = query.IncludeItemTypes; + if ("tvshows" === instance.options.collectionType ? query.IncludeArtists ? allowSearch = !1 : "Movie" !== queryIncludeItemTypes && "LiveTvProgram" !== queryIncludeItemTypes && "MusicAlbum" !== queryIncludeItemTypes && "Audio" !== queryIncludeItemTypes && "Book" !== queryIncludeItemTypes && "AudioBook" !== queryIncludeItemTypes && "Playlist" !== queryIncludeItemTypes && "PhotoAlbum" !== queryIncludeItemTypes && "Video" !== query.MediaTypes && "Photo" !== query.MediaTypes || (allowSearch = !1) : "movies" === instance.options.collectionType ? query.IncludeArtists ? allowSearch = !1 : "Series" !== queryIncludeItemTypes && "Episode" !== queryIncludeItemTypes && "LiveTvProgram" !== queryIncludeItemTypes && "MusicAlbum" !== queryIncludeItemTypes && "Audio" !== queryIncludeItemTypes && "Book" !== queryIncludeItemTypes && "AudioBook" !== queryIncludeItemTypes && "Playlist" !== queryIncludeItemTypes && "PhotoAlbum" !== queryIncludeItemTypes && "Video" !== query.MediaTypes && "Photo" !== query.MediaTypes || (allowSearch = !1) : "music" === instance.options.collectionType ? query.People ? allowSearch = !1 : "Series" !== queryIncludeItemTypes && "Episode" !== queryIncludeItemTypes && "LiveTvProgram" !== queryIncludeItemTypes && "Movie" !== queryIncludeItemTypes || (allowSearch = !1) : "livetv" === instance.options.collectionType && (query.IncludeArtists || query.IncludePeople ? allowSearch = !1 : "Series" !== queryIncludeItemTypes && "Episode" !== queryIncludeItemTypes && "MusicAlbum" !== queryIncludeItemTypes && "Audio" !== queryIncludeItemTypes && "Book" !== queryIncludeItemTypes && "AudioBook" !== queryIncludeItemTypes && "PhotoAlbum" !== queryIncludeItemTypes && "Movie" !== queryIncludeItemTypes && "Video" !== query.MediaTypes && "Photo" !== query.MediaTypes || (allowSearch = !1)), "NullType" === queryIncludeItemTypes && (allowSearch = !1), !allowSearch) return Promise.resolve({ + SearchHints: [] + }); + if (apiClient.isMinServerVersion("3.4.1.31")) { + query.Fields = "PrimaryImageAspectRatio,CanDelete,BasicSyncInfo,MediaSourceCount", query.Recursive = !0, query.EnableTotalRecordCount = !1, query.ImageTypeLimit = 1; + var methodName = "getItems"; + return query.IncludeMedia || (query.IncludePeople ? methodName = "getPeople" : query.IncludeArtists && (methodName = "getArtists")), apiClient[methodName](apiClient.getCurrentUserId(), query) + } + return query.UserId = apiClient.getCurrentUserId(), apiClient.getSearchHints(query) + } + + function search(instance, apiClient, context, value) { + value || layoutManager.tv ? (instance.mode = "search", context.querySelector(".searchSuggestions").classList.add("hide")) : (instance.mode = "suggestions", loadSuggestions(instance, context, apiClient)), "livetv" === instance.options.collectionType ? searchType(instance, apiClient, { + searchTerm: value, + IncludePeople: !1, + IncludeMedia: !0, + IncludeGenres: !1, + IncludeStudios: !1, + IncludeArtists: !1, + IncludeItemTypes: "LiveTvProgram", + IsMovie: !0, + IsKids: !1, + IsNews: !1 + }, context, ".movieResults", { + preferThumb: !0, + inheritThumb: !1, + shape: enableScrollX() ? "overflowPortrait" : "portrait", + showParentTitleOrTitle: !0, + showTitle: !1, + centerText: !0, + coverImage: !0, + overlayText: !1, + overlayMoreButton: !0, + showAirTime: !0, + showAirDateTime: !0, + showChannelName: !0 + }) : searchType(instance, apiClient, { + searchTerm: value, + IncludePeople: !1, + IncludeMedia: !0, + IncludeGenres: !1, + IncludeStudios: !1, + IncludeArtists: !1, + IncludeItemTypes: "Movie" + }, context, ".movieResults", { + showTitle: !0, + overlayText: !1, + centerText: !0, + showYear: !0 + }), searchType(instance, apiClient, { + searchTerm: value, + IncludePeople: !1, + IncludeMedia: !0, + IncludeGenres: !1, + IncludeStudios: !1, + IncludeArtists: !1, + IncludeItemTypes: "Series" + }, context, ".seriesResults", { + showTitle: !0, + overlayText: !1, + centerText: !0, + showYear: !0 + }), "livetv" === instance.options.collectionType ? searchType(instance, apiClient, { + searchTerm: value, + IncludePeople: !1, + IncludeMedia: !0, + IncludeGenres: !1, + IncludeStudios: !1, + IncludeArtists: !1, + IncludeItemTypes: "LiveTvProgram", + IsSeries: !0, + IsSports: !1, + IsKids: !1, + IsNews: !1 + }, context, ".episodeResults", { + preferThumb: !0, + inheritThumb: !1, + shape: enableScrollX() ? "overflowBackdrop" : "backdrop", + showParentTitleOrTitle: !0, + showTitle: !1, + centerText: !0, + coverImage: !0, + overlayText: !1, + overlayMoreButton: !0, + showAirTime: !0, + showAirDateTime: !0, + showChannelName: !0 + }) : searchType(instance, apiClient, { + searchTerm: value, + IncludePeople: !1, + IncludeMedia: !0, + IncludeGenres: !1, + IncludeStudios: !1, + IncludeArtists: !1, + IncludeItemTypes: "Episode" + }, context, ".episodeResults", { + coverImage: !0, + showTitle: !0, + showParentTitle: !0 + }), searchType(instance, apiClient, { + searchTerm: value, + IncludePeople: !1, + IncludeMedia: !0, + IncludeGenres: !1, + IncludeStudios: !1, + IncludeArtists: !1, + IncludeItemTypes: "livetv" === instance.options.collectionType ? "LiveTvProgram" : "NullType", + IsSports: !0 + }, context, ".sportsResults", { + preferThumb: !0, + inheritThumb: !1, + shape: enableScrollX() ? "overflowBackdrop" : "backdrop", + showParentTitleOrTitle: !0, + showTitle: !1, + centerText: !0, + coverImage: !0, + overlayText: !1, + overlayMoreButton: !0, + showAirTime: !0, + showAirDateTime: !0, + showChannelName: !0 + }), searchType(instance, apiClient, { + searchTerm: value, + IncludePeople: !1, + IncludeMedia: !0, + IncludeGenres: !1, + IncludeStudios: !1, + IncludeArtists: !1, + IncludeItemTypes: "livetv" === instance.options.collectionType ? "LiveTvProgram" : "NullType", + IsKids: !0 + }, context, ".kidsResults", { + preferThumb: !0, + inheritThumb: !1, + shape: enableScrollX() ? "overflowBackdrop" : "backdrop", + showParentTitleOrTitle: !0, + showTitle: !1, + centerText: !0, + coverImage: !0, + overlayText: !1, + overlayMoreButton: !0, + showAirTime: !0, + showAirDateTime: !0, + showChannelName: !0 + }), searchType(instance, apiClient, { + searchTerm: value, + IncludePeople: !1, + IncludeMedia: !0, + IncludeGenres: !1, + IncludeStudios: !1, + IncludeArtists: !1, + IncludeItemTypes: "livetv" === instance.options.collectionType ? "LiveTvProgram" : "NullType", + IsNews: !0 + }, context, ".newsResults", { + preferThumb: !0, + inheritThumb: !1, + shape: enableScrollX() ? "overflowBackdrop" : "backdrop", + showParentTitleOrTitle: !0, + showTitle: !1, + centerText: !0, + coverImage: !0, + overlayText: !1, + overlayMoreButton: !0, + showAirTime: !0, + showAirDateTime: !0, + showChannelName: !0 + }), searchType(instance, apiClient, { + searchTerm: value, + IncludePeople: !1, + IncludeMedia: !0, + IncludeGenres: !1, + IncludeStudios: !1, + IncludeArtists: !1, + IncludeItemTypes: "LiveTvProgram", + IsMovie: "livetv" !== instance.options.collectionType && null, + IsSeries: "livetv" !== instance.options.collectionType && null, + IsSports: "livetv" !== instance.options.collectionType && null, + IsKids: "livetv" !== instance.options.collectionType && null, + IsNews: "livetv" !== instance.options.collectionType && null + }, context, ".programResults", { + preferThumb: !0, + inheritThumb: !1, + shape: enableScrollX() ? "overflowBackdrop" : "backdrop", + showParentTitleOrTitle: !0, + showTitle: !1, + centerText: !0, + coverImage: !0, + overlayText: !1, + overlayMoreButton: !0, + showAirTime: !0, + showAirDateTime: !0, + showChannelName: !0 + }), searchType(instance, apiClient, { + searchTerm: value, + IncludePeople: !1, + IncludeMedia: !0, + IncludeGenres: !1, + IncludeStudios: !1, + IncludeArtists: !1, + MediaTypes: "Video", + ExcludeItemTypes: "Movie,Episode" + }, context, ".videoResults", { + showParentTitle: !0, + showTitle: !0, + overlayText: !1, + centerText: !0 + }), searchType(instance, apiClient, { + searchTerm: value, + IncludePeople: !0, + IncludeMedia: !1, + IncludeGenres: !1, + IncludeStudios: !1, + IncludeArtists: !1 + }, context, ".peopleResults", { + coverImage: !0, + showTitle: !0 + }), searchType(instance, apiClient, { + searchTerm: value, + IncludePeople: !1, + IncludeMedia: !1, + IncludeGenres: !1, + IncludeStudios: !1, + IncludeArtists: !0 + }, context, ".artistResults", { + coverImage: !0, + showTitle: !0 + }), searchType(instance, apiClient, { + searchTerm: value, + IncludePeople: !1, + IncludeMedia: !0, + IncludeGenres: !1, + IncludeStudios: !1, + IncludeArtists: !1, + IncludeItemTypes: "MusicAlbum" + }, context, ".albumResults", { + showParentTitle: !0, + showTitle: !0, + overlayText: !1, + centerText: !0 + }), searchType(instance, apiClient, { + searchTerm: value, + IncludePeople: !1, + IncludeMedia: !0, + IncludeGenres: !1, + IncludeStudios: !1, + IncludeArtists: !1, + IncludeItemTypes: "Audio" + }, context, ".songResults", { + showParentTitle: !0, + showTitle: !0, + overlayText: !1, + centerText: !0, + action: "play" + }), searchType(instance, apiClient, { + searchTerm: value, + IncludePeople: !1, + IncludeMedia: !0, + IncludeGenres: !1, + IncludeStudios: !1, + IncludeArtists: !1, + MediaTypes: "Photo" + }, context, ".photoResults", { + showParentTitle: !1, + showTitle: !0, + overlayText: !1, + centerText: !0 + }), searchType(instance, apiClient, { + searchTerm: value, + IncludePeople: !1, + IncludeMedia: !0, + IncludeGenres: !1, + IncludeStudios: !1, + IncludeArtists: !1, + IncludeItemTypes: "PhotoAlbum" + }, context, ".photoAlbumResults", { + showTitle: !0, + overlayText: !1, + centerText: !0 + }), searchType(instance, apiClient, { + searchTerm: value, + IncludePeople: !1, + IncludeMedia: !0, + IncludeGenres: !1, + IncludeStudios: !1, + IncludeArtists: !1, + IncludeItemTypes: "Book" + }, context, ".bookResults", { + showTitle: !0, + overlayText: !1, + centerText: !0 + }), searchType(instance, apiClient, { + searchTerm: value, + IncludePeople: !1, + IncludeMedia: !0, + IncludeGenres: !1, + IncludeStudios: !1, + IncludeArtists: !1, + IncludeItemTypes: "AudioBook" + }, context, ".audioBookResults", { + showTitle: !0, + overlayText: !1, + centerText: !0 + }), searchType(instance, apiClient, { + searchTerm: value, + IncludePeople: !1, + IncludeMedia: !0, + IncludeGenres: !1, + IncludeStudios: !1, + IncludeArtists: !1, + IncludeItemTypes: "Playlist" + }, context, ".playlistResults", { + showTitle: !0, + overlayText: !1, + centerText: !0 + }) + } + + function searchType(instance, apiClient, query, context, section, cardOptions) { + query.Limit = enableScrollX() ? 24 : 16, query.ParentId = instance.options.parentId, getSearchHints(instance, apiClient, query).then(function(result) { + populateResults(result, context, section, cardOptions) + }) + } + + function populateResults(result, context, section, cardOptions) { + section = context.querySelector(section); + var items = result.Items || result.SearchHints, + itemsContainer = section.querySelector(".itemsContainer"); + cardBuilder.buildCards(items, Object.assign({ + itemsContainer: itemsContainer, + parentContainer: section, + shape: enableScrollX() ? "autooverflow" : "auto", + scalable: !0, + overlayText: !1, + centerText: !0, + allowBottomPadding: !enableScrollX() + }, cardOptions || {})), section.querySelector(".emby-scroller").scrollToBeginning(!0) + } + + function enableScrollX() { + return !0 + } + + function replaceAll(originalString, strReplace, strWith) { + var reg = new RegExp(strReplace, "ig"); + return originalString.replace(reg, strWith) + } + + function embed(elem, instance, options) { + require(["text!./searchresults.template.html"], function(template) { + enableScrollX() || (template = replaceAll(template, 'data-horizontal="true"', 'data-horizontal="false"'), template = replaceAll(template, "itemsContainer scrollSlider", "itemsContainer scrollSlider vertical-wrap")); + var html = globalize.translateDocument(template, "sharedcomponents"); + elem.innerHTML = html, elem.classList.add("searchResults"), instance.search("") + }) + } + + function SearchResults(options) { + this.options = options, embed(options.element, this, options) + } + return SearchResults.prototype.search = function(value) { + search(this, connectionManager.getApiClient(this.options.serverId), this.options.element, value) + }, SearchResults.prototype.destroy = function() { + var options = this.options; + options && options.element.classList.remove("searchFields"), this.options = null + }, SearchResults +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/serverrestartdialog/serverrestartdialog.js b/dashboard-ui/bower_components/emby-webcomponents/serverrestartdialog/serverrestartdialog.js index 07a308114e..a86fa3ef16 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/serverrestartdialog/serverrestartdialog.js +++ b/dashboard-ui/bower_components/emby-webcomponents/serverrestartdialog/serverrestartdialog.js @@ -1 +1,70 @@ -define(["loading","events","dialogHelper","dom","layoutManager","scrollHelper","globalize","require","material-icons","emby-button","paper-icon-button-light","emby-input","formDialogStyle","flexStyles"],function(loading,events,dialogHelper,dom,layoutManager,scrollHelper,globalize,require){"use strict";function reloadPageWhenServerAvailable(retryCount){var apiClient=currentApiClient;apiClient&&apiClient.getJSON(apiClient.getUrl("System/Info")).then(function(info){info.IsShuttingDown?retryReload(retryCount):(currentInstance.restarted=!0,dialogHelper.close(currentDlg))},function(){retryReload(retryCount)})}function retryReload(retryCount){setTimeout(function(){retryCount=retryCount||0,++retryCount<150&&reloadPageWhenServerAvailable(retryCount)},500)}function startRestart(instance,apiClient,dlg){currentApiClient=apiClient,currentDlg=dlg,currentInstance=instance,apiClient.restartServer().then(function(){setTimeout(reloadPageWhenServerAvailable,250)})}function showDialog(instance,options,template){function onButtonClick(){dialogHelper.close(dlg)}var dialogOptions={removeOnClose:!0,scrollY:!1},enableTvLayout=layoutManager.tv;enableTvLayout&&(dialogOptions.size="fullscreen");var dlg=dialogHelper.createDialog(dialogOptions),configuredButtons=[];dlg.classList.add("formDialog"),dlg.innerHTML=globalize.translateHtml(template,"sharedcomponents"),dlg.classList.add("align-items-center"),dlg.classList.add("justify-items-center");var formDialogContent=dlg.querySelector(".formDialogContent");formDialogContent.style["flex-grow"]="initial",enableTvLayout?(formDialogContent.style["max-width"]="50%",formDialogContent.style["max-height"]="60%",scrollHelper.centerFocus.on(formDialogContent,!1)):(formDialogContent.style.maxWidth=Math.min(150*configuredButtons.length+200,dom.getWindowSize().innerWidth-50)+"px",dlg.classList.add("dialog-fullscreen-lowres")),dlg.querySelector(".formDialogHeaderTitle").innerHTML=globalize.translate("sharedcomponents#HeaderRestartingEmbyServer"),dlg.querySelector(".text").innerHTML=globalize.translate("sharedcomponents#RestartPleaseWaitMessage");var i,length,html="";for(i=0,length=configuredButtons.length;i"+item.name+""}dlg.querySelector(".formDialogFooter").innerHTML=html;var buttons=dlg.querySelectorAll(".btnOption");for(i=0,length=buttons.length;i" + item.name + "" + } + dlg.querySelector(".formDialogFooter").innerHTML = html; + var buttons = dlg.querySelectorAll(".btnOption"); + for (i = 0, length = buttons.length; i < length; i++) buttons[i].addEventListener("click", onButtonClick); + var dlgPromise = dialogHelper.open(dlg); + return startRestart(instance, options.apiClient, dlg), dlgPromise.then(function() { + enableTvLayout && scrollHelper.centerFocus.off(dlg.querySelector(".formDialogContent"), !1), instance.destroy(), loading.hide(), instance.restarted && events.trigger(instance, "restarted") + }) + } + + function ServerRestartDialog(options) { + this.options = options + } + var currentApiClient, currentDlg, currentInstance; + return ServerRestartDialog.prototype.show = function() { + var instance = this; + return loading.show(), new Promise(function(resolve, reject) { + require(["text!./../dialog/dialog.template.html"], function(template) { + showDialog(instance, instance.options, template).then(resolve, reject) + }) + }) + }, ServerRestartDialog.prototype.destroy = function() { + currentApiClient = null, currentDlg = null, currentInstance = null, this.options = null + }, ServerRestartDialog +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/serviceworker/notifications.js b/dashboard-ui/bower_components/emby-webcomponents/serviceworker/notifications.js index 2eaa3e1376..e99b2f44c1 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/serviceworker/notifications.js +++ b/dashboard-ui/bower_components/emby-webcomponents/serviceworker/notifications.js @@ -1 +1,31 @@ -!function(){"use strict";function getApiClient(serverId){return connectionManager?Promise.resolve(connectionManager.getApiClient(serverId)):Promise.reject()}function executeAction(action,data,serverId){return getApiClient(serverId).then(function(apiClient){switch(action){case"cancel-install":var id=data.id;return apiClient.cancelPackageInstallation(id);case"restart":return apiClient.restartServer();default:return clients.openWindow("/"),Promise.resolve()}})}var connectionManager;self.addEventListener("notificationclick",function(event){var notification=event.notification;notification.close();var data=notification.data,serverId=data.serverId,action=event.action;if(!action)return clients.openWindow("/"),void event.waitUntil(Promise.resolve());event.waitUntil(executeAction(action,data,serverId))},!1)}(); \ No newline at end of file +! function() { + "use strict"; + + function getApiClient(serverId) { + return connectionManager ? Promise.resolve(connectionManager.getApiClient(serverId)) : Promise.reject() + } + + function executeAction(action, data, serverId) { + return getApiClient(serverId).then(function(apiClient) { + switch (action) { + case "cancel-install": + var id = data.id; + return apiClient.cancelPackageInstallation(id); + case "restart": + return apiClient.restartServer(); + default: + return clients.openWindow("/"), Promise.resolve() + } + }) + } + var connectionManager; + self.addEventListener("notificationclick", function(event) { + var notification = event.notification; + notification.close(); + var data = notification.data, + serverId = data.serverId, + action = event.action; + if (!action) return clients.openWindow("/"), void event.waitUntil(Promise.resolve()); + event.waitUntil(executeAction(action, data, serverId)) + }, !1) +}(); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/serviceworker/sync.js b/dashboard-ui/bower_components/emby-webcomponents/serviceworker/sync.js index 88aeeff0f2..5fdaac113d 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/serviceworker/sync.js +++ b/dashboard-ui/bower_components/emby-webcomponents/serviceworker/sync.js @@ -1 +1,4 @@ -self.addEventListener("sync",function(event){"use strict";event.tag}); \ No newline at end of file +self.addEventListener("sync", function(event) { + "use strict"; + event.tag +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/sessionplayer.js b/dashboard-ui/bower_components/emby-webcomponents/sessionplayer.js index e8a572e22d..f7c45f561a 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/sessionplayer.js +++ b/dashboard-ui/bower_components/emby-webcomponents/sessionplayer.js @@ -1 +1,246 @@ -define(["playbackManager","events","serverNotifications","connectionManager"],function(playbackManager,events,serverNotifications,connectionManager){"use strict";function getActivePlayerId(){var info=playbackManager.getPlayerInfo();return info?info.id:null}function sendPlayCommand(apiClient,options,playType){var sessionId=getActivePlayerId(),ids=options.ids||options.items.map(function(i){return i.Id}),remoteOptions={ItemIds:ids.join(","),PlayCommand:playType};return options.startPositionTicks&&(remoteOptions.StartPositionTicks=options.startPositionTicks),options.mediaSourceId&&(remoteOptions.MediaSourceId=options.mediaSourceId),null!=options.audioStreamIndex&&(remoteOptions.AudioStreamIndex=options.audioStreamIndex),null!=options.subtitleStreamIndex&&(remoteOptions.SubtitleStreamIndex=options.subtitleStreamIndex),null!=options.startIndex&&(remoteOptions.StartIndex=options.startIndex),apiClient.sendPlayCommand(sessionId,remoteOptions)}function sendPlayStateCommand(apiClient,command,options){var sessionId=getActivePlayerId();apiClient.sendPlayStateCommand(sessionId,command,options)}function getCurrentApiClient(instance){var currentServerId=instance.currentServerId;return currentServerId?connectionManager.getApiClient(currentServerId):connectionManager.currentApiClient()}function sendCommandByName(instance,name,options){var command={Name:name};options&&(command.Arguments=options),instance.sendCommand(command)}function unsubscribeFromPlayerUpdates(instance){instance.isUpdating=!0,getCurrentApiClient(instance).sendMessage("SessionsStop"),instance.pollInterval&&(clearInterval(instance.pollInterval),instance.pollInterval=null)}function processUpdatedSessions(instance,sessions,apiClient){var serverId=apiClient.serverId();sessions.map(function(s){s.NowPlayingItem&&(s.NowPlayingItem.ServerId=serverId)});var currentTargetId=getActivePlayerId(),session=sessions.filter(function(s){return s.Id===currentTargetId})[0];if(session){normalizeImages(session,apiClient);var eventNames=getChangedEvents(instance.lastPlayerData,session);instance.lastPlayerData=session;for(var i=0,length=eventNames.length;i=30?"halloween":id}function loadThemeResources(id){if(lastSound=0,currentSound&&(currentSound.stop(),currentSound=null),backdrop.clear(),"halloween"===id)return void(themeResources={themeSong:"https://github.com/MediaBrowser/Emby.Resources/raw/master/themes/halloween/monsterparadefade.mp3",effect:"https://github.com/MediaBrowser/Emby.Resources/raw/master/themes/halloween/howl.wav",backdrop:"https://github.com/MediaBrowser/Emby.Resources/raw/master/themes/halloween/bg.jpg"});themeResources={}}function onThemeLoaded(){document.documentElement.classList.remove("preload");try{var color=getComputedStyle(document.querySelector(".skinHeader")).getPropertyValue("background-color");color&&appHost.setThemeColor(color)}catch(err){console.log("Error setting theme color: "+err)}}function onViewBeforeShow(e){e.detail&&"video-osd"===e.detail.type||(themeResources.backdrop&&backdrop.setBackdrop(themeResources.backdrop),!browser.mobile&&userSettings.enableThemeSongs()&&(0===lastSound?themeResources.themeSong&&playSound(themeResources.themeSong):(new Date).getTime()-lastSound>3e4&&themeResources.effect&&playSound(themeResources.effect)))}function playSound(path,volume){lastSound=(new Date).getTime(),require(["howler"],function(howler){try{var sound=new Howl({src:[path],volume:volume||.1});sound.play(),currentSound=sound}catch(err){console.log("Error playing sound: "+err)}})}var currentSkin,cacheParam=(new Date).getTime();events.on(userSettings,"change",function(e,name){"skin"!==name&&"language"!==name||loadUserSkin()});var themeStyleElement,currentThemeId,currentSound,skinManager={getCurrentSkin:getCurrentSkin,loadSkin:loadSkin,loadUserSkin:loadUserSkin,getThemes:getThemes},themeResources={},lastSound=0;return skinManager.setTheme=function(id,context){return new Promise(function(resolve,reject){var requiresRegistration=!0;if("serverdashboard"!==context){var newId=modifyThemeForSeasonal(id);newId!==id&&(requiresRegistration=!1),id=newId}if(currentThemeId&¤tThemeId===id)return void resolve();var isDefaultProperty="serverdashboard"===context?"isDefaultServerDashboard":"isDefault",info=getThemeStylesheetInfo(id,requiresRegistration,isDefaultProperty);if(currentThemeId&¤tThemeId===info.themeId)return void resolve();var linkUrl=info.stylesheetPath;unloadTheme();var link=document.createElement("link");link.setAttribute("rel","stylesheet"),link.setAttribute("type","text/css"),link.onload=function(){onThemeLoaded(),resolve()},link.setAttribute("href",linkUrl),document.head.appendChild(link),themeStyleElement=link,currentThemeId=info.themeId,loadThemeResources(info.themeId),onViewBeforeShow({})})},document.addEventListener("viewshow",onViewBeforeShow),skinManager}); \ No newline at end of file +define(["apphost", "userSettings", "browser", "events", "pluginManager", "backdrop", "globalize", "require", "appSettings"], function(appHost, userSettings, browser, events, pluginManager, backdrop, globalize, require, appSettings) { + "use strict"; + + function getCurrentSkin() { + return currentSkin + } + + function getRequirePromise(deps) { + return new Promise(function(resolve, reject) { + require(deps, resolve) + }) + } + + function loadSkin(id) { + var newSkin = pluginManager.plugins().filter(function(p) { + return p.id === id + })[0]; + newSkin || (newSkin = pluginManager.plugins().filter(function(p) { + return "defaultskin" === p.id + })[0]); + var unloadPromise; + if (currentSkin) { + if (currentSkin.id === newSkin.id) return Promise.resolve(currentSkin); + unloadPromise = unloadSkin(currentSkin) + } else unloadPromise = Promise.resolve(); + return unloadPromise.then(function() { + var deps = newSkin.getDependencies(); + return console.log("Loading skin dependencies"), getRequirePromise(deps).then(function() { + console.log("Skin dependencies loaded"); + var strings = newSkin.getTranslations ? newSkin.getTranslations() : []; + return globalize.loadStrings({ + name: newSkin.id, + strings: strings + }).then(function() { + return globalize.defaultModule(newSkin.id), loadSkinHeader(newSkin) + }) + }) + }) + } + + function unloadSkin(skin) { + return unloadTheme(), backdrop.clear(), console.log("Unloading skin: " + skin.name), skin.unload().then(function() { + document.dispatchEvent(new CustomEvent("skinunload", { + detail: { + name: skin.name + } + })) + }) + } + + function loadSkinHeader(skin) { + return getSkinHeader(skin).then(function(headerHtml) { + return document.querySelector(".skinHeader").innerHTML = headerHtml, currentSkin = skin, skin.load(), skin + }) + } + + function getSkinHeader(skin) { + return new Promise(function(resolve, reject) { + if (!skin.getHeaderTemplate) return void resolve(""); + var xhr = new XMLHttpRequest, + url = skin.getHeaderTemplate(); + url += -1 === url.indexOf("?") ? "?" : "&", url += "v=" + cacheParam, xhr.open("GET", url, !0), xhr.onload = function(e) { + resolve(this.status < 400 ? this.response : "") + }, xhr.send() + }) + } + + function loadUserSkin(options) { + loadSkin(userSettings.get("skin", !1) || "defaultskin").then(function(skin) { + options = options || {}, options.start ? Emby.Page.invokeShortcut(options.start) : Emby.Page.goHome() + }) + } + + function unloadTheme() { + var elem = themeStyleElement; + elem && (elem.parentNode.removeChild(elem), themeStyleElement = null, currentThemeId = null) + } + + function getThemes() { + return currentSkin.getThemes ? currentSkin.getThemes() : [] + } + + function onRegistrationSuccess() { + appSettings.set("appthemesregistered", "true") + } + + function onRegistrationFailure() { + appSettings.set("appthemesregistered", "false") + } + + function isRegistered() { + return getRequirePromise(["registrationServices"]).then(function(registrationServices) { + registrationServices.validateFeature("themes", { + showDialog: !1 + }).then(onRegistrationSuccess, onRegistrationFailure) + }), "false" !== appSettings.get("appthemesregistered") + } + + function getThemeStylesheetInfo(id, requiresRegistration, isDefaultProperty) { + for (var defaultTheme, selectedTheme, themes = skinManager.getThemes(), i = 0, length = themes.length; i < length; i++) { + var theme = themes[i]; + theme[isDefaultProperty] && (defaultTheme = theme), id === theme.id && (selectedTheme = theme) + } + selectedTheme = selectedTheme || defaultTheme, selectedTheme.id !== defaultTheme.id && requiresRegistration && !isRegistered() && (selectedTheme = defaultTheme); + return { + stylesheetPath: require.toUrl("bower_components/emby-webcomponents/themes/" + selectedTheme.id + "/theme.css"), + themeId: selectedTheme.id + } + } + + function modifyThemeForSeasonal(id) { + if (!userSettings.enableSeasonalThemes()) return id; + var date = new Date, + month = date.getMonth(), + day = date.getDate(); + return 9 === month && day >= 30 ? "halloween" : id + } + + function loadThemeResources(id) { + if (lastSound = 0, currentSound && (currentSound.stop(), currentSound = null), backdrop.clear(), "halloween" === id) return void(themeResources = { + themeSong: "https://github.com/MediaBrowser/Emby.Resources/raw/master/themes/halloween/monsterparadefade.mp3", + effect: "https://github.com/MediaBrowser/Emby.Resources/raw/master/themes/halloween/howl.wav", + backdrop: "https://github.com/MediaBrowser/Emby.Resources/raw/master/themes/halloween/bg.jpg" + }); + themeResources = {} + } + + function onThemeLoaded() { + document.documentElement.classList.remove("preload"); + try { + var color = getComputedStyle(document.querySelector(".skinHeader")).getPropertyValue("background-color"); + color && appHost.setThemeColor(color) + } catch (err) { + console.log("Error setting theme color: " + err) + } + } + + function onViewBeforeShow(e) { + e.detail && "video-osd" === e.detail.type || (themeResources.backdrop && backdrop.setBackdrop(themeResources.backdrop), !browser.mobile && userSettings.enableThemeSongs() && (0 === lastSound ? themeResources.themeSong && playSound(themeResources.themeSong) : (new Date).getTime() - lastSound > 3e4 && themeResources.effect && playSound(themeResources.effect))) + } + + function playSound(path, volume) { + lastSound = (new Date).getTime(), require(["howler"], function(howler) { + try { + var sound = new Howl({ + src: [path], + volume: volume || .1 + }); + sound.play(), currentSound = sound + } catch (err) { + console.log("Error playing sound: " + err) + } + }) + } + var currentSkin, cacheParam = (new Date).getTime(); + events.on(userSettings, "change", function(e, name) { + "skin" !== name && "language" !== name || loadUserSkin() + }); + var themeStyleElement, currentThemeId, currentSound, skinManager = { + getCurrentSkin: getCurrentSkin, + loadSkin: loadSkin, + loadUserSkin: loadUserSkin, + getThemes: getThemes + }, + themeResources = {}, + lastSound = 0; + return skinManager.setTheme = function(id, context) { + return new Promise(function(resolve, reject) { + var requiresRegistration = !0; + if ("serverdashboard" !== context) { + var newId = modifyThemeForSeasonal(id); + newId !== id && (requiresRegistration = !1), id = newId + } + if (currentThemeId && currentThemeId === id) return void resolve(); + var isDefaultProperty = "serverdashboard" === context ? "isDefaultServerDashboard" : "isDefault", + info = getThemeStylesheetInfo(id, requiresRegistration, isDefaultProperty); + if (currentThemeId && currentThemeId === info.themeId) return void resolve(); + var linkUrl = info.stylesheetPath; + unloadTheme(); + var link = document.createElement("link"); + link.setAttribute("rel", "stylesheet"), link.setAttribute("type", "text/css"), link.onload = function() { + onThemeLoaded(), resolve() + }, link.setAttribute("href", linkUrl), document.head.appendChild(link), themeStyleElement = link, currentThemeId = info.themeId, loadThemeResources(info.themeId), onViewBeforeShow({}) + }) + }, document.addEventListener("viewshow", onViewBeforeShow), skinManager +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/slideshow/slideshow.js b/dashboard-ui/bower_components/emby-webcomponents/slideshow/slideshow.js index 363eb0bc45..c5aeffc832 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/slideshow/slideshow.js +++ b/dashboard-ui/bower_components/emby-webcomponents/slideshow/slideshow.js @@ -1 +1,317 @@ -define(["dialogHelper","inputManager","connectionManager","layoutManager","focusManager","browser","apphost","loading","css!./style","material-icons","paper-icon-button-light"],function(dialogHelper,inputmanager,connectionManager,layoutManager,focusManager,browser,appHost,loading){"use strict";function getImageUrl(item,options,apiClient){return options=options||{},options.type=options.type||"Primary","string"==typeof item?apiClient.getScaledImageUrl(item,options):item.ImageTags&&item.ImageTags[options.type]?(options.tag=item.ImageTags[options.type],apiClient.getScaledImageUrl(item.Id,options)):"Primary"===options.type&&item.AlbumId&&item.AlbumPrimaryImageTag?(options.tag=item.AlbumPrimaryImageTag,apiClient.getScaledImageUrl(item.AlbumId,options)):null}function getBackdropImageUrl(item,options,apiClient){return options=options||{},options.type=options.type||"Backdrop",options.maxWidth||options.width||options.maxHeight||options.height||(options.quality=100),item.BackdropImageTags&&item.BackdropImageTags.length?(options.tag=item.BackdropImageTags[0],apiClient.getScaledImageUrl(item.Id,options)):null}function getImgUrl(item,original){var apiClient=connectionManager.getApiClient(item.ServerId),imageOptions={};return original||(imageOptions.maxWidth=screen.availWidth),item.BackdropImageTags&&item.BackdropImageTags.length?getBackdropImageUrl(item,imageOptions,apiClient):"Photo"===item.MediaType&&original?apiClient.getItemDownloadUrl(item.Id):(imageOptions.type="Primary",getImageUrl(item,imageOptions,apiClient))}function getIcon(icon,cssClass,canFocus,autoFocus){var tabIndex=canFocus?"":' tabindex="-1"';return autoFocus=autoFocus?" autofocus":"",'"}function setUserScalable(scalable){try{appHost.setUserScalable(scalable)}catch(err){console.log("error in appHost.setUserScalable: "+err)}}return function(options){function createElements(options){dlg=dialogHelper.createDialog({exitAnimationDuration:options.interactive?400:800,size:"fullscreen",autoFocus:!1,scrollY:!1,exitAnimation:"fadeout",removeOnClose:!0}),dlg.classList.add("slideshowDialog");var html="";if(options.interactive){var actionButtonsOnTop=layoutManager.mobile;html+="
    ",html+='
    ',html+=getIcon("keyboard_arrow_left","btnSlideshowPrevious slideshowButton hide-mouse-idle-tv",!1),html+=getIcon("keyboard_arrow_right","btnSlideshowNext slideshowButton hide-mouse-idle-tv",!1),html+='
    ',actionButtonsOnTop&&(appHost.supports("filedownload")&&(html+=getIcon("file_download","btnDownload slideshowButton",!0)),appHost.supports("sharing")&&(html+=getIcon("share","btnShare slideshowButton",!0))),html+=getIcon("close","slideshowButton btnSlideshowExit hide-mouse-idle-tv",!1),html+="
    ",actionButtonsOnTop||(html+='
    ',html+=getIcon("pause","btnSlideshowPause slideshowButton",!0,!0),appHost.supports("filedownload")&&(html+=getIcon("file_download","btnDownload slideshowButton",!0)),appHost.supports("sharing")&&(html+=getIcon("share","btnShare slideshowButton",!0)),html+="
    "),html+="
    "}else html+='

    ';if(dlg.innerHTML=html,options.interactive){dlg.querySelector(".btnSlideshowExit").addEventListener("click",function(e){dialogHelper.close(dlg)}),dlg.querySelector(".btnSlideshowNext").addEventListener("click",nextImage),dlg.querySelector(".btnSlideshowPrevious").addEventListener("click",previousImage);var btnPause=dlg.querySelector(".btnSlideshowPause");btnPause&&btnPause.addEventListener("click",playPause);var btnDownload=dlg.querySelector(".btnDownload");btnDownload&&btnDownload.addEventListener("click",download);var btnShare=dlg.querySelector(".btnShare");btnShare&&btnShare.addEventListener("click",share)}setUserScalable(!0),dialogHelper.open(dlg).then(function(){setUserScalable(!1),stopInterval()}),inputmanager.on(window,onInputCommand),document.addEventListener(window.PointerEvent?"pointermove":"mousemove",onPointerMove),dlg.addEventListener("close",onDialogClosed),options.interactive&&loadSwiper(dlg)}function loadSwiper(dlg){currentOptions.slides?dlg.querySelector(".swiper-wrapper").innerHTML=currentOptions.slides.map(getSwiperSlideHtmlFromSlide).join(""):dlg.querySelector(".swiper-wrapper").innerHTML=currentOptions.items.map(getSwiperSlideHtmlFromItem).join(""),require(["swiper"],function(swiper){swiperInstance=new Swiper(dlg.querySelector(".slideshowSwiperContainer"),{direction:"horizontal",loop:!1!==options.loop,autoplay:options.interval||8e3,preloadImages:!1,lazyLoading:!0,lazyLoadingInPrevNext:!0,autoplayDisableOnInteraction:!1,initialSlide:options.startIndex||0,speed:240}),layoutManager.mobile?pause():play()})}function getSwiperSlideHtmlFromItem(item){return getSwiperSlideHtmlFromSlide({imageUrl:getImgUrl(item),originalImage:getImgUrl(item,!0),Id:item.Id,ServerId:item.ServerId})}function getSwiperSlideHtmlFromSlide(item){var html="";return html+='
    ',html+='',(item.title||item.subtitle)&&(html+='
    ',html+='
    ',item.title&&(html+='

    ',html+=item.title,html+="

    "),item.description&&(html+='
    ',html+=item.description,html+="
    "),html+="
    ",html+="
    "),html+="
    "}function previousImage(){swiperInstance?swiperInstance.slidePrev():(stopInterval(),showNextImage(currentIndex-1))}function nextImage(){if(swiperInstance){if(!1===options.loop&&swiperInstance.activeIndex>=swiperInstance.slides.length-1)return void dialogHelper.close(dlg);swiperInstance.slideNext()}else stopInterval(),showNextImage(currentIndex+1)}function getCurrentImageInfo(){if(swiperInstance){var slide=document.querySelector(".swiper-slide-active");return slide?{url:slide.getAttribute("data-original"),shareUrl:slide.getAttribute("data-imageurl"),itemId:slide.getAttribute("data-itemid"),serverId:slide.getAttribute("data-serverid")}:null}return null}function download(){var imageInfo=getCurrentImageInfo();require(["fileDownloader"],function(fileDownloader){fileDownloader.download([imageInfo])})}function share(){var imageInfo=getCurrentImageInfo();navigator.share({url:imageInfo.shareUrl})}function play(){var btnSlideshowPause=dlg.querySelector(".btnSlideshowPause i");btnSlideshowPause&&(btnSlideshowPause.innerHTML="pause"),swiperInstance.startAutoplay()}function pause(){var btnSlideshowPause=dlg.querySelector(".btnSlideshowPause i");btnSlideshowPause&&(btnSlideshowPause.innerHTML="play_arrow"),swiperInstance.stopAutoplay()}function playPause(){"pause"!==dlg.querySelector(".btnSlideshowPause i").innerHTML?play():pause()}function onDialogClosed(){var swiper=swiperInstance;swiper&&(swiper.destroy(!0,!0),swiperInstance=null),inputmanager.off(window,onInputCommand),document.removeEventListener(window.PointerEvent?"pointermove":"mousemove",onPointerMove)}function startInterval(options){currentOptions=options,stopInterval(),createElements(options),options.interactive||(currentIntervalMs=options.interval||11e3,showNextImage(options.startIndex||0,!0))}function isOsdOpen(){return _osdOpen}function getOsdBottom(){return dlg.querySelector(".slideshowBottomBar")}function showOsd(){var bottom=getOsdBottom();bottom&&(slideUpToShow(bottom),startHideTimer())}function hideOsd(){var bottom=getOsdBottom();bottom&&slideDownToHide(bottom)}function startHideTimer(){stopHideTimer(),hideTimeout=setTimeout(hideOsd,4e3)}function stopHideTimer(){hideTimeout&&(clearTimeout(hideTimeout),hideTimeout=null)}function slideUpToShow(elem){if(elem.classList.contains("hide")){_osdOpen=!0,elem.classList.remove("hide");var onFinish=function(){focusManager.focus(elem.querySelector(".btnSlideshowPause"))};if(!elem.animate)return void onFinish();requestAnimationFrame(function(){var keyframes=[{transform:"translate3d(0,"+elem.offsetHeight+"px,0)",opacity:".3",offset:0},{transform:"translate3d(0,0,0)",opacity:"1",offset:1}],timing={duration:300,iterations:1,easing:"ease-out"};elem.animate(keyframes,timing).onfinish=onFinish})}}function slideDownToHide(elem){if(!elem.classList.contains("hide")){var onFinish=function(){elem.classList.add("hide"),_osdOpen=!1};if(!elem.animate)return void onFinish();requestAnimationFrame(function(){var keyframes=[{transform:"translate3d(0,0,0)",opacity:"1",offset:0},{transform:"translate3d(0,"+elem.offsetHeight+"px,0)",opacity:".3",offset:1}],timing={duration:300,iterations:1,easing:"ease-out"};elem.animate(keyframes,timing).onfinish=onFinish})}}function onPointerMove(e){if("mouse"===(e.pointerType||(layoutManager.mobile?"touch":"mouse"))){var eventX=e.screenX||0,eventY=e.screenY||0,obj=lastMouseMoveData;if(!obj)return void(lastMouseMoveData={x:eventX,y:eventY});if(Math.abs(eventX-obj.x)<10&&Math.abs(eventY-obj.y)<10)return;obj.x=eventX,obj.y=eventY,showOsd()}}function onInputCommand(e){switch(e.detail.command){case"left":isOsdOpen()||(e.preventDefault(),e.stopPropagation(),previousImage());break;case"right":isOsdOpen()||(e.preventDefault(),e.stopPropagation(),nextImage());break;case"up":case"down":case"select":case"menu":case"info":case"play":case"playpause":case"pause":showOsd()}}function showNextImage(index,skipPreload){index=Math.max(0,index),index>=currentOptions.items.length&&(index=0),currentIndex=index;var options=currentOptions,items=options.items,item=items[index],imgUrl=getImgUrl(item),onSrcLoaded=function(){var cardImageContainer=dlg.querySelector(".slideshowImage"),newCardImageContainer=document.createElement("div");newCardImageContainer.className=cardImageContainer.className,options.cover&&newCardImageContainer.classList.add("slideshowImage-cover"),newCardImageContainer.style.backgroundImage="url('"+imgUrl+"')",newCardImageContainer.classList.add("hide"),cardImageContainer.parentNode.appendChild(newCardImageContainer),options.showTitle?dlg.querySelector(".slideshowImageText").innerHTML=item.Name:dlg.querySelector(".slideshowImageText").innerHTML="",newCardImageContainer.classList.remove("hide");var onAnimationFinished=function(){var parentNode=cardImageContainer.parentNode;parentNode&&parentNode.removeChild(cardImageContainer)};if(newCardImageContainer.animate){var keyframes=[{opacity:"0",offset:0},{opacity:"1",offset:1}],timing={duration:1200,iterations:1};newCardImageContainer.animate(keyframes,timing).onfinish=onAnimationFinished}else onAnimationFinished();stopInterval(),currentTimeout=setTimeout(function(){showNextImage(index+1,!0)},currentIntervalMs)};if(skipPreload)onSrcLoaded();else{var img=new Image;img.onload=onSrcLoaded,img.src=imgUrl}}function stopInterval(){currentTimeout&&(clearTimeout(currentTimeout),currentTimeout=null)}var swiperInstance,dlg,currentTimeout,currentIntervalMs,currentOptions,currentIndex,self=this;browser.chromecast&&(options.interactive=!1);var hideTimeout,lastMouseMoveData,_osdOpen=!1;self.show=function(){startInterval(options)},self.hide=function(){var dialog=dlg;dialog&&dialogHelper.close(dialog)}}}); \ No newline at end of file +define(["dialogHelper", "inputManager", "connectionManager", "layoutManager", "focusManager", "browser", "apphost", "loading", "css!./style", "material-icons", "paper-icon-button-light"], function(dialogHelper, inputmanager, connectionManager, layoutManager, focusManager, browser, appHost, loading) { + "use strict"; + + function getImageUrl(item, options, apiClient) { + return options = options || {}, options.type = options.type || "Primary", "string" == typeof item ? apiClient.getScaledImageUrl(item, options) : item.ImageTags && item.ImageTags[options.type] ? (options.tag = item.ImageTags[options.type], apiClient.getScaledImageUrl(item.Id, options)) : "Primary" === options.type && item.AlbumId && item.AlbumPrimaryImageTag ? (options.tag = item.AlbumPrimaryImageTag, apiClient.getScaledImageUrl(item.AlbumId, options)) : null + } + + function getBackdropImageUrl(item, options, apiClient) { + return options = options || {}, options.type = options.type || "Backdrop", options.maxWidth || options.width || options.maxHeight || options.height || (options.quality = 100), item.BackdropImageTags && item.BackdropImageTags.length ? (options.tag = item.BackdropImageTags[0], apiClient.getScaledImageUrl(item.Id, options)) : null + } + + function getImgUrl(item, original) { + var apiClient = connectionManager.getApiClient(item.ServerId), + imageOptions = {}; + return original || (imageOptions.maxWidth = screen.availWidth), item.BackdropImageTags && item.BackdropImageTags.length ? getBackdropImageUrl(item, imageOptions, apiClient) : "Photo" === item.MediaType && original ? apiClient.getItemDownloadUrl(item.Id) : (imageOptions.type = "Primary", getImageUrl(item, imageOptions, apiClient)) + } + + function getIcon(icon, cssClass, canFocus, autoFocus) { + var tabIndex = canFocus ? "" : ' tabindex="-1"'; + return autoFocus = autoFocus ? " autofocus" : "", '" + } + + function setUserScalable(scalable) { + try { + appHost.setUserScalable(scalable) + } catch (err) { + console.log("error in appHost.setUserScalable: " + err) + } + } + return function(options) { + function createElements(options) { + dlg = dialogHelper.createDialog({ + exitAnimationDuration: options.interactive ? 400 : 800, + size: "fullscreen", + autoFocus: !1, + scrollY: !1, + exitAnimation: "fadeout", + removeOnClose: !0 + }), dlg.classList.add("slideshowDialog"); + var html = ""; + if (options.interactive) { + var actionButtonsOnTop = layoutManager.mobile; + html += "
    ", html += '
    ', html += getIcon("keyboard_arrow_left", "btnSlideshowPrevious slideshowButton hide-mouse-idle-tv", !1), html += getIcon("keyboard_arrow_right", "btnSlideshowNext slideshowButton hide-mouse-idle-tv", !1), html += '
    ', actionButtonsOnTop && (appHost.supports("filedownload") && (html += getIcon("file_download", "btnDownload slideshowButton", !0)), appHost.supports("sharing") && (html += getIcon("share", "btnShare slideshowButton", !0))), html += getIcon("close", "slideshowButton btnSlideshowExit hide-mouse-idle-tv", !1), html += "
    ", actionButtonsOnTop || (html += '
    ', html += getIcon("pause", "btnSlideshowPause slideshowButton", !0, !0), appHost.supports("filedownload") && (html += getIcon("file_download", "btnDownload slideshowButton", !0)), appHost.supports("sharing") && (html += getIcon("share", "btnShare slideshowButton", !0)), html += "
    "), html += "
    " + } else html += '

    '; + if (dlg.innerHTML = html, options.interactive) { + dlg.querySelector(".btnSlideshowExit").addEventListener("click", function(e) { + dialogHelper.close(dlg) + }), dlg.querySelector(".btnSlideshowNext").addEventListener("click", nextImage), dlg.querySelector(".btnSlideshowPrevious").addEventListener("click", previousImage); + var btnPause = dlg.querySelector(".btnSlideshowPause"); + btnPause && btnPause.addEventListener("click", playPause); + var btnDownload = dlg.querySelector(".btnDownload"); + btnDownload && btnDownload.addEventListener("click", download); + var btnShare = dlg.querySelector(".btnShare"); + btnShare && btnShare.addEventListener("click", share) + } + setUserScalable(!0), dialogHelper.open(dlg).then(function() { + setUserScalable(!1), stopInterval() + }), inputmanager.on(window, onInputCommand), document.addEventListener(window.PointerEvent ? "pointermove" : "mousemove", onPointerMove), dlg.addEventListener("close", onDialogClosed), options.interactive && loadSwiper(dlg) + } + + function loadSwiper(dlg) { + currentOptions.slides ? dlg.querySelector(".swiper-wrapper").innerHTML = currentOptions.slides.map(getSwiperSlideHtmlFromSlide).join("") : dlg.querySelector(".swiper-wrapper").innerHTML = currentOptions.items.map(getSwiperSlideHtmlFromItem).join(""), require(["swiper"], function(swiper) { + swiperInstance = new Swiper(dlg.querySelector(".slideshowSwiperContainer"), { + direction: "horizontal", + loop: !1 !== options.loop, + autoplay: options.interval || 8e3, + preloadImages: !1, + lazyLoading: !0, + lazyLoadingInPrevNext: !0, + autoplayDisableOnInteraction: !1, + initialSlide: options.startIndex || 0, + speed: 240 + }), layoutManager.mobile ? pause() : play() + }) + } + + function getSwiperSlideHtmlFromItem(item) { + return getSwiperSlideHtmlFromSlide({ + imageUrl: getImgUrl(item), + originalImage: getImgUrl(item, !0), + Id: item.Id, + ServerId: item.ServerId + }) + } + + function getSwiperSlideHtmlFromSlide(item) { + var html = ""; + return html += '
    ', html += '', (item.title || item.subtitle) && (html += '
    ', html += '
    ', item.title && (html += '

    ', html += item.title, html += "

    "), item.description && (html += '
    ', html += item.description, html += "
    "), html += "
    ", html += "
    "), html += "
    " + } + + function previousImage() { + swiperInstance ? swiperInstance.slidePrev() : (stopInterval(), showNextImage(currentIndex - 1)) + } + + function nextImage() { + if (swiperInstance) { + if (!1 === options.loop && swiperInstance.activeIndex >= swiperInstance.slides.length - 1) return void dialogHelper.close(dlg); + swiperInstance.slideNext() + } else stopInterval(), showNextImage(currentIndex + 1) + } + + function getCurrentImageInfo() { + if (swiperInstance) { + var slide = document.querySelector(".swiper-slide-active"); + return slide ? { + url: slide.getAttribute("data-original"), + shareUrl: slide.getAttribute("data-imageurl"), + itemId: slide.getAttribute("data-itemid"), + serverId: slide.getAttribute("data-serverid") + } : null + } + return null + } + + function download() { + var imageInfo = getCurrentImageInfo(); + require(["fileDownloader"], function(fileDownloader) { + fileDownloader.download([imageInfo]) + }) + } + + function share() { + var imageInfo = getCurrentImageInfo(); + navigator.share({ + url: imageInfo.shareUrl + }) + } + + function play() { + var btnSlideshowPause = dlg.querySelector(".btnSlideshowPause i"); + btnSlideshowPause && (btnSlideshowPause.innerHTML = "pause"), swiperInstance.startAutoplay() + } + + function pause() { + var btnSlideshowPause = dlg.querySelector(".btnSlideshowPause i"); + btnSlideshowPause && (btnSlideshowPause.innerHTML = "play_arrow"), swiperInstance.stopAutoplay() + } + + function playPause() { + "pause" !== dlg.querySelector(".btnSlideshowPause i").innerHTML ? play() : pause() + } + + function onDialogClosed() { + var swiper = swiperInstance; + swiper && (swiper.destroy(!0, !0), swiperInstance = null), inputmanager.off(window, onInputCommand), document.removeEventListener(window.PointerEvent ? "pointermove" : "mousemove", onPointerMove) + } + + function startInterval(options) { + currentOptions = options, stopInterval(), createElements(options), options.interactive || (currentIntervalMs = options.interval || 11e3, showNextImage(options.startIndex || 0, !0)) + } + + function isOsdOpen() { + return _osdOpen + } + + function getOsdBottom() { + return dlg.querySelector(".slideshowBottomBar") + } + + function showOsd() { + var bottom = getOsdBottom(); + bottom && (slideUpToShow(bottom), startHideTimer()) + } + + function hideOsd() { + var bottom = getOsdBottom(); + bottom && slideDownToHide(bottom) + } + + function startHideTimer() { + stopHideTimer(), hideTimeout = setTimeout(hideOsd, 4e3) + } + + function stopHideTimer() { + hideTimeout && (clearTimeout(hideTimeout), hideTimeout = null) + } + + function slideUpToShow(elem) { + if (elem.classList.contains("hide")) { + _osdOpen = !0, elem.classList.remove("hide"); + var onFinish = function() { + focusManager.focus(elem.querySelector(".btnSlideshowPause")) + }; + if (!elem.animate) return void onFinish(); + requestAnimationFrame(function() { + var keyframes = [{ + transform: "translate3d(0," + elem.offsetHeight + "px,0)", + opacity: ".3", + offset: 0 + }, { + transform: "translate3d(0,0,0)", + opacity: "1", + offset: 1 + }], + timing = { + duration: 300, + iterations: 1, + easing: "ease-out" + }; + elem.animate(keyframes, timing).onfinish = onFinish + }) + } + } + + function slideDownToHide(elem) { + if (!elem.classList.contains("hide")) { + var onFinish = function() { + elem.classList.add("hide"), _osdOpen = !1 + }; + if (!elem.animate) return void onFinish(); + requestAnimationFrame(function() { + var keyframes = [{ + transform: "translate3d(0,0,0)", + opacity: "1", + offset: 0 + }, { + transform: "translate3d(0," + elem.offsetHeight + "px,0)", + opacity: ".3", + offset: 1 + }], + timing = { + duration: 300, + iterations: 1, + easing: "ease-out" + }; + elem.animate(keyframes, timing).onfinish = onFinish + }) + } + } + + function onPointerMove(e) { + if ("mouse" === (e.pointerType || (layoutManager.mobile ? "touch" : "mouse"))) { + var eventX = e.screenX || 0, + eventY = e.screenY || 0, + obj = lastMouseMoveData; + if (!obj) return void(lastMouseMoveData = { + x: eventX, + y: eventY + }); + if (Math.abs(eventX - obj.x) < 10 && Math.abs(eventY - obj.y) < 10) return; + obj.x = eventX, obj.y = eventY, showOsd() + } + } + + function onInputCommand(e) { + switch (e.detail.command) { + case "left": + isOsdOpen() || (e.preventDefault(), e.stopPropagation(), previousImage()); + break; + case "right": + isOsdOpen() || (e.preventDefault(), e.stopPropagation(), nextImage()); + break; + case "up": + case "down": + case "select": + case "menu": + case "info": + case "play": + case "playpause": + case "pause": + showOsd() + } + } + + function showNextImage(index, skipPreload) { + index = Math.max(0, index), index >= currentOptions.items.length && (index = 0), currentIndex = index; + var options = currentOptions, + items = options.items, + item = items[index], + imgUrl = getImgUrl(item), + onSrcLoaded = function() { + var cardImageContainer = dlg.querySelector(".slideshowImage"), + newCardImageContainer = document.createElement("div"); + newCardImageContainer.className = cardImageContainer.className, options.cover && newCardImageContainer.classList.add("slideshowImage-cover"), newCardImageContainer.style.backgroundImage = "url('" + imgUrl + "')", newCardImageContainer.classList.add("hide"), cardImageContainer.parentNode.appendChild(newCardImageContainer), options.showTitle ? dlg.querySelector(".slideshowImageText").innerHTML = item.Name : dlg.querySelector(".slideshowImageText").innerHTML = "", newCardImageContainer.classList.remove("hide"); + var onAnimationFinished = function() { + var parentNode = cardImageContainer.parentNode; + parentNode && parentNode.removeChild(cardImageContainer) + }; + if (newCardImageContainer.animate) { + var keyframes = [{ + opacity: "0", + offset: 0 + }, { + opacity: "1", + offset: 1 + }], + timing = { + duration: 1200, + iterations: 1 + }; + newCardImageContainer.animate(keyframes, timing).onfinish = onAnimationFinished + } else onAnimationFinished(); + stopInterval(), currentTimeout = setTimeout(function() { + showNextImage(index + 1, !0) + }, currentIntervalMs) + }; + if (skipPreload) onSrcLoaded(); + else { + var img = new Image; + img.onload = onSrcLoaded, img.src = imgUrl + } + } + + function stopInterval() { + currentTimeout && (clearTimeout(currentTimeout), currentTimeout = null) + } + var swiperInstance, dlg, currentTimeout, currentIntervalMs, currentOptions, currentIndex, self = this; + browser.chromecast && (options.interactive = !1); + var hideTimeout, lastMouseMoveData, _osdOpen = !1; + self.show = function() { + startInterval(options) + }, self.hide = function() { + var dialog = dlg; + dialog && dialogHelper.close(dialog) + } + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/sortmenu/sortmenu.js b/dashboard-ui/bower_components/emby-webcomponents/sortmenu/sortmenu.js index edb77a7be2..b2298230d9 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/sortmenu/sortmenu.js +++ b/dashboard-ui/bower_components/emby-webcomponents/sortmenu/sortmenu.js @@ -1 +1,54 @@ -define(["require","dom","focusManager","dialogHelper","loading","layoutManager","connectionManager","globalize","userSettings","emby-select","paper-icon-button-light","material-icons","css!./../formdialog","emby-button","emby-linkbutton","flexStyles"],function(require,dom,focusManager,dialogHelper,loading,layoutManager,connectionManager,globalize,userSettings){"use strict";function onSubmit(e){return e.preventDefault(),!1}function initEditor(context,settings){context.querySelector("form").addEventListener("submit",onSubmit),context.querySelector(".selectSortOrder").value=settings.sortOrder,context.querySelector(".selectSortBy").value=settings.sortBy}function centerFocus(elem,horiz,on){require(["scrollHelper"],function(scrollHelper){var fn=on?"on":"off";scrollHelper.centerFocus[fn](elem,horiz)})}function fillSortBy(context,options){context.querySelector(".selectSortBy").innerHTML=options.map(function(o){return'"}).join("")}function saveValues(context,settings,settingsKey){userSettings.setFilter(settingsKey+"-sortorder",context.querySelector(".selectSortOrder").value),userSettings.setFilter(settingsKey+"-sortby",context.querySelector(".selectSortBy").value)}function SortMenu(){}return SortMenu.prototype.show=function(options){return new Promise(function(resolve,reject){require(["text!./sortmenu.template.html"],function(template){var dialogOptions={removeOnClose:!0,scrollY:!1};layoutManager.tv?dialogOptions.size="fullscreen":dialogOptions.size="small";var dlg=dialogHelper.createDialog(dialogOptions);dlg.classList.add("formDialog");var html="";html+='
    ',html+='',html+='

    ${Sort}

    ',html+="
    ",html+=template,dlg.innerHTML=globalize.translateDocument(html,"sharedcomponents"),fillSortBy(dlg,options.sortOptions),initEditor(dlg,options.settings),dlg.querySelector(".btnCancel").addEventListener("click",function(){dialogHelper.close(dlg)}),layoutManager.tv&¢erFocus(dlg.querySelector(".formDialogContent"),!1,!0);var submitted;dlg.querySelector("form").addEventListener("change",function(){submitted=!0},!0),dialogHelper.open(dlg).then(function(){if(layoutManager.tv&¢erFocus(dlg.querySelector(".formDialogContent"),!1,!1),submitted)return saveValues(dlg,options.settings,options.settingsKey),void resolve();reject()})})})},SortMenu}); \ No newline at end of file +define(["require", "dom", "focusManager", "dialogHelper", "loading", "layoutManager", "connectionManager", "globalize", "userSettings", "emby-select", "paper-icon-button-light", "material-icons", "css!./../formdialog", "emby-button", "emby-linkbutton", "flexStyles"], function(require, dom, focusManager, dialogHelper, loading, layoutManager, connectionManager, globalize, userSettings) { + "use strict"; + + function onSubmit(e) { + return e.preventDefault(), !1 + } + + function initEditor(context, settings) { + context.querySelector("form").addEventListener("submit", onSubmit), context.querySelector(".selectSortOrder").value = settings.sortOrder, context.querySelector(".selectSortBy").value = settings.sortBy + } + + function centerFocus(elem, horiz, on) { + require(["scrollHelper"], function(scrollHelper) { + var fn = on ? "on" : "off"; + scrollHelper.centerFocus[fn](elem, horiz) + }) + } + + function fillSortBy(context, options) { + context.querySelector(".selectSortBy").innerHTML = options.map(function(o) { + return '" + }).join("") + } + + function saveValues(context, settings, settingsKey) { + userSettings.setFilter(settingsKey + "-sortorder", context.querySelector(".selectSortOrder").value), userSettings.setFilter(settingsKey + "-sortby", context.querySelector(".selectSortBy").value) + } + + function SortMenu() {} + return SortMenu.prototype.show = function(options) { + return new Promise(function(resolve, reject) { + require(["text!./sortmenu.template.html"], function(template) { + var dialogOptions = { + removeOnClose: !0, + scrollY: !1 + }; + layoutManager.tv ? dialogOptions.size = "fullscreen" : dialogOptions.size = "small"; + var dlg = dialogHelper.createDialog(dialogOptions); + dlg.classList.add("formDialog"); + var html = ""; + html += '
    ', html += '', html += '

    ${Sort}

    ', html += "
    ", html += template, dlg.innerHTML = globalize.translateDocument(html, "sharedcomponents"), fillSortBy(dlg, options.sortOptions), initEditor(dlg, options.settings), dlg.querySelector(".btnCancel").addEventListener("click", function() { + dialogHelper.close(dlg) + }), layoutManager.tv && centerFocus(dlg.querySelector(".formDialogContent"), !1, !0); + var submitted; + dlg.querySelector("form").addEventListener("change", function() { + submitted = !0 + }, !0), dialogHelper.open(dlg).then(function() { + if (layoutManager.tv && centerFocus(dlg.querySelector(".formDialogContent"), !1, !1), submitted) return saveValues(dlg, options.settings, options.settingsKey), void resolve(); + reject() + }) + }) + }) + }, SortMenu +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/staticbackdrops.js b/dashboard-ui/bower_components/emby-webcomponents/staticbackdrops.js index d7269beab9..62a9a1f71d 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/staticbackdrops.js +++ b/dashboard-ui/bower_components/emby-webcomponents/staticbackdrops.js @@ -1 +1,66 @@ -define([],function(){"use strict";function getStaticBackdrops(){var list=[];return list.push([{url:"https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/images/wallpaper/bg1-1920.jpg",width:1920}]),list.push([{url:"https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/images/wallpaper/bg2-1920.jpg",width:1920}]),list.push([{url:"https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/images/wallpaper/bg3-1920.jpg",width:1920}]),list.push([{url:"https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/images/wallpaper/bg4-1920.jpg",width:1920}]),list.push([{url:"https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/images/wallpaper/bg5-1920.jpg",width:1920}]),list.push([{url:"https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/images/wallpaper/bg6-1920.jpg",width:1920}]),list.push([{url:"https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/images/wallpaper/bg7-1920.jpg",width:1920}]),list.push([{url:"https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/images/wallpaper/bg8-1920.jpg",width:1920}]),list.push([{url:"https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/images/wallpaper/bg9-1920.jpg",width:1920}]),list.push([{url:"https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/images/wallpaper/bg10-1920.jpg",width:1920}]),list.push([{url:"https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/images/wallpaper/bg11-1920.jpg",width:1920}]),list.push([{url:"https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/images/wallpaper/bg12-1920.jpg",width:1920}]),list.push([{url:"https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/images/wallpaper/bg13-1920.jpg",width:1920}]),list.push([{url:"https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/images/wallpaper/bg14-1920.jpg",width:1920}]),list.push([{url:"https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/images/wallpaper/bg15-1920.jpg",width:1920}]),list}function getRandomInt(min,max){return Math.floor(Math.random()*(max-min+1))+min}function getRandomImageUrl(){var images=getStaticBackdrops();return images[getRandomInt(0,images.length-1)][0].url}return{getStaticBackdrops:getStaticBackdrops,getRandomImageUrl:getRandomImageUrl}}); \ No newline at end of file +define([], function() { + "use strict"; + + function getStaticBackdrops() { + var list = []; + return list.push([{ + url: "https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/images/wallpaper/bg1-1920.jpg", + width: 1920 + }]), list.push([{ + url: "https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/images/wallpaper/bg2-1920.jpg", + width: 1920 + }]), list.push([{ + url: "https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/images/wallpaper/bg3-1920.jpg", + width: 1920 + }]), list.push([{ + url: "https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/images/wallpaper/bg4-1920.jpg", + width: 1920 + }]), list.push([{ + url: "https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/images/wallpaper/bg5-1920.jpg", + width: 1920 + }]), list.push([{ + url: "https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/images/wallpaper/bg6-1920.jpg", + width: 1920 + }]), list.push([{ + url: "https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/images/wallpaper/bg7-1920.jpg", + width: 1920 + }]), list.push([{ + url: "https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/images/wallpaper/bg8-1920.jpg", + width: 1920 + }]), list.push([{ + url: "https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/images/wallpaper/bg9-1920.jpg", + width: 1920 + }]), list.push([{ + url: "https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/images/wallpaper/bg10-1920.jpg", + width: 1920 + }]), list.push([{ + url: "https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/images/wallpaper/bg11-1920.jpg", + width: 1920 + }]), list.push([{ + url: "https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/images/wallpaper/bg12-1920.jpg", + width: 1920 + }]), list.push([{ + url: "https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/images/wallpaper/bg13-1920.jpg", + width: 1920 + }]), list.push([{ + url: "https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/images/wallpaper/bg14-1920.jpg", + width: 1920 + }]), list.push([{ + url: "https://raw.githubusercontent.com/MediaBrowser/Emby.Resources/master/images/wallpaper/bg15-1920.jpg", + width: 1920 + }]), list + } + + function getRandomInt(min, max) { + return Math.floor(Math.random() * (max - min + 1)) + min + } + + function getRandomImageUrl() { + var images = getStaticBackdrops(); + return images[getRandomInt(0, images.length - 1)][0].url + } + return { + getStaticBackdrops: getStaticBackdrops, + getRandomImageUrl: getRandomImageUrl + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/subtitleeditor/subtitleeditor.js b/dashboard-ui/bower_components/emby-webcomponents/subtitleeditor/subtitleeditor.js index 257ce0f39a..65b1a74b6b 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/subtitleeditor/subtitleeditor.js +++ b/dashboard-ui/bower_components/emby-webcomponents/subtitleeditor/subtitleeditor.js @@ -1 +1,187 @@ -define(["dialogHelper","require","layoutManager","globalize","userSettings","connectionManager","loading","focusManager","dom","apphost","emby-select","listViewStyle","paper-icon-button-light","css!./../formdialog","material-icons","css!./subtitleeditor","emby-button","flexStyles"],function(dialogHelper,require,layoutManager,globalize,userSettings,connectionManager,loading,focusManager,dom,appHost){"use strict";function downloadRemoteSubtitles(context,id){var url="Items/"+currentItem.Id+"/RemoteSearch/Subtitles/"+id,apiClient=connectionManager.getApiClient(currentItem.ServerId);apiClient.ajax({type:"POST",url:apiClient.getUrl(url)}).then(function(){hasChanges=!0,require(["toast"],function(toast){toast(globalize.translate("sharedcomponents#MessageDownloadQueued"))}),focusManager.autoFocus(context)})}function deleteLocalSubtitle(context,index){var msg=globalize.translate("sharedcomponents#MessageAreYouSureDeleteSubtitles");require(["confirm"],function(confirm){confirm({title:globalize.translate("sharedcomponents#ConfirmDeletion"),text:msg,confirmText:globalize.translate("sharedcomponents#Delete"),primary:"cancel"}).then(function(){loading.show();var itemId=currentItem.Id,url="Videos/"+itemId+"/Subtitles/"+index,apiClient=connectionManager.getApiClient(currentItem.ServerId);apiClient.ajax({type:"DELETE",url:apiClient.getUrl(url)}).then(function(){hasChanges=!0,reload(context,apiClient,itemId)})})})}function fillSubtitleList(context,item){var streams=item.MediaStreams||[],subs=streams.filter(function(s){return"Subtitle"===s.Type}),html="";subs.length&&(html+="

    "+globalize.translate("sharedcomponents#MySubtitles")+"

    ",html+="
    ",html+=subs.map(function(s){var itemHtml="",tagName=layoutManager.tv?"button":"div",className=layoutManager.tv&&s.Path?"listItem listItem-border btnDelete":"listItem listItem-border";return layoutManager.tv&&(className+=" listItem-focusscale listItem-button"),className+=" listItem-noborder",itemHtml+="<"+tagName+' class="'+className+'" data-index="'+s.Index+'">',itemHtml+='closed_caption',itemHtml+='
    ',itemHtml+="
    ",itemHtml+=s.DisplayTitle||"",itemHtml+="
    ",s.Path&&(itemHtml+='
    '+s.Path+"
    "),itemHtml+="",itemHtml+="
    ",layoutManager.tv||s.Path&&(itemHtml+=''),itemHtml+=""}).join(""),html+="
    ");var elem=context.querySelector(".subtitleList");subs.length?elem.classList.remove("hide"):elem.classList.add("hide"),elem.innerHTML=html}function fillLanguages(context,apiClient,languages){var selectLanguage=context.querySelector("#selectLanguage");selectLanguage.innerHTML=languages.map(function(l){return'"});var lastLanguage=userSettings.get("subtitleeditor-language");lastLanguage?selectLanguage.value=lastLanguage:apiClient.getCurrentUser().then(function(user){var lang=user.Configuration.SubtitleLanguagePreference;lang&&(selectLanguage.value=lang)})}function renderSearchResults(context,results){var lastProvider="",html="";if(!results.length)return context.querySelector(".noSearchResults").classList.remove("hide"),context.querySelector(".subtitleResults").innerHTML="",void loading.hide();context.querySelector(".noSearchResults").classList.add("hide");for(var i=0,length=results.length;i0&&(html+=""),html+="

    "+provider+"

    ",layoutManager.tv,html+="
    ",lastProvider=provider);var tagName=layoutManager.tv?"button":"div",className=layoutManager.tv?"listItem listItem-border btnOptions":"listItem listItem-border";layoutManager.tv&&(className+=" listItem-focusscale listItem-button"),html+="<"+tagName+' class="'+className+'" data-subid="'+result.Id+'">',html+='closed_caption';html+='
    ',html+="
    "+result.Name+"
    ",html+='
    ',result.Format&&(html+=''+globalize.translate("sharedcomponents#FormatValue",result.Format)+""),null!=result.DownloadCount&&(html+=""+globalize.translate("sharedcomponents#DownloadsValue",result.DownloadCount)+""),html+="
    ",result.Comment&&(html+='
    '+result.Comment+"
    "),result.IsHashMatch&&(html+='
    '+globalize.translate("sharedcomponents#PerfectMatch")+"
    "),html+="
    ",layoutManager.tv||(html+=''),html+=""}results.length&&(html+="
    "),context.querySelector(".subtitleResults").innerHTML=html,loading.hide()}function searchForSubtitles(context,language){userSettings.set("subtitleeditor-language",language),loading.show();var apiClient=connectionManager.getApiClient(currentItem.ServerId),url=apiClient.getUrl("Items/"+currentItem.Id+"/RemoteSearch/Subtitles/"+language);apiClient.getJSON(url).then(function(results){renderSearchResults(context,results)})}function reload(context,apiClient,itemId){function onGetItem(item){currentItem=item,fillSubtitleList(context,item);var file=item.Path||"",index=Math.max(file.lastIndexOf("/"),file.lastIndexOf("\\"));index>-1&&(file=file.substring(index+1)),file?(context.querySelector(".pathValue").innerHTML=file,context.querySelector(".originalFile").classList.remove("hide")):(context.querySelector(".pathValue").innerHTML="",context.querySelector(".originalFile").classList.add("hide")),loading.hide()}context.querySelector(".noSearchResults").classList.add("hide"),"string"==typeof itemId?apiClient.getItem(apiClient.getCurrentUserId(),itemId).then(onGetItem):onGetItem(itemId)}function onSearchSubmit(e){var form=this,lang=form.querySelector("#selectLanguage",form).value;return searchForSubtitles(dom.parentWithClass(form,"formDialogContent"),lang),e.preventDefault(),!1}function onSubtitleListClick(e){var btnDelete=dom.parentWithClass(e.target,"btnDelete");if(btnDelete){var index=btnDelete.getAttribute("data-index");deleteLocalSubtitle(dom.parentWithClass(btnDelete,"subtitleEditorDialog"),index)}}function onSubtitleResultsClick(e){var subtitleId,context,btnOptions=dom.parentWithClass(e.target,"btnOptions");btnOptions&&(subtitleId=btnOptions.getAttribute("data-subid"),context=dom.parentWithClass(btnOptions,"subtitleEditorDialog"),showDownloadOptions(btnOptions,context,subtitleId));var btnDownload=dom.parentWithClass(e.target,"btnDownload");btnDownload&&(subtitleId=btnDownload.getAttribute("data-subid"),context=dom.parentWithClass(btnDownload,"subtitleEditorDialog"),downloadRemoteSubtitles(context,subtitleId))}function showDownloadOptions(button,context,subtitleId){var items=[];items.push({name:Globalize.translate("sharedcomponents#Download"),id:"download"}),require(["actionsheet"],function(actionsheet){actionsheet.show({items:items,positionTo:button}).then(function(id){switch(id){case"download":downloadRemoteSubtitles(context,subtitleId)}})})}function centerFocus(elem,horiz,on){require(["scrollHelper"],function(scrollHelper){var fn=on?"on":"off";scrollHelper.centerFocus[fn](elem,horiz)})}function showEditorInternal(itemId,serverId,template){hasChanges=!1;var apiClient=connectionManager.getApiClient(serverId);return apiClient.getItem(apiClient.getCurrentUserId(),itemId).then(function(item){var dialogOptions={removeOnClose:!0,scrollY:!1};layoutManager.tv?dialogOptions.size="fullscreen":dialogOptions.size="small";var dlg=dialogHelper.createDialog(dialogOptions);dlg.classList.add("formDialog"),dlg.classList.add("subtitleEditorDialog"),dlg.innerHTML=globalize.translateDocument(template,"sharedcomponents"),dlg.querySelector(".originalSubtitleFileLabel").innerHTML=globalize.translate("sharedcomponents#File"),dlg.querySelector(".subtitleSearchForm").addEventListener("submit",onSearchSubmit);var btnSubmit=dlg.querySelector(".btnSubmit");layoutManager.tv?(centerFocus(dlg.querySelector(".formDialogContent"),!1,!0),dlg.querySelector(".btnSearchSubtitles").classList.add("hide")):btnSubmit.classList.add("hide");var editorContent=dlg.querySelector(".formDialogContent");return dlg.querySelector(".subtitleList").addEventListener("click",onSubtitleListClick),dlg.querySelector(".subtitleResults").addEventListener("click",onSubtitleResultsClick),apiClient.getCultures().then(function(languages){fillLanguages(editorContent,apiClient,languages)}),dlg.querySelector(".btnCancel").addEventListener("click",function(){dialogHelper.close(dlg)}),new Promise(function(resolve,reject){dlg.addEventListener("close",function(){layoutManager.tv&¢erFocus(dlg.querySelector(".formDialogContent"),!1,!1),hasChanges?resolve():reject()}),dialogHelper.open(dlg),reload(editorContent,apiClient,item)})})}function showEditor(itemId,serverId){return loading.show(),new Promise(function(resolve,reject){require(["text!./subtitleeditor.template.html"],function(template){showEditorInternal(itemId,serverId,template).then(resolve,reject)})})}var currentItem,hasChanges;return{show:showEditor}}); \ No newline at end of file +define(["dialogHelper", "require", "layoutManager", "globalize", "userSettings", "connectionManager", "loading", "focusManager", "dom", "apphost", "emby-select", "listViewStyle", "paper-icon-button-light", "css!./../formdialog", "material-icons", "css!./subtitleeditor", "emby-button", "flexStyles"], function(dialogHelper, require, layoutManager, globalize, userSettings, connectionManager, loading, focusManager, dom, appHost) { + "use strict"; + + function downloadRemoteSubtitles(context, id) { + var url = "Items/" + currentItem.Id + "/RemoteSearch/Subtitles/" + id, + apiClient = connectionManager.getApiClient(currentItem.ServerId); + apiClient.ajax({ + type: "POST", + url: apiClient.getUrl(url) + }).then(function() { + hasChanges = !0, require(["toast"], function(toast) { + toast(globalize.translate("sharedcomponents#MessageDownloadQueued")) + }), focusManager.autoFocus(context) + }) + } + + function deleteLocalSubtitle(context, index) { + var msg = globalize.translate("sharedcomponents#MessageAreYouSureDeleteSubtitles"); + require(["confirm"], function(confirm) { + confirm({ + title: globalize.translate("sharedcomponents#ConfirmDeletion"), + text: msg, + confirmText: globalize.translate("sharedcomponents#Delete"), + primary: "cancel" + }).then(function() { + loading.show(); + var itemId = currentItem.Id, + url = "Videos/" + itemId + "/Subtitles/" + index, + apiClient = connectionManager.getApiClient(currentItem.ServerId); + apiClient.ajax({ + type: "DELETE", + url: apiClient.getUrl(url) + }).then(function() { + hasChanges = !0, reload(context, apiClient, itemId) + }) + }) + }) + } + + function fillSubtitleList(context, item) { + var streams = item.MediaStreams || [], + subs = streams.filter(function(s) { + return "Subtitle" === s.Type + }), + html = ""; + subs.length && (html += "

    " + globalize.translate("sharedcomponents#MySubtitles") + "

    ", html += "
    ", html += subs.map(function(s) { + var itemHtml = "", + tagName = layoutManager.tv ? "button" : "div", + className = layoutManager.tv && s.Path ? "listItem listItem-border btnDelete" : "listItem listItem-border"; + return layoutManager.tv && (className += " listItem-focusscale listItem-button"), className += " listItem-noborder", itemHtml += "<" + tagName + ' class="' + className + '" data-index="' + s.Index + '">', itemHtml += 'closed_caption', itemHtml += '
    ', itemHtml += "
    ", itemHtml += s.DisplayTitle || "", itemHtml += "
    ", s.Path && (itemHtml += '
    ' + s.Path + "
    "), itemHtml += "", itemHtml += "
    ", layoutManager.tv || s.Path && (itemHtml += ''), itemHtml += "" + }).join(""), html += "
    "); + var elem = context.querySelector(".subtitleList"); + subs.length ? elem.classList.remove("hide") : elem.classList.add("hide"), elem.innerHTML = html + } + + function fillLanguages(context, apiClient, languages) { + var selectLanguage = context.querySelector("#selectLanguage"); + selectLanguage.innerHTML = languages.map(function(l) { + return '" + }); + var lastLanguage = userSettings.get("subtitleeditor-language"); + lastLanguage ? selectLanguage.value = lastLanguage : apiClient.getCurrentUser().then(function(user) { + var lang = user.Configuration.SubtitleLanguagePreference; + lang && (selectLanguage.value = lang) + }) + } + + function renderSearchResults(context, results) { + var lastProvider = "", + html = ""; + if (!results.length) return context.querySelector(".noSearchResults").classList.remove("hide"), context.querySelector(".subtitleResults").innerHTML = "", void loading.hide(); + context.querySelector(".noSearchResults").classList.add("hide"); + for (var i = 0, length = results.length; i < length; i++) { + var result = results[i], + provider = result.ProviderName; + provider !== lastProvider && (i > 0 && (html += ""), html += "

    " + provider + "

    ", layoutManager.tv, html += "
    ", lastProvider = provider); + var tagName = layoutManager.tv ? "button" : "div", + className = layoutManager.tv ? "listItem listItem-border btnOptions" : "listItem listItem-border"; + layoutManager.tv && (className += " listItem-focusscale listItem-button"), html += "<" + tagName + ' class="' + className + '" data-subid="' + result.Id + '">', html += 'closed_caption'; + html += '
    ', html += "
    " + result.Name + "
    ", html += '
    ', result.Format && (html += '' + globalize.translate("sharedcomponents#FormatValue", result.Format) + ""), null != result.DownloadCount && (html += "" + globalize.translate("sharedcomponents#DownloadsValue", result.DownloadCount) + ""), html += "
    ", result.Comment && (html += '
    ' + result.Comment + "
    "), result.IsHashMatch && (html += '
    ' + globalize.translate("sharedcomponents#PerfectMatch") + "
    "), html += "
    ", layoutManager.tv || (html += ''), html += "" + } + results.length && (html += "
    "), context.querySelector(".subtitleResults").innerHTML = html, loading.hide() + } + + function searchForSubtitles(context, language) { + userSettings.set("subtitleeditor-language", language), loading.show(); + var apiClient = connectionManager.getApiClient(currentItem.ServerId), + url = apiClient.getUrl("Items/" + currentItem.Id + "/RemoteSearch/Subtitles/" + language); + apiClient.getJSON(url).then(function(results) { + renderSearchResults(context, results) + }) + } + + function reload(context, apiClient, itemId) { + function onGetItem(item) { + currentItem = item, fillSubtitleList(context, item); + var file = item.Path || "", + index = Math.max(file.lastIndexOf("/"), file.lastIndexOf("\\")); + index > -1 && (file = file.substring(index + 1)), file ? (context.querySelector(".pathValue").innerHTML = file, context.querySelector(".originalFile").classList.remove("hide")) : (context.querySelector(".pathValue").innerHTML = "", context.querySelector(".originalFile").classList.add("hide")), loading.hide() + } + context.querySelector(".noSearchResults").classList.add("hide"), "string" == typeof itemId ? apiClient.getItem(apiClient.getCurrentUserId(), itemId).then(onGetItem) : onGetItem(itemId) + } + + function onSearchSubmit(e) { + var form = this, + lang = form.querySelector("#selectLanguage", form).value; + return searchForSubtitles(dom.parentWithClass(form, "formDialogContent"), lang), e.preventDefault(), !1 + } + + function onSubtitleListClick(e) { + var btnDelete = dom.parentWithClass(e.target, "btnDelete"); + if (btnDelete) { + var index = btnDelete.getAttribute("data-index"); + deleteLocalSubtitle(dom.parentWithClass(btnDelete, "subtitleEditorDialog"), index) + } + } + + function onSubtitleResultsClick(e) { + var subtitleId, context, btnOptions = dom.parentWithClass(e.target, "btnOptions"); + btnOptions && (subtitleId = btnOptions.getAttribute("data-subid"), context = dom.parentWithClass(btnOptions, "subtitleEditorDialog"), showDownloadOptions(btnOptions, context, subtitleId)); + var btnDownload = dom.parentWithClass(e.target, "btnDownload"); + btnDownload && (subtitleId = btnDownload.getAttribute("data-subid"), context = dom.parentWithClass(btnDownload, "subtitleEditorDialog"), downloadRemoteSubtitles(context, subtitleId)) + } + + function showDownloadOptions(button, context, subtitleId) { + var items = []; + items.push({ + name: Globalize.translate("sharedcomponents#Download"), + id: "download" + }), require(["actionsheet"], function(actionsheet) { + actionsheet.show({ + items: items, + positionTo: button + }).then(function(id) { + switch (id) { + case "download": + downloadRemoteSubtitles(context, subtitleId) + } + }) + }) + } + + function centerFocus(elem, horiz, on) { + require(["scrollHelper"], function(scrollHelper) { + var fn = on ? "on" : "off"; + scrollHelper.centerFocus[fn](elem, horiz) + }) + } + + function showEditorInternal(itemId, serverId, template) { + hasChanges = !1; + var apiClient = connectionManager.getApiClient(serverId); + return apiClient.getItem(apiClient.getCurrentUserId(), itemId).then(function(item) { + var dialogOptions = { + removeOnClose: !0, + scrollY: !1 + }; + layoutManager.tv ? dialogOptions.size = "fullscreen" : dialogOptions.size = "small"; + var dlg = dialogHelper.createDialog(dialogOptions); + dlg.classList.add("formDialog"), dlg.classList.add("subtitleEditorDialog"), dlg.innerHTML = globalize.translateDocument(template, "sharedcomponents"), dlg.querySelector(".originalSubtitleFileLabel").innerHTML = globalize.translate("sharedcomponents#File"), dlg.querySelector(".subtitleSearchForm").addEventListener("submit", onSearchSubmit); + var btnSubmit = dlg.querySelector(".btnSubmit"); + layoutManager.tv ? (centerFocus(dlg.querySelector(".formDialogContent"), !1, !0), dlg.querySelector(".btnSearchSubtitles").classList.add("hide")) : btnSubmit.classList.add("hide"); + var editorContent = dlg.querySelector(".formDialogContent"); + return dlg.querySelector(".subtitleList").addEventListener("click", onSubtitleListClick), dlg.querySelector(".subtitleResults").addEventListener("click", onSubtitleResultsClick), apiClient.getCultures().then(function(languages) { + fillLanguages(editorContent, apiClient, languages) + }), dlg.querySelector(".btnCancel").addEventListener("click", function() { + dialogHelper.close(dlg) + }), new Promise(function(resolve, reject) { + dlg.addEventListener("close", function() { + layoutManager.tv && centerFocus(dlg.querySelector(".formDialogContent"), !1, !1), hasChanges ? resolve() : reject() + }), dialogHelper.open(dlg), reload(editorContent, apiClient, item) + }) + }) + } + + function showEditor(itemId, serverId) { + return loading.show(), new Promise(function(resolve, reject) { + require(["text!./subtitleeditor.template.html"], function(template) { + showEditorInternal(itemId, serverId, template).then(resolve, reject) + }) + }) + } + var currentItem, hasChanges; + return { + show: showEditor + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/subtitlesettings/subtitleappearancehelper.js b/dashboard-ui/bower_components/emby-webcomponents/subtitlesettings/subtitleappearancehelper.js index f3fc5b9b4f..cfd79fd9fa 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/subtitlesettings/subtitleappearancehelper.js +++ b/dashboard-ui/bower_components/emby-webcomponents/subtitlesettings/subtitleappearancehelper.js @@ -1 +1,211 @@ -define([],function(){"use strict";function getTextStyles(settings,isCue){var list=[];if(isCue)switch(settings.textSize||""){case"smaller":list.push({name:"font-size",value:".5em"});break;case"small":list.push({name:"font-size",value:".7em"});break;case"large":list.push({name:"font-size",value:"1.3em"});break;case"larger":list.push({name:"font-size",value:"1.72em"});break;case"extralarge":list.push({name:"font-size",value:"2em"});break;default:case"medium":}else switch(settings.textSize||""){case"smaller":list.push({name:"font-size",value:".8em"});break;case"small":list.push({name:"font-size",value:"inherit"});break;case"larger":list.push({name:"font-size",value:"2em"});break;case"extralarge":list.push({name:"font-size",value:"2.2em"});break;case"large":list.push({name:"font-size",value:"1.72em"});break;default:case"medium":list.push({name:"font-size",value:"1.36em"})}switch(settings.dropShadow||""){case"raised":list.push({name:"text-shadow",value:"-1px -1px white, 0px -1px white, -1px 0px white, 1px 1px black, 0px 1px black, 1px 0px black"});break;case"depressed":list.push({name:"text-shadow",value:"1px 1px white, 0px 1px white, 1px 0px white, -1px -1px black, 0px -1px black, -1px 0px black"});break;case"uniform":list.push({name:"text-shadow",value:"-1px 0px #000000, 0px 1px #000000, 1px 0px #000000, 0px -1px #000000"});break;case"none":list.push({name:"text-shadow",value:"none"});break;default:case"dropshadow":list.push({name:"text-shadow",value:"#000000 0px 0px 7px"})}var background=settings.textBackground||"transparent";background&&list.push({name:"background-color",value:background});var textColor=settings.textColor||"#ffffff";switch(textColor&&list.push({name:"color",value:textColor}),settings.font||""){case"typewriter":list.push({name:"font-family",value:'"Courier New",monospace'}),list.push({name:"font-variant",value:"none"});break;case"print":list.push({name:"font-family",value:"Georgia,Times New Roman,Arial,Helvetica,serif"}),list.push({name:"font-variant",value:"none"});break;case"console":list.push({name:"font-family",value:"Consolas,Lucida Console,Menlo,Monaco,monospace"}),list.push({name:"font-variant",value:"none"});break;case"cursive":list.push({name:"font-family",value:"Lucida Handwriting,Brush Script MT,Segoe Script,cursive,Quintessential,system-ui,-apple-system,BlinkMacSystemFont,sans-serif"}),list.push({name:"font-variant",value:"none"});break;case"casual":list.push({name:"font-family",value:"Gabriola,Segoe Print,Comic Sans MS,Chalkboard,Short Stack,system-ui,-apple-system,BlinkMacSystemFont,sans-serif"}),list.push({name:"font-variant",value:"none"});break;case"smallcaps":list.push({name:"font-family",value:"Copperplate Gothic,Copperplate Gothic Bold,Copperplate,system-ui,-apple-system,BlinkMacSystemFont,sans-serif"}),list.push({name:"font-variant",value:"small-caps"});break;default:list.push({name:"font-family",value:"inherit"}),list.push({name:"font-variant",value:"none"})}return list}function getWindowStyles(settings){return[]}function getStyles(settings,isCue){return{text:getTextStyles(settings,isCue),window:getWindowStyles(settings)}}function applyStyleList(styles,elem){for(var i=0,length=styles.length;i";for(var i=0,length=languages.length;i"+culture.DisplayName+""}select.innerHTML=html}function getSubtitleAppearanceObject(context){var appearanceSettings={};return appearanceSettings.textSize=context.querySelector("#selectTextSize").value,appearanceSettings.dropShadow=context.querySelector("#selectDropShadow").value,appearanceSettings.font=context.querySelector("#selectFont").value,appearanceSettings.textBackground=context.querySelector("#inputTextBackground").value,appearanceSettings.textColor=context.querySelector("#inputTextColor").value,appearanceSettings}function loadForm(context,user,userSettings,appearanceSettings,apiClient){apiClient.getCultures().then(function(allCultures){appHost.supports("subtitleburnsettings")&&user.Policy.EnableVideoPlaybackTranscoding&&context.querySelector(".fldBurnIn").classList.remove("hide");var selectSubtitleLanguage=context.querySelector("#selectSubtitleLanguage");populateLanguages(selectSubtitleLanguage,allCultures),selectSubtitleLanguage.value=user.Configuration.SubtitleLanguagePreference||"",context.querySelector("#selectSubtitlePlaybackMode").value=user.Configuration.SubtitleMode||"",context.querySelector("#selectSubtitlePlaybackMode").dispatchEvent(new CustomEvent("change",{})),context.querySelector("#selectTextSize").value=appearanceSettings.textSize||"",context.querySelector("#selectDropShadow").value=appearanceSettings.dropShadow||"",context.querySelector("#inputTextBackground").value=appearanceSettings.textBackground||"transparent",context.querySelector("#inputTextColor").value=appearanceSettings.textColor||"#ffffff",context.querySelector("#selectFont").value=appearanceSettings.font||"",context.querySelector("#selectSubtitleBurnIn").value=appSettings.get("subtitleburnin")||"",onAppearanceFieldChange({target:context.querySelector("#selectTextSize")}),loading.hide()})}function saveUser(context,user,userSettingsInstance,appearanceKey,apiClient){var appearanceSettings=userSettingsInstance.getSubtitleAppearanceSettings(appearanceKey);return appearanceSettings=Object.assign(appearanceSettings,getSubtitleAppearanceObject(context)),userSettingsInstance.setSubtitleAppearanceSettings(appearanceSettings,appearanceKey),user.Configuration.SubtitleLanguagePreference=context.querySelector("#selectSubtitleLanguage").value,user.Configuration.SubtitleMode=context.querySelector("#selectSubtitlePlaybackMode").value,apiClient.updateUserConfiguration(user.Id,user.Configuration)}function save(instance,context,userId,userSettings,apiClient,enableSaveConfirmation){loading.show(),appSettings.set("subtitleburnin",context.querySelector("#selectSubtitleBurnIn").value),apiClient.getUser(userId).then(function(user){saveUser(context,user,userSettings,instance.appearanceKey,apiClient).then(function(){loading.hide(),enableSaveConfirmation&&require(["toast"],function(toast){toast(globalize.translate("sharedcomponents#SettingsSaved"))}),events.trigger(instance,"saved")},function(){loading.hide()})})}function onSubmit(e){var self=this,apiClient=connectionManager.getApiClient(self.options.serverId),userId=self.options.userId,userSettings=self.options.userSettings;return userSettings.setUserInfo(userId,apiClient).then(function(){var enableSaveConfirmation=self.options.enableSaveConfirmation;save(self,self.options.element,userId,userSettings,apiClient,enableSaveConfirmation)}),e&&e.preventDefault(),!1}function onSubtitleModeChange(e){for(var view=dom.parentWithClass(e.target,"subtitlesettings"),subtitlesHelp=view.querySelectorAll(".subtitlesHelp"),i=0,length=subtitlesHelp.length;i"; + for (var i = 0, length = languages.length; i < length; i++) { + var culture = languages[i]; + html += "" + } + select.innerHTML = html + } + + function getSubtitleAppearanceObject(context) { + var appearanceSettings = {}; + return appearanceSettings.textSize = context.querySelector("#selectTextSize").value, appearanceSettings.dropShadow = context.querySelector("#selectDropShadow").value, appearanceSettings.font = context.querySelector("#selectFont").value, appearanceSettings.textBackground = context.querySelector("#inputTextBackground").value, appearanceSettings.textColor = context.querySelector("#inputTextColor").value, appearanceSettings + } + + function loadForm(context, user, userSettings, appearanceSettings, apiClient) { + apiClient.getCultures().then(function(allCultures) { + appHost.supports("subtitleburnsettings") && user.Policy.EnableVideoPlaybackTranscoding && context.querySelector(".fldBurnIn").classList.remove("hide"); + var selectSubtitleLanguage = context.querySelector("#selectSubtitleLanguage"); + populateLanguages(selectSubtitleLanguage, allCultures), selectSubtitleLanguage.value = user.Configuration.SubtitleLanguagePreference || "", context.querySelector("#selectSubtitlePlaybackMode").value = user.Configuration.SubtitleMode || "", context.querySelector("#selectSubtitlePlaybackMode").dispatchEvent(new CustomEvent("change", {})), context.querySelector("#selectTextSize").value = appearanceSettings.textSize || "", context.querySelector("#selectDropShadow").value = appearanceSettings.dropShadow || "", context.querySelector("#inputTextBackground").value = appearanceSettings.textBackground || "transparent", context.querySelector("#inputTextColor").value = appearanceSettings.textColor || "#ffffff", context.querySelector("#selectFont").value = appearanceSettings.font || "", context.querySelector("#selectSubtitleBurnIn").value = appSettings.get("subtitleburnin") || "", onAppearanceFieldChange({ + target: context.querySelector("#selectTextSize") + }), loading.hide() + }) + } + + function saveUser(context, user, userSettingsInstance, appearanceKey, apiClient) { + var appearanceSettings = userSettingsInstance.getSubtitleAppearanceSettings(appearanceKey); + return appearanceSettings = Object.assign(appearanceSettings, getSubtitleAppearanceObject(context)), userSettingsInstance.setSubtitleAppearanceSettings(appearanceSettings, appearanceKey), user.Configuration.SubtitleLanguagePreference = context.querySelector("#selectSubtitleLanguage").value, user.Configuration.SubtitleMode = context.querySelector("#selectSubtitlePlaybackMode").value, apiClient.updateUserConfiguration(user.Id, user.Configuration) + } + + function save(instance, context, userId, userSettings, apiClient, enableSaveConfirmation) { + loading.show(), appSettings.set("subtitleburnin", context.querySelector("#selectSubtitleBurnIn").value), apiClient.getUser(userId).then(function(user) { + saveUser(context, user, userSettings, instance.appearanceKey, apiClient).then(function() { + loading.hide(), enableSaveConfirmation && require(["toast"], function(toast) { + toast(globalize.translate("sharedcomponents#SettingsSaved")) + }), events.trigger(instance, "saved") + }, function() { + loading.hide() + }) + }) + } + + function onSubmit(e) { + var self = this, + apiClient = connectionManager.getApiClient(self.options.serverId), + userId = self.options.userId, + userSettings = self.options.userSettings; + return userSettings.setUserInfo(userId, apiClient).then(function() { + var enableSaveConfirmation = self.options.enableSaveConfirmation; + save(self, self.options.element, userId, userSettings, apiClient, enableSaveConfirmation) + }), e && e.preventDefault(), !1 + } + + function onSubtitleModeChange(e) { + for (var view = dom.parentWithClass(e.target, "subtitlesettings"), subtitlesHelp = view.querySelectorAll(".subtitlesHelp"), i = 0, length = subtitlesHelp.length; i < length; i++) subtitlesHelp[i].classList.add("hide"); + view.querySelector(".subtitles" + this.value + "Help").classList.remove("hide") + } + + function onAppearanceFieldChange(e) { + var view = dom.parentWithClass(e.target, "subtitlesettings"), + appearanceSettings = getSubtitleAppearanceObject(view), + elements = { + window: view.querySelector(".subtitleappearance-preview-window"), + text: view.querySelector(".subtitleappearance-preview-text") + }; + subtitleAppearanceHelper.applyStyles(elements, appearanceSettings) + } + + function embed(options, self) { + require(["text!./subtitlesettings.template.html"], function(template) { + options.element.classList.add("subtitlesettings"), options.element.innerHTML = globalize.translateDocument(template, "sharedcomponents"), options.element.querySelector("form").addEventListener("submit", onSubmit.bind(self)), options.element.querySelector("#selectSubtitlePlaybackMode").addEventListener("change", onSubtitleModeChange), options.element.querySelector("#selectTextSize").addEventListener("change", onAppearanceFieldChange), options.element.querySelector("#selectDropShadow").addEventListener("change", onAppearanceFieldChange), options.element.querySelector("#selectFont").addEventListener("change", onAppearanceFieldChange), options.element.querySelector("#inputTextColor").addEventListener("change", onAppearanceFieldChange), options.element.querySelector("#inputTextBackground").addEventListener("change", onAppearanceFieldChange), options.enableSaveButton && options.element.querySelector(".btnSave").classList.remove("hide"), appHost.supports("subtitleappearancesettings") && options.element.querySelector(".subtitleAppearanceSection").classList.remove("hide"), self.loadData(), options.autoFocus && focusManager.autoFocus(options.element) + }) + } + + function SubtitleSettings(options) { + this.options = options, embed(options, this) + } + return SubtitleSettings.prototype.loadData = function() { + var self = this, + context = self.options.element; + loading.show(); + var userId = self.options.userId, + apiClient = connectionManager.getApiClient(self.options.serverId), + userSettings = self.options.userSettings; + apiClient.getUser(userId).then(function(user) { + userSettings.setUserInfo(userId, apiClient).then(function() { + self.dataLoaded = !0; + var appearanceSettings = userSettings.getSubtitleAppearanceSettings(self.options.appearanceKey); + loadForm(context, user, userSettings, appearanceSettings, apiClient) + }) + }) + }, SubtitleSettings.prototype.submit = function() { + onSubmit.call(this) + }, SubtitleSettings.prototype.destroy = function() { + this.options = null + }, SubtitleSettings +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/sync/emby-downloadbutton.js b/dashboard-ui/bower_components/emby-webcomponents/sync/emby-downloadbutton.js index fef243fcfc..9c1c37da08 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/sync/emby-downloadbutton.js +++ b/dashboard-ui/bower_components/emby-webcomponents/sync/emby-downloadbutton.js @@ -1 +1,71 @@ -define(["connectionManager","serverNotifications","events","globalize","emby-button"],function(connectionManager,serverNotifications,events,globalize,EmbyButtonPrototype){"use strict";function onClick(e){var button=this,id=button.getAttribute("data-id"),serverId=button.getAttribute("data-serverid"),apiClient=connectionManager.getApiClient(serverId);button.classList.contains("downloadbutton-on")?require(["confirm"],function(confirm){confirm({text:globalize.translate("sharedcomponents#ConfirmRemoveDownload"),confirmText:globalize.translate("sharedcomponents#RemoveDownload"),cancelText:globalize.translate("sharedcomponents#KeepDownload"),primary:"cancel"}).then(function(){apiClient.cancelSyncItems([id]),button.dispatchEvent(new CustomEvent("download-cancel",{cancelable:!1}))})}):require(["syncDialog"],function(syncDialog){syncDialog.showMenu({items:[id],mode:"download",serverId:serverId}).then(function(){button.dispatchEvent(new CustomEvent("download",{cancelable:!1}))})})}function updateSyncStatus(button,syncPercent){var icon=button.iconElement;icon||(button.iconElement=button.querySelector("i"),icon=button.iconElement),null!=syncPercent?(button.classList.add("downloadbutton-on"),icon&&icon.classList.add("downloadbutton-icon-on")):(button.classList.remove("downloadbutton-on"),icon&&icon.classList.remove("downloadbutton-icon-on")),(syncPercent||0)>=100?(button.classList.add("downloadbutton-complete"),icon&&icon.classList.add("downloadbutton-icon-complete")):(button.classList.remove("downloadbutton-complete"),icon&&icon.classList.remove("downloadbutton-icon-complete"));var text;text=(syncPercent||0)>=100?globalize.translate("sharedcomponents#Downloaded"):null!=syncPercent?globalize.translate("sharedcomponents#Downloading"):globalize.translate("sharedcomponents#Download");var textElement=button.querySelector(".emby-downloadbutton-downloadtext");textElement&&(textElement.innerHTML=text),button.title=text}function clearEvents(button){button.removeEventListener("click",onClick)}function bindEvents(button){clearEvents(button),button.addEventListener("click",onClick)}function fetchAndUpdate(button,item){connectionManager.getApiClient(item.ServerId).getSyncStatus(item.Id).then(function(result){updateSyncStatus(button,result.Progress)},function(){})}var EmbyDownloadButtonPrototype=Object.create(EmbyButtonPrototype);EmbyDownloadButtonPrototype.createdCallback=function(){EmbyButtonPrototype.createdCallback&&EmbyButtonPrototype.createdCallback.call(this)},EmbyDownloadButtonPrototype.attachedCallback=function(){EmbyButtonPrototype.attachedCallback&&EmbyButtonPrototype.attachedCallback.call(this);var itemId=this.getAttribute("data-id"),serverId=this.getAttribute("data-serverid");itemId&&serverId&&bindEvents(this)},EmbyDownloadButtonPrototype.detachedCallback=function(){EmbyButtonPrototype.detachedCallback&&EmbyButtonPrototype.detachedCallback.call(this),clearEvents(this),this.iconElement=null},EmbyDownloadButtonPrototype.setItem=function(item){item?(this.setAttribute("data-id",item.Id),this.setAttribute("data-serverid",item.ServerId),fetchAndUpdate(this,item),bindEvents(this)):(this.removeAttribute("data-id"),this.removeAttribute("data-serverid"),clearEvents(this))},document.registerElement("emby-downloadbutton",{prototype:EmbyDownloadButtonPrototype,extends:"button"})}); \ No newline at end of file +define(["connectionManager", "serverNotifications", "events", "globalize", "emby-button"], function(connectionManager, serverNotifications, events, globalize, EmbyButtonPrototype) { + "use strict"; + + function onClick(e) { + var button = this, + id = button.getAttribute("data-id"), + serverId = button.getAttribute("data-serverid"), + apiClient = connectionManager.getApiClient(serverId); + button.classList.contains("downloadbutton-on") ? require(["confirm"], function(confirm) { + confirm({ + text: globalize.translate("sharedcomponents#ConfirmRemoveDownload"), + confirmText: globalize.translate("sharedcomponents#RemoveDownload"), + cancelText: globalize.translate("sharedcomponents#KeepDownload"), + primary: "cancel" + }).then(function() { + apiClient.cancelSyncItems([id]), button.dispatchEvent(new CustomEvent("download-cancel", { + cancelable: !1 + })) + }) + }) : require(["syncDialog"], function(syncDialog) { + syncDialog.showMenu({ + items: [id], + mode: "download", + serverId: serverId + }).then(function() { + button.dispatchEvent(new CustomEvent("download", { + cancelable: !1 + })) + }) + }) + } + + function updateSyncStatus(button, syncPercent) { + var icon = button.iconElement; + icon || (button.iconElement = button.querySelector("i"), icon = button.iconElement), null != syncPercent ? (button.classList.add("downloadbutton-on"), icon && icon.classList.add("downloadbutton-icon-on")) : (button.classList.remove("downloadbutton-on"), icon && icon.classList.remove("downloadbutton-icon-on")), (syncPercent || 0) >= 100 ? (button.classList.add("downloadbutton-complete"), icon && icon.classList.add("downloadbutton-icon-complete")) : (button.classList.remove("downloadbutton-complete"), icon && icon.classList.remove("downloadbutton-icon-complete")); + var text; + text = (syncPercent || 0) >= 100 ? globalize.translate("sharedcomponents#Downloaded") : null != syncPercent ? globalize.translate("sharedcomponents#Downloading") : globalize.translate("sharedcomponents#Download"); + var textElement = button.querySelector(".emby-downloadbutton-downloadtext"); + textElement && (textElement.innerHTML = text), button.title = text + } + + function clearEvents(button) { + button.removeEventListener("click", onClick) + } + + function bindEvents(button) { + clearEvents(button), button.addEventListener("click", onClick) + } + + function fetchAndUpdate(button, item) { + connectionManager.getApiClient(item.ServerId).getSyncStatus(item.Id).then(function(result) { + updateSyncStatus(button, result.Progress) + }, function() {}) + } + var EmbyDownloadButtonPrototype = Object.create(EmbyButtonPrototype); + EmbyDownloadButtonPrototype.createdCallback = function() { + EmbyButtonPrototype.createdCallback && EmbyButtonPrototype.createdCallback.call(this) + }, EmbyDownloadButtonPrototype.attachedCallback = function() { + EmbyButtonPrototype.attachedCallback && EmbyButtonPrototype.attachedCallback.call(this); + var itemId = this.getAttribute("data-id"), + serverId = this.getAttribute("data-serverid"); + itemId && serverId && bindEvents(this) + }, EmbyDownloadButtonPrototype.detachedCallback = function() { + EmbyButtonPrototype.detachedCallback && EmbyButtonPrototype.detachedCallback.call(this), clearEvents(this), this.iconElement = null + }, EmbyDownloadButtonPrototype.setItem = function(item) { + item ? (this.setAttribute("data-id", item.Id), this.setAttribute("data-serverid", item.ServerId), fetchAndUpdate(this, item), bindEvents(this)) : (this.removeAttribute("data-id"), this.removeAttribute("data-serverid"), clearEvents(this)) + }, document.registerElement("emby-downloadbutton", { + prototype: EmbyDownloadButtonPrototype, + extends: "button" + }) +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/sync/sync.js b/dashboard-ui/bower_components/emby-webcomponents/sync/sync.js index eb76e14715..a50370da8c 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/sync/sync.js +++ b/dashboard-ui/bower_components/emby-webcomponents/sync/sync.js @@ -1 +1,295 @@ -define(["apphost","globalize","connectionManager","layoutManager","focusManager","scrollHelper","appSettings","registrationServices","dialogHelper","paper-icon-button-light","formDialogStyle"],function(appHost,globalize,connectionManager,layoutManager,focusManager,scrollHelper,appSettings,registrationServices,dialogHelper){"use strict";function submitJob(dlg,apiClient,userId,syncOptions,form){if(!userId)throw new Error("userId cannot be null");if(!syncOptions)throw new Error("syncOptions cannot be null");if(!form)throw new Error("form cannot be null");var selectSyncTarget=form.querySelector("#selectSyncTarget"),target=selectSyncTarget?selectSyncTarget.value:null;if(!target)return require(["toast"],function(toast){toast(globalize.translate("sharedcomponents#PleaseSelectDeviceToSyncTo"))}),!1;var options={userId:userId,TargetId:target,ParentId:syncOptions.ParentId,Category:syncOptions.Category};return setJobValues(options,form),syncOptions.items&&syncOptions.items.length&&(options.ItemIds=(syncOptions.items||[]).map(function(i){return i.Id||i}).join(",")),apiClient.ajax({type:"POST",url:apiClient.getUrl("Sync/Jobs"),data:JSON.stringify(options),contentType:"application/json",dataType:"json"}).then(function(){dialogHelper.close(dlg),require(["toast"],function(toast){showSubmissionToast(target,apiClient),"download"===syncOptions.mode&&syncNow()})}),!0}function showSubmissionToast(targetId,apiClient){require(["toast"],function(toast){toast(targetId===apiClient.deviceId()?globalize.translate("sharedcomponents#DownloadingDots"):globalize.translate("sharedcomponents#SyncingDots"))})}function syncNow(){require(["localsync"],function(localSync){localSync.sync()})}function submitQuickSyncJob(apiClient,userId,targetId,syncOptions){if(!userId)throw new Error("userId cannot be null");if(!syncOptions)throw new Error("syncOptions cannot be null");if(!targetId)throw new Error("targetId cannot be null");var options={userId:userId,TargetId:targetId,ParentId:syncOptions.ParentId,Category:syncOptions.Category,Quality:syncOptions.Quality,Bitrate:syncOptions.Bitrate};return syncOptions.items&&syncOptions.items.length&&(options.ItemIds=(syncOptions.items||[]).map(function(i){return i.Id||i}).join(",")),apiClient.ajax({type:"POST",url:apiClient.getUrl("Sync/Jobs"),data:JSON.stringify(options),contentType:"application/json",dataType:"json"}).then(function(){require(["toast"],function(toast){showSubmissionToast(targetId,apiClient),"download"===syncOptions.mode&&syncNow()})})}function setJobValues(job,form){var txtBitrate=form.querySelector("#txtBitrate"),bitrate=txtBitrate?txtBitrate.value:null;bitrate&&(bitrate=1e6*parseFloat(bitrate)),job.Bitrate=bitrate;var selectQuality=form.querySelector("#selectQuality");selectQuality&&(job.Quality=selectQuality.value,appSettings.set("sync-lastquality",job.Quality||""));var selectProfile=form.querySelector("#selectProfile");selectProfile&&(job.Profile=selectProfile.value);var txtItemLimit=form.querySelector("#txtItemLimit");txtItemLimit&&(job.ItemLimit=txtItemLimit.value||null);var chkSyncNewContent=form.querySelector("#chkSyncNewContent");chkSyncNewContent&&(job.SyncNewContent=chkSyncNewContent.checked);var chkUnwatchedOnly=form.querySelector("#chkUnwatchedOnly");chkUnwatchedOnly&&(job.UnwatchedOnly=chkUnwatchedOnly.checked)}function renderForm(options){return new Promise(function(resolve,reject){require(["emby-checkbox","emby-input","emby-select"],function(){renderFormInternal(options,connectionManager.deviceId(),resolve)})})}function renderFormInternal(options,defaultTargetId,resolve){var elem=options.elem,dialogOptions=options.dialogOptions,targets=dialogOptions.Targets,html="",mode=options.mode,targetContainerClass="download"===mode?" hide":"",syncTargetLabel="convert"===mode?globalize.translate("sharedcomponents#LabelConvertTo"):globalize.translate("sharedcomponents#LabelSyncTo");options.readOnlySyncTarget?(html+='
    ',html+='',html+="
    "):(html+='
    ',html+='",targets.length||(html+='
    '+globalize.translate("sharedcomponents#LabelSyncNoTargetsHelp")+"
    "),appHost.supports("externallinks")&&(html+='"),html+="
    "),html+='
    ',html+='",html+='
    ',html+="
    ",html+='
    ',html+='",html+='
    ',html+="
    ",html+='
    ',html+='',html+="
    ",-1!==dialogOptions.Options.indexOf("UnwatchedOnly")&&(html+='
    ',html+="",html+="convert"===mode?'
    '+globalize.translate("sharedcomponents#ConvertUnwatchedVideosOnlyHelp")+"
    ":'
    '+globalize.translate("sharedcomponents#SyncUnwatchedVideosOnlyHelp")+"
    ",html+="
    "),-1!==dialogOptions.Options.indexOf("SyncNewContent")&&(html+='
    ',html+="",html+="convert"===mode?'
    '+globalize.translate("sharedcomponents#AutomaticallyConvertNewContentHelp")+"
    ":'
    '+globalize.translate("sharedcomponents#AutomaticallySyncNewContentHelp")+"
    ",html+="
    "),-1!==dialogOptions.Options.indexOf("ItemLimit")&&(html+='
    ',html+='',html+="convert"===mode?'
    '+globalize.translate("sharedcomponents#ConvertItemLimitHelp")+"
    ":'
    '+globalize.translate("sharedcomponents#DownloadItemLimitHelp")+"
    ",html+="
    "),elem.innerHTML=html;var selectSyncTarget=elem.querySelector("#selectSyncTarget");selectSyncTarget&&(selectSyncTarget.addEventListener("change",function(){loadQualityOptions(elem,this.value,options.dialogOptionsFn).then(resolve)}),selectSyncTarget.dispatchEvent(new CustomEvent("change",{bubbles:!0})));var selectProfile=elem.querySelector("#selectProfile");selectProfile&&(selectProfile.addEventListener("change",function(){onProfileChange(elem,this.value)}),dialogOptions.ProfileOptions.length&&selectProfile.dispatchEvent(new CustomEvent("change",{bubbles:!0})));var selectQuality=elem.querySelector("#selectQuality");selectQuality&&(selectQuality.addEventListener("change",function(){onQualityChange(elem,this.value)}),selectQuality.dispatchEvent(new CustomEvent("change",{bubbles:!0}))),setTimeout(function(){focusManager.autoFocus(elem)},100)}function showWifiMessage(){require(["dialog","appRouter"],function(dialog,appRouter){var options={title:globalize.translate("sharedcomponents#HeaderWaitingForWifi"),text:globalize.translate("sharedcomponents#WifiRequiredToDownload")},items=[];items.push({name:options.confirmText||globalize.translate("sharedcomponents#ButtonOk"),id:"ok",type:"submit"}),items.push({name:options.cancelText||globalize.translate("sharedcomponents#HeaderDownloadSettings"),id:"downloadsettings",type:"cancel"}),options.buttons=items,dialog(options).then(function(result){return"ok"===result?Promise.resolve():"downloadsettings"===result?(appRouter.show(appRouter.getRouteUrl("downloadsettings")),Promise.resolve()):Promise.reject()})})}function validateNetwork(){switch(navigator.connection?navigator.connection.type:null){case"cellular":case"bluetooth":return showWifiMessage(),!1;default:return!0}}function showSyncMenu(options){return"download"===options.mode&&appSettings.syncOnlyOnWifi()&&!validateNetwork()?Promise.reject():registrationServices.validateFeature("sync").then(function(){return showSyncMenuInternal(options)})}function enableAutoSync(options){if("download"!==options.mode)return!1;var firstItem=(options.items||[])[0]||{};return"Audio"===firstItem.Type||("MusicAlbum"===firstItem.Type||("MusicArtist"===firstItem.Type||("MusicGenre"===firstItem.Type||"Playlist"===firstItem.Type&&"Audio"===firstItem.MediaType)))}function showSyncMenuInternal(options){var apiClient=connectionManager.getApiClient(options.serverId),userId=apiClient.getCurrentUserId();if(enableAutoSync(options))return submitQuickSyncJob(apiClient,userId,apiClient.deviceId(),{items:options.items,Quality:"custom",Bitrate:appSettings.maxStaticMusicBitrate()});var dialogOptionsFn=getTargetDialogOptionsFn(apiClient,{UserId:userId,ItemIds:(options.items||[]).map(function(i){return i.Id||i}).join(","),ParentId:options.ParentId,Category:options.Category,IncludeProviders:"convert"===options.mode?"ConvertSyncProvider":null,ExcludeProviders:"convert"===options.mode?null:"ConvertSyncProvider"});return dialogOptionsFn().then(function(dialogOptions){currentDialogOptions=dialogOptions;var dlgElementOptions={removeOnClose:!0,scrollY:!1,autoFocus:!1};layoutManager.tv?dlgElementOptions.size="fullscreen":dlgElementOptions.size="small";var dlg=dialogHelper.createDialog(dlgElementOptions);dlg.classList.add("formDialog");var html="";html+='
    ',html+='',html+='

    ';var syncButtonLabel="download"===options.mode?globalize.translate("sharedcomponents#Download"):"convert"===options.mode?globalize.translate("sharedcomponents#Convert"):globalize.translate("sharedcomponents#Sync");html+=syncButtonLabel,html+="

    ",appHost.supports("externallinks")&&(html+='info'+globalize.translate("sharedcomponents#Help")+""),html+="
    ",html+='
    ',html+='
    ',html+='
    ',html+='
    ',html+='
    ',html+='",html+="
    ",html+="
    ",html+="
    ",html+="
    ",dlg.innerHTML=html;var submitted=!1;dlg.querySelector("form").addEventListener("submit",function(e){return submitted=submitJob(dlg,apiClient,userId,options,this),e.preventDefault(),!1}),dlg.querySelector(".btnCancel").addEventListener("click",function(){dialogHelper.close(dlg)}),layoutManager.tv&&scrollHelper.centerFocus.on(dlg.querySelector(".formDialogContent"),!1);var promise=dialogHelper.open(dlg);return renderForm({elem:dlg.querySelector(".formFields"),dialogOptions:dialogOptions,dialogOptionsFn:dialogOptionsFn,mode:options.mode}),promise.then(function(){return layoutManager.tv&&scrollHelper.centerFocus.off(dlg.querySelector(".formDialogContent"),!1),submitted?Promise.resolve():Promise.reject()})})}function getTargetDialogOptionsFn(apiClient,query){return function(targetId){return query.TargetId=targetId,apiClient.getJSON(apiClient.getUrl("Sync/Options",query))}}function setQualityFieldVisible(form,visible){var fldQuality=form.querySelector(".fldQuality"),selectQuality=form.querySelector("#selectQuality");visible?(fldQuality&&fldQuality.classList.remove("hide"),selectQuality&&selectQuality.removeAttribute("required")):(fldQuality&&fldQuality.classList.add("hide"),selectQuality&&selectQuality.removeAttribute("required"))}function onProfileChange(form,profileId){var options=currentDialogOptions||{},profileOptions=options.ProfileOptions||[];if(profileOptions.length){var option=profileOptions.filter(function(o){return o.Id===profileId})[0],qualityOptions=options.QualityOptions||[];option?(form.querySelector(".profileDescription").innerHTML=option.Description||"",setQualityFieldVisible(form,qualityOptions.length>0&&option.EnableQualityOptions&&-1!==options.Options.indexOf("Quality"))):(form.querySelector(".profileDescription").innerHTML="",setQualityFieldVisible(form,qualityOptions.length>0&&-1!==options.Options.indexOf("Quality")))}}function onQualityChange(form,qualityId){var options=currentDialogOptions||{},option=(options.QualityOptions||[]).filter(function(o){return o.Id===qualityId})[0],qualityDescription=form.querySelector(".qualityDescription");qualityDescription.innerHTML=option?option.Description||"":"";var fldBitrate=form.querySelector(".fldBitrate"),txtBitrate=form.querySelector("#txtBitrate");"custom"===qualityId?(fldBitrate&&fldBitrate.classList.remove("hide"),txtBitrate&&txtBitrate.setAttribute("required","required")):(fldBitrate&&fldBitrate.classList.add("hide"),txtBitrate&&txtBitrate.removeAttribute("required"))}function renderTargetDialogOptions(form,options){currentDialogOptions=options;var fldProfile=form.querySelector(".fldProfile"),selectProfile=form.querySelector("#selectProfile");options.ProfileOptions.length&&-1!==options.Options.indexOf("Profile")?(fldProfile&&fldProfile.classList.remove("hide"),selectProfile&&selectProfile.setAttribute("required","required")):(fldProfile&&fldProfile.classList.add("hide"),selectProfile&&selectProfile.removeAttribute("required")),setQualityFieldVisible(form,options.QualityOptions.length>0),selectProfile&&(selectProfile.innerHTML=options.ProfileOptions.map(function(o){var selectedAttribute=o.IsDefault?' selected="selected"':"";return'"}).join(""),selectProfile.dispatchEvent(new CustomEvent("change",{bubbles:!0})));var selectQuality=form.querySelector("#selectQuality");if(selectQuality){selectQuality.innerHTML=options.QualityOptions.map(function(o){var selectedAttribute=o.IsDefault?' selected="selected"':"";return'"}).join("");var lastQuality=appSettings.get("sync-lastquality");lastQuality&&options.QualityOptions.filter(function(i){return i.Id===lastQuality}).length&&(selectQuality.value=lastQuality),selectQuality.dispatchEvent(new CustomEvent("change",{bubbles:!0}))}}function loadQualityOptions(form,targetId,dialogOptionsFn){return dialogOptionsFn(targetId).then(function(options){return renderTargetDialogOptions(form,options)})}var currentDialogOptions;return{showMenu:showSyncMenu,renderForm:renderForm,setJobValues:setJobValues}}); \ No newline at end of file +define(["apphost", "globalize", "connectionManager", "layoutManager", "focusManager", "scrollHelper", "appSettings", "registrationServices", "dialogHelper", "paper-icon-button-light", "formDialogStyle"], function(appHost, globalize, connectionManager, layoutManager, focusManager, scrollHelper, appSettings, registrationServices, dialogHelper) { + "use strict"; + + function submitJob(dlg, apiClient, userId, syncOptions, form) { + if (!userId) throw new Error("userId cannot be null"); + if (!syncOptions) throw new Error("syncOptions cannot be null"); + if (!form) throw new Error("form cannot be null"); + var selectSyncTarget = form.querySelector("#selectSyncTarget"), + target = selectSyncTarget ? selectSyncTarget.value : null; + if (!target) return require(["toast"], function(toast) { + toast(globalize.translate("sharedcomponents#PleaseSelectDeviceToSyncTo")) + }), !1; + var options = { + userId: userId, + TargetId: target, + ParentId: syncOptions.ParentId, + Category: syncOptions.Category + }; + return setJobValues(options, form), syncOptions.items && syncOptions.items.length && (options.ItemIds = (syncOptions.items || []).map(function(i) { + return i.Id || i + }).join(",")), apiClient.ajax({ + type: "POST", + url: apiClient.getUrl("Sync/Jobs"), + data: JSON.stringify(options), + contentType: "application/json", + dataType: "json" + }).then(function() { + dialogHelper.close(dlg), require(["toast"], function(toast) { + showSubmissionToast(target, apiClient), "download" === syncOptions.mode && syncNow() + }) + }), !0 + } + + function showSubmissionToast(targetId, apiClient) { + require(["toast"], function(toast) { + toast(targetId === apiClient.deviceId() ? globalize.translate("sharedcomponents#DownloadingDots") : globalize.translate("sharedcomponents#SyncingDots")) + }) + } + + function syncNow() { + require(["localsync"], function(localSync) { + localSync.sync() + }) + } + + function submitQuickSyncJob(apiClient, userId, targetId, syncOptions) { + if (!userId) throw new Error("userId cannot be null"); + if (!syncOptions) throw new Error("syncOptions cannot be null"); + if (!targetId) throw new Error("targetId cannot be null"); + var options = { + userId: userId, + TargetId: targetId, + ParentId: syncOptions.ParentId, + Category: syncOptions.Category, + Quality: syncOptions.Quality, + Bitrate: syncOptions.Bitrate + }; + return syncOptions.items && syncOptions.items.length && (options.ItemIds = (syncOptions.items || []).map(function(i) { + return i.Id || i + }).join(",")), apiClient.ajax({ + type: "POST", + url: apiClient.getUrl("Sync/Jobs"), + data: JSON.stringify(options), + contentType: "application/json", + dataType: "json" + }).then(function() { + require(["toast"], function(toast) { + showSubmissionToast(targetId, apiClient), "download" === syncOptions.mode && syncNow() + }) + }) + } + + function setJobValues(job, form) { + var txtBitrate = form.querySelector("#txtBitrate"), + bitrate = txtBitrate ? txtBitrate.value : null; + bitrate && (bitrate = 1e6 * parseFloat(bitrate)), job.Bitrate = bitrate; + var selectQuality = form.querySelector("#selectQuality"); + selectQuality && (job.Quality = selectQuality.value, appSettings.set("sync-lastquality", job.Quality || "")); + var selectProfile = form.querySelector("#selectProfile"); + selectProfile && (job.Profile = selectProfile.value); + var txtItemLimit = form.querySelector("#txtItemLimit"); + txtItemLimit && (job.ItemLimit = txtItemLimit.value || null); + var chkSyncNewContent = form.querySelector("#chkSyncNewContent"); + chkSyncNewContent && (job.SyncNewContent = chkSyncNewContent.checked); + var chkUnwatchedOnly = form.querySelector("#chkUnwatchedOnly"); + chkUnwatchedOnly && (job.UnwatchedOnly = chkUnwatchedOnly.checked) + } + + function renderForm(options) { + return new Promise(function(resolve, reject) { + require(["emby-checkbox", "emby-input", "emby-select"], function() { + renderFormInternal(options, connectionManager.deviceId(), resolve) + }) + }) + } + + function renderFormInternal(options, defaultTargetId, resolve) { + var elem = options.elem, + dialogOptions = options.dialogOptions, + targets = dialogOptions.Targets, + html = "", + mode = options.mode, + targetContainerClass = "download" === mode ? " hide" : "", + syncTargetLabel = "convert" === mode ? globalize.translate("sharedcomponents#LabelConvertTo") : globalize.translate("sharedcomponents#LabelSyncTo"); + options.readOnlySyncTarget ? (html += '
    ', html += '', html += "
    ") : (html += '
    ', html += '", targets.length || (html += '
    ' + globalize.translate("sharedcomponents#LabelSyncNoTargetsHelp") + "
    "), appHost.supports("externallinks") && (html += '"), html += "
    "), html += '
    ', html += '", html += '
    ', html += "
    ", html += '
    ', html += '", html += '
    ', html += "
    ", html += '
    ', html += '', html += "
    ", -1 !== dialogOptions.Options.indexOf("UnwatchedOnly") && (html += '
    ', html += "", html += "convert" === mode ? '
    ' + globalize.translate("sharedcomponents#ConvertUnwatchedVideosOnlyHelp") + "
    " : '
    ' + globalize.translate("sharedcomponents#SyncUnwatchedVideosOnlyHelp") + "
    ", html += "
    "), -1 !== dialogOptions.Options.indexOf("SyncNewContent") && (html += '
    ', html += "", html += "convert" === mode ? '
    ' + globalize.translate("sharedcomponents#AutomaticallyConvertNewContentHelp") + "
    " : '
    ' + globalize.translate("sharedcomponents#AutomaticallySyncNewContentHelp") + "
    ", html += "
    "), -1 !== dialogOptions.Options.indexOf("ItemLimit") && (html += '
    ', html += '', html += "convert" === mode ? '
    ' + globalize.translate("sharedcomponents#ConvertItemLimitHelp") + "
    " : '
    ' + globalize.translate("sharedcomponents#DownloadItemLimitHelp") + "
    ", html += "
    "), elem.innerHTML = html; + var selectSyncTarget = elem.querySelector("#selectSyncTarget"); + selectSyncTarget && (selectSyncTarget.addEventListener("change", function() { + loadQualityOptions(elem, this.value, options.dialogOptionsFn).then(resolve) + }), selectSyncTarget.dispatchEvent(new CustomEvent("change", { + bubbles: !0 + }))); + var selectProfile = elem.querySelector("#selectProfile"); + selectProfile && (selectProfile.addEventListener("change", function() { + onProfileChange(elem, this.value) + }), dialogOptions.ProfileOptions.length && selectProfile.dispatchEvent(new CustomEvent("change", { + bubbles: !0 + }))); + var selectQuality = elem.querySelector("#selectQuality"); + selectQuality && (selectQuality.addEventListener("change", function() { + onQualityChange(elem, this.value) + }), selectQuality.dispatchEvent(new CustomEvent("change", { + bubbles: !0 + }))), setTimeout(function() { + focusManager.autoFocus(elem) + }, 100) + } + + function showWifiMessage() { + require(["dialog", "appRouter"], function(dialog, appRouter) { + var options = { + title: globalize.translate("sharedcomponents#HeaderWaitingForWifi"), + text: globalize.translate("sharedcomponents#WifiRequiredToDownload") + }, + items = []; + items.push({ + name: options.confirmText || globalize.translate("sharedcomponents#ButtonOk"), + id: "ok", + type: "submit" + }), items.push({ + name: options.cancelText || globalize.translate("sharedcomponents#HeaderDownloadSettings"), + id: "downloadsettings", + type: "cancel" + }), options.buttons = items, dialog(options).then(function(result) { + return "ok" === result ? Promise.resolve() : "downloadsettings" === result ? (appRouter.show(appRouter.getRouteUrl("downloadsettings")), Promise.resolve()) : Promise.reject() + }) + }) + } + + function validateNetwork() { + switch (navigator.connection ? navigator.connection.type : null) { + case "cellular": + case "bluetooth": + return showWifiMessage(), !1; + default: + return !0 + } + } + + function showSyncMenu(options) { + return "download" === options.mode && appSettings.syncOnlyOnWifi() && !validateNetwork() ? Promise.reject() : registrationServices.validateFeature("sync").then(function() { + return showSyncMenuInternal(options) + }) + } + + function enableAutoSync(options) { + if ("download" !== options.mode) return !1; + var firstItem = (options.items || [])[0] || {}; + return "Audio" === firstItem.Type || ("MusicAlbum" === firstItem.Type || ("MusicArtist" === firstItem.Type || ("MusicGenre" === firstItem.Type || "Playlist" === firstItem.Type && "Audio" === firstItem.MediaType))) + } + + function showSyncMenuInternal(options) { + var apiClient = connectionManager.getApiClient(options.serverId), + userId = apiClient.getCurrentUserId(); + if (enableAutoSync(options)) return submitQuickSyncJob(apiClient, userId, apiClient.deviceId(), { + items: options.items, + Quality: "custom", + Bitrate: appSettings.maxStaticMusicBitrate() + }); + var dialogOptionsFn = getTargetDialogOptionsFn(apiClient, { + UserId: userId, + ItemIds: (options.items || []).map(function(i) { + return i.Id || i + }).join(","), + ParentId: options.ParentId, + Category: options.Category, + IncludeProviders: "convert" === options.mode ? "ConvertSyncProvider" : null, + ExcludeProviders: "convert" === options.mode ? null : "ConvertSyncProvider" + }); + return dialogOptionsFn().then(function(dialogOptions) { + currentDialogOptions = dialogOptions; + var dlgElementOptions = { + removeOnClose: !0, + scrollY: !1, + autoFocus: !1 + }; + layoutManager.tv ? dlgElementOptions.size = "fullscreen" : dlgElementOptions.size = "small"; + var dlg = dialogHelper.createDialog(dlgElementOptions); + dlg.classList.add("formDialog"); + var html = ""; + html += '
    ', html += '', html += '

    '; + var syncButtonLabel = "download" === options.mode ? globalize.translate("sharedcomponents#Download") : "convert" === options.mode ? globalize.translate("sharedcomponents#Convert") : globalize.translate("sharedcomponents#Sync"); + html += syncButtonLabel, html += "

    ", appHost.supports("externallinks") && (html += 'info' + globalize.translate("sharedcomponents#Help") + ""), html += "
    ", html += '
    ', html += '
    ', html += '
    ', html += '
    ', html += '
    ', html += '", html += "
    ", html += "
    ", html += "
    ", html += "
    ", dlg.innerHTML = html; + var submitted = !1; + dlg.querySelector("form").addEventListener("submit", function(e) { + return submitted = submitJob(dlg, apiClient, userId, options, this), e.preventDefault(), !1 + }), dlg.querySelector(".btnCancel").addEventListener("click", function() { + dialogHelper.close(dlg) + }), layoutManager.tv && scrollHelper.centerFocus.on(dlg.querySelector(".formDialogContent"), !1); + var promise = dialogHelper.open(dlg); + return renderForm({ + elem: dlg.querySelector(".formFields"), + dialogOptions: dialogOptions, + dialogOptionsFn: dialogOptionsFn, + mode: options.mode + }), promise.then(function() { + return layoutManager.tv && scrollHelper.centerFocus.off(dlg.querySelector(".formDialogContent"), !1), submitted ? Promise.resolve() : Promise.reject() + }) + }) + } + + function getTargetDialogOptionsFn(apiClient, query) { + return function(targetId) { + return query.TargetId = targetId, apiClient.getJSON(apiClient.getUrl("Sync/Options", query)) + } + } + + function setQualityFieldVisible(form, visible) { + var fldQuality = form.querySelector(".fldQuality"), + selectQuality = form.querySelector("#selectQuality"); + visible ? (fldQuality && fldQuality.classList.remove("hide"), selectQuality && selectQuality.removeAttribute("required")) : (fldQuality && fldQuality.classList.add("hide"), selectQuality && selectQuality.removeAttribute("required")) + } + + function onProfileChange(form, profileId) { + var options = currentDialogOptions || {}, + profileOptions = options.ProfileOptions || []; + if (profileOptions.length) { + var option = profileOptions.filter(function(o) { + return o.Id === profileId + })[0], + qualityOptions = options.QualityOptions || []; + option ? (form.querySelector(".profileDescription").innerHTML = option.Description || "", setQualityFieldVisible(form, qualityOptions.length > 0 && option.EnableQualityOptions && -1 !== options.Options.indexOf("Quality"))) : (form.querySelector(".profileDescription").innerHTML = "", setQualityFieldVisible(form, qualityOptions.length > 0 && -1 !== options.Options.indexOf("Quality"))) + } + } + + function onQualityChange(form, qualityId) { + var options = currentDialogOptions || {}, + option = (options.QualityOptions || []).filter(function(o) { + return o.Id === qualityId + })[0], + qualityDescription = form.querySelector(".qualityDescription"); + qualityDescription.innerHTML = option ? option.Description || "" : ""; + var fldBitrate = form.querySelector(".fldBitrate"), + txtBitrate = form.querySelector("#txtBitrate"); + "custom" === qualityId ? (fldBitrate && fldBitrate.classList.remove("hide"), txtBitrate && txtBitrate.setAttribute("required", "required")) : (fldBitrate && fldBitrate.classList.add("hide"), txtBitrate && txtBitrate.removeAttribute("required")) + } + + function renderTargetDialogOptions(form, options) { + currentDialogOptions = options; + var fldProfile = form.querySelector(".fldProfile"), + selectProfile = form.querySelector("#selectProfile"); + options.ProfileOptions.length && -1 !== options.Options.indexOf("Profile") ? (fldProfile && fldProfile.classList.remove("hide"), selectProfile && selectProfile.setAttribute("required", "required")) : (fldProfile && fldProfile.classList.add("hide"), selectProfile && selectProfile.removeAttribute("required")), setQualityFieldVisible(form, options.QualityOptions.length > 0), selectProfile && (selectProfile.innerHTML = options.ProfileOptions.map(function(o) { + var selectedAttribute = o.IsDefault ? ' selected="selected"' : ""; + return '" + }).join(""), selectProfile.dispatchEvent(new CustomEvent("change", { + bubbles: !0 + }))); + var selectQuality = form.querySelector("#selectQuality"); + if (selectQuality) { + selectQuality.innerHTML = options.QualityOptions.map(function(o) { + var selectedAttribute = o.IsDefault ? ' selected="selected"' : ""; + return '" + }).join(""); + var lastQuality = appSettings.get("sync-lastquality"); + lastQuality && options.QualityOptions.filter(function(i) { + return i.Id === lastQuality + }).length && (selectQuality.value = lastQuality), selectQuality.dispatchEvent(new CustomEvent("change", { + bubbles: !0 + })) + } + } + + function loadQualityOptions(form, targetId, dialogOptionsFn) { + return dialogOptionsFn(targetId).then(function(options) { + return renderTargetDialogOptions(form, options) + }) + } + var currentDialogOptions; + return { + showMenu: showSyncMenu, + renderForm: renderForm, + setJobValues: setJobValues + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/sync/syncjobeditor.js b/dashboard-ui/bower_components/emby-webcomponents/sync/syncjobeditor.js index 42e6d32445..3f78d1511f 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/sync/syncjobeditor.js +++ b/dashboard-ui/bower_components/emby-webcomponents/sync/syncjobeditor.js @@ -1 +1,221 @@ -define(["connectionManager","serverNotifications","events","datetime","dom","imageLoader","loading","globalize","apphost","layoutManager","scrollHelper","dialogHelper","listViewStyle","paper-icon-button-light","emby-button","formDialogStyle","emby-linkbutton"],function(connectionManager,serverNotifications,events,datetime,dom,imageLoader,loading,globalize,appHost,layoutManager,scrollHelper,dialogHelper){"use strict";function syncNow(){require(["localsync"],function(localSync){localSync.sync()})}function renderJob(context,job,dialogOptions){require(["syncDialog"],function(syncDialog){syncDialog.renderForm({elem:context.querySelector(".syncJobFormContent"),dialogOptions:dialogOptions,dialogOptionsFn:getTargetDialogOptionsFn(dialogOptions),readOnlySyncTarget:!0}).then(function(){fillJobValues(context,job,dialogOptions)})})}function getTargetDialogOptionsFn(dialogOptions){return function(targetId){return Promise.resolve(dialogOptions)}}function getJobItemHtml(jobItem,apiClient,index){var nextAction,html="",status=jobItem.Status;"Failed"===status?nextAction="retry":"Cancelled"===status?nextAction="retry":"Queued"===status||"Transferring"===status||"Converting"===status||"ReadyToTransfer"===status?nextAction="cancel":"Synced"!==status||jobItem.IsMarkedForRemoval||(nextAction="remove");var listItemClass="listItem listItem-border";layoutManager.tv&&nextAction&&(listItemClass+=" btnJobItemMenu"),layoutManager.tv&&(listItemClass+=" listItem-button");var tagName=layoutManager.tv?"button":"div";html+="<"+tagName+' type="button" class="'+listItemClass+'" data-itemid="'+jobItem.Id+'" data-status="'+jobItem.Status+'" data-action="'+nextAction+'">';var imgUrl;jobItem.PrimaryImageItemId&&(imgUrl=apiClient.getImageUrl(jobItem.PrimaryImageItemId,{type:"Primary",width:80,tag:jobItem.PrimaryImageTag,minScale:1.5})),html+=imgUrl?'
    ":'sync',html+='
    ',html+='

    ',html+=jobItem.ItemName,html+="

    ","Failed"===jobItem.Status?html+='
    ':html+='
    ',html+=globalize.translate("sharedcomponents#SyncJobItemStatus"+jobItem.Status),"Synced"===jobItem.Status&&jobItem.IsMarkedForRemoval&&(html+="
    ",html+=globalize.translate("sharedcomponents#RemovingFromDevice")),html+="
    ",html+='
    ',html+='
    ',html+="
    ",html+="
    ";return layoutManager.tv||("retry"===nextAction?html+='':"cancel"===nextAction?html+='':"remove"===nextAction&&(html+='')),html+=""}function renderJobItems(context,items,apiClient){var html="";html+="

    "+globalize.translate("sharedcomponents#Items")+"

    ",html+='
    ';var index=0;html+=items.map(function(i){return getJobItemHtml(i,apiClient,index++)}).join(""),html+="
    ";var elem=context.querySelector(".jobItems");elem.innerHTML=html,imageLoader.lazyChildren(elem)}function parentWithClass(elem,className){for(;!elem.classList||!elem.classList.contains(className);)if(!(elem=elem.parentNode))return null;return elem}function showJobItemMenu(elem,jobId,apiClient){var action=elem.getAttribute("data-action"),context=parentWithClass(elem,"formDialog"),listItem=parentWithClass(elem,"listItem"),jobItemId=listItem.getAttribute("data-itemid");"retry"===action?retryJobItem(context,jobId,jobItemId,apiClient):"cancel"!==action&&"remove"!==action||cancelJobItem(context,jobId,jobItemId,apiClient)}function cancelJobItem(context,jobId,jobItemId,apiClient){showRemoveConfirm(function(){loading.show(),apiClient.ajax({type:"DELETE",url:apiClient.getUrl("Sync/JobItems/"+jobItemId)}).then(function(){appHost.supports("sync")&&syncNow(),loadJob(context,jobId,apiClient)})})}function retryJobItem(context,jobId,jobItemId,apiClient){showRetryConfirm(function(){apiClient.ajax({type:"POST",url:apiClient.getUrl("Sync/JobItems/"+jobItemId+"/Enable")}).then(function(){appHost.supports("sync")&&syncNow(),loadJob(context,jobId,apiClient)})})}function showRetryConfirm(callback){require(["confirm"],function(confirm){confirm({text:globalize.translate("sharedcomponents#ConfirmRemoveDownload"),confirmText:globalize.translate("sharedcomponents#RemoveDownload"),cancelText:globalize.translate("sharedcomponents#KeepDownload"),primary:"cancel"}).then(callback)})}function showRemoveConfirm(callback){require(["confirm"],function(confirm){confirm({text:globalize.translate("sharedcomponents#ConfirmRemoveDownload"),confirmText:globalize.translate("sharedcomponents#RemoveDownload"),cancelText:globalize.translate("sharedcomponents#KeepDownload"),primary:"cancel"}).then(callback)})}function fillJobValues(context,job,editOptions){var selectProfile=context.querySelector("#selectProfile");selectProfile&&(selectProfile.value=job.Profile||"");var selectQuality=context.querySelector("#selectQuality");selectQuality&&(selectQuality.value=job.Quality||"");var chkUnwatchedOnly=context.querySelector("#chkUnwatchedOnly");chkUnwatchedOnly&&(chkUnwatchedOnly.checked=job.UnwatchedOnly);var chkSyncNewContent=context.querySelector("#chkSyncNewContent");chkSyncNewContent&&(chkSyncNewContent.checked=job.SyncNewContent);var txtItemLimit=context.querySelector("#txtItemLimit");txtItemLimit&&(txtItemLimit.value=job.ItemLimit);var txtBitrate=context.querySelector("#txtBitrate");job.Bitrate?txtBitrate.value=job.Bitrate/1e6:txtBitrate.value="";var target=editOptions.Targets.filter(function(t){return t.Id===job.TargetId})[0],targetName=target?target.Name:"",selectSyncTarget=context.querySelector("#selectSyncTarget");selectSyncTarget&&(selectSyncTarget.value=targetName)}function loadJob(context,id,apiClient){loading.show(),apiClient.getJSON(apiClient.getUrl("Sync/Jobs/"+id)).then(function(job){apiClient.getJSON(apiClient.getUrl("Sync/Options",{UserId:job.UserId,ItemIds:job.RequestedItemIds&&job.RequestedItemIds.length?job.RequestedItemIds.join(""):null,ParentId:job.ParentId,Category:job.Category,TargetId:job.TargetId})).then(function(options){_jobOptions=options,renderJob(context,job,options),loading.hide()})}),apiClient.getJSON(apiClient.getUrl("Sync/JobItems",{JobId:id,AddMetadata:!0})).then(function(result){renderJobItems(context,result.Items,apiClient),loading.hide()})}function loadJobInfo(context,job,jobItems,apiClient){renderJobItems(context,jobItems,apiClient),loading.hide()}function saveJob(context,id,apiClient){loading.show(),apiClient.getJSON(apiClient.getUrl("Sync/Jobs/"+id)).then(function(job){require(["syncDialog"],function(syncDialog){syncDialog.setJobValues(job,context),apiClient.ajax({url:apiClient.getUrl("Sync/Jobs/"+id),type:"POST",data:JSON.stringify(job),contentType:"application/json"}).then(function(){appHost.supports("sync")&&syncNow(),loading.hide(),dialogHelper.close(context)})})})}function startListening(apiClient,jobId){var startParams="0,1500";startParams+=","+jobId,apiClient.sendMessage("SyncJobStart",startParams)}function stopListening(apiClient){apiClient.sendMessage("SyncJobStop","")}function bindEvents(context,jobId,apiClient){context.querySelector(".jobItems").addEventListener("click",function(e){var btnJobItemMenu=dom.parentWithClass(e.target,"btnJobItemMenu");btnJobItemMenu&&showJobItemMenu(btnJobItemMenu,jobId,apiClient)})}function showEditor(options){function onSyncJobMessage(e,apiClient,msg){loadJobInfo(dlg,msg.Job,msg.JobItems,apiClient)}var apiClient=connectionManager.getApiClient(options.serverId),id=options.jobId,dlgElementOptions={removeOnClose:!0,scrollY:!1,autoFocus:!1};layoutManager.tv?dlgElementOptions.size="fullscreen":dlgElementOptions.size="medium";var dlg=dialogHelper.createDialog(dlgElementOptions);dlg.classList.add("formDialog");var html="";html+='
    ',html+='',html+='

    ',html+=globalize.translate("sharedcomponents#Sync"),html+="

    ",appHost.supports("externallinks")&&(html+='info'+globalize.translate("sharedcomponents#Help")+""),html+="
    ",html+='
    ',html+='
    ',html+='
    ',html+='
    ',html+='
    ',html+='
    ',html+='",html+="
    ",html+="
    ",html+="
    ",html+="
    ",dlg.innerHTML=html;dlg.querySelector("form").addEventListener("submit",function(e){return saveJob(dlg,id,apiClient),e.preventDefault(),!1}),dlg.querySelector(".btnCancel").addEventListener("click",function(){dialogHelper.close(dlg)}),layoutManager.tv&&scrollHelper.centerFocus.on(dlg.querySelector(".formDialogContent"),!1),loadJob(dlg,id,apiClient),bindEvents(dlg,id,apiClient);var promise=dialogHelper.open(dlg);return startListening(apiClient,id),events.on(serverNotifications,"SyncJob",onSyncJobMessage),promise.then(function(){return stopListening(apiClient),events.off(serverNotifications,"SyncJob",onSyncJobMessage),layoutManager.tv&&scrollHelper.centerFocus.off(dlg.querySelector(".formDialogContent"),!1),Promise.reject()})}var _jobOptions;return{show:showEditor}}); \ No newline at end of file +define(["connectionManager", "serverNotifications", "events", "datetime", "dom", "imageLoader", "loading", "globalize", "apphost", "layoutManager", "scrollHelper", "dialogHelper", "listViewStyle", "paper-icon-button-light", "emby-button", "formDialogStyle", "emby-linkbutton"], function(connectionManager, serverNotifications, events, datetime, dom, imageLoader, loading, globalize, appHost, layoutManager, scrollHelper, dialogHelper) { + "use strict"; + + function syncNow() { + require(["localsync"], function(localSync) { + localSync.sync() + }) + } + + function renderJob(context, job, dialogOptions) { + require(["syncDialog"], function(syncDialog) { + syncDialog.renderForm({ + elem: context.querySelector(".syncJobFormContent"), + dialogOptions: dialogOptions, + dialogOptionsFn: getTargetDialogOptionsFn(dialogOptions), + readOnlySyncTarget: !0 + }).then(function() { + fillJobValues(context, job, dialogOptions) + }) + }) + } + + function getTargetDialogOptionsFn(dialogOptions) { + return function(targetId) { + return Promise.resolve(dialogOptions) + } + } + + function getJobItemHtml(jobItem, apiClient, index) { + var nextAction, html = "", + status = jobItem.Status; + "Failed" === status ? nextAction = "retry" : "Cancelled" === status ? nextAction = "retry" : "Queued" === status || "Transferring" === status || "Converting" === status || "ReadyToTransfer" === status ? nextAction = "cancel" : "Synced" !== status || jobItem.IsMarkedForRemoval || (nextAction = "remove"); + var listItemClass = "listItem listItem-border"; + layoutManager.tv && nextAction && (listItemClass += " btnJobItemMenu"), layoutManager.tv && (listItemClass += " listItem-button"); + var tagName = layoutManager.tv ? "button" : "div"; + html += "<" + tagName + ' type="button" class="' + listItemClass + '" data-itemid="' + jobItem.Id + '" data-status="' + jobItem.Status + '" data-action="' + nextAction + '">'; + var imgUrl; + jobItem.PrimaryImageItemId && (imgUrl = apiClient.getImageUrl(jobItem.PrimaryImageItemId, { + type: "Primary", + width: 80, + tag: jobItem.PrimaryImageTag, + minScale: 1.5 + })), html += imgUrl ? '
    " : 'sync', html += '
    ', html += '

    ', html += jobItem.ItemName, html += "

    ", "Failed" === jobItem.Status ? html += '
    ' : html += '
    ', html += globalize.translate("sharedcomponents#SyncJobItemStatus" + jobItem.Status), "Synced" === jobItem.Status && jobItem.IsMarkedForRemoval && (html += "
    ", html += globalize.translate("sharedcomponents#RemovingFromDevice")), html += "
    ", html += '
    ', html += '
    ', html += "
    ", html += "
    "; + return layoutManager.tv || ("retry" === nextAction ? html += '' : "cancel" === nextAction ? html += '' : "remove" === nextAction && (html += '')), html += "" + } + + function renderJobItems(context, items, apiClient) { + var html = ""; + html += "

    " + globalize.translate("sharedcomponents#Items") + "

    ", html += '
    '; + var index = 0; + html += items.map(function(i) { + return getJobItemHtml(i, apiClient, index++) + }).join(""), html += "
    "; + var elem = context.querySelector(".jobItems"); + elem.innerHTML = html, imageLoader.lazyChildren(elem) + } + + function parentWithClass(elem, className) { + for (; !elem.classList || !elem.classList.contains(className);) + if (!(elem = elem.parentNode)) return null; + return elem + } + + function showJobItemMenu(elem, jobId, apiClient) { + var action = elem.getAttribute("data-action"), + context = parentWithClass(elem, "formDialog"), + listItem = parentWithClass(elem, "listItem"), + jobItemId = listItem.getAttribute("data-itemid"); + "retry" === action ? retryJobItem(context, jobId, jobItemId, apiClient) : "cancel" !== action && "remove" !== action || cancelJobItem(context, jobId, jobItemId, apiClient) + } + + function cancelJobItem(context, jobId, jobItemId, apiClient) { + showRemoveConfirm(function() { + loading.show(), apiClient.ajax({ + type: "DELETE", + url: apiClient.getUrl("Sync/JobItems/" + jobItemId) + }).then(function() { + appHost.supports("sync") && syncNow(), loadJob(context, jobId, apiClient) + }) + }) + } + + function retryJobItem(context, jobId, jobItemId, apiClient) { + showRetryConfirm(function() { + apiClient.ajax({ + type: "POST", + url: apiClient.getUrl("Sync/JobItems/" + jobItemId + "/Enable") + }).then(function() { + appHost.supports("sync") && syncNow(), loadJob(context, jobId, apiClient) + }) + }) + } + + function showRetryConfirm(callback) { + require(["confirm"], function(confirm) { + confirm({ + text: globalize.translate("sharedcomponents#ConfirmRemoveDownload"), + confirmText: globalize.translate("sharedcomponents#RemoveDownload"), + cancelText: globalize.translate("sharedcomponents#KeepDownload"), + primary: "cancel" + }).then(callback) + }) + } + + function showRemoveConfirm(callback) { + require(["confirm"], function(confirm) { + confirm({ + text: globalize.translate("sharedcomponents#ConfirmRemoveDownload"), + confirmText: globalize.translate("sharedcomponents#RemoveDownload"), + cancelText: globalize.translate("sharedcomponents#KeepDownload"), + primary: "cancel" + }).then(callback) + }) + } + + function fillJobValues(context, job, editOptions) { + var selectProfile = context.querySelector("#selectProfile"); + selectProfile && (selectProfile.value = job.Profile || ""); + var selectQuality = context.querySelector("#selectQuality"); + selectQuality && (selectQuality.value = job.Quality || ""); + var chkUnwatchedOnly = context.querySelector("#chkUnwatchedOnly"); + chkUnwatchedOnly && (chkUnwatchedOnly.checked = job.UnwatchedOnly); + var chkSyncNewContent = context.querySelector("#chkSyncNewContent"); + chkSyncNewContent && (chkSyncNewContent.checked = job.SyncNewContent); + var txtItemLimit = context.querySelector("#txtItemLimit"); + txtItemLimit && (txtItemLimit.value = job.ItemLimit); + var txtBitrate = context.querySelector("#txtBitrate"); + job.Bitrate ? txtBitrate.value = job.Bitrate / 1e6 : txtBitrate.value = ""; + var target = editOptions.Targets.filter(function(t) { + return t.Id === job.TargetId + })[0], + targetName = target ? target.Name : "", + selectSyncTarget = context.querySelector("#selectSyncTarget"); + selectSyncTarget && (selectSyncTarget.value = targetName) + } + + function loadJob(context, id, apiClient) { + loading.show(), apiClient.getJSON(apiClient.getUrl("Sync/Jobs/" + id)).then(function(job) { + apiClient.getJSON(apiClient.getUrl("Sync/Options", { + UserId: job.UserId, + ItemIds: job.RequestedItemIds && job.RequestedItemIds.length ? job.RequestedItemIds.join("") : null, + ParentId: job.ParentId, + Category: job.Category, + TargetId: job.TargetId + })).then(function(options) { + _jobOptions = options, renderJob(context, job, options), loading.hide() + }) + }), apiClient.getJSON(apiClient.getUrl("Sync/JobItems", { + JobId: id, + AddMetadata: !0 + })).then(function(result) { + renderJobItems(context, result.Items, apiClient), loading.hide() + }) + } + + function loadJobInfo(context, job, jobItems, apiClient) { + renderJobItems(context, jobItems, apiClient), loading.hide() + } + + function saveJob(context, id, apiClient) { + loading.show(), apiClient.getJSON(apiClient.getUrl("Sync/Jobs/" + id)).then(function(job) { + require(["syncDialog"], function(syncDialog) { + syncDialog.setJobValues(job, context), apiClient.ajax({ + url: apiClient.getUrl("Sync/Jobs/" + id), + type: "POST", + data: JSON.stringify(job), + contentType: "application/json" + }).then(function() { + appHost.supports("sync") && syncNow(), loading.hide(), dialogHelper.close(context) + }) + }) + }) + } + + function startListening(apiClient, jobId) { + var startParams = "0,1500"; + startParams += "," + jobId, apiClient.sendMessage("SyncJobStart", startParams) + } + + function stopListening(apiClient) { + apiClient.sendMessage("SyncJobStop", "") + } + + function bindEvents(context, jobId, apiClient) { + context.querySelector(".jobItems").addEventListener("click", function(e) { + var btnJobItemMenu = dom.parentWithClass(e.target, "btnJobItemMenu"); + btnJobItemMenu && showJobItemMenu(btnJobItemMenu, jobId, apiClient) + }) + } + + function showEditor(options) { + function onSyncJobMessage(e, apiClient, msg) { + loadJobInfo(dlg, msg.Job, msg.JobItems, apiClient) + } + var apiClient = connectionManager.getApiClient(options.serverId), + id = options.jobId, + dlgElementOptions = { + removeOnClose: !0, + scrollY: !1, + autoFocus: !1 + }; + layoutManager.tv ? dlgElementOptions.size = "fullscreen" : dlgElementOptions.size = "medium"; + var dlg = dialogHelper.createDialog(dlgElementOptions); + dlg.classList.add("formDialog"); + var html = ""; + html += '
    ', html += '', html += '

    ', html += globalize.translate("sharedcomponents#Sync"), html += "

    ", appHost.supports("externallinks") && (html += 'info' + globalize.translate("sharedcomponents#Help") + ""), html += "
    ", html += '
    ', html += '
    ', html += '
    ', html += '
    ', html += '
    ', html += '
    ', html += '", html += "
    ", html += "
    ", html += "
    ", html += "
    ", dlg.innerHTML = html; + dlg.querySelector("form").addEventListener("submit", function(e) { + return saveJob(dlg, id, apiClient), e.preventDefault(), !1 + }), dlg.querySelector(".btnCancel").addEventListener("click", function() { + dialogHelper.close(dlg) + }), layoutManager.tv && scrollHelper.centerFocus.on(dlg.querySelector(".formDialogContent"), !1), loadJob(dlg, id, apiClient), bindEvents(dlg, id, apiClient); + var promise = dialogHelper.open(dlg); + return startListening(apiClient, id), events.on(serverNotifications, "SyncJob", onSyncJobMessage), promise.then(function() { + return stopListening(apiClient), events.off(serverNotifications, "SyncJob", onSyncJobMessage), layoutManager.tv && scrollHelper.centerFocus.off(dlg.querySelector(".formDialogContent"), !1), Promise.reject() + }) + } + var _jobOptions; + return { + show: showEditor + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/sync/syncjoblist.js b/dashboard-ui/bower_components/emby-webcomponents/sync/syncjoblist.js index 0208990a9a..aa14d247f9 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/sync/syncjoblist.js +++ b/dashboard-ui/bower_components/emby-webcomponents/sync/syncjoblist.js @@ -1 +1,209 @@ -define(["serverNotifications","events","loading","connectionManager","imageLoader","dom","globalize","registrationServices","layoutManager","listViewStyle"],function(serverNotifications,events,loading,connectionManager,imageLoader,dom,globalize,registrationServices,layoutManager){"use strict";function onSyncJobCreated(e,apiClient,data){fetchData(this)}function onSyncJobUpdated(e,apiClient,data){refreshJob(this,data)}function onSyncJobCancelled(e,apiClient,data){fetchData(this)}function refreshList(listInstance,jobs){for(var i=0,length=jobs.length;i0&&progress<100&&(progress=progress.toFixed(1)),html+=progress+"%"}return html}function getSyncJobHtml(listInstance,job,apiClient){var html="",tagName=layoutManager.tv?"button":"div",typeAttribute="button"===tagName?' type="button"':"",listItemClass="listItem listItem-border";layoutManager.tv&&(listItemClass+=" listItem-button listItem-focusscale",listItemClass+=" btnJobMenu");var canEdit=(job.ItemCount||1)>1||"Queued"===job.Status;html+="<"+tagName+typeAttribute+' class="'+listItemClass+'" data-canedit="'+canEdit+'" data-id="'+job.Id+'" data-status="'+job.Status+'">';var imgUrl;job.PrimaryImageItemId&&(imgUrl=apiClient.getImageUrl(job.PrimaryImageItemId,{type:"Primary",width:80,tag:job.PrimaryImageTag,minScale:1.5})),imgUrl?(html+='
    ',html+="
    "):html+='file_download';var textLines=[],name=job.Name;job.ParentName&&(name+=" - "+job.ParentName),textLines.push(name),1===job.ItemCount||textLines.push(globalize.translate("sharedcomponents#ItemCount",job.ItemCount)),html+='
    ';for(var i=0,length=textLines.length;i',html+=textLines[i],html+=""):(html+='
    ',html+=textLines[i],html+="
    ");return html+='
    ',html+=getProgressText(job),html+="
    ",html+="
    ",layoutManager.tv||(html+=canEdit?'':''),html+=""}function renderList(listInstance,jobs,apiClient){if((new Date).getTime()-listInstance.lastDataLoad<6e4)return void refreshList(listInstance,jobs);listInstance.lastDataLoad=(new Date).getTime();for(var html="",lastTargetName="",mode=listInstance.options.mode,showTargetName="download"!==mode,hasOpenSection=!1,i=0,length=jobs.length;i",html+="
    ",hasOpenSection=!1),lastTargetName=targetName,html+='
    ',html+='
    ',html+='

    '+targetName+"

    ",html+="
    ",html+='
    ',hasOpenSection=!0)}html+=getSyncJobHtml(listInstance,job,apiClient)}hasOpenSection&&(html+="
    ",html+="
    ");var elem=listInstance.options.element.querySelector(".syncJobListContent");html||(html="download"===mode?'
    '+globalize.translate("sharedcomponents#MessageNoDownloadsFound")+"
    ":'
    '+globalize.translate("sharedcomponents#MessageNoSyncJobsFound")+"
    "),elem.innerHTML=html,imageLoader.lazyChildren(elem)}function fetchData(listInstance){listInstance.lastDataLoad=0,loading.show();var options={},apiClient=getApiClient(listInstance);return listInstance.options.userId&&(options.UserId=listInstance.options.userId),"download"===listInstance.options.mode&&(options.TargetId=apiClient.deviceId()),apiClient.getJSON(apiClient.getUrl("Sync/Jobs",options)).then(function(response){renderList(listInstance,response.Items,apiClient),loading.hide()})}function getApiClient(listInstance){return connectionManager.getApiClient(listInstance.options.serverId)}function showJobMenu(listInstance,elem){var item=dom.parentWithClass(elem,"listItem"),jobId=item.getAttribute("data-id"),menuItems=(item.getAttribute("data-status"),[]);"true"===item.getAttribute("data-canedit")&&menuItems.push({name:globalize.translate("sharedcomponents#Edit"),id:"edit"});var txt=globalize.translate("sharedcomponents#RemoveDownload");menuItems.push({name:txt,id:"cancel"}),require(["actionsheet"],function(actionsheet){actionsheet.show({items:menuItems,positionTo:elem,callback:function(id){switch(id){case"delete":case"cancel":cancelJob(listInstance,jobId);break;case"edit":showJobEditor(listInstance,elem)}}})})}function onElementClick(e){var listInstance=this,btnJobMenu=dom.parentWithClass(e.target,"btnJobMenu");if(btnJobMenu)return void showJobMenu(listInstance,btnJobMenu);var btnCancelJob=dom.parentWithClass(e.target,"btnCancelJob");if(btnCancelJob){var listItem=dom.parentWithClass(btnCancelJob,"listItem");if(listItem){cancelJob(listInstance,listItem.getAttribute("data-id"))}}else showJobEditor(listInstance,e.target)}function showJobEditor(listInstance,elem){var listItem=dom.parentWithClass(elem,"listItem");if(listItem&&"true"===listItem.getAttribute("data-canedit")){var jobId=listItem.getAttribute("data-id");require(["syncJobEditor"],function(syncJobEditor){syncJobEditor.show({serverId:listInstance.options.serverId,jobId:jobId,mode:listInstance.options.mode}).then(function(){fetchData(listInstance)})})}}function syncJobList(options){this.options=options;var onSyncJobCreatedHandler=onSyncJobCreated.bind(this);this.onSyncJobCreatedHandler=onSyncJobCreatedHandler,events.on(serverNotifications,"SyncJobCreated",onSyncJobCreatedHandler);var onSyncJobCancelledHandler=onSyncJobCancelled.bind(this);this.onSyncJobCancelledHandler=onSyncJobCancelledHandler,events.on(serverNotifications,"SyncJobCancelled",onSyncJobCancelledHandler);var onSyncJobUpdatedHandler=onSyncJobUpdated.bind(this);this.onSyncJobUpdatedHandler=onSyncJobUpdatedHandler,events.on(serverNotifications,"SyncJobUpdated",onSyncJobUpdatedHandler);var onClickHandler=onElementClick.bind(this);options.element.addEventListener("click",onClickHandler),this.onClickHandler=onClickHandler,options.element.innerHTML='
    ',fetchData(this),initSupporterInfo(options.element,getApiClient(this))}function showSupporterInfo(context){var html='' : ''), html += "" + } + + function renderList(listInstance, jobs, apiClient) { + if ((new Date).getTime() - listInstance.lastDataLoad < 6e4) return void refreshList(listInstance, jobs); + listInstance.lastDataLoad = (new Date).getTime(); + for (var html = "", lastTargetName = "", mode = listInstance.options.mode, showTargetName = "download" !== mode, hasOpenSection = !1, i = 0, length = jobs.length; i < length; i++) { + var job = jobs[i]; + if (showTargetName) { + var targetName = job.TargetName || "Unknown"; + targetName !== lastTargetName && (lastTargetName && (html += "
    ", html += "
    ", hasOpenSection = !1), lastTargetName = targetName, html += '
    ', html += '
    ', html += '

    ' + targetName + "

    ", html += "
    ", html += '
    ', hasOpenSection = !0) + } + html += getSyncJobHtml(listInstance, job, apiClient) + } + hasOpenSection && (html += "
    ", html += "
    "); + var elem = listInstance.options.element.querySelector(".syncJobListContent"); + html || (html = "download" === mode ? '
    ' + globalize.translate("sharedcomponents#MessageNoDownloadsFound") + "
    " : '
    ' + globalize.translate("sharedcomponents#MessageNoSyncJobsFound") + "
    "), elem.innerHTML = html, imageLoader.lazyChildren(elem) + } + + function fetchData(listInstance) { + listInstance.lastDataLoad = 0, loading.show(); + var options = {}, + apiClient = getApiClient(listInstance); + return listInstance.options.userId && (options.UserId = listInstance.options.userId), "download" === listInstance.options.mode && (options.TargetId = apiClient.deviceId()), apiClient.getJSON(apiClient.getUrl("Sync/Jobs", options)).then(function(response) { + renderList(listInstance, response.Items, apiClient), loading.hide() + }) + } + + function getApiClient(listInstance) { + return connectionManager.getApiClient(listInstance.options.serverId) + } + + function showJobMenu(listInstance, elem) { + var item = dom.parentWithClass(elem, "listItem"), + jobId = item.getAttribute("data-id"), + menuItems = (item.getAttribute("data-status"), []); + "true" === item.getAttribute("data-canedit") && menuItems.push({ + name: globalize.translate("sharedcomponents#Edit"), + id: "edit" + }); + var txt = globalize.translate("sharedcomponents#RemoveDownload"); + menuItems.push({ + name: txt, + id: "cancel" + }), require(["actionsheet"], function(actionsheet) { + actionsheet.show({ + items: menuItems, + positionTo: elem, + callback: function(id) { + switch (id) { + case "delete": + case "cancel": + cancelJob(listInstance, jobId); + break; + case "edit": + showJobEditor(listInstance, elem) + } + } + }) + }) + } + + function onElementClick(e) { + var listInstance = this, + btnJobMenu = dom.parentWithClass(e.target, "btnJobMenu"); + if (btnJobMenu) return void showJobMenu(listInstance, btnJobMenu); + var btnCancelJob = dom.parentWithClass(e.target, "btnCancelJob"); + if (btnCancelJob) { + var listItem = dom.parentWithClass(btnCancelJob, "listItem"); + if (listItem) { + cancelJob(listInstance, listItem.getAttribute("data-id")) + } + } else showJobEditor(listInstance, e.target) + } + + function showJobEditor(listInstance, elem) { + var listItem = dom.parentWithClass(elem, "listItem"); + if (listItem && "true" === listItem.getAttribute("data-canedit")) { + var jobId = listItem.getAttribute("data-id"); + require(["syncJobEditor"], function(syncJobEditor) { + syncJobEditor.show({ + serverId: listInstance.options.serverId, + jobId: jobId, + mode: listInstance.options.mode + }).then(function() { + fetchData(listInstance) + }) + }) + } + } + + function syncJobList(options) { + this.options = options; + var onSyncJobCreatedHandler = onSyncJobCreated.bind(this); + this.onSyncJobCreatedHandler = onSyncJobCreatedHandler, events.on(serverNotifications, "SyncJobCreated", onSyncJobCreatedHandler); + var onSyncJobCancelledHandler = onSyncJobCancelled.bind(this); + this.onSyncJobCancelledHandler = onSyncJobCancelledHandler, events.on(serverNotifications, "SyncJobCancelled", onSyncJobCancelledHandler); + var onSyncJobUpdatedHandler = onSyncJobUpdated.bind(this); + this.onSyncJobUpdatedHandler = onSyncJobUpdatedHandler, events.on(serverNotifications, "SyncJobUpdated", onSyncJobUpdatedHandler); + var onClickHandler = onElementClick.bind(this); + options.element.addEventListener("click", onClickHandler), this.onClickHandler = onClickHandler, options.element.innerHTML = '
    ', fetchData(this), initSupporterInfo(options.element, getApiClient(this)) + } + + function showSupporterInfo(context) { + var html = '
    '),btnFilter.classList.add("btnFilterWithBubble"),bubble=btnFilter.querySelector(".filterButtonBubble")}hasFilters?bubble.classList.remove("hide"):bubble.classList.add("hide")}},ItemsTab.prototype.onPause=function(){var scroller=this.scroller;scroller&&scroller.pause&&scroller.pause();var alphaNumericShortcuts=this.alphaNumericShortcuts;alphaNumericShortcuts&&(alphaNumericShortcuts.destroy(),this.alphaNumericShortcuts=null)},ItemsTab.prototype.destroy=function(){this.view=null,this.itemsContainer=null,this.params=null,this.apiClient=null,this.scroller=null,this.filterButtons=null,this.alphaPicker&&(this.alphaPicker.destroy(),this.alphaPicker=null),this.sortButtons=null,this.btnSortText=null,this.btnSortIcon=null,this.alphaPickerElement=null},ItemsTab}); \ No newline at end of file +define(["playbackManager", "userSettings", "alphaPicker", "alphaNumericShortcuts", "connectionManager", "focusManager", "loading", "globalize"], function(playbackManager, userSettings, AlphaPicker, AlphaNumericShortcuts, connectionManager, focusManager, loading, globalize) { + "use strict"; + + function trySelectValue(instance, scroller, view, value) { + var card; + if ("#" === value && (card = view.querySelector(".card"))) return void scroller.toStart(card, !1); + if (card = view.querySelector(".card[data-prefix^='" + value + "']")) return void scroller.toStart(card, !1); + var values = instance.alphaPicker.values(), + index = values.indexOf(value); + if (index < values.length - 2) trySelectValue(instance, scroller, view, values[index + 1]); + else { + var all = view.querySelectorAll(".card"); + card = all.length ? all[all.length - 1] : null, card && scroller.toStart(card, !1) + } + } + + function onAlphaValueChanged() { + var value = this.alphaPicker.value(); + trySelectValue(this, this.scroller, this.itemsContainer, value) + } + + function initAlphaPicker(instance, view) { + instance.itemsContainer = view.querySelector(".itemsContainer"), instance.alphaPicker = new AlphaPicker({ + element: instance.alphaPickerElement, + itemsContainer: instance.itemsContainer, + itemClass: "card" + }), instance.alphaPicker.on("alphavaluechanged", onAlphaValueChanged.bind(instance)) + } + + function showFilterMenu() { + var instance = this; + require(["filterMenu"], function(FilterMenu) { + (new FilterMenu).show({ + settingsKey: instance.getSettingsKey(), + settings: instance.getFilters(), + visibleSettings: instance.getVisibleFilters(), + onChange: instance.itemsContainer.refreshItems.bind(instance.itemsContainer), + parentId: instance.params.parentId, + itemTypes: instance.getItemTypes ? instance.getItemTypes() : [], + serverId: instance.apiClient.serverId(), + filterMenuOptions: instance.getFilterMenuOptions() + }).then(function() { + instance.itemsContainer.refreshItems() + }) + }) + } + + function updateAlphaPickerState(instance) { + if (instance.alphaPicker) { + var alphaPicker = instance.alphaPickerElement; + if (alphaPicker) { + var values = instance.getSortValues(); + "SortName" === values.sortBy && "Ascending" === values.sortOrder ? alphaPicker.classList.remove("hide") : alphaPicker.classList.add("hide") + } + } + } + + function showSortMenu() { + var instance = this; + require(["sortMenu"], function(SortMenu) { + (new SortMenu).show({ + settingsKey: instance.getSettingsKey(), + settings: instance.getSortValues(), + onChange: instance.itemsContainer.refreshItems.bind(instance.itemsContainer), + serverId: instance.params.serverId, + sortOptions: instance.getSortMenuOptions() + }).then(function() { + updateSortText(instance), updateAlphaPickerState(instance), instance.itemsContainer.refreshItems() + }) + }) + } + + function showViewSettingsMenu() { + var instance = this; + require(["viewSettings"], function(ViewSettings) { + (new ViewSettings).show({ + settingsKey: instance.getSettingsKey(), + settings: instance.getViewSettings(), + visibleSettings: instance.getVisibleViewSettings() + }).then(function() { + updateItemsContainerForViewType(instance), instance.itemsContainer.refreshItems() + }) + }) + } + + function updateItemsContainerForViewType(instance) { + "list" === instance.getViewSettings().imageType ? (instance.itemsContainer.classList.remove("vertical-wrap"), instance.itemsContainer.classList.add("vertical-list")) : (instance.itemsContainer.classList.add("vertical-wrap"), instance.itemsContainer.classList.remove("vertical-list")) + } + + function updateSortText(instance) { + var btnSortText = instance.btnSortText; + if (btnSortText) { + for (var options = instance.getSortMenuOptions(), values = instance.getSortValues(), sortBy = values.sortBy, i = 0, length = options.length; i < length; i++) + if (sortBy === options[i].value) { + btnSortText.innerHTML = globalize.translate("sharedcomponents#SortByValue", options[i].name); + break + } var btnSortIcon = instance.btnSortIcon; + btnSortIcon && (btnSortIcon.innerHTML = "Descending" === values.sortOrder ? "" : "") + } + } + + function bindAll(elems, eventName, fn) { + for (var i = 0, length = elems.length; i < length; i++) elems[i].addEventListener(eventName, fn) + } + + function play() { + this.fetchData().then(function(result) { + playbackManager.play({ + items: result.Items || result + }) + }) + } + + function shuffle() { + this.fetchData().then(function(result) { + playbackManager.play({ + items: result.Items || result + }) + }) + } + + function hideOrShowAll(elems, hide) { + for (var i = 0, length = elems.length; i < length; i++) hide ? elems[i].classList.add("hide") : elems[i].classList.remove("hide") + } + + function ItemsTab(view, params) { + this.view = view, this.params = params, params.serverId && (this.apiClient = connectionManager.getApiClient(params.serverId)), this.itemsContainer = view.querySelector(".itemsContainer"), this.scroller = view.querySelector(".scrollFrameY"), this.itemsContainer.fetchData = this.fetchData.bind(this), this.itemsContainer.getItemsHtml = this.getItemsHtml.bind(this), params.parentId && this.itemsContainer.setAttribute("data-parentid", params.parentId); + var i, length, btnViewSettings = view.querySelectorAll(".btnViewSettings"); + for (i = 0, length = btnViewSettings.length; i < length; i++) btnViewSettings[i].addEventListener("click", showViewSettingsMenu.bind(this)); + var filterButtons = view.querySelectorAll(".btnFilter"); + this.filterButtons = filterButtons; + var hasVisibleFilters = this.getVisibleFilters().length; + for (i = 0, length = filterButtons.length; i < length; i++) { + var btnFilter = filterButtons[i]; + btnFilter.addEventListener("click", showFilterMenu.bind(this)), hasVisibleFilters ? btnFilter.classList.remove("hide") : btnFilter.classList.add("hide") + } + var sortButtons = view.querySelectorAll(".btnSort"); + for (this.sortButtons = sortButtons, i = 0, length = sortButtons.length; i < length; i++) { + var sortButton = sortButtons[i]; + sortButton.addEventListener("click", showSortMenu.bind(this)), "nextup" !== params.type && sortButton.classList.remove("hide") + } + this.btnSortText = view.querySelector(".btnSortText"), this.btnSortIcon = view.querySelector(".btnSortIcon"), this.alphaPickerElement = view.querySelector(".alphaPicker"), hideOrShowAll(view.querySelectorAll(".btnShuffle"), !0), bindAll(view.querySelectorAll(".btnPlay"), "click", play.bind(this)), bindAll(view.querySelectorAll(".btnShuffle"), "click", shuffle.bind(this)) + } + return ItemsTab.prototype.getViewSettings = function() { + var basekey = this.getSettingsKey(); + return { + showTitle: "false" !== userSettings.get(basekey + "-showTitle"), + showYear: "false" !== userSettings.get(basekey + "-showYear"), + imageType: userSettings.get(basekey + "-imageType") || this.getDefaultImageType() + } + }, ItemsTab.prototype.getDefaultImageType = function() { + return "primary" + }, ItemsTab.prototype.getSettingsKey = function() { + return this.params.parentId + "-1" + }, ItemsTab.prototype.onResume = function(options) { + options && options.refresh && (updateSortText(this), updateItemsContainerForViewType(this), loading.show()); + var view = this.view, + scroller = this.scroller; + scroller && scroller.resume && scroller.resume(), this.enableAlphaPicker && !this.alphaPicker && (initAlphaPicker(this, view), updateAlphaPickerState(this)), !1 !== this.enableAlphaNumericShortcuts && (this.alphaNumericShortcuts = new AlphaNumericShortcuts({ + itemsContainer: this.itemsContainer + })); + var instance = this, + autoFocus = options.autoFocus; + this.itemsContainer.resume(options).then(function(result) { + loading.hide(), autoFocus && focusManager.autoFocus(instance.itemsContainer) + }) + }, ItemsTab.prototype.getVisibleViewSettings = function() { + return ["showTitle", "showYear", "imageType"] + }, ItemsTab.prototype.getFilters = function() { + var basekey = this.getSettingsKey(); + return { + IsPlayed: "true" === userSettings.getFilter(basekey + "-filter-IsPlayed"), + IsUnplayed: "true" === userSettings.getFilter(basekey + "-filter-IsUnplayed"), + IsFavorite: "true" === userSettings.getFilter(basekey + "-filter-IsFavorite"), + IsResumable: "true" === userSettings.getFilter(basekey + "-filter-IsResumable"), + Is4K: "true" === userSettings.getFilter(basekey + "-filter-Is4K"), + IsHD: "true" === userSettings.getFilter(basekey + "-filter-IsHD"), + IsSD: "true" === userSettings.getFilter(basekey + "-filter-IsSD"), + Is3D: "true" === userSettings.getFilter(basekey + "-filter-Is3D"), + VideoTypes: userSettings.getFilter(basekey + "-filter-VideoTypes"), + SeriesStatus: userSettings.getFilter(basekey + "-filter-SeriesStatus"), + HasSubtitles: userSettings.getFilter(basekey + "-filter-HasSubtitles"), + HasTrailer: userSettings.getFilter(basekey + "-filter-HasTrailer"), + HasSpecialFeature: userSettings.getFilter(basekey + "-filter-HasSpecialFeature"), + HasThemeSong: userSettings.getFilter(basekey + "-filter-HasThemeSong"), + HasThemeVideo: userSettings.getFilter(basekey + "-filter-HasThemeVideo"), + GenreIds: userSettings.getFilter(basekey + "-filter-GenreIds") + } + }, ItemsTab.prototype.getSortValues = function() { + var basekey = this.getSettingsKey(); + return { + sortBy: userSettings.getFilter(basekey + "-sortby") || this.getSortMenuOptions()[0].value, + sortOrder: "Descending" === userSettings.getFilter(basekey + "-sortorder") ? "Descending" : "Ascending" + } + }, ItemsTab.prototype.getVisibleFilters = function() { + return ["IsUnplayed", "IsPlayed", "IsFavorite", "IsResumable", "VideoType", "HasSubtitles", "HasTrailer", "HasSpecialFeature", "HasThemeSong", "HasThemeVideo"] + }, ItemsTab.prototype.getDefaultSortBy = function() { + return "SortName" + }, ItemsTab.prototype.getSortMenuOptions = function() { + var sortBy = [], + option = this.getNameSortOption(); + return option && sortBy.push(option), option = this.getCommunityRatingSortOption(), option && sortBy.push(option), option = this.getCriticRatingSortOption(), option && sortBy.push(option), sortBy.push({ + name: globalize.translate("sharedcomponents#DateAdded"), + value: "DateCreated,SortName" + }), option = this.getDatePlayedSortOption(), option && sortBy.push(option), sortBy.push({ + name: globalize.translate("sharedcomponents#ParentalRating"), + value: "OfficialRating,SortName" + }), option = this.getPlayCountSortOption(), option && sortBy.push(option), sortBy.push({ + name: globalize.translate("sharedcomponents#ReleaseDate"), + value: "PremiereDate,ProductionYear,SortName" + }), sortBy.push({ + name: globalize.translate("sharedcomponents#Runtime"), + value: "Runtime,SortName" + }), sortBy + }, ItemsTab.prototype.getNameSortOption = function() { + return { + name: globalize.translate("sharedcomponents#Name"), + value: "SortName" + } + }, ItemsTab.prototype.getPlayCountSortOption = function() { + return { + name: globalize.translate("sharedcomponents#PlayCount"), + value: "PlayCount,SortName" + } + }, ItemsTab.prototype.getDatePlayedSortOption = function() { + return { + name: globalize.translate("sharedcomponents#DatePlayed"), + value: "DatePlayed,SortName" + } + }, ItemsTab.prototype.getCriticRatingSortOption = function() { + return { + name: globalize.translate("sharedcomponents#CriticRating"), + value: "CriticRating,SortName" + } + }, ItemsTab.prototype.getCommunityRatingSortOption = function() { + return { + name: globalize.translate("sharedcomponents#CommunityRating"), + value: "CommunityRating,SortName" + } + }, ItemsTab.prototype.getFilterMenuOptions = function() { + this.params; + return {} + }, ItemsTab.prototype.getItemTypes = function() { + return [] + }, ItemsTab.prototype.setFilterStatus = function(hasFilters) { + this.hasFilters = hasFilters; + var filterButtons = this.filterButtons; + if (filterButtons.length) + for (var i = 0, length = filterButtons.length; i < length; i++) { + var btnFilter = filterButtons[i], + bubble = btnFilter.querySelector(".filterButtonBubble"); + if (!bubble) { + if (!hasFilters) continue; + btnFilter.insertAdjacentHTML("afterbegin", '
    !
    '), btnFilter.classList.add("btnFilterWithBubble"), bubble = btnFilter.querySelector(".filterButtonBubble") + } + hasFilters ? bubble.classList.remove("hide") : bubble.classList.add("hide") + } + }, ItemsTab.prototype.onPause = function() { + var scroller = this.scroller; + scroller && scroller.pause && scroller.pause(); + var alphaNumericShortcuts = this.alphaNumericShortcuts; + alphaNumericShortcuts && (alphaNumericShortcuts.destroy(), this.alphaNumericShortcuts = null) + }, ItemsTab.prototype.destroy = function() { + this.view = null, this.itemsContainer = null, this.params = null, this.apiClient = null, this.scroller = null, this.filterButtons = null, this.alphaPicker && (this.alphaPicker.destroy(), this.alphaPicker = null), this.sortButtons = null, this.btnSortText = null, this.btnSortIcon = null, this.alphaPickerElement = null + }, ItemsTab +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/tabbedview/tabbedview.js b/dashboard-ui/bower_components/emby-webcomponents/tabbedview/tabbedview.js index ac0041dd38..d4f5ef6675 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/tabbedview/tabbedview.js +++ b/dashboard-ui/bower_components/emby-webcomponents/tabbedview/tabbedview.js @@ -1 +1,59 @@ -define(["backdrop","mainTabsManager","layoutManager","emby-tabs"],function(backdrop,mainTabsManager,layoutManager){"use strict";function onViewDestroy(e){var tabControllers=this.tabControllers;tabControllers&&(tabControllers.forEach(function(t){t.destroy&&t.destroy()}),this.tabControllers=null),this.view=null,this.params=null,this.currentTabController=null,this.initialTabIndex=null}function onBeforeTabChange(){}function TabbedView(view,params){function validateTabLoad(index){return self.validateTabLoad?self.validateTabLoad(index):Promise.resolve()}function loadTab(index,previousIndex){validateTabLoad(index).then(function(){self.getTabController(index).then(function(controller){var refresh=!controller.refreshed;controller.onResume({autoFocus:null==previousIndex&&layoutManager.tv,refresh:refresh}),controller.refreshed=!0,currentTabIndex=index,self.currentTabController=controller})})}function getTabContainers(){return view.querySelectorAll(".tabContent")}function onTabChange(e){var newIndex=parseInt(e.detail.selectedTabIndex),previousIndex=e.detail.previousIndex,previousTabController=null==previousIndex?null:self.tabControllers[previousIndex];previousTabController&&previousTabController.onPause&&previousTabController.onPause(),loadTab(newIndex,previousIndex)}this.tabControllers=[],this.view=view,this.params=params;var self=this,currentTabIndex=parseInt(params.tab||this.getDefaultTabIndex(params.parentId));this.initialTabIndex=currentTabIndex,view.addEventListener("viewbeforehide",this.onPause.bind(this)),view.addEventListener("viewbeforeshow",function(e){mainTabsManager.setTabs(view,currentTabIndex,self.getTabs,getTabContainers,onBeforeTabChange,onTabChange,!1)}),view.addEventListener("viewshow",function(e){self.onResume(e.detail)}),view.addEventListener("viewdestroy",onViewDestroy.bind(this))}return TabbedView.prototype.onResume=function(options){this.setTitle(),backdrop.clear();var currentTabController=this.currentTabController;currentTabController?currentTabController&¤tTabController.onResume&¤tTabController.onResume({}):mainTabsManager.selectedTabIndex(this.initialTabIndex)},TabbedView.prototype.onPause=function(){var currentTabController=this.currentTabController;currentTabController&¤tTabController.onPause&¤tTabController.onPause()},TabbedView.prototype.setTitle=function(){Emby.Page.setTitle("")},TabbedView}); \ No newline at end of file +define(["backdrop", "mainTabsManager", "layoutManager", "emby-tabs"], function(backdrop, mainTabsManager, layoutManager) { + "use strict"; + + function onViewDestroy(e) { + var tabControllers = this.tabControllers; + tabControllers && (tabControllers.forEach(function(t) { + t.destroy && t.destroy() + }), this.tabControllers = null), this.view = null, this.params = null, this.currentTabController = null, this.initialTabIndex = null + } + + function onBeforeTabChange() {} + + function TabbedView(view, params) { + function validateTabLoad(index) { + return self.validateTabLoad ? self.validateTabLoad(index) : Promise.resolve() + } + + function loadTab(index, previousIndex) { + validateTabLoad(index).then(function() { + self.getTabController(index).then(function(controller) { + var refresh = !controller.refreshed; + controller.onResume({ + autoFocus: null == previousIndex && layoutManager.tv, + refresh: refresh + }), controller.refreshed = !0, currentTabIndex = index, self.currentTabController = controller + }) + }) + } + + function getTabContainers() { + return view.querySelectorAll(".tabContent") + } + + function onTabChange(e) { + var newIndex = parseInt(e.detail.selectedTabIndex), + previousIndex = e.detail.previousIndex, + previousTabController = null == previousIndex ? null : self.tabControllers[previousIndex]; + previousTabController && previousTabController.onPause && previousTabController.onPause(), loadTab(newIndex, previousIndex) + } + this.tabControllers = [], this.view = view, this.params = params; + var self = this, + currentTabIndex = parseInt(params.tab || this.getDefaultTabIndex(params.parentId)); + this.initialTabIndex = currentTabIndex, view.addEventListener("viewbeforehide", this.onPause.bind(this)), view.addEventListener("viewbeforeshow", function(e) { + mainTabsManager.setTabs(view, currentTabIndex, self.getTabs, getTabContainers, onBeforeTabChange, onTabChange, !1) + }), view.addEventListener("viewshow", function(e) { + self.onResume(e.detail) + }), view.addEventListener("viewdestroy", onViewDestroy.bind(this)) + } + return TabbedView.prototype.onResume = function(options) { + this.setTitle(), backdrop.clear(); + var currentTabController = this.currentTabController; + currentTabController ? currentTabController && currentTabController.onResume && currentTabController.onResume({}) : mainTabsManager.selectedTabIndex(this.initialTabIndex) + }, TabbedView.prototype.onPause = function() { + var currentTabController = this.currentTabController; + currentTabController && currentTabController.onPause && currentTabController.onPause() + }, TabbedView.prototype.setTitle = function() { + Emby.Page.setTitle("") + }, TabbedView +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/thememediaplayer.js b/dashboard-ui/bower_components/emby-webcomponents/thememediaplayer.js index b2132ff727..532ff2b851 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/thememediaplayer.js +++ b/dashboard-ui/bower_components/emby-webcomponents/thememediaplayer.js @@ -1 +1,49 @@ -define(["playbackManager","userSettings","connectionManager"],function(playbackManager,userSettings,connectionManager){"use strict";function playThemeMedia(items,ownerId){var currentThemeItems=items.filter(function(i){return enabled(i.MediaType)});if(currentThemeItems.length){if(!currentOwnerId&&playbackManager.isPlaying())return;currentThemeIds=currentThemeItems.map(function(i){return i.Id}),playbackManager.play({items:currentThemeItems,fullscreen:!1,enableRemotePlayers:!1}).then(function(){currentOwnerId=ownerId})}else stopIfPlaying()}function stopIfPlaying(){currentOwnerId&&playbackManager.stop(),currentOwnerId=null}function enabled(mediaType){return"Video"===mediaType?userSettings.enableThemeVideos():userSettings.enableThemeSongs()}function loadThemeMedia(item){if(item.CollectionType)return void stopIfPlaying();if(-1!==excludeTypes.indexOf(item.Type))return void stopIfPlaying();var apiClient=connectionManager.getApiClient(item.ServerId);apiClient.getThemeMedia(apiClient.getCurrentUserId(),item.Id,!0).then(function(themeMediaResult){var ownerId=themeMediaResult.ThemeVideosResult.Items.length?themeMediaResult.ThemeVideosResult.OwnerId:themeMediaResult.ThemeSongsResult.OwnerId;if(ownerId!==currentOwnerId){playThemeMedia(themeMediaResult.ThemeVideosResult.Items.length?themeMediaResult.ThemeVideosResult.Items:themeMediaResult.ThemeSongsResult.Items,ownerId)}})}var currentOwnerId,currentThemeIds=[],excludeTypes=["CollectionFolder","UserView","Program","SeriesTimer","Person","TvChannel","Channel"];document.addEventListener("viewshow",function(e){var state=e.detail.state||{},item=state.item;if(item&&item.ServerId)return void loadThemeMedia(item);(e.detail.options||{}).supportsThemeMedia||playThemeMedia([],null)},!0)}); \ No newline at end of file +define(["playbackManager", "userSettings", "connectionManager"], function(playbackManager, userSettings, connectionManager) { + "use strict"; + + function playThemeMedia(items, ownerId) { + var currentThemeItems = items.filter(function(i) { + return enabled(i.MediaType) + }); + if (currentThemeItems.length) { + if (!currentOwnerId && playbackManager.isPlaying()) return; + currentThemeIds = currentThemeItems.map(function(i) { + return i.Id + }), playbackManager.play({ + items: currentThemeItems, + fullscreen: !1, + enableRemotePlayers: !1 + }).then(function() { + currentOwnerId = ownerId + }) + } else stopIfPlaying() + } + + function stopIfPlaying() { + currentOwnerId && playbackManager.stop(), currentOwnerId = null + } + + function enabled(mediaType) { + return "Video" === mediaType ? userSettings.enableThemeVideos() : userSettings.enableThemeSongs() + } + + function loadThemeMedia(item) { + if (item.CollectionType) return void stopIfPlaying(); + if (-1 !== excludeTypes.indexOf(item.Type)) return void stopIfPlaying(); + var apiClient = connectionManager.getApiClient(item.ServerId); + apiClient.getThemeMedia(apiClient.getCurrentUserId(), item.Id, !0).then(function(themeMediaResult) { + var ownerId = themeMediaResult.ThemeVideosResult.Items.length ? themeMediaResult.ThemeVideosResult.OwnerId : themeMediaResult.ThemeSongsResult.OwnerId; + if (ownerId !== currentOwnerId) { + playThemeMedia(themeMediaResult.ThemeVideosResult.Items.length ? themeMediaResult.ThemeVideosResult.Items : themeMediaResult.ThemeSongsResult.Items, ownerId) + } + }) + } + var currentOwnerId, currentThemeIds = [], + excludeTypes = ["CollectionFolder", "UserView", "Program", "SeriesTimer", "Person", "TvChannel", "Channel"]; + document.addEventListener("viewshow", function(e) { + var state = e.detail.state || {}, + item = state.item; + if (item && item.ServerId) return void loadThemeMedia(item); + (e.detail.options || {}).supportsThemeMedia || playThemeMedia([], null) + }, !0) +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/toast/toast.js b/dashboard-ui/bower_components/emby-webcomponents/toast/toast.js index 4310a97b2f..56b27182c1 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/toast/toast.js +++ b/dashboard-ui/bower_components/emby-webcomponents/toast/toast.js @@ -1 +1,24 @@ -define(["css!./toast"],function(){"use strict";function remove(elem){setTimeout(function(){elem.parentNode.removeChild(elem)},300)}function animateRemove(elem){setTimeout(function(){elem.classList.remove("toastVisible"),remove(elem)},3300)}return function(options){"string"==typeof options&&(options={text:options});var elem=document.createElement("div");elem.classList.add("toast"),elem.innerHTML=options.text,document.body.appendChild(elem),setTimeout(function(){elem.classList.add("toastVisible"),animateRemove(elem)},300)}}); \ No newline at end of file +define(["css!./toast"], function() { + "use strict"; + + function remove(elem) { + setTimeout(function() { + elem.parentNode.removeChild(elem) + }, 300) + } + + function animateRemove(elem) { + setTimeout(function() { + elem.classList.remove("toastVisible"), remove(elem) + }, 3300) + } + return function(options) { + "string" == typeof options && (options = { + text: options + }); + var elem = document.createElement("div"); + elem.classList.add("toast"), elem.innerHTML = options.text, document.body.appendChild(elem), setTimeout(function() { + elem.classList.add("toastVisible"), animateRemove(elem) + }, 300) + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/touchhelper.js b/dashboard-ui/bower_components/emby-webcomponents/touchhelper.js index c9f068c752..33d18484db 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/touchhelper.js +++ b/dashboard-ui/bower_components/emby-webcomponents/touchhelper.js @@ -1 +1,74 @@ -define(["dom","events"],function(dom,events){"use strict";function getTouches(e){return e.changedTouches||e.targetTouches||e.touches}function TouchHelper(elem,options){options=options||{};var touchTarget,touchStartX,touchStartY,lastDeltaX,lastDeltaY,thresholdYMet,self=this,swipeXThreshold=options.swipeXThreshold||50,swipeYThreshold=options.swipeYThreshold||50,excludeTagNames=options.ignoreTagNames||[],touchStart=function(e){var touch=getTouches(e)[0];if(touchTarget=null,touchStartX=0,touchStartY=0,lastDeltaX=null,lastDeltaY=null,thresholdYMet=!1,touch){var currentTouchTarget=touch.target;if(dom.parentWithTag(currentTouchTarget,excludeTagNames))return;touchTarget=currentTouchTarget,touchStartX=touch.clientX,touchStartY=touch.clientY}},touchEnd=function(e){var isTouchMove="touchmove"===e.type;if(touchTarget){var deltaX,deltaY,clientX,clientY,touch=getTouches(e)[0];touch?(clientX=touch.clientX||0,clientY=touch.clientY||0,deltaX=clientX-(touchStartX||0),deltaY=clientY-(touchStartY||0)):(deltaX=0,deltaY=0);var currentDeltaX=null==lastDeltaX?deltaX:deltaX-lastDeltaX,currentDeltaY=null==lastDeltaY?deltaY:deltaY-lastDeltaY;lastDeltaX=deltaX,lastDeltaY=deltaY,deltaX>swipeXThreshold&&Math.abs(deltaY)<30?events.trigger(self,"swiperight",[touchTarget]):deltaX<0-swipeXThreshold&&Math.abs(deltaY)<30?events.trigger(self,"swipeleft",[touchTarget]):(deltaY<0-swipeYThreshold||thresholdYMet)&&Math.abs(deltaX)<30?(thresholdYMet=!0,events.trigger(self,"swipeup",[touchTarget,{deltaY:deltaY,deltaX:deltaX,clientX:clientX,clientY:clientY,currentDeltaX:currentDeltaX,currentDeltaY:currentDeltaY}])):(deltaY>swipeYThreshold||thresholdYMet)&&Math.abs(deltaX)<30&&(thresholdYMet=!0,events.trigger(self,"swipedown",[touchTarget,{deltaY:deltaY,deltaX:deltaX,clientX:clientX,clientY:clientY,currentDeltaX:currentDeltaX,currentDeltaY:currentDeltaY}])),isTouchMove&&options.preventDefaultOnMove&&e.preventDefault()}isTouchMove||(touchTarget=null,touchStartX=0,touchStartY=0,lastDeltaX=null,lastDeltaY=null,thresholdYMet=!1)};this.touchStart=touchStart,this.touchEnd=touchEnd,dom.addEventListener(elem,"touchstart",touchStart,{passive:!0}),options.triggerOnMove&&dom.addEventListener(elem,"touchmove",touchEnd,{passive:!options.preventDefaultOnMove}),dom.addEventListener(elem,"touchend",touchEnd,{passive:!0}),dom.addEventListener(elem,"touchcancel",touchEnd,{passive:!0})}return TouchHelper.prototype.destroy=function(){var elem=this.elem;if(elem){var touchStart=this.touchStart,touchEnd=this.touchEnd;dom.removeEventListener(elem,"touchstart",touchStart,{passive:!0}),dom.removeEventListener(elem,"touchmove",touchEnd,{passive:!0}),dom.removeEventListener(elem,"touchend",touchEnd,{passive:!0}),dom.removeEventListener(elem,"touchcancel",touchEnd,{passive:!0})}this.touchStart=null,this.touchEnd=null,this.elem=null},TouchHelper}); \ No newline at end of file +define(["dom", "events"], function(dom, events) { + "use strict"; + + function getTouches(e) { + return e.changedTouches || e.targetTouches || e.touches + } + + function TouchHelper(elem, options) { + options = options || {}; + var touchTarget, touchStartX, touchStartY, lastDeltaX, lastDeltaY, thresholdYMet, self = this, + swipeXThreshold = options.swipeXThreshold || 50, + swipeYThreshold = options.swipeYThreshold || 50, + excludeTagNames = options.ignoreTagNames || [], + touchStart = function(e) { + var touch = getTouches(e)[0]; + if (touchTarget = null, touchStartX = 0, touchStartY = 0, lastDeltaX = null, lastDeltaY = null, thresholdYMet = !1, touch) { + var currentTouchTarget = touch.target; + if (dom.parentWithTag(currentTouchTarget, excludeTagNames)) return; + touchTarget = currentTouchTarget, touchStartX = touch.clientX, touchStartY = touch.clientY + } + }, + touchEnd = function(e) { + var isTouchMove = "touchmove" === e.type; + if (touchTarget) { + var deltaX, deltaY, clientX, clientY, touch = getTouches(e)[0]; + touch ? (clientX = touch.clientX || 0, clientY = touch.clientY || 0, deltaX = clientX - (touchStartX || 0), deltaY = clientY - (touchStartY || 0)) : (deltaX = 0, deltaY = 0); + var currentDeltaX = null == lastDeltaX ? deltaX : deltaX - lastDeltaX, + currentDeltaY = null == lastDeltaY ? deltaY : deltaY - lastDeltaY; + lastDeltaX = deltaX, lastDeltaY = deltaY, deltaX > swipeXThreshold && Math.abs(deltaY) < 30 ? events.trigger(self, "swiperight", [touchTarget]) : deltaX < 0 - swipeXThreshold && Math.abs(deltaY) < 30 ? events.trigger(self, "swipeleft", [touchTarget]) : (deltaY < 0 - swipeYThreshold || thresholdYMet) && Math.abs(deltaX) < 30 ? (thresholdYMet = !0, events.trigger(self, "swipeup", [touchTarget, { + deltaY: deltaY, + deltaX: deltaX, + clientX: clientX, + clientY: clientY, + currentDeltaX: currentDeltaX, + currentDeltaY: currentDeltaY + }])) : (deltaY > swipeYThreshold || thresholdYMet) && Math.abs(deltaX) < 30 && (thresholdYMet = !0, events.trigger(self, "swipedown", [touchTarget, { + deltaY: deltaY, + deltaX: deltaX, + clientX: clientX, + clientY: clientY, + currentDeltaX: currentDeltaX, + currentDeltaY: currentDeltaY + }])), isTouchMove && options.preventDefaultOnMove && e.preventDefault() + } + isTouchMove || (touchTarget = null, touchStartX = 0, touchStartY = 0, lastDeltaX = null, lastDeltaY = null, thresholdYMet = !1) + }; + this.touchStart = touchStart, this.touchEnd = touchEnd, dom.addEventListener(elem, "touchstart", touchStart, { + passive: !0 + }), options.triggerOnMove && dom.addEventListener(elem, "touchmove", touchEnd, { + passive: !options.preventDefaultOnMove + }), dom.addEventListener(elem, "touchend", touchEnd, { + passive: !0 + }), dom.addEventListener(elem, "touchcancel", touchEnd, { + passive: !0 + }) + } + return TouchHelper.prototype.destroy = function() { + var elem = this.elem; + if (elem) { + var touchStart = this.touchStart, + touchEnd = this.touchEnd; + dom.removeEventListener(elem, "touchstart", touchStart, { + passive: !0 + }), dom.removeEventListener(elem, "touchmove", touchEnd, { + passive: !0 + }), dom.removeEventListener(elem, "touchend", touchEnd, { + passive: !0 + }), dom.removeEventListener(elem, "touchcancel", touchEnd, { + passive: !0 + }) + } + this.touchStart = null, this.touchEnd = null, this.elem = null + }, TouchHelper +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/upnextdialog/upnextdialog.js b/dashboard-ui/bower_components/emby-webcomponents/upnextdialog/upnextdialog.js index d01a8ad1c6..0a3427509f 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/upnextdialog/upnextdialog.js +++ b/dashboard-ui/bower_components/emby-webcomponents/upnextdialog/upnextdialog.js @@ -1 +1,134 @@ -define(["dom","playbackManager","connectionManager","events","mediaInfo","layoutManager","focusManager","globalize","itemHelper","css!./upnextdialog","emby-button","flexStyles"],function(dom,playbackManager,connectionManager,events,mediaInfo,layoutManager,focusManager,globalize,itemHelper){"use strict";function seriesImageUrl(item,options){if("Episode"!==item.Type)return null;if(options=options||{},options.type=options.type||"Primary","Primary"===options.type&&item.SeriesPrimaryImageTag)return options.tag=item.SeriesPrimaryImageTag,connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.SeriesId,options);if("Thumb"===options.type){if(item.SeriesThumbImageTag)return options.tag=item.SeriesThumbImageTag,connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.SeriesId,options);if(item.ParentThumbImageTag)return options.tag=item.ParentThumbImageTag,connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.ParentThumbItemId,options)}return null}function imageUrl(item,options){return options=options||{},options.type=options.type||"Primary",item.ImageTags&&item.ImageTags[options.type]?(options.tag=item.ImageTags[options.type],connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.PrimaryImageItemId||item.Id,options)):"Primary"===options.type&&item.AlbumId&&item.AlbumPrimaryImageTag?(options.tag=item.AlbumPrimaryImageTag,connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.AlbumId,options)):null}function setPoster(osdPoster,item,secondaryItem){if(item){var imgUrl=seriesImageUrl(item,{type:"Primary"})||seriesImageUrl(item,{type:"Thumb"})||imageUrl(item,{type:"Primary"});if(!imgUrl&&secondaryItem&&(imgUrl=seriesImageUrl(secondaryItem,{type:"Primary"})||seriesImageUrl(secondaryItem,{type:"Thumb"})||imageUrl(secondaryItem,{type:"Primary"})),imgUrl)return void(osdPoster.innerHTML='')}osdPoster.innerHTML=""}function getHtml(){var html="";return html+='
    ',html+="
    ",html+='
    ',html+='

     

    ',html+='

    ',html+='
    ',html+="
    ",html+='
    ',html+='
    ',html+='",html+='",html+="
    ",html+="
    "}function setNextVideoText(){var instance=this,elem=instance.options.parent,secondsRemaining=Math.max(Math.round(getTimeRemainingMs(instance)/1e3),0);console.log("up next seconds remaining: "+secondsRemaining);var timeText=''+globalize.translate("sharedcomponents#HeaderSecondsValue",secondsRemaining)+"",nextVideoText="Episode"===instance.itemType?globalize.translate("sharedcomponents#HeaderNextEpisodePlayingInValue",timeText):globalize.translate("sharedcomponents#HeaderNextVideoPlayingInValue",timeText);elem.querySelector(".upNextDialog-nextVideoText").innerHTML=nextVideoText}function fillItem(item){var instance=this,elem=instance.options.parent;setPoster(elem.querySelector(".upNextDialog-poster"),item),elem.querySelector(".upNextDialog-overview").innerHTML=item.Overview||"",elem.querySelector(".upNextDialog-mediainfo").innerHTML=mediaInfo.getPrimaryMediaInfoHtml(item,{});var title=itemHelper.getDisplayName(item);item.SeriesName&&(title=item.SeriesName+" - "+title),elem.querySelector(".upNextDialog-title").innerHTML=title||"",instance.itemType=item.Type,instance.show()}function clearCountdownTextTimeout(instance){instance._countdownTextTimeout&&(clearInterval(instance._countdownTextTimeout),instance._countdownTextTimeout=null)}function onStartNowClick(){var options=this.options;if(options){var player=options.player;this.hide(),playbackManager.nextTrack(player)}}function init(instance,options){options.parent.innerHTML=getHtml(),options.parent.classList.add("hide"),options.parent.classList.add("upNextDialog"),options.parent.classList.add("upNextDialog-hidden"),fillItem.call(instance,options.nextItem),options.parent.querySelector(".btnHide").addEventListener("click",instance.hide.bind(instance)),options.parent.querySelector(".btnStartNow").addEventListener("click",onStartNowClick.bind(instance))}function clearHideAnimationEventListeners(instance,elem){var fn=instance._onHideAnimationComplete;fn&&dom.removeEventListener(elem,transitionEndEventName,fn,{once:!0})}function onHideAnimationComplete(e){var instance=this,elem=e.target;elem.classList.add("hide"),clearHideAnimationEventListeners(instance,elem),events.trigger(instance,"hide")}function hideComingUpNext(){var instance=this;if(clearCountdownTextTimeout(this),instance.options){var elem=instance.options.parent;if(elem&&(clearHideAnimationEventListeners(this,elem),!elem.classList.contains("upNextDialog-hidden"))){elem.offsetWidth,elem.classList.add("upNextDialog-hidden");var fn=onHideAnimationComplete.bind(instance);instance._onHideAnimationComplete=fn,dom.addEventListener(elem,transitionEndEventName,fn,{once:!0})}}}function getTimeRemainingMs(instance){var options=instance.options;if(options){var runtimeTicks=playbackManager.duration(options.player);if(runtimeTicks){var timeRemainingTicks=runtimeTicks-playbackManager.currentTime(options.player);return Math.round(timeRemainingTicks/1e4)}}return 0}function startComingUpNextHideTimer(instance){getTimeRemainingMs(instance)<=0||(setNextVideoText.call(instance),clearCountdownTextTimeout(instance),instance._countdownTextTimeout=setInterval(setNextVideoText.bind(instance),400))}function UpNextDialog(options){this.options=options,init(this,options)}var transitionEndEventName=dom.whichTransitionEvent();return UpNextDialog.prototype.show=function(){var elem=this.options.parent;clearHideAnimationEventListeners(this,elem),elem.classList.remove("hide"),elem.offsetWidth,elem.classList.remove("upNextDialog-hidden"),layoutManager.tv&&setTimeout(function(){focusManager.focus(elem.querySelector(".btnStartNow"))},50),startComingUpNextHideTimer(this)},UpNextDialog.prototype.hide=function(){hideComingUpNext.call(this)},UpNextDialog.prototype.destroy=function(){hideComingUpNext.call(this),this.options=null,this.itemType=null},UpNextDialog}); \ No newline at end of file +define(["dom", "playbackManager", "connectionManager", "events", "mediaInfo", "layoutManager", "focusManager", "globalize", "itemHelper", "css!./upnextdialog", "emby-button", "flexStyles"], function(dom, playbackManager, connectionManager, events, mediaInfo, layoutManager, focusManager, globalize, itemHelper) { + "use strict"; + + function seriesImageUrl(item, options) { + if ("Episode" !== item.Type) return null; + if (options = options || {}, options.type = options.type || "Primary", "Primary" === options.type && item.SeriesPrimaryImageTag) return options.tag = item.SeriesPrimaryImageTag, connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.SeriesId, options); + if ("Thumb" === options.type) { + if (item.SeriesThumbImageTag) return options.tag = item.SeriesThumbImageTag, connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.SeriesId, options); + if (item.ParentThumbImageTag) return options.tag = item.ParentThumbImageTag, connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.ParentThumbItemId, options) + } + return null + } + + function imageUrl(item, options) { + return options = options || {}, options.type = options.type || "Primary", item.ImageTags && item.ImageTags[options.type] ? (options.tag = item.ImageTags[options.type], connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.PrimaryImageItemId || item.Id, options)) : "Primary" === options.type && item.AlbumId && item.AlbumPrimaryImageTag ? (options.tag = item.AlbumPrimaryImageTag, connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.AlbumId, options)) : null + } + + function setPoster(osdPoster, item, secondaryItem) { + if (item) { + var imgUrl = seriesImageUrl(item, { + type: "Primary" + }) || seriesImageUrl(item, { + type: "Thumb" + }) || imageUrl(item, { + type: "Primary" + }); + if (!imgUrl && secondaryItem && (imgUrl = seriesImageUrl(secondaryItem, { + type: "Primary" + }) || seriesImageUrl(secondaryItem, { + type: "Thumb" + }) || imageUrl(secondaryItem, { + type: "Primary" + })), imgUrl) return void(osdPoster.innerHTML = '') + } + osdPoster.innerHTML = "" + } + + function getHtml() { + var html = ""; + return html += '
    ', html += "
    ", html += '
    ', html += '

     

    ', html += '

    ', html += '
    ', html += "
    ", html += '
    ', html += '
    ', html += '", html += '", html += "
    ", html += "
    " + } + + function setNextVideoText() { + var instance = this, + elem = instance.options.parent, + secondsRemaining = Math.max(Math.round(getTimeRemainingMs(instance) / 1e3), 0); + console.log("up next seconds remaining: " + secondsRemaining); + var timeText = '' + globalize.translate("sharedcomponents#HeaderSecondsValue", secondsRemaining) + "", + nextVideoText = "Episode" === instance.itemType ? globalize.translate("sharedcomponents#HeaderNextEpisodePlayingInValue", timeText) : globalize.translate("sharedcomponents#HeaderNextVideoPlayingInValue", timeText); + elem.querySelector(".upNextDialog-nextVideoText").innerHTML = nextVideoText + } + + function fillItem(item) { + var instance = this, + elem = instance.options.parent; + setPoster(elem.querySelector(".upNextDialog-poster"), item), elem.querySelector(".upNextDialog-overview").innerHTML = item.Overview || "", elem.querySelector(".upNextDialog-mediainfo").innerHTML = mediaInfo.getPrimaryMediaInfoHtml(item, {}); + var title = itemHelper.getDisplayName(item); + item.SeriesName && (title = item.SeriesName + " - " + title), elem.querySelector(".upNextDialog-title").innerHTML = title || "", instance.itemType = item.Type, instance.show() + } + + function clearCountdownTextTimeout(instance) { + instance._countdownTextTimeout && (clearInterval(instance._countdownTextTimeout), instance._countdownTextTimeout = null) + } + + function onStartNowClick() { + var options = this.options; + if (options) { + var player = options.player; + this.hide(), playbackManager.nextTrack(player) + } + } + + function init(instance, options) { + options.parent.innerHTML = getHtml(), options.parent.classList.add("hide"), options.parent.classList.add("upNextDialog"), options.parent.classList.add("upNextDialog-hidden"), fillItem.call(instance, options.nextItem), options.parent.querySelector(".btnHide").addEventListener("click", instance.hide.bind(instance)), options.parent.querySelector(".btnStartNow").addEventListener("click", onStartNowClick.bind(instance)) + } + + function clearHideAnimationEventListeners(instance, elem) { + var fn = instance._onHideAnimationComplete; + fn && dom.removeEventListener(elem, transitionEndEventName, fn, { + once: !0 + }) + } + + function onHideAnimationComplete(e) { + var instance = this, + elem = e.target; + elem.classList.add("hide"), clearHideAnimationEventListeners(instance, elem), events.trigger(instance, "hide") + } + + function hideComingUpNext() { + var instance = this; + if (clearCountdownTextTimeout(this), instance.options) { + var elem = instance.options.parent; + if (elem && (clearHideAnimationEventListeners(this, elem), !elem.classList.contains("upNextDialog-hidden"))) { + elem.offsetWidth, elem.classList.add("upNextDialog-hidden"); + var fn = onHideAnimationComplete.bind(instance); + instance._onHideAnimationComplete = fn, dom.addEventListener(elem, transitionEndEventName, fn, { + once: !0 + }) + } + } + } + + function getTimeRemainingMs(instance) { + var options = instance.options; + if (options) { + var runtimeTicks = playbackManager.duration(options.player); + if (runtimeTicks) { + var timeRemainingTicks = runtimeTicks - playbackManager.currentTime(options.player); + return Math.round(timeRemainingTicks / 1e4) + } + } + return 0 + } + + function startComingUpNextHideTimer(instance) { + getTimeRemainingMs(instance) <= 0 || (setNextVideoText.call(instance), clearCountdownTextTimeout(instance), instance._countdownTextTimeout = setInterval(setNextVideoText.bind(instance), 400)) + } + + function UpNextDialog(options) { + this.options = options, init(this, options) + } + var transitionEndEventName = dom.whichTransitionEvent(); + return UpNextDialog.prototype.show = function() { + var elem = this.options.parent; + clearHideAnimationEventListeners(this, elem), elem.classList.remove("hide"), elem.offsetWidth, elem.classList.remove("upNextDialog-hidden"), layoutManager.tv && setTimeout(function() { + focusManager.focus(elem.querySelector(".btnStartNow")) + }, 50), startComingUpNextHideTimer(this) + }, UpNextDialog.prototype.hide = function() { + hideComingUpNext.call(this) + }, UpNextDialog.prototype.destroy = function() { + hideComingUpNext.call(this), this.options = null, this.itemType = null + }, UpNextDialog +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/userdatabuttons/emby-playstatebutton.js b/dashboard-ui/bower_components/emby-webcomponents/userdatabuttons/emby-playstatebutton.js index 6d09939206..d0aa874321 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/userdatabuttons/emby-playstatebutton.js +++ b/dashboard-ui/bower_components/emby-webcomponents/userdatabuttons/emby-playstatebutton.js @@ -1 +1,64 @@ -define(["connectionManager","serverNotifications","events","globalize","emby-button"],function(connectionManager,serverNotifications,events,globalize,EmbyButtonPrototype){"use strict";function addNotificationEvent(instance,name,handler){var localHandler=handler.bind(instance);events.on(serverNotifications,name,localHandler),instance[name]=localHandler}function removeNotificationEvent(instance,name){var handler=instance[name];handler&&(events.off(serverNotifications,name,handler),instance[name]=null)}function onClick(e){var button=this,id=button.getAttribute("data-id"),serverId=button.getAttribute("data-serverid"),apiClient=connectionManager.getApiClient(serverId);button.classList.contains("playstatebutton-played")?(apiClient.markUnplayed(apiClient.getCurrentUserId(),id,new Date),setState(button,!1)):(apiClient.markPlayed(apiClient.getCurrentUserId(),id,new Date),setState(button,!0))}function onUserDataChanged(e,apiClient,userData){var button=this;userData.ItemId===button.getAttribute("data-id")&&setState(button,userData.Played)}function setState(button,played,updateAttribute){var icon=button.iconElement;icon||(button.iconElement=button.querySelector("i"),icon=button.iconElement),played?(button.classList.add("playstatebutton-played"),icon&&(icon.classList.add("playstatebutton-icon-played"),icon.classList.remove("playstatebutton-icon-unplayed"))):(button.classList.remove("playstatebutton-played"),icon&&(icon.classList.remove("playstatebutton-icon-played"),icon.classList.add("playstatebutton-icon-unplayed"))),!1!==updateAttribute&&button.setAttribute("data-played",played)}function setTitle(button,itemType){button.title="AudioBook"!==itemType&&"AudioPodcast"!==itemType?globalize.translate("sharedcomponents#Watched"):globalize.translate("sharedcomponents#Played");var text=button.querySelector(".button-text");text&&(text.innerHTML=button.title)}function clearEvents(button){button.removeEventListener("click",onClick),removeNotificationEvent(button,"UserDataChanged")}function bindEvents(button){clearEvents(button),button.addEventListener("click",onClick),addNotificationEvent(button,"UserDataChanged",onUserDataChanged)}var EmbyPlaystateButtonPrototype=Object.create(EmbyButtonPrototype);EmbyPlaystateButtonPrototype.createdCallback=function(){EmbyButtonPrototype.createdCallback&&EmbyButtonPrototype.createdCallback.call(this)},EmbyPlaystateButtonPrototype.attachedCallback=function(){EmbyButtonPrototype.attachedCallback&&EmbyButtonPrototype.attachedCallback.call(this);var itemId=this.getAttribute("data-id"),serverId=this.getAttribute("data-serverid");itemId&&serverId&&(setState(this,"true"===this.getAttribute("data-played"),!1),bindEvents(this),setTitle(this,this.getAttribute("data-type")))},EmbyPlaystateButtonPrototype.detachedCallback=function(){EmbyButtonPrototype.detachedCallback&&EmbyButtonPrototype.detachedCallback.call(this),clearEvents(this),this.iconElement=null},EmbyPlaystateButtonPrototype.setItem=function(item){if(item){this.setAttribute("data-id",item.Id),this.setAttribute("data-serverid",item.ServerId);setState(this,item.UserData&&item.UserData.Played),bindEvents(this),setTitle(this,item.Type)}else this.removeAttribute("data-id"),this.removeAttribute("data-serverid"),this.removeAttribute("data-played"),clearEvents(this)},document.registerElement("emby-playstatebutton",{prototype:EmbyPlaystateButtonPrototype,extends:"button"})}); \ No newline at end of file +define(["connectionManager", "serverNotifications", "events", "globalize", "emby-button"], function(connectionManager, serverNotifications, events, globalize, EmbyButtonPrototype) { + "use strict"; + + function addNotificationEvent(instance, name, handler) { + var localHandler = handler.bind(instance); + events.on(serverNotifications, name, localHandler), instance[name] = localHandler + } + + function removeNotificationEvent(instance, name) { + var handler = instance[name]; + handler && (events.off(serverNotifications, name, handler), instance[name] = null) + } + + function onClick(e) { + var button = this, + id = button.getAttribute("data-id"), + serverId = button.getAttribute("data-serverid"), + apiClient = connectionManager.getApiClient(serverId); + button.classList.contains("playstatebutton-played") ? (apiClient.markUnplayed(apiClient.getCurrentUserId(), id, new Date), setState(button, !1)) : (apiClient.markPlayed(apiClient.getCurrentUserId(), id, new Date), setState(button, !0)) + } + + function onUserDataChanged(e, apiClient, userData) { + var button = this; + userData.ItemId === button.getAttribute("data-id") && setState(button, userData.Played) + } + + function setState(button, played, updateAttribute) { + var icon = button.iconElement; + icon || (button.iconElement = button.querySelector("i"), icon = button.iconElement), played ? (button.classList.add("playstatebutton-played"), icon && (icon.classList.add("playstatebutton-icon-played"), icon.classList.remove("playstatebutton-icon-unplayed"))) : (button.classList.remove("playstatebutton-played"), icon && (icon.classList.remove("playstatebutton-icon-played"), icon.classList.add("playstatebutton-icon-unplayed"))), !1 !== updateAttribute && button.setAttribute("data-played", played) + } + + function setTitle(button, itemType) { + button.title = "AudioBook" !== itemType && "AudioPodcast" !== itemType ? globalize.translate("sharedcomponents#Watched") : globalize.translate("sharedcomponents#Played"); + var text = button.querySelector(".button-text"); + text && (text.innerHTML = button.title) + } + + function clearEvents(button) { + button.removeEventListener("click", onClick), removeNotificationEvent(button, "UserDataChanged") + } + + function bindEvents(button) { + clearEvents(button), button.addEventListener("click", onClick), addNotificationEvent(button, "UserDataChanged", onUserDataChanged) + } + var EmbyPlaystateButtonPrototype = Object.create(EmbyButtonPrototype); + EmbyPlaystateButtonPrototype.createdCallback = function() { + EmbyButtonPrototype.createdCallback && EmbyButtonPrototype.createdCallback.call(this) + }, EmbyPlaystateButtonPrototype.attachedCallback = function() { + EmbyButtonPrototype.attachedCallback && EmbyButtonPrototype.attachedCallback.call(this); + var itemId = this.getAttribute("data-id"), + serverId = this.getAttribute("data-serverid"); + itemId && serverId && (setState(this, "true" === this.getAttribute("data-played"), !1), bindEvents(this), setTitle(this, this.getAttribute("data-type"))) + }, EmbyPlaystateButtonPrototype.detachedCallback = function() { + EmbyButtonPrototype.detachedCallback && EmbyButtonPrototype.detachedCallback.call(this), clearEvents(this), this.iconElement = null + }, EmbyPlaystateButtonPrototype.setItem = function(item) { + if (item) { + this.setAttribute("data-id", item.Id), this.setAttribute("data-serverid", item.ServerId); + setState(this, item.UserData && item.UserData.Played), bindEvents(this), setTitle(this, item.Type) + } else this.removeAttribute("data-id"), this.removeAttribute("data-serverid"), this.removeAttribute("data-played"), clearEvents(this) + }, document.registerElement("emby-playstatebutton", { + prototype: EmbyPlaystateButtonPrototype, + extends: "button" + }) +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/userdatabuttons/emby-ratingbutton.js b/dashboard-ui/bower_components/emby-webcomponents/userdatabuttons/emby-ratingbutton.js index f4dc1ee821..2363e9a34e 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/userdatabuttons/emby-ratingbutton.js +++ b/dashboard-ui/bower_components/emby-webcomponents/userdatabuttons/emby-ratingbutton.js @@ -1 +1,78 @@ -define(["connectionManager","serverNotifications","events","globalize","emby-button"],function(connectionManager,serverNotifications,events,globalize,EmbyButtonPrototype){"use strict";function addNotificationEvent(instance,name,handler){var localHandler=handler.bind(instance);events.on(serverNotifications,name,localHandler),instance[name]=localHandler}function removeNotificationEvent(instance,name){var handler=instance[name];handler&&(events.off(serverNotifications,name,handler),instance[name]=null)}function showPicker(button,apiClient,itemId,likes,isFavorite){return apiClient.updateFavoriteStatus(apiClient.getCurrentUserId(),itemId,!isFavorite)}function onClick(e){var button=this,id=button.getAttribute("data-id"),serverId=button.getAttribute("data-serverid"),apiClient=connectionManager.getApiClient(serverId),likes=this.getAttribute("data-likes"),isFavorite="true"===this.getAttribute("data-isfavorite");likes="true"===likes||"false"!==likes&&null,showPicker(button,apiClient,id,likes,isFavorite).then(function(userData){setState(button,userData.Likes,userData.IsFavorite)})}function onUserDataChanged(e,apiClient,userData){var button=this;userData.ItemId===button.getAttribute("data-id")&&setState(button,userData.Likes,userData.IsFavorite)}function setState(button,likes,isFavorite,updateAttribute){var icon=button.querySelector("i");isFavorite?(icon&&(icon.innerHTML="",icon.classList.add("ratingbutton-icon-withrating")),button.classList.add("ratingbutton-withrating")):(icon&&(icon.innerHTML="",icon.classList.remove("ratingbutton-icon-withrating")),button.classList.remove("ratingbutton-withrating")),!1!==updateAttribute&&(button.setAttribute("data-isfavorite",isFavorite),button.setAttribute("data-likes",null===likes?"":likes))}function setTitle(button){button.title=globalize.translate("sharedcomponents#Favorite");var text=button.querySelector(".button-text");text&&(text.innerHTML=button.title)}function clearEvents(button){button.removeEventListener("click",onClick),removeNotificationEvent(button,"UserDataChanged")}function bindEvents(button){clearEvents(button),button.addEventListener("click",onClick),addNotificationEvent(button,"UserDataChanged",onUserDataChanged)}var EmbyRatingButtonPrototype=Object.create(EmbyButtonPrototype);EmbyRatingButtonPrototype.createdCallback=function(){EmbyButtonPrototype.createdCallback&&EmbyButtonPrototype.createdCallback.call(this)},EmbyRatingButtonPrototype.attachedCallback=function(){EmbyButtonPrototype.attachedCallback&&EmbyButtonPrototype.attachedCallback.call(this);var itemId=this.getAttribute("data-id"),serverId=this.getAttribute("data-serverid");if(itemId&&serverId){var likes=this.getAttribute("data-likes"),isFavorite="true"===this.getAttribute("data-isfavorite");likes="true"===likes||"false"!==likes&&null,setState(this,likes,isFavorite,!1),bindEvents(this)}setTitle(this)},EmbyRatingButtonPrototype.detachedCallback=function(){EmbyButtonPrototype.detachedCallback&&EmbyButtonPrototype.detachedCallback.call(this),clearEvents(this)},EmbyRatingButtonPrototype.setItem=function(item){if(item){this.setAttribute("data-id",item.Id),this.setAttribute("data-serverid",item.ServerId);var userData=item.UserData||{};setState(this,userData.Likes,userData.IsFavorite),bindEvents(this)}else this.removeAttribute("data-id"),this.removeAttribute("data-serverid"),this.removeAttribute("data-likes"),this.removeAttribute("data-isfavorite"),clearEvents(this)},document.registerElement("emby-ratingbutton",{prototype:EmbyRatingButtonPrototype,extends:"button"})}); \ No newline at end of file +define(["connectionManager", "serverNotifications", "events", "globalize", "emby-button"], function(connectionManager, serverNotifications, events, globalize, EmbyButtonPrototype) { + "use strict"; + + function addNotificationEvent(instance, name, handler) { + var localHandler = handler.bind(instance); + events.on(serverNotifications, name, localHandler), instance[name] = localHandler + } + + function removeNotificationEvent(instance, name) { + var handler = instance[name]; + handler && (events.off(serverNotifications, name, handler), instance[name] = null) + } + + function showPicker(button, apiClient, itemId, likes, isFavorite) { + return apiClient.updateFavoriteStatus(apiClient.getCurrentUserId(), itemId, !isFavorite) + } + + function onClick(e) { + var button = this, + id = button.getAttribute("data-id"), + serverId = button.getAttribute("data-serverid"), + apiClient = connectionManager.getApiClient(serverId), + likes = this.getAttribute("data-likes"), + isFavorite = "true" === this.getAttribute("data-isfavorite"); + likes = "true" === likes || "false" !== likes && null, showPicker(button, apiClient, id, likes, isFavorite).then(function(userData) { + setState(button, userData.Likes, userData.IsFavorite) + }) + } + + function onUserDataChanged(e, apiClient, userData) { + var button = this; + userData.ItemId === button.getAttribute("data-id") && setState(button, userData.Likes, userData.IsFavorite) + } + + function setState(button, likes, isFavorite, updateAttribute) { + var icon = button.querySelector("i"); + isFavorite ? (icon && (icon.innerHTML = "", icon.classList.add("ratingbutton-icon-withrating")), button.classList.add("ratingbutton-withrating")) : (icon && (icon.innerHTML = "", icon.classList.remove("ratingbutton-icon-withrating")), button.classList.remove("ratingbutton-withrating")), !1 !== updateAttribute && (button.setAttribute("data-isfavorite", isFavorite), button.setAttribute("data-likes", null === likes ? "" : likes)) + } + + function setTitle(button) { + button.title = globalize.translate("sharedcomponents#Favorite"); + var text = button.querySelector(".button-text"); + text && (text.innerHTML = button.title) + } + + function clearEvents(button) { + button.removeEventListener("click", onClick), removeNotificationEvent(button, "UserDataChanged") + } + + function bindEvents(button) { + clearEvents(button), button.addEventListener("click", onClick), addNotificationEvent(button, "UserDataChanged", onUserDataChanged) + } + var EmbyRatingButtonPrototype = Object.create(EmbyButtonPrototype); + EmbyRatingButtonPrototype.createdCallback = function() { + EmbyButtonPrototype.createdCallback && EmbyButtonPrototype.createdCallback.call(this) + }, EmbyRatingButtonPrototype.attachedCallback = function() { + EmbyButtonPrototype.attachedCallback && EmbyButtonPrototype.attachedCallback.call(this); + var itemId = this.getAttribute("data-id"), + serverId = this.getAttribute("data-serverid"); + if (itemId && serverId) { + var likes = this.getAttribute("data-likes"), + isFavorite = "true" === this.getAttribute("data-isfavorite"); + likes = "true" === likes || "false" !== likes && null, setState(this, likes, isFavorite, !1), bindEvents(this) + } + setTitle(this) + }, EmbyRatingButtonPrototype.detachedCallback = function() { + EmbyButtonPrototype.detachedCallback && EmbyButtonPrototype.detachedCallback.call(this), clearEvents(this) + }, EmbyRatingButtonPrototype.setItem = function(item) { + if (item) { + this.setAttribute("data-id", item.Id), this.setAttribute("data-serverid", item.ServerId); + var userData = item.UserData || {}; + setState(this, userData.Likes, userData.IsFavorite), bindEvents(this) + } else this.removeAttribute("data-id"), this.removeAttribute("data-serverid"), this.removeAttribute("data-likes"), this.removeAttribute("data-isfavorite"), clearEvents(this) + }, document.registerElement("emby-ratingbutton", { + prototype: EmbyRatingButtonPrototype, + extends: "button" + }) +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/userdatabuttons/userdatabuttons.js b/dashboard-ui/bower_components/emby-webcomponents/userdatabuttons/userdatabuttons.js index 76aa83d176..b1b5631468 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/userdatabuttons/userdatabuttons.js +++ b/dashboard-ui/bower_components/emby-webcomponents/userdatabuttons/userdatabuttons.js @@ -1 +1,110 @@ -define(["connectionManager","globalize","dom","itemHelper","paper-icon-button-light","material-icons","emby-button","css!./userdatabuttons"],function(connectionManager,globalize,dom,itemHelper){"use strict";function getUserDataButtonHtml(method,itemId,serverId,buttonCssClass,iconCssClass,icon,tooltip,style){"fab-mini"===style&&(style="fab",buttonCssClass=buttonCssClass?buttonCssClass+" mini":"mini");var is="fab"===style?"emby-button":"paper-icon-button-light",className="fab"===style?"autoSize fab":"autoSize";return buttonCssClass&&(className+=" "+buttonCssClass),iconCssClass?iconCssClass+=" ":iconCssClass="",iconCssClass+="md-icon",'"}function onContainerClick(e){var btnUserData=dom.parentWithClass(e.target,"btnUserData");if(btnUserData){var method=btnUserData.getAttribute("data-method");userDataMethods[method](btnUserData)}}function fill(options){var html=getIconsHtml(options);"insertAdjacent"===options.fillMode?options.element.insertAdjacentHTML(options.insertLocation||"beforeend",html):options.element.innerHTML=html,dom.removeEventListener(options.element,"click",onContainerClick,{passive:!0}),dom.addEventListener(options.element,"click",onContainerClick,{passive:!0})}function destroy(options){options.element.innerHTML="",dom.removeEventListener(options.element,"click",onContainerClick,{passive:!0})}function getIconsHtml(options){var item=options.item,includePlayed=options.includePlayed,cssClass=options.cssClass,style=options.style,html="",userData=item.UserData||{},itemId=item.Id;if(itemHelper.isLocalItem(item))return html;var btnCssClass="btnUserData";cssClass&&(btnCssClass+=" "+cssClass);var iconCssClass=options.iconCssClass,serverId=item.ServerId;if(!1!==includePlayed){var tooltipPlayed=globalize.translate("sharedcomponents#MarkPlayed");itemHelper.canMarkPlayed(item)&&(html+=userData.Played?getUserDataButtonHtml("markPlayed",itemId,serverId,btnCssClass+" btnUserDataOn",iconCssClass,"",tooltipPlayed,style):getUserDataButtonHtml("markPlayed",itemId,serverId,btnCssClass,iconCssClass,"",tooltipPlayed,style))}var tooltipFavorite=globalize.translate("sharedcomponents#Favorite");return html+=userData.IsFavorite?getUserDataButtonHtml("markFavorite",itemId,serverId,btnCssClass+" btnUserData btnUserDataOn",iconCssClass,"",tooltipFavorite,style):getUserDataButtonHtml("markFavorite",itemId,serverId,btnCssClass+" btnUserData",iconCssClass,"",tooltipFavorite,style)}function markFavorite(link){var id=link.getAttribute("data-itemid"),serverId=link.getAttribute("data-serverid"),markAsFavorite=!link.classList.contains("btnUserDataOn");favorite(id,serverId,markAsFavorite),markAsFavorite?link.classList.add("btnUserDataOn"):link.classList.remove("btnUserDataOn")}function markLike(link){var id=link.getAttribute("data-itemid"),serverId=link.getAttribute("data-serverid");link.classList.contains("btnUserDataOn")?(clearLike(id,serverId),link.classList.remove("btnUserDataOn")):(likes(id,serverId,!0),link.classList.add("btnUserDataOn")),link.parentNode.querySelector(".btnDislike").classList.remove("btnUserDataOn")}function markDislike(link){var id=link.getAttribute("data-itemid"),serverId=link.getAttribute("data-serverid");link.classList.contains("btnUserDataOn")?(clearLike(id,serverId),link.classList.remove("btnUserDataOn")):(likes(id,serverId,!1),link.classList.add("btnUserDataOn")),link.parentNode.querySelector(".btnLike").classList.remove("btnUserDataOn")}function markPlayed(link){var id=link.getAttribute("data-itemid"),serverId=link.getAttribute("data-serverid");link.classList.contains("btnUserDataOn")?(played(id,serverId,!1),link.classList.remove("btnUserDataOn")):(played(id,serverId,!0),link.classList.add("btnUserDataOn"))}function likes(id,serverId,isLiked){var apiClient=connectionManager.getApiClient(serverId);return apiClient.updateUserItemRating(apiClient.getCurrentUserId(),id,isLiked)}function played(id,serverId,isPlayed){var apiClient=connectionManager.getApiClient(serverId);return apiClient[isPlayed?"markPlayed":"markUnplayed"](apiClient.getCurrentUserId(),id,new Date)}function favorite(id,serverId,isFavorite){var apiClient=connectionManager.getApiClient(serverId);return apiClient.updateFavoriteStatus(apiClient.getCurrentUserId(),id,isFavorite)}function clearLike(id,serverId){var apiClient=connectionManager.getApiClient(serverId);return apiClient.clearUserItemRating(apiClient.getCurrentUserId(),id)}var userDataMethods={markPlayed:markPlayed,markDislike:markDislike,markLike:markLike,markFavorite:markFavorite};return{fill:fill,destroy:destroy,getIconsHtml:getIconsHtml}}); \ No newline at end of file +define(["connectionManager", "globalize", "dom", "itemHelper", "paper-icon-button-light", "material-icons", "emby-button", "css!./userdatabuttons"], function(connectionManager, globalize, dom, itemHelper) { + "use strict"; + + function getUserDataButtonHtml(method, itemId, serverId, buttonCssClass, iconCssClass, icon, tooltip, style) { + "fab-mini" === style && (style = "fab", buttonCssClass = buttonCssClass ? buttonCssClass + " mini" : "mini"); + var is = "fab" === style ? "emby-button" : "paper-icon-button-light", + className = "fab" === style ? "autoSize fab" : "autoSize"; + return buttonCssClass && (className += " " + buttonCssClass), iconCssClass ? iconCssClass += " " : iconCssClass = "", iconCssClass += "md-icon", '" + } + + function onContainerClick(e) { + var btnUserData = dom.parentWithClass(e.target, "btnUserData"); + if (btnUserData) { + var method = btnUserData.getAttribute("data-method"); + userDataMethods[method](btnUserData) + } + } + + function fill(options) { + var html = getIconsHtml(options); + "insertAdjacent" === options.fillMode ? options.element.insertAdjacentHTML(options.insertLocation || "beforeend", html) : options.element.innerHTML = html, dom.removeEventListener(options.element, "click", onContainerClick, { + passive: !0 + }), dom.addEventListener(options.element, "click", onContainerClick, { + passive: !0 + }) + } + + function destroy(options) { + options.element.innerHTML = "", dom.removeEventListener(options.element, "click", onContainerClick, { + passive: !0 + }) + } + + function getIconsHtml(options) { + var item = options.item, + includePlayed = options.includePlayed, + cssClass = options.cssClass, + style = options.style, + html = "", + userData = item.UserData || {}, + itemId = item.Id; + if (itemHelper.isLocalItem(item)) return html; + var btnCssClass = "btnUserData"; + cssClass && (btnCssClass += " " + cssClass); + var iconCssClass = options.iconCssClass, + serverId = item.ServerId; + if (!1 !== includePlayed) { + var tooltipPlayed = globalize.translate("sharedcomponents#MarkPlayed"); + itemHelper.canMarkPlayed(item) && (html += userData.Played ? getUserDataButtonHtml("markPlayed", itemId, serverId, btnCssClass + " btnUserDataOn", iconCssClass, "", tooltipPlayed, style) : getUserDataButtonHtml("markPlayed", itemId, serverId, btnCssClass, iconCssClass, "", tooltipPlayed, style)) + } + var tooltipFavorite = globalize.translate("sharedcomponents#Favorite"); + return html += userData.IsFavorite ? getUserDataButtonHtml("markFavorite", itemId, serverId, btnCssClass + " btnUserData btnUserDataOn", iconCssClass, "", tooltipFavorite, style) : getUserDataButtonHtml("markFavorite", itemId, serverId, btnCssClass + " btnUserData", iconCssClass, "", tooltipFavorite, style) + } + + function markFavorite(link) { + var id = link.getAttribute("data-itemid"), + serverId = link.getAttribute("data-serverid"), + markAsFavorite = !link.classList.contains("btnUserDataOn"); + favorite(id, serverId, markAsFavorite), markAsFavorite ? link.classList.add("btnUserDataOn") : link.classList.remove("btnUserDataOn") + } + + function markLike(link) { + var id = link.getAttribute("data-itemid"), + serverId = link.getAttribute("data-serverid"); + link.classList.contains("btnUserDataOn") ? (clearLike(id, serverId), link.classList.remove("btnUserDataOn")) : (likes(id, serverId, !0), link.classList.add("btnUserDataOn")), link.parentNode.querySelector(".btnDislike").classList.remove("btnUserDataOn") + } + + function markDislike(link) { + var id = link.getAttribute("data-itemid"), + serverId = link.getAttribute("data-serverid"); + link.classList.contains("btnUserDataOn") ? (clearLike(id, serverId), link.classList.remove("btnUserDataOn")) : (likes(id, serverId, !1), link.classList.add("btnUserDataOn")), link.parentNode.querySelector(".btnLike").classList.remove("btnUserDataOn") + } + + function markPlayed(link) { + var id = link.getAttribute("data-itemid"), + serverId = link.getAttribute("data-serverid"); + link.classList.contains("btnUserDataOn") ? (played(id, serverId, !1), link.classList.remove("btnUserDataOn")) : (played(id, serverId, !0), link.classList.add("btnUserDataOn")) + } + + function likes(id, serverId, isLiked) { + var apiClient = connectionManager.getApiClient(serverId); + return apiClient.updateUserItemRating(apiClient.getCurrentUserId(), id, isLiked) + } + + function played(id, serverId, isPlayed) { + var apiClient = connectionManager.getApiClient(serverId); + return apiClient[isPlayed ? "markPlayed" : "markUnplayed"](apiClient.getCurrentUserId(), id, new Date) + } + + function favorite(id, serverId, isFavorite) { + var apiClient = connectionManager.getApiClient(serverId); + return apiClient.updateFavoriteStatus(apiClient.getCurrentUserId(), id, isFavorite) + } + + function clearLike(id, serverId) { + var apiClient = connectionManager.getApiClient(serverId); + return apiClient.clearUserItemRating(apiClient.getCurrentUserId(), id) + } + var userDataMethods = { + markPlayed: markPlayed, + markDislike: markDislike, + markLike: markLike, + markFavorite: markFavorite + }; + return { + fill: fill, + destroy: destroy, + getIconsHtml: getIconsHtml + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/usersettings/usersettings.js b/dashboard-ui/bower_components/emby-webcomponents/usersettings/usersettings.js index b14def8d65..0712e46299 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/usersettings/usersettings.js +++ b/dashboard-ui/bower_components/emby-webcomponents/usersettings/usersettings.js @@ -1 +1,4 @@ -define(["userSettingsBuilder"],function(userSettingsBuilder){"use strict";return new userSettingsBuilder}); \ No newline at end of file +define(["userSettingsBuilder"], function(userSettingsBuilder) { + "use strict"; + return new userSettingsBuilder +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/usersettings/usersettingsbuilder.js b/dashboard-ui/bower_components/emby-webcomponents/usersettings/usersettingsbuilder.js index a07cc82b3e..568b1fcaa6 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/usersettings/usersettingsbuilder.js +++ b/dashboard-ui/bower_components/emby-webcomponents/usersettings/usersettingsbuilder.js @@ -1 +1,86 @@ -define(["appSettings","events"],function(appsettings,events){"use strict";function onSaveTimeout(){var self=this;self.saveTimeout=null,self.currentApiClient.updateDisplayPreferences("usersettings",self.displayPrefs,self.currentUserId,"emby")}function saveServerPreferences(instance){instance.saveTimeout&&clearTimeout(instance.saveTimeout),instance.saveTimeout=setTimeout(onSaveTimeout.bind(instance),50)}function UserSettings(){}return UserSettings.prototype.setUserInfo=function(userId,apiClient){if(this.saveTimeout&&clearTimeout(this.saveTimeout),this.currentUserId=userId,this.currentApiClient=apiClient,!userId)return this.displayPrefs=null,Promise.resolve();var self=this;return apiClient.getDisplayPreferences("usersettings",userId,"emby").then(function(result){result.CustomPrefs=result.CustomPrefs||{},self.displayPrefs=result})},UserSettings.prototype.getData=function(){return this.displayPrefs},UserSettings.prototype.importFrom=function(instance){this.displayPrefs=instance.getData()},UserSettings.prototype.set=function(name,value,enableOnServer){var userId=this.currentUserId;if(!userId)throw new Error("userId cannot be null");var currentValue=this.get(name,enableOnServer),result=appsettings.set(name,value,userId);return!1!==enableOnServer&&this.displayPrefs&&(this.displayPrefs.CustomPrefs[name]=null==value?value:value.toString(),saveServerPreferences(this)),currentValue!==value&&events.trigger(this,"change",[name]),result},UserSettings.prototype.get=function(name,enableOnServer){var userId=this.currentUserId;return userId?!1!==enableOnServer&&this.displayPrefs?this.displayPrefs.CustomPrefs[name]:appsettings.get(name,userId):null},UserSettings.prototype.serverConfig=function(config){var apiClient=this.currentApiClient;return config?apiClient.updateUserConfiguration(this.currentUserId,config):apiClient.getUser(this.currentUserId).then(function(user){return user.Configuration})},UserSettings.prototype.enableCinemaMode=function(val){return null!=val?this.set("enableCinemaMode",val.toString(),!1):!(val=this.get("enableCinemaMode",!1))||"false"!==val},UserSettings.prototype.enableNextVideoInfoOverlay=function(val){return null!=val?this.set("enableNextVideoInfoOverlay",val.toString()):"false"!==(val=this.get("enableNextVideoInfoOverlay"))},UserSettings.prototype.enableThemeSongs=function(val){return null!=val?this.set("enableThemeSongs",val.toString(),!1):"false"!==(val=this.get("enableThemeSongs",!1))},UserSettings.prototype.enableThemeVideos=function(val){return null!=val?this.set("enableThemeVideos",val.toString(),!1):(val=this.get("enableThemeVideos",!1),val?"false"!==val:UserSettings.defaults.enableThemeVideos)},UserSettings.prototype.enableBackdrops=function(val){return null!=val?this.set("enableBackdrops",val.toString(),!1):(val=this.get("enableBackdrops",!1),val?"false"!==val:UserSettings.defaults.enableBackdrops)},UserSettings.prototype.language=function(val){return null!=val?this.set("language",val.toString(),!1):this.get("language",!1)},UserSettings.prototype.dateTimeLocale=function(val){return null!=val?this.set("datetimelocale",val.toString(),!1):this.get("datetimelocale",!1)},UserSettings.prototype.skipBackLength=function(val){return null!=val?this.set("skipBackLength",val.toString()):parseInt(this.get("skipBackLength")||"10000")},UserSettings.prototype.skipForwardLength=function(val){return null!=val?this.set("skipForwardLength",val.toString()):parseInt(this.get("skipForwardLength")||"30000")},UserSettings.prototype.dashboardTheme=function(val){return null!=val?this.set("dashboardTheme",val):this.get("dashboardTheme")},UserSettings.prototype.skin=function(val){return null!=val?this.set("skin",val,!1):this.get("skin",!1)||UserSettings.defaults.skin},UserSettings.prototype.theme=function(val){return null!=val?this.set("appTheme",val,!1):this.get("appTheme",!1)||UserSettings.defaults.theme},UserSettings.prototype.enableSeasonalThemes=function(val){return null!=val?this.set("enableSeasonalThemes",val,!1):"false"!==this.get("enableSeasonalThemes",!1)},UserSettings.prototype.screensaver=function(val){return null!=val?this.set("screensaver",val,!1):this.get("screensaver",!1)||UserSettings.defaults.screensaver},UserSettings.prototype.soundEffects=function(val){return null!=val?this.set("soundeffects",val,!1):this.get("soundeffects",!1)||UserSettings.defaults.soundEffects},UserSettings.defaults={theme:null,enableThemeVideos:!0},UserSettings.prototype.loadQuerySettings=function(key,query){var values=this.get(key);return values?(values=JSON.parse(values),Object.assign(query,values)):query},UserSettings.prototype.saveQuerySettings=function(key,query){var values={};return query.SortBy&&(values.SortBy=query.SortBy),query.SortOrder&&(values.SortOrder=query.SortOrder),this.set(key,JSON.stringify(values))},UserSettings.prototype.getSubtitleAppearanceSettings=function(key){return key=key||"localplayersubtitleappearance3",JSON.parse(this.get(key,!1)||"{}")},UserSettings.prototype.setSubtitleAppearanceSettings=function(value,key){return key=key||"localplayersubtitleappearance3",this.set(key,JSON.stringify(value),!1)},UserSettings.prototype.setFilter=function(key,value){return this.set(key,value,!0)},UserSettings.prototype.getFilter=function(key){return this.get(key,!0)},UserSettings}); \ No newline at end of file +define(["appSettings", "events"], function(appsettings, events) { + "use strict"; + + function onSaveTimeout() { + var self = this; + self.saveTimeout = null, self.currentApiClient.updateDisplayPreferences("usersettings", self.displayPrefs, self.currentUserId, "emby") + } + + function saveServerPreferences(instance) { + instance.saveTimeout && clearTimeout(instance.saveTimeout), instance.saveTimeout = setTimeout(onSaveTimeout.bind(instance), 50) + } + + function UserSettings() {} + return UserSettings.prototype.setUserInfo = function(userId, apiClient) { + if (this.saveTimeout && clearTimeout(this.saveTimeout), this.currentUserId = userId, this.currentApiClient = apiClient, !userId) return this.displayPrefs = null, Promise.resolve(); + var self = this; + return apiClient.getDisplayPreferences("usersettings", userId, "emby").then(function(result) { + result.CustomPrefs = result.CustomPrefs || {}, self.displayPrefs = result + }) + }, UserSettings.prototype.getData = function() { + return this.displayPrefs + }, UserSettings.prototype.importFrom = function(instance) { + this.displayPrefs = instance.getData() + }, UserSettings.prototype.set = function(name, value, enableOnServer) { + var userId = this.currentUserId; + if (!userId) throw new Error("userId cannot be null"); + var currentValue = this.get(name, enableOnServer), + result = appsettings.set(name, value, userId); + return !1 !== enableOnServer && this.displayPrefs && (this.displayPrefs.CustomPrefs[name] = null == value ? value : value.toString(), saveServerPreferences(this)), currentValue !== value && events.trigger(this, "change", [name]), result + }, UserSettings.prototype.get = function(name, enableOnServer) { + var userId = this.currentUserId; + return userId ? !1 !== enableOnServer && this.displayPrefs ? this.displayPrefs.CustomPrefs[name] : appsettings.get(name, userId) : null + }, UserSettings.prototype.serverConfig = function(config) { + var apiClient = this.currentApiClient; + return config ? apiClient.updateUserConfiguration(this.currentUserId, config) : apiClient.getUser(this.currentUserId).then(function(user) { + return user.Configuration + }) + }, UserSettings.prototype.enableCinemaMode = function(val) { + return null != val ? this.set("enableCinemaMode", val.toString(), !1) : !(val = this.get("enableCinemaMode", !1)) || "false" !== val + }, UserSettings.prototype.enableNextVideoInfoOverlay = function(val) { + return null != val ? this.set("enableNextVideoInfoOverlay", val.toString()) : "false" !== (val = this.get("enableNextVideoInfoOverlay")) + }, UserSettings.prototype.enableThemeSongs = function(val) { + return null != val ? this.set("enableThemeSongs", val.toString(), !1) : "false" !== (val = this.get("enableThemeSongs", !1)) + }, UserSettings.prototype.enableThemeVideos = function(val) { + return null != val ? this.set("enableThemeVideos", val.toString(), !1) : (val = this.get("enableThemeVideos", !1), val ? "false" !== val : UserSettings.defaults.enableThemeVideos) + }, UserSettings.prototype.enableBackdrops = function(val) { + return null != val ? this.set("enableBackdrops", val.toString(), !1) : (val = this.get("enableBackdrops", !1), val ? "false" !== val : UserSettings.defaults.enableBackdrops) + }, UserSettings.prototype.language = function(val) { + return null != val ? this.set("language", val.toString(), !1) : this.get("language", !1) + }, UserSettings.prototype.dateTimeLocale = function(val) { + return null != val ? this.set("datetimelocale", val.toString(), !1) : this.get("datetimelocale", !1) + }, UserSettings.prototype.skipBackLength = function(val) { + return null != val ? this.set("skipBackLength", val.toString()) : parseInt(this.get("skipBackLength") || "10000") + }, UserSettings.prototype.skipForwardLength = function(val) { + return null != val ? this.set("skipForwardLength", val.toString()) : parseInt(this.get("skipForwardLength") || "30000") + }, UserSettings.prototype.dashboardTheme = function(val) { + return null != val ? this.set("dashboardTheme", val) : this.get("dashboardTheme") + }, UserSettings.prototype.skin = function(val) { + return null != val ? this.set("skin", val, !1) : this.get("skin", !1) || UserSettings.defaults.skin + }, UserSettings.prototype.theme = function(val) { + return null != val ? this.set("appTheme", val, !1) : this.get("appTheme", !1) || UserSettings.defaults.theme + }, UserSettings.prototype.enableSeasonalThemes = function(val) { + return null != val ? this.set("enableSeasonalThemes", val, !1) : "false" !== this.get("enableSeasonalThemes", !1) + }, UserSettings.prototype.screensaver = function(val) { + return null != val ? this.set("screensaver", val, !1) : this.get("screensaver", !1) || UserSettings.defaults.screensaver + }, UserSettings.prototype.soundEffects = function(val) { + return null != val ? this.set("soundeffects", val, !1) : this.get("soundeffects", !1) || UserSettings.defaults.soundEffects + }, UserSettings.defaults = { + theme: null, + enableThemeVideos: !0 + }, UserSettings.prototype.loadQuerySettings = function(key, query) { + var values = this.get(key); + return values ? (values = JSON.parse(values), Object.assign(query, values)) : query + }, UserSettings.prototype.saveQuerySettings = function(key, query) { + var values = {}; + return query.SortBy && (values.SortBy = query.SortBy), query.SortOrder && (values.SortOrder = query.SortOrder), this.set(key, JSON.stringify(values)) + }, UserSettings.prototype.getSubtitleAppearanceSettings = function(key) { + return key = key || "localplayersubtitleappearance3", JSON.parse(this.get(key, !1) || "{}") + }, UserSettings.prototype.setSubtitleAppearanceSettings = function(value, key) { + return key = key || "localplayersubtitleappearance3", this.set(key, JSON.stringify(value), !1) + }, UserSettings.prototype.setFilter = function(key, value) { + return this.set(key, value, !0) + }, UserSettings.prototype.getFilter = function(key) { + return this.get(key, !0) + }, UserSettings +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/viewmanager/viewcontainer-lite.js b/dashboard-ui/bower_components/emby-webcomponents/viewmanager/viewcontainer-lite.js index fc20b90078..0e3f492d15 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/viewmanager/viewcontainer-lite.js +++ b/dashboard-ui/bower_components/emby-webcomponents/viewmanager/viewcontainer-lite.js @@ -1 +1,148 @@ -define(["browser","dom","layoutManager","css!./viewcontainer-lite"],function(browser,dom,layoutManager){"use strict";function enableAnimation(){return!browser.tv&&browser.supportsCssAnimation()}function findLastView(parent,className){for(var nodes=parent.childNodes,i=nodes.length-1;i>=0;i--){var node=nodes[i],classList=node.classList;if(classList&&classList.contains(className))return node}}function findViewBefore(elem,className){for(var node=elem.previousSibling;node;){var classList=node.classList;if(classList&&classList.contains(className))return node;node=node.previousSibling}}function loadView(options){if(!options.cancel){cancelActiveAnimations();var selected=selectedPageIndex,previousAnimatable=-1===selected?null:allPages[selected],pageIndex=selected+1;pageIndex>=pageContainerCount&&(pageIndex=0);var viewHtml=options.view,properties=[];options.fullscreen&&properties.push("fullscreen");var view,currentPage=allPages[pageIndex];return currentPage?(triggerDestroy(currentPage),currentPage.insertAdjacentHTML("beforebegin",viewHtml),view=findViewBefore(currentPage,"view"),mainAnimatedPages.removeChild(currentPage)):(mainAnimatedPages.insertAdjacentHTML("beforeend",viewHtml),view=findLastView(mainAnimatedPages,"view")),view.classList.add("mainAnimatedPage"),properties.length&&view.setAttribute("data-properties",properties.join(",")),options.type&&view.setAttribute("data-type",options.type),allPages[pageIndex]=view,onBeforeChange&&onBeforeChange(view,!1,options),beforeAnimate(allPages,pageIndex,selected),animate(view,previousAnimatable,options.transition,options.isBack).then(function(){return selectedPageIndex=pageIndex,currentUrls[pageIndex]=options.url,!options.cancel&&previousAnimatable&&afterAnimate(allPages,pageIndex),view})}}function beforeAnimate(allPages,newPageIndex,oldPageIndex){for(var i=0,length=allPages.length;i= 0; i--) { + var node = nodes[i], + classList = node.classList; + if (classList && classList.contains(className)) return node + } + } + + function findViewBefore(elem, className) { + for (var node = elem.previousSibling; node;) { + var classList = node.classList; + if (classList && classList.contains(className)) return node; + node = node.previousSibling + } + } + + function loadView(options) { + if (!options.cancel) { + cancelActiveAnimations(); + var selected = selectedPageIndex, + previousAnimatable = -1 === selected ? null : allPages[selected], + pageIndex = selected + 1; + pageIndex >= pageContainerCount && (pageIndex = 0); + var viewHtml = options.view, + properties = []; + options.fullscreen && properties.push("fullscreen"); + var view, currentPage = allPages[pageIndex]; + return currentPage ? (triggerDestroy(currentPage), currentPage.insertAdjacentHTML("beforebegin", viewHtml), view = findViewBefore(currentPage, "view"), mainAnimatedPages.removeChild(currentPage)) : (mainAnimatedPages.insertAdjacentHTML("beforeend", viewHtml), view = findLastView(mainAnimatedPages, "view")), view.classList.add("mainAnimatedPage"), properties.length && view.setAttribute("data-properties", properties.join(",")), options.type && view.setAttribute("data-type", options.type), allPages[pageIndex] = view, onBeforeChange && onBeforeChange(view, !1, options), beforeAnimate(allPages, pageIndex, selected), animate(view, previousAnimatable, options.transition, options.isBack).then(function() { + return selectedPageIndex = pageIndex, currentUrls[pageIndex] = options.url, !options.cancel && previousAnimatable && afterAnimate(allPages, pageIndex), view + }) + } + } + + function beforeAnimate(allPages, newPageIndex, oldPageIndex) { + for (var i = 0, length = allPages.length; i < length; i++) newPageIndex === i || oldPageIndex === i || allPages[i].classList.add("hide") + } + + function afterAnimate(allPages, newPageIndex) { + for (var i = 0, length = allPages.length; i < length; i++) newPageIndex === i || allPages[i].classList.add("hide") + } + + function animate(newAnimatedPage, oldAnimatedPage, transition, isBack) { + if (enableAnimation() && oldAnimatedPage) { + if ("slide" === transition) return slide(newAnimatedPage, oldAnimatedPage, transition, isBack); + if ("fade" === transition) return fade(newAnimatedPage, oldAnimatedPage, transition, isBack); + clearAnimation(newAnimatedPage), oldAnimatedPage && clearAnimation(oldAnimatedPage) + } + return Promise.resolve() + } + + function clearAnimation(elem) { + setAnimation(elem, "none") + } + + function slide(newAnimatedPage, oldAnimatedPage, transition, isBack) { + return new Promise(function(resolve, reject) { + var duration = layoutManager.tv ? 450 : 160, + animations = []; + oldAnimatedPage && (isBack ? setAnimation(oldAnimatedPage, "view-slideright-r " + duration + "ms ease-out normal both") : setAnimation(oldAnimatedPage, "view-slideleft-r " + duration + "ms ease-out normal both"), animations.push(oldAnimatedPage)), isBack ? setAnimation(newAnimatedPage, "view-slideright " + duration + "ms ease-out normal both") : setAnimation(newAnimatedPage, "view-slideleft " + duration + "ms ease-out normal both"), animations.push(newAnimatedPage), currentAnimations = animations; + var onAnimationComplete = function() { + dom.removeEventListener(newAnimatedPage, dom.whichAnimationEvent(), onAnimationComplete, { + once: !0 + }), resolve() + }; + dom.addEventListener(newAnimatedPage, dom.whichAnimationEvent(), onAnimationComplete, { + once: !0 + }) + }) + } + + function fade(newAnimatedPage, oldAnimatedPage, transition, isBack) { + return new Promise(function(resolve, reject) { + var duration = layoutManager.tv ? 450 : 270, + animations = []; + newAnimatedPage.style.opacity = 0, setAnimation(newAnimatedPage, "view-fadein " + duration + "ms ease-in normal both"), animations.push(newAnimatedPage), oldAnimatedPage && (setAnimation(oldAnimatedPage, "view-fadeout " + duration + "ms ease-out normal both"), animations.push(oldAnimatedPage)), currentAnimations = animations; + var onAnimationComplete = function() { + dom.removeEventListener(newAnimatedPage, dom.whichAnimationEvent(), onAnimationComplete, { + once: !0 + }), resolve() + }; + dom.addEventListener(newAnimatedPage, dom.whichAnimationEvent(), onAnimationComplete, { + once: !0 + }) + }) + } + + function setAnimation(elem, value) { + requestAnimationFrame(function() { + elem.style.animation = value + }) + } + + function cancelActiveAnimations() { + for (var animations = currentAnimations, i = 0, length = animations.length; i < length; i++) animations[i].style.animation = "none" + } + + function setOnBeforeChange(fn) { + onBeforeChange = fn + } + + function tryRestoreView(options) { + var url = options.url, + index = currentUrls.indexOf(url); + if (-1 !== index) { + var animatable = allPages[index], + view = animatable; + if (view) { + if (options.cancel) return; + cancelActiveAnimations(); + var selected = selectedPageIndex, + previousAnimatable = -1 === selected ? null : allPages[selected]; + return onBeforeChange && onBeforeChange(view, !0, options), beforeAnimate(allPages, index, selected), animatable.classList.remove("hide"), animate(animatable, previousAnimatable, options.transition, options.isBack).then(function() { + return selectedPageIndex = index, !options.cancel && previousAnimatable && afterAnimate(allPages, index), view + }) + } + } + return Promise.reject() + } + + function triggerDestroy(view) { + view.dispatchEvent(new CustomEvent("viewdestroy", { + cancelable: !1 + })) + } + + function reset() { + allPages = [], currentUrls = [], mainAnimatedPages.innerHTML = "", selectedPageIndex = -1 + } + var onBeforeChange, mainAnimatedPages = document.querySelector(".mainAnimatedPages"), + allPages = [], + currentUrls = [], + pageContainerCount = 3, + selectedPageIndex = -1, + currentAnimations = []; + return { + loadView: loadView, + tryRestoreView: tryRestoreView, + reset: reset, + setOnBeforeChange: setOnBeforeChange + } +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/viewmanager/viewmanager.js b/dashboard-ui/bower_components/emby-webcomponents/viewmanager/viewmanager.js index 49c6abfa81..3ab5afa710 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/viewmanager/viewmanager.js +++ b/dashboard-ui/bower_components/emby-webcomponents/viewmanager/viewmanager.js @@ -1 +1,82 @@ -define(["viewcontainer","focusManager","queryString","layoutManager"],function(viewcontainer,focusManager,queryString,layoutManager){"use strict";function onViewChange(view,options,isRestore){var lastView=currentView;lastView&&dispatchViewEvent(lastView,null,"viewhide"),currentView=view;var eventDetail=getViewEventDetail(view,options,isRestore);isRestore?layoutManager.mobile||(view.activeElement&&document.body.contains(view.activeElement)&&focusManager.isCurrentlyFocusable(view.activeElement)?focusManager.focus(view.activeElement):focusManager.autoFocus(view)):!1!==options.autoFocus&&focusManager.autoFocus(view),view.dispatchEvent(new CustomEvent("viewshow",eventDetail)),dispatchPageEvents&&view.dispatchEvent(new CustomEvent("pageshow",eventDetail))}function getProperties(view){var props=view.getAttribute("data-properties");return props?props.split(","):[]}function dispatchViewEvent(view,eventInfo,eventName,isCancellable){eventInfo||(eventInfo={detail:{type:view.getAttribute("data-type"),properties:getProperties(view)},bubbles:!0,cancelable:isCancellable}),eventInfo.cancelable=isCancellable||!1;var eventResult=view.dispatchEvent(new CustomEvent(eventName,eventInfo));return dispatchPageEvents&&(eventInfo.cancelable=!1,view.dispatchEvent(new CustomEvent(eventName.replace("view","page"),eventInfo))),eventResult}function getViewEventDetail(view,options,isRestore){var url=options.url,index=url.indexOf("?"),params=-1===index?{}:queryString.parse(url.substring(index+1));return{detail:{type:view.getAttribute("data-type"),properties:getProperties(view),params:params,isRestored:isRestore,state:options.state,options:options.options||{}},bubbles:!0,cancelable:!1}}function resetCachedViews(){viewcontainer.reset()}function ViewManager(){}var currentView,dispatchPageEvents;return viewcontainer.setOnBeforeChange(function(newView,isRestored,options){var lastView=currentView;if(lastView){dispatchViewEvent(lastView,null,"viewbeforehide",!0)}var eventDetail=getViewEventDetail(newView,options,isRestored);if(!newView.initComplete){if(newView.initComplete=!0,options.controllerFactory){new options.controllerFactory(newView,eventDetail.detail.params)}options.controllerFactory&&!dispatchPageEvents||dispatchViewEvent(newView,eventDetail,"viewinit")}dispatchViewEvent(newView,eventDetail,"viewbeforeshow")}),document.addEventListener("skinunload",resetCachedViews),ViewManager.prototype.loadView=function(options){var lastView=currentView;lastView&&(lastView.activeElement=document.activeElement),options.cancel||viewcontainer.loadView(options).then(function(view){onViewChange(view,options)})},ViewManager.prototype.tryRestoreView=function(options,onViewChanging){return options.cancel?Promise.reject({cancelled:!0}):(currentView&&(currentView.activeElement=document.activeElement),viewcontainer.tryRestoreView(options).then(function(view){onViewChanging(),onViewChange(view,options,!0)}))},ViewManager.prototype.currentView=function(){return currentView},ViewManager.prototype.dispatchPageEvents=function(value){dispatchPageEvents=value},new ViewManager}); \ No newline at end of file +define(["viewcontainer", "focusManager", "queryString", "layoutManager"], function(viewcontainer, focusManager, queryString, layoutManager) { + "use strict"; + + function onViewChange(view, options, isRestore) { + var lastView = currentView; + lastView && dispatchViewEvent(lastView, null, "viewhide"), currentView = view; + var eventDetail = getViewEventDetail(view, options, isRestore); + isRestore ? layoutManager.mobile || (view.activeElement && document.body.contains(view.activeElement) && focusManager.isCurrentlyFocusable(view.activeElement) ? focusManager.focus(view.activeElement) : focusManager.autoFocus(view)) : !1 !== options.autoFocus && focusManager.autoFocus(view), view.dispatchEvent(new CustomEvent("viewshow", eventDetail)), dispatchPageEvents && view.dispatchEvent(new CustomEvent("pageshow", eventDetail)) + } + + function getProperties(view) { + var props = view.getAttribute("data-properties"); + return props ? props.split(",") : [] + } + + function dispatchViewEvent(view, eventInfo, eventName, isCancellable) { + eventInfo || (eventInfo = { + detail: { + type: view.getAttribute("data-type"), + properties: getProperties(view) + }, + bubbles: !0, + cancelable: isCancellable + }), eventInfo.cancelable = isCancellable || !1; + var eventResult = view.dispatchEvent(new CustomEvent(eventName, eventInfo)); + return dispatchPageEvents && (eventInfo.cancelable = !1, view.dispatchEvent(new CustomEvent(eventName.replace("view", "page"), eventInfo))), eventResult + } + + function getViewEventDetail(view, options, isRestore) { + var url = options.url, + index = url.indexOf("?"), + params = -1 === index ? {} : queryString.parse(url.substring(index + 1)); + return { + detail: { + type: view.getAttribute("data-type"), + properties: getProperties(view), + params: params, + isRestored: isRestore, + state: options.state, + options: options.options || {} + }, + bubbles: !0, + cancelable: !1 + } + } + + function resetCachedViews() { + viewcontainer.reset() + } + + function ViewManager() {} + var currentView, dispatchPageEvents; + return viewcontainer.setOnBeforeChange(function(newView, isRestored, options) { + var lastView = currentView; + if (lastView) { + dispatchViewEvent(lastView, null, "viewbeforehide", !0) + } + var eventDetail = getViewEventDetail(newView, options, isRestored); + if (!newView.initComplete) { + if (newView.initComplete = !0, options.controllerFactory) { + new options.controllerFactory(newView, eventDetail.detail.params) + } + options.controllerFactory && !dispatchPageEvents || dispatchViewEvent(newView, eventDetail, "viewinit") + } + dispatchViewEvent(newView, eventDetail, "viewbeforeshow") + }), document.addEventListener("skinunload", resetCachedViews), ViewManager.prototype.loadView = function(options) { + var lastView = currentView; + lastView && (lastView.activeElement = document.activeElement), options.cancel || viewcontainer.loadView(options).then(function(view) { + onViewChange(view, options) + }) + }, ViewManager.prototype.tryRestoreView = function(options, onViewChanging) { + return options.cancel ? Promise.reject({ + cancelled: !0 + }) : (currentView && (currentView.activeElement = document.activeElement), viewcontainer.tryRestoreView(options).then(function(view) { + onViewChanging(), onViewChange(view, options, !0) + })) + }, ViewManager.prototype.currentView = function() { + return currentView + }, ViewManager.prototype.dispatchPageEvents = function(value) { + dispatchPageEvents = value + }, new ViewManager +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/viewsettings/viewsettings.js b/dashboard-ui/bower_components/emby-webcomponents/viewsettings/viewsettings.js index f5612aac23..9fd54e6db5 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/viewsettings/viewsettings.js +++ b/dashboard-ui/bower_components/emby-webcomponents/viewsettings/viewsettings.js @@ -1 +1,60 @@ -define(["require","dialogHelper","loading","apphost","layoutManager","connectionManager","appRouter","globalize","userSettings","emby-checkbox","emby-input","paper-icon-button-light","emby-select","material-icons","css!./../formdialog","emby-button","emby-linkbutton","flexStyles"],function(require,dialogHelper,loading,appHost,layoutManager,connectionManager,appRouter,globalize,userSettings){"use strict";function onSubmit(e){return e.preventDefault(),!1}function initEditor(context,settings){context.querySelector("form").addEventListener("submit",onSubmit);for(var elems=context.querySelectorAll(".viewSetting-checkboxContainer"),i=0,length=elems.length;i=0&&rec.top0&&rec.bottom<=vpHeight+thresholdY,lViz=rec.left>=0&&rec.left0&&rec.right<=vpWidth+thresholdX,vVisible=partial?tViz||bViz:tViz&&bViz,hVisible=partial?lViz||rViz:lViz&&rViz;return vVisible&&hVisible}return visibleInViewport}); \ No newline at end of file +define(["dom"], function(dom) { + "use strict"; + + function visibleInViewport(elem, partial, thresholdX, thresholdY) { + if (thresholdX = thresholdX || 0, thresholdY = thresholdY || 0, !elem.getBoundingClientRect) return !0; + var windowSize = dom.getWindowSize(), + vpWidth = windowSize.innerWidth, + vpHeight = windowSize.innerHeight, + rec = elem.getBoundingClientRect(), + tViz = rec.top >= 0 && rec.top < vpHeight + thresholdY, + bViz = rec.bottom > 0 && rec.bottom <= vpHeight + thresholdY, + lViz = rec.left >= 0 && rec.left < vpWidth + thresholdX, + rViz = rec.right > 0 && rec.right <= vpWidth + thresholdX, + vVisible = partial ? tViz || bViz : tViz && bViz, + hVisible = partial ? lViz || rViz : lViz && rViz; + return vVisible && hVisible + } + return visibleInViewport +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/emby-webcomponents/youtubeplayer/plugin.js b/dashboard-ui/bower_components/emby-webcomponents/youtubeplayer/plugin.js index 82e9643b2a..243050eccb 100644 --- a/dashboard-ui/bower_components/emby-webcomponents/youtubeplayer/plugin.js +++ b/dashboard-ui/bower_components/emby-webcomponents/youtubeplayer/plugin.js @@ -1 +1,181 @@ -define(["require","events","browser","appRouter","loading"],function(require,events,browser,appRouter,loading){"use strict";function zoomIn(elem,iterations){var keyframes=[{transform:"scale3d(.2, .2, .2) ",opacity:".6",offset:0},{transform:"none",opacity:"1",offset:1}],timing={duration:240,iterations:iterations};return elem.animate(keyframes,timing)}function createMediaElement(instance,options){return new Promise(function(resolve,reject){var dlg=document.querySelector(".youtubePlayerContainer");dlg?resolve(dlg.querySelector("#player")):require(["css!./style"],function(){loading.show();var dlg=document.createElement("div");dlg.classList.add("youtubePlayerContainer"),options.fullscreen&&dlg.classList.add("onTop"),dlg.innerHTML='
    ';var videoElement=dlg.querySelector("#player");document.body.insertBefore(dlg,document.body.firstChild),instance.videoDialog=dlg,options.fullscreen&&dlg.animate&&!browser.slow?zoomIn(dlg,1).onfinish=function(){resolve(videoElement)}:resolve(videoElement)})})}function onVideoResize(){var instance=this,player=instance.currentYoutubePlayer,dlg=instance.videoDialog;player&&dlg&&player.setSize(dlg.offsetWidth,dlg.offsetHeight)}function clearTimeUpdateInterval(instance){instance.timeUpdateInterval&&clearInterval(instance.timeUpdateInterval),instance.timeUpdateInterval=null}function onEndedInternal(instance){clearTimeUpdateInterval(instance);var resizeListener=instance.resizeListener;resizeListener&&(window.removeEventListener("resize",resizeListener),window.removeEventListener("orientationChange",resizeListener),instance.resizeListener=null);var stopInfo={src:instance._currentSrc};events.trigger(instance,"stopped",[stopInfo]),instance._currentSrc=null,instance.currentYoutubePlayer&&instance.currentYoutubePlayer.destroy(),instance.currentYoutubePlayer=null}function onPlayerReady(event){event.target.playVideo()}function onTimeUpdate(e){events.trigger(this,"timeupdate")}function onPlaying(instance,playOptions,resolve){instance.started||(instance.started=!0,resolve(),clearTimeUpdateInterval(instance),instance.timeUpdateInterval=setInterval(onTimeUpdate.bind(instance),500),playOptions.fullscreen?appRouter.showVideoOsd().then(function(){instance.videoDialog.classList.remove("onTop")}):(appRouter.setTransparency("backdrop"),instance.videoDialog.classList.remove("onTop")),require(["loading"],function(loading){loading.hide()}))}function setCurrentSrc(instance,elem,options){return new Promise(function(resolve,reject){require(["queryString"],function(queryString){instance._currentSrc=options.url;var params=queryString.parse(options.url.split("?")[1]);if(window.onYouTubeIframeAPIReady=function(){instance.currentYoutubePlayer=new YT.Player("player",{height:instance.videoDialog.offsetHeight,width:instance.videoDialog.offsetWidth,videoId:params.v,events:{onReady:onPlayerReady,onStateChange:function(event){event.data===YT.PlayerState.PLAYING?onPlaying(instance,options,resolve):event.data===YT.PlayerState.ENDED?onEndedInternal(instance):event.data===YT.PlayerState.PAUSED&&events.trigger(instance,"pause")}},playerVars:{controls:0,enablejsapi:1,modestbranding:1,rel:0,showinfo:0,fs:0,playsinline:1}});var resizeListener=instance.resizeListener;resizeListener?(window.removeEventListener("resize",resizeListener),window.addEventListener("resize",resizeListener)):(resizeListener=instance.resizeListener=onVideoResize.bind(instance),window.addEventListener("resize",resizeListener)),window.removeEventListener("orientationChange",resizeListener),window.addEventListener("orientationChange",resizeListener)},window.YT)window.onYouTubeIframeAPIReady();else{var tag=document.createElement("script");tag.src="https://www.youtube.com/iframe_api";var firstScriptTag=document.getElementsByTagName("script")[0];firstScriptTag.parentNode.insertBefore(tag,firstScriptTag)}})})}function YoutubePlayer(){this.name="Youtube Player",this.type="mediaplayer",this.id="youtubeplayer",this.priority=1}return YoutubePlayer.prototype.play=function(options){this.started=!1;var instance=this;return createMediaElement(this,options).then(function(elem){return setCurrentSrc(instance,elem,options)})},YoutubePlayer.prototype.stop=function(destroyPlayer){return this._currentSrc&&(this.currentYoutubePlayer&&this.currentYoutubePlayer.stopVideo(),onEndedInternal(this),destroyPlayer&&this.destroy()),Promise.resolve()},YoutubePlayer.prototype.destroy=function(){appRouter.setTransparency("none");var dlg=this.videoDialog;dlg&&(this.videoDialog=null,dlg.parentNode.removeChild(dlg))},YoutubePlayer.prototype.canPlayMediaType=function(mediaType){return"audio"===(mediaType=(mediaType||"").toLowerCase())||"video"===mediaType},YoutubePlayer.prototype.canPlayItem=function(item){return!1},YoutubePlayer.prototype.canPlayUrl=function(url){return-1!==url.toLowerCase().indexOf("youtube.com")},YoutubePlayer.prototype.getDeviceProfile=function(){return Promise.resolve({})},YoutubePlayer.prototype.currentSrc=function(){return this._currentSrc},YoutubePlayer.prototype.setSubtitleStreamIndex=function(index){},YoutubePlayer.prototype.canSetAudioStreamIndex=function(){return!1},YoutubePlayer.prototype.setAudioStreamIndex=function(index){},YoutubePlayer.prototype.currentTime=function(val){var currentYoutubePlayer=this.currentYoutubePlayer;if(currentYoutubePlayer)return null!=val?void currentYoutubePlayer.seekTo(val/1e3,!0):1e3*currentYoutubePlayer.getCurrentTime()},YoutubePlayer.prototype.duration=function(val){var currentYoutubePlayer=this.currentYoutubePlayer;return currentYoutubePlayer?1e3*currentYoutubePlayer.getDuration():null},YoutubePlayer.prototype.pause=function(){var currentYoutubePlayer=this.currentYoutubePlayer;if(currentYoutubePlayer){currentYoutubePlayer.pauseVideo();var instance=this;setTimeout(function(){events.trigger(instance,"pause")},200)}},YoutubePlayer.prototype.unpause=function(){var currentYoutubePlayer=this.currentYoutubePlayer;if(currentYoutubePlayer){currentYoutubePlayer.playVideo();var instance=this;setTimeout(function(){events.trigger(instance,"unpause")},200)}},YoutubePlayer.prototype.paused=function(){var currentYoutubePlayer=this.currentYoutubePlayer;return!!currentYoutubePlayer&&2===currentYoutubePlayer.getPlayerState()},YoutubePlayer.prototype.volume=function(val){return null!=val?this.setVolume(val):this.getVolume()},YoutubePlayer.prototype.setVolume=function(val){var currentYoutubePlayer=this.currentYoutubePlayer;currentYoutubePlayer&&null!=val&¤tYoutubePlayer.setVolume(val)},YoutubePlayer.prototype.getVolume=function(){var currentYoutubePlayer=this.currentYoutubePlayer;if(currentYoutubePlayer)return currentYoutubePlayer.getVolume()},YoutubePlayer.prototype.setMute=function(mute){var currentYoutubePlayer=this.currentYoutubePlayer;mute?currentYoutubePlayer&¤tYoutubePlayer.mute():currentYoutubePlayer&¤tYoutubePlayer.unMute()},YoutubePlayer.prototype.isMuted=function(){var currentYoutubePlayer=this.currentYoutubePlayer;if(currentYoutubePlayer)return currentYoutubePlayer.isMuted()},YoutubePlayer}); \ No newline at end of file +define(["require", "events", "browser", "appRouter", "loading"], function(require, events, browser, appRouter, loading) { + "use strict"; + + function zoomIn(elem, iterations) { + var keyframes = [{ + transform: "scale3d(.2, .2, .2) ", + opacity: ".6", + offset: 0 + }, { + transform: "none", + opacity: "1", + offset: 1 + }], + timing = { + duration: 240, + iterations: iterations + }; + return elem.animate(keyframes, timing) + } + + function createMediaElement(instance, options) { + return new Promise(function(resolve, reject) { + var dlg = document.querySelector(".youtubePlayerContainer"); + dlg ? resolve(dlg.querySelector("#player")) : require(["css!./style"], function() { + loading.show(); + var dlg = document.createElement("div"); + dlg.classList.add("youtubePlayerContainer"), options.fullscreen && dlg.classList.add("onTop"), dlg.innerHTML = '
    '; + var videoElement = dlg.querySelector("#player"); + document.body.insertBefore(dlg, document.body.firstChild), instance.videoDialog = dlg, options.fullscreen && dlg.animate && !browser.slow ? zoomIn(dlg, 1).onfinish = function() { + resolve(videoElement) + } : resolve(videoElement) + }) + }) + } + + function onVideoResize() { + var instance = this, + player = instance.currentYoutubePlayer, + dlg = instance.videoDialog; + player && dlg && player.setSize(dlg.offsetWidth, dlg.offsetHeight) + } + + function clearTimeUpdateInterval(instance) { + instance.timeUpdateInterval && clearInterval(instance.timeUpdateInterval), instance.timeUpdateInterval = null + } + + function onEndedInternal(instance) { + clearTimeUpdateInterval(instance); + var resizeListener = instance.resizeListener; + resizeListener && (window.removeEventListener("resize", resizeListener), window.removeEventListener("orientationChange", resizeListener), instance.resizeListener = null); + var stopInfo = { + src: instance._currentSrc + }; + events.trigger(instance, "stopped", [stopInfo]), instance._currentSrc = null, instance.currentYoutubePlayer && instance.currentYoutubePlayer.destroy(), instance.currentYoutubePlayer = null + } + + function onPlayerReady(event) { + event.target.playVideo() + } + + function onTimeUpdate(e) { + events.trigger(this, "timeupdate") + } + + function onPlaying(instance, playOptions, resolve) { + instance.started || (instance.started = !0, resolve(), clearTimeUpdateInterval(instance), instance.timeUpdateInterval = setInterval(onTimeUpdate.bind(instance), 500), playOptions.fullscreen ? appRouter.showVideoOsd().then(function() { + instance.videoDialog.classList.remove("onTop") + }) : (appRouter.setTransparency("backdrop"), instance.videoDialog.classList.remove("onTop")), require(["loading"], function(loading) { + loading.hide() + })) + } + + function setCurrentSrc(instance, elem, options) { + return new Promise(function(resolve, reject) { + require(["queryString"], function(queryString) { + instance._currentSrc = options.url; + var params = queryString.parse(options.url.split("?")[1]); + if (window.onYouTubeIframeAPIReady = function() { + instance.currentYoutubePlayer = new YT.Player("player", { + height: instance.videoDialog.offsetHeight, + width: instance.videoDialog.offsetWidth, + videoId: params.v, + events: { + onReady: onPlayerReady, + onStateChange: function(event) { + event.data === YT.PlayerState.PLAYING ? onPlaying(instance, options, resolve) : event.data === YT.PlayerState.ENDED ? onEndedInternal(instance) : event.data === YT.PlayerState.PAUSED && events.trigger(instance, "pause") + } + }, + playerVars: { + controls: 0, + enablejsapi: 1, + modestbranding: 1, + rel: 0, + showinfo: 0, + fs: 0, + playsinline: 1 + } + }); + var resizeListener = instance.resizeListener; + resizeListener ? (window.removeEventListener("resize", resizeListener), window.addEventListener("resize", resizeListener)) : (resizeListener = instance.resizeListener = onVideoResize.bind(instance), window.addEventListener("resize", resizeListener)), window.removeEventListener("orientationChange", resizeListener), window.addEventListener("orientationChange", resizeListener) + }, window.YT) window.onYouTubeIframeAPIReady(); + else { + var tag = document.createElement("script"); + tag.src = "https://www.youtube.com/iframe_api"; + var firstScriptTag = document.getElementsByTagName("script")[0]; + firstScriptTag.parentNode.insertBefore(tag, firstScriptTag) + } + }) + }) + } + + function YoutubePlayer() { + this.name = "Youtube Player", this.type = "mediaplayer", this.id = "youtubeplayer", this.priority = 1 + } + return YoutubePlayer.prototype.play = function(options) { + this.started = !1; + var instance = this; + return createMediaElement(this, options).then(function(elem) { + return setCurrentSrc(instance, elem, options) + }) + }, YoutubePlayer.prototype.stop = function(destroyPlayer) { + return this._currentSrc && (this.currentYoutubePlayer && this.currentYoutubePlayer.stopVideo(), onEndedInternal(this), destroyPlayer && this.destroy()), Promise.resolve() + }, YoutubePlayer.prototype.destroy = function() { + appRouter.setTransparency("none"); + var dlg = this.videoDialog; + dlg && (this.videoDialog = null, dlg.parentNode.removeChild(dlg)) + }, YoutubePlayer.prototype.canPlayMediaType = function(mediaType) { + return "audio" === (mediaType = (mediaType || "").toLowerCase()) || "video" === mediaType + }, YoutubePlayer.prototype.canPlayItem = function(item) { + return !1 + }, YoutubePlayer.prototype.canPlayUrl = function(url) { + return -1 !== url.toLowerCase().indexOf("youtube.com") + }, YoutubePlayer.prototype.getDeviceProfile = function() { + return Promise.resolve({}) + }, YoutubePlayer.prototype.currentSrc = function() { + return this._currentSrc + }, YoutubePlayer.prototype.setSubtitleStreamIndex = function(index) {}, YoutubePlayer.prototype.canSetAudioStreamIndex = function() { + return !1 + }, YoutubePlayer.prototype.setAudioStreamIndex = function(index) {}, YoutubePlayer.prototype.currentTime = function(val) { + var currentYoutubePlayer = this.currentYoutubePlayer; + if (currentYoutubePlayer) return null != val ? void currentYoutubePlayer.seekTo(val / 1e3, !0) : 1e3 * currentYoutubePlayer.getCurrentTime() + }, YoutubePlayer.prototype.duration = function(val) { + var currentYoutubePlayer = this.currentYoutubePlayer; + return currentYoutubePlayer ? 1e3 * currentYoutubePlayer.getDuration() : null + }, YoutubePlayer.prototype.pause = function() { + var currentYoutubePlayer = this.currentYoutubePlayer; + if (currentYoutubePlayer) { + currentYoutubePlayer.pauseVideo(); + var instance = this; + setTimeout(function() { + events.trigger(instance, "pause") + }, 200) + } + }, YoutubePlayer.prototype.unpause = function() { + var currentYoutubePlayer = this.currentYoutubePlayer; + if (currentYoutubePlayer) { + currentYoutubePlayer.playVideo(); + var instance = this; + setTimeout(function() { + events.trigger(instance, "unpause") + }, 200) + } + }, YoutubePlayer.prototype.paused = function() { + var currentYoutubePlayer = this.currentYoutubePlayer; + return !!currentYoutubePlayer && 2 === currentYoutubePlayer.getPlayerState() + }, YoutubePlayer.prototype.volume = function(val) { + return null != val ? this.setVolume(val) : this.getVolume() + }, YoutubePlayer.prototype.setVolume = function(val) { + var currentYoutubePlayer = this.currentYoutubePlayer; + currentYoutubePlayer && null != val && currentYoutubePlayer.setVolume(val) + }, YoutubePlayer.prototype.getVolume = function() { + var currentYoutubePlayer = this.currentYoutubePlayer; + if (currentYoutubePlayer) return currentYoutubePlayer.getVolume() + }, YoutubePlayer.prototype.setMute = function(mute) { + var currentYoutubePlayer = this.currentYoutubePlayer; + mute ? currentYoutubePlayer && currentYoutubePlayer.mute() : currentYoutubePlayer && currentYoutubePlayer.unMute() + }, YoutubePlayer.prototype.isMuted = function() { + var currentYoutubePlayer = this.currentYoutubePlayer; + if (currentYoutubePlayer) return currentYoutubePlayer.isMuted() + }, YoutubePlayer +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/fetch/fetch.js b/dashboard-ui/bower_components/fetch/fetch.js index 7d540d3071..cd40b3ed2d 100644 --- a/dashboard-ui/bower_components/fetch/fetch.js +++ b/dashboard-ui/bower_components/fetch/fetch.js @@ -1 +1,263 @@ -!function(self){"use strict";function normalizeName(name){if("string"!=typeof name&&(name=String(name)),/[^a-z0-9\-#$%&'*+.\^_`|~]/i.test(name))throw new TypeError("Invalid character in header field name");return name.toLowerCase()}function normalizeValue(value){return"string"!=typeof value&&(value=String(value)),value}function iteratorFor(items){var iterator={next:function(){var value=items.shift();return{done:void 0===value,value:value}}};return support.iterable&&(iterator[Symbol.iterator]=function(){return iterator}),iterator}function Headers(headers){this.map={},headers instanceof Headers?headers.forEach(function(value,name){this.append(name,value)},this):headers&&Object.getOwnPropertyNames(headers).forEach(function(name){this.append(name,headers[name])},this)}function consumed(body){if(body.bodyUsed)return Promise.reject(new TypeError("Already read"));body.bodyUsed=!0}function fileReaderReady(reader){return new Promise(function(resolve,reject){reader.onload=function(){resolve(reader.result)},reader.onerror=function(){reject(reader.error)}})}function readBlobAsArrayBuffer(blob){var reader=new FileReader,promise=fileReaderReady(reader);return reader.readAsArrayBuffer(blob),promise}function readBlobAsText(blob){var reader=new FileReader,promise=fileReaderReady(reader);return reader.readAsText(blob),promise}function readArrayBufferAsText(buf){for(var view=new Uint8Array(buf),chars=new Array(view.length),i=0;i-1?upcased:method}function Request(input,options){options=options||{};var body=options.body;if("string"==typeof input)this.url=input;else{if(input.bodyUsed)throw new TypeError("Already read");this.url=input.url,this.credentials=input.credentials,options.headers||(this.headers=new Headers(input.headers)),this.method=input.method,this.mode=input.mode,body||null==input._bodyInit||(body=input._bodyInit,input.bodyUsed=!0)}if(this.credentials=options.credentials||this.credentials||"omit",!options.headers&&this.headers||(this.headers=new Headers(options.headers)),this.method=normalizeMethod(options.method||this.method||"GET"),this.mode=options.mode||this.mode||null,this.referrer=null,("GET"===this.method||"HEAD"===this.method)&&body)throw new TypeError("Body not allowed for GET or HEAD requests");this._initBody(body)}function decode(body){var form=new FormData;return body.trim().split("&").forEach(function(bytes){if(bytes){var split=bytes.split("="),name=split.shift().replace(/\+/g," "),value=split.join("=").replace(/\+/g," ");form.append(decodeURIComponent(name),decodeURIComponent(value))}}),form}function parseHeaders(rawHeaders){var headers=new Headers;return rawHeaders.split("\r\n").forEach(function(line){var parts=line.split(":"),key=parts.shift().trim();if(key){var value=parts.join(":").trim();headers.append(key,value)}}),headers}function Response(bodyInit,options){options||(options={}),this.type="default",this.status="status"in options?options.status:200,this.ok=this.status>=200&&this.status<300,this.statusText="statusText"in options?options.statusText:"OK",this.headers=new Headers(options.headers),this.url=options.url||"",this._initBody(bodyInit)}if(!self.fetch){var support={searchParams:"URLSearchParams"in self,iterable:"Symbol"in self&&"iterator"in Symbol,blob:"FileReader"in self&&"Blob"in self&&function(){try{return new Blob,!0}catch(e){return!1}}(),formData:"FormData"in self,arrayBuffer:"ArrayBuffer"in self};if(support.arrayBuffer)var viewClasses=["[object Int8Array]","[object Uint8Array]","[object Uint8ClampedArray]","[object Int16Array]","[object Uint16Array]","[object Int32Array]","[object Uint32Array]","[object Float32Array]","[object Float64Array]"],isDataView=function(obj){return obj&&DataView.prototype.isPrototypeOf(obj)},isArrayBufferView=ArrayBuffer.isView||function(obj){return obj&&viewClasses.indexOf(Object.prototype.toString.call(obj))>-1};Headers.prototype.append=function(name,value){name=normalizeName(name),value=normalizeValue(value);var list=this.map[name];list||(list=[],this.map[name]=list),list.push(value)},Headers.prototype.delete=function(name){delete this.map[normalizeName(name)]},Headers.prototype.get=function(name){var values=this.map[normalizeName(name)];return values?values[0]:null},Headers.prototype.getAll=function(name){return this.map[normalizeName(name)]||[]},Headers.prototype.has=function(name){return this.map.hasOwnProperty(normalizeName(name))},Headers.prototype.set=function(name,value){this.map[normalizeName(name)]=[normalizeValue(value)]},Headers.prototype.forEach=function(callback,thisArg){Object.getOwnPropertyNames(this.map).forEach(function(name){this.map[name].forEach(function(value){callback.call(thisArg,value,name,this)},this)},this)},Headers.prototype.keys=function(){var items=[];return this.forEach(function(value,name){items.push(name)}),iteratorFor(items)},Headers.prototype.values=function(){var items=[];return this.forEach(function(value){items.push(value)}),iteratorFor(items)},Headers.prototype.entries=function(){var items=[];return this.forEach(function(value,name){items.push([name,value])}),iteratorFor(items)},support.iterable&&(Headers.prototype[Symbol.iterator]=Headers.prototype.entries);var methods=["DELETE","GET","HEAD","OPTIONS","POST","PUT"];Request.prototype.clone=function(){return new Request(this,{body:this._bodyInit})},Body.call(Request.prototype),Body.call(Response.prototype),Response.prototype.clone=function(){return new Response(this._bodyInit,{status:this.status,statusText:this.statusText,headers:new Headers(this.headers),url:this.url})},Response.error=function(){var response=new Response(null,{status:0,statusText:""});return response.type="error",response};var redirectStatuses=[301,302,303,307,308];Response.redirect=function(url,status){if(-1===redirectStatuses.indexOf(status))throw new RangeError("Invalid status code");return new Response(null,{status:status,headers:{location:url}})},self.Headers=Headers,self.Request=Request,self.Response=Response,self.fetch=function(input,init){return new Promise(function(resolve,reject){var request=new Request(input,init),xhr=new XMLHttpRequest;xhr.onload=function(){var options={status:xhr.status,statusText:xhr.statusText,headers:parseHeaders(xhr.getAllResponseHeaders()||"")};options.url="responseURL"in xhr?xhr.responseURL:options.headers.get("X-Request-URL");var body="response"in xhr?xhr.response:xhr.responseText;resolve(new Response(body,options))},xhr.onerror=function(){reject(new TypeError("Network request failed"))},xhr.ontimeout=function(){reject(new TypeError("Network request failed"))},xhr.open(request.method,request.url,!0),"include"===request.credentials&&(xhr.withCredentials=!0),"responseType"in xhr&&support.blob&&(xhr.responseType="blob"),request.headers.forEach(function(value,name){xhr.setRequestHeader(name,value)}),xhr.send(void 0===request._bodyInit?null:request._bodyInit)})},self.fetch.polyfill=!0}}("undefined"!=typeof self?self:this); \ No newline at end of file +! function(self) { + "use strict"; + + function normalizeName(name) { + if ("string" != typeof name && (name = String(name)), /[^a-z0-9\-#$%&'*+.\^_`|~]/i.test(name)) throw new TypeError("Invalid character in header field name"); + return name.toLowerCase() + } + + function normalizeValue(value) { + return "string" != typeof value && (value = String(value)), value + } + + function iteratorFor(items) { + var iterator = { + next: function() { + var value = items.shift(); + return { + done: void 0 === value, + value: value + } + } + }; + return support.iterable && (iterator[Symbol.iterator] = function() { + return iterator + }), iterator + } + + function Headers(headers) { + this.map = {}, headers instanceof Headers ? headers.forEach(function(value, name) { + this.append(name, value) + }, this) : headers && Object.getOwnPropertyNames(headers).forEach(function(name) { + this.append(name, headers[name]) + }, this) + } + + function consumed(body) { + if (body.bodyUsed) return Promise.reject(new TypeError("Already read")); + body.bodyUsed = !0 + } + + function fileReaderReady(reader) { + return new Promise(function(resolve, reject) { + reader.onload = function() { + resolve(reader.result) + }, reader.onerror = function() { + reject(reader.error) + } + }) + } + + function readBlobAsArrayBuffer(blob) { + var reader = new FileReader, + promise = fileReaderReady(reader); + return reader.readAsArrayBuffer(blob), promise + } + + function readBlobAsText(blob) { + var reader = new FileReader, + promise = fileReaderReady(reader); + return reader.readAsText(blob), promise + } + + function readArrayBufferAsText(buf) { + for (var view = new Uint8Array(buf), chars = new Array(view.length), i = 0; i < view.length; i++) chars[i] = String.fromCharCode(view[i]); + return chars.join("") + } + + function bufferClone(buf) { + if (buf.slice) return buf.slice(0); + var view = new Uint8Array(buf.byteLength); + return view.set(new Uint8Array(buf)), view.buffer + } + + function Body() { + return this.bodyUsed = !1, this._initBody = function(body) { + if (this._bodyInit = body, body) + if ("string" == typeof body) this._bodyText = body; + else if (support.blob && Blob.prototype.isPrototypeOf(body)) this._bodyBlob = body; + else if (support.formData && FormData.prototype.isPrototypeOf(body)) this._bodyFormData = body; + else if (support.searchParams && URLSearchParams.prototype.isPrototypeOf(body)) this._bodyText = body.toString(); + else if (support.arrayBuffer && support.blob && isDataView(body)) this._bodyArrayBuffer = bufferClone(body.buffer), this._bodyInit = new Blob([this._bodyArrayBuffer]); + else { + if (!support.arrayBuffer || !ArrayBuffer.prototype.isPrototypeOf(body) && !isArrayBufferView(body)) throw new Error("unsupported BodyInit type"); + this._bodyArrayBuffer = bufferClone(body) + } else this._bodyText = ""; + this.headers.get("content-type") || ("string" == typeof body ? this.headers.set("content-type", "text/plain;charset=UTF-8") : this._bodyBlob && this._bodyBlob.type ? this.headers.set("content-type", this._bodyBlob.type) : support.searchParams && URLSearchParams.prototype.isPrototypeOf(body) && this.headers.set("content-type", "application/x-www-form-urlencoded;charset=UTF-8")) + }, support.blob && (this.blob = function() { + var rejected = consumed(this); + if (rejected) return rejected; + if (this._bodyBlob) return Promise.resolve(this._bodyBlob); + if (this._bodyArrayBuffer) return Promise.resolve(new Blob([this._bodyArrayBuffer])); + if (this._bodyFormData) throw new Error("could not read FormData body as blob"); + return Promise.resolve(new Blob([this._bodyText])) + }, this.arrayBuffer = function() { + return this._bodyArrayBuffer ? consumed(this) || Promise.resolve(this._bodyArrayBuffer) : this.blob().then(readBlobAsArrayBuffer) + }), this.text = function() { + var rejected = consumed(this); + if (rejected) return rejected; + if (this._bodyBlob) return readBlobAsText(this._bodyBlob); + if (this._bodyArrayBuffer) return Promise.resolve(readArrayBufferAsText(this._bodyArrayBuffer)); + if (this._bodyFormData) throw new Error("could not read FormData body as text"); + return Promise.resolve(this._bodyText) + }, support.formData && (this.formData = function() { + return this.text().then(decode) + }), this.json = function() { + return this.text().then(JSON.parse) + }, this + } + + function normalizeMethod(method) { + var upcased = method.toUpperCase(); + return methods.indexOf(upcased) > -1 ? upcased : method + } + + function Request(input, options) { + options = options || {}; + var body = options.body; + if ("string" == typeof input) this.url = input; + else { + if (input.bodyUsed) throw new TypeError("Already read"); + this.url = input.url, this.credentials = input.credentials, options.headers || (this.headers = new Headers(input.headers)), this.method = input.method, this.mode = input.mode, body || null == input._bodyInit || (body = input._bodyInit, input.bodyUsed = !0) + } + if (this.credentials = options.credentials || this.credentials || "omit", !options.headers && this.headers || (this.headers = new Headers(options.headers)), this.method = normalizeMethod(options.method || this.method || "GET"), this.mode = options.mode || this.mode || null, this.referrer = null, ("GET" === this.method || "HEAD" === this.method) && body) throw new TypeError("Body not allowed for GET or HEAD requests"); + this._initBody(body) + } + + function decode(body) { + var form = new FormData; + return body.trim().split("&").forEach(function(bytes) { + if (bytes) { + var split = bytes.split("="), + name = split.shift().replace(/\+/g, " "), + value = split.join("=").replace(/\+/g, " "); + form.append(decodeURIComponent(name), decodeURIComponent(value)) + } + }), form + } + + function parseHeaders(rawHeaders) { + var headers = new Headers; + return rawHeaders.split("\r\n").forEach(function(line) { + var parts = line.split(":"), + key = parts.shift().trim(); + if (key) { + var value = parts.join(":").trim(); + headers.append(key, value) + } + }), headers + } + + function Response(bodyInit, options) { + options || (options = {}), this.type = "default", this.status = "status" in options ? options.status : 200, this.ok = this.status >= 200 && this.status < 300, this.statusText = "statusText" in options ? options.statusText : "OK", this.headers = new Headers(options.headers), this.url = options.url || "", this._initBody(bodyInit) + } + if (!self.fetch) { + var support = { + searchParams: "URLSearchParams" in self, + iterable: "Symbol" in self && "iterator" in Symbol, + blob: "FileReader" in self && "Blob" in self && function() { + try { + return new Blob, !0 + } catch (e) { + return !1 + } + }(), + formData: "FormData" in self, + arrayBuffer: "ArrayBuffer" in self + }; + if (support.arrayBuffer) var viewClasses = ["[object Int8Array]", "[object Uint8Array]", "[object Uint8ClampedArray]", "[object Int16Array]", "[object Uint16Array]", "[object Int32Array]", "[object Uint32Array]", "[object Float32Array]", "[object Float64Array]"], + isDataView = function(obj) { + return obj && DataView.prototype.isPrototypeOf(obj) + }, + isArrayBufferView = ArrayBuffer.isView || function(obj) { + return obj && viewClasses.indexOf(Object.prototype.toString.call(obj)) > -1 + }; + Headers.prototype.append = function(name, value) { + name = normalizeName(name), value = normalizeValue(value); + var list = this.map[name]; + list || (list = [], this.map[name] = list), list.push(value) + }, Headers.prototype.delete = function(name) { + delete this.map[normalizeName(name)] + }, Headers.prototype.get = function(name) { + var values = this.map[normalizeName(name)]; + return values ? values[0] : null + }, Headers.prototype.getAll = function(name) { + return this.map[normalizeName(name)] || [] + }, Headers.prototype.has = function(name) { + return this.map.hasOwnProperty(normalizeName(name)) + }, Headers.prototype.set = function(name, value) { + this.map[normalizeName(name)] = [normalizeValue(value)] + }, Headers.prototype.forEach = function(callback, thisArg) { + Object.getOwnPropertyNames(this.map).forEach(function(name) { + this.map[name].forEach(function(value) { + callback.call(thisArg, value, name, this) + }, this) + }, this) + }, Headers.prototype.keys = function() { + var items = []; + return this.forEach(function(value, name) { + items.push(name) + }), iteratorFor(items) + }, Headers.prototype.values = function() { + var items = []; + return this.forEach(function(value) { + items.push(value) + }), iteratorFor(items) + }, Headers.prototype.entries = function() { + var items = []; + return this.forEach(function(value, name) { + items.push([name, value]) + }), iteratorFor(items) + }, support.iterable && (Headers.prototype[Symbol.iterator] = Headers.prototype.entries); + var methods = ["DELETE", "GET", "HEAD", "OPTIONS", "POST", "PUT"]; + Request.prototype.clone = function() { + return new Request(this, { + body: this._bodyInit + }) + }, Body.call(Request.prototype), Body.call(Response.prototype), Response.prototype.clone = function() { + return new Response(this._bodyInit, { + status: this.status, + statusText: this.statusText, + headers: new Headers(this.headers), + url: this.url + }) + }, Response.error = function() { + var response = new Response(null, { + status: 0, + statusText: "" + }); + return response.type = "error", response + }; + var redirectStatuses = [301, 302, 303, 307, 308]; + Response.redirect = function(url, status) { + if (-1 === redirectStatuses.indexOf(status)) throw new RangeError("Invalid status code"); + return new Response(null, { + status: status, + headers: { + location: url + } + }) + }, self.Headers = Headers, self.Request = Request, self.Response = Response, self.fetch = function(input, init) { + return new Promise(function(resolve, reject) { + var request = new Request(input, init), + xhr = new XMLHttpRequest; + xhr.onload = function() { + var options = { + status: xhr.status, + statusText: xhr.statusText, + headers: parseHeaders(xhr.getAllResponseHeaders() || "") + }; + options.url = "responseURL" in xhr ? xhr.responseURL : options.headers.get("X-Request-URL"); + var body = "response" in xhr ? xhr.response : xhr.responseText; + resolve(new Response(body, options)) + }, xhr.onerror = function() { + reject(new TypeError("Network request failed")) + }, xhr.ontimeout = function() { + reject(new TypeError("Network request failed")) + }, xhr.open(request.method, request.url, !0), "include" === request.credentials && (xhr.withCredentials = !0), "responseType" in xhr && support.blob && (xhr.responseType = "blob"), request.headers.forEach(function(value, name) { + xhr.setRequestHeader(name, value) + }), xhr.send(void 0 === request._bodyInit ? null : request._bodyInit) + }) + }, self.fetch.polyfill = !0 + } +}("undefined" != typeof self ? self : this); \ No newline at end of file diff --git a/dashboard-ui/bower_components/hlsjs/dist/hls.min.js b/dashboard-ui/bower_components/hlsjs/dist/hls.min.js index bd74c923ba..9c48ae7403 100644 --- a/dashboard-ui/bower_components/hlsjs/dist/hls.min.js +++ b/dashboard-ui/bower_components/hlsjs/dist/hls.min.js @@ -1,3 +1,8745 @@ -!function(t,e){"object"==typeof exports&&"object"==typeof module?module.exports=e():"function"==typeof define&&define.amd?define([],e):"object"==typeof exports?exports.Hls=e():t.Hls=e()}(this,function(){return function(t){function e(i){if(r[i])return r[i].exports;var a=r[i]={i:i,l:!1,exports:{}};return t[i].call(a.exports,a,a.exports,e),a.l=!0,a.exports}var r={};return e.m=t,e.c=r,e.d=function(t,r,i){e.o(t,r)||Object.defineProperty(t,r,{configurable:!1,enumerable:!0,get:i})},e.n=function(t){var r=t&&t.__esModule?function(){return t.default}:function(){return t};return e.d(r,"a",r),r},e.o=function(t,e){return Object.prototype.hasOwnProperty.call(t,e)},e.p="/dist/",e(e.s=28)}([function(t,e,r){"use strict";function i(){}function a(t,e){return e="["+t+"] > "+e}function n(t){var e=c.console[t];return e?function(){for(var r=arguments.length,i=Array(r),n=0;n1?e-1:0),i=1;i1?r-1:0),n=1;n0)r=a+1;else{if(!(o<0))return n;i=a-1}}return null}};e.a=i},function(t,e,r){"use strict";function i(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}r.d(e,"b",function(){return n});var a=function(){function t(){i(this,t)}return t.isHeader=function(t,e){return e+10<=t.length&&73===t[e]&&68===t[e+1]&&51===t[e+2]&&t[e+3]<255&&t[e+4]<255&&t[e+6]<128&&t[e+7]<128&&t[e+8]<128&&t[e+9]<128},t.isFooter=function(t,e){return e+10<=t.length&&51===t[e]&&68===t[e+1]&&73===t[e+2]&&t[e+3]<255&&t[e+4]<255&&t[e+6]<128&&t[e+7]<128&&t[e+8]<128&&t[e+9]<128},t.getID3Data=function(e,r){for(var i=r,a=0;t.isHeader(e,r);){a+=10;a+=t._readSize(e,r+6),t.isFooter(e,r+10)&&(a+=10),r+=a}if(a>0)return e.subarray(i,i+a)},t._readSize=function(t,e){var r=0;return r=(127&t[e])<<21,r|=(127&t[e+1])<<14,r|=(127&t[e+2])<<7,r|=127&t[e+3]},t.getTimeStamp=function(e){for(var r=t.getID3Frames(e),i=0;i1&&void 0!==arguments[1]&&arguments[1],r=t.length,i=void 0,a=void 0,n=void 0,o="",s=0;s>4){case 0:case 1:case 2:case 3:case 4:case 5:case 6:case 7:o+=String.fromCharCode(i);break;case 12:case 13:a=t[s++],o+=String.fromCharCode((31&i)<<6|63&a);break;case 14:a=t[s++],n=t[s++],o+=String.fromCharCode((15&i)<<12|(63&a)<<6|(63&n)<<0)}}return o},t}(),n=a._utf8ArrayToStr;e.a=a},function(t,e,r){"use strict";function i(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function a(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function n(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}var o=r(3),s=function(t){function e(r){i(this,e);for(var n=arguments.length,o=Array(n>1?n-1:0),s=1;s1&&(this.clearNextTick(),this._tickTimer=setTimeout(this._boundTick,0)),this._tickCallCount=0)},e.prototype.doTick=function(){},e}(o.a);e.a=s},function(t,e,r){"use strict";function i(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}var a=r(5),n=r.n(a),o=r(18),s=function(){function t(t,e){for(var r=0;r>8*(15-r)&255;return e},t.prototype.fragmentDecryptdataFromLevelkey=function(t,e){var r=t;return t&&t.method&&t.uri&&!t.iv&&(r=new o.a,r.method=t.method,r.baseuri=t.baseuri,r.reluri=t.reluri,r.iv=this.createInitializationVector(e)),r},s(t,[{key:"url",get:function(){return!this._url&&this.relurl&&(this._url=n.a.buildAbsoluteURL(this.baseurl,this.relurl,{alwaysNormalize:!0})),this._url},set:function(t){this._url=t}},{key:"programDateTime",get:function(){return!this._programDateTime&&this.rawProgramDateTime&&(this._programDateTime=new Date(Date.parse(this.rawProgramDateTime))),this._programDateTime}},{key:"byteRange",get:function(){if(!this._byteRange&&!this.rawByteRange)return[];if(this._byteRange)return this._byteRange;var t=[];if(this.rawByteRange){var e=this.rawByteRange.split("@",2);if(1===e.length){var r=this.lastByteRangeEndOffset;t[0]=r||0}else t[0]=parseInt(e[1]);t[1]=parseInt(e[0])+t[0],this._byteRange=t}return t}},{key:"byteRangeStartOffset",get:function(){return this.byteRange[0]}},{key:"byteRangeEndOffset",get:function(){return this.byteRange[1]}},{key:"decryptdata",get:function(){return this._decryptdata||(this._decryptdata=this.fragmentDecryptdataFromLevelkey(this.levelkey,this.sn)),this._decryptdata}},{key:"encrypted",get:function(){return!(!this.decryptdata||null===this.decryptdata.uri||null!==this.decryptdata.key)}}],[{key:"ElementaryStreamTypes",get:function(){return{AUDIO:"audio",VIDEO:"video"}}}]),t}();e.a=l},function(t,e,r){"use strict";function i(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function a(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function n(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}r.d(e,"a",function(){return l}),r.d(e,"b",function(){return u});var o=r(3),s=r(1),l={NOT_LOADED:"NOT_LOADED",APPENDING:"APPENDING",PARTIAL:"PARTIAL",OK:"OK"},u=function(t){function e(r){i(this,e);var n=a(this,t.call(this,r,s.a.BUFFER_APPENDED,s.a.FRAG_BUFFERED,s.a.FRAG_LOADED));return n.bufferPadding=.2,n.fragments=Object.create(null),n.timeRanges=Object.create(null),n.config=r.config,n}return n(e,t),e.prototype.destroy=function(){this.fragments=null,this.timeRanges=null,this.config=null,o.a.prototype.destroy.call(this),t.prototype.destroy.call(this)},e.prototype.getBufferedFrag=function(t,e){var r=this.fragments,i=Object.keys(r).filter(function(i){var a=r[i];if(a.body.type!==e)return!1;if(!a.buffered)return!1;var n=a.body;return n.startPTS<=t&&t<=n.endPTS});if(0===i.length)return null;var a=i.pop();return r[a].body},e.prototype.detectEvictedFragments=function(t,e){var r=this,i=void 0,a=void 0;Object.keys(this.fragments).forEach(function(n){var o=r.fragments[n];if(!0===o.buffered){var s=o.range[t];if(s){i=s.time;for(var l=0;l=a&&e<=n){i.push({startPTS:Math.max(t,r.start(s)),endPTS:Math.min(e,r.end(s))});break}if(ta)i.push({startPTS:Math.max(t,r.start(s)),endPTS:Math.min(e,r.end(s))}),o=!0;else if(e<=a)break}return{time:i,partial:o}},e.prototype.getFragmentKey=function(t){return t.type+"_"+t.level+"_"+t.urlId+"_"+t.sn},e.prototype.getPartialFragment=function(t){var e=this,r=void 0,i=void 0,a=void 0,n=null,o=0;return Object.keys(this.fragments).forEach(function(s){var l=e.fragments[s];e.isPartial(l)&&(i=l.body.startPTS-e.bufferPadding,a=l.body.endPTS+e.bufferPadding,t>=i&&t<=a&&(r=Math.min(t-i,a-t),o<=r&&(n=l.body,o=r)))}),n},e.prototype.getState=function(t){var e=this.getFragmentKey(t),r=this.fragments[e],i=l.NOT_LOADED;return void 0!==r&&(i=r.buffered?!0===this.isPartial(r)?l.PARTIAL:l.OK:l.APPENDING),i},e.prototype.isPartial=function(t){return!0===t.buffered&&(void 0!==t.range.video&&!0===t.range.video.partial||void 0!==t.range.audio&&!0===t.range.audio.partial)},e.prototype.isTimeBuffered=function(t,e,r){for(var i=void 0,a=void 0,n=0;n=i&&e<=a)return!0;if(e<=i)return!1}return!1},e.prototype.onFragLoaded=function(t){var e=t.frag;if(!isNaN(e.sn)&&!e.bitrateTest){var r=this.getFragmentKey(e),i={body:e,range:Object.create(null),buffered:!1};this.fragments[r]=i}},e.prototype.onBufferAppended=function(t){var e=this;this.timeRanges=t.timeRanges,Object.keys(this.timeRanges).forEach(function(t){var r=e.timeRanges[t];e.detectEvictedFragments(t,r)})},e.prototype.onFragBuffered=function(t){this.detectPartialFragments(t.frag)},e.prototype.hasFragment=function(t){var e=this.getFragmentKey(t);return void 0!==this.fragments[e]},e.prototype.removeFragment=function(t){var e=this.getFragmentKey(t);delete this.fragments[e]},e.prototype.removeAllFragments=function(){this.fragments=Object.create(null)},e}(o.a)},function(t,e,r){"use strict";function i(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}r.d(e,"a",function(){return a});var a=function(){function t(){i(this,t)}return t.isBuffered=function(t,e){try{if(t)for(var r=t.buffered,i=0;i=r.start(i)&&e<=r.end(i))return!0}catch(t){}return!1},t.bufferInfo=function(t,e,r){try{if(t){var i=t.buffered,a=[],n=void 0;for(n=0;nd&&(i[u-1].end=t[l].end):i.push(t[l])}else i.push(t[l])}for(l=0,a=0,n=o=e;l=c&&e0&&this._events[t].length>a&&(this._events[t].warned=!0,console.error("(node) warning: possible EventEmitter memory leak detected. %d listeners added. Use emitter.setMaxListeners() to increase limit.",this._events[t].length),"function"==typeof console.trace&&console.trace()),this},r.prototype.on=r.prototype.addListener,r.prototype.once=function(t,e){function r(){this.removeListener(t,r),a||(a=!0,e.apply(this,arguments))}if(!i(e))throw TypeError("listener must be a function");var a=!1;return r.listener=e,this.on(t,r),this},r.prototype.removeListener=function(t,e){var r,a,o,s;if(!i(e))throw TypeError("listener must be a function");if(!this._events||!this._events[t])return this;if(r=this._events[t],o=r.length,a=-1,r===e||i(r.listener)&&r.listener===e)delete this._events[t],this._events.removeListener&&this.emit("removeListener",t,e);else if(n(r)){for(s=o;s-- >0;)if(r[s]===e||r[s].listener&&r[s].listener===e){a=s;break}if(a<0)return this;1===r.length?(r.length=0,delete this._events[t]):r.splice(a,1),this._events.removeListener&&this.emit("removeListener",t,e)}return this},r.prototype.removeAllListeners=function(t){var e,r;if(!this._events)return this;if(!this._events.removeListener)return 0===arguments.length?this._events={}:this._events[t]&&delete this._events[t],this;if(0===arguments.length){for(e in this._events)"removeListener"!==e&&this.removeAllListeners(e);return this.removeAllListeners("removeListener"),this._events={},this}if(r=this._events[t],i(r))this.removeListener(t,r);else if(r)for(;r.length;)this.removeListener(t,r[r.length-1]);return delete this._events[t],this},r.prototype.listeners=function(t){return this._events&&this._events[t]?i(this._events[t])?[this._events[t]]:this._events[t].slice():[]},r.prototype.listenerCount=function(t){if(this._events){var e=this._events[t];if(i(e))return 1;if(e)return e.length}return 0},r.listenerCount=function(t,e){return t.listenerCount(e)}},function(t,e,r){"use strict";function i(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}var a=r(35),n=r(36),o=r(37),s=r(2),l=r(0),u=r(1),d=r(4),c=Object(d.a)(),h=function(){function t(e,r){var a=arguments.length>2&&void 0!==arguments[2]?arguments[2]:{},n=a.removePKCS7Padding,o=void 0===n||n;if(i(this,t),this.logEnabled=!0,this.observer=e,this.config=r,this.removePKCS7Padding=o,o)try{var s=c.crypto;s&&(this.subtle=s.subtle||s.webkitSubtle)}catch(t){}this.disableWebCrypto=!this.subtle}return t.prototype.isSync=function(){return this.disableWebCrypto&&this.config.enableSoftwareAES},t.prototype.decrypt=function(t,e,r,i){var s=this;if(this.disableWebCrypto&&this.config.enableSoftwareAES){this.logEnabled&&(l.b.log("JS AES decrypt"),this.logEnabled=!1);var u=this.decryptor;u||(this.decryptor=u=new o.a),u.expandKey(e),i(u.decrypt(t,0,r,this.removePKCS7Padding))}else{this.logEnabled&&(l.b.log("WebCrypto AES decrypt"),this.logEnabled=!1);var d=this.subtle;this.key!==e&&(this.key=e,this.fastAesKey=new n.a(d,e)),this.fastAesKey.expandKey().then(function(n){new a.a(d,r).decrypt(t,n).catch(function(a){s.onWebCryptoError(a,t,e,r,i)}).then(function(t){i(t)})}).catch(function(a){s.onWebCryptoError(a,t,e,r,i)})}},t.prototype.onWebCryptoError=function(t,e,r,i,a){this.config.enableSoftwareAES?(l.b.log("WebCrypto Error, disable WebCrypto API"),this.disableWebCrypto=!0,this.logEnabled=!0,this.decrypt(e,r,i,a)):(l.b.error("decrypting error : "+t.message),this.observer.trigger(u.a.ERROR,{type:s.b.MEDIA_ERROR,details:s.a.FRAG_DECRYPT_ERROR,fatal:!0,reason:t.message}))},t.prototype.destroy=function(){var t=this.decryptor;t&&(t.destroy(),this.decryptor=void 0)},t}();e.a=h},function(t,e,r){"use strict";function i(){if("undefined"!=typeof window)return window.MediaSource||window.WebKitMediaSource}e.a=i},function(t,e,r){"use strict";function i(t,e,r){switch(e){case"audio":t.audioGroupIds||(t.audioGroupIds=[]),t.audioGroupIds.push(r);break;case"text":t.textGroupIds||(t.textGroupIds=[]),t.textGroupIds.push(r)}}function a(t,e,r){var i=t[e],a=t[r],n=a.startPTS;isNaN(n)?a.start=r>e?i.start+i.duration:Math.max(i.start-a.duration,0):r>e?(i.duration=n-i.start,i.duration<0&&s.b.warn("negative duration computed for frag "+i.sn+",level "+i.level+", there should be some duration drift between playlist and fragment!")):(a.duration=i.start-n,a.duration<0&&s.b.warn("negative duration computed for frag "+a.sn+",level "+a.level+", there should be some duration drift between playlist and fragment!"))}function n(t,e,r,i,n,o){var s=r;if(!isNaN(e.startPTS)){var l=Math.abs(e.startPTS-r);isNaN(e.deltaPTS)?e.deltaPTS=l:e.deltaPTS=Math.max(l,e.deltaPTS),s=Math.max(r,e.startPTS),r=Math.min(r,e.startPTS),i=Math.max(i,e.endPTS),n=Math.min(n,e.startDTS),o=Math.max(o,e.endDTS)}var u=r-e.start;e.start=e.startPTS=r,e.maxStartPTS=s,e.endPTS=i,e.startDTS=n,e.endDTS=o,e.duration=i-r;var d=e.sn;if(!t||dt.endSN)return 0;var c=void 0,h=void 0,f=void 0;for(c=d-t.startSN,h=t.fragments,h[c]=e,f=c;f>0;f--)a(h,f,f-1);for(f=c;f=0&&a3&&void 0!==arguments[3]?arguments[3]:null;if(r.isSidxRequest)return this._handleSidxRequest(t,r),void this._handlePlaylistLoaded(t,e,r,i);this.resetInternalLoader(r.type);var a=t.data;if(e.tload=p.now(),0!==a.indexOf("#EXTM3U"))return void this._handleManifestParsingError(t,r,"no EXTM3U delimiter",i);a.indexOf("#EXTINF:")>0||a.indexOf("#EXT-X-TARGETDURATION:")>0?this._handleTrackOrLevelPlaylist(t,e,r,i):this._handleMasterPlaylist(t,e,r,i)},e.prototype.loaderror=function(t,e){var r=arguments.length>2&&void 0!==arguments[2]?arguments[2]:null;this._handleNetworkError(e,r)},e.prototype.loadtimeout=function(t,e){var r=arguments.length>2&&void 0!==arguments[2]?arguments[2]:null;this._handleNetworkError(e,r,!0)},e.prototype._handleMasterPlaylist=function(t,r,i,a){var n=this.hls,s=t.data,l=e.getResponseUrl(t,i),d=c.a.parseMasterPlaylist(s,l);if(!d.length)return void this._handleManifestParsingError(t,i,"no level found in manifest",a);var h=d.map(function(t){return{id:t.attrs.AUDIO,codec:t.audioCodec}}),f=c.a.parseMasterPlaylistMedia(s,l,"AUDIO",h),p=c.a.parseMasterPlaylistMedia(s,l,"SUBTITLES");if(f.length){var v=!1;f.forEach(function(t){t.url||(v=!0)}),!1===v&&d[0].audioCodec&&!d[0].attrs.AUDIO&&(u.b.log("audio codec signaled in quality level, but no embedded audio track signaled, create one"),f.unshift({type:"main",name:"main"}))}n.trigger(o.a.MANIFEST_LOADED,{levels:d,audioTracks:f,subtitles:p,url:l,stats:r,networkDetails:a})},e.prototype._handleTrackOrLevelPlaylist=function(t,r,i,a){var n=this.hls,s=i.id,l=i.level,u=i.type,d=e.getResponseUrl(t,i),h=isNaN(s)?0:s,f=isNaN(l)?h:l,g=e.mapContextToLevelType(i),y=c.a.parseLevelPlaylist(t.data,d,f,g,h);if(y.tload=r.tload,u===v.MANIFEST){var m={url:d,details:y};n.trigger(o.a.MANIFEST_LOADED,{levels:[m],audioTracks:[],url:d,stats:r,networkDetails:a})}if(r.tparsed=p.now(),y.needSidxRanges){var b=y.initSegment.url;return void this.load(b,{isSidxRequest:!0,type:u,level:l,levelDetails:y,id:s,rangeStart:0,rangeEnd:2048,responseType:"arraybuffer"})}i.levelDetails=y,this._handlePlaylistLoaded(t,r,i,a)},e.prototype._handleSidxRequest=function(t,e){var r=d.a.parseSegmentIndex(new Uint8Array(t.data));r.references.forEach(function(t,r){var i=t.info,a=e.levelDetails.fragments[r];0===a.byteRange.length&&(a.rawByteRange=String(1+i.end-i.start)+"@"+String(i.start))}),e.levelDetails.initSegment.rawByteRange=String(r.moovEndOffset)+"@0"},e.prototype._handleManifestParsingError=function(t,e,r,i){this.hls.trigger(o.a.ERROR,{type:l.b.NETWORK_ERROR,details:l.a.MANIFEST_PARSING_ERROR,fatal:!0,url:t.url,reason:r,networkDetails:i})},e.prototype._handleNetworkError=function(t,e){var r=arguments.length>2&&void 0!==arguments[2]&&arguments[2];u.b.info("A network error occured while loading a "+t.type+"-type playlist");var i=void 0,a=void 0,n=this.getInternalLoader(t);switch(t.type){case v.MANIFEST:i=r?l.a.MANIFEST_LOAD_TIMEOUT:l.a.MANIFEST_LOAD_ERROR,a=!0;break;case v.LEVEL:i=r?l.a.LEVEL_LOAD_TIMEOUT:l.a.LEVEL_LOAD_ERROR,a=!1;break;case v.AUDIO_TRACK:i=r?l.a.AUDIO_TRACK_LOAD_TIMEOUT:l.a.AUDIO_TRACK_LOAD_ERROR,a=!1;break;default:a=!1}n&&(n.abort(),this.resetInternalLoader(t.type)),this.hls.trigger(o.a.ERROR,{type:l.b.NETWORK_ERROR,details:i,fatal:a,url:n.url,loader:n,context:t,networkDetails:e})},e.prototype._handlePlaylistLoaded=function(t,r,i,a){var n=i.type,s=i.level,l=i.id,u=i.levelDetails;if(!u.targetduration)return void this._handleManifestParsingError(t,i,"invalid target duration",a);if(e.canHaveQualityLevels(i.type))this.hls.trigger(o.a.LEVEL_LOADED,{details:u,level:s||0,id:l||0,stats:r,networkDetails:a});else switch(n){case v.AUDIO_TRACK:this.hls.trigger(o.a.AUDIO_TRACK_LOADED,{details:u,id:l,stats:r,networkDetails:a});break;case v.SUBTITLE_TRACK:this.hls.trigger(o.a.SUBTITLE_TRACK_LOADED,{details:u,id:l,stats:r,networkDetails:a})}},h(e,null,[{key:"ContextType",get:function(){return v}},{key:"LevelType",get:function(){return g}}]),e}(s.a);e.a=y},function(t,e,r){"use strict";function i(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}var a=r(0),n=r(1),o=Math.pow(2,32)-1,s=function(){function t(e,r){i(this,t),this.observer=e,this.remuxer=r}return t.prototype.resetTimeStamp=function(t){this.initPTS=t},t.prototype.resetInitSegment=function(e,r,i,a){if(e&&e.byteLength){var o=this.initData=t.parseInitSegment(e);null==r&&(r="mp4a.40.5"),null==i&&(i="avc1.42e01e");var s={};o.audio&&o.video?s.audiovideo={container:"video/mp4",codec:r+","+i,initSegment:a?e:null}:(o.audio&&(s.audio={container:"audio/mp4",codec:r,initSegment:a?e:null}),o.video&&(s.video={container:"video/mp4",codec:i,initSegment:a?e:null})),this.observer.trigger(n.a.FRAG_PARSING_INIT_SEGMENT,{tracks:s})}else r&&(this.audioCodec=r),i&&(this.videoCodec=i)},t.probe=function(e){return t.findBox({data:e,start:0,end:Math.min(e.length,16384)},["moof"]).length>0},t.bin2str=function(t){return String.fromCharCode.apply(null,t)},t.readUint16=function(t,e){t.data&&(e+=t.start,t=t.data);var r=t[e]<<8|t[e+1];return r<0?65536+r:r},t.readUint32=function(t,e){t.data&&(e+=t.start,t=t.data);var r=t[e]<<24|t[e+1]<<16|t[e+2]<<8|t[e+3];return r<0?4294967296+r:r},t.writeUint32=function(t,e,r){t.data&&(e+=t.start,t=t.data),t[e]=r>>24,t[e+1]=r>>16&255,t[e+2]=r>>8&255,t[e+3]=255&r},t.findBox=function(e,r){var i=[],a=void 0,n=void 0,o=void 0,s=void 0,l=void 0,u=void 0,d=void 0;if(e.data?(u=e.start,s=e.end,e=e.data):(u=0,s=e.byteLength),!r.length)return null;for(a=u;a1?a+n:s,o===r[0]&&(1===r.length?i.push({data:e,start:a+8,end:d}):(l=t.findBox({data:e,start:a+8,end:d},r.slice(1)),l.length&&(i=i.concat(l)))),a=d;return i},t.parseSegmentIndex=function(e){var r=t.findBox(e,["moov"])[0],i=r?r.end:null,a=0,n=t.findBox(e,["sidx"]),o=void 0;if(!n||!n[0])return null;o=[],n=n[0];var s=n.data[0];a=0===s?8:16;var l=t.readUint32(n,a);a+=4;a+=0===s?8:16,a+=2;var u=n.end+0,d=t.readUint16(n,a);a+=2;for(var c=0;c>>31)return void console.warn("SIDX has hierarchical references (not supported)");var v=t.readUint32(n,h);h+=4,o.push({referenceSize:p,subsegmentDuration:v,info:{duration:v/l,start:u,end:u+p-1}}),u+=p,h+=4,a=h}return{earliestPresentationTime:0,timescale:l,version:s,referencesCount:d,references:o,moovEndOffset:i}},t.parseInitSegment=function(e){var r=[];return t.findBox(e,["moov","trak"]).forEach(function(e){var i=t.findBox(e,["tkhd"])[0];if(i){var n=i.data[i.start],o=0===n?12:20,s=t.readUint32(i,o),l=t.findBox(e,["mdia","mdhd"])[0];if(l){n=l.data[l.start],o=0===n?12:20;var u=t.readUint32(l,o),d=t.findBox(e,["mdia","hdlr"])[0];if(d){var c=t.bin2str(d.data.subarray(d.start+8,d.start+12)),h={soun:"audio",vide:"video"}[c];if(h){var f=t.findBox(e,["mdia","minf","stbl","stsd"]);if(f.length){f=f[0];var p=t.bin2str(f.data.subarray(f.start+12,f.start+16));a.b.log("MP4Demuxer:"+h+":"+p+" found")}r[s]={timescale:u,type:h},r[h]={timescale:u,id:s}}}}}}),r},t.getStartDTS=function(e,r){var i=void 0,a=void 0,n=void 0;return i=t.findBox(r,["moof","traf"]),a=[].concat.apply([],i.map(function(r){return t.findBox(r,["tfhd"]).map(function(i){var a=void 0,n=void 0;return a=t.readUint32(i,4),n=e[a].timescale||9e4,t.findBox(r,["tfdt"]).map(function(e){var r=void 0,i=void 0;return r=e.data[e.start],i=t.readUint32(e,4),1===r&&(i*=Math.pow(2,32),i+=t.readUint32(e,8)),i})[0]/n})})),n=Math.min.apply(null,a),isFinite(n)?n:0},t.offsetStartDTS=function(e,r,i){t.findBox(r,["moof","traf"]).map(function(r){return t.findBox(r,["tfhd"]).map(function(a){var n=t.readUint32(a,4),s=e[n].timescale||9e4;t.findBox(r,["tfdt"]).map(function(e){var r=e.data[e.start],a=t.readUint32(e,4);if(0===r)t.writeUint32(e,4,a-i*s);else{a*=Math.pow(2,32),a+=t.readUint32(e,8),a-=i*s,a=Math.max(a,0);var n=Math.floor(a/(o+1)),l=Math.floor(a%(o+1));t.writeUint32(e,4,n),t.writeUint32(e,8,l)}})})})},t.prototype.append=function(e,r,i,a){var o=this.initData;o||(this.resetInitSegment(e,this.audioCodec,this.videoCodec,!1),o=this.initData);var s=void 0,l=this.initPTS;if(void 0===l){var u=t.getStartDTS(o,e);this.initPTS=l=u-r,this.observer.trigger(n.a.INIT_PTS_FOUND,{initPTS:l})}t.offsetStartDTS(o,e,l),s=t.getStartDTS(o,e),this.remuxer.remux(o.audio,o.video,null,null,s,i,a,e)},t.prototype.destroy=function(){},t}();e.a=s},function(t,e,r){"use strict";function i(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}var a=r(5),n=r.n(a),o=function(){function t(t,e){for(var r=0;r1?e-1:0),i=1;i1?e-1:0),i=1;i0&&null!=e&&null!=e.key&&"AES-128"===e.method){var p=this.decrypter;null==p&&(p=this.decrypter=new o.a(this.observer,this.config));var g=this,y=void 0;try{y=v.now()}catch(t){y=Date.now()}p.decrypt(t,e.key.buffer,e.iv.buffer,function(t){var o=void 0;try{o=v.now()}catch(t){o=Date.now()}g.observer.trigger(a.a.FRAG_DECRYPTED,{stats:{tstart:y,tdecrypt:o}}),g.pushDecrypted(new Uint8Array(t),e,new Uint8Array(r),i,n,s,l,u,d,c,h,f)})}else this.pushDecrypted(new Uint8Array(t),e,new Uint8Array(r),i,n,s,l,u,d,c,h,f)},t.prototype.pushDecrypted=function(t,e,r,i,o,f,p,v,g,y,m,b){var E=this.demuxer;if(!E||(p||v)&&!this.probe(t)){for(var T=this.observer,S=this.typeSupported,R=this.config,A=[{demux:u.a,remux:c.a},{demux:l.a,remux:h.a},{demux:s.a,remux:c.a},{demux:d.a,remux:c.a}],_=0,w=A.length;_>>6),(n=(60&e[r+2])>>>2)>c.length-1?void t.trigger(v.a.ERROR,{type:p.b.MEDIA_ERROR,details:p.a.FRAG_PARSING_ERROR,fatal:!0,reason:"invalid ADTS sampling index:"+n}):(s=(1&e[r+2])<<2,s|=(192&e[r+3])>>>6,f.b.log("manifest codec:"+i+",ADTS data:type:"+a+",sampleingIndex:"+n+"["+c[n]+"Hz],channelConfig:"+s),/firefox/i.test(u)?n>=6?(a=5,l=new Array(4),o=n-3):(a=2,l=new Array(2),o=n):-1!==u.indexOf("android")?(a=2,l=new Array(2),o=n):(a=5,l=new Array(4),i&&(-1!==i.indexOf("mp4a.40.29")||-1!==i.indexOf("mp4a.40.5"))||!i&&n>=6?o=n-3:((i&&-1!==i.indexOf("mp4a.40.2")&&(n>=6&&1===s||/vivaldi/i.test(u))||!i&&1===s)&&(a=2,l=new Array(2)),o=n)),l[0]=a<<3,l[0]|=(14&n)>>1,l[1]|=(1&n)<<7,l[1]|=s<<3,5===a&&(l[1]|=(14&o)>>1,l[2]=(1&o)<<7,l[2]|=8,l[3]=0),{config:l,samplerate:c[n],channelCount:s,codec:"mp4a.40."+a,manifestCodec:d})}function a(t,e){return 255===t[e]&&240==(246&t[e+1])}function n(t,e){return 1&t[e+1]?7:9}function o(t,e){return(3&t[e+3])<<11|t[e+4]<<3|(224&t[e+5])>>>5}function s(t,e){return!!(e+10&&e+s+l<=d)return u=r+i*a,{headerLength:s,frameLength:l,stamp:u}}function h(t,e,r,i,a){var n=d(t.samplerate),o=c(e,r,i,a,n);if(o){var s=o.stamp,l=o.headerLength,u=o.frameLength,h={unit:e.subarray(r+l,r+l+u),pts:s,dts:s};return t.samples.push(h),t.len+=u,{sample:h,length:u+l}}}e.d=s,e.e=l,e.c=u,e.b=d,e.a=h;var f=r(0),p=r(2),v=r(1);r(4)},function(t,e,r){"use strict";var i={BitratesMap:[32,64,96,128,160,192,224,256,288,320,352,384,416,448,32,48,56,64,80,96,112,128,160,192,224,256,320,384,32,40,48,56,64,80,96,112,128,160,192,224,256,320,32,48,56,64,80,96,112,128,144,160,176,192,224,256,8,16,24,32,40,48,56,64,80,96,112,128,144,160],SamplingRateMap:[44100,48e3,32e3,22050,24e3,16e3,11025,12e3,8e3],SamplesCoefficients:[[0,72,144,12],[0,0,0,0],[0,72,144,12],[0,144,144,12]],BytesInSlot:[0,1,1,4],appendFrame:function(t,e,r,i,a){if(!(r+24>e.length)){var n=this.parseHeader(e,r);if(n&&r+n.frameLength<=e.length){var o=9e4*n.samplesPerFrame/n.sampleRate,s=i+a*o,l={unit:e.subarray(r,r+n.frameLength),pts:s,dts:s};return t.config=[],t.channelCount=n.channelCount,t.samplerate=n.sampleRate,t.samples.push(l),t.len+=n.frameLength,{sample:l,length:n.frameLength}}}},parseHeader:function(t,e){var r=t[e+1]>>3&3,a=t[e+1]>>1&3,n=t[e+2]>>4&15,o=t[e+2]>>2&3,s=t[e+2]>>1&1;if(1!==r&&0!==n&&15!==n&&3!==o){var l=3===r?3-a:3===a?3:4,u=1e3*i.BitratesMap[14*l+n-1],d=3===r?0:2===r?1:2,c=i.SamplingRateMap[3*d+o],h=t[e+3]>>6==3?1:2,f=i.SamplesCoefficients[r][a],p=i.BytesInSlot[a],v=8*f*p;return{sampleRate:c,channelCount:h,frameLength:parseInt(f*u/c+s,10)*p,samplesPerFrame:v}}},isHeaderPattern:function(t,e){return 255===t[e]&&224==(224&t[e+1])&&0!=(6&t[e+1])},isHeader:function(t,e){return!!(e+1e?-1:0})}function n(t,e,r){var i=!1;return e&&e.details&&r&&(r.endCC>r.startCC||t&&t.cc0;)t.removeCue(t.cues[0])}e.b=i,e.a=a},function(t,e,r){"use strict";function i(){this.window=window,this.state="INITIAL",this.buffer="",this.decoder=new d,this.regionList=[]}function a(t){function e(t,e,r,i){return 3600*(0|t)+60*(0|e)+(0|r)+(0|i)/1e3}var r=t.match(/^(\d+):(\d{2})(:\d{2})?\.(\d{3})/);return r?r[3]?e(r[1],r[2],r[3].replace(":",""),r[4]):r[1]>59?e(r[1],r[2],0,r[4]):e(0,r[1],r[2],r[4]):null}function n(){this.values=Object.create(null)}function o(t,e,r,i){var a=i?t.split(i):[t];for(var n in a)if("string"==typeof a[n]){var o=a[n].split(r);if(2===o.length){var s=o[0],l=o[1];e(s,l)}}}function s(t,e,r){function i(){var e=a(t);if(null===e)throw new Error("Malformed timestamp: "+l);return t=t.replace(/^[^\sa-zA-Z-]+/,""),e}function s(){t=t.replace(/^\s+/,"")}var l=t;if(s(),e.startTime=i(),s(),"--\x3e"!==t.substr(0,3))throw new Error("Malformed time stamp (time stamps must be separated by '--\x3e'): "+l);t=t.substr(3),s(),e.endTime=i(),s(),function(t,e){var i=new n;o(t,function(t,e){switch(t){case"region":for(var a=r.length-1;a>=0;a--)if(r[a].id===e){i.set(t,r[a].region);break}break;case"vertical":i.alt(t,e,["rl","lr"]);break;case"line":var n=e.split(","),o=n[0];i.integer(t,o),i.percent(t,o)&&i.set("snapToLines",!1),i.alt(t,o,["auto"]),2===n.length&&i.alt("lineAlign",n[1],["start",h,"end"]);break;case"position":n=e.split(","),i.percent(t,n[0]),2===n.length&&i.alt("positionAlign",n[1],["start",h,"end","line-left","line-right","auto"]);break;case"size":i.percent(t,e);break;case"align":i.alt(t,e,["start",h,"end","left","right"])}},/:/,/\s/),e.region=i.get("region",null),e.vertical=i.get("vertical","");var a=i.get("line","auto");"auto"===a&&-1===c.line&&(a=-1),e.line=a,e.lineAlign=i.get("lineAlign","start"),e.snapToLines=i.get("snapToLines",!0),e.size=i.get("size",100),e.align=i.get("align",h);var s=i.get("position","auto");"auto"===s&&50===c.position&&(s="start"===e.align||"left"===e.align?0:"end"===e.align||"right"===e.align?100:50),e.position=s}(t,e)}function l(t){return t.replace(//gi,"\n")}r.d(e,"b",function(){return l});var u=r(63),d=function(){return{decode:function(t){if(!t)return"";if("string"!=typeof t)throw new Error("Error - expected string data.");return decodeURIComponent(encodeURIComponent(t))}}};n.prototype={set:function(t,e){this.get(t)||""===e||(this.values[t]=e)},get:function(t,e,r){return r?this.has(t)?this.values[t]:e[r]:this.has(t)?this.values[t]:e},has:function(t){return t in this.values},alt:function(t,e,r){for(var i=0;i=0&&e<=100)&&(this.set(t,e),!0)}};var c=new u.a(0,0,0),h="middle"===c.align?"middle":"center";i.prototype={parse:function(t){function e(){var t=r.buffer,e=0;for(t=l(t);e0&&void 0!==arguments[0]?arguments[0]:{};i(this,t);var a=t.DefaultConfig;if((r.liveSyncDurationCount||r.liveMaxLatencyDurationCount)&&(r.liveSyncDuration||r.liveMaxLatencyDuration))throw new Error("Illegal hls.js config: don't mix up liveSyncDurationCount/liveMaxLatencyDurationCount and liveSyncDuration/liveMaxLatencyDuration");for(var n in a)n in r||(r[n]=a[n]);if(void 0!==r.liveMaxLatencyDurationCount&&r.liveMaxLatencyDurationCount<=r.liveSyncDurationCount)throw new Error('Illegal hls.js config: "liveMaxLatencyDurationCount" must be gt "liveSyncDurationCount"');if(void 0!==r.liveMaxLatencyDuration&&(r.liveMaxLatencyDuration<=r.liveSyncDuration||void 0===r.liveSyncDuration))throw new Error('Illegal hls.js config: "liveMaxLatencyDuration" must be gt "liveSyncDuration"');Object(v.a)(r.debug),this.config=r,this._autoLevelCapping=-1;var o=this.observer=new b.a;o.trigger=function(t){for(var e=arguments.length,r=Array(e>1?e-1:0),i=1;i1?e-1:0),i=1;i0&&void 0!==arguments[0]?arguments[0]:-1;v.b.log("startLoad("+t+")"),this.networkControllers.forEach(function(e){e.startLoad(t)})},t.prototype.stopLoad=function(){v.b.log("stopLoad"),this.networkControllers.forEach(function(t){t.stopLoad()})},t.prototype.swapAudioCodec=function(){v.b.log("swapAudioCodec"),this.streamController.swapAudioCodec()},t.prototype.recoverMediaError=function(){v.b.log("recoverMediaError");var t=this.media;this.detachMedia(),this.attachMedia(t)},E(t,[{key:"levels",get:function(){return this.levelController.levels}},{key:"currentLevel",get:function(){return this.streamController.currentLevel},set:function(t){v.b.log("set currentLevel:"+t),this.loadLevel=t,this.streamController.immediateLevelSwitch()}},{key:"nextLevel",get:function(){return this.streamController.nextLevel},set:function(t){v.b.log("set nextLevel:"+t),this.levelController.manualLevel=t,this.streamController.nextLevelSwitch()}},{key:"loadLevel",get:function(){return this.levelController.level},set:function(t){v.b.log("set loadLevel:"+t),this.levelController.manualLevel=t}},{key:"nextLoadLevel",get:function(){return this.levelController.nextLoadLevel},set:function(t){this.levelController.nextLoadLevel=t}},{key:"firstLevel",get:function(){return Math.max(this.levelController.firstLevel,this.minAutoLevel)},set:function(t){v.b.log("set firstLevel:"+t),this.levelController.firstLevel=t}},{key:"startLevel",get:function(){return this.levelController.startLevel},set:function(t){v.b.log("set startLevel:"+t);var e=this;-1!==t&&(t=Math.max(t,e.minAutoLevel)),e.levelController.startLevel=t}},{key:"autoLevelCapping",get:function(){return this._autoLevelCapping},set:function(t){v.b.log("set autoLevelCapping:"+t),this._autoLevelCapping=t}},{key:"autoLevelEnabled",get:function(){return-1===this.levelController.manualLevel}},{key:"manualLevel",get:function(){return this.levelController.manualLevel}},{key:"minAutoLevel",get:function(){for(var t=this,e=t.levels,r=t.config.minAutoBitrate,i=e?e.length:0,a=0;ar)return a}return 0}},{key:"maxAutoLevel",get:function(){var t=this,e=t.levels,r=t.autoLevelCapping;return-1===r&&e&&e.length?e.length-1:r}},{key:"nextAutoLevel",get:function(){var t=this;return Math.min(Math.max(t.abrController.nextAutoLevel,t.minAutoLevel),t.maxAutoLevel)},set:function(t){var e=this;e.abrController.nextAutoLevel=Math.max(e.minAutoLevel,t)}},{key:"audioTracks",get:function(){var t=this.audioTrackController;return t?t.audioTracks:[]}},{key:"audioTrack",get:function(){var t=this.audioTrackController;return t?t.audioTrack:-1},set:function(t){var e=this.audioTrackController;e&&(e.audioTrack=t)}},{key:"liveSyncPosition",get:function(){return this.streamController.liveSyncPosition}},{key:"subtitleTracks",get:function(){var t=this.subtitleTrackController;return t?t.subtitleTracks:[]}},{key:"subtitleTrack",get:function(){var t=this.subtitleTrackController;return t?t.subtitleTrack:-1},set:function(t){var e=this.subtitleTrackController;e&&(e.subtitleTrack=t)}},{key:"subtitleDisplay",get:function(){var t=this.subtitleTrackController;return!!t&&t.subtitleDisplay},set:function(t){var e=this.subtitleTrackController;e&&(e.subtitleDisplay=t)}}]),t}();e.default=T},function(t,e,r){"use strict";function i(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}var a=r(5),n=r.n(a),o=r(9),s=r(18),l=r(30),u=r(0),d=r(19),c=/#EXT-X-STREAM-INF:([^\n\r]*)[\r\n]+([^\r\n]+)/g,h=/#EXT-X-MEDIA:(.*)/g,f=new RegExp([/#EXTINF:\s*(\d*(?:\.\d+)?)(?:,(.*)\s+)?/.source,/|(?!#)(\S+)/.source,/|#EXT-X-BYTERANGE:*(.+)/.source,/|#EXT-X-PROGRAM-DATE-TIME:(.+)/.source,/|#.*/.source].join(""),"g"),p=/(?:(?:#(EXTM3U))|(?:#EXT-X-(PLAYLIST-TYPE):(.+))|(?:#EXT-X-(MEDIA-SEQUENCE): *(\d+))|(?:#EXT-X-(TARGETDURATION): *(\d+))|(?:#EXT-X-(KEY):(.+))|(?:#EXT-X-(START):(.+))|(?:#EXT-X-(ENDLIST))|(?:#EXT-X-(DISCONTINUITY-SEQ)UENCE:(\d+))|(?:#EXT-X-(DIS)CONTINUITY))|(?:#EXT-X-(VERSION):(\d+))|(?:#EXT-X-(MAP):(.+))|(?:(#)(.*):(.*))|(?:(#)(.*))(?:.*)\r?\n?/,v=/\.(mp4|m4s|m4v|m4a)$/i,g=function(){function t(){i(this,t)}return t.findGroup=function(t,e){if(!t)return null;for(var r=null,i=0;i2?(e=r.shift()+".",e+=parseInt(r.shift()).toString(16),e+=("000"+parseInt(r.shift()).toString(16)).substr(-4)):e=t,e},t.resolve=function(t,e){return n.a.buildAbsoluteURL(e,t,{alwaysNormalize:!0})},t.parseMasterPlaylist=function(e,r){var i=[],a=void 0;for(c.lastIndex=0;null!=(a=c.exec(e));){var n={},o=n.attrs=new l.a(a[1]);n.url=t.resolve(a[2],r);var s=o.decimalResolution("RESOLUTION");s&&(n.width=s.width,n.height=s.height),n.bitrate=o.decimalInteger("AVERAGE-BANDWIDTH")||o.decimalInteger("BANDWIDTH"),n.name=o.NAME,function(t,e){["video","audio"].forEach(function(r){var i=t.filter(function(t){return Object(d.b)(t,r)});if(i.length){var a=i.filter(function(t){return 0===t.lastIndexOf("avc1",0)||0===t.lastIndexOf("mp4a",0)});e[r+"Codec"]=a.length>0?a[0]:i[0],t=t.filter(function(t){return-1===i.indexOf(t)})}}),e.unknownCodecs=t}([].concat((o.CODECS||"").split(/[ ,]+/)),n),n.videoCodec&&-1!==n.videoCodec.indexOf("avc1")&&(n.videoCodec=t.convertAVC1ToAVCOTI(n.videoCodec)),i.push(n)}return i},t.parseMasterPlaylistMedia=function(e,r,i){var a=arguments.length>3&&void 0!==arguments[3]?arguments[3]:[],n=void 0,o=[],s=0;for(h.lastIndex=0;null!==(n=h.exec(e));){var u={},d=new l.a(n[1]);if(d.TYPE===i){if(u.groupId=d["GROUP-ID"],u.name=d.NAME,u.type=i,u.default="YES"===d.DEFAULT,u.autoselect="YES"===d.AUTOSELECT,u.forced="YES"===d.FORCED,d.URI&&(u.url=t.resolve(d.URI,r)),u.lang=d.LANGUAGE,u.name||(u.name=u.lang),a.length){var c=t.findGroup(a,u.groupId);u.audioCodec=c?c.codec:a[0].codec}u.id=s++,o.push(u)}}return o},t.parseLevelPlaylist=function(t,e,r,i,a){var n=0,d=0,c={type:null,version:null,url:e,fragments:[],live:!0,startSN:0},h=new s.a,g=0,y=null,m=new o.a,b=void 0,E=void 0;for(f.lastIndex=0;null!==(b=f.exec(t));){var T=b[1];if(T){m.duration=parseFloat(T);var S=(" "+b[2]).slice(1);m.title=S||null,m.tagList.push(S?["INF",T,S]:["INF",T])}else if(b[3]){if(!isNaN(m.duration)){var R=n++;m.type=i,m.start=d,m.levelkey=h,m.sn=R,m.level=r,m.cc=g,m.urlId=a,m.baseurl=e,m.relurl=(" "+b[3]).slice(1),c.programDateTime&&(y?m.rawProgramDateTime?m.pdt=Date.parse(m.rawProgramDateTime):m.pdt=y.pdt+1e3*y.duration:m.pdt=Date.parse(c.programDateTime),m.endPdt=m.pdt+1e3*m.duration),c.fragments.push(m),y=m,d+=m.duration,m=new o.a}}else if(b[4]){if(m.rawByteRange=(" "+b[4]).slice(1),y){var A=y.byteRangeEndOffset;A&&(m.lastByteRangeEndOffset=A)}}else if(b[5])m.rawProgramDateTime=(" "+b[5]).slice(1),m.tagList.push(["PROGRAM-DATE-TIME",m.rawProgramDateTime]),void 0===c.programDateTime&&(c.programDateTime=new Date(new Date(Date.parse(b[5]))-1e3*d));else{for(b=b[0].match(p),E=1;E=0&&(h.method=I,h.baseuri=e,h.reluri=k,h.key=null,h.iv=O));break;case"START":var C=_,P=new l.a(C),x=P.decimalFloatingPoint("TIME-OFFSET");isNaN(x)||(c.startTimeOffset=x);break;case"MAP":var F=new l.a(_);m.relurl=F.URI,m.rawByteRange=F.BYTERANGE,m.baseurl=e,m.level=r,m.type=i,m.sn="initSegment",c.initSegment=m,m=new o.a;break;default:u.b.warn("line parsed but not handled: "+b)}}}return m=y,m&&!m.relurl&&(c.fragments.pop(),d-=m.duration),c.totalduration=d,c.averagetargetduration=d/c.fragments.length,c.endSN=n-1,c.startCC=c.fragments[0]?c.fragments[0].cc:0,c.endCC=g,!c.initSegment&&c.fragments.length&&c.fragments.every(function(t){return v.test(t.relurl)})&&(u.b.warn("MP4 fragments found but no init segment (probably no MAP, incomplete M3U8), trying to fetch SIDX"),m=new o.a,m.relurl=c.fragments[0].relurl,m.baseurl=e,m.level=r,m.type=i,m.sn="initSegment",c.initSegment=m,c.needSidxRanges=!0),c},t}();e.a=g},function(t,e,r){"use strict";function i(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}var a=/^(\d+)x(\d+)$/,n=/\s*(.+?)\s*=((?:\".*?\")|.*?)(?:,|$)/g,o=function(){function t(e){i(this,t),"string"==typeof e&&(e=t.parseAttrList(e));for(var r in e)e.hasOwnProperty(r)&&(this[r]=e[r])}return t.prototype.decimalInteger=function(t){var e=parseInt(this[t],10);return e>Number.MAX_SAFE_INTEGER?1/0:e},t.prototype.hexadecimalInteger=function(t){if(this[t]){var e=(this[t]||"0x").slice(2);e=(1&e.length?"0":"")+e;for(var r=new Uint8Array(e.length/2),i=0;iNumber.MAX_SAFE_INTEGER?1/0:e},t.prototype.decimalFloatingPoint=function(t){return parseFloat(this[t])},t.prototype.enumeratedString=function(t){return this[t]},t.prototype.decimalResolution=function(t){var e=a.exec(this[t]);if(null!==e)return{width:parseInt(e[1],10),height:parseInt(e[2],10)}},t.parseAttrList=function(t){var e=void 0,r={};for(n.lastIndex=0;null!==(e=n.exec(t));){var i=e[2];0===i.indexOf('"')&&i.lastIndexOf('"')===i.length-1&&(i=i.slice(1,-1)),r[e[1]]=i}return r},t}();e.a=o},function(t,e,r){"use strict";function i(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function a(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function n(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}var o=r(1),s=r(3),l=r(2),u=r(0),d=function(t){function e(r){i(this,e);var n=a(this,t.call(this,r,o.a.FRAG_LOADING));return n.loaders={},n}return n(e,t),e.prototype.destroy=function(){var e=this.loaders;for(var r in e){var i=e[r];i&&i.destroy()}this.loaders={},t.prototype.destroy.call(this)},e.prototype.onFragLoading=function(t){var e=t.frag,r=e.type,i=this.loaders,a=this.hls.config,n=a.fLoader,o=a.loader;e.loaded=0;var s=i[r];s&&(u.b.warn("abort previous fragment loader for type: "+r),s.abort()),s=i[r]=e.loader=a.fLoader?new n(a):new o(a);var l=void 0,d=void 0,c=void 0;l={url:e.url,frag:e,responseType:"arraybuffer",progressData:!1};var h=e.byteRangeStartOffset,f=e.byteRangeEndOffset;isNaN(h)||isNaN(f)||(l.rangeStart=h,l.rangeEnd=f),d={timeout:a.fragLoadingTimeOut,maxRetry:0,retryDelay:0,maxRetryDelay:a.fragLoadingMaxRetryTimeout},c={onSuccess:this.loadsuccess.bind(this),onError:this.loaderror.bind(this),onTimeout:this.loadtimeout.bind(this),onProgress:this.loadprogress.bind(this)},s.load(l,d,c)},e.prototype.loadsuccess=function(t,e,r){var i=arguments.length>3&&void 0!==arguments[3]?arguments[3]:null,a=t.data,n=r.frag;n.loader=void 0,this.loaders[n.type]=void 0,this.hls.trigger(o.a.FRAG_LOADED,{payload:a,frag:n,stats:e,networkDetails:i})},e.prototype.loaderror=function(t,e){var r=arguments.length>2&&void 0!==arguments[2]?arguments[2]:null,i=e.loader;i&&i.abort(),this.loaders[e.type]=void 0,this.hls.trigger(o.a.ERROR,{type:l.b.NETWORK_ERROR,details:l.a.FRAG_LOAD_ERROR,fatal:!1,frag:e.frag,response:t,networkDetails:r})},e.prototype.loadtimeout=function(t,e){var r=arguments.length>2&&void 0!==arguments[2]?arguments[2]:null,i=e.loader;i&&i.abort(),this.loaders[e.type]=void 0,this.hls.trigger(o.a.ERROR,{type:l.b.NETWORK_ERROR,details:l.a.FRAG_LOAD_TIMEOUT,fatal:!1,frag:e.frag,networkDetails:r})},e.prototype.loadprogress=function(t,e,r){var i=arguments.length>3&&void 0!==arguments[3]?arguments[3]:null,a=e.frag;a.loaded=t.loaded,this.hls.trigger(o.a.FRAG_LOAD_PROGRESS,{frag:a,stats:t,networkDetails:i})},e}(s.a);e.a=d},function(t,e,r){"use strict";function i(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function a(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function n(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}var o=r(1),s=r(3),l=r(2),u=r(0),d=function(t){function e(r){i(this,e);var n=a(this,t.call(this,r,o.a.KEY_LOADING));return n.loaders={},n.decryptkey=null,n.decrypturl=null,n}return n(e,t),e.prototype.destroy=function(){for(var t in this.loaders){var e=this.loaders[t];e&&e.destroy()}this.loaders={},s.a.prototype.destroy.call(this)},e.prototype.onKeyLoading=function(t){var e=t.frag,r=e.type,i=this.loaders[r],a=e.decryptdata,n=a.uri;if(n!==this.decrypturl||null===this.decryptkey){var s=this.hls.config;i&&(u.b.warn("abort previous key loader for type:"+r),i.abort()),e.loader=this.loaders[r]=new s.loader(s),this.decrypturl=n,this.decryptkey=null;var l=void 0,d=void 0,c=void 0;l={url:n,frag:e,responseType:"arraybuffer"},d={timeout:s.fragLoadingTimeOut,maxRetry:s.fragLoadingMaxRetry,retryDelay:s.fragLoadingRetryDelay,maxRetryDelay:s.fragLoadingMaxRetryTimeout},c={onSuccess:this.loadsuccess.bind(this),onError:this.loaderror.bind(this),onTimeout:this.loadtimeout.bind(this)},e.loader.load(l,d,c)}else this.decryptkey&&(a.key=this.decryptkey,this.hls.trigger(o.a.KEY_LOADED,{frag:e}))},e.prototype.loadsuccess=function(t,e,r){var i=r.frag;this.decryptkey=i.decryptdata.key=new Uint8Array(t.data),i.loader=void 0,this.loaders[i.type]=void 0,this.hls.trigger(o.a.KEY_LOADED,{frag:i})},e.prototype.loaderror=function(t,e){var r=e.frag,i=r.loader;i&&i.abort(),this.loaders[e.type]=void 0,this.hls.trigger(o.a.ERROR,{type:l.b.NETWORK_ERROR,details:l.a.KEY_LOAD_ERROR,fatal:!1,frag:r,response:t})},e.prototype.loadtimeout=function(t,e){var r=e.frag,i=r.loader;i&&i.abort(),this.loaders[e.type]=void 0,this.hls.trigger(o.a.ERROR,{type:l.b.NETWORK_ERROR,details:l.a.KEY_LOAD_TIMEOUT,fatal:!1,frag:r})},e}(s.a);e.a=d},function(t,e,r){"use strict";function i(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function a(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function n(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}var o=r(6),s=r(11),l=r(20),u=r(1),d=r(10),c=r(9),h=r(16),f=r(15),p=r(24),v=r(2),g=r(0),y=r(25),m=r(8),b=r(48),E=function(){function t(t,e){for(var r=0;r0&&-1===t&&(g.b.log("override startPosition with lastCurrentTime @"+e.toFixed(3)),t=e),this.state=T.IDLE,this.nextLoadPosition=this.startPosition=this.lastCurrentTime=t,this.tick()}else this.forceStartLoad=!0,this.state=T.STOPPED},e.prototype.stopLoad=function(){var t=this.fragCurrent;t&&(t.loader&&t.loader.abort(),this.fragmentTracker.removeFragment(t),this.fragCurrent=null),this.fragPrevious=null,this.demuxer&&(this.demuxer.destroy(),this.demuxer=null),this.clearInterval(),this.state=T.STOPPED,this.forceStartLoad=!1},e.prototype.doTick=function(){switch(this.state){case T.BUFFER_FLUSHING:this.fragLoadError=0;break;case T.IDLE:this._doTickIdle();break;case T.WAITING_LEVEL:var t=this.levels[this.level];t&&t.details&&(this.state=T.IDLE);break;case T.FRAG_LOADING_WAITING_RETRY:var e=window.performance.now(),r=this.retryDate;(!r||e>=r||this.media&&this.media.seeking)&&(g.b.log("mediaController: retryDate reached, switch back to IDLE state"),this.state=T.IDLE);break;case T.ERROR:case T.STOPPED:case T.FRAG_LOADING:case T.PARSING:case T.PARSED:case T.ENDED:}this._checkBuffer(),this._checkFragmentChanged()},e.prototype._doTickIdle=function(){var t=this.hls,e=t.config,r=this.media;if(void 0!==this.levelLastLoaded&&(r||!this.startFragRequested&&e.startFragPrefetch)){var i=void 0;i=this.loadedmetadata?r.currentTime:this.nextLoadPosition;var a=t.nextLoadLevel,n=this.levels[a];if(n){var o=n.bitrate,l=void 0;l=o?Math.max(8*e.maxBufferSize/o,e.maxBufferLength):e.maxBufferLength,l=Math.min(l,e.maxMaxBufferLength);var d=s.a.bufferInfo(this.mediaBuffer?this.mediaBuffer:r,i,e.maxBufferHole),c=d.len;if(!(c>=l)){g.b.trace("buffer length of "+c.toFixed(3)+" is below max of "+l.toFixed(3)+". checking for more payload ..."),this.level=t.nextLoadLevel=a;var h=n.details;if(!h||h.live&&this.levelLastLoaded!==a)return void(this.state=T.WAITING_LEVEL);var f=this.fragPrevious;if(!h.live&&f&&!f.backtracked&&f.sn===h.endSN&&!d.nextStart){if(Math.min(r.duration,f.start+f.duration)-Math.max(d.end,f.start)<=Math.max(.2,f.duration)){var p={};return this.altAudio&&(p.type="video"),this.hls.trigger(u.a.BUFFER_EOS,p),void(this.state=T.ENDED)}}this._fetchPayloadOrEos(i,d,h)}}}},e.prototype._fetchPayloadOrEos=function(t,e,r){var i=this.fragPrevious,a=this.level,n=r.fragments,o=n.length;if(0!==o){var s=n[0].start,l=n[o-1].start+n[o-1].duration,u=e.end,d=void 0;if(r.initSegment&&!r.initSegment.data)d=r.initSegment;else if(r.live){var c=this.config.initialLiveManifestSize;if(oh&&(u.currentTime=h),this.nextLoadPosition=h}if(t.PTSKnown&&e>i&&u&&u.readyState)return null;if(this.startFragRequested&&!t.PTSKnown){if(a)if(t.programDateTime)d=Object(b.b)(n,a.endPdt+1);else{var f=a.sn+1;if(f>=t.startSN&&f<=t.endSN){var p=n[f-t.startSN];a.cc===p.cc&&(d=p,g.b.log("live playlist, switching playlist, load frag with next SN: "+d.sn))}d||(d=o.a.search(n,function(t){return a.cc-t.cc}))&&g.b.log("live playlist, switching playlist, load frag with same CC: "+d.sn)}d||(d=n[Math.min(s-1,Math.round(s/2))],g.b.log("live playlist, switching playlist, unknown, load middle frag : "+d.sn))}return d},e.prototype._findFragment=function(t,e,r,i,a,n,o){var s=this.hls.config,l=void 0,u=void 0;if(as.maxBufferHole&&e.dropped&&d?(l=h,g.b.warn("SN just loaded, with large PTS gap between audio and video, maybe frag is not starting with a keyframe ? load previous one to try to overcome this")):(l=f,g.b.log("SN just loaded, load next one: "+l.sn))}else l=null;else l.backtracked&&(f&&f.backtracked?(g.b.warn("Already backtracked from fragment "+f.sn+", will not backtrack to fragment "+l.sn+". Loading fragment "+f.sn),l=f):(g.b.warn("Loaded fragment with dropped frames, backtracking 1 segment to find a keyframe"),l.dropped=0,h?(l=h,l.backtracked=!0):d&&(l=null)))}return l},e.prototype._loadKey=function(t){this.state=T.KEY_LOADING,this.hls.trigger(u.a.KEY_LOADING,{frag:t})},e.prototype._loadFragment=function(t){var e=this.fragmentTracker.getState(t);this.fragCurrent=t,this.startFragRequested=!0,isNaN(t.sn)||t.bitrateTest||(this.nextLoadPosition=t.start+t.duration),t.backtracked||e===d.a.NOT_LOADED||e===d.a.PARTIAL?(t.autoLevel=this.hls.autoLevelEnabled,t.bitrateTest=this.bitrateTest,this.hls.trigger(u.a.FRAG_LOADING,{frag:t}),this.demuxer||(this.demuxer=new l.a(this.hls,"main")),this.state=T.FRAG_LOADING):e===d.a.APPENDING&&this._reduceMaxBufferLength(t.duration)&&this.fragmentTracker.removeFragment(t)},e.prototype.getBufferedFrag=function(t){return this.fragmentTracker.getBufferedFrag(t,h.a.LevelType.MAIN)},e.prototype.followingBufferedFrag=function(t){return t?this.getBufferedFrag(t.endPTS+.5):null},e.prototype._checkFragmentChanged=function(){var t=void 0,e=void 0,r=this.media;if(r&&r.readyState&&!1===r.seeking&&(e=r.currentTime,e>this.lastCurrentTime&&(this.lastCurrentTime=e),s.a.isBuffered(r,e)?t=this.getBufferedFrag(e):s.a.isBuffered(r,e+.1)&&(t=this.getBufferedFrag(e+.1)),t)){var i=t;if(i!==this.fragPlaying){this.hls.trigger(u.a.FRAG_CHANGED,{frag:i});var a=i.level;this.fragPlaying&&this.fragPlaying.level===a||this.hls.trigger(u.a.LEVEL_SWITCHED,{level:a}),this.fragPlaying=i}}},e.prototype.immediateLevelSwitch=function(){if(g.b.log("immediateLevelSwitch"),!this.immediateSwitch){this.immediateSwitch=!0;var t=this.media,e=void 0;t?(e=t.paused,t.pause()):e=!0,this.previouslyPaused=e}var r=this.fragCurrent;r&&r.loader&&r.loader.abort(),this.fragCurrent=null,this.flushMainBuffer(0,Number.POSITIVE_INFINITY)},e.prototype.immediateLevelSwitchEnd=function(){var t=this.media;t&&t.buffered.length&&(this.immediateSwitch=!1,s.a.isBuffered(t,t.currentTime)&&(t.currentTime-=1e-4),this.previouslyPaused||t.play())},e.prototype.nextLevelSwitch=function(){var t=this.media;if(t&&t.readyState){var e=void 0,r=void 0,i=void 0;if(r=this.getBufferedFrag(t.currentTime),r&&r.startPTS>1&&this.flushMainBuffer(0,r.startPTS-1),t.paused)e=0;else{var a=this.hls.nextLoadLevel,n=this.levels[a],o=this.fragLastKbps;e=o&&this.fragCurrent?this.fragCurrent.duration*n.bitrate/(1e3*o)+1:0}if((i=this.getBufferedFrag(t.currentTime+e))&&(i=this.followingBufferedFrag(i))){var s=this.fragCurrent;s&&s.loader&&s.loader.abort(),this.fragCurrent=null,this.flushMainBuffer(i.maxStartPTS,Number.POSITIVE_INFINITY)}}},e.prototype.flushMainBuffer=function(t,e){this.state=T.BUFFER_FLUSHING;var r={startOffset:t,endOffset:e};this.altAudio&&(r.type="video"),this.hls.trigger(u.a.BUFFER_FLUSHING,r)},e.prototype.onMediaAttached=function(t){var e=this.media=this.mediaBuffer=t.media;this.onvseeking=this.onMediaSeeking.bind(this),this.onvseeked=this.onMediaSeeked.bind(this),this.onvended=this.onMediaEnded.bind(this),e.addEventListener("seeking",this.onvseeking),e.addEventListener("seeked",this.onvseeked),e.addEventListener("ended",this.onvended);var r=this.config;this.levels&&r.autoStartLoad&&this.hls.startLoad(r.startPosition)},e.prototype.onMediaDetaching=function(){var t=this.media;t&&t.ended&&(g.b.log("MSE detaching and video ended, reset startPosition"),this.startPosition=this.lastCurrentTime=0);var e=this.levels;e&&e.forEach(function(t){t.details&&t.details.fragments.forEach(function(t){t.backtracked=void 0})}),t&&(t.removeEventListener("seeking",this.onvseeking),t.removeEventListener("seeked",this.onvseeked),t.removeEventListener("ended",this.onvended),this.onvseeking=this.onvseeked=this.onvended=null),this.media=this.mediaBuffer=null,this.loadedmetadata=!1,this.stopLoad()},e.prototype.onMediaSeeking=function(){var t=this.media,e=t?t.currentTime:void 0,r=this.config;isNaN(e)||g.b.log("media seeking to "+e.toFixed(3));var i=this.mediaBuffer?this.mediaBuffer:t,a=s.a.bufferInfo(i,e,this.config.maxBufferHole);if(this.state===T.FRAG_LOADING){var n=this.fragCurrent;if(0===a.len&&n){var o=r.maxFragLookUpTolerance,l=n.start-o,u=n.start+n.duration+o;eu?(n.loader&&(g.b.log("seeking outside of buffer while fragment load in progress, cancel fragment load"),n.loader.abort()),this.fragCurrent=null,this.fragPrevious=null,this.state=T.IDLE):g.b.log("seeking outside of buffer but within currently loaded fragment range")}}else this.state===T.ENDED&&(0===a.len&&(this.fragPrevious=0),this.state=T.IDLE);t&&(this.lastCurrentTime=e),this.loadedmetadata||(this.nextLoadPosition=this.startPosition=e),this.tick()},e.prototype.onMediaSeeked=function(){var t=this.media,e=t?t.currentTime:void 0;isNaN(e)||g.b.log("media seeked to "+e.toFixed(3)),this.tick()},e.prototype.onMediaEnded=function(){g.b.log("media ended"),this.startPosition=this.lastCurrentTime=0},e.prototype.onManifestLoading=function(){g.b.log("trigger BUFFER_RESET"),this.hls.trigger(u.a.BUFFER_RESET),this.fragmentTracker.removeAllFragments(),this.stalled=!1,this.startPosition=this.lastCurrentTime=0},e.prototype.onManifestParsed=function(t){var e=!1,r=!1,i=void 0;t.levels.forEach(function(t){(i=t.audioCodec)&&(-1!==i.indexOf("mp4a.40.2")&&(e=!0),-1!==i.indexOf("mp4a.40.5")&&(r=!0))}),this.audioCodecSwitch=e&&r,this.audioCodecSwitch&&g.b.log("both AAC/HE-AAC audio found in levels; declaring level codec as HE-AAC"),this.levels=t.levels,this.startFragRequested=!1;var a=this.config;(a.autoStartLoad||this.forceStartLoad)&&this.hls.startLoad(a.startPosition)},e.prototype.onLevelLoaded=function(t){var e=t.details,r=t.level,i=this.levels[this.levelLastLoaded],a=this.levels[r],n=e.totalduration,o=0;if(g.b.log("level "+r+" loaded ["+e.startSN+","+e.endSN+"],duration:"+n),e.live){var s=a.details;s&&e.fragments.length>0?(f.b(s,e),o=e.fragments[0].start,this.liveSyncPosition=this.computeLivePosition(o,s),e.PTSKnown&&!isNaN(o)?g.b.log("live playlist sliding:"+o.toFixed(3)):(g.b.log("live playlist - outdated PTS, unknown sliding"),Object(y.a)(this.fragPrevious,i,e))):(g.b.log("live playlist - first load, unknown sliding"),e.PTSKnown=!1,Object(y.a)(this.fragPrevious,i,e))}else e.PTSKnown=!1;if(a.details=e,this.levelLastLoaded=r,this.hls.trigger(u.a.LEVEL_UPDATED,{details:e,level:r}),!1===this.startFragRequested){if(-1===this.startPosition||-1===this.lastCurrentTime){var l=e.startTimeOffset;isNaN(l)?e.live?(this.startPosition=this.computeLivePosition(o,e),g.b.log("configure startPosition to "+this.startPosition)):this.startPosition=0:(l<0&&(g.b.log("negative start time offset "+l+", count from end of last fragment"),l=o+n+l),g.b.log("start time offset found in playlist, adjust startPosition to "+l),this.startPosition=l),this.lastCurrentTime=this.startPosition}this.nextLoadPosition=this.startPosition}this.state===T.WAITING_LEVEL&&(this.state=T.IDLE),this.tick()},e.prototype.onKeyLoaded=function(){this.state===T.KEY_LOADING&&(this.state=T.IDLE,this.tick())},e.prototype.onFragLoaded=function(t){var e=this.fragCurrent,r=t.frag;if(this.state===T.FRAG_LOADING&&e&&"main"===r.type&&r.level===e.level&&r.sn===e.sn){var i=t.stats,a=this.levels[e.level],n=a.details;if(g.b.log("Loaded "+e.sn+" of ["+n.startSN+" ,"+n.endSN+"],level "+e.level),this.bitrateTest=!1,this.stats=i,!0===r.bitrateTest&&this.hls.nextLoadLevel)this.state=T.IDLE,this.startFragRequested=!1,i.tparsed=i.tbuffered=window.performance.now(),this.hls.trigger(u.a.FRAG_BUFFERED,{stats:i,frag:e,id:"main"}),this.tick();else if("initSegment"===r.sn)this.state=T.IDLE,i.tparsed=i.tbuffered=window.performance.now(),n.initSegment.data=t.payload,this.hls.trigger(u.a.FRAG_BUFFERED,{stats:i,frag:e,id:"main"}),this.tick();else{this.state=T.PARSING;var o=n.totalduration,s=e.level,d=e.sn,c=this.config.defaultAudioCodec||a.audioCodec;this.audioCodecSwap&&(g.b.log("swapping playlist audio codec"),void 0===c&&(c=this.lastAudioCodec),c&&(c=-1!==c.indexOf("mp4a.40.5")?"mp4a.40.2":"mp4a.40.5")),this.pendingBuffering=!0,this.appended=!1,g.b.log("Parsing "+d+" of ["+n.startSN+" ,"+n.endSN+"],level "+s+", cc "+e.cc);var h=this.demuxer;h||(h=this.demuxer=new l.a(this.hls,"main"));var f=this.media,p=f&&f.seeking,v=!p&&(n.PTSKnown||!n.live),y=n.initSegment?n.initSegment.data:[];h.push(t.payload,y,c,a.videoCodec,e,o,v,void 0)}}this.fragLoadError=0},e.prototype.onFragParsingInitSegment=function(t){var e=this.fragCurrent,r=t.frag;if(e&&"main"===t.id&&r.sn===e.sn&&r.level===e.level&&this.state===T.PARSING){var i=t.tracks,a=void 0,n=void 0;if(i.audio&&this.altAudio&&delete i.audio,n=i.audio){var o=this.levels[this.level].audioCodec,s=navigator.userAgent.toLowerCase();o&&this.audioCodecSwap&&(g.b.log("swapping playlist audio codec"),o=-1!==o.indexOf("mp4a.40.5")?"mp4a.40.2":"mp4a.40.5"),this.audioCodecSwitch&&1!==n.metadata.channelCount&&-1===s.indexOf("firefox")&&(o="mp4a.40.5"),-1!==s.indexOf("android")&&"audio/mpeg"!==n.container&&(o="mp4a.40.2",g.b.log("Android: force audio codec to "+o)),n.levelCodec=o,n.id=t.id}n=i.video,n&&(n.levelCodec=this.levels[this.level].videoCodec,n.id=t.id),this.hls.trigger(u.a.BUFFER_CODECS,i);for(a in i){n=i[a],g.b.log("main track:"+a+",container:"+n.container+",codecs[level/parsed]=["+n.levelCodec+"/"+n.codec+"]");var l=n.initSegment;l&&(this.appended=!0,this.pendingBuffering=!0,this.hls.trigger(u.a.BUFFER_APPENDING,{type:a,data:l,parent:"main",content:"initSegment"}))}this.tick()}},e.prototype.onFragParsingData=function(t){var e=this,r=this.fragCurrent,i=t.frag;if(r&&"main"===t.id&&i.sn===r.sn&&i.level===r.level&&("audio"!==t.type||!this.altAudio)&&this.state===T.PARSING){var a=this.levels[this.level],n=r;if(isNaN(t.endPTS)&&(t.endPTS=t.startPTS+r.duration,t.endDTS=t.startDTS+r.duration),!0===t.hasAudio&&n.addElementaryStream(c.a.ElementaryStreamTypes.AUDIO),!0===t.hasVideo&&n.addElementaryStream(c.a.ElementaryStreamTypes.VIDEO),g.b.log("Parsed "+t.type+",PTS:["+t.startPTS.toFixed(3)+","+t.endPTS.toFixed(3)+"],DTS:["+t.startDTS.toFixed(3)+"/"+t.endDTS.toFixed(3)+"],nb:"+t.nb+",dropped:"+(t.dropped||0)),"video"===t.type)if(n.dropped=t.dropped,n.dropped)if(n.backtracked)g.b.warn("Already backtracked on this fragment, appending with the gap",n.sn);else{var o=a.details;if(!o||n.sn!==o.startSN)return g.b.warn("missing video frame(s), backtracking fragment",n.sn),this.fragmentTracker.removeFragment(n),n.backtracked=!0,this.nextLoadPosition=t.startPTS,this.state=T.IDLE,this.fragPrevious=n,void this.tick();g.b.warn("missing video frame(s) on first frag, appending with gap",n.sn)}else n.backtracked=!1;var s=f.c(a.details,n,t.startPTS,t.endPTS,t.startDTS,t.endDTS),l=this.hls;l.trigger(u.a.LEVEL_PTS_UPDATED,{details:a.details,level:this.level,drift:s,type:t.type,start:t.startPTS,end:t.endPTS}),[t.data1,t.data2].forEach(function(r){r&&r.length&&e.state===T.PARSING&&(e.appended=!0,e.pendingBuffering=!0,l.trigger(u.a.BUFFER_APPENDING,{type:t.type,data:r,parent:"main",content:"data"}))}),this.tick()}},e.prototype.onFragParsed=function(t){var e=this.fragCurrent,r=t.frag;e&&"main"===t.id&&r.sn===e.sn&&r.level===e.level&&this.state===T.PARSING&&(this.stats.tparsed=window.performance.now(),this.state=T.PARSED,this._checkAppendedParsed())},e.prototype.onAudioTrackSwitching=function(t){var e=!!t.url,r=t.id;if(!e){if(this.mediaBuffer!==this.media){g.b.log("switching on main audio, use media.buffered to schedule main fragment loading"),this.mediaBuffer=this.media;var i=this.fragCurrent;i.loader&&(g.b.log("switching to main audio track, cancel main fragment load"),i.loader.abort()),this.fragCurrent=null,this.fragPrevious=null,this.demuxer&&(this.demuxer.destroy(),this.demuxer=null),this.state=T.IDLE}var a=this.hls;a.trigger(u.a.BUFFER_FLUSHING,{startOffset:0,endOffset:Number.POSITIVE_INFINITY,type:"audio"}),a.trigger(u.a.AUDIO_TRACK_SWITCHED,{id:r}),this.altAudio=!1}},e.prototype.onAudioTrackSwitched=function(t){var e=t.id,r=!!this.hls.audioTracks[e].url;if(r){var i=this.videoBuffer;i&&this.mediaBuffer!==i&&(g.b.log("switching on alternate audio, use video.buffered to schedule main fragment loading"),this.mediaBuffer=i)}this.altAudio=r,this.tick()},e.prototype.onBufferCreated=function(t){var e=t.tracks,r=void 0,i=void 0,a=!1;for(var n in e){var o=e[n];"main"===o.id?(i=n,r=o,"video"===n&&(this.videoBuffer=e[n].buffer)):a=!0}a&&r?(g.b.log("alternate track found, use "+i+".buffered to schedule main fragment loading"),this.mediaBuffer=r.buffer):this.mediaBuffer=this.media},e.prototype.onBufferAppended=function(t){if("main"===t.parent){var e=this.state;e!==T.PARSING&&e!==T.PARSED||(this.pendingBuffering=t.pending>0,this._checkAppendedParsed())}},e.prototype._checkAppendedParsed=function(){if(!(this.state!==T.PARSED||this.appended&&this.pendingBuffering)){var t=this.fragCurrent;if(t){var e=this.mediaBuffer?this.mediaBuffer:this.media;g.b.log("main buffered : "+p.a.toString(e.buffered)),this.fragPrevious=t;var r=this.stats;r.tbuffered=window.performance.now(),this.fragLastKbps=Math.round(8*r.total/(r.tbuffered-r.tfirst)),this.hls.trigger(u.a.FRAG_BUFFERED,{stats:r,frag:t,id:"main"}),this.state=T.IDLE}this.tick()}},e.prototype.onError=function(t){var e=t.frag||this.fragCurrent;if(!e||"main"===e.type){var r=!!this.media&&s.a.isBuffered(this.media,this.media.currentTime)&&s.a.isBuffered(this.media,this.media.currentTime+.5);switch(t.details){case v.a.FRAG_LOAD_ERROR:case v.a.FRAG_LOAD_TIMEOUT:case v.a.KEY_LOAD_ERROR:case v.a.KEY_LOAD_TIMEOUT:if(!t.fatal)if(this.fragLoadError+1<=this.config.fragLoadingMaxRetry){var i=Math.min(Math.pow(2,this.fragLoadError)*this.config.fragLoadingRetryDelay,this.config.fragLoadingMaxRetryTimeout);g.b.warn("mediaController: frag loading failed, retry in "+i+" ms"),this.retryDate=window.performance.now()+i,this.loadedmetadata||(this.startFragRequested=!1,this.nextLoadPosition=this.startPosition),this.fragLoadError++,this.state=T.FRAG_LOADING_WAITING_RETRY}else g.b.error("mediaController: "+t.details+" reaches max retry, redispatch as fatal ..."),t.fatal=!0,this.state=T.ERROR;break;case v.a.LEVEL_LOAD_ERROR:case v.a.LEVEL_LOAD_TIMEOUT:this.state!==T.ERROR&&(t.fatal?(this.state=T.ERROR,g.b.warn("streamController: "+t.details+",switch to "+this.state+" state ...")):t.levelRetry||this.state!==T.WAITING_LEVEL||(this.state=T.IDLE));break;case v.a.BUFFER_FULL_ERROR:"main"!==t.parent||this.state!==T.PARSING&&this.state!==T.PARSED||(r?(this._reduceMaxBufferLength(this.config.maxBufferLength),this.state=T.IDLE):(g.b.warn("buffer full error also media.currentTime is not buffered, flush everything"),this.fragCurrent=null,this.flushMainBuffer(0,Number.POSITIVE_INFINITY)))}}},e.prototype._reduceMaxBufferLength=function(t){var e=this.config;return e.maxMaxBufferLength>=t&&(e.maxMaxBufferLength/=2,g.b.warn("main:reduce max buffer length to "+e.maxMaxBufferLength+"s"),!0)},e.prototype._checkBuffer=function(){var t=this.config,e=this.media;if(e&&0!==e.readyState){var r=e.currentTime,i=this.mediaBuffer?this.mediaBuffer:e,a=i.buffered;if(!this.loadedmetadata&&a.length)this.loadedmetadata=!0,this._seekToStartPos();else if(this.immediateSwitch)this.immediateLevelSwitchEnd();else{var n=!(e.paused&&e.readyState>1||e.ended||0===e.buffered.length),o=window.performance.now();if(r!==this.lastCurrentTime)this.stallReported&&(g.b.warn("playback not stuck anymore @"+r+", after "+Math.round(o-this.stalled)+"ms"),this.stallReported=!1),this.stalled=null,this.nudgeRetry=0;else if(n){var l=o-this.stalled,u=s.a.bufferInfo(e,r,t.maxBufferHole);if(!this.stalled)return void(this.stalled=o);l>=1e3&&this._reportStall(u.len),this._tryFixBufferStall(u,l)}}}},e.prototype.onFragLoadEmergencyAborted=function(){this.state=T.IDLE,this.loadedmetadata||(this.startFragRequested=!1,this.nextLoadPosition=this.startPosition),this.tick()},e.prototype.onBufferFlushed=function(){var t=this.mediaBuffer?this.mediaBuffer:this.media;t&&this.fragmentTracker.detectEvictedFragments(c.a.ElementaryStreamTypes.VIDEO,t.buffered),this.state=T.IDLE,this.fragPrevious=null},e.prototype.swapAudioCodec=function(){this.audioCodecSwap=!this.audioCodecSwap},e.prototype.computeLivePosition=function(t,e){var r=void 0!==this.config.liveSyncDuration?this.config.liveSyncDuration:this.config.liveSyncDurationCount*e.targetduration;return t+Math.max(0,e.totalduration-r)},e.prototype._tryFixBufferStall=function(t,e){var r=this.config,i=this.media,a=i.currentTime,n=this.fragmentTracker.getPartialFragment(a);n&&this._trySkipBufferHole(n),t.len>.5&&e>1e3*r.highBufferWatchdogPeriod&&(this.stalled=null,this._tryNudgeBuffer())},e.prototype._reportStall=function(t){var e=this.hls,r=this.media;this.stallReported||(this.stallReported=!0,g.b.warn("Playback stalling at @"+r.currentTime+" due to low buffer"),e.trigger(u.a.ERROR,{type:v.b.MEDIA_ERROR,details:v.a.BUFFER_STALLED_ERROR,fatal:!1,buffer:t}))},e.prototype._trySkipBufferHole=function(t){for(var e=this.hls,r=this.media,i=r.currentTime,a=0,n=0;n=a&&i"+t),this.hls.trigger(u.a.STREAM_STATE_TRANSITION,{previousState:e,nextState:t})}},get:function(){return this._state}},{key:"currentLevel",get:function(){var t=this.media;if(t){var e=this.getBufferedFrag(t.currentTime);if(e)return e.level}return-1}},{key:"nextBufferedFrag",get:function(){var t=this.media;return t?this.followingBufferedFrag(this.getBufferedFrag(t.currentTime)):null}},{key:"nextLevel",get:function(){var t=this.nextBufferedFrag;return t?t.level:-1}},{key:"liveSyncPosition",get:function(){return this._liveSyncPosition},set:function(t){this._liveSyncPosition=t}}]),e}(m.a);e.a=S},function(t,e,r){function i(t){function e(i){if(r[i])return r[i].exports;var a=r[i]={i:i,l:!1,exports:{}};return t[i].call(a.exports,a,a.exports,e),a.l=!0,a.exports}var r={};e.m=t,e.c=r,e.i=function(t){return t},e.d=function(t,r,i){e.o(t,r)||Object.defineProperty(t,r,{configurable:!1,enumerable:!0,get:i})},e.n=function(t){var r=t&&t.__esModule?function(){return t.default}:function(){return t};return e.d(r,"a",r),r},e.o=function(t,e){return Object.prototype.hasOwnProperty.call(t,e)},e.p="/",e.oe=function(t){throw console.error(t),t};var i=e(e.s=ENTRY_MODULE);return i.default||i}function a(t){return(t+"").replace(/[.?*+^$[\]\\(){}|-]/g,"\\$&")}function n(t,e,i){var n={};n[i]=[];var o=e.toString(),s=o.match(/^function\s?\(\w+,\s*\w+,\s*(\w+)\)/);if(!s)return n;for(var d,c=s[1],h=new RegExp("(\\\\n|\\W)"+a(c)+u,"g");d=h.exec(o);)"dll-reference"!==d[3]&&n[i].push(d[3]);for(h=new RegExp("\\("+a(c)+'\\("(dll-reference\\s('+l+'))"\\)\\)'+u,"g");d=h.exec(o);)t[d[2]]||(n[i].push(d[1]),t[d[2]]=r(d[1]).m),n[d[2]]=n[d[2]]||[],n[d[2]].push(d[4]);return n}function o(t){return Object.keys(t).reduce(function(e,r){return e||t[r].length>0},!1)}function s(t,e){for(var r={main:[e]},i={main:[]},a={main:{}};o(r);)for(var s=Object.keys(r),l=0;l>>8^255&g^99,t[f]=g,e[g]=f;var y=h[f],m=h[y],b=h[m],E=257*h[g]^16843008*g;i[f]=E<<24|E>>>8,a[f]=E<<16|E>>>16,n[f]=E<<8|E>>>24,o[f]=E,E=16843009*b^65537*m^257*y^16843008*f,l[g]=E<<24|E>>>8,u[g]=E<<16|E>>>16,d[g]=E<<8|E>>>24,c[g]=E,f?(f=y^h[h[h[b^y]]],p^=h[h[p]]):f=p=1}},t.prototype.expandKey=function(t){for(var e=this.uint8ArrayToUint32Array_(t),r=!0,i=0;i>4>1){if((h=n+5+e[n+4])===n+188)continue}else h=n+4;switch(c){case b:l&&(R&&(f=D(R))&&void 0!==f.pts&&I(f,!1),R={data:[],size:0}),R&&(R.data.push(e.subarray(h,n+188)),R.size+=n+188-h);break;case E:l&&(A&&(f=D(A))&&void 0!==f.pts&&(y.isAAC?k(f):O(f)),A={data:[],size:0}),A&&(A.data.push(e.subarray(h,n+188)),A.size+=n+188-h);break;case T:l&&(_&&(f=D(_))&&void 0!==f.pts&&C(f),_={data:[],size:0}),_&&(_.data.push(e.subarray(h,n+188)),_.size+=n+188-h);break;case 0:l&&(h+=e[h]+1),S=this._pmtId=w(e,h);break;case S:l&&(h+=e[h]+1);var x=L(e,h,!0===this.typeSupported.mpeg||!0===this.typeSupported.mp3,null!=this.sampleAes);b=x.avc,b>0&&(g.pid=b),E=x.audio,E>0&&(y.pid=E,y.isAAC=x.isAAC),T=x.id3,T>0&&(m.pid=T),p&&!v&&(u.b.log("reparse from beginning"),p=!1,n=P-188),v=this.pmtParsed=!0;break;case 17:case 8191:break;default:p=!0}}else this.observer.trigger(o.a.ERROR,{type:d.b.MEDIA_ERROR,details:d.a.FRAG_PARSING_ERROR,fatal:!1,reason:"TS packet did not start with 0x47"});R&&(f=D(R))&&void 0!==f.pts?(I(f,!0),g.pesData=null):g.pesData=R,A&&(f=D(A))&&void 0!==f.pts?(y.isAAC?k(f):O(f),y.pesData=null):(A&&A.size&&u.b.log("last AAC PES packet truncated,might overlap between fragments"),y.pesData=A),_&&(f=D(_))&&void 0!==f.pts?(C(f),m.pesData=null):m.pesData=_,null==this.sampleAes?this.remuxer.remux(y,g,m,this._txtTrack,r,i,a):this.decryptAndRemux(y,g,m,this._txtTrack,r,i,a)},t.prototype.decryptAndRemux=function(t,e,r,i,a,n,o){if(t.samples&&t.isAAC){var s=this;this.sampleAes.decryptAacSamples(t.samples,0,function(){s.decryptAndRemuxAvc(t,e,r,i,a,n,o)})}else this.decryptAndRemuxAvc(t,e,r,i,a,n,o)},t.prototype.decryptAndRemuxAvc=function(t,e,r,i,a,n,o){if(e.samples){var s=this;this.sampleAes.decryptAvcSamples(e.samples,0,0,function(){s.remuxer.remux(t,e,r,i,a,n,o)})}else this.remuxer.remux(t,e,r,i,a,n,o)},t.prototype.destroy=function(){this._initPTS=this._initDTS=void 0,this._duration=0},t.prototype._parsePAT=function(t,e){return(31&t[e+10])<<8|t[e+11]},t.prototype._parsePMT=function(t,e,r,i){var a=void 0,n=void 0,o=void 0,s=void 0,l={audio:-1,avc:-1,id3:-1,isAAC:!0};for(a=(15&t[e+1])<<8|t[e+2],n=e+3+a-4,o=(15&t[e+10])<<8|t[e+11],e+=12+o;e1;){var h=new Uint8Array(c[0].length+c[1].length);h.set(c[0]),h.set(c[1],c[0].length),c[0]=h,c.splice(1,1)}if(r=c[0],1===(r[0]<<16)+(r[1]<<8)+r[2]){if((a=(r[4]<<8)+r[5])&&a>t.size-6)return null;i=r[7],192&i&&(s=536870912*(14&r[9])+4194304*(255&r[10])+16384*(254&r[11])+128*(255&r[12])+(254&r[13])/2,s>4294967295&&(s-=8589934592),64&i?(l=536870912*(14&r[14])+4194304*(255&r[15])+16384*(254&r[16])+128*(255&r[17])+(254&r[18])/2,l>4294967295&&(l-=8589934592),s-l>54e5&&(u.b.warn(Math.round((s-l)/9e4)+"s delta between PTS and DTS, align them"),s=l)):l=s),n=r[8],d=n+9,t.size-=d,o=new Uint8Array(t.size);for(var f=0,p=c.length;fv){d-=v;continue}r=r.subarray(d),v-=d,d=0}o.set(r,e),e+=v}return a&&(a-=n+3),{data:o,pts:s,dts:l,len:a}}return null},t.prototype.pushAccesUnit=function(t,e){if(t.units.length&&t.frame){var r=e.samples,i=r.length;!this.config.forceKeyFrameOnDiscontinuity||!0===t.key||e.sps&&(i||this.contiguous)?(t.id=i,r.push(t)):e.dropped++}t.debug.length&&u.b.log(t.pts+"/"+t.dts+":"+t.debug)},t.prototype._parseAVCPES=function(t,e){var r=this,i=this._avcTrack,a=this._parseAVCNALu(t.data),n=void 0,o=this.avcSample,l=void 0,u=!1,d=void 0,c=this.pushAccesUnit.bind(this),h=function(t,e,r,i){return{key:t,pts:e,dts:r,units:[],debug:i}};t.data=null,o&&a.length&&!i.audFound&&(c(o,i),o=this.avcSample=h(!1,t.pts,t.dts,"")),a.forEach(function(e){switch(e.type){case 1:l=!0,o||(o=r.avcSample=h(!0,t.pts,t.dts,"")),o.frame=!0;var a=e.data;if(u&&a.length>4){var f=new s.a(a).readSliceType();2!==f&&4!==f&&7!==f&&9!==f||(o.key=!0)}break;case 5:l=!0,o||(o=r.avcSample=h(!0,t.pts,t.dts,"")),o.key=!0,o.frame=!0;break;case 6:l=!0,n=new s.a(r.discardEPB(e.data)),n.readUByte();for(var p=0,v=0,g=!1,y=0;!g&&n.bytesAvailable>1;){p=0;do{y=n.readUByte(),p+=y}while(255===y);v=0;do{y=n.readUByte(),v+=y}while(255===y);if(4===p&&0!==n.bytesAvailable){g=!0;if(181===n.readUByte()){if(49===n.readUShort()){if(1195456820===n.readUInt()){if(3===n.readUByte()){var m=n.readUByte(),b=n.readUByte(),E=31&m,T=[m,b];for(d=0;d0){if(e.pts>=t[r-1].pts)t.push(e);else for(var i=r-1;i>=0;i--)if(e.pts=0)u={data:t.subarray(c,e-o-1),type:h},l.push(u);else{var f=this._getLastNalUnit();if(f&&(s&&e<=4-s&&f.state&&(f.data=f.data.subarray(0,f.data.byteLength-s)),(a=e-o-1)>0)){var p=new Uint8Array(f.data.byteLength+a);p.set(f.data,0),p.set(t.subarray(0,a),f.data.byteLength),f.data=p}}e=0&&o>=0&&(u={data:t.subarray(c,r),type:h,state:o},l.push(u)),0===l.length){var v=this._getLastNalUnit();if(v){var g=new Uint8Array(v.data.byteLength+t.byteLength);g.set(v.data,0),g.set(t,v.data.byteLength),v.data=g}}return n.naluState=o,l},t.prototype.discardEPB=function(t){for(var e=t.byteLength,r=[],i=1,a=void 0,n=void 0;i1&&(u.b.log("AAC: align PTS for overlapping frames by "+Math.round((m-i)/90)),i=m)}for(;ht?(this.word<<=t,this.bitsAvailable-=t):(t-=this.bitsAvailable,e=t>>3,t-=e>>3,this.bytesAvailable-=e,this.loadWord(),this.word<<=t,this.bitsAvailable-=t)},t.prototype.readBits=function(t){var e=Math.min(this.bitsAvailable,t),r=this.word>>>32-e;return t>32&&a.b.error("Cannot read more than 32 bits at a time"),this.bitsAvailable-=e,this.bitsAvailable>0?this.word<<=e:this.bytesAvailable>0&&this.loadWord(),e=t-e,e>0&&this.bitsAvailable?r<>>t))return this.word<<=t,this.bitsAvailable-=t,t;return this.loadWord(),t+this.skipLZ()},t.prototype.skipUEG=function(){this.skipBits(1+this.skipLZ())},t.prototype.skipEG=function(){this.skipBits(1+this.skipLZ())},t.prototype.readUEG=function(){var t=this.skipLZ();return this.readBits(t+1)-1},t.prototype.readEG=function(){var t=this.readUEG();return 1&t?1+t>>>1:-1*(t>>>1)},t.prototype.readBoolean=function(){return 1===this.readBits(1)},t.prototype.readUByte=function(){return this.readBits(8)},t.prototype.readUShort=function(){return this.readBits(16)},t.prototype.readUInt=function(){return this.readBits(32)},t.prototype.skipScalingList=function(t){var e=8,r=8,i=void 0,a=void 0;for(i=0;i=t.length)return void r();if(!(t[e].unit.length<32)){var i=this.decrypter.isSync();if(this.decryptAacSample(t,e,r,i),!i)return}}},t.prototype.getAvcEncryptedData=function(t){for(var e=16*Math.floor((t.length-48)/160)+16,r=new Int8Array(e),i=0,a=32;a<=t.length-16;a+=160,i+=16)r.set(t.subarray(a,a+16),i);return r},t.prototype.getAvcDecryptedUnit=function(t,e){e=new Uint8Array(e);for(var r=0,i=32;i<=t.length-16;i+=160,r+=16)t.set(e.subarray(r,r+16),i);return t},t.prototype.decryptAvcSample=function(t,e,r,i,a,n){var o=this.discardEPB(a.data),s=this.getAvcEncryptedData(o),l=this;this.decryptBuffer(s.buffer,function(s){a.data=l.getAvcDecryptedUnit(o,s),n||l.decryptAvcSamples(t,e,r+1,i)})},t.prototype.decryptAvcSamples=function(t,e,r,i){for(;;e++,r=0){if(e>=t.length)return void i();for(var a=t[e].units;!(r>=a.length);r++){var n=a[r];if(!(n.length<=48||1!==n.type&&5!==n.type)){var o=this.decrypter.isSync();if(this.decryptAvcSample(t,e,r,i,n,o),!o)return}}}},t}();e.a=n},function(t,e,r){"use strict";function i(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}var a=r(7),n=r(0),o=r(23),s=function(){function t(e,r,a){i(this,t),this.observer=e,this.config=a,this.remuxer=r}return t.prototype.resetInitSegment=function(t,e,r,i){this._audioTrack={container:"audio/mpeg",type:"audio",id:-1,sequenceNumber:0,isAAC:!1,samples:[],len:0,manifestCodec:e,duration:i,inputTimeScale:9e4}},t.prototype.resetTimeStamp=function(){},t.probe=function(t){var e=void 0,r=void 0,i=a.a.getID3Data(t,0);if(i&&void 0!==a.a.getTimeStamp(i))for(e=i.length,r=Math.min(t.length-1,e+100);e-1&&o&&!o.match("CriOS"),this.ISGenerated=!1}return t.prototype.destroy=function(){},t.prototype.resetTimeStamp=function(t){this._initPTS=this._initDTS=t},t.prototype.resetInitSegment=function(){this.ISGenerated=!1},t.prototype.remux=function(t,e,r,i,a,n,s){if(this.ISGenerated||this.generateIS(t,e,a),this.ISGenerated){var u=t.samples.length,d=e.samples.length,c=a,h=a;if(u&&d){var f=(t.samples[0].dts-e.samples[0].dts)/e.inputTimeScale;c+=Math.max(0,f),h+=Math.max(0,-f)}if(u){t.timescale||(l.b.warn("regenerate InitSegment as audio detected"),this.generateIS(t,e,a));var p=this.remuxAudio(t,c,n,s);if(d){var v=void 0;p&&(v=p.endPTS-p.startPTS),e.timescale||(l.b.warn("regenerate InitSegment as video detected"),this.generateIS(t,e,a)),this.remuxVideo(e,h,n,v,s)}}else if(d){var g=this.remuxVideo(e,h,n,0,s);g&&t.codec&&this.remuxEmptyAudio(t,c,n,g)}}r.samples.length&&this.remuxID3(r,a),i.samples.length&&this.remuxText(i,a),this.observer.trigger(o.a.FRAG_PARSED)},t.prototype.generateIS=function(t,e,r){var i=this.observer,a=t.samples,u=e.samples,d=this.typeSupported,c="audio/mp4",h={},f={tracks:h},p=void 0===this._initPTS,v=void 0,g=void 0;if(p&&(v=g=1/0),t.config&&a.length&&(t.timescale=t.samplerate,l.b.log("audio sampling rate : "+t.samplerate),t.isAAC||(d.mpeg?(c="audio/mpeg",t.codec=""):d.mp3&&(t.codec="mp3")),h.audio={container:c,codec:t.codec,initSegment:!t.isAAC&&d.mpeg?new Uint8Array:n.a.initSegment([t]),metadata:{channelCount:t.channelCount}},p&&(v=g=a[0].pts-t.inputTimeScale*r)),e.sps&&e.pps&&u.length){var y=e.inputTimeScale;e.timescale=y,h.video={container:"video/mp4",codec:e.codec,initSegment:n.a.initSegment([e]),metadata:{width:e.width,height:e.height}},p&&(v=Math.min(v,u[0].pts-y*r),g=Math.min(g,u[0].dts-y*r),this.observer.trigger(o.a.INIT_PTS_FOUND,{initPTS:v}))}Object.keys(h).length?(i.trigger(o.a.FRAG_PARSING_INIT_SEGMENT,f),this.ISGenerated=!0,p&&(this._initPTS=v,this._initDTS=g)):i.trigger(o.a.ERROR,{type:s.b.MEDIA_ERROR,details:s.a.FRAG_PARSING_ERROR,fatal:!1,reason:"no audio/video samples found"})},t.prototype.remuxVideo=function(t,e,r,i,a){var u=8,d=t.timescale,c=void 0,h=void 0,f=void 0,p=void 0,v=void 0,g=void 0,y=void 0,m=t.samples,b=[],E=m.length,T=this._PTSNormalize,S=this._initDTS,R=this.nextAvcDts,A=this.isSafari;if(0!==E){A&&(r|=m.length&&R&&(a&&Math.abs(e-R/d)<.1||Math.abs(m[0].pts-R-S)1?l.b.log("AVC:"+D+" ms hole between fragments detected,filling it"):D<-1&&l.b.log("AVC:"+-D+" ms overlapping between fragments detected"),v=R,m[0].dts=v,p=Math.max(p-D,R),m[0].pts=p,l.b.log("Video/PTS/DTS adjusted: "+Math.round(p/90)+"/"+Math.round(v/90)+",delta:"+D+" ms")),v,L=m[m.length-1],y=Math.max(L.dts,0),g=Math.max(L.pts,0,y),A&&(c=Math.round((y-v)/(m.length-1)));for(var I=0,k=0,O=0;O0?B-1:B].dts;if(z.stretchShortVideoTrack){var $=z.maxBufferHole,J=Math.floor($*d),Z=(i?p+i*d:this.nextAudioPts)-G.pts;Z>J?(c=Z-Q,c<0&&(c=Q),l.b.log("It is approximately "+Z/90+" ms to the next segment; using duration "+c/90+" ms for the last video frame.")):c=Q}else c=Q}H=Math.round(G.pts-G.dts)}b.push({size:j,duration:c,cts:H,flags:{isLeading:0,isDependedOn:0,hasRedundancy:0,degradPrio:0,dependsOn:G.key?2:1,isNonSync:G.key?0:1}})}this.nextAvcDts=y+c;var tt=t.dropped;if(t.len=0,t.nbNalu=0,t.dropped=0,b.length&&navigator.userAgent.toLowerCase().indexOf("chrome")>-1){var et=b[0].flags;et.dependsOn=2,et.isNonSync=0}t.samples=b,f=n.a.moof(t.sequenceNumber++,v,t),t.samples=[];var rt={data1:f,data2:h,startPTS:p/d,endPTS:(g+c)/d,startDTS:v/d,endDTS:this.nextAvcDts/d,type:"video",hasAudio:!1,hasVideo:!0,nb:b.length,dropped:tt};return this.observer.trigger(o.a.FRAG_PARSING_DATA,rt),rt}},t.prototype.remuxAudio=function(t,e,r,i){var u=t.inputTimeScale,d=t.timescale,c=u/d,h=t.isAAC?1024:1152,f=h*c,p=this._PTSNormalize,v=this._initDTS,g=!t.isAAC&&this.typeSupported.mpeg,y=void 0,m=void 0,b=void 0,E=void 0,T=void 0,S=void 0,R=void 0,A=t.samples,_=[],w=this.nextAudioPts;if(r|=A.length&&w&&(i&&Math.abs(e-w/u)<.1||Math.abs(A[0].pts-w-v)<20*f),A.forEach(function(t){t.pts=t.dts=p(t.pts-v,e*u)}),A=A.filter(function(t){return t.pts>=0}),0!==A.length){if(r||(w=i?e*u:A[0].pts),t.isAAC)for(var L=this.config.maxAudioFramesDrift,D=0,I=w;D=L*f&&P<1e4&&I){var x=Math.round(k/f);l.b.warn("Injecting "+x+" audio frame @ "+(I/u).toFixed(3)+"s due to "+Math.round(1e3*k/u)+" ms gap.");for(var F=0;F0&&j<1e4)H=Math.round((K-w)/f),l.b.log(j+" ms hole between AAC samples detected,filling it"),H>0&&(b=a.a.getSilentFrame(t.manifestCodec||t.codec,t.channelCount),b||(b=G.subarray()),t.len+=H*b.length);else if(j<-12){l.b.log("drop overlapping AAC sample, expected/parsed/delta:"+(w/u).toFixed(3)+"s/"+(K/u).toFixed(3)+"s/"+-j+"ms"),t.len-=G.byteLength;continue}K=w}if(S=K,!(t.len>0))return;var V=g?t.len:t.len+8;y=g?0:8;try{E=new Uint8Array(V)}catch(t){return void this.observer.trigger(o.a.ERROR,{type:s.b.MUX_ERROR,details:s.a.REMUX_ALLOC_ERROR,fatal:!1,bytes:V,reason:"fail allocating audio mdat "+V})}if(!g){new DataView(E.buffer).setUint32(0,V),E.set(n.a.types.mdat,4)}for(var Y=0;Y=2&&(q=_[X-2].duration,m.duration=q),X){this.nextAudioPts=w=R+c*q,t.len=0,t.samples=_,T=g?new Uint8Array:n.a.moof(t.sequenceNumber++,S/c,t),t.samples=[];var z=S/u,Q=w/u,$={data1:T,data2:E,startPTS:z,endPTS:Q,startDTS:z,endDTS:Q,type:"audio",hasAudio:!0,hasVideo:!1,nb:X};return this.observer.trigger(o.a.FRAG_PARSING_DATA,$),$}return null}},t.prototype.remuxEmptyAudio=function(t,e,r,i){var n=t.inputTimeScale,o=t.samplerate?t.samplerate:n,s=n/o,u=this.nextAudioPts,d=(void 0!==u?u:i.startDTS*n)+this._initDTS,c=i.endDTS*n+this._initDTS,h=1024*s,f=Math.ceil((c-d)/h),p=a.a.getSilentFrame(t.manifestCodec||t.codec,t.channelCount);if(l.b.warn("remux empty Audio"),!p)return void l.b.trace("Unable to remuxEmptyAudio since we were unable to get a silent frame for given audio codec!");for(var v=[],g=0;g4294967296;)t+=r;return t},t}();e.a=u},function(t,e,r){"use strict";function i(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}var a=function(){function t(){i(this,t)}return t.getSilentFrame=function(t,e){switch(t){case"mp4a.40.2":if(1===e)return new Uint8Array([0,200,0,128,35,128]);if(2===e)return new Uint8Array([33,0,73,144,2,25,0,35,128]);if(3===e)return new Uint8Array([0,200,0,128,32,132,1,38,64,8,100,0,142]);if(4===e)return new Uint8Array([0,200,0,128,32,132,1,38,64,8,100,0,128,44,128,8,2,56]);if(5===e)return new Uint8Array([0,200,0,128,32,132,1,38,64,8,100,0,130,48,4,153,0,33,144,2,56]);if(6===e)return new Uint8Array([0,200,0,128,32,132,1,38,64,8,100,0,130,48,4,153,0,33,144,2,0,178,0,32,8,224]);break;default:if(1===e)return new Uint8Array([1,64,34,128,163,78,230,128,186,8,0,0,0,28,6,241,193,10,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,94]);if(2===e)return new Uint8Array([1,64,34,128,163,94,230,128,186,8,0,0,0,0,149,0,6,241,161,10,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,94]);if(3===e)return new Uint8Array([1,64,34,128,163,94,230,128,186,8,0,0,0,0,149,0,6,241,161,10,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,90,94])}return null},t}();e.a=a},function(t,e,r){"use strict";function i(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}var a=Math.pow(2,32)-1,n=function(){function t(){i(this,t)}return t.init=function(){t.types={avc1:[],avcC:[],btrt:[],dinf:[],dref:[],esds:[],ftyp:[],hdlr:[],mdat:[],mdhd:[],mdia:[],mfhd:[],minf:[],moof:[],moov:[],mp4a:[],".mp3":[],mvex:[],mvhd:[],pasp:[],sdtp:[],stbl:[],stco:[],stsc:[],stsd:[],stsz:[],stts:[],tfdt:[],tfhd:[],traf:[],trak:[],trun:[],trex:[],tkhd:[],vmhd:[],smhd:[]};var e=void 0;for(e in t.types)t.types.hasOwnProperty(e)&&(t.types[e]=[e.charCodeAt(0),e.charCodeAt(1),e.charCodeAt(2),e.charCodeAt(3)]);var r=new Uint8Array([0,0,0,0,0,0,0,0,118,105,100,101,0,0,0,0,0,0,0,0,0,0,0,0,86,105,100,101,111,72,97,110,100,108,101,114,0]),i=new Uint8Array([0,0,0,0,0,0,0,0,115,111,117,110,0,0,0,0,0,0,0,0,0,0,0,0,83,111,117,110,100,72,97,110,100,108,101,114,0]);t.HDLR_TYPES={video:r,audio:i};var a=new Uint8Array([0,0,0,0,0,0,0,1,0,0,0,12,117,114,108,32,0,0,0,1]),n=new Uint8Array([0,0,0,0,0,0,0,0]);t.STTS=t.STSC=t.STCO=n,t.STSZ=new Uint8Array([0,0,0,0,0,0,0,0,0,0,0,0]),t.VMHD=new Uint8Array([0,0,0,1,0,0,0,0,0,0,0,0]),t.SMHD=new Uint8Array([0,0,0,0,0,0,0,0]),t.STSD=new Uint8Array([0,0,0,0,0,0,0,1]);var o=new Uint8Array([105,115,111,109]),s=new Uint8Array([97,118,99,49]),l=new Uint8Array([0,0,0,1]);t.FTYP=t.box(t.types.ftyp,o,l,o,s),t.DINF=t.box(t.types.dinf,t.box(t.types.dref,a))},t.box=function(t){for(var e=Array.prototype.slice.call(arguments,1),r=8,i=e.length,a=i,n=void 0;i--;)r+=e[i].byteLength;for(n=new Uint8Array(r),n[0]=r>>24&255,n[1]=r>>16&255,n[2]=r>>8&255,n[3]=255&r,n.set(t,4),i=0,r=8;i>24&255,e>>16&255,e>>8&255,255&e,i>>24,i>>16&255,i>>8&255,255&i,n>>24,n>>16&255,n>>8&255,255&n,85,196,0,0]))},t.mdia=function(e){return t.box(t.types.mdia,t.mdhd(e.timescale,e.duration),t.hdlr(e.type),t.minf(e))},t.mfhd=function(e){return t.box(t.types.mfhd,new Uint8Array([0,0,0,0,e>>24,e>>16&255,e>>8&255,255&e]))},t.minf=function(e){return"audio"===e.type?t.box(t.types.minf,t.box(t.types.smhd,t.SMHD),t.DINF,t.stbl(e)):t.box(t.types.minf,t.box(t.types.vmhd,t.VMHD),t.DINF,t.stbl(e))},t.moof=function(e,r,i){return t.box(t.types.moof,t.mfhd(e),t.traf(i,r))},t.moov=function(e){for(var r=e.length,i=[];r--;)i[r]=t.trak(e[r]);return t.box.apply(null,[t.types.moov,t.mvhd(e[0].timescale,e[0].duration)].concat(i).concat(t.mvex(e)))},t.mvex=function(e){for(var r=e.length,i=[];r--;)i[r]=t.trex(e[r]);return t.box.apply(null,[t.types.mvex].concat(i))},t.mvhd=function(e,r){r*=e;var i=Math.floor(r/(a+1)),n=Math.floor(r%(a+1)),o=new Uint8Array([1,0,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,3,e>>24&255,e>>16&255,e>>8&255,255&e,i>>24,i>>16&255,i>>8&255,255&i,n>>24,n>>16&255,n>>8&255,255&n,0,1,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,64,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,255,255,255,255]);return t.box(t.types.mvhd,o)},t.sdtp=function(e){var r=e.samples||[],i=new Uint8Array(4+r.length),a=void 0,n=void 0;for(n=0;n>>8&255),r.push(255&o),r=r.concat(Array.prototype.slice.call(n));for(a=0;a>>8&255),i.push(255&o),i=i.concat(Array.prototype.slice.call(n));var s=t.box(t.types.avcC,new Uint8Array([1,r[3],r[4],r[5],255,224|e.sps.length].concat(r).concat([e.pps.length]).concat(i))),l=e.width,u=e.height,d=e.pixelRatio[0],c=e.pixelRatio[1];return t.box(t.types.avc1,new Uint8Array([0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,l>>8&255,255&l,u>>8&255,255&u,0,72,0,0,0,72,0,0,0,0,0,0,0,1,18,100,97,105,108,121,109,111,116,105,111,110,47,104,108,115,46,106,115,0,0,0,0,0,0,0,0,0,0,0,0,0,0,24,17,17]),s,t.box(t.types.btrt,new Uint8Array([0,28,156,128,0,45,198,192,0,45,198,192])),t.box(t.types.pasp,new Uint8Array([d>>24,d>>16&255,d>>8&255,255&d,c>>24,c>>16&255,c>>8&255,255&c])))},t.esds=function(t){var e=t.config.length;return new Uint8Array([0,0,0,0,3,23+e,0,1,0,4,15+e,64,21,0,0,0,0,0,0,0,0,0,0,0,5].concat([e]).concat(t.config).concat([6,1,2]))},t.mp4a=function(e){var r=e.samplerate;return t.box(t.types.mp4a,new Uint8Array([0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,e.channelCount,0,16,0,0,0,0,r>>8&255,255&r,0,0]),t.box(t.types.esds,t.esds(e)))},t.mp3=function(e){var r=e.samplerate;return t.box(t.types[".mp3"],new Uint8Array([0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,e.channelCount,0,16,0,0,0,0,r>>8&255,255&r,0,0]))},t.stsd=function(e){return"audio"===e.type?e.isAAC||"mp3"!==e.codec?t.box(t.types.stsd,t.STSD,t.mp4a(e)):t.box(t.types.stsd,t.STSD,t.mp3(e)):t.box(t.types.stsd,t.STSD,t.avc1(e))},t.tkhd=function(e){var r=e.id,i=e.duration*e.timescale,n=e.width,o=e.height,s=Math.floor(i/(a+1)),l=Math.floor(i%(a+1));return t.box(t.types.tkhd,new Uint8Array([1,0,0,7,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,3,r>>24&255,r>>16&255,r>>8&255,255&r,0,0,0,0,s>>24,s>>16&255,s>>8&255,255&s,l>>24,l>>16&255,l>>8&255,255&l,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,64,0,0,0,n>>8&255,255&n,0,0,o>>8&255,255&o,0,0]))},t.traf=function(e,r){var i=t.sdtp(e),n=e.id,o=Math.floor(r/(a+1)),s=Math.floor(r%(a+1));return t.box(t.types.traf,t.box(t.types.tfhd,new Uint8Array([0,0,0,0,n>>24,n>>16&255,n>>8&255,255&n])),t.box(t.types.tfdt,new Uint8Array([1,0,0,0,o>>24,o>>16&255,o>>8&255,255&o,s>>24,s>>16&255,s>>8&255,255&s])),t.trun(e,i.length+16+20+8+16+8+8),i)},t.trak=function(e){return e.duration=e.duration||4294967295,t.box(t.types.trak,t.tkhd(e),t.mdia(e))},t.trex=function(e){var r=e.id;return t.box(t.types.trex,new Uint8Array([0,0,0,0,r>>24,r>>16&255,r>>8&255,255&r,0,0,0,1,0,0,0,0,0,0,0,0,0,1,0,1]))},t.trun=function(e,r){var i=e.samples||[],a=i.length,n=12+16*a,o=new Uint8Array(n),s=void 0,l=void 0,u=void 0,d=void 0,c=void 0,h=void 0;for(r+=8+n,o.set([0,0,15,1,a>>>24&255,a>>>16&255,a>>>8&255,255&a,r>>>24&255,r>>>16&255,r>>>8&255,255&r],0),s=0;s>>24&255,u>>>16&255,u>>>8&255,255&u,d>>>24&255,d>>>16&255,d>>>8&255,255&d,c.isLeading<<2|c.dependsOn,c.isDependedOn<<6|c.hasRedundancy<<4|c.paddingValue<<1|c.isNonSync,61440&c.degradPrio,15&c.degradPrio,h>>>24&255,h>>>16&255,h>>>8&255,255&h],12+16*s);return t.box(t.types.trun,o)},t.initSegment=function(e){t.types||t.init();var r=t.moov(e),i=void 0;return i=new Uint8Array(t.FTYP.byteLength+r.byteLength),i.set(t.FTYP),i.set(r,t.FTYP.byteLength),i},t}();e.a=n},function(t,e,r){"use strict";function i(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}var a=r(1),n=function(){function t(e){i(this,t),this.observer=e}return t.prototype.destroy=function(){},t.prototype.resetTimeStamp=function(){},t.prototype.resetInitSegment=function(){},t.prototype.remux=function(t,e,r,i,n,o,s,l){var u=this.observer,d="";t&&(d+="audio"),e&&(d+="video"),u.trigger(a.a.FRAG_PARSING_DATA,{data1:l,startPTS:n,startDTS:n,type:d,hasAudio:!!t,hasVideo:!!e,nb:1,dropped:0}),u.trigger(a.a.FRAG_PARSED)},t}();e.a=n},function(t,e,r){"use strict";Object.defineProperty(e,"__esModule",{value:!0});var i=r(21),a=r(1),n=r(0),o=r(12),s=r.n(o),l=function(t){var e=new s.a;e.trigger=function(t){for(var r=arguments.length,i=Array(r>1?r-1:0),a=1;a1?r-1:0),a=1;a0&&void 0!==arguments[0]?arguments[0]:0,e=arguments.length>1&&void 0!==arguments[1]?arguments[1]:0,r=arguments[2],i=0;if(r.programDateTime){var a=Date.parse(r.programDateTime);isNaN(a)||(i=1e3*e+a-1e3*t)}return i}function a(t){var e=arguments.length>1&&void 0!==arguments[1]?arguments[1]:null;if(!Array.isArray(t)||!t.length||null===e)return null;if(e=t[t.length-1].endPdt)return null;for(var r=0;r2&&void 0!==arguments[2]?arguments[2]:0,i=arguments.length>3&&void 0!==arguments[3]?arguments[3]:0,a=arguments.length>4&&void 0!==arguments[4]?arguments[4]:0,n=void 0,l=t?e[t.sn-e[0].sn+1]:null;return ri-a&&(a=0),n=l&&!o(r,a,l)?l:s.a.search(e,o.bind(null,r,a))),n}function o(){var t=arguments.length>0&&void 0!==arguments[0]?arguments[0]:0,e=arguments.length>1&&void 0!==arguments[1]?arguments[1]:0,r=arguments[2],i=Math.min(e,r.duration+(r.deltaPTS?r.deltaPTS:0));return r.start+r.duration-i<=t?1:r.start-i>t&&r.start?-1:0}e.a=i,e.b=a,e.c=n,e.d=o;var s=r(6)},function(t,e,r){"use strict";function i(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function a(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function n(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}var o=r(1),s=r(3),l=r(0),u=r(2),d=r(19),c=r(15),h="function"==typeof Symbol&&"symbol"==typeof Symbol.iterator?function(t){return typeof t}:function(t){return t&&"function"==typeof Symbol&&t.constructor===Symbol&&t!==Symbol.prototype?"symbol":typeof t},f=function(){function t(t,e){for(var r=0;r0){r=e[0].bitrate,e.sort(function(t,e){return t.bitrate-e.bitrate}),this._levels=e;for(var p=0;p0&&n})}else this.hls.trigger(o.a.ERROR,{type:u.b.MEDIA_ERROR,details:u.a.MANIFEST_INCOMPATIBLE_CODECS_ERROR,fatal:!0,url:this.hls.url,reason:"no level with compatible codecs found in manifest"})},e.prototype.setLevelInternal=function(t){var e=this._levels,r=this.hls;if(t>=0&&t1&&s.loadError0){var e=this.currentLevelIndex,r=t.urlId,i=t.url[r];l.b.log("Attempt loading level index "+e+" with URL-id "+r),this.hls.trigger(o.a.LEVEL_LOADING,{url:i,level:e,id:r})}}},f(e,[{key:"levels",get:function(){return this._levels}},{key:"level",get:function(){return this.currentLevelIndex},set:function(t){var e=this._levels;e&&(t=Math.min(t,e.length-1),this.currentLevelIndex===t&&e[t].details||this.setLevelInternal(t))}},{key:"manualLevel",get:function(){return this.manualLevelIndex},set:function(t){this.manualLevelIndex=t,void 0===this._startLevel&&(this._startLevel=t),-1!==t&&(this.level=t)}},{key:"firstLevel",get:function(){return this._firstLevel},set:function(t){this._firstLevel=t}},{key:"startLevel",get:function(){if(void 0===this._startLevel){var t=this.hls.config.startLevel;return void 0!==t?t:this._firstLevel}return this._startLevel},set:function(t){this._startLevel=t}},{key:"nextLoadLevel",get:function(){return-1!==this.manualLevelIndex?this.manualLevelIndex:this.hls.nextAutoLevel},set:function(t){this.level=t,-1===this.manualLevelIndex&&(this.hls.nextAutoLevel=t)}}]),e}(s.a);e.a=g},function(t,e,r){"use strict";function i(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function a(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function n(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}var o=r(1),s=r(3),l=r(7),u=r(26),d=function(t){function e(r){i(this,e);var n=a(this,t.call(this,r,o.a.MEDIA_ATTACHED,o.a.MEDIA_DETACHING,o.a.FRAG_PARSING_METADATA));return n.id3Track=void 0,n.media=void 0,n}return n(e,t),e.prototype.destroy=function(){s.a.prototype.destroy.call(this)},e.prototype.onMediaAttached=function(t){this.media=t.media,this.media},e.prototype.onMediaDetaching=function(){Object(u.a)(this.id3Track),this.id3Track=void 0,this.media=void 0},e.prototype.getID3Track=function(t){for(var e=0;e500*r.duration/u){var c=t.levels,h=Math.max(1,n.bw?n.bw/8:1e3*n.loaded/s),f=c[r.level],v=f.realBitrate?Math.max(f.realBitrate,f.bitrate):f.bitrate,g=n.total?n.total:Math.max(n.loaded,Math.round(r.duration*v/8)),y=e.currentTime,m=(g-n.loaded)/h,b=(l.a.bufferInfo(e,y,t.config.maxBufferHole).end-y)/u;if(b<2*r.duration/u&&m>b){var E=void 0,T=void 0;for(T=r.level-1;T>a;T--){var S=c[T].realBitrate?Math.max(c[T].realBitrate,c[T].bitrate):c[T].bitrate;if((E=r.duration*S/(6.4*h))=i;u--){var c=l[u],h=c.details,f=h?h.totalduration/h.fragments.length:e,p=!!h&&h.live,v=void 0;v=u<=t?o*r:s*r;var g=l[u].realBitrate?Math.max(l[u].realBitrate,l[u].bitrate):l[u].bitrate,y=g*f/v;if(d.b.trace("level/adjustedbw/bitrate/avgDuration/maxFetchDuration/fetchDuration: "+u+"/"+Math.round(v)+"/"+g+"/"+f+"/"+n+"/"+y),v>g&&(!y||p&&!this.bitrateTestDelay||y=0)return p;d.b.trace("rebuffering expected to happen, lets try to find a quality level minimizing the rebuffering");var v=s?Math.min(s,i.maxStarvationDelay):i.maxStarvationDelay,g=i.abrBandWidthFactor,y=i.abrBandWidthUpFactor;if(0===f){var m=this.bitrateTestDelay;if(m){v=(s?Math.min(s,i.maxLoadingDelay):i.maxLoadingDelay)-m,d.b.trace("bitrate test took "+Math.round(1e3*m)+"ms, set first fragment max fetchDuration to "+Math.round(1e3*v)+" ms"),g=y=1}}return p=this._findBestLevel(o,s,h,a,e,f+v,g,y,r),Math.max(p,0)}}]),e}(s.a);e.a=v},function(t,e,r){"use strict";function i(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}var a=r(55),n=function(){function t(e,r,n,o){i(this,t),this.hls=e,this.defaultEstimate_=o,this.minWeight_=.001,this.minDelayMs_=50,this.slow_=new a.a(r),this.fast_=new a.a(n)}return t.prototype.sample=function(t,e){t=Math.max(t,this.minDelayMs_);var r=8e3*e/t,i=t/1e3;this.fast_.sample(i,r),this.slow_.sample(i,r)},t.prototype.canEstimate=function(){var t=this.fast_;return t&&t.getTotalWeight()>=this.minWeight_},t.prototype.getEstimate=function(){return this.canEstimate()?Math.min(this.fast_.getEstimate(),this.slow_.getEstimate()):this.defaultEstimate_},t.prototype.destroy=function(){},t}();e.a=n},function(t,e,r){"use strict";function i(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}var a=function(){function t(e){i(this,t),this.alpha_=e?Math.exp(Math.log(.5)/e):0,this.estimate_=0,this.totalWeight_=0}return t.prototype.sample=function(t,e){var r=Math.pow(this.alpha_,t);this.estimate_=e*(1-r)+r*this.estimate_,this.totalWeight_+=t},t.prototype.getTotalWeight=function(){return this.totalWeight_},t.prototype.getEstimate=function(){if(this.alpha_){var t=1-Math.pow(this.alpha_,this.totalWeight_);return this.estimate_/t}return this.estimate_},t}();e.a=a},function(t,e,r){"use strict";function i(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function a(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function n(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}var o=r(1),s=r(3),l=r(0),u=r(2),d=r(14),c=Object(d.a)(),h=function(t){function e(r){i(this,e);var n=a(this,t.call(this,r,o.a.MEDIA_ATTACHING,o.a.MEDIA_DETACHING,o.a.MANIFEST_PARSED,o.a.BUFFER_RESET,o.a.BUFFER_APPENDING,o.a.BUFFER_CODECS,o.a.BUFFER_EOS,o.a.BUFFER_FLUSHING,o.a.LEVEL_PTS_UPDATED,o.a.LEVEL_UPDATED));return n._msDuration=null,n._levelDuration=null,n._live=null,n._objectUrl=null,n.onsbue=n.onSBUpdateEnd.bind(n),n.onsbe=n.onSBUpdateError.bind(n),n.pendingTracks={},n.tracks={},n}return n(e,t),e.prototype.destroy=function(){s.a.prototype.destroy.call(this)},e.prototype.onLevelPtsUpdated=function(t){var e=t.type,r=this.tracks.audio;if("audio"===e&&r&&"audio/mpeg"===r.container){var i=this.sourceBuffer.audio;if(Math.abs(i.timestampOffset-t.start)>.1){var a=i.updating;try{i.abort()}catch(t){a=!0,l.b.warn("can not abort audio buffer: "+t)}a?this.audioTimestampOffset=t.start:(l.b.warn("change mpeg audio timestamp offset from "+i.timestampOffset+" to "+t.start),i.timestampOffset=t.start)}}},e.prototype.onManifestParsed=function(t){var e=t.audio,r=t.video||t.levels.length&&t.altAudio,i=0;t.altAudio&&(e||r)&&(i=(e?1:0)+(r?1:0),l.b.log(i+" sourceBuffer(s) expected")),this.sourceBufferNb=i},e.prototype.onMediaAttaching=function(t){var e=this.media=t.media;if(e){var r=this.mediaSource=new c;this.onmso=this.onMediaSourceOpen.bind(this),this.onmse=this.onMediaSourceEnded.bind(this),this.onmsc=this.onMediaSourceClose.bind(this),r.addEventListener("sourceopen",this.onmso),r.addEventListener("sourceended",this.onmse),r.addEventListener("sourceclose",this.onmsc),e.src=window.URL.createObjectURL(r),this._objectUrl=e.src}},e.prototype.onMediaDetaching=function(){l.b.log("media source detaching");var t=this.mediaSource;if(t){if("open"===t.readyState)try{t.endOfStream()}catch(t){l.b.warn("onMediaDetaching:"+t.message+" while calling endOfStream")}t.removeEventListener("sourceopen",this.onmso),t.removeEventListener("sourceended",this.onmse),t.removeEventListener("sourceclose",this.onmsc),this.media&&(window.URL.revokeObjectURL(this._objectUrl),this.media.src===this._objectUrl?(this.media.removeAttribute("src"),this.media.load()):l.b.warn("media.src was changed by a third party - skip cleanup")),this.mediaSource=null,this.media=null,this._objectUrl=null,this.pendingTracks={},this.tracks={},this.sourceBuffer={},this.flushRange=[],this.segments=[],this.appended=0}this.onmso=this.onmse=this.onmsc=null,this.hls.trigger(o.a.MEDIA_DETACHED)},e.prototype.onMediaSourceOpen=function(){l.b.log("media source opened"),this.hls.trigger(o.a.MEDIA_ATTACHED,{media:this.media});var t=this.mediaSource;t&&t.removeEventListener("sourceopen",this.onmso),this.checkPendingTracks()},e.prototype.checkPendingTracks=function(){var t=this.pendingTracks,e=Object.keys(t).length;e&&(this.sourceBufferNb<=e||0===this.sourceBufferNb)&&(this.createSourceBuffers(t),this.pendingTracks={},this.doAppending())},e.prototype.onMediaSourceClose=function(){l.b.log("media source closed")},e.prototype.onMediaSourceEnded=function(){l.b.log("media source ended")},e.prototype.onSBUpdateEnd=function(){if(this.audioTimestampOffset){var t=this.sourceBuffer.audio;l.b.warn("change mpeg audio timestamp offset from "+t.timestampOffset+" to "+this.audioTimestampOffset),t.timestampOffset=this.audioTimestampOffset,delete this.audioTimestampOffset}this._needsFlush&&this.doFlush(),this._needsEos&&this.checkEos(),this.appending=!1;var e=this.parent,r=this.segments.reduce(function(t,r){return r.parent===e?t+1:t},0),i={},a=this.sourceBuffer;for(var n in a)i[n]=a[n].buffered;this.hls.trigger(o.a.BUFFER_APPENDED,{parent:e,pending:r,timeRanges:i}),this._needsFlush||this.doAppending(),this.updateMediaElementDuration()},e.prototype.onSBUpdateError=function(t){l.b.error("sourceBuffer error:",t),this.hls.trigger(o.a.ERROR,{type:u.b.MEDIA_ERROR,details:u.a.BUFFER_APPENDING_ERROR,fatal:!1})},e.prototype.onBufferReset=function(){var t=this.sourceBuffer;for(var e in t){var r=t[e];try{this.mediaSource.removeSourceBuffer(r),r.removeEventListener("updateend",this.onsbue),r.removeEventListener("error",this.onsbe)}catch(t){}}this.sourceBuffer={},this.flushRange=[],this.segments=[],this.appended=0},e.prototype.onBufferCodecs=function(t){if(0===Object.keys(this.sourceBuffer).length){for(var e in t)this.pendingTracks[e]=t[e];var r=this.mediaSource;r&&"open"===r.readyState&&this.checkPendingTracks()}},e.prototype.createSourceBuffers=function(t){var e=this.sourceBuffer,r=this.mediaSource;for(var i in t)if(!e[i]){var a=t[i],n=a.levelCodec||a.codec,s=a.container+";codecs="+n;l.b.log("creating sourceBuffer("+s+")");try{var d=e[i]=r.addSourceBuffer(s);d.addEventListener("updateend",this.onsbue),d.addEventListener("error",this.onsbe),this.tracks[i]={codec:n,container:a.container},a.buffer=d}catch(t){l.b.error("error while trying to add sourceBuffer:"+t.message),this.hls.trigger(o.a.ERROR,{type:u.b.MEDIA_ERROR,details:u.a.BUFFER_ADD_CODEC_ERROR,fatal:!1,err:t,mimeType:s})}}this.hls.trigger(o.a.BUFFER_CREATED,{tracks:t})},e.prototype.onBufferAppending=function(t){this._needsFlush||(this.segments?this.segments.push(t):this.segments=[t],this.doAppending())},e.prototype.onBufferAppendFail=function(t){l.b.error("sourceBuffer error:",t.event),this.hls.trigger(o.a.ERROR,{type:u.b.MEDIA_ERROR,details:u.a.BUFFER_APPENDING_ERROR,fatal:!1})},e.prototype.onBufferEos=function(t){var e=this.sourceBuffer,r=t.type;for(var i in e)r&&i!==r||e[i].ended||(e[i].ended=!0,l.b.log(i+" sourceBuffer now EOS"));this.checkEos()},e.prototype.checkEos=function(){var t=this.sourceBuffer,e=this.mediaSource;if(!e||"open"!==e.readyState)return void(this._needsEos=!1);for(var r in t){var i=t[r];if(!i.ended)return;if(i.updating)return void(this._needsEos=!0)}l.b.log("all media data available, signal endOfStream() to MediaSource and stop loading fragment");try{e.endOfStream()}catch(t){l.b.warn("exception while calling mediaSource.endOfStream()")}this._needsEos=!1},e.prototype.onBufferFlushing=function(t){this.flushRange.push({start:t.startOffset,end:t.endOffset,type:t.type}),this.flushBufferCounter=0,this.doFlush()},e.prototype.onLevelUpdated=function(t){var e=t.details;e.fragments.length>0&&(this._levelDuration=e.totalduration+e.fragments[0].start,this._live=e.live,this.updateMediaElementDuration())},e.prototype.updateMediaElementDuration=function(){var t=this.hls.config,e=void 0;if(null!==this._levelDuration&&this.media&&this.mediaSource&&this.sourceBuffer&&0!==this.media.readyState&&"open"===this.mediaSource.readyState){for(var r in this.sourceBuffer)if(!0===this.sourceBuffer[r].updating)return;e=this.media.duration,null===this._msDuration&&(this._msDuration=this.mediaSource.duration),!0===this._live&&!0===t.liveDurationInfinity?(l.b.log("Media Source duration is set to Infinity"),this._msDuration=this.mediaSource.duration=1/0):(this._levelDuration>this._msDuration&&this._levelDuration>e||e===1/0||isNaN(e))&&(l.b.log("Updating Media Source duration to "+this._levelDuration.toFixed(3)),this._msDuration=this.mediaSource.duration=this._levelDuration)}},e.prototype.doFlush=function(){for(;this.flushRange.length;){var t=this.flushRange[0];if(!this.flushBuffer(t.start,t.end,t.type))return void(this._needsFlush=!0);this.flushRange.shift(),this.flushBufferCounter=0}if(0===this.flushRange.length){this._needsFlush=!1;var e=0,r=this.sourceBuffer;try{for(var i in r)e+=r[i].buffered.length}catch(t){l.b.error("error while accessing sourceBuffer.buffered")}this.appended=e,this.hls.trigger(o.a.BUFFER_FLUSHED)}},e.prototype.doAppending=function(){var t=this.hls,e=this.sourceBuffer,r=this.segments;if(Object.keys(e).length){if(this.media.error)return this.segments=[],void l.b.error("trying to append although a media error occured, flush segment and abort");if(this.appending)return;if(r&&r.length){var i=r.shift();try{var a=i.type,n=e[a];n?n.updating?r.unshift(i):(n.ended=!1,this.parent=i.parent,n.appendBuffer(i.data),this.appendError=0,this.appended++,this.appending=!0):this.onSBUpdateEnd()}catch(e){l.b.error("error while trying to append buffer:"+e.message),r.unshift(i);var s={type:u.b.MEDIA_ERROR,parent:i.parent};22!==e.code?(this.appendError?this.appendError++:this.appendError=1,s.details=u.a.BUFFER_APPEND_ERROR,this.appendError>t.config.appendErrorMaxRetry?(l.b.log("fail "+t.config.appendErrorMaxRetry+" times to append segment in sourceBuffer"),r=[],s.fatal=!0,t.trigger(o.a.ERROR,s)):(s.fatal=!1,t.trigger(o.a.ERROR,s))):(this.segments=[],s.details=u.a.BUFFER_FULL_ERROR,s.fatal=!1,t.trigger(o.a.ERROR,s))}}}},e.prototype.flushBuffer=function(t,e,r){var i=void 0,a=void 0,n=void 0,o=void 0,s=void 0,u=void 0,d=this.sourceBuffer;if(Object.keys(d).length){if(l.b.log("flushBuffer,pos/start/end: "+this.media.currentTime.toFixed(3)+"/"+t+"/"+e),this.flushBufferCounter.5)return this.flushBufferCounter++,l.b.log("flush "+c+" ["+s+","+u+"], of ["+n+","+o+"], pos:"+this.media.currentTime),i.remove(s,u),!1}catch(t){l.b.warn("exception while accessing sourcebuffer, it might have been removed from MediaSource")}}}else l.b.warn("abort flushing too many retries");l.b.log("buffer flushed")}return!0},e}(s.a);e.a=h},function(t,e,r){"use strict";function i(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function a(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function n(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}var o=r(1),s=r(3),l=function(){function t(t,e){for(var r=0;rthis.autoLevelCapping&&e.streamController.nextLevelSwitch(),this.autoLevelCapping=e.autoLevelCapping}}},e.prototype.getMaxLevel=function(t){var r=this;if(!this.levels)return-1;var i=this.levels.filter(function(i,a){return e.isLevelAllowed(a,r.restrictedLevels)&&a<=t});return e.getMaxLevelByMediaSize(i,this.mediaWidth,this.mediaHeight)},e.prototype._startCapping=function(){this.timer||(this.autoLevelCapping=Number.POSITIVE_INFINITY,this.hls.firstLevel=this.getMaxLevel(this.firstLevel),clearInterval(this.timer),this.timer=setInterval(this.detectPlayerSize.bind(this),1e3),this.detectPlayerSize())},e.prototype._stopCapping=function(){this.restrictedLevels=[],this.firstLevel=null,this.autoLevelCapping=Number.POSITIVE_INFINITY,this.timer&&(this.timer=clearInterval(this.timer),this.timer=null)},e.isLevelAllowed=function(t){return-1===(arguments.length>1&&void 0!==arguments[1]?arguments[1]:[]).indexOf(t)},e.getMaxLevelByMediaSize=function(t,e,r){if(!t||t&&!t.length)return-1;for(var i=t.length-1,a=0;a=e||n.height>=r)&&function(t,e){return!e||(t.width!==e.width||t.height!==e.height)}(n,t[a+1])){i=a;break}}return i},l(e,[{key:"mediaWidth",get:function(){var t=void 0,r=this.media;return r&&(t=r.width||r.clientWidth||r.offsetWidth,t*=e.contentScaleFactor),t}},{key:"mediaHeight",get:function(){var t=void 0,r=this.media;return r&&(t=r.height||r.clientHeight||r.offsetHeight,t*=e.contentScaleFactor),t}}],[{key:"contentScaleFactor",get:function(){var t=1;try{t=window.devicePixelRatio}catch(t){}return t}}]),e}(s.a);e.a=u},function(t,e,r){"use strict";function i(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function a(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function n(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}var o=r(1),s=r(3),l=r(0),u=window,d=u.performance,c=function(t){function e(r){return i(this,e),a(this,t.call(this,r,o.a.MEDIA_ATTACHING))}return n(e,t),e.prototype.destroy=function(){this.timer&&clearInterval(this.timer),this.isVideoPlaybackQualityAvailable=!1},e.prototype.onMediaAttaching=function(t){var e=this.hls.config;if(e.capLevelOnFPSDrop){"function"==typeof(this.video=t.media instanceof window.HTMLVideoElement?t.media:null).getVideoPlaybackQuality&&(this.isVideoPlaybackQualityAvailable=!0),clearInterval(this.timer),this.timer=setInterval(this.checkFPSInterval.bind(this),e.fpsDroppedMonitoringPeriod)}},e.prototype.checkFPS=function(t,e,r){var i=d.now();if(e){if(this.lastTime){var a=i-this.lastTime,n=r-this.lastDroppedFrames,s=e-this.lastDecodedFrames,u=1e3*n/a,c=this.hls;if(c.trigger(o.a.FPS_DROP,{currentDropped:n,currentDecoded:s,totalDroppedFrames:r}),u>0&&n>c.config.fpsDroppedMonitoringThreshold*s){var h=c.currentLevel;l.b.warn("drop FPS ratio greater than max allowed value for currentLevel: "+h),h>0&&(-1===c.autoLevelCapping||c.autoLevelCapping>=h)&&(h-=1,c.trigger(o.a.FPS_DROP_LEVEL_CAPPING,{level:h,droppedLevel:c.currentLevel}),c.autoLevelCapping=h,c.streamController.nextLevelSwitch())}}this.lastTime=i,this.lastDroppedFrames=r,this.lastDecodedFrames=e}},e.prototype.checkFPSInterval=function(){var t=this.video;if(t)if(this.isVideoPlaybackQualityAvailable){var e=t.getVideoPlaybackQuality();this.checkFPS(t,e.totalVideoFrames,e.droppedVideoFrames)}else this.checkFPS(t,t.webkitDecodedFrameCount,t.webkitDroppedFrameCount)},e}(s.a);e.a=c},function(t,e,r){"use strict";function i(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}var a=r(0),n=window,o=n.performance,s=n.XMLHttpRequest,l=function(){function t(e){i(this,t),e&&e.xhrSetup&&(this.xhrSetup=e.xhrSetup)}return t.prototype.destroy=function(){this.abort(),this.loader=null},t.prototype.abort=function(){var t=this.loader;t&&4!==t.readyState&&(this.stats.aborted=!0,t.abort()),window.clearTimeout(this.requestTimeout),this.requestTimeout=null,window.clearTimeout(this.retryTimeout),this.retryTimeout=null},t.prototype.load=function(t,e,r){this.context=t,this.config=e,this.callbacks=r,this.stats={trequest:o.now(),retry:0},this.retryDelay=e.retryDelay,this.loadInternal()},t.prototype.loadInternal=function(){var t=void 0,e=this.context;t=this.loader=new s;var r=this.stats;r.tfirst=0,r.loaded=0;var i=this.xhrSetup;try{if(i)try{i(t,e.url)}catch(r){t.open("GET",e.url,!0),i(t,e.url)}t.readyState||t.open("GET",e.url,!0)}catch(r){return void this.callbacks.onError({code:t.status,text:r.message},e,t)}e.rangeEnd&&t.setRequestHeader("Range","bytes="+e.rangeStart+"-"+(e.rangeEnd-1)),t.onreadystatechange=this.readystatechange.bind(this),t.onprogress=this.loadprogress.bind(this),t.responseType=e.responseType,this.requestTimeout=window.setTimeout(this.loadtimeout.bind(this),this.config.timeout),t.send()},t.prototype.readystatechange=function(t){var e=t.currentTarget,r=e.readyState,i=this.stats,n=this.context,s=this.config;if(!i.aborted&&r>=2)if(window.clearTimeout(this.requestTimeout),0===i.tfirst&&(i.tfirst=Math.max(o.now(),i.trequest)),4===r){var l=e.status;if(l>=200&&l<300){i.tload=Math.max(i.tfirst,o.now());var u=void 0,d=void 0;"arraybuffer"===n.responseType?(u=e.response,d=u.byteLength):(u=e.responseText,d=u.length),i.loaded=i.total=d;var c={url:e.responseURL,data:u};this.callbacks.onSuccess(c,i,n,e)}else i.retry>=s.maxRetry||l>=400&&l<499?(a.b.error(l+" while loading "+n.url),this.callbacks.onError({code:l,text:e.statusText},n,e)):(a.b.warn(l+" while loading "+n.url+", retrying in "+this.retryDelay+"..."),this.destroy(),this.retryTimeout=window.setTimeout(this.loadInternal.bind(this),this.retryDelay),this.retryDelay=Math.min(2*this.retryDelay,s.maxRetryDelay),i.retry++)}else this.requestTimeout=window.setTimeout(this.loadtimeout.bind(this),s.timeout)},t.prototype.loadtimeout=function(){a.b.warn("timeout while loading "+this.context.url),this.callbacks.onTimeout(this.stats,this.context,null)},t.prototype.loadprogress=function(t){var e=t.currentTarget,r=this.stats;r.loaded=t.loaded,t.lengthComputable&&(r.total=t.total);var i=this.callbacks.onProgress;i&&i(r,this.context,null,e)},t}();e.a=l},function(t,e,r){"use strict";function i(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function a(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function n(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}var o=r(1),s=r(8),l=r(0),u=r(2),d=function(){function t(t,e){for(var r=0;r=this.tracks.length)return void l.b.warn("Invalid audio track id:",t.id);if(l.b.log("audioTrack "+t.id+" loaded"),this.tracks[t.id].details=t.details,t.details.live&&!this.hasInterval()){var e=1e3*t.details.targetduration;this.setInterval(e)}!t.details.live&&this.hasInterval()&&this.clearInterval()},e.prototype.onAudioTrackSwitched=function(t){var e=this.tracks[t.id].groupId;e&&this.audioGroupId!==e&&(this.audioGroupId=e)},e.prototype.onLevelLoaded=function(t){var e=this.hls.levels[t.level];if(e.audioGroupIds){var r=e.audioGroupIds[e.urlId];this.audioGroupId!==r&&(this.audioGroupId=r,this._selectInitialAudioTrack())}},e.prototype.onError=function(t){t.type===u.b.NETWORK_ERROR&&(t.fatal&&this.clearInterval(),t.details===u.a.AUDIO_TRACK_LOAD_ERROR&&(l.b.warn("Network failure on audio-track id:",t.context.id),this._handleLoadError()))},e.prototype.doTick=function(){this._updateTrack(this.trackId)},e.prototype._selectInitialAudioTrack=function(){var t=this,e=this.tracks;if(e.length){var r=this.tracks[this.trackId],i=null;r&&(i=r.name);var a=e.filter(function(t){return t.default});a.length?e=a:l.b.warn("No default audio tracks defined");var n=!1,s=function(){e.forEach(function(e){n||t.audioGroupId&&e.groupId!==t.audioGroupId||i&&i!==e.name||(t.audioTrack=e.id,n=!0)})};s(),n||(i=null,s()),n||(l.b.error("No track found for running audio group-ID: "+this.audioGroupId),this.hls.trigger(o.a.ERROR,{type:u.b.MEDIA_ERROR,details:u.a.AUDIO_TRACK_LOAD_ERROR,fatal:!0}))}},e.prototype._needsTrackLoading=function(t){var e=t.details;return!e||(!!e.live||void 0)},e.prototype._loadTrackDetailsIfNeeded=function(t){if(this._needsTrackLoading(t)){var e=t.url,r=t.id;l.b.log("loading audio-track playlist for id: "+r),this.hls.trigger(o.a.AUDIO_TRACK_LOADING,{url:e,id:r})}},e.prototype._updateTrack=function(t){if(!(t<0||t>=this.tracks.length)){this.clearInterval(),this.trackId=t,l.b.log("trying to update audio-track "+t);var e=this.tracks[t];this._loadTrackDetailsIfNeeded(e)}},e.prototype._handleLoadError=function(){this.trackIdBlacklist[this.trackId]=!0;var t=this.trackId,e=this.tracks[t],r=e.name,i=e.language,a=e.groupId;l.b.warn("Loading failed on audio track id: "+t+", group-id: "+a+', name/language: "'+r+'" / "'+i+'"');for(var n=t,o=0;o no-op");if(t<0||t>=this.tracks.length)return void l.b.warn("Invalid id passed to audio-track controller");var e=this.tracks[t];l.b.log("Now switching to audio-track index "+t),this.clearInterval(),this.trackId=t;var r=e.url,i=e.type,a=e.id;this.hls.trigger(o.a.AUDIO_TRACK_SWITCHING,{id:a,type:i,url:r}),this._loadTrackDetailsIfNeeded(e)}}]),e}(s.a);e.a=c},function(t,e,r){"use strict";function i(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function a(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function n(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}var o=r(6),s=r(11),l=r(20),u=r(1),d=r(15),c=r(24),h=r(2),f=r(0),p=r(25),v=r(8),g=r(10),y=r(9),m=function(){function t(t,e){for(var r=0;r0&&-1===t?(f.b.log("audio:override startPosition with lastCurrentTime @"+e.toFixed(3)),this.state=T.IDLE):(this.lastCurrentTime=this.startPosition?this.startPosition:t,this.state=T.STARTING),this.nextLoadPosition=this.startPosition=this.lastCurrentTime,this.tick()}else this.startPosition=t,this.state=T.STOPPED},e.prototype.stopLoad=function(){var t=this.fragCurrent;t&&(t.loader&&t.loader.abort(),this.fragmentTracker.removeFragment(t),this.fragCurrent=null),this.fragPrevious=null,this.demuxer&&(this.demuxer.destroy(),this.demuxer=null),this.state=T.STOPPED},e.prototype.doTick=function(){var t=void 0,e=void 0,r=void 0,i=this.hls,a=i.config;switch(this.state){case T.ERROR:case T.PAUSED:case T.BUFFER_FLUSHING:break;case T.STARTING:this.state=T.WAITING_TRACK,this.loadedmetadata=!1;break;case T.IDLE:var n=this.tracks;if(!n)break;if(!this.media&&(this.startFragRequested||!a.startFragPrefetch))break;if(this.loadedmetadata)t=this.media.currentTime;else if(void 0===(t=this.nextLoadPosition))break;var l=this.mediaBuffer?this.mediaBuffer:this.media,d=this.videoBuffer?this.videoBuffer:this.media,c=s.a.bufferInfo(l,t,a.maxBufferHole),h=s.a.bufferInfo(d,t,a.maxBufferHole),v=c.len,y=c.end,m=this.fragPrevious,b=Math.min(a.maxBufferLength,a.maxMaxBufferLength),S=Math.max(b,h.len),R=this.audioSwitch,A=this.trackId;if((vL||c.nextStart))return;f.b.log("alt audio track ahead of main track, seek to start of alt audio track"),this.media.currentTime=L+.05}if(r.initSegment&&!r.initSegment.data)I=r.initSegment;else if(y<=L){if(I=_[0],null!==this.videoTrackCC&&I.cc!==this.videoTrackCC&&(I=Object(p.b)(_,this.videoTrackCC)),r.live&&I.loadIdx&&I.loadIdx===this.fragLoadIdx){var k=c.nextStart?c.nextStart:L;return f.b.log("no alt audio available @currentTime:"+this.media.currentTime+", seeking @"+(k+.05)),void(this.media.currentTime=k+.05)}}else{var O=void 0,C=a.maxFragLookUpTolerance,P=m?_[m.sn-_[0].sn+1]:void 0,x=function(t){var e=Math.min(C,t.duration);return t.start+t.duration-e<=y?1:t.start-e>y&&t.start?-1:0};yD-C&&(C=0),O=P&&!x(P)?P:o.a.search(_,x)):O=_[w-1],O&&(I=O,L=O.start,m&&I.level===m.level&&I.sn===m.sn&&(I.sn=N||M)&&(f.b.log("audioStreamController: retryDate reached, switch back to IDLE state"),this.state=T.IDLE);break;case T.WAITING_INIT_PTS:var U=this.videoTrackCC;if(void 0===this.initPTS[U])break;var B=this.waitingFragment;if(B){var G=B.frag.cc;U!==G?(e=this.tracks[this.trackId],e.details&&e.details.live&&(f.b.warn("Waiting fragment CC ("+G+") does not match video track CC ("+U+")"),this.waitingFragment=null,this.state=T.IDLE)):(this.state=T.FRAG_LOADING,this.onFragLoaded(this.waitingFragment),this.waitingFragment=null)}else this.state=T.IDLE;break;case T.STOPPED:case T.FRAG_LOADING:case T.PARSING:case T.PARSED:case T.ENDED:}},e.prototype.onMediaAttached=function(t){var e=this.media=this.mediaBuffer=t.media;this.onvseeking=this.onMediaSeeking.bind(this),this.onvended=this.onMediaEnded.bind(this),e.addEventListener("seeking",this.onvseeking),e.addEventListener("ended",this.onvended);var r=this.config;this.tracks&&r.autoStartLoad&&this.startLoad(r.startPosition)},e.prototype.onMediaDetaching=function(){var t=this.media;t&&t.ended&&(f.b.log("MSE detaching and video ended, reset startPosition"),this.startPosition=this.lastCurrentTime=0),t&&(t.removeEventListener("seeking",this.onvseeking),t.removeEventListener("ended",this.onvended),this.onvseeking=this.onvseeked=this.onvended=null),this.media=this.mediaBuffer=this.videoBuffer=null,this.loadedmetadata=!1,this.stopLoad()},e.prototype.onMediaSeeking=function(){this.state===T.ENDED&&(this.state=T.IDLE),this.media&&(this.lastCurrentTime=this.media.currentTime),this.tick()},e.prototype.onMediaEnded=function(){this.startPosition=this.lastCurrentTime=0},e.prototype.onAudioTracksUpdated=function(t){f.b.log("audio tracks updated"),this.tracks=t.audioTracks},e.prototype.onAudioTrackSwitching=function(t){var e=!!t.url;this.trackId=t.id,this.fragCurrent=null,this.state=T.PAUSED,this.waitingFragment=null,e?this.setInterval(100):this.demuxer&&(this.demuxer.destroy(),this.demuxer=null),e&&(this.audioSwitch=!0,this.state=T.IDLE),this.tick()},e.prototype.onAudioTrackLoaded=function(t){var e=t.details,r=t.id,i=this.tracks[r],a=e.totalduration,n=0;if(f.b.log("track "+r+" loaded ["+e.startSN+","+e.endSN+"],duration:"+a),e.live){var o=i.details;o&&e.fragments.length>0?(d.b(o,e),n=e.fragments[0].start,e.PTSKnown?f.b.log("live audio playlist sliding:"+n.toFixed(3)):f.b.log("live audio playlist - outdated PTS, unknown sliding")):(e.PTSKnown=!1,f.b.log("live audio playlist - first load, unknown sliding"))}else e.PTSKnown=!1;if(i.details=e,!this.startFragRequested){if(-1===this.startPosition){var s=e.startTimeOffset;isNaN(s)?this.startPosition=0:(f.b.log("start time offset found in playlist, adjust startPosition to "+s),this.startPosition=s)}this.nextLoadPosition=this.startPosition}this.state===T.WAITING_TRACK&&(this.state=T.IDLE),this.tick()},e.prototype.onKeyLoaded=function(){this.state===T.KEY_LOADING&&(this.state=T.IDLE,this.tick())},e.prototype.onFragLoaded=function(t){var e=this.fragCurrent,r=t.frag;if(this.state===T.FRAG_LOADING&&e&&"audio"===r.type&&r.level===e.level&&r.sn===e.sn){var i=this.tracks[this.trackId],a=i.details,n=a.totalduration,o=e.level,s=e.sn,d=e.cc,c=this.config.defaultAudioCodec||i.audioCodec||"mp4a.40.2",h=this.stats=t.stats;if("initSegment"===s)this.state=T.IDLE,h.tparsed=h.tbuffered=E.now(),a.initSegment.data=t.payload,this.hls.trigger(u.a.FRAG_BUFFERED,{stats:h,frag:e,id:"audio"}),this.tick();else{this.state=T.PARSING,this.appended=!1,this.demuxer||(this.demuxer=new l.a(this.hls,"audio"));var p=this.initPTS[d],v=a.initSegment?a.initSegment.data:[];if(a.initSegment||void 0!==p){this.pendingBuffering=!0,f.b.log("Demuxing "+s+" of ["+a.startSN+" ,"+a.endSN+"],track "+o);this.demuxer.push(t.payload,v,c,null,e,n,!1,p)}else f.b.log("unknown video PTS for continuity counter "+d+", waiting for video PTS before demuxing audio frag "+s+" of ["+a.startSN+" ,"+a.endSN+"],track "+o),this.waitingFragment=t,this.state=T.WAITING_INIT_PTS}}this.fragLoadError=0},e.prototype.onFragParsingInitSegment=function(t){var e=this.fragCurrent,r=t.frag;if(e&&"audio"===t.id&&r.sn===e.sn&&r.level===e.level&&this.state===T.PARSING){var i=t.tracks,a=void 0;if(i.video&&delete i.video,a=i.audio){a.levelCodec=a.codec,a.id=t.id,this.hls.trigger(u.a.BUFFER_CODECS,i),f.b.log("audio track:audio,container:"+a.container+",codecs[level/parsed]=["+a.levelCodec+"/"+a.codec+"]");var n=a.initSegment;if(n){var o={type:"audio",data:n,parent:"audio",content:"initSegment"};this.audioSwitch?this.pendingData=[o]:(this.appended=!0,this.pendingBuffering=!0,this.hls.trigger(u.a.BUFFER_APPENDING,o))}this.tick()}}},e.prototype.onFragParsingData=function(t){var e=this,r=this.fragCurrent,i=t.frag;if(r&&"audio"===t.id&&"audio"===t.type&&i.sn===r.sn&&i.level===r.level&&this.state===T.PARSING){var a=this.trackId,n=this.tracks[a],o=this.hls;isNaN(t.endPTS)&&(t.endPTS=t.startPTS+r.duration,t.endDTS=t.startDTS+r.duration),r.addElementaryStream(y.a.ElementaryStreamTypes.AUDIO),f.b.log("parsed "+t.type+",PTS:["+t.startPTS.toFixed(3)+","+t.endPTS.toFixed(3)+"],DTS:["+t.startDTS.toFixed(3)+"/"+t.endDTS.toFixed(3)+"],nb:"+t.nb),d.c(n.details,r,t.startPTS,t.endPTS);var s=this.audioSwitch,l=this.media,c=!1;if(s&&l)if(l.readyState){var p=l.currentTime;f.b.log("switching audio track : currentTime:"+p),p>=t.startPTS&&(f.b.log("switching audio track : flushing all audio"),this.state=T.BUFFER_FLUSHING,o.trigger(u.a.BUFFER_FLUSHING,{startOffset:0,endOffset:Number.POSITIVE_INFINITY,type:"audio"}),c=!0,this.audioSwitch=!1,o.trigger(u.a.AUDIO_TRACK_SWITCHED,{id:a}))}else this.audioSwitch=!1,o.trigger(u.a.AUDIO_TRACK_SWITCHED,{id:a});var v=this.pendingData;if(!v)return f.b.warn("Apparently attempt to enqueue media payload without codec initialization data upfront"),void o.trigger(u.a.ERROR,{type:h.b.MEDIA_ERROR,details:null,fatal:!0});this.audioSwitch||([t.data1,t.data2].forEach(function(e){e&&e.length&&v.push({type:t.type,data:e,parent:"audio",content:"data"})}),!c&&v.length&&(v.forEach(function(t){e.state===T.PARSING&&(e.pendingBuffering=!0,e.hls.trigger(u.a.BUFFER_APPENDING,t))}),this.pendingData=[],this.appended=!0)),this.tick()}},e.prototype.onFragParsed=function(t){var e=this.fragCurrent,r=t.frag;e&&"audio"===t.id&&r.sn===e.sn&&r.level===e.level&&this.state===T.PARSING&&(this.stats.tparsed=E.now(),this.state=T.PARSED,this._checkAppendedParsed())},e.prototype.onBufferReset=function(){this.mediaBuffer=this.videoBuffer=null,this.loadedmetadata=!1},e.prototype.onBufferCreated=function(t){var e=t.tracks.audio;e&&(this.mediaBuffer=e.buffer,this.loadedmetadata=!0),t.tracks.video&&(this.videoBuffer=t.tracks.video.buffer)},e.prototype.onBufferAppended=function(t){if("audio"===t.parent){var e=this.state;e!==T.PARSING&&e!==T.PARSED||(this.pendingBuffering=t.pending>0,this._checkAppendedParsed())}},e.prototype._checkAppendedParsed=function(){if(!(this.state!==T.PARSED||this.appended&&this.pendingBuffering)){var t=this.fragCurrent,e=this.stats,r=this.hls;if(t){this.fragPrevious=t,e.tbuffered=E.now(),r.trigger(u.a.FRAG_BUFFERED,{stats:e,frag:t,id:"audio"});var i=this.mediaBuffer?this.mediaBuffer:this.media;f.b.log("audio buffered : "+c.a.toString(i.buffered)),this.audioSwitch&&this.appended&&(this.audioSwitch=!1,r.trigger(u.a.AUDIO_TRACK_SWITCHED,{id:this.trackId})),this.state=T.IDLE}this.tick()}},e.prototype.onError=function(t){var e=t.frag;if(!e||"audio"===e.type)switch(t.details){case h.a.FRAG_LOAD_ERROR:case h.a.FRAG_LOAD_TIMEOUT:var r=t.frag;if(r&&"audio"!==r.type)break;if(!t.fatal){var i=this.fragLoadError;i?i++:i=1;var a=this.config;if(i<=a.fragLoadingMaxRetry){this.fragLoadError=i;var n=Math.min(Math.pow(2,i-1)*a.fragLoadingRetryDelay,a.fragLoadingMaxRetryTimeout);f.b.warn("AudioStreamController: frag loading failed, retry in "+n+" ms"),this.retryDate=E.now()+n,this.state=T.FRAG_LOADING_WAITING_RETRY}else f.b.error("AudioStreamController: "+t.details+" reaches max retry, redispatch as fatal ..."),t.fatal=!0,this.state=T.ERROR}break;case h.a.AUDIO_TRACK_LOAD_ERROR:case h.a.AUDIO_TRACK_LOAD_TIMEOUT:case h.a.KEY_LOAD_ERROR:case h.a.KEY_LOAD_TIMEOUT:this.state!==T.ERROR&&(this.state=t.fatal?T.ERROR:T.IDLE,f.b.warn("AudioStreamController: "+t.details+" while loading frag, now switching to "+this.state+" state ..."));break;case h.a.BUFFER_FULL_ERROR:if("audio"===t.parent&&(this.state===T.PARSING||this.state===T.PARSED)){var o=this.mediaBuffer,l=this.media.currentTime;if(o&&s.a.isBuffered(o,l)&&s.a.isBuffered(o,l+.5)){var d=this.config;d.maxMaxBufferLength>=d.maxBufferLength&&(d.maxMaxBufferLength/=2,f.b.warn("AudioStreamController: reduce max buffer length to "+d.maxMaxBufferLength+"s")),this.state=T.IDLE}else f.b.warn("AudioStreamController: buffer full error also media.currentTime is not buffered, flush audio buffer"),this.fragCurrent=null,this.state=T.BUFFER_FLUSHING,this.hls.trigger(u.a.BUFFER_FLUSHING,{startOffset:0,endOffset:Number.POSITIVE_INFINITY,type:"audio"})}}},e.prototype.onBufferFlushed=function(){var t=this,e=this.pendingData;e&&e.length?(f.b.log("AudioStreamController: appending pending audio data after buffer flushed"),e.forEach(function(e){t.hls.trigger(u.a.BUFFER_APPENDING,e)}),this.appended=!0,this.pendingData=[],this.state=T.PARSED):(this.state=T.IDLE,this.fragPrevious=null,this.tick())},m(e,[{key:"state",set:function(t){if(this.state!==t){var e=this.state;this._state=t,f.b.log("audio stream:"+e+"->"+t)}},get:function(){return this._state}}]),e}(v.a);e.a=S},function(t,e,r){"use strict";function i(t,e,r,i){for(var n=void 0,o=void 0,s=void 0,l=void 0,u=void 0,d=window.VTTCue||window.TextTrackCue,c=0;c=16?l--:l++,navigator.userAgent.match(/Firefox\//)?o.line=c+1:o.line=c>7?c-2:c+1,o.align="left",o.position=Math.max(0,Math.min(100,l/32*100+(navigator.userAgent.match(/Firefox\//)?50:0))),t.addCue(o)}}Object.defineProperty(e,"__esModule",{value:!0}),e.newCue=i;var a=r(27)},function(t,e,r){"use strict";e.a=function(){function t(t){return"string"==typeof t&&(!!n[t.toLowerCase()]&&t.toLowerCase())}function e(t){return"string"==typeof t&&(!!o[t.toLowerCase()]&&t.toLowerCase())}function r(t){for(var e=1;e100)throw new Error("Position must be between 0 and 100.");E=t,this.hasBeenReset=!0}})),Object.defineProperty(s,"positionAlign",r({},u,{get:function(){return T},set:function(t){var r=e(t);if(!r)throw new SyntaxError("An invalid or illegal string was specified.");T=r,this.hasBeenReset=!0}})),Object.defineProperty(s,"size",r({},u,{get:function(){return S},set:function(t){if(t<0||t>100)throw new Error("Size must be between 0 and 100.");S=t,this.hasBeenReset=!0}})),Object.defineProperty(s,"align",r({},u,{get:function(){return R},set:function(t){var r=e(t);if(!r)throw new SyntaxError("An invalid or illegal string was specified.");R=r,this.hasBeenReset=!0}})),s.displayState=void 0,l)return s}if("undefined"!=typeof window&&window.VTTCue)return window.VTTCue;var a="auto",n={"":!0,lr:!0,rl:!0},o={start:!0,middle:!0,end:!0,left:!0,right:!0};return i.prototype.getCueAsHTML=function(){return window.WebVTT.convertCueToDOMTree(window,this.text)},i}()},function(t,e,r){"use strict";function i(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function a(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function n(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}function o(t,e){return t&&t.label===e.name&&!(t.textTrack1||t.textTrack2)}function s(t,e,r,i){return Math.min(e,i)-Math.max(t,r)}var l=r(1),u=r(3),d=r(65),c=r(66),h=r(67),f=r(0),p=r(26),v=function(t){function e(r){i(this,e);var n=a(this,t.call(this,r,l.a.MEDIA_ATTACHING,l.a.MEDIA_DETACHING,l.a.FRAG_PARSING_USERDATA,l.a.FRAG_DECRYPTED,l.a.MANIFEST_LOADING,l.a.MANIFEST_LOADED,l.a.FRAG_LOADED,l.a.LEVEL_SWITCHING,l.a.INIT_PTS_FOUND));if(n.hls=r,n.config=r.config,n.enabled=!0,n.Cues=r.config.cueHandler,n.textTracks=[],n.tracks=[],n.unparsedVttFrags=[],n.initPTS=void 0,n.cueRanges=[],n.captionsTracks={},n.captionsProperties={textTrack1:{label:n.config.captionsTextTrack1Label,languageCode:n.config.captionsTextTrack1LanguageCode},textTrack2:{label:n.config.captionsTextTrack2Label,languageCode:n.config.captionsTextTrack2LanguageCode}},n.config.enableCEA708Captions){var o=new c.a(n,"textTrack1"),s=new c.a(n,"textTrack2");n.cea608Parser=new d.a(0,o,s)}return n}return n(e,t),e.prototype.addCues=function(t,e,r,i){for(var a=this.cueRanges,n=!1,o=a.length;o--;){var l=a[o],u=s(l[0],l[1],e,r);if(u>=0&&(l[0]=Math.min(l[0],e),l[1]=Math.max(l[1],r),n=!0,u/(r-e)>.5))return}n||a.push([e,r]),this.Cues.newCue(this.captionsTracks[t],e,r,i)},e.prototype.onInitPtsFound=function(t){var e=this;void 0===this.initPTS&&(this.initPTS=t.initPTS),this.unparsedVttFrags.length&&(this.unparsedVttFrags.forEach(function(t){e.onFragLoaded(t)}),this.unparsedVttFrags=[])},e.prototype.getExistingTrack=function(t){var e=this.media;if(e)for(var r=0;rs&&(f.log("ERROR","Too large cursor position "+this.pos),this.pos=s)},t.prototype.moveCursor=function(t){var e=this.pos+t;if(t>1)for(var r=this.pos+1;r=144&&this.backSpace();var e=n(t);if(this.pos>=s)return void f.log("ERROR","Cannot insert "+t.toString(16)+" ("+e+") at position "+this.pos+". Skipping it!");this.chars[this.pos].setChar(e,this.currPenState),this.moveCursor(1)},t.prototype.clearFromPos=function(t){var e=void 0;for(e=t;e0&&(r=t?"["+e.join(" | ")+"]":e.join("\n")),r},t.prototype.getTextAndFormat=function(){return this.rows},t}(),b=function(){function t(e,r){i(this,t),this.chNr=e,this.outputFilter=r,this.mode=null,this.verbose=0,this.displayedMemory=new m,this.nonDisplayedMemory=new m,this.lastOutputScreen=new m,this.currRollUpRow=this.displayedMemory.rows[o-1],this.writeScreen=this.displayedMemory,this.mode=null,this.cueStartTime=null}return t.prototype.reset=function(){this.mode=null,this.displayedMemory.reset(),this.nonDisplayedMemory.reset(),this.lastOutputScreen.reset(),this.currRollUpRow=this.displayedMemory.rows[o-1],this.writeScreen=this.displayedMemory,this.mode=null,this.cueStartTime=null,this.lastCueEndTime=null},t.prototype.getHandler=function(){return this.outputFilter},t.prototype.setHandler=function(t){this.outputFilter=t},t.prototype.setPAC=function(t){this.writeScreen.setPAC(t)},t.prototype.setBkgData=function(t){this.writeScreen.setBkgData(t)},t.prototype.setMode=function(t){t!==this.mode&&(this.mode=t,f.log("INFO","MODE="+t),"MODE_POP-ON"===this.mode?this.writeScreen=this.nonDisplayedMemory:(this.writeScreen=this.displayedMemory,this.writeScreen.reset()),"MODE_ROLL-UP"!==this.mode&&(this.displayedMemory.nrRollUpRows=null,this.nonDisplayedMemory.nrRollUpRows=null),this.mode=t)},t.prototype.insertChars=function(t){for(var e=0;e=46,e.italics)e.foreground="white";else{var r=Math.floor(t/2)-16,i=["white","green","blue","cyan","red","yellow","magenta"];e.foreground=i[r]}f.log("INFO","MIDROW: "+JSON.stringify(e)),this.writeScreen.setPen(e)},t.prototype.outputDataUpdate=function(){var t=arguments.length>0&&void 0!==arguments[0]&&arguments[0],e=f.time;null!==e&&this.outputFilter&&(null!==this.cueStartTime||this.displayedMemory.isEmpty()?this.displayedMemory.equals(this.lastOutputScreen)||(this.outputFilter.newCue&&(this.outputFilter.newCue(this.cueStartTime,e,this.lastOutputScreen),!0===t&&this.outputFilter.dispatchCue&&this.outputFilter.dispatchCue()),this.cueStartTime=this.displayedMemory.isEmpty()?null:e):this.cueStartTime=e,this.lastOutputScreen.copy(this.displayedMemory))},t.prototype.cueSplitAtTime=function(t){this.outputFilter&&(this.displayedMemory.isEmpty()||(this.outputFilter.newCue&&this.outputFilter.newCue(this.cueStartTime,t,this.displayedMemory),this.cueStartTime=t))},t}(),E=function(){function t(e,r,a){i(this,t),this.field=e||1,this.outputs=[r,a],this.channels=[new b(1,r),new b(2,a)],this.currChNr=-1,this.lastCmdA=null,this.lastCmdB=null,this.bufferedData=[],this.startTime=null,this.lastTime=null,this.dataCounters={padding:0,char:0,cmd:0,other:0}}return t.prototype.getHandler=function(t){return this.channels[t].getHandler()},t.prototype.setHandler=function(t,e){this.channels[t].setHandler(e)},t.prototype.addData=function(t,e){var r=void 0,i=void 0,a=void 0,n=!1;this.lastTime=t,f.setTime(t);for(var o=0;o ("+p([i,a])+")"),r=this.parseCmd(i,a),r||(r=this.parseMidrow(i,a)),r||(r=this.parsePAC(i,a)),r||(r=this.parseBackgroundAttributes(i,a)),!r&&(n=this.parseChars(i,a)))if(this.currChNr&&this.currChNr>=0){var s=this.channels[this.currChNr-1];s.insertChars(n)}else f.log("WARNING","No channel found yet. TEXT-MODE?");r?this.dataCounters.cmd+=2:n?this.dataCounters.char+=2:(this.dataCounters.other+=2,f.log("WARNING","Couldn't parse cleaned data "+p([i,a])+" orig: "+p([e[o],e[o+1]])))}else this.dataCounters.padding+=2},t.prototype.parseCmd=function(t,e){var r=null,i=(20===t||28===t)&&e>=32&&e<=47,a=(23===t||31===t)&&e>=33&&e<=35;if(!i&&!a)return!1;if(t===this.lastCmdA&&e===this.lastCmdB)return this.lastCmdA=null,this.lastCmdB=null,f.log("DEBUG","Repeated command ("+p([t,e])+") is dropped"),!0;r=20===t||23===t?1:2;var n=this.channels[r-1];return 20===t||28===t?32===e?n.ccRCL():33===e?n.ccBS():34===e?n.ccAOF():35===e?n.ccAON():36===e?n.ccDER():37===e?n.ccRU(2):38===e?n.ccRU(3):39===e?n.ccRU(4):40===e?n.ccFON():41===e?n.ccRDC():42===e?n.ccTR():43===e?n.ccRTD():44===e?n.ccEDM():45===e?n.ccCR():46===e?n.ccENM():47===e&&n.ccEOC():n.ccTO(e-32),this.lastCmdA=t,this.lastCmdB=e,this.currChNr=r,!0},t.prototype.parseMidrow=function(t,e){var r=null;if((17===t||25===t)&&e>=32&&e<=47){if((r=17===t?1:2)!==this.currChNr)return f.log("ERROR","Mismatch channel in midrow parsing"),!1;return this.channels[r-1].ccMIDROW(e),f.log("DEBUG","MIDROW ("+p([t,e])+")"),!0}return!1},t.prototype.parsePAC=function(t,e){var r=null,i=null,a=(t>=17&&t<=23||t>=25&&t<=31)&&e>=64&&e<=127,n=(16===t||24===t)&&e>=64&&e<=95;if(!a&&!n)return!1;if(t===this.lastCmdA&&e===this.lastCmdB)return this.lastCmdA=null,this.lastCmdB=null,!0;r=t<=23?1:2,i=e>=64&&e<=95?1===r?l[t]:d[t]:1===r?u[t]:c[t];var o=this.interpretPAC(i,e);return this.channels[r-1].setPAC(o),this.lastCmdA=t,this.lastCmdB=e,this.currChNr=r,!0},t.prototype.interpretPAC=function(t,e){var r=e,i={color:null,italics:!1,indent:null,underline:!1,row:t};return r=e>95?e-96:e-64,i.underline=1==(1&r),r<=13?i.color=["white","green","blue","cyan","red","yellow","magenta","white"][Math.floor(r/2)]:r<=15?(i.italics=!0,i.color="white"):i.indent=4*Math.floor((r-16)/2),i},t.prototype.parseChars=function(t,e){var r=null,i=null,a=null;if(t>=25?(r=2,a=t-8):(r=1,a=t),a>=17&&a<=19){var o=e;o=17===a?e+80:18===a?e+112:e+144,f.log("INFO","Special char '"+n(o)+"' in channel "+r),i=[o]}else t>=32&&t<=127&&(i=0===e?[t]:[t,e]);if(i){var s=p(i);f.log("DEBUG","Char codes = "+s.join(",")),this.lastCmdA=null,this.lastCmdB=null}return i},t.prototype.parseBackgroundAttributes=function(t,e){var r=void 0,i=void 0,a=void 0,n=void 0,o=(16===t||24===t)&&e>=32&&e<=47,s=(23===t||31===t)&&e>=45&&e<=47;return!(!o&&!s)&&(r={},16===t||24===t?(i=Math.floor((e-32)/2),r.background=h[i],e%2==1&&(r.background=r.background+"_semi")):45===e?r.background="transparent":(r.foreground="black",47===e&&(r.underline=!0)),a=t<24?1:2,n=this.channels[a-1],n.setBkgData(r),this.lastCmdA=null,this.lastCmdB=null,!0)},t.prototype.reset=function(){for(var t=0;tt)&&(this.startTime=t),this.endTime=e,this.screen=r,this.timelineController.createCaptionsTrack(this.trackName)},t}();e.a=a},function(t,e,r){"use strict";var i=r(27),a=r(7),n=function(t,e,r){return t.substr(r||0,e.length)===e},o=function(t){var e=parseInt(t.substr(-3)),r=parseInt(t.substr(-6,2)),i=parseInt(t.substr(-9,2)),a=t.length>9?parseInt(t.substr(0,t.indexOf(":"))):0;return isNaN(e)||isNaN(r)||isNaN(i)||isNaN(a)?-1:(e+=1e3*r,e+=6e4*i,e+=36e5*a)},s=function(t){for(var e=5381,r=t.length;r;)e=33*e^t.charCodeAt(--r);return(e>>>0).toString()},l=function(t,e,r){var i=t[e],a=t[i.prevCC];if(!a||!a.new&&i.new)return t.ccOffset=t.presentationOffset=i.start,void(i.new=!1);for(;a&&a.new;)t.ccOffset+=i.start-a.start,i.new=!1,i=a,a=t[i.prevCC];t.presentationOffset=r},u={parse:function(t,e,r,u,d,c){var h=/\r\n|\n\r|\n|\r/g,f=Object(a.b)(new Uint8Array(t)).trim().replace(h,"\n").split("\n"),p="00:00.000",v=0,g=0,y=0,m=[],b=void 0,E=!0,T=new i.a;T.oncue=function(t){var e=r[u],i=r.ccOffset;e&&e.new&&(void 0!==g?i=r.ccOffset=e.start:l(r,u,y)),y&&(i=y+r.ccOffset-r.presentationOffset),t.startTime+=i-g,t.endTime+=i-g,t.id=s(t.startTime.toString())+s(t.endTime.toString())+s(t.text),t.text=decodeURIComponent(encodeURIComponent(t.text)),t.endTime>0&&m.push(t)},T.onparsingerror=function(t){b=t},T.onflush=function(){if(b&&c)return void c(b);d(m)},f.forEach(function(t){if(E){if(n(t,"X-TIMESTAMP-MAP=")){E=!1,t.substr(16).split(",").forEach(function(t){n(t,"LOCAL:")?p=t.substr(6):n(t,"MPEGTS:")&&(v=parseInt(t.substr(7)))});try{e=e<0?e+8589934592:e,v-=e,g=o(p)/1e3,y=v/9e4,-1===g&&(b=new Error("Malformed X-TIMESTAMP-MAP: "+t))}catch(e){b=new Error("Malformed X-TIMESTAMP-MAP: "+t)}return}""===t&&(E=!1)}T.parse(t+"\n")}),T.flush()}};e.a=u},function(t,e,r){"use strict";function i(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function a(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function n(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}function o(t){for(var e=[],r=0;r=r.length)&&(this._stopTimer(),this.trackId=t,u.b.log("switching to subtitle track "+t),e.trigger(s.a.SUBTITLE_TRACK_SWITCH,{id:t}),-1!==t)){var i=r[t],a=i.details;a&&!a.live||(u.b.log("(re)loading playlist for subtitle track "+t),e.trigger(s.a.SUBTITLE_TRACK_LOADING,{url:i.url,id:t}))}},e.prototype._stopTimer=function(){this.timer&&(clearInterval(this.timer),this.timer=null)},e.prototype._toggleTrackModes=function(t){var e=this.media,r=this.subtitleDisplay,i=this.trackId;if(e){var a=o(e.textTracks);if(-1===t)[].slice.call(a).forEach(function(t){t.mode="disabled"});else{var n=a[i];n&&(n.mode="disabled")}var s=a[t];s&&(s.mode=r?"showing":"hidden")}},d(e,[{key:"subtitleTracks",get:function(){return this.tracks}},{key:"subtitleTrack",get:function(){return this.trackId},set:function(t){this.trackId!==t&&(this._toggleTrackModes(t),this.setSubtitleTrackInternal(t))}}]),e}(l.a);e.a=c},function(t,e,r){"use strict";function i(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function a(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function n(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}var o=r(1),s=r(0),l=r(13),u=r(8),d=window,c=d.performance,h={STOPPED:"STOPPED",IDLE:"IDLE",KEY_LOADING:"KEY_LOADING",FRAG_LOADING:"FRAG_LOADING"},f=function(t){function e(r){i(this,e);var n=a(this,t.call(this,r,o.a.MEDIA_ATTACHED,o.a.ERROR,o.a.KEY_LOADED,o.a.FRAG_LOADED,o.a.SUBTITLE_TRACKS_UPDATED,o.a.SUBTITLE_TRACK_SWITCH,o.a.SUBTITLE_TRACK_LOADED,o.a.SUBTITLE_FRAG_PROCESSED));return n.config=r.config,n.vttFragSNsProcessed={},n.vttFragQueues=void 0,n.currentlyProcessing=null,n.state=h.STOPPED,n.currentTrackId=-1,n.decrypter=new l.a(r.observer,r.config),n}return n(e,t),e.prototype.onHandlerDestroyed=function(){this.state=h.STOPPED},e.prototype.clearVttFragQueues=function(){var t=this;this.vttFragQueues={},this.tracks.forEach(function(e){t.vttFragQueues[e.id]=[]})},e.prototype.nextFrag=function(){if(null===this.currentlyProcessing&&this.currentTrackId>-1&&this.vttFragQueues[this.currentTrackId].length){var t=this.currentlyProcessing=this.vttFragQueues[this.currentTrackId].shift();this.fragCurrent=t,this.hls.trigger(o.a.FRAG_LOADING,{frag:t}),this.state=h.FRAG_LOADING}},e.prototype.onSubtitleFragProcessed=function(t){t.success&&this.vttFragSNsProcessed[t.frag.trackId].push(t.frag.sn),this.currentlyProcessing=null,this.state=h.IDLE,this.nextFrag()},e.prototype.onMediaAttached=function(){this.state=h.IDLE},e.prototype.onError=function(t){var e=t.frag;e&&"subtitle"!==e.type||this.currentlyProcessing&&(this.currentlyProcessing=null,this.nextFrag())},e.prototype.doTick=function(){var t=this;switch(this.state){case h.IDLE:var e=this.tracks,r=this.currentTrackId,i=this.vttFragSNsProcessed[r],a=this.vttFragQueues[r],n=this.currentlyProcessing?this.currentlyProcessing.sn:-1,l=function(t){return i.indexOf(t.sn)>-1},u=function(t){return a.some(function(e){return e.sn===t.sn})};if(!e)break;var d;if(r0&&null!=r&&null!=r.key&&"AES-128"===r.method){var n=void 0;try{n=c.now()}catch(t){n=Date.now()}this.decrypter.decrypt(t.payload,r.key.buffer,r.iv.buffer,function(t){var e=void 0;try{e=c.now()}catch(t){e=Date.now()}a.trigger(o.a.FRAG_DECRYPTED,{frag:i,payload:t,stats:{tstart:n,tdecrypt:e}})})}},e}(u.a);e.a=f},function(t,e,r){"use strict";function i(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function a(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function n(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}var o=r(3),s=r(1),l=r(2),u=r(0),d=function(){function t(t,e){for(var r=0;r1){var s=arguments[1];void 0!==s&&(o=s?Number(s):0)!=o&&(o=0)}var l=Math.min(Math.max(o,0),i),u=l-n;if(u<0)return!1;for(var d=-1;++d " + e + } + + function n(t) { + var e = c.console[t]; + return e ? function() { + for (var r = arguments.length, i = Array(r), n = 0; n < r; n++) i[n] = arguments[n]; + i[0] && (i[0] = a(t, i[0])), e.apply(c.console, i) + } : i + } + + function o(t) { + for (var e = arguments.length, r = Array(e > 1 ? e - 1 : 0), i = 1; i < e; i++) r[i - 1] = arguments[i]; + r.forEach(function(e) { + d[e] = t[e] ? t[e].bind(t) : n(e) + }) + } + r.d(e, "a", function() { + return h + }), r.d(e, "b", function() { + return f + }); + var s = r(4), + l = "function" == typeof Symbol && "symbol" == typeof Symbol.iterator ? function(t) { + return typeof t + } : function(t) { + return t && "function" == typeof Symbol && t.constructor === Symbol && t !== Symbol.prototype ? "symbol" : typeof t + }, + u = { + trace: i, + debug: i, + log: i, + warn: i, + info: i, + error: i + }, + d = u, + c = Object(s.a)(), + h = function(t) { + if (!0 === t || "object" === (void 0 === t ? "undefined" : l(t))) { + o(t, "debug", "log", "info", "warn", "error"); + try { + d.log() + } catch (t) { + d = u + } + } else d = u + }, + f = d + }, function(t, e, r) { + "use strict"; + var i = { + MEDIA_ATTACHING: "hlsMediaAttaching", + MEDIA_ATTACHED: "hlsMediaAttached", + MEDIA_DETACHING: "hlsMediaDetaching", + MEDIA_DETACHED: "hlsMediaDetached", + BUFFER_RESET: "hlsBufferReset", + BUFFER_CODECS: "hlsBufferCodecs", + BUFFER_CREATED: "hlsBufferCreated", + BUFFER_APPENDING: "hlsBufferAppending", + BUFFER_APPENDED: "hlsBufferAppended", + BUFFER_EOS: "hlsBufferEos", + BUFFER_FLUSHING: "hlsBufferFlushing", + BUFFER_FLUSHED: "hlsBufferFlushed", + MANIFEST_LOADING: "hlsManifestLoading", + MANIFEST_LOADED: "hlsManifestLoaded", + MANIFEST_PARSED: "hlsManifestParsed", + LEVEL_SWITCHING: "hlsLevelSwitching", + LEVEL_SWITCHED: "hlsLevelSwitched", + LEVEL_LOADING: "hlsLevelLoading", + LEVEL_LOADED: "hlsLevelLoaded", + LEVEL_UPDATED: "hlsLevelUpdated", + LEVEL_PTS_UPDATED: "hlsLevelPtsUpdated", + AUDIO_TRACKS_UPDATED: "hlsAudioTracksUpdated", + AUDIO_TRACK_SWITCHING: "hlsAudioTrackSwitching", + AUDIO_TRACK_SWITCHED: "hlsAudioTrackSwitched", + AUDIO_TRACK_LOADING: "hlsAudioTrackLoading", + AUDIO_TRACK_LOADED: "hlsAudioTrackLoaded", + SUBTITLE_TRACKS_UPDATED: "hlsSubtitleTracksUpdated", + SUBTITLE_TRACK_SWITCH: "hlsSubtitleTrackSwitch", + SUBTITLE_TRACK_LOADING: "hlsSubtitleTrackLoading", + SUBTITLE_TRACK_LOADED: "hlsSubtitleTrackLoaded", + SUBTITLE_FRAG_PROCESSED: "hlsSubtitleFragProcessed", + INIT_PTS_FOUND: "hlsInitPtsFound", + FRAG_LOADING: "hlsFragLoading", + FRAG_LOAD_PROGRESS: "hlsFragLoadProgress", + FRAG_LOAD_EMERGENCY_ABORTED: "hlsFragLoadEmergencyAborted", + FRAG_LOADED: "hlsFragLoaded", + FRAG_DECRYPTED: "hlsFragDecrypted", + FRAG_PARSING_INIT_SEGMENT: "hlsFragParsingInitSegment", + FRAG_PARSING_USERDATA: "hlsFragParsingUserdata", + FRAG_PARSING_METADATA: "hlsFragParsingMetadata", + FRAG_PARSING_DATA: "hlsFragParsingData", + FRAG_PARSED: "hlsFragParsed", + FRAG_BUFFERED: "hlsFragBuffered", + FRAG_CHANGED: "hlsFragChanged", + FPS_DROP: "hlsFpsDrop", + FPS_DROP_LEVEL_CAPPING: "hlsFpsDropLevelCapping", + ERROR: "hlsError", + DESTROYING: "hlsDestroying", + KEY_LOADING: "hlsKeyLoading", + KEY_LOADED: "hlsKeyLoaded", + STREAM_STATE_TRANSITION: "hlsStreamStateTransition" + }; + e.a = i + }, function(t, e, r) { + "use strict"; + r.d(e, "b", function() { + return i + }), r.d(e, "a", function() { + return a + }); + var i = { + NETWORK_ERROR: "networkError", + MEDIA_ERROR: "mediaError", + KEY_SYSTEM_ERROR: "keySystemError", + MUX_ERROR: "muxError", + OTHER_ERROR: "otherError" + }, + a = { + KEY_SYSTEM_NO_KEYS: "keySystemNoKeys", + KEY_SYSTEM_NO_ACCESS: "keySystemNoAccess", + KEY_SYSTEM_NO_SESSION: "keySystemNoSession", + KEY_SYSTEM_LICENSE_REQUEST_FAILED: "keySystemLicenseRequestFailed", + MANIFEST_LOAD_ERROR: "manifestLoadError", + MANIFEST_LOAD_TIMEOUT: "manifestLoadTimeOut", + MANIFEST_PARSING_ERROR: "manifestParsingError", + MANIFEST_INCOMPATIBLE_CODECS_ERROR: "manifestIncompatibleCodecsError", + LEVEL_LOAD_ERROR: "levelLoadError", + LEVEL_LOAD_TIMEOUT: "levelLoadTimeOut", + LEVEL_SWITCH_ERROR: "levelSwitchError", + AUDIO_TRACK_LOAD_ERROR: "audioTrackLoadError", + AUDIO_TRACK_LOAD_TIMEOUT: "audioTrackLoadTimeOut", + FRAG_LOAD_ERROR: "fragLoadError", + FRAG_LOAD_TIMEOUT: "fragLoadTimeOut", + FRAG_DECRYPT_ERROR: "fragDecryptError", + FRAG_PARSING_ERROR: "fragParsingError", + REMUX_ALLOC_ERROR: "remuxAllocError", + KEY_LOAD_ERROR: "keyLoadError", + KEY_LOAD_TIMEOUT: "keyLoadTimeOut", + BUFFER_ADD_CODEC_ERROR: "bufferAddCodecError", + BUFFER_APPEND_ERROR: "bufferAppendError", + BUFFER_APPENDING_ERROR: "bufferAppendingError", + BUFFER_STALLED_ERROR: "bufferStalledError", + BUFFER_FULL_ERROR: "bufferFullError", + BUFFER_SEEK_OVER_HOLE: "bufferSeekOverHole", + BUFFER_NUDGE_ON_STALL: "bufferNudgeOnStall", + INTERNAL_EXCEPTION: "internalException" + } + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + var a = r(0), + n = r(2), + o = r(1), + s = "function" == typeof Symbol && "symbol" == typeof Symbol.iterator ? function(t) { + return typeof t + } : function(t) { + return t && "function" == typeof Symbol && t.constructor === Symbol && t !== Symbol.prototype ? "symbol" : typeof t + }, + l = new Set(["hlsEventGeneric", "hlsHandlerDestroying", "hlsHandlerDestroyed"]), + u = function() { + function t(e) { + i(this, t), this.hls = e, this.onEvent = this.onEvent.bind(this); + for (var r = arguments.length, a = Array(r > 1 ? r - 1 : 0), n = 1; n < r; n++) a[n - 1] = arguments[n]; + this.handledEvents = a, this.useGenericHandler = !0, this.registerListeners() + } + return t.prototype.destroy = function() { + this.onHandlerDestroying(), this.unregisterListeners(), this.onHandlerDestroyed() + }, t.prototype.onHandlerDestroying = function() {}, t.prototype.onHandlerDestroyed = function() {}, t.prototype.isEventHandler = function() { + return "object" === s(this.handledEvents) && this.handledEvents.length && "function" == typeof this.onEvent + }, t.prototype.registerListeners = function() { + this.isEventHandler() && this.handledEvents.forEach(function(t) { + if (l.has(t)) throw new Error("Forbidden event-name: " + t); + this.hls.on(t, this.onEvent) + }, this) + }, t.prototype.unregisterListeners = function() { + this.isEventHandler() && this.handledEvents.forEach(function(t) { + this.hls.off(t, this.onEvent) + }, this) + }, t.prototype.onEvent = function(t, e) { + this.onEventGeneric(t, e) + }, t.prototype.onEventGeneric = function(t, e) { + var r = function(t, e) { + var r = "on" + t.replace("hls", ""); + if ("function" != typeof this[r]) throw new Error("Event " + t + " has no generic handler in this " + this.constructor.name + " class (tried " + r + ")"); + return this[r].bind(this, e) + }; + try { + r.call(this, t, e).call() + } catch (e) { + a.b.error("An internal error happened while handling event " + t + '. Error message: "' + e.message + '". Here is a stacktrace:', e), this.hls.trigger(o.a.ERROR, { + type: n.b.OTHER_ERROR, + details: n.a.INTERNAL_EXCEPTION, + fatal: !1, + event: t, + err: e + }) + } + }, t + }(); + e.a = u + }, function(t, e, r) { + "use strict"; + + function i() { + return "undefined" == typeof window ? self : window + } + e.a = i + }, function(t, e, r) { + ! function(e) { + var r = /^((?:[a-zA-Z0-9+\-.]+:)?)(\/\/[^\/\;?#]*)?(.*?)??(;.*?)?(\?.*?)?(#.*?)?$/, + i = /^([^\/;?#]*)(.*)$/, + a = /(?:\/|^)\.(?=\/)/g, + n = /(?:\/|^)\.\.\/(?!\.\.\/).*?(?=\/)/g, + o = { + buildAbsoluteURL: function(t, e, r) { + if (r = r || {}, t = t.trim(), !(e = e.trim())) { + if (!r.alwaysNormalize) return t; + var a = this.parseURL(t); + if (!s) throw new Error("Error trying to parse base URL."); + return a.path = o.normalizePath(a.path), o.buildURLFromParts(a) + } + var n = this.parseURL(e); + if (!n) throw new Error("Error trying to parse relative URL."); + if (n.scheme) return r.alwaysNormalize ? (n.path = o.normalizePath(n.path), o.buildURLFromParts(n)) : e; + var s = this.parseURL(t); + if (!s) throw new Error("Error trying to parse base URL."); + if (!s.netLoc && s.path && "/" !== s.path[0]) { + var l = i.exec(s.path); + s.netLoc = l[1], s.path = l[2] + } + s.netLoc && !s.path && (s.path = "/"); + var u = { + scheme: s.scheme, + netLoc: n.netLoc, + path: null, + params: n.params, + query: n.query, + fragment: n.fragment + }; + if (!n.netLoc && (u.netLoc = s.netLoc, "/" !== n.path[0])) + if (n.path) { + var d = s.path, + c = d.substring(0, d.lastIndexOf("/") + 1) + n.path; + u.path = o.normalizePath(c) + } else u.path = s.path, n.params || (u.params = s.params, n.query || (u.query = s.query)); + return null === u.path && (u.path = r.alwaysNormalize ? o.normalizePath(n.path) : n.path), o.buildURLFromParts(u) + }, + parseURL: function(t) { + var e = r.exec(t); + return e ? { + scheme: e[1] || "", + netLoc: e[2] || "", + path: e[3] || "", + params: e[4] || "", + query: e[5] || "", + fragment: e[6] || "" + } : null + }, + normalizePath: function(t) { + for (t = t.split("").reverse().join("").replace(a, ""); t.length !== (t = t.replace(n, "")).length;); + return t.split("").reverse().join("") + }, + buildURLFromParts: function(t) { + return t.scheme + t.netLoc + t.path + t.params + t.query + t.fragment + } + }; + t.exports = o + }() + }, function(t, e, r) { + "use strict"; + var i = { + search: function(t, e) { + for (var r = 0, i = t.length - 1, a = null, n = null; r <= i;) { + a = (r + i) / 2 | 0, n = t[a]; + var o = e(n); + if (o > 0) r = a + 1; + else { + if (!(o < 0)) return n; + i = a - 1 + } + } + return null + } + }; + e.a = i + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + r.d(e, "b", function() { + return n + }); + var a = function() { + function t() { + i(this, t) + } + return t.isHeader = function(t, e) { + return e + 10 <= t.length && 73 === t[e] && 68 === t[e + 1] && 51 === t[e + 2] && t[e + 3] < 255 && t[e + 4] < 255 && t[e + 6] < 128 && t[e + 7] < 128 && t[e + 8] < 128 && t[e + 9] < 128 + }, t.isFooter = function(t, e) { + return e + 10 <= t.length && 51 === t[e] && 68 === t[e + 1] && 73 === t[e + 2] && t[e + 3] < 255 && t[e + 4] < 255 && t[e + 6] < 128 && t[e + 7] < 128 && t[e + 8] < 128 && t[e + 9] < 128 + }, t.getID3Data = function(e, r) { + for (var i = r, a = 0; t.isHeader(e, r);) { + a += 10; + a += t._readSize(e, r + 6), t.isFooter(e, r + 10) && (a += 10), r += a + } + if (a > 0) return e.subarray(i, i + a) + }, t._readSize = function(t, e) { + var r = 0; + return r = (127 & t[e]) << 21, r |= (127 & t[e + 1]) << 14, r |= (127 & t[e + 2]) << 7, r |= 127 & t[e + 3] + }, t.getTimeStamp = function(e) { + for (var r = t.getID3Frames(e), i = 0; i < r.length; i++) { + var a = r[i]; + if (t.isTimeStampFrame(a)) return t._readTimeStamp(a) + } + }, t.isTimeStampFrame = function(t) { + return t && "PRIV" === t.key && "com.apple.streaming.transportStreamTimestamp" === t.info + }, t._getFrameData = function(e) { + var r = String.fromCharCode(e[0], e[1], e[2], e[3]), + i = t._readSize(e, 4); + return { + type: r, + size: i, + data: e.subarray(10, 10 + i) + } + }, t.getID3Frames = function(e) { + for (var r = 0, i = []; t.isHeader(e, r);) { + var a = t._readSize(e, r + 6); + r += 10; + for (var n = r + a; r + 8 < n;) { + var o = t._getFrameData(e.subarray(r)), + s = t._decodeFrame(o); + s && i.push(s), r += o.size + 10 + } + t.isFooter(e, r) && (r += 10) + } + return i + }, t._decodeFrame = function(e) { + return "PRIV" === e.type ? t._decodePrivFrame(e) : "T" === e.type[0] ? t._decodeTextFrame(e) : "W" === e.type[0] ? t._decodeURLFrame(e) : void 0 + }, t._readTimeStamp = function(t) { + if (8 === t.data.byteLength) { + var e = new Uint8Array(t.data), + r = 1 & e[3], + i = (e[4] << 23) + (e[5] << 15) + (e[6] << 7) + e[7]; + return i /= 45, r && (i += 47721858.84), Math.round(i) + } + }, t._decodePrivFrame = function(e) { + if (!(e.size < 2)) { + var r = t._utf8ArrayToStr(e.data, !0), + i = new Uint8Array(e.data.subarray(r.length + 1)); + return { + key: e.type, + info: r, + data: i.buffer + } + } + }, t._decodeTextFrame = function(e) { + if (!(e.size < 2)) { + if ("TXXX" === e.type) { + var r = 1, + i = t._utf8ArrayToStr(e.data.subarray(r)); + r += i.length + 1; + var a = t._utf8ArrayToStr(e.data.subarray(r)); + return { + key: e.type, + info: i, + data: a + } + } + var n = t._utf8ArrayToStr(e.data.subarray(1)); + return { + key: e.type, + data: n + } + } + }, t._decodeURLFrame = function(e) { + if ("WXXX" === e.type) { + if (e.size < 2) return; + var r = 1, + i = t._utf8ArrayToStr(e.data.subarray(r)); + r += i.length + 1; + var a = t._utf8ArrayToStr(e.data.subarray(r)); + return { + key: e.type, + info: i, + data: a + } + } + var n = t._utf8ArrayToStr(e.data); + return { + key: e.type, + data: n + } + }, t._utf8ArrayToStr = function(t) { + for (var e = arguments.length > 1 && void 0 !== arguments[1] && arguments[1], r = t.length, i = void 0, a = void 0, n = void 0, o = "", s = 0; s < r;) { + if (0 === (i = t[s++]) && e) return o; + if (0 !== i && 3 !== i) switch (i >> 4) { + case 0: + case 1: + case 2: + case 3: + case 4: + case 5: + case 6: + case 7: + o += String.fromCharCode(i); + break; + case 12: + case 13: + a = t[s++], o += String.fromCharCode((31 & i) << 6 | 63 & a); + break; + case 14: + a = t[s++], n = t[s++], o += String.fromCharCode((15 & i) << 12 | (63 & a) << 6 | (63 & n) << 0) + } + } + return o + }, t + }(), + n = a._utf8ArrayToStr; + e.a = a + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + + function a(t, e) { + if (!t) throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); + return !e || "object" != typeof e && "function" != typeof e ? t : e + } + + function n(t, e) { + if ("function" != typeof e && null !== e) throw new TypeError("Super expression must either be null or a function, not " + typeof e); + t.prototype = Object.create(e && e.prototype, { + constructor: { + value: t, + enumerable: !1, + writable: !0, + configurable: !0 + } + }), e && (Object.setPrototypeOf ? Object.setPrototypeOf(t, e) : t.__proto__ = e) + } + var o = r(3), + s = function(t) { + function e(r) { + i(this, e); + for (var n = arguments.length, o = Array(n > 1 ? n - 1 : 0), s = 1; s < n; s++) o[s - 1] = arguments[s]; + var l = a(this, t.call.apply(t, [this, r].concat(o))); + return l._tickInterval = null, l._tickTimer = null, l._tickCallCount = 0, l._boundTick = l.tick.bind(l), l + } + return n(e, t), e.prototype.onHandlerDestroying = function() { + this.clearNextTick(), this.clearInterval() + }, e.prototype.hasInterval = function() { + return !!this._tickInterval + }, e.prototype.hasNextTick = function() { + return !!this._tickTimer + }, e.prototype.setInterval = function(t) { + function e(e) { + return t.apply(this, arguments) + } + return e.toString = function() { + return t.toString() + }, e + }(function(t) { + return !this._tickInterval && (this._tickInterval = setInterval(this._boundTick, t), !0) + }), e.prototype.clearInterval = function(t) { + function e() { + return t.apply(this, arguments) + } + return e.toString = function() { + return t.toString() + }, e + }(function() { + return !!this._tickInterval && (clearInterval(this._tickInterval), this._tickInterval = null, !0) + }), e.prototype.clearNextTick = function() { + return !!this._tickTimer && (clearTimeout(this._tickTimer), this._tickTimer = null, !0) + }, e.prototype.tick = function() { + 1 === ++this._tickCallCount && (this.doTick(), this._tickCallCount > 1 && (this.clearNextTick(), this._tickTimer = setTimeout(this._boundTick, 0)), this._tickCallCount = 0) + }, e.prototype.doTick = function() {}, e + }(o.a); + e.a = s + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + var a = r(5), + n = r.n(a), + o = r(18), + s = function() { + function t(t, e) { + for (var r = 0; r < e.length; r++) { + var i = e[r]; + i.enumerable = i.enumerable || !1, i.configurable = !0, "value" in i && (i.writable = !0), Object.defineProperty(t, i.key, i) + } + } + return function(e, r, i) { + return r && t(e.prototype, r), i && t(e, i), e + } + }(), + l = function() { + function t() { + var e; + i(this, t), this._url = null, this._byteRange = null, this._decryptdata = null, this.tagList = [], this._elementaryStreams = (e = {}, e[t.ElementaryStreamTypes.AUDIO] = !1, e[t.ElementaryStreamTypes.VIDEO] = !1, e) + } + return t.prototype.addElementaryStream = function(t) { + this._elementaryStreams[t] = !0 + }, t.prototype.hasElementaryStream = function(t) { + return !0 === this._elementaryStreams[t] + }, t.prototype.createInitializationVector = function(t) { + for (var e = new Uint8Array(16), r = 12; r < 16; r++) e[r] = t >> 8 * (15 - r) & 255; + return e + }, t.prototype.fragmentDecryptdataFromLevelkey = function(t, e) { + var r = t; + return t && t.method && t.uri && !t.iv && (r = new o.a, r.method = t.method, r.baseuri = t.baseuri, r.reluri = t.reluri, r.iv = this.createInitializationVector(e)), r + }, s(t, [{ + key: "url", + get: function() { + return !this._url && this.relurl && (this._url = n.a.buildAbsoluteURL(this.baseurl, this.relurl, { + alwaysNormalize: !0 + })), this._url + }, + set: function(t) { + this._url = t + } + }, { + key: "programDateTime", + get: function() { + return !this._programDateTime && this.rawProgramDateTime && (this._programDateTime = new Date(Date.parse(this.rawProgramDateTime))), this._programDateTime + } + }, { + key: "byteRange", + get: function() { + if (!this._byteRange && !this.rawByteRange) return []; + if (this._byteRange) return this._byteRange; + var t = []; + if (this.rawByteRange) { + var e = this.rawByteRange.split("@", 2); + if (1 === e.length) { + var r = this.lastByteRangeEndOffset; + t[0] = r || 0 + } else t[0] = parseInt(e[1]); + t[1] = parseInt(e[0]) + t[0], this._byteRange = t + } + return t + } + }, { + key: "byteRangeStartOffset", + get: function() { + return this.byteRange[0] + } + }, { + key: "byteRangeEndOffset", + get: function() { + return this.byteRange[1] + } + }, { + key: "decryptdata", + get: function() { + return this._decryptdata || (this._decryptdata = this.fragmentDecryptdataFromLevelkey(this.levelkey, this.sn)), this._decryptdata + } + }, { + key: "encrypted", + get: function() { + return !(!this.decryptdata || null === this.decryptdata.uri || null !== this.decryptdata.key) + } + }], [{ + key: "ElementaryStreamTypes", + get: function() { + return { + AUDIO: "audio", + VIDEO: "video" + } + } + }]), t + }(); + e.a = l + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + + function a(t, e) { + if (!t) throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); + return !e || "object" != typeof e && "function" != typeof e ? t : e + } + + function n(t, e) { + if ("function" != typeof e && null !== e) throw new TypeError("Super expression must either be null or a function, not " + typeof e); + t.prototype = Object.create(e && e.prototype, { + constructor: { + value: t, + enumerable: !1, + writable: !0, + configurable: !0 + } + }), e && (Object.setPrototypeOf ? Object.setPrototypeOf(t, e) : t.__proto__ = e) + } + r.d(e, "a", function() { + return l + }), r.d(e, "b", function() { + return u + }); + var o = r(3), + s = r(1), + l = { + NOT_LOADED: "NOT_LOADED", + APPENDING: "APPENDING", + PARTIAL: "PARTIAL", + OK: "OK" + }, + u = function(t) { + function e(r) { + i(this, e); + var n = a(this, t.call(this, r, s.a.BUFFER_APPENDED, s.a.FRAG_BUFFERED, s.a.FRAG_LOADED)); + return n.bufferPadding = .2, n.fragments = Object.create(null), n.timeRanges = Object.create(null), n.config = r.config, n + } + return n(e, t), e.prototype.destroy = function() { + this.fragments = null, this.timeRanges = null, this.config = null, o.a.prototype.destroy.call(this), t.prototype.destroy.call(this) + }, e.prototype.getBufferedFrag = function(t, e) { + var r = this.fragments, + i = Object.keys(r).filter(function(i) { + var a = r[i]; + if (a.body.type !== e) return !1; + if (!a.buffered) return !1; + var n = a.body; + return n.startPTS <= t && t <= n.endPTS + }); + if (0 === i.length) return null; + var a = i.pop(); + return r[a].body + }, e.prototype.detectEvictedFragments = function(t, e) { + var r = this, + i = void 0, + a = void 0; + Object.keys(this.fragments).forEach(function(n) { + var o = r.fragments[n]; + if (!0 === o.buffered) { + var s = o.range[t]; + if (s) { + i = s.time; + for (var l = 0; l < i.length; l++) + if (a = i[l], !1 === r.isTimeBuffered(a.startPTS, a.endPTS, e)) { + r.removeFragment(o.body); + break + } + } + } + }) + }, e.prototype.detectPartialFragments = function(t) { + var e = this, + r = this.getFragmentKey(t), + i = this.fragments[r]; + i && (i.buffered = !0, Object.keys(this.timeRanges).forEach(function(r) { + if (!0 === t.hasElementaryStream(r)) { + var a = e.timeRanges[r]; + i.range[r] = e.getBufferedTimes(t.startPTS, t.endPTS, a) + } + })) + }, e.prototype.getBufferedTimes = function(t, e, r) { + for (var i = [], a = void 0, n = void 0, o = !1, s = 0; s < r.length; s++) { + if (a = r.start(s) - this.bufferPadding, n = r.end(s) + this.bufferPadding, t >= a && e <= n) { + i.push({ + startPTS: Math.max(t, r.start(s)), + endPTS: Math.min(e, r.end(s)) + }); + break + } + if (t < n && e > a) i.push({ + startPTS: Math.max(t, r.start(s)), + endPTS: Math.min(e, r.end(s)) + }), o = !0; + else if (e <= a) break + } + return { + time: i, + partial: o + } + }, e.prototype.getFragmentKey = function(t) { + return t.type + "_" + t.level + "_" + t.urlId + "_" + t.sn + }, e.prototype.getPartialFragment = function(t) { + var e = this, + r = void 0, + i = void 0, + a = void 0, + n = null, + o = 0; + return Object.keys(this.fragments).forEach(function(s) { + var l = e.fragments[s]; + e.isPartial(l) && (i = l.body.startPTS - e.bufferPadding, a = l.body.endPTS + e.bufferPadding, t >= i && t <= a && (r = Math.min(t - i, a - t), o <= r && (n = l.body, o = r))) + }), n + }, e.prototype.getState = function(t) { + var e = this.getFragmentKey(t), + r = this.fragments[e], + i = l.NOT_LOADED; + return void 0 !== r && (i = r.buffered ? !0 === this.isPartial(r) ? l.PARTIAL : l.OK : l.APPENDING), i + }, e.prototype.isPartial = function(t) { + return !0 === t.buffered && (void 0 !== t.range.video && !0 === t.range.video.partial || void 0 !== t.range.audio && !0 === t.range.audio.partial) + }, e.prototype.isTimeBuffered = function(t, e, r) { + for (var i = void 0, a = void 0, n = 0; n < r.length; n++) { + if (i = r.start(n) - this.bufferPadding, a = r.end(n) + this.bufferPadding, t >= i && e <= a) return !0; + if (e <= i) return !1 + } + return !1 + }, e.prototype.onFragLoaded = function(t) { + var e = t.frag; + if (!isNaN(e.sn) && !e.bitrateTest) { + var r = this.getFragmentKey(e), + i = { + body: e, + range: Object.create(null), + buffered: !1 + }; + this.fragments[r] = i + } + }, e.prototype.onBufferAppended = function(t) { + var e = this; + this.timeRanges = t.timeRanges, Object.keys(this.timeRanges).forEach(function(t) { + var r = e.timeRanges[t]; + e.detectEvictedFragments(t, r) + }) + }, e.prototype.onFragBuffered = function(t) { + this.detectPartialFragments(t.frag) + }, e.prototype.hasFragment = function(t) { + var e = this.getFragmentKey(t); + return void 0 !== this.fragments[e] + }, e.prototype.removeFragment = function(t) { + var e = this.getFragmentKey(t); + delete this.fragments[e] + }, e.prototype.removeAllFragments = function() { + this.fragments = Object.create(null) + }, e + }(o.a) + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + r.d(e, "a", function() { + return a + }); + var a = function() { + function t() { + i(this, t) + } + return t.isBuffered = function(t, e) { + try { + if (t) + for (var r = t.buffered, i = 0; i < r.length; i++) + if (e >= r.start(i) && e <= r.end(i)) return !0 + } catch (t) {} + return !1 + }, t.bufferInfo = function(t, e, r) { + try { + if (t) { + var i = t.buffered, + a = [], + n = void 0; + for (n = 0; n < i.length; n++) a.push({ + start: i.start(n), + end: i.end(n) + }); + return this.bufferedInfo(a, e, r) + } + } catch (t) {} + return { + len: 0, + start: e, + end: e, + nextStart: void 0 + } + }, t.bufferedInfo = function(t, e, r) { + var i = [], + a = void 0, + n = void 0, + o = void 0, + s = void 0, + l = void 0; + for (t.sort(function(t, e) { + var r = t.start - e.start; + return r || e.end - t.end + }), l = 0; l < t.length; l++) { + var u = i.length; + if (u) { + var d = i[u - 1].end; + t[l].start - d < r ? t[l].end > d && (i[u - 1].end = t[l].end) : i.push(t[l]) + } else i.push(t[l]) + } + for (l = 0, a = 0, n = o = e; l < i.length; l++) { + var c = i[l].start, + h = i[l].end; + if (e + r >= c && e < h) n = c, o = h, a = o - e; + else if (e + r < c) { + s = c; + break + } + } + return { + len: a, + start: n, + end: o, + nextStart: s + } + }, t + }() + }, function(t, e) { + function r() { + this._events = this._events || {}, this._maxListeners = this._maxListeners || void 0 + } + + function i(t) { + return "function" == typeof t + } + + function a(t) { + return "number" == typeof t + } + + function n(t) { + return "object" == typeof t && null !== t + } + + function o(t) { + return void 0 === t + } + t.exports = r, r.EventEmitter = r, r.prototype._events = void 0, r.prototype._maxListeners = void 0, r.defaultMaxListeners = 10, r.prototype.setMaxListeners = function(t) { + if (!a(t) || t < 0 || isNaN(t)) throw TypeError("n must be a positive number"); + return this._maxListeners = t, this + }, r.prototype.emit = function(t) { + var e, r, a, s, l, u; + if (this._events || (this._events = {}), "error" === t && (!this._events.error || n(this._events.error) && !this._events.error.length)) { + if ((e = arguments[1]) instanceof Error) throw e; + var d = new Error('Uncaught, unspecified "error" event. (' + e + ")"); + throw d.context = e, d + } + if (r = this._events[t], o(r)) return !1; + if (i(r)) switch (arguments.length) { + case 1: + r.call(this); + break; + case 2: + r.call(this, arguments[1]); + break; + case 3: + r.call(this, arguments[1], arguments[2]); + break; + default: + s = Array.prototype.slice.call(arguments, 1), r.apply(this, s) + } else if (n(r)) + for (s = Array.prototype.slice.call(arguments, 1), u = r.slice(), a = u.length, l = 0; l < a; l++) u[l].apply(this, s); + return !0 + }, r.prototype.addListener = function(t, e) { + var a; + if (!i(e)) throw TypeError("listener must be a function"); + return this._events || (this._events = {}), this._events.newListener && this.emit("newListener", t, i(e.listener) ? e.listener : e), this._events[t] ? n(this._events[t]) ? this._events[t].push(e) : this._events[t] = [this._events[t], e] : this._events[t] = e, n(this._events[t]) && !this._events[t].warned && (a = o(this._maxListeners) ? r.defaultMaxListeners : this._maxListeners) && a > 0 && this._events[t].length > a && (this._events[t].warned = !0, console.error("(node) warning: possible EventEmitter memory leak detected. %d listeners added. Use emitter.setMaxListeners() to increase limit.", this._events[t].length), "function" == typeof console.trace && console.trace()), this + }, r.prototype.on = r.prototype.addListener, r.prototype.once = function(t, e) { + function r() { + this.removeListener(t, r), a || (a = !0, e.apply(this, arguments)) + } + if (!i(e)) throw TypeError("listener must be a function"); + var a = !1; + return r.listener = e, this.on(t, r), this + }, r.prototype.removeListener = function(t, e) { + var r, a, o, s; + if (!i(e)) throw TypeError("listener must be a function"); + if (!this._events || !this._events[t]) return this; + if (r = this._events[t], o = r.length, a = -1, r === e || i(r.listener) && r.listener === e) delete this._events[t], this._events.removeListener && this.emit("removeListener", t, e); + else if (n(r)) { + for (s = o; s-- > 0;) + if (r[s] === e || r[s].listener && r[s].listener === e) { + a = s; + break + } if (a < 0) return this; + 1 === r.length ? (r.length = 0, delete this._events[t]) : r.splice(a, 1), this._events.removeListener && this.emit("removeListener", t, e) + } + return this + }, r.prototype.removeAllListeners = function(t) { + var e, r; + if (!this._events) return this; + if (!this._events.removeListener) return 0 === arguments.length ? this._events = {} : this._events[t] && delete this._events[t], this; + if (0 === arguments.length) { + for (e in this._events) "removeListener" !== e && this.removeAllListeners(e); + return this.removeAllListeners("removeListener"), this._events = {}, this + } + if (r = this._events[t], i(r)) this.removeListener(t, r); + else if (r) + for (; r.length;) this.removeListener(t, r[r.length - 1]); + return delete this._events[t], this + }, r.prototype.listeners = function(t) { + return this._events && this._events[t] ? i(this._events[t]) ? [this._events[t]] : this._events[t].slice() : [] + }, r.prototype.listenerCount = function(t) { + if (this._events) { + var e = this._events[t]; + if (i(e)) return 1; + if (e) return e.length + } + return 0 + }, r.listenerCount = function(t, e) { + return t.listenerCount(e) + } + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + var a = r(35), + n = r(36), + o = r(37), + s = r(2), + l = r(0), + u = r(1), + d = r(4), + c = Object(d.a)(), + h = function() { + function t(e, r) { + var a = arguments.length > 2 && void 0 !== arguments[2] ? arguments[2] : {}, + n = a.removePKCS7Padding, + o = void 0 === n || n; + if (i(this, t), this.logEnabled = !0, this.observer = e, this.config = r, this.removePKCS7Padding = o, o) try { + var s = c.crypto; + s && (this.subtle = s.subtle || s.webkitSubtle) + } catch (t) {} + this.disableWebCrypto = !this.subtle + } + return t.prototype.isSync = function() { + return this.disableWebCrypto && this.config.enableSoftwareAES + }, t.prototype.decrypt = function(t, e, r, i) { + var s = this; + if (this.disableWebCrypto && this.config.enableSoftwareAES) { + this.logEnabled && (l.b.log("JS AES decrypt"), this.logEnabled = !1); + var u = this.decryptor; + u || (this.decryptor = u = new o.a), u.expandKey(e), i(u.decrypt(t, 0, r, this.removePKCS7Padding)) + } else { + this.logEnabled && (l.b.log("WebCrypto AES decrypt"), this.logEnabled = !1); + var d = this.subtle; + this.key !== e && (this.key = e, this.fastAesKey = new n.a(d, e)), this.fastAesKey.expandKey().then(function(n) { + new a.a(d, r).decrypt(t, n).catch(function(a) { + s.onWebCryptoError(a, t, e, r, i) + }).then(function(t) { + i(t) + }) + }).catch(function(a) { + s.onWebCryptoError(a, t, e, r, i) + }) + } + }, t.prototype.onWebCryptoError = function(t, e, r, i, a) { + this.config.enableSoftwareAES ? (l.b.log("WebCrypto Error, disable WebCrypto API"), this.disableWebCrypto = !0, this.logEnabled = !0, this.decrypt(e, r, i, a)) : (l.b.error("decrypting error : " + t.message), this.observer.trigger(u.a.ERROR, { + type: s.b.MEDIA_ERROR, + details: s.a.FRAG_DECRYPT_ERROR, + fatal: !0, + reason: t.message + })) + }, t.prototype.destroy = function() { + var t = this.decryptor; + t && (t.destroy(), this.decryptor = void 0) + }, t + }(); + e.a = h + }, function(t, e, r) { + "use strict"; + + function i() { + if ("undefined" != typeof window) return window.MediaSource || window.WebKitMediaSource + } + e.a = i + }, function(t, e, r) { + "use strict"; + + function i(t, e, r) { + switch (e) { + case "audio": + t.audioGroupIds || (t.audioGroupIds = []), t.audioGroupIds.push(r); + break; + case "text": + t.textGroupIds || (t.textGroupIds = []), t.textGroupIds.push(r) + } + } + + function a(t, e, r) { + var i = t[e], + a = t[r], + n = a.startPTS; + isNaN(n) ? a.start = r > e ? i.start + i.duration : Math.max(i.start - a.duration, 0) : r > e ? (i.duration = n - i.start, i.duration < 0 && s.b.warn("negative duration computed for frag " + i.sn + ",level " + i.level + ", there should be some duration drift between playlist and fragment!")) : (a.duration = i.start - n, a.duration < 0 && s.b.warn("negative duration computed for frag " + a.sn + ",level " + a.level + ", there should be some duration drift between playlist and fragment!")) + } + + function n(t, e, r, i, n, o) { + var s = r; + if (!isNaN(e.startPTS)) { + var l = Math.abs(e.startPTS - r); + isNaN(e.deltaPTS) ? e.deltaPTS = l : e.deltaPTS = Math.max(l, e.deltaPTS), s = Math.max(r, e.startPTS), r = Math.min(r, e.startPTS), i = Math.max(i, e.endPTS), n = Math.min(n, e.startDTS), o = Math.max(o, e.endDTS) + } + var u = r - e.start; + e.start = e.startPTS = r, e.maxStartPTS = s, e.endPTS = i, e.startDTS = n, e.endDTS = o, e.duration = i - r; + var d = e.sn; + if (!t || d < t.startSN || d > t.endSN) return 0; + var c = void 0, + h = void 0, + f = void 0; + for (c = d - t.startSN, h = t.fragments, h[c] = e, f = c; f > 0; f--) a(h, f, f - 1); + for (f = c; f < h.length - 1; f++) a(h, f, f + 1); + return t.PTSKnown = !0, u + } + + function o(t, e) { + var r = Math.max(t.startSN, e.startSN) - e.startSN, + i = Math.min(t.endSN, e.endSN) - e.startSN, + a = e.startSN - t.startSN, + o = t.fragments, + l = e.fragments, + u = 0, + d = void 0; + if (e.initSegment && t.initSegment && (e.initSegment = t.initSegment), i < r) return void(e.PTSKnown = !1); + for (var c = r; c <= i; c++) { + var h = o[a + c], + f = l[c]; + f && h && (u = h.cc - f.cc, isNaN(h.startPTS) || (f.start = f.startPTS = h.startPTS, f.endPTS = h.endPTS, f.duration = h.duration, f.backtracked = h.backtracked, f.dropped = h.dropped, d = f)) + } + if (u) + for (s.b.log("discontinuity sliding from playlist, take drift into account"), c = 0; c < l.length; c++) l[c].cc += u; + if (d) n(e, d, d.startPTS, d.endPTS, d.startDTS, d.endDTS); + else if (a >= 0 && a < o.length) { + var p = o[a].start; + for (c = 0; c < l.length; c++) l[c].start += p + } + e.PTSKnown = t.PTSKnown + } + e.a = i, e.c = n, e.b = o; + var s = r(0) + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + + function a(t, e) { + if (!t) throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); + return !e || "object" != typeof e && "function" != typeof e ? t : e + } + + function n(t, e) { + if ("function" != typeof e && null !== e) throw new TypeError("Super expression must either be null or a function, not " + typeof e); + t.prototype = Object.create(e && e.prototype, { + constructor: { + value: t, + enumerable: !1, + writable: !0, + configurable: !0 + } + }), e && (Object.setPrototypeOf ? Object.setPrototypeOf(t, e) : t.__proto__ = e) + } + var o = r(1), + s = r(3), + l = r(2), + u = r(0), + d = r(17), + c = r(29), + h = function() { + function t(t, e) { + for (var r = 0; r < e.length; r++) { + var i = e[r]; + i.enumerable = i.enumerable || !1, i.configurable = !0, "value" in i && (i.writable = !0), Object.defineProperty(t, i.key, i) + } + } + return function(e, r, i) { + return r && t(e.prototype, r), i && t(e, i), e + } + }(), + f = window, + p = f.performance, + v = { + MANIFEST: "manifest", + LEVEL: "level", + AUDIO_TRACK: "audioTrack", + SUBTITLE_TRACK: "subtitleTrack" + }, + g = { + MAIN: "main", + AUDIO: "audio", + SUBTITLE: "subtitle" + }, + y = function(t) { + function e(r) { + i(this, e); + var n = a(this, t.call(this, r, o.a.MANIFEST_LOADING, o.a.LEVEL_LOADING, o.a.AUDIO_TRACK_LOADING, o.a.SUBTITLE_TRACK_LOADING)); + return n.loaders = {}, n + } + return n(e, t), e.canHaveQualityLevels = function(t) { + return t !== v.AUDIO_TRACK && t !== v.SUBTITLE_TRACK + }, e.mapContextToLevelType = function(t) { + switch (t.type) { + case v.AUDIO_TRACK: + return g.AUDIO; + case v.SUBTITLE_TRACK: + return g.SUBTITLE; + default: + return g.MAIN + } + }, e.getResponseUrl = function(t, e) { + var r = t.url; + return void 0 !== r && 0 !== r.indexOf("data:") || (r = e.url), r + }, e.prototype.createInternalLoader = function(t) { + var e = this.hls.config, + r = e.pLoader, + i = e.loader, + a = r || i, + n = new a(e); + return t.loader = n, this.loaders[t.type] = n, n + }, e.prototype.getInternalLoader = function(t) { + return this.loaders[t.type] + }, e.prototype.resetInternalLoader = function(t) { + this.loaders[t] && delete this.loaders[t] + }, e.prototype.destroyInternalLoaders = function() { + for (var t in this.loaders) { + var e = this.loaders[t]; + e && e.destroy(), this.resetInternalLoader(t) + } + }, e.prototype.destroy = function() { + this.destroyInternalLoaders(), t.prototype.destroy.call(this) + }, e.prototype.onManifestLoading = function(t) { + this.load(t.url, { + type: v.MANIFEST, + level: 0, + id: null + }) + }, e.prototype.onLevelLoading = function(t) { + this.load(t.url, { + type: v.LEVEL, + level: t.level, + id: t.id + }) + }, e.prototype.onAudioTrackLoading = function(t) { + this.load(t.url, { + type: v.AUDIO_TRACK, + level: 0, + id: t.id + }) + }, e.prototype.onSubtitleTrackLoading = function(t) { + this.load(t.url, { + type: v.SUBTITLE_TRACK, + level: 0, + id: t.id + }) + }, e.prototype.load = function(t, e) { + var r = this.hls.config; + u.b.debug("Loading playlist of type " + e.type + ", level: " + e.level + ", id: " + e.id); + var i = this.getInternalLoader(e); + if (i) { + var a = i.context; + if (a && a.url === t) return u.b.trace("playlist request ongoing"), !1; + u.b.warn("aborting previous loader for type: " + e.type), i.abort() + } + var n = void 0, + o = void 0, + s = void 0, + l = void 0; + switch (e.type) { + case v.MANIFEST: + n = r.manifestLoadingMaxRetry, o = r.manifestLoadingTimeOut, s = r.manifestLoadingRetryDelay, l = r.manifestLoadingMaxRetryTimeout; + break; + case v.LEVEL: + n = 0, o = r.levelLoadingTimeOut; + break; + default: + n = r.levelLoadingMaxRetry, o = r.levelLoadingTimeOut, s = r.levelLoadingRetryDelay, l = r.levelLoadingMaxRetryTimeout + } + i = this.createInternalLoader(e), e.url = t, e.responseType = e.responseType || ""; + var d = { + timeout: o, + maxRetry: n, + retryDelay: s, + maxRetryDelay: l + }, + c = { + onSuccess: this.loadsuccess.bind(this), + onError: this.loaderror.bind(this), + onTimeout: this.loadtimeout.bind(this) + }; + return u.b.debug("Calling internal loader delegate for URL: " + t), i.load(e, d, c), !0 + }, e.prototype.loadsuccess = function(t, e, r) { + var i = arguments.length > 3 && void 0 !== arguments[3] ? arguments[3] : null; + if (r.isSidxRequest) return this._handleSidxRequest(t, r), void this._handlePlaylistLoaded(t, e, r, i); + this.resetInternalLoader(r.type); + var a = t.data; + if (e.tload = p.now(), 0 !== a.indexOf("#EXTM3U")) return void this._handleManifestParsingError(t, r, "no EXTM3U delimiter", i); + a.indexOf("#EXTINF:") > 0 || a.indexOf("#EXT-X-TARGETDURATION:") > 0 ? this._handleTrackOrLevelPlaylist(t, e, r, i) : this._handleMasterPlaylist(t, e, r, i) + }, e.prototype.loaderror = function(t, e) { + var r = arguments.length > 2 && void 0 !== arguments[2] ? arguments[2] : null; + this._handleNetworkError(e, r) + }, e.prototype.loadtimeout = function(t, e) { + var r = arguments.length > 2 && void 0 !== arguments[2] ? arguments[2] : null; + this._handleNetworkError(e, r, !0) + }, e.prototype._handleMasterPlaylist = function(t, r, i, a) { + var n = this.hls, + s = t.data, + l = e.getResponseUrl(t, i), + d = c.a.parseMasterPlaylist(s, l); + if (!d.length) return void this._handleManifestParsingError(t, i, "no level found in manifest", a); + var h = d.map(function(t) { + return { + id: t.attrs.AUDIO, + codec: t.audioCodec + } + }), + f = c.a.parseMasterPlaylistMedia(s, l, "AUDIO", h), + p = c.a.parseMasterPlaylistMedia(s, l, "SUBTITLES"); + if (f.length) { + var v = !1; + f.forEach(function(t) { + t.url || (v = !0) + }), !1 === v && d[0].audioCodec && !d[0].attrs.AUDIO && (u.b.log("audio codec signaled in quality level, but no embedded audio track signaled, create one"), f.unshift({ + type: "main", + name: "main" + })) + } + n.trigger(o.a.MANIFEST_LOADED, { + levels: d, + audioTracks: f, + subtitles: p, + url: l, + stats: r, + networkDetails: a + }) + }, e.prototype._handleTrackOrLevelPlaylist = function(t, r, i, a) { + var n = this.hls, + s = i.id, + l = i.level, + u = i.type, + d = e.getResponseUrl(t, i), + h = isNaN(s) ? 0 : s, + f = isNaN(l) ? h : l, + g = e.mapContextToLevelType(i), + y = c.a.parseLevelPlaylist(t.data, d, f, g, h); + if (y.tload = r.tload, u === v.MANIFEST) { + var m = { + url: d, + details: y + }; + n.trigger(o.a.MANIFEST_LOADED, { + levels: [m], + audioTracks: [], + url: d, + stats: r, + networkDetails: a + }) + } + if (r.tparsed = p.now(), y.needSidxRanges) { + var b = y.initSegment.url; + return void this.load(b, { + isSidxRequest: !0, + type: u, + level: l, + levelDetails: y, + id: s, + rangeStart: 0, + rangeEnd: 2048, + responseType: "arraybuffer" + }) + } + i.levelDetails = y, this._handlePlaylistLoaded(t, r, i, a) + }, e.prototype._handleSidxRequest = function(t, e) { + var r = d.a.parseSegmentIndex(new Uint8Array(t.data)); + r.references.forEach(function(t, r) { + var i = t.info, + a = e.levelDetails.fragments[r]; + 0 === a.byteRange.length && (a.rawByteRange = String(1 + i.end - i.start) + "@" + String(i.start)) + }), e.levelDetails.initSegment.rawByteRange = String(r.moovEndOffset) + "@0" + }, e.prototype._handleManifestParsingError = function(t, e, r, i) { + this.hls.trigger(o.a.ERROR, { + type: l.b.NETWORK_ERROR, + details: l.a.MANIFEST_PARSING_ERROR, + fatal: !0, + url: t.url, + reason: r, + networkDetails: i + }) + }, e.prototype._handleNetworkError = function(t, e) { + var r = arguments.length > 2 && void 0 !== arguments[2] && arguments[2]; + u.b.info("A network error occured while loading a " + t.type + "-type playlist"); + var i = void 0, + a = void 0, + n = this.getInternalLoader(t); + switch (t.type) { + case v.MANIFEST: + i = r ? l.a.MANIFEST_LOAD_TIMEOUT : l.a.MANIFEST_LOAD_ERROR, a = !0; + break; + case v.LEVEL: + i = r ? l.a.LEVEL_LOAD_TIMEOUT : l.a.LEVEL_LOAD_ERROR, a = !1; + break; + case v.AUDIO_TRACK: + i = r ? l.a.AUDIO_TRACK_LOAD_TIMEOUT : l.a.AUDIO_TRACK_LOAD_ERROR, a = !1; + break; + default: + a = !1 + } + n && (n.abort(), this.resetInternalLoader(t.type)), this.hls.trigger(o.a.ERROR, { + type: l.b.NETWORK_ERROR, + details: i, + fatal: a, + url: n.url, + loader: n, + context: t, + networkDetails: e + }) + }, e.prototype._handlePlaylistLoaded = function(t, r, i, a) { + var n = i.type, + s = i.level, + l = i.id, + u = i.levelDetails; + if (!u.targetduration) return void this._handleManifestParsingError(t, i, "invalid target duration", a); + if (e.canHaveQualityLevels(i.type)) this.hls.trigger(o.a.LEVEL_LOADED, { + details: u, + level: s || 0, + id: l || 0, + stats: r, + networkDetails: a + }); + else switch (n) { + case v.AUDIO_TRACK: + this.hls.trigger(o.a.AUDIO_TRACK_LOADED, { + details: u, + id: l, + stats: r, + networkDetails: a + }); + break; + case v.SUBTITLE_TRACK: + this.hls.trigger(o.a.SUBTITLE_TRACK_LOADED, { + details: u, + id: l, + stats: r, + networkDetails: a + }) + } + }, h(e, null, [{ + key: "ContextType", + get: function() { + return v + } + }, { + key: "LevelType", + get: function() { + return g + } + }]), e + }(s.a); + e.a = y + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + var a = r(0), + n = r(1), + o = Math.pow(2, 32) - 1, + s = function() { + function t(e, r) { + i(this, t), this.observer = e, this.remuxer = r + } + return t.prototype.resetTimeStamp = function(t) { + this.initPTS = t + }, t.prototype.resetInitSegment = function(e, r, i, a) { + if (e && e.byteLength) { + var o = this.initData = t.parseInitSegment(e); + null == r && (r = "mp4a.40.5"), null == i && (i = "avc1.42e01e"); + var s = {}; + o.audio && o.video ? s.audiovideo = { + container: "video/mp4", + codec: r + "," + i, + initSegment: a ? e : null + } : (o.audio && (s.audio = { + container: "audio/mp4", + codec: r, + initSegment: a ? e : null + }), o.video && (s.video = { + container: "video/mp4", + codec: i, + initSegment: a ? e : null + })), this.observer.trigger(n.a.FRAG_PARSING_INIT_SEGMENT, { + tracks: s + }) + } else r && (this.audioCodec = r), i && (this.videoCodec = i) + }, t.probe = function(e) { + return t.findBox({ + data: e, + start: 0, + end: Math.min(e.length, 16384) + }, ["moof"]).length > 0 + }, t.bin2str = function(t) { + return String.fromCharCode.apply(null, t) + }, t.readUint16 = function(t, e) { + t.data && (e += t.start, t = t.data); + var r = t[e] << 8 | t[e + 1]; + return r < 0 ? 65536 + r : r + }, t.readUint32 = function(t, e) { + t.data && (e += t.start, t = t.data); + var r = t[e] << 24 | t[e + 1] << 16 | t[e + 2] << 8 | t[e + 3]; + return r < 0 ? 4294967296 + r : r + }, t.writeUint32 = function(t, e, r) { + t.data && (e += t.start, t = t.data), t[e] = r >> 24, t[e + 1] = r >> 16 & 255, t[e + 2] = r >> 8 & 255, t[e + 3] = 255 & r + }, t.findBox = function(e, r) { + var i = [], + a = void 0, + n = void 0, + o = void 0, + s = void 0, + l = void 0, + u = void 0, + d = void 0; + if (e.data ? (u = e.start, s = e.end, e = e.data) : (u = 0, s = e.byteLength), !r.length) return null; + for (a = u; a < s;) n = t.readUint32(e, a), o = t.bin2str(e.subarray(a + 4, a + 8)), d = n > 1 ? a + n : s, o === r[0] && (1 === r.length ? i.push({ + data: e, + start: a + 8, + end: d + }) : (l = t.findBox({ + data: e, + start: a + 8, + end: d + }, r.slice(1)), l.length && (i = i.concat(l)))), a = d; + return i + }, t.parseSegmentIndex = function(e) { + var r = t.findBox(e, ["moov"])[0], + i = r ? r.end : null, + a = 0, + n = t.findBox(e, ["sidx"]), + o = void 0; + if (!n || !n[0]) return null; + o = [], n = n[0]; + var s = n.data[0]; + a = 0 === s ? 8 : 16; + var l = t.readUint32(n, a); + a += 4; + a += 0 === s ? 8 : 16, a += 2; + var u = n.end + 0, + d = t.readUint16(n, a); + a += 2; + for (var c = 0; c < d; c++) { + var h = a, + f = t.readUint32(n, h); + h += 4; + var p = 2147483647 & f; + if (1 === (2147483648 & f) >>> 31) return void console.warn("SIDX has hierarchical references (not supported)"); + var v = t.readUint32(n, h); + h += 4, o.push({ + referenceSize: p, + subsegmentDuration: v, + info: { + duration: v / l, + start: u, + end: u + p - 1 + } + }), u += p, h += 4, a = h + } + return { + earliestPresentationTime: 0, + timescale: l, + version: s, + referencesCount: d, + references: o, + moovEndOffset: i + } + }, t.parseInitSegment = function(e) { + var r = []; + return t.findBox(e, ["moov", "trak"]).forEach(function(e) { + var i = t.findBox(e, ["tkhd"])[0]; + if (i) { + var n = i.data[i.start], + o = 0 === n ? 12 : 20, + s = t.readUint32(i, o), + l = t.findBox(e, ["mdia", "mdhd"])[0]; + if (l) { + n = l.data[l.start], o = 0 === n ? 12 : 20; + var u = t.readUint32(l, o), + d = t.findBox(e, ["mdia", "hdlr"])[0]; + if (d) { + var c = t.bin2str(d.data.subarray(d.start + 8, d.start + 12)), + h = { + soun: "audio", + vide: "video" + } [c]; + if (h) { + var f = t.findBox(e, ["mdia", "minf", "stbl", "stsd"]); + if (f.length) { + f = f[0]; + var p = t.bin2str(f.data.subarray(f.start + 12, f.start + 16)); + a.b.log("MP4Demuxer:" + h + ":" + p + " found") + } + r[s] = { + timescale: u, + type: h + }, r[h] = { + timescale: u, + id: s + } + } + } + } + } + }), r + }, t.getStartDTS = function(e, r) { + var i = void 0, + a = void 0, + n = void 0; + return i = t.findBox(r, ["moof", "traf"]), a = [].concat.apply([], i.map(function(r) { + return t.findBox(r, ["tfhd"]).map(function(i) { + var a = void 0, + n = void 0; + return a = t.readUint32(i, 4), n = e[a].timescale || 9e4, t.findBox(r, ["tfdt"]).map(function(e) { + var r = void 0, + i = void 0; + return r = e.data[e.start], i = t.readUint32(e, 4), 1 === r && (i *= Math.pow(2, 32), i += t.readUint32(e, 8)), i + })[0] / n + }) + })), n = Math.min.apply(null, a), isFinite(n) ? n : 0 + }, t.offsetStartDTS = function(e, r, i) { + t.findBox(r, ["moof", "traf"]).map(function(r) { + return t.findBox(r, ["tfhd"]).map(function(a) { + var n = t.readUint32(a, 4), + s = e[n].timescale || 9e4; + t.findBox(r, ["tfdt"]).map(function(e) { + var r = e.data[e.start], + a = t.readUint32(e, 4); + if (0 === r) t.writeUint32(e, 4, a - i * s); + else { + a *= Math.pow(2, 32), a += t.readUint32(e, 8), a -= i * s, a = Math.max(a, 0); + var n = Math.floor(a / (o + 1)), + l = Math.floor(a % (o + 1)); + t.writeUint32(e, 4, n), t.writeUint32(e, 8, l) + } + }) + }) + }) + }, t.prototype.append = function(e, r, i, a) { + var o = this.initData; + o || (this.resetInitSegment(e, this.audioCodec, this.videoCodec, !1), o = this.initData); + var s = void 0, + l = this.initPTS; + if (void 0 === l) { + var u = t.getStartDTS(o, e); + this.initPTS = l = u - r, this.observer.trigger(n.a.INIT_PTS_FOUND, { + initPTS: l + }) + } + t.offsetStartDTS(o, e, l), s = t.getStartDTS(o, e), this.remuxer.remux(o.audio, o.video, null, null, s, i, a, e) + }, t.prototype.destroy = function() {}, t + }(); + e.a = s + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + var a = r(5), + n = r.n(a), + o = function() { + function t(t, e) { + for (var r = 0; r < e.length; r++) { + var i = e[r]; + i.enumerable = i.enumerable || !1, i.configurable = !0, "value" in i && (i.writable = !0), Object.defineProperty(t, i.key, i) + } + } + return function(e, r, i) { + return r && t(e.prototype, r), i && t(e, i), e + } + }(), + s = function() { + function t() { + i(this, t), this.method = null, this.key = null, this.iv = null, this._uri = null + } + return o(t, [{ + key: "uri", + get: function() { + return !this._uri && this.reluri && (this._uri = n.a.buildAbsoluteURL(this.baseuri, this.reluri, { + alwaysNormalize: !0 + })), this._uri + } + }]), t + }(); + e.a = s + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + var r = n[e]; + return !!r && !0 === r[t.slice(0, 4)] + } + + function a(t, e) { + return window.MediaSource.isTypeSupported((e || "video") + '/mp4;codecs="' + t + '"') + } + r.d(e, "b", function() { + return i + }), r.d(e, "a", function() { + return a + }); + var n = { + audio: { + a3ds: !0, + "ac-3": !0, + "ac-4": !0, + alac: !0, + alaw: !0, + dra1: !0, + "dts+": !0, + "dts-": !0, + dtsc: !0, + dtse: !0, + dtsh: !0, + "ec-3": !0, + enca: !0, + g719: !0, + g726: !0, + m4ae: !0, + mha1: !0, + mha2: !0, + mhm1: !0, + mhm2: !0, + mlpa: !0, + mp4a: !0, + "raw ": !0, + Opus: !0, + samr: !0, + sawb: !0, + sawp: !0, + sevc: !0, + sqcp: !0, + ssmv: !0, + twos: !0, + ulaw: !0 + }, + video: { + avc1: !0, + avc2: !0, + avc3: !0, + avc4: !0, + avcp: !0, + drac: !0, + dvav: !0, + dvhe: !0, + encv: !0, + hev1: !0, + hvc1: !0, + mjp2: !0, + mp4v: !0, + mvc1: !0, + mvc2: !0, + mvc3: !0, + mvc4: !0, + resv: !0, + rv60: !0, + s263: !0, + svc1: !0, + svc2: !0, + "vc-1": !0, + vp08: !0, + vp09: !0 + } + } + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + var a = r(12), + n = r.n(a), + o = r(34), + s = r.n(o), + l = r(1), + u = r(21), + d = r(0), + c = r(2), + h = r(14), + f = r(4), + p = Object(f.a)(), + v = Object(h.a)(), + g = function() { + function t(e, r) { + i(this, t), this.hls = e, this.id = r; + var a = this.observer = new n.a, + o = e.config; + a.trigger = function(t) { + for (var e = arguments.length, r = Array(e > 1 ? e - 1 : 0), i = 1; i < e; i++) r[i - 1] = arguments[i]; + a.emit.apply(a, [t, t].concat(r)) + }, a.off = function(t) { + for (var e = arguments.length, r = Array(e > 1 ? e - 1 : 0), i = 1; i < e; i++) r[i - 1] = arguments[i]; + a.removeListener.apply(a, [t].concat(r)) + }; + var h = function(t, r) { + r = r || {}, r.frag = this.frag, r.id = this.id, e.trigger(t, r) + }.bind(this); + a.on(l.a.FRAG_DECRYPTED, h), a.on(l.a.FRAG_PARSING_INIT_SEGMENT, h), a.on(l.a.FRAG_PARSING_DATA, h), a.on(l.a.FRAG_PARSED, h), a.on(l.a.ERROR, h), a.on(l.a.FRAG_PARSING_METADATA, h), a.on(l.a.FRAG_PARSING_USERDATA, h), a.on(l.a.INIT_PTS_FOUND, h); + var f = { + mp4: v.isTypeSupported("video/mp4"), + mpeg: v.isTypeSupported("audio/mpeg"), + mp3: v.isTypeSupported('audio/mp4; codecs="mp3"') + }, + g = navigator.vendor; + if (o.enableWorker && "undefined" != typeof Worker) { + d.b.log("demuxing in webworker"); + var y = void 0; + try { + y = this.w = s()(47), this.onwmsg = this.onWorkerMessage.bind(this), y.addEventListener("message", this.onwmsg), y.onerror = function(t) { + e.trigger(l.a.ERROR, { + type: c.b.OTHER_ERROR, + details: c.a.INTERNAL_EXCEPTION, + fatal: !0, + event: "demuxerWorker", + err: { + message: t.message + " (" + t.filename + ":" + t.lineno + ")" + } + }) + }, y.postMessage({ + cmd: "init", + typeSupported: f, + vendor: g, + id: r, + config: JSON.stringify(o) + }) + } catch (t) { + d.b.error("error while initializing DemuxerWorker, fallback on DemuxerInline"), y && p.URL.revokeObjectURL(y.objectURL), this.demuxer = new u.a(a, f, o, g), this.w = void 0 + } + } else this.demuxer = new u.a(a, f, o, g) + } + return t.prototype.destroy = function() { + var t = this.w; + if (t) t.removeEventListener("message", this.onwmsg), t.terminate(), this.w = null; + else { + var e = this.demuxer; + e && (e.destroy(), this.demuxer = null) + } + var r = this.observer; + r && (r.removeAllListeners(), this.observer = null) + }, t.prototype.push = function(t, e, r, i, a, n, o, s) { + var l = this.w, + u = isNaN(a.startDTS) ? a.start : a.startDTS, + c = a.decryptdata, + h = this.frag, + f = !(h && a.cc === h.cc), + p = !(h && a.level === h.level), + v = h && a.sn === h.sn + 1, + g = !p && v; + if (f && d.b.log(this.id + ":discontinuity detected"), p && d.b.log(this.id + ":switch detected"), this.frag = a, l) l.postMessage({ + cmd: "demux", + data: t, + decryptdata: c, + initSegment: e, + audioCodec: r, + videoCodec: i, + timeOffset: u, + discontinuity: f, + trackSwitch: p, + contiguous: g, + duration: n, + accurateTimeOffset: o, + defaultInitPTS: s + }, t instanceof ArrayBuffer ? [t] : []); + else { + var y = this.demuxer; + y && y.push(t, c, e, r, i, u, f, p, g, n, o, s) + } + }, t.prototype.onWorkerMessage = function(t) { + var e = t.data, + r = this.hls; + switch (e.event) { + case "init": + p.URL.revokeObjectURL(this.w.objectURL); + break; + case l.a.FRAG_PARSING_DATA: + e.data.data1 = new Uint8Array(e.data1), e.data2 && (e.data.data2 = new Uint8Array(e.data2)); + default: + e.data = e.data || {}, e.data.frag = this.frag, e.data.id = this.id, r.trigger(e.event, e.data) + } + }, t + }(); + e.a = g + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + var a = r(1), + n = r(2), + o = r(13), + s = r(38), + l = r(17), + u = r(39), + d = r(42), + c = r(43), + h = r(46), + f = r(4), + p = Object(f.a)(), + v = p, + g = function() { + function t(e, r, a, n) { + i(this, t), this.observer = e, this.typeSupported = r, this.config = a, this.vendor = n + } + return t.prototype.destroy = function() { + var t = this.demuxer; + t && t.destroy() + }, t.prototype.push = function(t, e, r, i, n, s, l, u, d, c, h, f) { + if (t.byteLength > 0 && null != e && null != e.key && "AES-128" === e.method) { + var p = this.decrypter; + null == p && (p = this.decrypter = new o.a(this.observer, this.config)); + var g = this, + y = void 0; + try { + y = v.now() + } catch (t) { + y = Date.now() + } + p.decrypt(t, e.key.buffer, e.iv.buffer, function(t) { + var o = void 0; + try { + o = v.now() + } catch (t) { + o = Date.now() + } + g.observer.trigger(a.a.FRAG_DECRYPTED, { + stats: { + tstart: y, + tdecrypt: o + } + }), g.pushDecrypted(new Uint8Array(t), e, new Uint8Array(r), i, n, s, l, u, d, c, h, f) + }) + } else this.pushDecrypted(new Uint8Array(t), e, new Uint8Array(r), i, n, s, l, u, d, c, h, f) + }, t.prototype.pushDecrypted = function(t, e, r, i, o, f, p, v, g, y, m, b) { + var E = this.demuxer; + if (!E || (p || v) && !this.probe(t)) { + for (var T = this.observer, S = this.typeSupported, R = this.config, A = [{ + demux: u.a, + remux: c.a + }, { + demux: l.a, + remux: h.a + }, { + demux: s.a, + remux: c.a + }, { + demux: d.a, + remux: c.a + }], _ = 0, w = A.length; _ < w; _++) { + var L = A[_], + D = L.demux.probe; + if (D(t)) { + var I = this.remuxer = new L.remux(T, R, S, this.vendor); + E = new L.demux(T, I, R, S), this.probe = D; + break + } + } + if (!E) return void T.trigger(a.a.ERROR, { + type: n.b.MEDIA_ERROR, + details: n.a.FRAG_PARSING_ERROR, + fatal: !0, + reason: "no demux matching with content found" + }); + this.demuxer = E + } + var k = this.remuxer; + (p || v) && (E.resetInitSegment(r, i, o, y), k.resetInitSegment()), p && (E.resetTimeStamp(b), k.resetTimeStamp(b)), "function" == typeof E.setDecryptData && E.setDecryptData(e), E.append(t, f, g, m) + }, t + }(); + e.a = g + }, function(t, e, r) { + "use strict"; + + function i(t, e, r, i) { + var a = void 0, + n = void 0, + o = void 0, + s = void 0, + l = void 0, + u = navigator.userAgent.toLowerCase(), + d = i, + c = [96e3, 88200, 64e3, 48e3, 44100, 32e3, 24e3, 22050, 16e3, 12e3, 11025, 8e3, 7350]; + return a = 1 + ((192 & e[r + 2]) >>> 6), (n = (60 & e[r + 2]) >>> 2) > c.length - 1 ? void t.trigger(v.a.ERROR, { + type: p.b.MEDIA_ERROR, + details: p.a.FRAG_PARSING_ERROR, + fatal: !0, + reason: "invalid ADTS sampling index:" + n + }) : (s = (1 & e[r + 2]) << 2, s |= (192 & e[r + 3]) >>> 6, f.b.log("manifest codec:" + i + ",ADTS data:type:" + a + ",sampleingIndex:" + n + "[" + c[n] + "Hz],channelConfig:" + s), /firefox/i.test(u) ? n >= 6 ? (a = 5, l = new Array(4), o = n - 3) : (a = 2, l = new Array(2), o = n) : -1 !== u.indexOf("android") ? (a = 2, l = new Array(2), o = n) : (a = 5, l = new Array(4), i && (-1 !== i.indexOf("mp4a.40.29") || -1 !== i.indexOf("mp4a.40.5")) || !i && n >= 6 ? o = n - 3 : ((i && -1 !== i.indexOf("mp4a.40.2") && (n >= 6 && 1 === s || /vivaldi/i.test(u)) || !i && 1 === s) && (a = 2, l = new Array(2)), o = n)), l[0] = a << 3, l[0] |= (14 & n) >> 1, l[1] |= (1 & n) << 7, l[1] |= s << 3, 5 === a && (l[1] |= (14 & o) >> 1, l[2] = (1 & o) << 7, l[2] |= 8, l[3] = 0), { + config: l, + samplerate: c[n], + channelCount: s, + codec: "mp4a.40." + a, + manifestCodec: d + }) + } + + function a(t, e) { + return 255 === t[e] && 240 == (246 & t[e + 1]) + } + + function n(t, e) { + return 1 & t[e + 1] ? 7 : 9 + } + + function o(t, e) { + return (3 & t[e + 3]) << 11 | t[e + 4] << 3 | (224 & t[e + 5]) >>> 5 + } + + function s(t, e) { + return !!(e + 1 < t.length && a(t, e)) + } + + function l(t, e) { + if (e + 1 < t.length && a(t, e)) { + var r = n(t, e), + i = r; + e + 5 < t.length && (i = o(t, e)); + var s = e + i; + if (s === t.length || s + 1 < t.length && a(t, s)) return !0 + } + return !1 + } + + function u(t, e, r, a, n) { + if (!t.samplerate) { + var o = i(e, r, a, n); + t.config = o.config, t.samplerate = o.samplerate, t.channelCount = o.channelCount, t.codec = o.codec, t.manifestCodec = o.manifestCodec, f.b.log("parsed codec:" + t.codec + ",rate:" + o.samplerate + ",nb channel:" + o.channelCount) + } + } + + function d(t) { + return 9216e4 / t + } + + function c(t, e, r, i, a) { + var s = void 0, + l = void 0, + u = void 0, + d = t.length; + if (s = n(t, e), l = o(t, e), (l -= s) > 0 && e + s + l <= d) return u = r + i * a, { + headerLength: s, + frameLength: l, + stamp: u + } + } + + function h(t, e, r, i, a) { + var n = d(t.samplerate), + o = c(e, r, i, a, n); + if (o) { + var s = o.stamp, + l = o.headerLength, + u = o.frameLength, + h = { + unit: e.subarray(r + l, r + l + u), + pts: s, + dts: s + }; + return t.samples.push(h), t.len += u, { + sample: h, + length: u + l + } + } + } + e.d = s, e.e = l, e.c = u, e.b = d, e.a = h; + var f = r(0), + p = r(2), + v = r(1); + r(4) + }, function(t, e, r) { + "use strict"; + var i = { + BitratesMap: [32, 64, 96, 128, 160, 192, 224, 256, 288, 320, 352, 384, 416, 448, 32, 48, 56, 64, 80, 96, 112, 128, 160, 192, 224, 256, 320, 384, 32, 40, 48, 56, 64, 80, 96, 112, 128, 160, 192, 224, 256, 320, 32, 48, 56, 64, 80, 96, 112, 128, 144, 160, 176, 192, 224, 256, 8, 16, 24, 32, 40, 48, 56, 64, 80, 96, 112, 128, 144, 160], + SamplingRateMap: [44100, 48e3, 32e3, 22050, 24e3, 16e3, 11025, 12e3, 8e3], + SamplesCoefficients: [ + [0, 72, 144, 12], + [0, 0, 0, 0], + [0, 72, 144, 12], + [0, 144, 144, 12] + ], + BytesInSlot: [0, 1, 1, 4], + appendFrame: function(t, e, r, i, a) { + if (!(r + 24 > e.length)) { + var n = this.parseHeader(e, r); + if (n && r + n.frameLength <= e.length) { + var o = 9e4 * n.samplesPerFrame / n.sampleRate, + s = i + a * o, + l = { + unit: e.subarray(r, r + n.frameLength), + pts: s, + dts: s + }; + return t.config = [], t.channelCount = n.channelCount, t.samplerate = n.sampleRate, t.samples.push(l), t.len += n.frameLength, { + sample: l, + length: n.frameLength + } + } + } + }, + parseHeader: function(t, e) { + var r = t[e + 1] >> 3 & 3, + a = t[e + 1] >> 1 & 3, + n = t[e + 2] >> 4 & 15, + o = t[e + 2] >> 2 & 3, + s = t[e + 2] >> 1 & 1; + if (1 !== r && 0 !== n && 15 !== n && 3 !== o) { + var l = 3 === r ? 3 - a : 3 === a ? 3 : 4, + u = 1e3 * i.BitratesMap[14 * l + n - 1], + d = 3 === r ? 0 : 2 === r ? 1 : 2, + c = i.SamplingRateMap[3 * d + o], + h = t[e + 3] >> 6 == 3 ? 1 : 2, + f = i.SamplesCoefficients[r][a], + p = i.BytesInSlot[a], + v = 8 * f * p; + return { + sampleRate: c, + channelCount: h, + frameLength: parseInt(f * u / c + s, 10) * p, + samplesPerFrame: v + } + } + }, + isHeaderPattern: function(t, e) { + return 255 === t[e] && 224 == (224 & t[e + 1]) && 0 != (6 & t[e + 1]) + }, + isHeader: function(t, e) { + return !!(e + 1 < t.length && this.isHeaderPattern(t, e)) + }, + probe: function(t, e) { + if (e + 1 < t.length && this.isHeaderPattern(t, e)) { + var r = this.parseHeader(t, e), + i = 4; + r && r.frameLength && (i = r.frameLength); + var a = e + i; + if (a === t.length || a + 1 < t.length && this.isHeaderPattern(t, a)) return !0 + } + return !1 + } + }; + e.a = i + }, function(t, e, r) { + "use strict"; + var i = { + toString: function(t) { + for (var e = "", r = t.length, i = 0; i < r; i++) e += "[" + t.start(i).toFixed(3) + "," + t.end(i).toFixed(3) + "]"; + return e + } + }; + e.a = i + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + for (var r = null, i = 0; i < t.length; i += 1) { + var a = t[i]; + if (a && a.cc === e) { + r = a; + break + } + } + return r + } + + function a(t, e) { + return u.a.search(t, function(t) { + return t.cc < e ? 1 : t.cc > e ? -1 : 0 + }) + } + + function n(t, e, r) { + var i = !1; + return e && e.details && r && (r.endCC > r.startCC || t && t.cc < r.startCC) && (i = !0), i + } + + function o(t, e) { + var r = t.fragments, + a = e.fragments; + if (!a.length || !r.length) return void d.b.log("No fragments to align"); + var n = i(r, a[0].cc); + return !n || n && !n.startPTS ? void d.b.log("No frag in previous level to align on") : n + } + + function s(t, e) { + e.fragments.forEach(function(e) { + if (e) { + var r = e.start + t; + e.start = e.startPTS = r, e.endPTS = r + e.duration + } + }), e.PTSKnown = !0 + } + + function l(t, e, r) { + if (n(t, e, r)) { + var i = o(e.details, r); + i && (d.b.log("Adjusting PTS using last level due to CC increase within current level"), s(i.start, r)) + } + if (!1 === r.PTSKnown && e && e.details && e.details.fragments && e.details.fragments.length) { + var a = e.details.programDateTime, + l = r.programDateTime, + u = (l - a) / 1e3 + e.details.fragments[0].start; + isNaN(u) || (d.b.log("adjusting PTS using programDateTime delta, sliding:" + u.toFixed(3)), s(u, r)) + } + } + e.b = a, e.a = l; + var u = r(6), + d = r(0) + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + var r = null; + try { + r = new window.Event("addtrack") + } catch (t) { + r = document.createEvent("Event"), r.initEvent("addtrack", !1, !1) + } + r.track = t, e.dispatchEvent(r) + } + + function a(t) { + if (t && t.cues) + for (; t.cues.length > 0;) t.removeCue(t.cues[0]) + } + e.b = i, e.a = a + }, function(t, e, r) { + "use strict"; + + function i() { + this.window = window, this.state = "INITIAL", this.buffer = "", this.decoder = new d, this.regionList = [] + } + + function a(t) { + function e(t, e, r, i) { + return 3600 * (0 | t) + 60 * (0 | e) + (0 | r) + (0 | i) / 1e3 + } + var r = t.match(/^(\d+):(\d{2})(:\d{2})?\.(\d{3})/); + return r ? r[3] ? e(r[1], r[2], r[3].replace(":", ""), r[4]) : r[1] > 59 ? e(r[1], r[2], 0, r[4]) : e(0, r[1], r[2], r[4]) : null + } + + function n() { + this.values = Object.create(null) + } + + function o(t, e, r, i) { + var a = i ? t.split(i) : [t]; + for (var n in a) + if ("string" == typeof a[n]) { + var o = a[n].split(r); + if (2 === o.length) { + var s = o[0], + l = o[1]; + e(s, l) + } + } + } + + function s(t, e, r) { + function i() { + var e = a(t); + if (null === e) throw new Error("Malformed timestamp: " + l); + return t = t.replace(/^[^\sa-zA-Z-]+/, ""), e + } + + function s() { + t = t.replace(/^\s+/, "") + } + var l = t; + if (s(), e.startTime = i(), s(), "--\x3e" !== t.substr(0, 3)) throw new Error("Malformed time stamp (time stamps must be separated by '--\x3e'): " + l); + t = t.substr(3), s(), e.endTime = i(), s(), + function(t, e) { + var i = new n; + o(t, function(t, e) { + switch (t) { + case "region": + for (var a = r.length - 1; a >= 0; a--) + if (r[a].id === e) { + i.set(t, r[a].region); + break + } break; + case "vertical": + i.alt(t, e, ["rl", "lr"]); + break; + case "line": + var n = e.split(","), + o = n[0]; + i.integer(t, o), i.percent(t, o) && i.set("snapToLines", !1), i.alt(t, o, ["auto"]), 2 === n.length && i.alt("lineAlign", n[1], ["start", h, "end"]); + break; + case "position": + n = e.split(","), i.percent(t, n[0]), 2 === n.length && i.alt("positionAlign", n[1], ["start", h, "end", "line-left", "line-right", "auto"]); + break; + case "size": + i.percent(t, e); + break; + case "align": + i.alt(t, e, ["start", h, "end", "left", "right"]) + } + }, /:/, /\s/), e.region = i.get("region", null), e.vertical = i.get("vertical", ""); + var a = i.get("line", "auto"); + "auto" === a && -1 === c.line && (a = -1), e.line = a, e.lineAlign = i.get("lineAlign", "start"), e.snapToLines = i.get("snapToLines", !0), e.size = i.get("size", 100), e.align = i.get("align", h); + var s = i.get("position", "auto"); + "auto" === s && 50 === c.position && (s = "start" === e.align || "left" === e.align ? 0 : "end" === e.align || "right" === e.align ? 100 : 50), e.position = s + }(t, e) + } + + function l(t) { + return t.replace(//gi, "\n") + } + r.d(e, "b", function() { + return l + }); + var u = r(63), + d = function() { + return { + decode: function(t) { + if (!t) return ""; + if ("string" != typeof t) throw new Error("Error - expected string data."); + return decodeURIComponent(encodeURIComponent(t)) + } + } + }; + n.prototype = { + set: function(t, e) { + this.get(t) || "" === e || (this.values[t] = e) + }, + get: function(t, e, r) { + return r ? this.has(t) ? this.values[t] : e[r] : this.has(t) ? this.values[t] : e + }, + has: function(t) { + return t in this.values + }, + alt: function(t, e, r) { + for (var i = 0; i < r.length; ++i) + if (e === r[i]) { + this.set(t, e); + break + } + }, + integer: function(t, e) { + /^-?\d+$/.test(e) && this.set(t, parseInt(e, 10)) + }, + percent: function(t, e) { + return !!(e.match(/^([\d]{1,3})(\.[\d]*)?%$/) && (e = parseFloat(e)) >= 0 && e <= 100) && (this.set(t, e), !0) + } + }; + var c = new u.a(0, 0, 0), + h = "middle" === c.align ? "middle" : "center"; + i.prototype = { + parse: function(t) { + function e() { + var t = r.buffer, + e = 0; + for (t = l(t); e < t.length && "\r" !== t[e] && "\n" !== t[e];) ++e; + var i = t.substr(0, e); + return "\r" === t[e] && ++e, "\n" === t[e] && ++e, r.buffer = t.substr(e), i + } + var r = this; + t && (r.buffer += r.decoder.decode(t, { + stream: !0 + })); + try { + var i = void 0; + if ("INITIAL" === r.state) { + if (!/\r\n|\n/.test(r.buffer)) return this; + i = e(); + var a = i.match(/^()?WEBVTT([ \t].*)?$/); + if (!a || !a[0]) throw new Error("Malformed WebVTT signature."); + r.state = "HEADER" + } + for (var n = !1; r.buffer;) { + if (!/\r\n|\n/.test(r.buffer)) return this; + switch (n ? n = !1 : i = e(), r.state) { + case "HEADER": + /:/.test(i) ? function(t) { + o(t, function(t, e) {}, /:/) + }(i) : i || (r.state = "ID"); + continue; + case "NOTE": + i || (r.state = "ID"); + continue; + case "ID": + if (/^NOTE($|[ \t])/.test(i)) { + r.state = "NOTE"; + break + } + if (!i) continue; + if (r.cue = new u.a(0, 0, ""), r.state = "CUE", -1 === i.indexOf("--\x3e")) { + r.cue.id = i; + continue + } + case "CUE": + try { + s(i, r.cue, r.regionList) + } catch (t) { + r.cue = null, r.state = "BADCUE"; + continue + } + r.state = "CUETEXT"; + continue; + case "CUETEXT": + var d = -1 !== i.indexOf("--\x3e"); + if (!i || d && (n = !0)) { + r.oncue && r.oncue(r.cue), r.cue = null, r.state = "ID"; + continue + } + r.cue.text && (r.cue.text += "\n"), r.cue.text += i; + continue; + case "BADCUE": + i || (r.state = "ID"); + continue + } + } + } catch (t) { + "CUETEXT" === r.state && r.cue && r.oncue && r.oncue(r.cue), r.cue = null, r.state = "INITIAL" === r.state ? "BADWEBVTT" : "BADCUE" + } + return this + }, + flush: function() { + var t = this; + try { + if (t.buffer += t.decoder.decode(), (t.cue || "HEADER" === t.state) && (t.buffer += "\n\n", t.parse()), "INITIAL" === t.state) throw new Error("Malformed WebVTT signature.") + } catch (t) { + throw t + } + return t.onflush && t.onflush(), this + } + }, e.a = i + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + Object.defineProperty(e, "__esModule", { + value: !0 + }); + var a = r(5), + n = r.n(a), + o = r(2), + s = r(16), + l = r(31), + u = r(32), + d = r(10), + c = r(33), + h = r(49), + f = r(50), + p = r(51), + v = r(0), + g = r(52), + y = r(1), + m = r(12), + b = r.n(m), + E = function() { + function t(t, e) { + for (var r = 0; r < e.length; r++) { + var i = e[r]; + i.enumerable = i.enumerable || !1, i.configurable = !0, "value" in i && (i.writable = !0), Object.defineProperty(t, i.key, i) + } + } + return function(e, r, i) { + return r && t(e.prototype, r), i && t(e, i), e + } + }(); + r(72); + var T = function() { + function t() { + var e = this, + r = arguments.length > 0 && void 0 !== arguments[0] ? arguments[0] : {}; + i(this, t); + var a = t.DefaultConfig; + if ((r.liveSyncDurationCount || r.liveMaxLatencyDurationCount) && (r.liveSyncDuration || r.liveMaxLatencyDuration)) throw new Error("Illegal hls.js config: don't mix up liveSyncDurationCount/liveMaxLatencyDurationCount and liveSyncDuration/liveMaxLatencyDuration"); + for (var n in a) n in r || (r[n] = a[n]); + if (void 0 !== r.liveMaxLatencyDurationCount && r.liveMaxLatencyDurationCount <= r.liveSyncDurationCount) throw new Error('Illegal hls.js config: "liveMaxLatencyDurationCount" must be gt "liveSyncDurationCount"'); + if (void 0 !== r.liveMaxLatencyDuration && (r.liveMaxLatencyDuration <= r.liveSyncDuration || void 0 === r.liveSyncDuration)) throw new Error('Illegal hls.js config: "liveMaxLatencyDuration" must be gt "liveSyncDuration"'); + Object(v.a)(r.debug), this.config = r, this._autoLevelCapping = -1; + var o = this.observer = new b.a; + o.trigger = function(t) { + for (var e = arguments.length, r = Array(e > 1 ? e - 1 : 0), i = 1; i < e; i++) r[i - 1] = arguments[i]; + o.emit.apply(o, [t, t].concat(r)) + }, o.off = function(t) { + for (var e = arguments.length, r = Array(e > 1 ? e - 1 : 0), i = 1; i < e; i++) r[i - 1] = arguments[i]; + o.removeListener.apply(o, [t].concat(r)) + }, this.on = o.on.bind(o), this.off = o.off.bind(o), this.once = o.once.bind(o), this.trigger = o.trigger.bind(o); + var p = this.abrController = new r.abrController(this), + g = new r.bufferController(this), + y = new r.capLevelController(this), + m = new r.fpsController(this), + E = new s.a(this), + T = new l.a(this), + S = new u.a(this), + R = new f.a(this), + A = this.levelController = new h.a(this), + _ = new d.b(this), + w = this.streamController = new c.a(this, _), + L = [A, w], + D = r.audioStreamController; + D && L.push(new D(this, _)), this.networkControllers = L; + var I = [E, T, S, p, g, y, m, R, _]; + if (D = r.audioTrackController) { + var k = new D(this); + this.audioTrackController = k, I.push(k) + } + if (D = r.subtitleTrackController) { + var O = new D(this); + this.subtitleTrackController = O, I.push(O) + } + if (D = r.emeController) { + var C = new D(this); + this.emeController = C, I.push(C) + } [r.subtitleStreamController, r.timelineController].forEach(function(t) { + t && I.push(new t(e)) + }), this.coreComponents = I + } + return t.isSupported = function() { + return Object(p.a)() + }, E(t, null, [{ + key: "version", + get: function() { + return "0.10.0" + } + }, { + key: "Events", + get: function() { + return y.a + } + }, { + key: "ErrorTypes", + get: function() { + return o.b + } + }, { + key: "ErrorDetails", + get: function() { + return o.a + } + }, { + key: "DefaultConfig", + get: function() { + return t.defaultConfig ? t.defaultConfig : g.a + }, + set: function(e) { + t.defaultConfig = e + } + }]), t.prototype.destroy = function() { + v.b.log("destroy"), this.trigger(y.a.DESTROYING), this.detachMedia(), this.coreComponents.concat(this.networkControllers).forEach(function(t) { + t.destroy() + }), this.url = null, this.observer.removeAllListeners(), this._autoLevelCapping = -1 + }, t.prototype.attachMedia = function(t) { + v.b.log("attachMedia"), this.media = t, this.trigger(y.a.MEDIA_ATTACHING, { + media: t + }) + }, t.prototype.detachMedia = function() { + v.b.log("detachMedia"), this.trigger(y.a.MEDIA_DETACHING), this.media = null + }, t.prototype.loadSource = function(t) { + t = n.a.buildAbsoluteURL(window.location.href, t, { + alwaysNormalize: !0 + }), v.b.log("loadSource:" + t), this.url = t, this.trigger(y.a.MANIFEST_LOADING, { + url: t + }) + }, t.prototype.startLoad = function() { + var t = arguments.length > 0 && void 0 !== arguments[0] ? arguments[0] : -1; + v.b.log("startLoad(" + t + ")"), this.networkControllers.forEach(function(e) { + e.startLoad(t) + }) + }, t.prototype.stopLoad = function() { + v.b.log("stopLoad"), this.networkControllers.forEach(function(t) { + t.stopLoad() + }) + }, t.prototype.swapAudioCodec = function() { + v.b.log("swapAudioCodec"), this.streamController.swapAudioCodec() + }, t.prototype.recoverMediaError = function() { + v.b.log("recoverMediaError"); + var t = this.media; + this.detachMedia(), this.attachMedia(t) + }, E(t, [{ + key: "levels", + get: function() { + return this.levelController.levels + } + }, { + key: "currentLevel", + get: function() { + return this.streamController.currentLevel + }, + set: function(t) { + v.b.log("set currentLevel:" + t), this.loadLevel = t, this.streamController.immediateLevelSwitch() + } + }, { + key: "nextLevel", + get: function() { + return this.streamController.nextLevel + }, + set: function(t) { + v.b.log("set nextLevel:" + t), this.levelController.manualLevel = t, this.streamController.nextLevelSwitch() + } + }, { + key: "loadLevel", + get: function() { + return this.levelController.level + }, + set: function(t) { + v.b.log("set loadLevel:" + t), this.levelController.manualLevel = t + } + }, { + key: "nextLoadLevel", + get: function() { + return this.levelController.nextLoadLevel + }, + set: function(t) { + this.levelController.nextLoadLevel = t + } + }, { + key: "firstLevel", + get: function() { + return Math.max(this.levelController.firstLevel, this.minAutoLevel) + }, + set: function(t) { + v.b.log("set firstLevel:" + t), this.levelController.firstLevel = t + } + }, { + key: "startLevel", + get: function() { + return this.levelController.startLevel + }, + set: function(t) { + v.b.log("set startLevel:" + t); + var e = this; - 1 !== t && (t = Math.max(t, e.minAutoLevel)), e.levelController.startLevel = t + } + }, { + key: "autoLevelCapping", + get: function() { + return this._autoLevelCapping + }, + set: function(t) { + v.b.log("set autoLevelCapping:" + t), this._autoLevelCapping = t + } + }, { + key: "autoLevelEnabled", + get: function() { + return -1 === this.levelController.manualLevel + } + }, { + key: "manualLevel", + get: function() { + return this.levelController.manualLevel + } + }, { + key: "minAutoLevel", + get: function() { + for (var t = this, e = t.levels, r = t.config.minAutoBitrate, i = e ? e.length : 0, a = 0; a < i; a++) { + if ((e[a].realBitrate ? Math.max(e[a].realBitrate, e[a].bitrate) : e[a].bitrate) > r) return a + } + return 0 + } + }, { + key: "maxAutoLevel", + get: function() { + var t = this, + e = t.levels, + r = t.autoLevelCapping; + return -1 === r && e && e.length ? e.length - 1 : r + } + }, { + key: "nextAutoLevel", + get: function() { + var t = this; + return Math.min(Math.max(t.abrController.nextAutoLevel, t.minAutoLevel), t.maxAutoLevel) + }, + set: function(t) { + var e = this; + e.abrController.nextAutoLevel = Math.max(e.minAutoLevel, t) + } + }, { + key: "audioTracks", + get: function() { + var t = this.audioTrackController; + return t ? t.audioTracks : [] + } + }, { + key: "audioTrack", + get: function() { + var t = this.audioTrackController; + return t ? t.audioTrack : -1 + }, + set: function(t) { + var e = this.audioTrackController; + e && (e.audioTrack = t) + } + }, { + key: "liveSyncPosition", + get: function() { + return this.streamController.liveSyncPosition + } + }, { + key: "subtitleTracks", + get: function() { + var t = this.subtitleTrackController; + return t ? t.subtitleTracks : [] + } + }, { + key: "subtitleTrack", + get: function() { + var t = this.subtitleTrackController; + return t ? t.subtitleTrack : -1 + }, + set: function(t) { + var e = this.subtitleTrackController; + e && (e.subtitleTrack = t) + } + }, { + key: "subtitleDisplay", + get: function() { + var t = this.subtitleTrackController; + return !!t && t.subtitleDisplay + }, + set: function(t) { + var e = this.subtitleTrackController; + e && (e.subtitleDisplay = t) + } + }]), t + }(); + e.default = T + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + var a = r(5), + n = r.n(a), + o = r(9), + s = r(18), + l = r(30), + u = r(0), + d = r(19), + c = /#EXT-X-STREAM-INF:([^\n\r]*)[\r\n]+([^\r\n]+)/g, + h = /#EXT-X-MEDIA:(.*)/g, + f = new RegExp([/#EXTINF:\s*(\d*(?:\.\d+)?)(?:,(.*)\s+)?/.source, /|(?!#)(\S+)/.source, /|#EXT-X-BYTERANGE:*(.+)/.source, /|#EXT-X-PROGRAM-DATE-TIME:(.+)/.source, /|#.*/.source].join(""), "g"), + p = /(?:(?:#(EXTM3U))|(?:#EXT-X-(PLAYLIST-TYPE):(.+))|(?:#EXT-X-(MEDIA-SEQUENCE): *(\d+))|(?:#EXT-X-(TARGETDURATION): *(\d+))|(?:#EXT-X-(KEY):(.+))|(?:#EXT-X-(START):(.+))|(?:#EXT-X-(ENDLIST))|(?:#EXT-X-(DISCONTINUITY-SEQ)UENCE:(\d+))|(?:#EXT-X-(DIS)CONTINUITY))|(?:#EXT-X-(VERSION):(\d+))|(?:#EXT-X-(MAP):(.+))|(?:(#)(.*):(.*))|(?:(#)(.*))(?:.*)\r?\n?/, + v = /\.(mp4|m4s|m4v|m4a)$/i, + g = function() { + function t() { + i(this, t) + } + return t.findGroup = function(t, e) { + if (!t) return null; + for (var r = null, i = 0; i < t.length; i++) { + var a = t[i]; + a.id === e && (r = a) + } + return r + }, t.convertAVC1ToAVCOTI = function(t) { + var e = void 0, + r = t.split("."); + return r.length > 2 ? (e = r.shift() + ".", e += parseInt(r.shift()).toString(16), e += ("000" + parseInt(r.shift()).toString(16)).substr(-4)) : e = t, e + }, t.resolve = function(t, e) { + return n.a.buildAbsoluteURL(e, t, { + alwaysNormalize: !0 + }) + }, t.parseMasterPlaylist = function(e, r) { + var i = [], + a = void 0; + for (c.lastIndex = 0; null != (a = c.exec(e));) { + var n = {}, + o = n.attrs = new l.a(a[1]); + n.url = t.resolve(a[2], r); + var s = o.decimalResolution("RESOLUTION"); + s && (n.width = s.width, n.height = s.height), n.bitrate = o.decimalInteger("AVERAGE-BANDWIDTH") || o.decimalInteger("BANDWIDTH"), n.name = o.NAME, + function(t, e) { + ["video", "audio"].forEach(function(r) { + var i = t.filter(function(t) { + return Object(d.b)(t, r) + }); + if (i.length) { + var a = i.filter(function(t) { + return 0 === t.lastIndexOf("avc1", 0) || 0 === t.lastIndexOf("mp4a", 0) + }); + e[r + "Codec"] = a.length > 0 ? a[0] : i[0], t = t.filter(function(t) { + return -1 === i.indexOf(t) + }) + } + }), e.unknownCodecs = t + }([].concat((o.CODECS || "").split(/[ ,]+/)), n), n.videoCodec && -1 !== n.videoCodec.indexOf("avc1") && (n.videoCodec = t.convertAVC1ToAVCOTI(n.videoCodec)), i.push(n) + } + return i + }, t.parseMasterPlaylistMedia = function(e, r, i) { + var a = arguments.length > 3 && void 0 !== arguments[3] ? arguments[3] : [], + n = void 0, + o = [], + s = 0; + for (h.lastIndex = 0; null !== (n = h.exec(e));) { + var u = {}, + d = new l.a(n[1]); + if (d.TYPE === i) { + if (u.groupId = d["GROUP-ID"], u.name = d.NAME, u.type = i, u.default = "YES" === d.DEFAULT, u.autoselect = "YES" === d.AUTOSELECT, u.forced = "YES" === d.FORCED, d.URI && (u.url = t.resolve(d.URI, r)), u.lang = d.LANGUAGE, u.name || (u.name = u.lang), a.length) { + var c = t.findGroup(a, u.groupId); + u.audioCodec = c ? c.codec : a[0].codec + } + u.id = s++, o.push(u) + } + } + return o + }, t.parseLevelPlaylist = function(t, e, r, i, a) { + var n = 0, + d = 0, + c = { + type: null, + version: null, + url: e, + fragments: [], + live: !0, + startSN: 0 + }, + h = new s.a, + g = 0, + y = null, + m = new o.a, + b = void 0, + E = void 0; + for (f.lastIndex = 0; null !== (b = f.exec(t));) { + var T = b[1]; + if (T) { + m.duration = parseFloat(T); + var S = (" " + b[2]).slice(1); + m.title = S || null, m.tagList.push(S ? ["INF", T, S] : ["INF", T]) + } else if (b[3]) { + if (!isNaN(m.duration)) { + var R = n++; + m.type = i, m.start = d, m.levelkey = h, m.sn = R, m.level = r, m.cc = g, m.urlId = a, m.baseurl = e, m.relurl = (" " + b[3]).slice(1), c.programDateTime && (y ? m.rawProgramDateTime ? m.pdt = Date.parse(m.rawProgramDateTime) : m.pdt = y.pdt + 1e3 * y.duration : m.pdt = Date.parse(c.programDateTime), m.endPdt = m.pdt + 1e3 * m.duration), c.fragments.push(m), y = m, d += m.duration, m = new o.a + } + } else if (b[4]) { + if (m.rawByteRange = (" " + b[4]).slice(1), y) { + var A = y.byteRangeEndOffset; + A && (m.lastByteRangeEndOffset = A) + } + } else if (b[5]) m.rawProgramDateTime = (" " + b[5]).slice(1), m.tagList.push(["PROGRAM-DATE-TIME", m.rawProgramDateTime]), void 0 === c.programDateTime && (c.programDateTime = new Date(new Date(Date.parse(b[5])) - 1e3 * d)); + else { + for (b = b[0].match(p), E = 1; E < b.length && void 0 === b[E]; E++); + var _ = (" " + b[E + 1]).slice(1), + w = (" " + b[E + 2]).slice(1); + switch (b[E]) { + case "#": + m.tagList.push(w ? [_, w] : [_]); + break; + case "PLAYLIST-TYPE": + c.type = _.toUpperCase(); + break; + case "MEDIA-SEQUENCE": + n = c.startSN = parseInt(_); + break; + case "TARGETDURATION": + c.targetduration = parseFloat(_); + break; + case "VERSION": + c.version = parseInt(_); + break; + case "EXTM3U": + break; + case "ENDLIST": + c.live = !1; + break; + case "DIS": + g++, m.tagList.push(["DIS"]); + break; + case "DISCONTINUITY-SEQ": + g = parseInt(_); + break; + case "KEY": + var L = _, + D = new l.a(L), + I = D.enumeratedString("METHOD"), + k = D.URI, + O = D.hexadecimalInteger("IV"); + I && (h = new s.a, k && ["AES-128", "SAMPLE-AES", "SAMPLE-AES-CENC"].indexOf(I) >= 0 && (h.method = I, h.baseuri = e, h.reluri = k, h.key = null, h.iv = O)); + break; + case "START": + var C = _, + P = new l.a(C), + x = P.decimalFloatingPoint("TIME-OFFSET"); + isNaN(x) || (c.startTimeOffset = x); + break; + case "MAP": + var F = new l.a(_); + m.relurl = F.URI, m.rawByteRange = F.BYTERANGE, m.baseurl = e, m.level = r, m.type = i, m.sn = "initSegment", c.initSegment = m, m = new o.a; + break; + default: + u.b.warn("line parsed but not handled: " + b) + } + } + } + return m = y, m && !m.relurl && (c.fragments.pop(), d -= m.duration), c.totalduration = d, c.averagetargetduration = d / c.fragments.length, c.endSN = n - 1, c.startCC = c.fragments[0] ? c.fragments[0].cc : 0, c.endCC = g, !c.initSegment && c.fragments.length && c.fragments.every(function(t) { + return v.test(t.relurl) + }) && (u.b.warn("MP4 fragments found but no init segment (probably no MAP, incomplete M3U8), trying to fetch SIDX"), m = new o.a, m.relurl = c.fragments[0].relurl, m.baseurl = e, m.level = r, m.type = i, m.sn = "initSegment", c.initSegment = m, c.needSidxRanges = !0), c + }, t + }(); + e.a = g + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + var a = /^(\d+)x(\d+)$/, + n = /\s*(.+?)\s*=((?:\".*?\")|.*?)(?:,|$)/g, + o = function() { + function t(e) { + i(this, t), "string" == typeof e && (e = t.parseAttrList(e)); + for (var r in e) e.hasOwnProperty(r) && (this[r] = e[r]) + } + return t.prototype.decimalInteger = function(t) { + var e = parseInt(this[t], 10); + return e > Number.MAX_SAFE_INTEGER ? 1 / 0 : e + }, t.prototype.hexadecimalInteger = function(t) { + if (this[t]) { + var e = (this[t] || "0x").slice(2); + e = (1 & e.length ? "0" : "") + e; + for (var r = new Uint8Array(e.length / 2), i = 0; i < e.length / 2; i++) r[i] = parseInt(e.slice(2 * i, 2 * i + 2), 16); + return r + } + return null + }, t.prototype.hexadecimalIntegerAsNumber = function(t) { + var e = parseInt(this[t], 16); + return e > Number.MAX_SAFE_INTEGER ? 1 / 0 : e + }, t.prototype.decimalFloatingPoint = function(t) { + return parseFloat(this[t]) + }, t.prototype.enumeratedString = function(t) { + return this[t] + }, t.prototype.decimalResolution = function(t) { + var e = a.exec(this[t]); + if (null !== e) return { + width: parseInt(e[1], 10), + height: parseInt(e[2], 10) + } + }, t.parseAttrList = function(t) { + var e = void 0, + r = {}; + for (n.lastIndex = 0; null !== (e = n.exec(t));) { + var i = e[2]; + 0 === i.indexOf('"') && i.lastIndexOf('"') === i.length - 1 && (i = i.slice(1, -1)), r[e[1]] = i + } + return r + }, t + }(); + e.a = o + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + + function a(t, e) { + if (!t) throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); + return !e || "object" != typeof e && "function" != typeof e ? t : e + } + + function n(t, e) { + if ("function" != typeof e && null !== e) throw new TypeError("Super expression must either be null or a function, not " + typeof e); + t.prototype = Object.create(e && e.prototype, { + constructor: { + value: t, + enumerable: !1, + writable: !0, + configurable: !0 + } + }), e && (Object.setPrototypeOf ? Object.setPrototypeOf(t, e) : t.__proto__ = e) + } + var o = r(1), + s = r(3), + l = r(2), + u = r(0), + d = function(t) { + function e(r) { + i(this, e); + var n = a(this, t.call(this, r, o.a.FRAG_LOADING)); + return n.loaders = {}, n + } + return n(e, t), e.prototype.destroy = function() { + var e = this.loaders; + for (var r in e) { + var i = e[r]; + i && i.destroy() + } + this.loaders = {}, t.prototype.destroy.call(this) + }, e.prototype.onFragLoading = function(t) { + var e = t.frag, + r = e.type, + i = this.loaders, + a = this.hls.config, + n = a.fLoader, + o = a.loader; + e.loaded = 0; + var s = i[r]; + s && (u.b.warn("abort previous fragment loader for type: " + r), s.abort()), s = i[r] = e.loader = a.fLoader ? new n(a) : new o(a); + var l = void 0, + d = void 0, + c = void 0; + l = { + url: e.url, + frag: e, + responseType: "arraybuffer", + progressData: !1 + }; + var h = e.byteRangeStartOffset, + f = e.byteRangeEndOffset; + isNaN(h) || isNaN(f) || (l.rangeStart = h, l.rangeEnd = f), d = { + timeout: a.fragLoadingTimeOut, + maxRetry: 0, + retryDelay: 0, + maxRetryDelay: a.fragLoadingMaxRetryTimeout + }, c = { + onSuccess: this.loadsuccess.bind(this), + onError: this.loaderror.bind(this), + onTimeout: this.loadtimeout.bind(this), + onProgress: this.loadprogress.bind(this) + }, s.load(l, d, c) + }, e.prototype.loadsuccess = function(t, e, r) { + var i = arguments.length > 3 && void 0 !== arguments[3] ? arguments[3] : null, + a = t.data, + n = r.frag; + n.loader = void 0, this.loaders[n.type] = void 0, this.hls.trigger(o.a.FRAG_LOADED, { + payload: a, + frag: n, + stats: e, + networkDetails: i + }) + }, e.prototype.loaderror = function(t, e) { + var r = arguments.length > 2 && void 0 !== arguments[2] ? arguments[2] : null, + i = e.loader; + i && i.abort(), this.loaders[e.type] = void 0, this.hls.trigger(o.a.ERROR, { + type: l.b.NETWORK_ERROR, + details: l.a.FRAG_LOAD_ERROR, + fatal: !1, + frag: e.frag, + response: t, + networkDetails: r + }) + }, e.prototype.loadtimeout = function(t, e) { + var r = arguments.length > 2 && void 0 !== arguments[2] ? arguments[2] : null, + i = e.loader; + i && i.abort(), this.loaders[e.type] = void 0, this.hls.trigger(o.a.ERROR, { + type: l.b.NETWORK_ERROR, + details: l.a.FRAG_LOAD_TIMEOUT, + fatal: !1, + frag: e.frag, + networkDetails: r + }) + }, e.prototype.loadprogress = function(t, e, r) { + var i = arguments.length > 3 && void 0 !== arguments[3] ? arguments[3] : null, + a = e.frag; + a.loaded = t.loaded, this.hls.trigger(o.a.FRAG_LOAD_PROGRESS, { + frag: a, + stats: t, + networkDetails: i + }) + }, e + }(s.a); + e.a = d + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + + function a(t, e) { + if (!t) throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); + return !e || "object" != typeof e && "function" != typeof e ? t : e + } + + function n(t, e) { + if ("function" != typeof e && null !== e) throw new TypeError("Super expression must either be null or a function, not " + typeof e); + t.prototype = Object.create(e && e.prototype, { + constructor: { + value: t, + enumerable: !1, + writable: !0, + configurable: !0 + } + }), e && (Object.setPrototypeOf ? Object.setPrototypeOf(t, e) : t.__proto__ = e) + } + var o = r(1), + s = r(3), + l = r(2), + u = r(0), + d = function(t) { + function e(r) { + i(this, e); + var n = a(this, t.call(this, r, o.a.KEY_LOADING)); + return n.loaders = {}, n.decryptkey = null, n.decrypturl = null, n + } + return n(e, t), e.prototype.destroy = function() { + for (var t in this.loaders) { + var e = this.loaders[t]; + e && e.destroy() + } + this.loaders = {}, s.a.prototype.destroy.call(this) + }, e.prototype.onKeyLoading = function(t) { + var e = t.frag, + r = e.type, + i = this.loaders[r], + a = e.decryptdata, + n = a.uri; + if (n !== this.decrypturl || null === this.decryptkey) { + var s = this.hls.config; + i && (u.b.warn("abort previous key loader for type:" + r), i.abort()), e.loader = this.loaders[r] = new s.loader(s), this.decrypturl = n, this.decryptkey = null; + var l = void 0, + d = void 0, + c = void 0; + l = { + url: n, + frag: e, + responseType: "arraybuffer" + }, d = { + timeout: s.fragLoadingTimeOut, + maxRetry: s.fragLoadingMaxRetry, + retryDelay: s.fragLoadingRetryDelay, + maxRetryDelay: s.fragLoadingMaxRetryTimeout + }, c = { + onSuccess: this.loadsuccess.bind(this), + onError: this.loaderror.bind(this), + onTimeout: this.loadtimeout.bind(this) + }, e.loader.load(l, d, c) + } else this.decryptkey && (a.key = this.decryptkey, this.hls.trigger(o.a.KEY_LOADED, { + frag: e + })) + }, e.prototype.loadsuccess = function(t, e, r) { + var i = r.frag; + this.decryptkey = i.decryptdata.key = new Uint8Array(t.data), i.loader = void 0, this.loaders[i.type] = void 0, this.hls.trigger(o.a.KEY_LOADED, { + frag: i + }) + }, e.prototype.loaderror = function(t, e) { + var r = e.frag, + i = r.loader; + i && i.abort(), this.loaders[e.type] = void 0, this.hls.trigger(o.a.ERROR, { + type: l.b.NETWORK_ERROR, + details: l.a.KEY_LOAD_ERROR, + fatal: !1, + frag: r, + response: t + }) + }, e.prototype.loadtimeout = function(t, e) { + var r = e.frag, + i = r.loader; + i && i.abort(), this.loaders[e.type] = void 0, this.hls.trigger(o.a.ERROR, { + type: l.b.NETWORK_ERROR, + details: l.a.KEY_LOAD_TIMEOUT, + fatal: !1, + frag: r + }) + }, e + }(s.a); + e.a = d + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + + function a(t, e) { + if (!t) throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); + return !e || "object" != typeof e && "function" != typeof e ? t : e + } + + function n(t, e) { + if ("function" != typeof e && null !== e) throw new TypeError("Super expression must either be null or a function, not " + typeof e); + t.prototype = Object.create(e && e.prototype, { + constructor: { + value: t, + enumerable: !1, + writable: !0, + configurable: !0 + } + }), e && (Object.setPrototypeOf ? Object.setPrototypeOf(t, e) : t.__proto__ = e) + } + var o = r(6), + s = r(11), + l = r(20), + u = r(1), + d = r(10), + c = r(9), + h = r(16), + f = r(15), + p = r(24), + v = r(2), + g = r(0), + y = r(25), + m = r(8), + b = r(48), + E = function() { + function t(t, e) { + for (var r = 0; r < e.length; r++) { + var i = e[r]; + i.enumerable = i.enumerable || !1, i.configurable = !0, "value" in i && (i.writable = !0), Object.defineProperty(t, i.key, i) + } + } + return function(e, r, i) { + return r && t(e.prototype, r), i && t(e, i), e + } + }(), + T = { + STOPPED: "STOPPED", + IDLE: "IDLE", + KEY_LOADING: "KEY_LOADING", + FRAG_LOADING: "FRAG_LOADING", + FRAG_LOADING_WAITING_RETRY: "FRAG_LOADING_WAITING_RETRY", + WAITING_LEVEL: "WAITING_LEVEL", + PARSING: "PARSING", + PARSED: "PARSED", + BUFFER_FLUSHING: "BUFFER_FLUSHING", + ENDED: "ENDED", + ERROR: "ERROR" + }, + S = function(t) { + function e(r, n) { + i(this, e); + var o = a(this, t.call(this, r, u.a.MEDIA_ATTACHED, u.a.MEDIA_DETACHING, u.a.MANIFEST_LOADING, u.a.MANIFEST_PARSED, u.a.LEVEL_LOADED, u.a.KEY_LOADED, u.a.FRAG_LOADED, u.a.FRAG_LOAD_EMERGENCY_ABORTED, u.a.FRAG_PARSING_INIT_SEGMENT, u.a.FRAG_PARSING_DATA, u.a.FRAG_PARSED, u.a.ERROR, u.a.AUDIO_TRACK_SWITCHING, u.a.AUDIO_TRACK_SWITCHED, u.a.BUFFER_CREATED, u.a.BUFFER_APPENDED, u.a.BUFFER_FLUSHED)); + return o.fragmentTracker = n, o.config = r.config, o.audioCodecSwap = !1, o._state = T.STOPPED, o.stallReported = !1, o + } + return n(e, t), e.prototype.onHandlerDestroying = function() { + this.stopLoad(), t.prototype.onHandlerDestroying.call(this) + }, e.prototype.onHandlerDestroyed = function() { + this.state = T.STOPPED, this.fragmentTracker = null, t.prototype.onHandlerDestroyed.call(this) + }, e.prototype.startLoad = function(t) { + if (this.levels) { + var e = this.lastCurrentTime, + r = this.hls; + if (this.stopLoad(), this.setInterval(100), this.level = -1, this.fragLoadError = 0, !this.startFragRequested) { + var i = r.startLevel; - 1 === i && (i = 0, this.bitrateTest = !0), this.level = r.nextLoadLevel = i, this.loadedmetadata = !1 + } + e > 0 && -1 === t && (g.b.log("override startPosition with lastCurrentTime @" + e.toFixed(3)), t = e), this.state = T.IDLE, this.nextLoadPosition = this.startPosition = this.lastCurrentTime = t, this.tick() + } else this.forceStartLoad = !0, this.state = T.STOPPED + }, e.prototype.stopLoad = function() { + var t = this.fragCurrent; + t && (t.loader && t.loader.abort(), this.fragmentTracker.removeFragment(t), this.fragCurrent = null), this.fragPrevious = null, this.demuxer && (this.demuxer.destroy(), this.demuxer = null), this.clearInterval(), this.state = T.STOPPED, this.forceStartLoad = !1 + }, e.prototype.doTick = function() { + switch (this.state) { + case T.BUFFER_FLUSHING: + this.fragLoadError = 0; + break; + case T.IDLE: + this._doTickIdle(); + break; + case T.WAITING_LEVEL: + var t = this.levels[this.level]; + t && t.details && (this.state = T.IDLE); + break; + case T.FRAG_LOADING_WAITING_RETRY: + var e = window.performance.now(), + r = this.retryDate; + (!r || e >= r || this.media && this.media.seeking) && (g.b.log("mediaController: retryDate reached, switch back to IDLE state"), this.state = T.IDLE); + break; + case T.ERROR: + case T.STOPPED: + case T.FRAG_LOADING: + case T.PARSING: + case T.PARSED: + case T.ENDED: + } + this._checkBuffer(), this._checkFragmentChanged() + }, e.prototype._doTickIdle = function() { + var t = this.hls, + e = t.config, + r = this.media; + if (void 0 !== this.levelLastLoaded && (r || !this.startFragRequested && e.startFragPrefetch)) { + var i = void 0; + i = this.loadedmetadata ? r.currentTime : this.nextLoadPosition; + var a = t.nextLoadLevel, + n = this.levels[a]; + if (n) { + var o = n.bitrate, + l = void 0; + l = o ? Math.max(8 * e.maxBufferSize / o, e.maxBufferLength) : e.maxBufferLength, l = Math.min(l, e.maxMaxBufferLength); + var d = s.a.bufferInfo(this.mediaBuffer ? this.mediaBuffer : r, i, e.maxBufferHole), + c = d.len; + if (!(c >= l)) { + g.b.trace("buffer length of " + c.toFixed(3) + " is below max of " + l.toFixed(3) + ". checking for more payload ..."), this.level = t.nextLoadLevel = a; + var h = n.details; + if (!h || h.live && this.levelLastLoaded !== a) return void(this.state = T.WAITING_LEVEL); + var f = this.fragPrevious; + if (!h.live && f && !f.backtracked && f.sn === h.endSN && !d.nextStart) { + if (Math.min(r.duration, f.start + f.duration) - Math.max(d.end, f.start) <= Math.max(.2, f.duration)) { + var p = {}; + return this.altAudio && (p.type = "video"), this.hls.trigger(u.a.BUFFER_EOS, p), void(this.state = T.ENDED) + } + } + this._fetchPayloadOrEos(i, d, h) + } + } + } + }, e.prototype._fetchPayloadOrEos = function(t, e, r) { + var i = this.fragPrevious, + a = this.level, + n = r.fragments, + o = n.length; + if (0 !== o) { + var s = n[0].start, + l = n[o - 1].start + n[o - 1].duration, + u = e.end, + d = void 0; + if (r.initSegment && !r.initSegment.data) d = r.initSegment; + else if (r.live) { + var c = this.config.initialLiveManifestSize; + if (o < c) return void g.b.warn("Can not start playback of a level, reason: not enough fragments " + o + " < " + c); + if (null === (d = this._ensureFragmentAtLivePoint(r, u, s, l, i, n, o))) return + } else u < s && (d = n[0]); + d || (d = this._findFragment(s, i, o, n, u, l, r)), d && (d.encrypted ? (g.b.log("Loading key for " + d.sn + " of [" + r.startSN + " ," + r.endSN + "],level " + a), this._loadKey(d)) : (g.b.log("Loading " + d.sn + " of [" + r.startSN + " ," + r.endSN + "],level " + a + ", currentTime:" + t.toFixed(3) + ",bufferEnd:" + u.toFixed(3)), this._loadFragment(d))) + } + }, e.prototype._ensureFragmentAtLivePoint = function(t, e, r, i, a, n, s) { + var l = this.hls.config, + u = this.media, + d = void 0, + c = void 0 !== l.liveMaxLatencyDuration ? l.liveMaxLatencyDuration : l.liveMaxLatencyDurationCount * t.targetduration; + if (e < Math.max(r - l.maxFragLookUpTolerance, i - c)) { + var h = this.liveSyncPosition = this.computeLivePosition(r, t); + g.b.log("buffer end: " + e.toFixed(3) + " is located too far from the end of live sliding playlist, reset currentTime to : " + h.toFixed(3)), e = h, u && u.readyState && u.duration > h && (u.currentTime = h), this.nextLoadPosition = h + } + if (t.PTSKnown && e > i && u && u.readyState) return null; + if (this.startFragRequested && !t.PTSKnown) { + if (a) + if (t.programDateTime) d = Object(b.b)(n, a.endPdt + 1); + else { + var f = a.sn + 1; + if (f >= t.startSN && f <= t.endSN) { + var p = n[f - t.startSN]; + a.cc === p.cc && (d = p, g.b.log("live playlist, switching playlist, load frag with next SN: " + d.sn)) + } + d || (d = o.a.search(n, function(t) { + return a.cc - t.cc + })) && g.b.log("live playlist, switching playlist, load frag with same CC: " + d.sn) + } d || (d = n[Math.min(s - 1, Math.round(s / 2))], g.b.log("live playlist, switching playlist, unknown, load middle frag : " + d.sn)) + } + return d + }, e.prototype._findFragment = function(t, e, r, i, a, n, o) { + var s = this.hls.config, + l = void 0, + u = void 0; + if (a < n ? o.programDateTime ? (u = Object(b.b)(i, Object(b.a)(t, a, o))) && !Object(b.d)(a, s.maxFragLookUpTolerance, u) || (g.b.warn("Frag found by PDT search did not fit within tolerance; falling back to finding by SN"), u = function() { + return Object(b.c)(e, i, a, n, s.maxFragLookUpTolerance) + }()) : u = Object(b.c)(e, i, a, n, s.maxFragLookUpTolerance) : u = i[r - 1], u) { + l = u; + var d = l.sn - o.startSN, + c = e && l.level === e.level, + h = i[d - 1], + f = i[d + 1]; + if (e && l.sn === e.sn) + if (c && !l.backtracked) + if (l.sn < o.endSN) { + var p = e.deltaPTS; + p && p > s.maxBufferHole && e.dropped && d ? (l = h, g.b.warn("SN just loaded, with large PTS gap between audio and video, maybe frag is not starting with a keyframe ? load previous one to try to overcome this")) : (l = f, g.b.log("SN just loaded, load next one: " + l.sn)) + } else l = null; + else l.backtracked && (f && f.backtracked ? (g.b.warn("Already backtracked from fragment " + f.sn + ", will not backtrack to fragment " + l.sn + ". Loading fragment " + f.sn), l = f) : (g.b.warn("Loaded fragment with dropped frames, backtracking 1 segment to find a keyframe"), l.dropped = 0, h ? (l = h, l.backtracked = !0) : d && (l = null))) + } + return l + }, e.prototype._loadKey = function(t) { + this.state = T.KEY_LOADING, this.hls.trigger(u.a.KEY_LOADING, { + frag: t + }) + }, e.prototype._loadFragment = function(t) { + var e = this.fragmentTracker.getState(t); + this.fragCurrent = t, this.startFragRequested = !0, isNaN(t.sn) || t.bitrateTest || (this.nextLoadPosition = t.start + t.duration), t.backtracked || e === d.a.NOT_LOADED || e === d.a.PARTIAL ? (t.autoLevel = this.hls.autoLevelEnabled, t.bitrateTest = this.bitrateTest, this.hls.trigger(u.a.FRAG_LOADING, { + frag: t + }), this.demuxer || (this.demuxer = new l.a(this.hls, "main")), this.state = T.FRAG_LOADING) : e === d.a.APPENDING && this._reduceMaxBufferLength(t.duration) && this.fragmentTracker.removeFragment(t) + }, e.prototype.getBufferedFrag = function(t) { + return this.fragmentTracker.getBufferedFrag(t, h.a.LevelType.MAIN) + }, e.prototype.followingBufferedFrag = function(t) { + return t ? this.getBufferedFrag(t.endPTS + .5) : null + }, e.prototype._checkFragmentChanged = function() { + var t = void 0, + e = void 0, + r = this.media; + if (r && r.readyState && !1 === r.seeking && (e = r.currentTime, e > this.lastCurrentTime && (this.lastCurrentTime = e), s.a.isBuffered(r, e) ? t = this.getBufferedFrag(e) : s.a.isBuffered(r, e + .1) && (t = this.getBufferedFrag(e + .1)), t)) { + var i = t; + if (i !== this.fragPlaying) { + this.hls.trigger(u.a.FRAG_CHANGED, { + frag: i + }); + var a = i.level; + this.fragPlaying && this.fragPlaying.level === a || this.hls.trigger(u.a.LEVEL_SWITCHED, { + level: a + }), this.fragPlaying = i + } + } + }, e.prototype.immediateLevelSwitch = function() { + if (g.b.log("immediateLevelSwitch"), !this.immediateSwitch) { + this.immediateSwitch = !0; + var t = this.media, + e = void 0; + t ? (e = t.paused, t.pause()) : e = !0, this.previouslyPaused = e + } + var r = this.fragCurrent; + r && r.loader && r.loader.abort(), this.fragCurrent = null, this.flushMainBuffer(0, Number.POSITIVE_INFINITY) + }, e.prototype.immediateLevelSwitchEnd = function() { + var t = this.media; + t && t.buffered.length && (this.immediateSwitch = !1, s.a.isBuffered(t, t.currentTime) && (t.currentTime -= 1e-4), this.previouslyPaused || t.play()) + }, e.prototype.nextLevelSwitch = function() { + var t = this.media; + if (t && t.readyState) { + var e = void 0, + r = void 0, + i = void 0; + if (r = this.getBufferedFrag(t.currentTime), r && r.startPTS > 1 && this.flushMainBuffer(0, r.startPTS - 1), t.paused) e = 0; + else { + var a = this.hls.nextLoadLevel, + n = this.levels[a], + o = this.fragLastKbps; + e = o && this.fragCurrent ? this.fragCurrent.duration * n.bitrate / (1e3 * o) + 1 : 0 + } + if ((i = this.getBufferedFrag(t.currentTime + e)) && (i = this.followingBufferedFrag(i))) { + var s = this.fragCurrent; + s && s.loader && s.loader.abort(), this.fragCurrent = null, this.flushMainBuffer(i.maxStartPTS, Number.POSITIVE_INFINITY) + } + } + }, e.prototype.flushMainBuffer = function(t, e) { + this.state = T.BUFFER_FLUSHING; + var r = { + startOffset: t, + endOffset: e + }; + this.altAudio && (r.type = "video"), this.hls.trigger(u.a.BUFFER_FLUSHING, r) + }, e.prototype.onMediaAttached = function(t) { + var e = this.media = this.mediaBuffer = t.media; + this.onvseeking = this.onMediaSeeking.bind(this), this.onvseeked = this.onMediaSeeked.bind(this), this.onvended = this.onMediaEnded.bind(this), e.addEventListener("seeking", this.onvseeking), e.addEventListener("seeked", this.onvseeked), e.addEventListener("ended", this.onvended); + var r = this.config; + this.levels && r.autoStartLoad && this.hls.startLoad(r.startPosition) + }, e.prototype.onMediaDetaching = function() { + var t = this.media; + t && t.ended && (g.b.log("MSE detaching and video ended, reset startPosition"), this.startPosition = this.lastCurrentTime = 0); + var e = this.levels; + e && e.forEach(function(t) { + t.details && t.details.fragments.forEach(function(t) { + t.backtracked = void 0 + }) + }), t && (t.removeEventListener("seeking", this.onvseeking), t.removeEventListener("seeked", this.onvseeked), t.removeEventListener("ended", this.onvended), this.onvseeking = this.onvseeked = this.onvended = null), this.media = this.mediaBuffer = null, this.loadedmetadata = !1, this.stopLoad() + }, e.prototype.onMediaSeeking = function() { + var t = this.media, + e = t ? t.currentTime : void 0, + r = this.config; + isNaN(e) || g.b.log("media seeking to " + e.toFixed(3)); + var i = this.mediaBuffer ? this.mediaBuffer : t, + a = s.a.bufferInfo(i, e, this.config.maxBufferHole); + if (this.state === T.FRAG_LOADING) { + var n = this.fragCurrent; + if (0 === a.len && n) { + var o = r.maxFragLookUpTolerance, + l = n.start - o, + u = n.start + n.duration + o; + e < l || e > u ? (n.loader && (g.b.log("seeking outside of buffer while fragment load in progress, cancel fragment load"), n.loader.abort()), this.fragCurrent = null, this.fragPrevious = null, this.state = T.IDLE) : g.b.log("seeking outside of buffer but within currently loaded fragment range") + } + } else this.state === T.ENDED && (0 === a.len && (this.fragPrevious = 0), this.state = T.IDLE); + t && (this.lastCurrentTime = e), this.loadedmetadata || (this.nextLoadPosition = this.startPosition = e), this.tick() + }, e.prototype.onMediaSeeked = function() { + var t = this.media, + e = t ? t.currentTime : void 0; + isNaN(e) || g.b.log("media seeked to " + e.toFixed(3)), this.tick() + }, e.prototype.onMediaEnded = function() { + g.b.log("media ended"), this.startPosition = this.lastCurrentTime = 0 + }, e.prototype.onManifestLoading = function() { + g.b.log("trigger BUFFER_RESET"), this.hls.trigger(u.a.BUFFER_RESET), this.fragmentTracker.removeAllFragments(), this.stalled = !1, this.startPosition = this.lastCurrentTime = 0 + }, e.prototype.onManifestParsed = function(t) { + var e = !1, + r = !1, + i = void 0; + t.levels.forEach(function(t) { + (i = t.audioCodec) && (-1 !== i.indexOf("mp4a.40.2") && (e = !0), -1 !== i.indexOf("mp4a.40.5") && (r = !0)) + }), this.audioCodecSwitch = e && r, this.audioCodecSwitch && g.b.log("both AAC/HE-AAC audio found in levels; declaring level codec as HE-AAC"), this.levels = t.levels, this.startFragRequested = !1; + var a = this.config; + (a.autoStartLoad || this.forceStartLoad) && this.hls.startLoad(a.startPosition) + }, e.prototype.onLevelLoaded = function(t) { + var e = t.details, + r = t.level, + i = this.levels[this.levelLastLoaded], + a = this.levels[r], + n = e.totalduration, + o = 0; + if (g.b.log("level " + r + " loaded [" + e.startSN + "," + e.endSN + "],duration:" + n), e.live) { + var s = a.details; + s && e.fragments.length > 0 ? (f.b(s, e), o = e.fragments[0].start, this.liveSyncPosition = this.computeLivePosition(o, s), e.PTSKnown && !isNaN(o) ? g.b.log("live playlist sliding:" + o.toFixed(3)) : (g.b.log("live playlist - outdated PTS, unknown sliding"), Object(y.a)(this.fragPrevious, i, e))) : (g.b.log("live playlist - first load, unknown sliding"), e.PTSKnown = !1, Object(y.a)(this.fragPrevious, i, e)) + } else e.PTSKnown = !1; + if (a.details = e, this.levelLastLoaded = r, this.hls.trigger(u.a.LEVEL_UPDATED, { + details: e, + level: r + }), !1 === this.startFragRequested) { + if (-1 === this.startPosition || -1 === this.lastCurrentTime) { + var l = e.startTimeOffset; + isNaN(l) ? e.live ? (this.startPosition = this.computeLivePosition(o, e), g.b.log("configure startPosition to " + this.startPosition)) : this.startPosition = 0 : (l < 0 && (g.b.log("negative start time offset " + l + ", count from end of last fragment"), l = o + n + l), g.b.log("start time offset found in playlist, adjust startPosition to " + l), this.startPosition = l), this.lastCurrentTime = this.startPosition + } + this.nextLoadPosition = this.startPosition + } + this.state === T.WAITING_LEVEL && (this.state = T.IDLE), this.tick() + }, e.prototype.onKeyLoaded = function() { + this.state === T.KEY_LOADING && (this.state = T.IDLE, this.tick()) + }, e.prototype.onFragLoaded = function(t) { + var e = this.fragCurrent, + r = t.frag; + if (this.state === T.FRAG_LOADING && e && "main" === r.type && r.level === e.level && r.sn === e.sn) { + var i = t.stats, + a = this.levels[e.level], + n = a.details; + if (g.b.log("Loaded " + e.sn + " of [" + n.startSN + " ," + n.endSN + "],level " + e.level), this.bitrateTest = !1, this.stats = i, !0 === r.bitrateTest && this.hls.nextLoadLevel) this.state = T.IDLE, this.startFragRequested = !1, i.tparsed = i.tbuffered = window.performance.now(), this.hls.trigger(u.a.FRAG_BUFFERED, { + stats: i, + frag: e, + id: "main" + }), this.tick(); + else if ("initSegment" === r.sn) this.state = T.IDLE, i.tparsed = i.tbuffered = window.performance.now(), n.initSegment.data = t.payload, this.hls.trigger(u.a.FRAG_BUFFERED, { + stats: i, + frag: e, + id: "main" + }), this.tick(); + else { + this.state = T.PARSING; + var o = n.totalduration, + s = e.level, + d = e.sn, + c = this.config.defaultAudioCodec || a.audioCodec; + this.audioCodecSwap && (g.b.log("swapping playlist audio codec"), void 0 === c && (c = this.lastAudioCodec), c && (c = -1 !== c.indexOf("mp4a.40.5") ? "mp4a.40.2" : "mp4a.40.5")), this.pendingBuffering = !0, this.appended = !1, g.b.log("Parsing " + d + " of [" + n.startSN + " ," + n.endSN + "],level " + s + ", cc " + e.cc); + var h = this.demuxer; + h || (h = this.demuxer = new l.a(this.hls, "main")); + var f = this.media, + p = f && f.seeking, + v = !p && (n.PTSKnown || !n.live), + y = n.initSegment ? n.initSegment.data : []; + h.push(t.payload, y, c, a.videoCodec, e, o, v, void 0) + } + } + this.fragLoadError = 0 + }, e.prototype.onFragParsingInitSegment = function(t) { + var e = this.fragCurrent, + r = t.frag; + if (e && "main" === t.id && r.sn === e.sn && r.level === e.level && this.state === T.PARSING) { + var i = t.tracks, + a = void 0, + n = void 0; + if (i.audio && this.altAudio && delete i.audio, n = i.audio) { + var o = this.levels[this.level].audioCodec, + s = navigator.userAgent.toLowerCase(); + o && this.audioCodecSwap && (g.b.log("swapping playlist audio codec"), o = -1 !== o.indexOf("mp4a.40.5") ? "mp4a.40.2" : "mp4a.40.5"), this.audioCodecSwitch && 1 !== n.metadata.channelCount && -1 === s.indexOf("firefox") && (o = "mp4a.40.5"), -1 !== s.indexOf("android") && "audio/mpeg" !== n.container && (o = "mp4a.40.2", g.b.log("Android: force audio codec to " + o)), n.levelCodec = o, n.id = t.id + } + n = i.video, n && (n.levelCodec = this.levels[this.level].videoCodec, n.id = t.id), this.hls.trigger(u.a.BUFFER_CODECS, i); + for (a in i) { + n = i[a], g.b.log("main track:" + a + ",container:" + n.container + ",codecs[level/parsed]=[" + n.levelCodec + "/" + n.codec + "]"); + var l = n.initSegment; + l && (this.appended = !0, this.pendingBuffering = !0, this.hls.trigger(u.a.BUFFER_APPENDING, { + type: a, + data: l, + parent: "main", + content: "initSegment" + })) + } + this.tick() + } + }, e.prototype.onFragParsingData = function(t) { + var e = this, + r = this.fragCurrent, + i = t.frag; + if (r && "main" === t.id && i.sn === r.sn && i.level === r.level && ("audio" !== t.type || !this.altAudio) && this.state === T.PARSING) { + var a = this.levels[this.level], + n = r; + if (isNaN(t.endPTS) && (t.endPTS = t.startPTS + r.duration, t.endDTS = t.startDTS + r.duration), !0 === t.hasAudio && n.addElementaryStream(c.a.ElementaryStreamTypes.AUDIO), !0 === t.hasVideo && n.addElementaryStream(c.a.ElementaryStreamTypes.VIDEO), g.b.log("Parsed " + t.type + ",PTS:[" + t.startPTS.toFixed(3) + "," + t.endPTS.toFixed(3) + "],DTS:[" + t.startDTS.toFixed(3) + "/" + t.endDTS.toFixed(3) + "],nb:" + t.nb + ",dropped:" + (t.dropped || 0)), "video" === t.type) + if (n.dropped = t.dropped, n.dropped) + if (n.backtracked) g.b.warn("Already backtracked on this fragment, appending with the gap", n.sn); + else { + var o = a.details; + if (!o || n.sn !== o.startSN) return g.b.warn("missing video frame(s), backtracking fragment", n.sn), this.fragmentTracker.removeFragment(n), n.backtracked = !0, this.nextLoadPosition = t.startPTS, this.state = T.IDLE, this.fragPrevious = n, void this.tick(); + g.b.warn("missing video frame(s) on first frag, appending with gap", n.sn) + } + else n.backtracked = !1; + var s = f.c(a.details, n, t.startPTS, t.endPTS, t.startDTS, t.endDTS), + l = this.hls; + l.trigger(u.a.LEVEL_PTS_UPDATED, { + details: a.details, + level: this.level, + drift: s, + type: t.type, + start: t.startPTS, + end: t.endPTS + }), [t.data1, t.data2].forEach(function(r) { + r && r.length && e.state === T.PARSING && (e.appended = !0, e.pendingBuffering = !0, l.trigger(u.a.BUFFER_APPENDING, { + type: t.type, + data: r, + parent: "main", + content: "data" + })) + }), this.tick() + } + }, e.prototype.onFragParsed = function(t) { + var e = this.fragCurrent, + r = t.frag; + e && "main" === t.id && r.sn === e.sn && r.level === e.level && this.state === T.PARSING && (this.stats.tparsed = window.performance.now(), this.state = T.PARSED, this._checkAppendedParsed()) + }, e.prototype.onAudioTrackSwitching = function(t) { + var e = !!t.url, + r = t.id; + if (!e) { + if (this.mediaBuffer !== this.media) { + g.b.log("switching on main audio, use media.buffered to schedule main fragment loading"), this.mediaBuffer = this.media; + var i = this.fragCurrent; + i.loader && (g.b.log("switching to main audio track, cancel main fragment load"), i.loader.abort()), this.fragCurrent = null, this.fragPrevious = null, this.demuxer && (this.demuxer.destroy(), this.demuxer = null), this.state = T.IDLE + } + var a = this.hls; + a.trigger(u.a.BUFFER_FLUSHING, { + startOffset: 0, + endOffset: Number.POSITIVE_INFINITY, + type: "audio" + }), a.trigger(u.a.AUDIO_TRACK_SWITCHED, { + id: r + }), this.altAudio = !1 + } + }, e.prototype.onAudioTrackSwitched = function(t) { + var e = t.id, + r = !!this.hls.audioTracks[e].url; + if (r) { + var i = this.videoBuffer; + i && this.mediaBuffer !== i && (g.b.log("switching on alternate audio, use video.buffered to schedule main fragment loading"), this.mediaBuffer = i) + } + this.altAudio = r, this.tick() + }, e.prototype.onBufferCreated = function(t) { + var e = t.tracks, + r = void 0, + i = void 0, + a = !1; + for (var n in e) { + var o = e[n]; + "main" === o.id ? (i = n, r = o, "video" === n && (this.videoBuffer = e[n].buffer)) : a = !0 + } + a && r ? (g.b.log("alternate track found, use " + i + ".buffered to schedule main fragment loading"), this.mediaBuffer = r.buffer) : this.mediaBuffer = this.media + }, e.prototype.onBufferAppended = function(t) { + if ("main" === t.parent) { + var e = this.state; + e !== T.PARSING && e !== T.PARSED || (this.pendingBuffering = t.pending > 0, this._checkAppendedParsed()) + } + }, e.prototype._checkAppendedParsed = function() { + if (!(this.state !== T.PARSED || this.appended && this.pendingBuffering)) { + var t = this.fragCurrent; + if (t) { + var e = this.mediaBuffer ? this.mediaBuffer : this.media; + g.b.log("main buffered : " + p.a.toString(e.buffered)), this.fragPrevious = t; + var r = this.stats; + r.tbuffered = window.performance.now(), this.fragLastKbps = Math.round(8 * r.total / (r.tbuffered - r.tfirst)), this.hls.trigger(u.a.FRAG_BUFFERED, { + stats: r, + frag: t, + id: "main" + }), this.state = T.IDLE + } + this.tick() + } + }, e.prototype.onError = function(t) { + var e = t.frag || this.fragCurrent; + if (!e || "main" === e.type) { + var r = !!this.media && s.a.isBuffered(this.media, this.media.currentTime) && s.a.isBuffered(this.media, this.media.currentTime + .5); + switch (t.details) { + case v.a.FRAG_LOAD_ERROR: + case v.a.FRAG_LOAD_TIMEOUT: + case v.a.KEY_LOAD_ERROR: + case v.a.KEY_LOAD_TIMEOUT: + if (!t.fatal) + if (this.fragLoadError + 1 <= this.config.fragLoadingMaxRetry) { + var i = Math.min(Math.pow(2, this.fragLoadError) * this.config.fragLoadingRetryDelay, this.config.fragLoadingMaxRetryTimeout); + g.b.warn("mediaController: frag loading failed, retry in " + i + " ms"), this.retryDate = window.performance.now() + i, this.loadedmetadata || (this.startFragRequested = !1, this.nextLoadPosition = this.startPosition), this.fragLoadError++, this.state = T.FRAG_LOADING_WAITING_RETRY + } else g.b.error("mediaController: " + t.details + " reaches max retry, redispatch as fatal ..."), t.fatal = !0, this.state = T.ERROR; + break; + case v.a.LEVEL_LOAD_ERROR: + case v.a.LEVEL_LOAD_TIMEOUT: + this.state !== T.ERROR && (t.fatal ? (this.state = T.ERROR, g.b.warn("streamController: " + t.details + ",switch to " + this.state + " state ...")) : t.levelRetry || this.state !== T.WAITING_LEVEL || (this.state = T.IDLE)); + break; + case v.a.BUFFER_FULL_ERROR: + "main" !== t.parent || this.state !== T.PARSING && this.state !== T.PARSED || (r ? (this._reduceMaxBufferLength(this.config.maxBufferLength), this.state = T.IDLE) : (g.b.warn("buffer full error also media.currentTime is not buffered, flush everything"), this.fragCurrent = null, this.flushMainBuffer(0, Number.POSITIVE_INFINITY))) + } + } + }, e.prototype._reduceMaxBufferLength = function(t) { + var e = this.config; + return e.maxMaxBufferLength >= t && (e.maxMaxBufferLength /= 2, g.b.warn("main:reduce max buffer length to " + e.maxMaxBufferLength + "s"), !0) + }, e.prototype._checkBuffer = function() { + var t = this.config, + e = this.media; + if (e && 0 !== e.readyState) { + var r = e.currentTime, + i = this.mediaBuffer ? this.mediaBuffer : e, + a = i.buffered; + if (!this.loadedmetadata && a.length) this.loadedmetadata = !0, this._seekToStartPos(); + else if (this.immediateSwitch) this.immediateLevelSwitchEnd(); + else { + var n = !(e.paused && e.readyState > 1 || e.ended || 0 === e.buffered.length), + o = window.performance.now(); + if (r !== this.lastCurrentTime) this.stallReported && (g.b.warn("playback not stuck anymore @" + r + ", after " + Math.round(o - this.stalled) + "ms"), this.stallReported = !1), this.stalled = null, this.nudgeRetry = 0; + else if (n) { + var l = o - this.stalled, + u = s.a.bufferInfo(e, r, t.maxBufferHole); + if (!this.stalled) return void(this.stalled = o); + l >= 1e3 && this._reportStall(u.len), this._tryFixBufferStall(u, l) + } + } + } + }, e.prototype.onFragLoadEmergencyAborted = function() { + this.state = T.IDLE, this.loadedmetadata || (this.startFragRequested = !1, this.nextLoadPosition = this.startPosition), this.tick() + }, e.prototype.onBufferFlushed = function() { + var t = this.mediaBuffer ? this.mediaBuffer : this.media; + t && this.fragmentTracker.detectEvictedFragments(c.a.ElementaryStreamTypes.VIDEO, t.buffered), this.state = T.IDLE, this.fragPrevious = null + }, e.prototype.swapAudioCodec = function() { + this.audioCodecSwap = !this.audioCodecSwap + }, e.prototype.computeLivePosition = function(t, e) { + var r = void 0 !== this.config.liveSyncDuration ? this.config.liveSyncDuration : this.config.liveSyncDurationCount * e.targetduration; + return t + Math.max(0, e.totalduration - r) + }, e.prototype._tryFixBufferStall = function(t, e) { + var r = this.config, + i = this.media, + a = i.currentTime, + n = this.fragmentTracker.getPartialFragment(a); + n && this._trySkipBufferHole(n), t.len > .5 && e > 1e3 * r.highBufferWatchdogPeriod && (this.stalled = null, this._tryNudgeBuffer()) + }, e.prototype._reportStall = function(t) { + var e = this.hls, + r = this.media; + this.stallReported || (this.stallReported = !0, g.b.warn("Playback stalling at @" + r.currentTime + " due to low buffer"), e.trigger(u.a.ERROR, { + type: v.b.MEDIA_ERROR, + details: v.a.BUFFER_STALLED_ERROR, + fatal: !1, + buffer: t + })) + }, e.prototype._trySkipBufferHole = function(t) { + for (var e = this.hls, r = this.media, i = r.currentTime, a = 0, n = 0; n < r.buffered.length; n++) { + var o = r.buffered.start(n); + if (i >= a && i < o) return r.currentTime = Math.max(o, r.currentTime + .1), g.b.warn("skipping hole, adjusting currentTime from " + i + " to " + r.currentTime), this.stalled = null, void e.trigger(u.a.ERROR, { + type: v.b.MEDIA_ERROR, + details: v.a.BUFFER_SEEK_OVER_HOLE, + fatal: !1, + reason: "fragment loaded with buffer holes, seeking from " + i + " to " + r.currentTime, + frag: t + }); + a = r.buffered.end(n) + } + }, e.prototype._tryNudgeBuffer = function() { + var t = this.config, + e = this.hls, + r = this.media, + i = r.currentTime, + a = (this.nudgeRetry || 0) + 1; + if (this.nudgeRetry = a, a < t.nudgeMaxRetry) { + var n = i + a * t.nudgeOffset; + g.b.log("adjust currentTime from " + i + " to " + n), r.currentTime = n, e.trigger(u.a.ERROR, { + type: v.b.MEDIA_ERROR, + details: v.a.BUFFER_NUDGE_ON_STALL, + fatal: !1 + }) + } else g.b.error("still stuck in high buffer @" + i + " after " + t.nudgeMaxRetry + ", raise fatal error"), e.trigger(u.a.ERROR, { + type: v.b.MEDIA_ERROR, + details: v.a.BUFFER_STALLED_ERROR, + fatal: !0 + }) + }, e.prototype._seekToStartPos = function() { + var t = this.media, + e = t.currentTime, + r = t.seeking ? e : this.startPosition; + e !== r && (g.b.log("target start position not buffered, seek to buffered.start(0) " + r + " from current time " + e + " "), t.currentTime = r) + }, E(e, [{ + key: "state", + set: function(t) { + if (this.state !== t) { + var e = this.state; + this._state = t, g.b.log("main stream:" + e + "->" + t), this.hls.trigger(u.a.STREAM_STATE_TRANSITION, { + previousState: e, + nextState: t + }) + } + }, + get: function() { + return this._state + } + }, { + key: "currentLevel", + get: function() { + var t = this.media; + if (t) { + var e = this.getBufferedFrag(t.currentTime); + if (e) return e.level + } + return -1 + } + }, { + key: "nextBufferedFrag", + get: function() { + var t = this.media; + return t ? this.followingBufferedFrag(this.getBufferedFrag(t.currentTime)) : null + } + }, { + key: "nextLevel", + get: function() { + var t = this.nextBufferedFrag; + return t ? t.level : -1 + } + }, { + key: "liveSyncPosition", + get: function() { + return this._liveSyncPosition + }, + set: function(t) { + this._liveSyncPosition = t + } + }]), e + }(m.a); + e.a = S + }, function(t, e, r) { + function i(t) { + function e(i) { + if (r[i]) return r[i].exports; + var a = r[i] = { + i: i, + l: !1, + exports: {} + }; + return t[i].call(a.exports, a, a.exports, e), a.l = !0, a.exports + } + var r = {}; + e.m = t, e.c = r, e.i = function(t) { + return t + }, e.d = function(t, r, i) { + e.o(t, r) || Object.defineProperty(t, r, { + configurable: !1, + enumerable: !0, + get: i + }) + }, e.n = function(t) { + var r = t && t.__esModule ? function() { + return t.default + } : function() { + return t + }; + return e.d(r, "a", r), r + }, e.o = function(t, e) { + return Object.prototype.hasOwnProperty.call(t, e) + }, e.p = "/", e.oe = function(t) { + throw console.error(t), t + }; + var i = e(e.s = ENTRY_MODULE); + return i.default || i + } + + function a(t) { + return (t + "").replace(/[.?*+^$[\]\\(){}|-]/g, "\\$&") + } + + function n(t, e, i) { + var n = {}; + n[i] = []; + var o = e.toString(), + s = o.match(/^function\s?\(\w+,\s*\w+,\s*(\w+)\)/); + if (!s) return n; + for (var d, c = s[1], h = new RegExp("(\\\\n|\\W)" + a(c) + u, "g"); d = h.exec(o);) "dll-reference" !== d[3] && n[i].push(d[3]); + for (h = new RegExp("\\(" + a(c) + '\\("(dll-reference\\s(' + l + '))"\\)\\)' + u, "g"); d = h.exec(o);) t[d[2]] || (n[i].push(d[1]), t[d[2]] = r(d[1]).m), n[d[2]] = n[d[2]] || [], n[d[2]].push(d[4]); + return n + } + + function o(t) { + return Object.keys(t).reduce(function(e, r) { + return e || t[r].length > 0 + }, !1) + } + + function s(t, e) { + for (var r = { + main: [e] + }, i = { + main: [] + }, a = { + main: {} + }; o(r);) + for (var s = Object.keys(r), l = 0; l < s.length; l++) { + var u = s[l], + d = r[u], + c = d.pop(); + if (a[u] = a[u] || {}, !a[u][c] && t[u][c]) { + a[u][c] = !0, i[u] = i[u] || [], i[u].push(c); + for (var h = n(t, t[u][c], u), f = Object.keys(h), p = 0; p < f.length; p++) r[f[p]] = r[f[p]] || [], r[f[p]] = r[f[p]].concat(h[f[p]]) + } + } + return i + } + var l = "[\\.|\\-|\\+|\\w|/|@]+", + u = "\\((/\\*.*?\\*/)?s?.*?(" + l + ").*?\\)"; + t.exports = function(t, e) { + e = e || {}; + var a = { + main: r.m + }, + n = e.all ? { + main: Object.keys(a) + } : s(a, t), + o = ""; + Object.keys(n).filter(function(t) { + return "main" !== t + }).forEach(function(t) { + for (var e = 0; n[t][e];) e++; + n[t].push(e), a[t][e] = "(function(module, exports, __webpack_require__) { module.exports = __webpack_require__; })", o = o + "var " + t + " = (" + i.toString().replace("ENTRY_MODULE", JSON.stringify(e)) + ")({" + n[t].map(function(e) { + return JSON.stringify(e) + ": " + a[t][e].toString() + }).join(",") + "});\n" + }), o = o + "(" + i.toString().replace("ENTRY_MODULE", JSON.stringify(t)) + ")({" + n.main.map(function(t) { + return JSON.stringify(t) + ": " + a.main[t].toString() + }).join(",") + "})(self);"; + var l = new window.Blob([o], { + type: "text/javascript" + }); + if (e.bare) return l; + var u = window.URL || window.webkitURL || window.mozURL || window.msURL, + d = u.createObjectURL(l), + c = new window.Worker(d); + return c.objectURL = d, c + } + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + var a = function() { + function t(e, r) { + i(this, t), this.subtle = e, this.aesIV = r + } + return t.prototype.decrypt = function(t, e) { + return this.subtle.decrypt({ + name: "AES-CBC", + iv: this.aesIV + }, e, t) + }, t + }(); + e.a = a + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + var a = function() { + function t(e, r) { + i(this, t), this.subtle = e, this.key = r + } + return t.prototype.expandKey = function() { + return this.subtle.importKey("raw", this.key, { + name: "AES-CBC" + }, !1, ["encrypt", "decrypt"]) + }, t + }(); + e.a = a + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + + function a(t) { + var e = t.byteLength, + r = e && new DataView(t).getUint8(e - 1); + return r ? t.slice(0, e - r) : t + } + var n = function() { + function t() { + i(this, t), this.rcon = [0, 1, 2, 4, 8, 16, 32, 64, 128, 27, 54], this.subMix = [new Uint32Array(256), new Uint32Array(256), new Uint32Array(256), new Uint32Array(256)], this.invSubMix = [new Uint32Array(256), new Uint32Array(256), new Uint32Array(256), new Uint32Array(256)], this.sBox = new Uint32Array(256), this.invSBox = new Uint32Array(256), this.key = new Uint32Array(0), this.initTable() + } + return t.prototype.uint8ArrayToUint32Array_ = function(t) { + for (var e = new DataView(t), r = new Uint32Array(4), i = 0; i < 4; i++) r[i] = e.getUint32(4 * i); + return r + }, t.prototype.initTable = function() { + var t = this.sBox, + e = this.invSBox, + r = this.subMix, + i = r[0], + a = r[1], + n = r[2], + o = r[3], + s = this.invSubMix, + l = s[0], + u = s[1], + d = s[2], + c = s[3], + h = new Uint32Array(256), + f = 0, + p = 0, + v = 0; + for (v = 0; v < 256; v++) h[v] = v < 128 ? v << 1 : v << 1 ^ 283; + for (v = 0; v < 256; v++) { + var g = p ^ p << 1 ^ p << 2 ^ p << 3 ^ p << 4; + g = g >>> 8 ^ 255 & g ^ 99, t[f] = g, e[g] = f; + var y = h[f], + m = h[y], + b = h[m], + E = 257 * h[g] ^ 16843008 * g; + i[f] = E << 24 | E >>> 8, a[f] = E << 16 | E >>> 16, n[f] = E << 8 | E >>> 24, o[f] = E, E = 16843009 * b ^ 65537 * m ^ 257 * y ^ 16843008 * f, l[g] = E << 24 | E >>> 8, u[g] = E << 16 | E >>> 16, d[g] = E << 8 | E >>> 24, c[g] = E, f ? (f = y ^ h[h[h[b ^ y]]], p ^= h[h[p]]) : f = p = 1 + } + }, t.prototype.expandKey = function(t) { + for (var e = this.uint8ArrayToUint32Array_(t), r = !0, i = 0; i < e.length && r;) r = e[i] === this.key[i], i++; + if (!r) { + this.key = e; + var a = this.keySize = e.length; + if (4 !== a && 6 !== a && 8 !== a) throw new Error("Invalid aes key size=" + a); + var n = this.ksRows = 4 * (a + 6 + 1), + o = void 0, + s = void 0, + l = this.keySchedule = new Uint32Array(n), + u = this.invKeySchedule = new Uint32Array(n), + d = this.sBox, + c = this.rcon, + h = this.invSubMix, + f = h[0], + p = h[1], + v = h[2], + g = h[3], + y = void 0, + m = void 0; + for (o = 0; o < n; o++) o < a ? y = l[o] = e[o] : (m = y, o % a == 0 ? (m = m << 8 | m >>> 24, m = d[m >>> 24] << 24 | d[m >>> 16 & 255] << 16 | d[m >>> 8 & 255] << 8 | d[255 & m], m ^= c[o / a | 0] << 24) : a > 6 && o % a == 4 && (m = d[m >>> 24] << 24 | d[m >>> 16 & 255] << 16 | d[m >>> 8 & 255] << 8 | d[255 & m]), l[o] = y = (l[o - a] ^ m) >>> 0); + for (s = 0; s < n; s++) o = n - s, m = 3 & s ? l[o] : l[o - 4], u[s] = s < 4 || o <= 4 ? m : f[d[m >>> 24]] ^ p[d[m >>> 16 & 255]] ^ v[d[m >>> 8 & 255]] ^ g[d[255 & m]], u[s] = u[s] >>> 0 + } + }, t.prototype.networkToHostOrderSwap = function(t) { + return t << 24 | (65280 & t) << 8 | (16711680 & t) >> 8 | t >>> 24 + }, t.prototype.decrypt = function(t, e, r, i) { + for (var n = this.keySize + 6, o = this.invKeySchedule, s = this.invSBox, l = this.invSubMix, u = l[0], d = l[1], c = l[2], h = l[3], f = this.uint8ArrayToUint32Array_(r), p = f[0], v = f[1], g = f[2], y = f[3], m = new Int32Array(t), b = new Int32Array(m.length), E = void 0, T = void 0, S = void 0, R = void 0, A = void 0, _ = void 0, w = void 0, L = void 0, D = void 0, I = void 0, k = void 0, O = void 0, C = void 0, P = void 0, x = this.networkToHostOrderSwap; e < m.length;) { + for (D = x(m[e]), I = x(m[e + 1]), k = x(m[e + 2]), O = x(m[e + 3]), A = D ^ o[0], _ = O ^ o[1], w = k ^ o[2], L = I ^ o[3], C = 4, P = 1; P < n; P++) E = u[A >>> 24] ^ d[_ >> 16 & 255] ^ c[w >> 8 & 255] ^ h[255 & L] ^ o[C], T = u[_ >>> 24] ^ d[w >> 16 & 255] ^ c[L >> 8 & 255] ^ h[255 & A] ^ o[C + 1], S = u[w >>> 24] ^ d[L >> 16 & 255] ^ c[A >> 8 & 255] ^ h[255 & _] ^ o[C + 2], R = u[L >>> 24] ^ d[A >> 16 & 255] ^ c[_ >> 8 & 255] ^ h[255 & w] ^ o[C + 3], A = E, _ = T, w = S, L = R, C += 4; + E = s[A >>> 24] << 24 ^ s[_ >> 16 & 255] << 16 ^ s[w >> 8 & 255] << 8 ^ s[255 & L] ^ o[C], T = s[_ >>> 24] << 24 ^ s[w >> 16 & 255] << 16 ^ s[L >> 8 & 255] << 8 ^ s[255 & A] ^ o[C + 1], S = s[w >>> 24] << 24 ^ s[L >> 16 & 255] << 16 ^ s[A >> 8 & 255] << 8 ^ s[255 & _] ^ o[C + 2], R = s[L >>> 24] << 24 ^ s[A >> 16 & 255] << 16 ^ s[_ >> 8 & 255] << 8 ^ s[255 & w] ^ o[C + 3], C += 3, b[e] = x(E ^ p), b[e + 1] = x(R ^ v), b[e + 2] = x(S ^ g), b[e + 3] = x(T ^ y), p = D, v = I, g = k, y = O, e += 4 + } + return i ? a(b.buffer) : b.buffer + }, t.prototype.destroy = function() { + this.key = void 0, this.keySize = void 0, this.ksRows = void 0, this.sBox = void 0, this.invSBox = void 0, this.subMix = void 0, this.invSubMix = void 0, this.keySchedule = void 0, this.invKeySchedule = void 0, this.rcon = void 0 + }, t + }(); + e.a = n + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + var a = r(22), + n = r(0), + o = r(7), + s = function() { + function t(e, r, a) { + i(this, t), this.observer = e, this.config = a, this.remuxer = r + } + return t.prototype.resetInitSegment = function(t, e, r, i) { + this._audioTrack = { + container: "audio/adts", + type: "audio", + id: 0, + sequenceNumber: 0, + isAAC: !0, + samples: [], + len: 0, + manifestCodec: e, + duration: i, + inputTimeScale: 9e4 + } + }, t.prototype.resetTimeStamp = function() {}, t.probe = function(t) { + if (!t) return !1; + for (var e = o.a.getID3Data(t, 0) || [], r = e.length, i = t.length; r < i; r++) + if (a.e(t, r)) return n.b.log("ADTS sync word found !"), !0; + return !1 + }, t.prototype.append = function(t, e, r, i) { + for (var s = this._audioTrack, l = o.a.getID3Data(t, 0) || [], u = o.a.getTimeStamp(l), d = u ? 90 * u : 9e4 * e, c = 0, h = d, f = t.length, p = l.length, v = [{ + pts: h, + dts: h, + data: l + }]; p < f - 1;) + if (a.d(t, p) && p + 5 < f) { + a.c(s, this.observer, t, p, s.manifestCodec); + var g = a.a(s, t, p, d, c); + if (!g) { + n.b.log("Unable to parse AAC frame"); + break + } + p += g.length, h = g.sample.pts, c++ + } else o.a.isHeader(t, p) ? (l = o.a.getID3Data(t, p), v.push({ + pts: h, + dts: h, + data: l + }), p += l.length) : p++; + this.remuxer.remux(s, { + samples: [] + }, { + samples: v, + inputTimeScale: 9e4 + }, { + samples: [] + }, e, r, i) + }, t.prototype.destroy = function() {}, t + }(); + e.a = s + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + var a = r(22), + n = r(23), + o = r(1), + s = r(40), + l = r(41), + u = r(0), + d = r(2), + c = { + video: 1, + audio: 2, + id3: 3, + text: 4 + }, + h = function() { + function t(e, r, a, n) { + i(this, t), this.observer = e, this.config = a, this.typeSupported = n, this.remuxer = r, this.sampleAes = null + } + return t.prototype.setDecryptData = function(t) { + null != t && null != t.key && "SAMPLE-AES" === t.method ? this.sampleAes = new l.a(this.observer, this.config, t, this.discardEPB) : this.sampleAes = null + }, t.probe = function(e) { + var r = t._syncOffset(e); + return !(r < 0) && (r && u.b.warn("MPEG2-TS detected but first sync word found @ offset " + r + ", junk ahead ?"), !0) + }, t._syncOffset = function(t) { + for (var e = Math.min(1e3, t.length - 564), r = 0; r < e;) { + if (71 === t[r] && 71 === t[r + 188] && 71 === t[r + 376]) return r; + r++ + } + return -1 + }, t.createTrack = function(t, e) { + return { + container: "video" === t || "audio" === t ? "video/mp2t" : void 0, + type: t, + id: c[t], + pid: -1, + inputTimeScale: 9e4, + sequenceNumber: 0, + samples: [], + len: 0, + dropped: "video" === t ? 0 : void 0, + isAAC: "audio" === t || void 0, + duration: "audio" === t ? e : void 0 + } + }, t.prototype.resetInitSegment = function(e, r, i, a) { + this.pmtParsed = !1, this._pmtId = -1, this._avcTrack = t.createTrack("video", a), this._audioTrack = t.createTrack("audio", a), this._id3Track = t.createTrack("id3", a), this._txtTrack = t.createTrack("text", a), this.aacOverFlow = null, this.aacLastPTS = null, this.avcSample = null, this.audioCodec = r, this.videoCodec = i, this._duration = a + }, t.prototype.resetTimeStamp = function() {}, t.prototype.append = function(e, r, i, a) { + var n = void 0, + s = e.length, + l = void 0, + c = void 0, + h = void 0, + f = void 0, + p = !1; + this.contiguous = i; + var v = this.pmtParsed, + g = this._avcTrack, + y = this._audioTrack, + m = this._id3Track, + b = g.pid, + E = y.pid, + T = m.pid, + S = this._pmtId, + R = g.pesData, + A = y.pesData, + _ = m.pesData, + w = this._parsePAT, + L = this._parsePMT, + D = this._parsePES, + I = this._parseAVCPES.bind(this), + k = this._parseAACPES.bind(this), + O = this._parseMPEGPES.bind(this), + C = this._parseID3PES.bind(this), + P = t._syncOffset(e); + for (s -= (s + P) % 188, n = P; n < s; n += 188) + if (71 === e[n]) { + if (l = !!(64 & e[n + 1]), c = ((31 & e[n + 1]) << 8) + e[n + 2], (48 & e[n + 3]) >> 4 > 1) { + if ((h = n + 5 + e[n + 4]) === n + 188) continue + } else h = n + 4; + switch (c) { + case b: + l && (R && (f = D(R)) && void 0 !== f.pts && I(f, !1), R = { + data: [], + size: 0 + }), R && (R.data.push(e.subarray(h, n + 188)), R.size += n + 188 - h); + break; + case E: + l && (A && (f = D(A)) && void 0 !== f.pts && (y.isAAC ? k(f) : O(f)), A = { + data: [], + size: 0 + }), A && (A.data.push(e.subarray(h, n + 188)), A.size += n + 188 - h); + break; + case T: + l && (_ && (f = D(_)) && void 0 !== f.pts && C(f), _ = { + data: [], + size: 0 + }), _ && (_.data.push(e.subarray(h, n + 188)), _.size += n + 188 - h); + break; + case 0: + l && (h += e[h] + 1), S = this._pmtId = w(e, h); + break; + case S: + l && (h += e[h] + 1); + var x = L(e, h, !0 === this.typeSupported.mpeg || !0 === this.typeSupported.mp3, null != this.sampleAes); + b = x.avc, b > 0 && (g.pid = b), E = x.audio, E > 0 && (y.pid = E, y.isAAC = x.isAAC), T = x.id3, T > 0 && (m.pid = T), p && !v && (u.b.log("reparse from beginning"), p = !1, n = P - 188), v = this.pmtParsed = !0; + break; + case 17: + case 8191: + break; + default: + p = !0 + } + } else this.observer.trigger(o.a.ERROR, { + type: d.b.MEDIA_ERROR, + details: d.a.FRAG_PARSING_ERROR, + fatal: !1, + reason: "TS packet did not start with 0x47" + }); + R && (f = D(R)) && void 0 !== f.pts ? (I(f, !0), g.pesData = null) : g.pesData = R, A && (f = D(A)) && void 0 !== f.pts ? (y.isAAC ? k(f) : O(f), y.pesData = null) : (A && A.size && u.b.log("last AAC PES packet truncated,might overlap between fragments"), y.pesData = A), _ && (f = D(_)) && void 0 !== f.pts ? (C(f), m.pesData = null) : m.pesData = _, null == this.sampleAes ? this.remuxer.remux(y, g, m, this._txtTrack, r, i, a) : this.decryptAndRemux(y, g, m, this._txtTrack, r, i, a) + }, t.prototype.decryptAndRemux = function(t, e, r, i, a, n, o) { + if (t.samples && t.isAAC) { + var s = this; + this.sampleAes.decryptAacSamples(t.samples, 0, function() { + s.decryptAndRemuxAvc(t, e, r, i, a, n, o) + }) + } else this.decryptAndRemuxAvc(t, e, r, i, a, n, o) + }, t.prototype.decryptAndRemuxAvc = function(t, e, r, i, a, n, o) { + if (e.samples) { + var s = this; + this.sampleAes.decryptAvcSamples(e.samples, 0, 0, function() { + s.remuxer.remux(t, e, r, i, a, n, o) + }) + } else this.remuxer.remux(t, e, r, i, a, n, o) + }, t.prototype.destroy = function() { + this._initPTS = this._initDTS = void 0, this._duration = 0 + }, t.prototype._parsePAT = function(t, e) { + return (31 & t[e + 10]) << 8 | t[e + 11] + }, t.prototype._parsePMT = function(t, e, r, i) { + var a = void 0, + n = void 0, + o = void 0, + s = void 0, + l = { + audio: -1, + avc: -1, + id3: -1, + isAAC: !0 + }; + for (a = (15 & t[e + 1]) << 8 | t[e + 2], n = e + 3 + a - 4, o = (15 & t[e + 10]) << 8 | t[e + 11], e += 12 + o; e < n;) { + switch (s = (31 & t[e + 1]) << 8 | t[e + 2], t[e]) { + case 207: + if (!i) { + u.b.log("unkown stream type:" + t[e]); + break + } + case 15: + -1 === l.audio && (l.audio = s); + break; + case 21: + -1 === l.id3 && (l.id3 = s); + break; + case 219: + if (!i) { + u.b.log("unkown stream type:" + t[e]); + break + } + case 27: + -1 === l.avc && (l.avc = s); + break; + case 3: + case 4: + r ? -1 === l.audio && (l.audio = s, l.isAAC = !1) : u.b.log("MPEG audio found, not supported in this browser for now"); + break; + case 36: + u.b.warn("HEVC stream type found, not supported for now"); + break; + default: + u.b.log("unkown stream type:" + t[e]) + } + e += 5 + ((15 & t[e + 3]) << 8 | t[e + 4]) + } + return l + }, t.prototype._parsePES = function(t) { + var e = 0, + r = void 0, + i = void 0, + a = void 0, + n = void 0, + o = void 0, + s = void 0, + l = void 0, + d = void 0, + c = t.data; + if (!t || 0 === t.size) return null; + for (; c[0].length < 19 && c.length > 1;) { + var h = new Uint8Array(c[0].length + c[1].length); + h.set(c[0]), h.set(c[1], c[0].length), c[0] = h, c.splice(1, 1) + } + if (r = c[0], 1 === (r[0] << 16) + (r[1] << 8) + r[2]) { + if ((a = (r[4] << 8) + r[5]) && a > t.size - 6) return null; + i = r[7], 192 & i && (s = 536870912 * (14 & r[9]) + 4194304 * (255 & r[10]) + 16384 * (254 & r[11]) + 128 * (255 & r[12]) + (254 & r[13]) / 2, s > 4294967295 && (s -= 8589934592), 64 & i ? (l = 536870912 * (14 & r[14]) + 4194304 * (255 & r[15]) + 16384 * (254 & r[16]) + 128 * (255 & r[17]) + (254 & r[18]) / 2, l > 4294967295 && (l -= 8589934592), s - l > 54e5 && (u.b.warn(Math.round((s - l) / 9e4) + "s delta between PTS and DTS, align them"), s = l)) : l = s), n = r[8], d = n + 9, t.size -= d, o = new Uint8Array(t.size); + for (var f = 0, p = c.length; f < p; f++) { + r = c[f]; + var v = r.byteLength; + if (d) { + if (d > v) { + d -= v; + continue + } + r = r.subarray(d), v -= d, d = 0 + } + o.set(r, e), e += v + } + return a && (a -= n + 3), { + data: o, + pts: s, + dts: l, + len: a + } + } + return null + }, t.prototype.pushAccesUnit = function(t, e) { + if (t.units.length && t.frame) { + var r = e.samples, + i = r.length; + !this.config.forceKeyFrameOnDiscontinuity || !0 === t.key || e.sps && (i || this.contiguous) ? (t.id = i, r.push(t)) : e.dropped++ + } + t.debug.length && u.b.log(t.pts + "/" + t.dts + ":" + t.debug) + }, t.prototype._parseAVCPES = function(t, e) { + var r = this, + i = this._avcTrack, + a = this._parseAVCNALu(t.data), + n = void 0, + o = this.avcSample, + l = void 0, + u = !1, + d = void 0, + c = this.pushAccesUnit.bind(this), + h = function(t, e, r, i) { + return { + key: t, + pts: e, + dts: r, + units: [], + debug: i + } + }; + t.data = null, o && a.length && !i.audFound && (c(o, i), o = this.avcSample = h(!1, t.pts, t.dts, "")), a.forEach(function(e) { + switch (e.type) { + case 1: + l = !0, o || (o = r.avcSample = h(!0, t.pts, t.dts, "")), o.frame = !0; + var a = e.data; + if (u && a.length > 4) { + var f = new s.a(a).readSliceType(); + 2 !== f && 4 !== f && 7 !== f && 9 !== f || (o.key = !0) + } + break; + case 5: + l = !0, o || (o = r.avcSample = h(!0, t.pts, t.dts, "")), o.key = !0, o.frame = !0; + break; + case 6: + l = !0, n = new s.a(r.discardEPB(e.data)), n.readUByte(); + for (var p = 0, v = 0, g = !1, y = 0; !g && n.bytesAvailable > 1;) { + p = 0; + do { + y = n.readUByte(), p += y + } while (255 === y); + v = 0; + do { + y = n.readUByte(), v += y + } while (255 === y); + if (4 === p && 0 !== n.bytesAvailable) { + g = !0; + if (181 === n.readUByte()) { + if (49 === n.readUShort()) { + if (1195456820 === n.readUInt()) { + if (3 === n.readUByte()) { + var m = n.readUByte(), + b = n.readUByte(), + E = 31 & m, + T = [m, b]; + for (d = 0; d < E; d++) T.push(n.readUByte()), T.push(n.readUByte()), T.push(n.readUByte()); + r._insertSampleInOrder(r._txtTrack.samples, { + type: 3, + pts: t.pts, + bytes: T + }) + } + } + } + } + } else if (v < n.bytesAvailable) + for (d = 0; d < v; d++) n.readUByte() + } + break; + case 7: + if (l = !0, u = !0, !i.sps) { + n = new s.a(e.data); + var S = n.readSPS(); + i.width = S.width, i.height = S.height, i.pixelRatio = S.pixelRatio, i.sps = [e.data], i.duration = r._duration; + var R = e.data.subarray(1, 4), + A = "avc1."; + for (d = 0; d < 3; d++) { + var _ = R[d].toString(16); + _.length < 2 && (_ = "0" + _), A += _ + } + i.codec = A + } + break; + case 8: + l = !0, i.pps || (i.pps = [e.data]); + break; + case 9: + l = !1, i.audFound = !0, o && c(o, i), o = r.avcSample = h(!1, t.pts, t.dts, ""); + break; + case 12: + l = !1; + break; + default: + l = !1, o && (o.debug += "unknown NAL " + e.type + " ") + } + if (o && l) { + o.units.push(e) + } + }), e && o && (c(o, i), this.avcSample = null) + }, t.prototype._insertSampleInOrder = function(t, e) { + var r = t.length; + if (r > 0) { + if (e.pts >= t[r - 1].pts) t.push(e); + else + for (var i = r - 1; i >= 0; i--) + if (e.pts < t[i].pts) { + t.splice(i, 0, e); + break + } + } else t.push(e) + }, t.prototype._getLastNalUnit = function() { + var t = this.avcSample, + e = void 0; + if (!t || 0 === t.units.length) { + var r = this._avcTrack, + i = r.samples; + t = i[i.length - 1] + } + if (t) { + var a = t.units; + e = a[a.length - 1] + } + return e + }, t.prototype._parseAVCNALu = function(t) { + var e = 0, + r = t.byteLength, + i = void 0, + a = void 0, + n = this._avcTrack, + o = n.naluState || 0, + s = o, + l = [], + u = void 0, + d = void 0, + c = -1, + h = void 0; + for (-1 === o && (c = 0, h = 31 & t[0], o = 0, e = 1); e < r;) + if (i = t[e++], o) + if (1 !== o) + if (i) + if (1 === i) { + if (c >= 0) u = { + data: t.subarray(c, e - o - 1), + type: h + }, l.push(u); + else { + var f = this._getLastNalUnit(); + if (f && (s && e <= 4 - s && f.state && (f.data = f.data.subarray(0, f.data.byteLength - s)), (a = e - o - 1) > 0)) { + var p = new Uint8Array(f.data.byteLength + a); + p.set(f.data, 0), p.set(t.subarray(0, a), f.data.byteLength), f.data = p + } + } + e < r ? (d = 31 & t[e], c = e, h = d, o = 0) : o = -1 + } else o = 0; + else o = 3; + else o = i ? 0 : 2; + else o = i ? 0 : 1; + if (c >= 0 && o >= 0 && (u = { + data: t.subarray(c, r), + type: h, + state: o + }, l.push(u)), 0 === l.length) { + var v = this._getLastNalUnit(); + if (v) { + var g = new Uint8Array(v.data.byteLength + t.byteLength); + g.set(v.data, 0), g.set(t, v.data.byteLength), v.data = g + } + } + return n.naluState = o, l + }, t.prototype.discardEPB = function(t) { + for (var e = t.byteLength, r = [], i = 1, a = void 0, n = void 0; i < e - 2;) 0 === t[i] && 0 === t[i + 1] && 3 === t[i + 2] ? (r.push(i + 2), i += 2) : i++; + if (0 === r.length) return t; + a = e - r.length, n = new Uint8Array(a); + var o = 0; + for (i = 0; i < a; o++, i++) o === r[0] && (o++, r.shift()), n[i] = t[o]; + return n + }, t.prototype._parseAACPES = function(t) { + var e = this._audioTrack, + r = t.data, + i = t.pts, + n = this.aacOverFlow, + s = this.aacLastPTS, + l = void 0, + c = void 0, + h = void 0, + f = void 0, + p = void 0; + if (n) { + var v = new Uint8Array(n.byteLength + r.byteLength); + v.set(n, 0), v.set(r, n.byteLength), r = v + } + for (h = 0, p = r.length; h < p - 1 && !a.d(r, h); h++); + if (h) { + var g = void 0, + y = void 0; + if (h < p - 1 ? (g = "AAC PES did not start with ADTS header,offset:" + h, y = !1) : (g = "no ADTS header found in AAC PES", y = !0), u.b.warn("parsing error:" + g), this.observer.trigger(o.a.ERROR, { + type: d.b.MEDIA_ERROR, + details: d.a.FRAG_PARSING_ERROR, + fatal: y, + reason: g + }), y) return + } + if (a.c(e, this.observer, r, h, this.audioCodec), c = 0, l = a.b(e.samplerate), n && s) { + var m = s + l; + Math.abs(m - i) > 1 && (u.b.log("AAC: align PTS for overlapping frames by " + Math.round((m - i) / 90)), i = m) + } + for (; h < p;) + if (a.d(r, h) && h + 5 < p) { + var b = a.a(e, r, h, i, c); + if (!b) break; + h += b.length, f = b.sample.pts, c++ + } else h++; + n = h < p ? r.subarray(h, p) : null, this.aacOverFlow = n, this.aacLastPTS = f + }, t.prototype._parseMPEGPES = function(t) { + for (var e = t.data, r = e.length, i = 0, a = 0, o = t.pts; a < r;) + if (n.a.isHeader(e, a)) { + var s = n.a.appendFrame(this._audioTrack, e, a, o, i); + if (!s) break; + a += s.length, i++ + } else a++ + }, t.prototype._parseID3PES = function(t) { + this._id3Track.samples.push(t) + }, t + }(); + e.a = h + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + var a = r(0), + n = function() { + function t(e) { + i(this, t), this.data = e, this.bytesAvailable = e.byteLength, this.word = 0, this.bitsAvailable = 0 + } + return t.prototype.loadWord = function() { + var t = this.data, + e = this.bytesAvailable, + r = t.byteLength - e, + i = new Uint8Array(4), + a = Math.min(4, e); + if (0 === a) throw new Error("no bytes available"); + i.set(t.subarray(r, r + a)), this.word = new DataView(i.buffer).getUint32(0), this.bitsAvailable = 8 * a, this.bytesAvailable -= a + }, t.prototype.skipBits = function(t) { + var e = void 0; + this.bitsAvailable > t ? (this.word <<= t, this.bitsAvailable -= t) : (t -= this.bitsAvailable, e = t >> 3, t -= e >> 3, this.bytesAvailable -= e, this.loadWord(), this.word <<= t, this.bitsAvailable -= t) + }, t.prototype.readBits = function(t) { + var e = Math.min(this.bitsAvailable, t), + r = this.word >>> 32 - e; + return t > 32 && a.b.error("Cannot read more than 32 bits at a time"), this.bitsAvailable -= e, this.bitsAvailable > 0 ? this.word <<= e : this.bytesAvailable > 0 && this.loadWord(), e = t - e, e > 0 && this.bitsAvailable ? r << e | this.readBits(e) : r + }, t.prototype.skipLZ = function() { + var t = void 0; + for (t = 0; t < this.bitsAvailable; ++t) + if (0 != (this.word & 2147483648 >>> t)) return this.word <<= t, this.bitsAvailable -= t, t; + return this.loadWord(), t + this.skipLZ() + }, t.prototype.skipUEG = function() { + this.skipBits(1 + this.skipLZ()) + }, t.prototype.skipEG = function() { + this.skipBits(1 + this.skipLZ()) + }, t.prototype.readUEG = function() { + var t = this.skipLZ(); + return this.readBits(t + 1) - 1 + }, t.prototype.readEG = function() { + var t = this.readUEG(); + return 1 & t ? 1 + t >>> 1 : -1 * (t >>> 1) + }, t.prototype.readBoolean = function() { + return 1 === this.readBits(1) + }, t.prototype.readUByte = function() { + return this.readBits(8) + }, t.prototype.readUShort = function() { + return this.readBits(16) + }, t.prototype.readUInt = function() { + return this.readBits(32) + }, t.prototype.skipScalingList = function(t) { + var e = 8, + r = 8, + i = void 0, + a = void 0; + for (i = 0; i < t; i++) 0 !== r && (a = this.readEG(), r = (e + a + 256) % 256), e = 0 === r ? e : r + }, t.prototype.readSPS = function() { + var t = 0, + e = 0, + r = 0, + i = 0, + a = void 0, + n = void 0, + o = void 0, + s = void 0, + l = void 0, + u = void 0, + d = void 0, + c = this.readUByte.bind(this), + h = this.readBits.bind(this), + f = this.readUEG.bind(this), + p = this.readBoolean.bind(this), + v = this.skipBits.bind(this), + g = this.skipEG.bind(this), + y = this.skipUEG.bind(this), + m = this.skipScalingList.bind(this); + if (c(), a = c(), h(5), v(3), c(), y(), 100 === a || 110 === a || 122 === a || 244 === a || 44 === a || 83 === a || 86 === a || 118 === a || 128 === a) { + var b = f(); + if (3 === b && v(1), y(), y(), v(1), p()) + for (u = 3 !== b ? 8 : 12, d = 0; d < u; d++) p() && m(d < 6 ? 16 : 64) + } + y(); + var E = f(); + if (0 === E) f(); + else if (1 === E) + for (v(1), g(), g(), n = f(), d = 0; d < n; d++) g(); + y(), v(1), o = f(), s = f(), l = h(1), 0 === l && v(1), v(1), p() && (t = f(), e = f(), r = f(), i = f()); + var T = [1, 1]; + if (p() && p()) { + switch (c()) { + case 1: + T = [1, 1]; + break; + case 2: + T = [12, 11]; + break; + case 3: + T = [10, 11]; + break; + case 4: + T = [16, 11]; + break; + case 5: + T = [40, 33]; + break; + case 6: + T = [24, 11]; + break; + case 7: + T = [20, 11]; + break; + case 8: + T = [32, 11]; + break; + case 9: + T = [80, 33]; + break; + case 10: + T = [18, 11]; + break; + case 11: + T = [15, 11]; + break; + case 12: + T = [64, 33]; + break; + case 13: + T = [160, 99]; + break; + case 14: + T = [4, 3]; + break; + case 15: + T = [3, 2]; + break; + case 16: + T = [2, 1]; + break; + case 255: + T = [c() << 8 | c(), c() << 8 | c()] + } + } + return { + width: Math.ceil(16 * (o + 1) - 2 * t - 2 * e), + height: (2 - l) * (s + 1) * 16 - (l ? 2 : 4) * (r + i), + pixelRatio: T + } + }, t.prototype.readSliceType = function() { + return this.readUByte(), this.readUEG(), this.readUEG() + }, t + }(); + e.a = n + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + var a = r(13), + n = function() { + function t(e, r, n, o) { + i(this, t), this.decryptdata = n, this.discardEPB = o, this.decrypter = new a.a(e, r, { + removePKCS7Padding: !1 + }) + } + return t.prototype.decryptBuffer = function(t, e) { + this.decrypter.decrypt(t, this.decryptdata.key.buffer, this.decryptdata.iv.buffer, e) + }, t.prototype.decryptAacSample = function(t, e, r, i) { + var a = t[e].unit, + n = a.subarray(16, a.length - a.length % 16), + o = n.buffer.slice(n.byteOffset, n.byteOffset + n.length), + s = this; + this.decryptBuffer(o, function(n) { + n = new Uint8Array(n), a.set(n, 16), i || s.decryptAacSamples(t, e + 1, r) + }) + }, t.prototype.decryptAacSamples = function(t, e, r) { + for (;; e++) { + if (e >= t.length) return void r(); + if (!(t[e].unit.length < 32)) { + var i = this.decrypter.isSync(); + if (this.decryptAacSample(t, e, r, i), !i) return + } + } + }, t.prototype.getAvcEncryptedData = function(t) { + for (var e = 16 * Math.floor((t.length - 48) / 160) + 16, r = new Int8Array(e), i = 0, a = 32; a <= t.length - 16; a += 160, i += 16) r.set(t.subarray(a, a + 16), i); + return r + }, t.prototype.getAvcDecryptedUnit = function(t, e) { + e = new Uint8Array(e); + for (var r = 0, i = 32; i <= t.length - 16; i += 160, r += 16) t.set(e.subarray(r, r + 16), i); + return t + }, t.prototype.decryptAvcSample = function(t, e, r, i, a, n) { + var o = this.discardEPB(a.data), + s = this.getAvcEncryptedData(o), + l = this; + this.decryptBuffer(s.buffer, function(s) { + a.data = l.getAvcDecryptedUnit(o, s), n || l.decryptAvcSamples(t, e, r + 1, i) + }) + }, t.prototype.decryptAvcSamples = function(t, e, r, i) { + for (;; e++, r = 0) { + if (e >= t.length) return void i(); + for (var a = t[e].units; !(r >= a.length); r++) { + var n = a[r]; + if (!(n.length <= 48 || 1 !== n.type && 5 !== n.type)) { + var o = this.decrypter.isSync(); + if (this.decryptAvcSample(t, e, r, i, n, o), !o) return + } + } + } + }, t + }(); + e.a = n + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + var a = r(7), + n = r(0), + o = r(23), + s = function() { + function t(e, r, a) { + i(this, t), this.observer = e, this.config = a, this.remuxer = r + } + return t.prototype.resetInitSegment = function(t, e, r, i) { + this._audioTrack = { + container: "audio/mpeg", + type: "audio", + id: -1, + sequenceNumber: 0, + isAAC: !1, + samples: [], + len: 0, + manifestCodec: e, + duration: i, + inputTimeScale: 9e4 + } + }, t.prototype.resetTimeStamp = function() {}, t.probe = function(t) { + var e = void 0, + r = void 0, + i = a.a.getID3Data(t, 0); + if (i && void 0 !== a.a.getTimeStamp(i)) + for (e = i.length, r = Math.min(t.length - 1, e + 100); e < r; e++) + if (o.a.probe(t, e)) return n.b.log("MPEG Audio sync word found !"), !0; + return !1 + }, t.prototype.append = function(t, e, r, i) { + for (var n = a.a.getID3Data(t, 0), s = a.a.getTimeStamp(n), l = s ? 90 * s : 9e4 * e, u = n.length, d = t.length, c = 0, h = 0, f = this._audioTrack, p = [{ + pts: l, + dts: l, + data: n + }]; u < d;) + if (o.a.isHeader(t, u)) { + var v = o.a.appendFrame(f, t, u, l, c); + if (!v) break; + u += v.length, h = v.sample.pts, c++ + } else a.a.isHeader(t, u) ? (n = a.a.getID3Data(t, u), p.push({ + pts: h, + dts: h, + data: n + }), u += n.length) : u++; + this.remuxer.remux(f, { + samples: [] + }, { + samples: p, + inputTimeScale: 9e4 + }, { + samples: [] + }, e, r, i) + }, t.prototype.destroy = function() {}, t + }(); + e.a = s + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + var a = r(44), + n = r(45), + o = r(1), + s = r(2), + l = r(0), + u = function() { + function t(e, r, a, n) { + i(this, t), this.observer = e, this.config = r, this.typeSupported = a; + var o = navigator.userAgent; + this.isSafari = n && n.indexOf("Apple") > -1 && o && !o.match("CriOS"), this.ISGenerated = !1 + } + return t.prototype.destroy = function() {}, t.prototype.resetTimeStamp = function(t) { + this._initPTS = this._initDTS = t + }, t.prototype.resetInitSegment = function() { + this.ISGenerated = !1 + }, t.prototype.remux = function(t, e, r, i, a, n, s) { + if (this.ISGenerated || this.generateIS(t, e, a), this.ISGenerated) { + var u = t.samples.length, + d = e.samples.length, + c = a, + h = a; + if (u && d) { + var f = (t.samples[0].dts - e.samples[0].dts) / e.inputTimeScale; + c += Math.max(0, f), h += Math.max(0, -f) + } + if (u) { + t.timescale || (l.b.warn("regenerate InitSegment as audio detected"), this.generateIS(t, e, a)); + var p = this.remuxAudio(t, c, n, s); + if (d) { + var v = void 0; + p && (v = p.endPTS - p.startPTS), e.timescale || (l.b.warn("regenerate InitSegment as video detected"), this.generateIS(t, e, a)), this.remuxVideo(e, h, n, v, s) + } + } else if (d) { + var g = this.remuxVideo(e, h, n, 0, s); + g && t.codec && this.remuxEmptyAudio(t, c, n, g) + } + } + r.samples.length && this.remuxID3(r, a), i.samples.length && this.remuxText(i, a), this.observer.trigger(o.a.FRAG_PARSED) + }, t.prototype.generateIS = function(t, e, r) { + var i = this.observer, + a = t.samples, + u = e.samples, + d = this.typeSupported, + c = "audio/mp4", + h = {}, + f = { + tracks: h + }, + p = void 0 === this._initPTS, + v = void 0, + g = void 0; + if (p && (v = g = 1 / 0), t.config && a.length && (t.timescale = t.samplerate, l.b.log("audio sampling rate : " + t.samplerate), t.isAAC || (d.mpeg ? (c = "audio/mpeg", t.codec = "") : d.mp3 && (t.codec = "mp3")), h.audio = { + container: c, + codec: t.codec, + initSegment: !t.isAAC && d.mpeg ? new Uint8Array : n.a.initSegment([t]), + metadata: { + channelCount: t.channelCount + } + }, p && (v = g = a[0].pts - t.inputTimeScale * r)), e.sps && e.pps && u.length) { + var y = e.inputTimeScale; + e.timescale = y, h.video = { + container: "video/mp4", + codec: e.codec, + initSegment: n.a.initSegment([e]), + metadata: { + width: e.width, + height: e.height + } + }, p && (v = Math.min(v, u[0].pts - y * r), g = Math.min(g, u[0].dts - y * r), this.observer.trigger(o.a.INIT_PTS_FOUND, { + initPTS: v + })) + } + Object.keys(h).length ? (i.trigger(o.a.FRAG_PARSING_INIT_SEGMENT, f), this.ISGenerated = !0, p && (this._initPTS = v, this._initDTS = g)) : i.trigger(o.a.ERROR, { + type: s.b.MEDIA_ERROR, + details: s.a.FRAG_PARSING_ERROR, + fatal: !1, + reason: "no audio/video samples found" + }) + }, t.prototype.remuxVideo = function(t, e, r, i, a) { + var u = 8, + d = t.timescale, + c = void 0, + h = void 0, + f = void 0, + p = void 0, + v = void 0, + g = void 0, + y = void 0, + m = t.samples, + b = [], + E = m.length, + T = this._PTSNormalize, + S = this._initDTS, + R = this.nextAvcDts, + A = this.isSafari; + if (0 !== E) { + A && (r |= m.length && R && (a && Math.abs(e - R / d) < .1 || Math.abs(m[0].pts - R - S) < d / 5)), r || (R = e * d), m.forEach(function(t) { + t.pts = T(t.pts - S, R), t.dts = T(t.dts - S, R) + }), m.sort(function(t, e) { + var r = t.dts - e.dts, + i = t.pts - e.pts; + return r || i || t.id - e.id + }); + var _ = m.reduce(function(t, e) { + return Math.max(Math.min(t, e.pts - e.dts), -18e3) + }, 0); + if (_ < 0) { + l.b.warn("PTS < DTS detected in video samples, shifting DTS by " + Math.round(_ / 90) + " ms to overcome this issue"); + for (var w = 0; w < m.length; w++) m[w].dts += _ + } + var L = m[0]; + v = Math.max(L.dts, 0), p = Math.max(L.pts, 0); + var D = Math.round((v - R) / 90); + r && D && (D > 1 ? l.b.log("AVC:" + D + " ms hole between fragments detected,filling it") : D < -1 && l.b.log("AVC:" + -D + " ms overlapping between fragments detected"), v = R, m[0].dts = v, p = Math.max(p - D, R), m[0].pts = p, l.b.log("Video/PTS/DTS adjusted: " + Math.round(p / 90) + "/" + Math.round(v / 90) + ",delta:" + D + " ms")), v, L = m[m.length - 1], y = Math.max(L.dts, 0), g = Math.max(L.pts, 0, y), A && (c = Math.round((y - v) / (m.length - 1))); + for (var I = 0, k = 0, O = 0; O < E; O++) { + for (var C = m[O], P = C.units, x = P.length, F = 0, N = 0; N < x; N++) F += P[N].data.length; + k += F, I += x, C.length = F, C.dts = A ? v + O * c : Math.max(C.dts, v), C.pts = Math.max(C.pts, C.dts) + } + var M = k + 4 * I + 8; + try { + h = new Uint8Array(M) + } catch (t) { + return void this.observer.trigger(o.a.ERROR, { + type: s.b.MUX_ERROR, + details: s.a.REMUX_ALLOC_ERROR, + fatal: !1, + bytes: M, + reason: "fail allocating video mdat " + M + }) + } + var U = new DataView(h.buffer); + U.setUint32(0, M), h.set(n.a.types.mdat, 4); + for (var B = 0; B < E; B++) { + for (var G = m[B], K = G.units, j = 0, H = void 0, V = 0, Y = K.length; V < Y; V++) { + var W = K[V], + q = W.data, + X = W.data.byteLength; + U.setUint32(u, X), u += 4, h.set(q, u), u += X, j += 4 + X + } + if (A) H = Math.max(0, c * Math.round((G.pts - G.dts) / c)); + else { + if (B < E - 1) c = m[B + 1].dts - G.dts; + else { + var z = this.config, + Q = G.dts - m[B > 0 ? B - 1 : B].dts; + if (z.stretchShortVideoTrack) { + var $ = z.maxBufferHole, + J = Math.floor($ * d), + Z = (i ? p + i * d : this.nextAudioPts) - G.pts; + Z > J ? (c = Z - Q, c < 0 && (c = Q), l.b.log("It is approximately " + Z / 90 + " ms to the next segment; using duration " + c / 90 + " ms for the last video frame.")) : c = Q + } else c = Q + } + H = Math.round(G.pts - G.dts) + } + b.push({ + size: j, + duration: c, + cts: H, + flags: { + isLeading: 0, + isDependedOn: 0, + hasRedundancy: 0, + degradPrio: 0, + dependsOn: G.key ? 2 : 1, + isNonSync: G.key ? 0 : 1 + } + }) + } + this.nextAvcDts = y + c; + var tt = t.dropped; + if (t.len = 0, t.nbNalu = 0, t.dropped = 0, b.length && navigator.userAgent.toLowerCase().indexOf("chrome") > -1) { + var et = b[0].flags; + et.dependsOn = 2, et.isNonSync = 0 + } + t.samples = b, f = n.a.moof(t.sequenceNumber++, v, t), t.samples = []; + var rt = { + data1: f, + data2: h, + startPTS: p / d, + endPTS: (g + c) / d, + startDTS: v / d, + endDTS: this.nextAvcDts / d, + type: "video", + hasAudio: !1, + hasVideo: !0, + nb: b.length, + dropped: tt + }; + return this.observer.trigger(o.a.FRAG_PARSING_DATA, rt), rt + } + }, t.prototype.remuxAudio = function(t, e, r, i) { + var u = t.inputTimeScale, + d = t.timescale, + c = u / d, + h = t.isAAC ? 1024 : 1152, + f = h * c, + p = this._PTSNormalize, + v = this._initDTS, + g = !t.isAAC && this.typeSupported.mpeg, + y = void 0, + m = void 0, + b = void 0, + E = void 0, + T = void 0, + S = void 0, + R = void 0, + A = t.samples, + _ = [], + w = this.nextAudioPts; + if (r |= A.length && w && (i && Math.abs(e - w / u) < .1 || Math.abs(A[0].pts - w - v) < 20 * f), A.forEach(function(t) { + t.pts = t.dts = p(t.pts - v, e * u) + }), A = A.filter(function(t) { + return t.pts >= 0 + }), 0 !== A.length) { + if (r || (w = i ? e * u : A[0].pts), t.isAAC) + for (var L = this.config.maxAudioFramesDrift, D = 0, I = w; D < A.length;) { + var k, O = A[D], + C = O.pts; + k = C - I; + var P = Math.abs(1e3 * k / u); + if (k <= -L * f) l.b.warn("Dropping 1 audio frame @ " + (I / u).toFixed(3) + "s due to " + Math.round(P) + " ms overlap."), A.splice(D, 1), t.len -= O.unit.length; + else if (k >= L * f && P < 1e4 && I) { + var x = Math.round(k / f); + l.b.warn("Injecting " + x + " audio frame @ " + (I / u).toFixed(3) + "s due to " + Math.round(1e3 * k / u) + " ms gap."); + for (var F = 0; F < x; F++) { + var N = Math.max(I, 0); + b = a.a.getSilentFrame(t.manifestCodec || t.codec, t.channelCount), b || (l.b.log("Unable to get silent frame for given audio codec; duplicating last frame instead."), b = O.unit.subarray()), A.splice(D, 0, { + unit: b, + pts: N, + dts: N + }), t.len += b.length, I += f, D++ + } + O.pts = O.dts = I, I += f, D++ + } else Math.abs(k), O.pts = O.dts = I, I += f, D++ + } + for (var M = 0, U = A.length; M < U; M++) { + var B = A[M], + G = B.unit, + K = B.pts; + if (void 0 !== R) m.duration = Math.round((K - R) / c); + else { + var j = Math.round(1e3 * (K - w) / u), + H = 0; + if (r && t.isAAC && j) { + if (j > 0 && j < 1e4) H = Math.round((K - w) / f), l.b.log(j + " ms hole between AAC samples detected,filling it"), H > 0 && (b = a.a.getSilentFrame(t.manifestCodec || t.codec, t.channelCount), b || (b = G.subarray()), t.len += H * b.length); + else if (j < -12) { + l.b.log("drop overlapping AAC sample, expected/parsed/delta:" + (w / u).toFixed(3) + "s/" + (K / u).toFixed(3) + "s/" + -j + "ms"), t.len -= G.byteLength; + continue + } + K = w + } + if (S = K, !(t.len > 0)) return; + var V = g ? t.len : t.len + 8; + y = g ? 0 : 8; + try { + E = new Uint8Array(V) + } catch (t) { + return void this.observer.trigger(o.a.ERROR, { + type: s.b.MUX_ERROR, + details: s.a.REMUX_ALLOC_ERROR, + fatal: !1, + bytes: V, + reason: "fail allocating audio mdat " + V + }) + } + if (!g) { + new DataView(E.buffer).setUint32(0, V), E.set(n.a.types.mdat, 4) + } + for (var Y = 0; Y < H; Y++) b = a.a.getSilentFrame(t.manifestCodec || t.codec, t.channelCount), b || (l.b.log("Unable to get silent frame for given audio codec; duplicating this frame instead."), b = G.subarray()), E.set(b, y), y += b.byteLength, m = { + size: b.byteLength, + cts: 0, + duration: 1024, + flags: { + isLeading: 0, + isDependedOn: 0, + hasRedundancy: 0, + degradPrio: 0, + dependsOn: 1 + } + }, _.push(m) + } + E.set(G, y); + var W = G.byteLength; + y += W, m = { + size: W, + cts: 0, + duration: 0, + flags: { + isLeading: 0, + isDependedOn: 0, + hasRedundancy: 0, + degradPrio: 0, + dependsOn: 1 + } + }, _.push(m), R = K + } + var q = 0, + X = _.length; + if (X >= 2 && (q = _[X - 2].duration, m.duration = q), X) { + this.nextAudioPts = w = R + c * q, t.len = 0, t.samples = _, T = g ? new Uint8Array : n.a.moof(t.sequenceNumber++, S / c, t), t.samples = []; + var z = S / u, + Q = w / u, + $ = { + data1: T, + data2: E, + startPTS: z, + endPTS: Q, + startDTS: z, + endDTS: Q, + type: "audio", + hasAudio: !0, + hasVideo: !1, + nb: X + }; + return this.observer.trigger(o.a.FRAG_PARSING_DATA, $), $ + } + return null + } + }, t.prototype.remuxEmptyAudio = function(t, e, r, i) { + var n = t.inputTimeScale, + o = t.samplerate ? t.samplerate : n, + s = n / o, + u = this.nextAudioPts, + d = (void 0 !== u ? u : i.startDTS * n) + this._initDTS, + c = i.endDTS * n + this._initDTS, + h = 1024 * s, + f = Math.ceil((c - d) / h), + p = a.a.getSilentFrame(t.manifestCodec || t.codec, t.channelCount); + if (l.b.warn("remux empty Audio"), !p) return void l.b.trace("Unable to remuxEmptyAudio since we were unable to get a silent frame for given audio codec!"); + for (var v = [], g = 0; g < f; g++) { + var y = d + g * h; + v.push({ + unit: p, + pts: y, + dts: y + }), t.len += p.length + } + t.samples = v, this.remuxAudio(t, e, r) + }, t.prototype.remuxID3 = function(t, e) { + var r = t.samples.length, + i = void 0, + a = t.inputTimeScale, + n = this._initPTS, + s = this._initDTS; + if (r) { + for (var l = 0; l < r; l++) i = t.samples[l], i.pts = (i.pts - n) / a, i.dts = (i.dts - s) / a; + this.observer.trigger(o.a.FRAG_PARSING_METADATA, { + samples: t.samples + }) + } + t.samples = [], e = e + }, t.prototype.remuxText = function(t, e) { + t.samples.sort(function(t, e) { + return t.pts - e.pts + }); + var r = t.samples.length, + i = void 0, + a = t.inputTimeScale, + n = this._initPTS; + if (r) { + for (var s = 0; s < r; s++) i = t.samples[s], i.pts = (i.pts - n) / a; + this.observer.trigger(o.a.FRAG_PARSING_USERDATA, { + samples: t.samples + }) + } + t.samples = [], e = e + }, t.prototype._PTSNormalize = function(t, e) { + var r = void 0; + if (void 0 === e) return t; + for (r = e < t ? -8589934592 : 8589934592; Math.abs(t - e) > 4294967296;) t += r; + return t + }, t + }(); + e.a = u + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + var a = function() { + function t() { + i(this, t) + } + return t.getSilentFrame = function(t, e) { + switch (t) { + case "mp4a.40.2": + if (1 === e) return new Uint8Array([0, 200, 0, 128, 35, 128]); + if (2 === e) return new Uint8Array([33, 0, 73, 144, 2, 25, 0, 35, 128]); + if (3 === e) return new Uint8Array([0, 200, 0, 128, 32, 132, 1, 38, 64, 8, 100, 0, 142]); + if (4 === e) return new Uint8Array([0, 200, 0, 128, 32, 132, 1, 38, 64, 8, 100, 0, 128, 44, 128, 8, 2, 56]); + if (5 === e) return new Uint8Array([0, 200, 0, 128, 32, 132, 1, 38, 64, 8, 100, 0, 130, 48, 4, 153, 0, 33, 144, 2, 56]); + if (6 === e) return new Uint8Array([0, 200, 0, 128, 32, 132, 1, 38, 64, 8, 100, 0, 130, 48, 4, 153, 0, 33, 144, 2, 0, 178, 0, 32, 8, 224]); + break; + default: + if (1 === e) return new Uint8Array([1, 64, 34, 128, 163, 78, 230, 128, 186, 8, 0, 0, 0, 28, 6, 241, 193, 10, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 94]); + if (2 === e) return new Uint8Array([1, 64, 34, 128, 163, 94, 230, 128, 186, 8, 0, 0, 0, 0, 149, 0, 6, 241, 161, 10, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 94]); + if (3 === e) return new Uint8Array([1, 64, 34, 128, 163, 94, 230, 128, 186, 8, 0, 0, 0, 0, 149, 0, 6, 241, 161, 10, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 94]) + } + return null + }, t + }(); + e.a = a + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + var a = Math.pow(2, 32) - 1, + n = function() { + function t() { + i(this, t) + } + return t.init = function() { + t.types = { + avc1: [], + avcC: [], + btrt: [], + dinf: [], + dref: [], + esds: [], + ftyp: [], + hdlr: [], + mdat: [], + mdhd: [], + mdia: [], + mfhd: [], + minf: [], + moof: [], + moov: [], + mp4a: [], + ".mp3": [], + mvex: [], + mvhd: [], + pasp: [], + sdtp: [], + stbl: [], + stco: [], + stsc: [], + stsd: [], + stsz: [], + stts: [], + tfdt: [], + tfhd: [], + traf: [], + trak: [], + trun: [], + trex: [], + tkhd: [], + vmhd: [], + smhd: [] + }; + var e = void 0; + for (e in t.types) t.types.hasOwnProperty(e) && (t.types[e] = [e.charCodeAt(0), e.charCodeAt(1), e.charCodeAt(2), e.charCodeAt(3)]); + var r = new Uint8Array([0, 0, 0, 0, 0, 0, 0, 0, 118, 105, 100, 101, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 86, 105, 100, 101, 111, 72, 97, 110, 100, 108, 101, 114, 0]), + i = new Uint8Array([0, 0, 0, 0, 0, 0, 0, 0, 115, 111, 117, 110, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 83, 111, 117, 110, 100, 72, 97, 110, 100, 108, 101, 114, 0]); + t.HDLR_TYPES = { + video: r, + audio: i + }; + var a = new Uint8Array([0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 12, 117, 114, 108, 32, 0, 0, 0, 1]), + n = new Uint8Array([0, 0, 0, 0, 0, 0, 0, 0]); + t.STTS = t.STSC = t.STCO = n, t.STSZ = new Uint8Array([0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0]), t.VMHD = new Uint8Array([0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0]), t.SMHD = new Uint8Array([0, 0, 0, 0, 0, 0, 0, 0]), t.STSD = new Uint8Array([0, 0, 0, 0, 0, 0, 0, 1]); + var o = new Uint8Array([105, 115, 111, 109]), + s = new Uint8Array([97, 118, 99, 49]), + l = new Uint8Array([0, 0, 0, 1]); + t.FTYP = t.box(t.types.ftyp, o, l, o, s), t.DINF = t.box(t.types.dinf, t.box(t.types.dref, a)) + }, t.box = function(t) { + for (var e = Array.prototype.slice.call(arguments, 1), r = 8, i = e.length, a = i, n = void 0; i--;) r += e[i].byteLength; + for (n = new Uint8Array(r), n[0] = r >> 24 & 255, n[1] = r >> 16 & 255, n[2] = r >> 8 & 255, n[3] = 255 & r, n.set(t, 4), i = 0, r = 8; i < a; i++) n.set(e[i], r), r += e[i].byteLength; + return n + }, t.hdlr = function(e) { + return t.box(t.types.hdlr, t.HDLR_TYPES[e]) + }, t.mdat = function(e) { + return t.box(t.types.mdat, e) + }, t.mdhd = function(e, r) { + r *= e; + var i = Math.floor(r / (a + 1)), + n = Math.floor(r % (a + 1)); + return t.box(t.types.mdhd, new Uint8Array([1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 2, 0, 0, 0, 0, 0, 0, 0, 3, e >> 24 & 255, e >> 16 & 255, e >> 8 & 255, 255 & e, i >> 24, i >> 16 & 255, i >> 8 & 255, 255 & i, n >> 24, n >> 16 & 255, n >> 8 & 255, 255 & n, 85, 196, 0, 0])) + }, t.mdia = function(e) { + return t.box(t.types.mdia, t.mdhd(e.timescale, e.duration), t.hdlr(e.type), t.minf(e)) + }, t.mfhd = function(e) { + return t.box(t.types.mfhd, new Uint8Array([0, 0, 0, 0, e >> 24, e >> 16 & 255, e >> 8 & 255, 255 & e])) + }, t.minf = function(e) { + return "audio" === e.type ? t.box(t.types.minf, t.box(t.types.smhd, t.SMHD), t.DINF, t.stbl(e)) : t.box(t.types.minf, t.box(t.types.vmhd, t.VMHD), t.DINF, t.stbl(e)) + }, t.moof = function(e, r, i) { + return t.box(t.types.moof, t.mfhd(e), t.traf(i, r)) + }, t.moov = function(e) { + for (var r = e.length, i = []; r--;) i[r] = t.trak(e[r]); + return t.box.apply(null, [t.types.moov, t.mvhd(e[0].timescale, e[0].duration)].concat(i).concat(t.mvex(e))) + }, t.mvex = function(e) { + for (var r = e.length, i = []; r--;) i[r] = t.trex(e[r]); + return t.box.apply(null, [t.types.mvex].concat(i)) + }, t.mvhd = function(e, r) { + r *= e; + var i = Math.floor(r / (a + 1)), + n = Math.floor(r % (a + 1)), + o = new Uint8Array([1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 2, 0, 0, 0, 0, 0, 0, 0, 3, e >> 24 & 255, e >> 16 & 255, e >> 8 & 255, 255 & e, i >> 24, i >> 16 & 255, i >> 8 & 255, 255 & i, n >> 24, n >> 16 & 255, n >> 8 & 255, 255 & n, 0, 1, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 64, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 255, 255, 255, 255]); + return t.box(t.types.mvhd, o) + }, t.sdtp = function(e) { + var r = e.samples || [], + i = new Uint8Array(4 + r.length), + a = void 0, + n = void 0; + for (n = 0; n < r.length; n++) a = r[n].flags, i[n + 4] = a.dependsOn << 4 | a.isDependedOn << 2 | a.hasRedundancy; + return t.box(t.types.sdtp, i) + }, t.stbl = function(e) { + return t.box(t.types.stbl, t.stsd(e), t.box(t.types.stts, t.STTS), t.box(t.types.stsc, t.STSC), t.box(t.types.stsz, t.STSZ), t.box(t.types.stco, t.STCO)) + }, t.avc1 = function(e) { + var r = [], + i = [], + a = void 0, + n = void 0, + o = void 0; + for (a = 0; a < e.sps.length; a++) n = e.sps[a], o = n.byteLength, r.push(o >>> 8 & 255), r.push(255 & o), r = r.concat(Array.prototype.slice.call(n)); + for (a = 0; a < e.pps.length; a++) n = e.pps[a], o = n.byteLength, i.push(o >>> 8 & 255), i.push(255 & o), i = i.concat(Array.prototype.slice.call(n)); + var s = t.box(t.types.avcC, new Uint8Array([1, r[3], r[4], r[5], 255, 224 | e.sps.length].concat(r).concat([e.pps.length]).concat(i))), + l = e.width, + u = e.height, + d = e.pixelRatio[0], + c = e.pixelRatio[1]; + return t.box(t.types.avc1, new Uint8Array([0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, l >> 8 & 255, 255 & l, u >> 8 & 255, 255 & u, 0, 72, 0, 0, 0, 72, 0, 0, 0, 0, 0, 0, 0, 1, 18, 100, 97, 105, 108, 121, 109, 111, 116, 105, 111, 110, 47, 104, 108, 115, 46, 106, 115, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 24, 17, 17]), s, t.box(t.types.btrt, new Uint8Array([0, 28, 156, 128, 0, 45, 198, 192, 0, 45, 198, 192])), t.box(t.types.pasp, new Uint8Array([d >> 24, d >> 16 & 255, d >> 8 & 255, 255 & d, c >> 24, c >> 16 & 255, c >> 8 & 255, 255 & c]))) + }, t.esds = function(t) { + var e = t.config.length; + return new Uint8Array([0, 0, 0, 0, 3, 23 + e, 0, 1, 0, 4, 15 + e, 64, 21, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5].concat([e]).concat(t.config).concat([6, 1, 2])) + }, t.mp4a = function(e) { + var r = e.samplerate; + return t.box(t.types.mp4a, new Uint8Array([0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, e.channelCount, 0, 16, 0, 0, 0, 0, r >> 8 & 255, 255 & r, 0, 0]), t.box(t.types.esds, t.esds(e))) + }, t.mp3 = function(e) { + var r = e.samplerate; + return t.box(t.types[".mp3"], new Uint8Array([0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, e.channelCount, 0, 16, 0, 0, 0, 0, r >> 8 & 255, 255 & r, 0, 0])) + }, t.stsd = function(e) { + return "audio" === e.type ? e.isAAC || "mp3" !== e.codec ? t.box(t.types.stsd, t.STSD, t.mp4a(e)) : t.box(t.types.stsd, t.STSD, t.mp3(e)) : t.box(t.types.stsd, t.STSD, t.avc1(e)) + }, t.tkhd = function(e) { + var r = e.id, + i = e.duration * e.timescale, + n = e.width, + o = e.height, + s = Math.floor(i / (a + 1)), + l = Math.floor(i % (a + 1)); + return t.box(t.types.tkhd, new Uint8Array([1, 0, 0, 7, 0, 0, 0, 0, 0, 0, 0, 2, 0, 0, 0, 0, 0, 0, 0, 3, r >> 24 & 255, r >> 16 & 255, r >> 8 & 255, 255 & r, 0, 0, 0, 0, s >> 24, s >> 16 & 255, s >> 8 & 255, 255 & s, l >> 24, l >> 16 & 255, l >> 8 & 255, 255 & l, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 64, 0, 0, 0, n >> 8 & 255, 255 & n, 0, 0, o >> 8 & 255, 255 & o, 0, 0])) + }, t.traf = function(e, r) { + var i = t.sdtp(e), + n = e.id, + o = Math.floor(r / (a + 1)), + s = Math.floor(r % (a + 1)); + return t.box(t.types.traf, t.box(t.types.tfhd, new Uint8Array([0, 0, 0, 0, n >> 24, n >> 16 & 255, n >> 8 & 255, 255 & n])), t.box(t.types.tfdt, new Uint8Array([1, 0, 0, 0, o >> 24, o >> 16 & 255, o >> 8 & 255, 255 & o, s >> 24, s >> 16 & 255, s >> 8 & 255, 255 & s])), t.trun(e, i.length + 16 + 20 + 8 + 16 + 8 + 8), i) + }, t.trak = function(e) { + return e.duration = e.duration || 4294967295, t.box(t.types.trak, t.tkhd(e), t.mdia(e)) + }, t.trex = function(e) { + var r = e.id; + return t.box(t.types.trex, new Uint8Array([0, 0, 0, 0, r >> 24, r >> 16 & 255, r >> 8 & 255, 255 & r, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1])) + }, t.trun = function(e, r) { + var i = e.samples || [], + a = i.length, + n = 12 + 16 * a, + o = new Uint8Array(n), + s = void 0, + l = void 0, + u = void 0, + d = void 0, + c = void 0, + h = void 0; + for (r += 8 + n, o.set([0, 0, 15, 1, a >>> 24 & 255, a >>> 16 & 255, a >>> 8 & 255, 255 & a, r >>> 24 & 255, r >>> 16 & 255, r >>> 8 & 255, 255 & r], 0), s = 0; s < a; s++) l = i[s], u = l.duration, d = l.size, c = l.flags, h = l.cts, o.set([u >>> 24 & 255, u >>> 16 & 255, u >>> 8 & 255, 255 & u, d >>> 24 & 255, d >>> 16 & 255, d >>> 8 & 255, 255 & d, c.isLeading << 2 | c.dependsOn, c.isDependedOn << 6 | c.hasRedundancy << 4 | c.paddingValue << 1 | c.isNonSync, 61440 & c.degradPrio, 15 & c.degradPrio, h >>> 24 & 255, h >>> 16 & 255, h >>> 8 & 255, 255 & h], 12 + 16 * s); + return t.box(t.types.trun, o) + }, t.initSegment = function(e) { + t.types || t.init(); + var r = t.moov(e), + i = void 0; + return i = new Uint8Array(t.FTYP.byteLength + r.byteLength), i.set(t.FTYP), i.set(r, t.FTYP.byteLength), i + }, t + }(); + e.a = n + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + var a = r(1), + n = function() { + function t(e) { + i(this, t), this.observer = e + } + return t.prototype.destroy = function() {}, t.prototype.resetTimeStamp = function() {}, t.prototype.resetInitSegment = function() {}, t.prototype.remux = function(t, e, r, i, n, o, s, l) { + var u = this.observer, + d = ""; + t && (d += "audio"), e && (d += "video"), u.trigger(a.a.FRAG_PARSING_DATA, { + data1: l, + startPTS: n, + startDTS: n, + type: d, + hasAudio: !!t, + hasVideo: !!e, + nb: 1, + dropped: 0 + }), u.trigger(a.a.FRAG_PARSED) + }, t + }(); + e.a = n + }, function(t, e, r) { + "use strict"; + Object.defineProperty(e, "__esModule", { + value: !0 + }); + var i = r(21), + a = r(1), + n = r(0), + o = r(12), + s = r.n(o), + l = function(t) { + var e = new s.a; + e.trigger = function(t) { + for (var r = arguments.length, i = Array(r > 1 ? r - 1 : 0), a = 1; a < r; a++) i[a - 1] = arguments[a]; + e.emit.apply(e, [t, t].concat(i)) + }, e.off = function(t) { + for (var r = arguments.length, i = Array(r > 1 ? r - 1 : 0), a = 1; a < r; a++) i[a - 1] = arguments[a]; + e.removeListener.apply(e, [t].concat(i)) + }; + var r = function(e, r) { + t.postMessage({ + event: e, + data: r + }) + }; + t.addEventListener("message", function(a) { + var o = a.data; + switch (o.cmd) { + case "init": + var s = JSON.parse(o.config); + t.demuxer = new i.a(e, o.typeSupported, s, o.vendor); + try { + Object(n.a)(!0 === s.debug) + } catch (t) { + console.warn("demuxerWorker: unable to enable logs") + } + r("init", null); + break; + case "demux": + t.demuxer.push(o.data, o.decryptdata, o.initSegment, o.audioCodec, o.videoCodec, o.timeOffset, o.discontinuity, o.trackSwitch, o.contiguous, o.duration, o.accurateTimeOffset, o.defaultInitPTS) + } + }), e.on(a.a.FRAG_DECRYPTED, r), e.on(a.a.FRAG_PARSING_INIT_SEGMENT, r), e.on(a.a.FRAG_PARSED, r), e.on(a.a.ERROR, r), e.on(a.a.FRAG_PARSING_METADATA, r), e.on(a.a.FRAG_PARSING_USERDATA, r), e.on(a.a.INIT_PTS_FOUND, r), e.on(a.a.FRAG_PARSING_DATA, function(e, r) { + var i = [], + a = { + event: e, + data: r + }; + r.data1 && (a.data1 = r.data1.buffer, i.push(r.data1.buffer), delete r.data1), r.data2 && (a.data2 = r.data2.buffer, i.push(r.data2.buffer), delete r.data2), t.postMessage(a, i) + }) + }; + e.default = l + }, function(t, e, r) { + "use strict"; + + function i() { + var t = arguments.length > 0 && void 0 !== arguments[0] ? arguments[0] : 0, + e = arguments.length > 1 && void 0 !== arguments[1] ? arguments[1] : 0, + r = arguments[2], + i = 0; + if (r.programDateTime) { + var a = Date.parse(r.programDateTime); + isNaN(a) || (i = 1e3 * e + a - 1e3 * t) + } + return i + } + + function a(t) { + var e = arguments.length > 1 && void 0 !== arguments[1] ? arguments[1] : null; + if (!Array.isArray(t) || !t.length || null === e) return null; + if (e < t[0].pdt) return null; + if (e >= t[t.length - 1].endPdt) return null; + for (var r = 0; r < t.length; ++r) { + var i = t[r]; + if (e < i.endPdt) return i + } + return null + } + + function n(t, e) { + var r = arguments.length > 2 && void 0 !== arguments[2] ? arguments[2] : 0, + i = arguments.length > 3 && void 0 !== arguments[3] ? arguments[3] : 0, + a = arguments.length > 4 && void 0 !== arguments[4] ? arguments[4] : 0, + n = void 0, + l = t ? e[t.sn - e[0].sn + 1] : null; + return r < i && (r > i - a && (a = 0), n = l && !o(r, a, l) ? l : s.a.search(e, o.bind(null, r, a))), n + } + + function o() { + var t = arguments.length > 0 && void 0 !== arguments[0] ? arguments[0] : 0, + e = arguments.length > 1 && void 0 !== arguments[1] ? arguments[1] : 0, + r = arguments[2], + i = Math.min(e, r.duration + (r.deltaPTS ? r.deltaPTS : 0)); + return r.start + r.duration - i <= t ? 1 : r.start - i > t && r.start ? -1 : 0 + } + e.a = i, e.b = a, e.c = n, e.d = o; + var s = r(6) + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + + function a(t, e) { + if (!t) throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); + return !e || "object" != typeof e && "function" != typeof e ? t : e + } + + function n(t, e) { + if ("function" != typeof e && null !== e) throw new TypeError("Super expression must either be null or a function, not " + typeof e); + t.prototype = Object.create(e && e.prototype, { + constructor: { + value: t, + enumerable: !1, + writable: !0, + configurable: !0 + } + }), e && (Object.setPrototypeOf ? Object.setPrototypeOf(t, e) : t.__proto__ = e) + } + var o = r(1), + s = r(3), + l = r(0), + u = r(2), + d = r(19), + c = r(15), + h = "function" == typeof Symbol && "symbol" == typeof Symbol.iterator ? function(t) { + return typeof t + } : function(t) { + return t && "function" == typeof Symbol && t.constructor === Symbol && t !== Symbol.prototype ? "symbol" : typeof t + }, + f = function() { + function t(t, e) { + for (var r = 0; r < e.length; r++) { + var i = e[r]; + i.enumerable = i.enumerable || !1, i.configurable = !0, "value" in i && (i.writable = !0), Object.defineProperty(t, i.key, i) + } + } + return function(e, r, i) { + return r && t(e.prototype, r), i && t(e, i), e + } + }(), + p = window, + v = p.performance, + g = function(t) { + function e(r) { + i(this, e); + var n = a(this, t.call(this, r, o.a.MANIFEST_LOADED, o.a.LEVEL_LOADED, o.a.AUDIO_TRACK_SWITCHED, o.a.FRAG_LOADED, o.a.ERROR)); + return n.canload = !1, n.currentLevelIndex = null, n.manualLevelIndex = -1, n.timer = null, n + } + return n(e, t), e.prototype.onHandlerDestroying = function() { + this.clearTimer(), this.manualLevelIndex = -1 + }, e.prototype.clearTimer = function() { + null !== this.timer && (clearTimeout(this.timer), this.timer = null) + }, e.prototype.startLoad = function() { + var t = this._levels; + this.canload = !0, this.levelRetryCount = 0, t && t.forEach(function(t) { + t.loadError = 0; + var e = t.details; + e && e.live && (t.details = void 0) + }), null !== this.timer && this.loadLevel() + }, e.prototype.stopLoad = function() { + this.canload = !1 + }, e.prototype.onManifestLoaded = function(t) { + var e = [], + r = void 0, + i = {}, + a = null, + n = !1, + s = !1, + h = /chrome|firefox/.test(navigator.userAgent.toLowerCase()), + f = []; + if (t.levels.forEach(function(t) { + t.loadError = 0, t.fragmentError = !1, n = n || !!t.videoCodec, s = s || !!t.audioCodec || !(!t.attrs || !t.attrs.AUDIO), h && t.audioCodec && -1 !== t.audioCodec.indexOf("mp4a.40.34") && (t.audioCodec = void 0), a = i[t.bitrate], a ? a.url.push(t.url) : (t.url = [t.url], t.urlId = 0, i[t.bitrate] = t, e.push(t)), t.attrs && t.attrs.AUDIO && Object(c.a)(a || t, "audio", t.attrs.AUDIO), t.attrs && t.attrs.SUBTITLES && Object(c.a)(a || t, "text", t.attrs.SUBTITLES) + }), n && s && (e = e.filter(function(t) { + return !!t.videoCodec + })), e = e.filter(function(t) { + var e = t.audioCodec, + r = t.videoCodec; + return (!e || Object(d.a)(e)) && (!r || Object(d.a)(r)) + }), t.audioTracks && (f = t.audioTracks.filter(function(t) { + return !t.audioCodec || Object(d.a)(t.audioCodec, "audio") + })), e.length > 0) { + r = e[0].bitrate, e.sort(function(t, e) { + return t.bitrate - e.bitrate + }), this._levels = e; + for (var p = 0; p < e.length; p++) + if (e[p].bitrate === r) { + this._firstLevel = p, l.b.log("manifest loaded," + e.length + " level(s) found, first bitrate:" + r); + break + } this.hls.trigger(o.a.MANIFEST_PARSED, { + levels: e, + audioTracks: f, + firstLevel: this._firstLevel, + stats: t.stats, + audio: s, + video: n, + altAudio: f.length > 0 && n + }) + } else this.hls.trigger(o.a.ERROR, { + type: u.b.MEDIA_ERROR, + details: u.a.MANIFEST_INCOMPATIBLE_CODECS_ERROR, + fatal: !0, + url: this.hls.url, + reason: "no level with compatible codecs found in manifest" + }) + }, e.prototype.setLevelInternal = function(t) { + var e = this._levels, + r = this.hls; + if (t >= 0 && t < e.length) { + if (this.clearTimer(), this.currentLevelIndex !== t) { + l.b.log("switching to level " + t), this.currentLevelIndex = t; + var i = e[t]; + i.level = t, r.trigger(o.a.LEVEL_SWITCHING, i) + } + var a = e[t], + n = a.details; + if (!n || n.live) { + var s = a.urlId; + r.trigger(o.a.LEVEL_LOADING, { + url: a.url[s], + level: t, + id: s + }) + } + } else r.trigger(o.a.ERROR, { + type: u.b.OTHER_ERROR, + details: u.a.LEVEL_SWITCH_ERROR, + level: t, + fatal: !1, + reason: "invalid level idx" + }) + }, e.prototype.onError = function(t) { + if (t.fatal) return void(t.type === u.b.NETWORK_ERROR && this.clearTimer()); + var e = !1, + r = !1, + i = void 0; + switch (t.details) { + case u.a.FRAG_LOAD_ERROR: + case u.a.FRAG_LOAD_TIMEOUT: + case u.a.KEY_LOAD_ERROR: + case u.a.KEY_LOAD_TIMEOUT: + i = t.frag.level, r = !0; + break; + case u.a.LEVEL_LOAD_ERROR: + case u.a.LEVEL_LOAD_TIMEOUT: + i = t.context.level, e = !0; + break; + case u.a.REMUX_ALLOC_ERROR: + i = t.level, e = !0 + } + void 0 !== i && this.recoverLevel(t, i, e, r) + }, e.prototype.recoverLevel = function(t, e, r, i) { + var a = this, + n = this.hls.config, + o = t.details, + s = this._levels[e], + u = void 0, + d = void 0, + c = void 0; + if (s.loadError++, s.fragmentError = i, r) { + if (!(this.levelRetryCount + 1 <= n.levelLoadingMaxRetry)) return l.b.error("level controller, cannot recover from " + o + " error"), this.currentLevelIndex = null, this.clearTimer(), void(t.fatal = !0); + d = Math.min(Math.pow(2, this.levelRetryCount) * n.levelLoadingRetryDelay, n.levelLoadingMaxRetryTimeout), this.timer = setTimeout(function() { + return a.loadLevel() + }, d), t.levelRetry = !0, this.levelRetryCount++, l.b.warn("level controller, " + o + ", retry in " + d + " ms, current retry count is " + this.levelRetryCount) + }(r || i) && (u = s.url.length, u > 1 && s.loadError < u ? (s.urlId = (s.urlId + 1) % u, s.details = void 0, l.b.warn("level controller, " + o + " for level " + e + ": switching to redundant URL-id " + s.urlId)) : -1 === this.manualLevelIndex ? (c = 0 === e ? this._levels.length - 1 : e - 1, l.b.warn("level controller, " + o + ": switch to " + c), this.hls.nextAutoLevel = this.currentLevelIndex = c) : i && (l.b.warn("level controller, " + o + ": reload a fragment"), this.currentLevelIndex = null)) + }, e.prototype.onFragLoaded = function(t) { + var e = t.frag; + if (void 0 !== e && "main" === e.type) { + var r = this._levels[e.level]; + void 0 !== r && (r.fragmentError = !1, r.loadError = 0, this.levelRetryCount = 0) + } + }, e.prototype.onLevelLoaded = function(t) { + var e = this, + r = t.level; + if (r === this.currentLevelIndex) { + var i = this._levels[r]; + i.fragmentError || (i.loadError = 0, this.levelRetryCount = 0); + var a = t.details; + if (a.live) { + var n = 1e3 * (a.averagetargetduration ? a.averagetargetduration : a.targetduration), + o = n, + s = i.details; + s && a.endSN === s.endSN && (o /= 2, l.b.log("same live playlist, reload twice faster")), o -= v.now() - t.stats.trequest, o = Math.max(n / 2, Math.round(o)), l.b.log("live playlist, reload in " + Math.round(o) + " ms"), this.timer = setTimeout(function() { + return e.loadLevel() + }, o) + } else this.clearTimer() + } + }, e.prototype.onAudioTrackSwitched = function(t) { + var e = this.hls.audioTracks[t.id].groupId, + r = this.hls.levels[this.currentLevelIndex]; + if (r && r.audioGroupIds) { + var i = r.audioGroupIds.findIndex(function(t) { + return t === e + }); + i !== r.urlId && (r.urlId = i, this.startLoad()) + } + }, e.prototype.loadLevel = function() { + if (l.b.debug("call to loadLevel"), null !== this.currentLevelIndex && this.canload) { + var t = this._levels[this.currentLevelIndex]; + if ("object" === (void 0 === t ? "undefined" : h(t)) && t.url.length > 0) { + var e = this.currentLevelIndex, + r = t.urlId, + i = t.url[r]; + l.b.log("Attempt loading level index " + e + " with URL-id " + r), this.hls.trigger(o.a.LEVEL_LOADING, { + url: i, + level: e, + id: r + }) + } + } + }, f(e, [{ + key: "levels", + get: function() { + return this._levels + } + }, { + key: "level", + get: function() { + return this.currentLevelIndex + }, + set: function(t) { + var e = this._levels; + e && (t = Math.min(t, e.length - 1), this.currentLevelIndex === t && e[t].details || this.setLevelInternal(t)) + } + }, { + key: "manualLevel", + get: function() { + return this.manualLevelIndex + }, + set: function(t) { + this.manualLevelIndex = t, void 0 === this._startLevel && (this._startLevel = t), -1 !== t && (this.level = t) + } + }, { + key: "firstLevel", + get: function() { + return this._firstLevel + }, + set: function(t) { + this._firstLevel = t + } + }, { + key: "startLevel", + get: function() { + if (void 0 === this._startLevel) { + var t = this.hls.config.startLevel; + return void 0 !== t ? t : this._firstLevel + } + return this._startLevel + }, + set: function(t) { + this._startLevel = t + } + }, { + key: "nextLoadLevel", + get: function() { + return -1 !== this.manualLevelIndex ? this.manualLevelIndex : this.hls.nextAutoLevel + }, + set: function(t) { + this.level = t, -1 === this.manualLevelIndex && (this.hls.nextAutoLevel = t) + } + }]), e + }(s.a); + e.a = g + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + + function a(t, e) { + if (!t) throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); + return !e || "object" != typeof e && "function" != typeof e ? t : e + } + + function n(t, e) { + if ("function" != typeof e && null !== e) throw new TypeError("Super expression must either be null or a function, not " + typeof e); + t.prototype = Object.create(e && e.prototype, { + constructor: { + value: t, + enumerable: !1, + writable: !0, + configurable: !0 + } + }), e && (Object.setPrototypeOf ? Object.setPrototypeOf(t, e) : t.__proto__ = e) + } + var o = r(1), + s = r(3), + l = r(7), + u = r(26), + d = function(t) { + function e(r) { + i(this, e); + var n = a(this, t.call(this, r, o.a.MEDIA_ATTACHED, o.a.MEDIA_DETACHING, o.a.FRAG_PARSING_METADATA)); + return n.id3Track = void 0, n.media = void 0, n + } + return n(e, t), e.prototype.destroy = function() { + s.a.prototype.destroy.call(this) + }, e.prototype.onMediaAttached = function(t) { + this.media = t.media, this.media + }, e.prototype.onMediaDetaching = function() { + Object(u.a)(this.id3Track), this.id3Track = void 0, this.media = void 0 + }, e.prototype.getID3Track = function(t) { + for (var e = 0; e < t.length; e++) { + var r = t[e]; + if ("metadata" === r.kind && "id3" === r.label) return Object(u.b)(r, this.media), r + } + return this.media.addTextTrack("metadata", "id3") + }, e.prototype.onFragParsingMetadata = function(t) { + var e = t.frag, + r = t.samples; + this.id3Track || (this.id3Track = this.getID3Track(this.media.textTracks), this.id3Track.mode = "hidden"); + for (var i = window.WebKitDataCue || window.VTTCue || window.TextTrackCue, a = 0; a < r.length; a++) { + var n = l.a.getID3Frames(r[a].data); + if (n) { + var o = r[a].pts, + s = a < r.length - 1 ? r[a + 1].pts : e.endPTS; + o === s && (s += 1e-4); + for (var u = 0; u < n.length; u++) { + var d = n[u]; + if (!l.a.isTimeStampFrame(d)) { + var c = new i(o, s, ""); + c.value = d, this.id3Track.addCue(c) + } + } + } + } + }, e + }(s.a); + e.a = d + }, function(t, e, r) { + "use strict"; + + function i() { + var t = Object(a.a)(), + e = window.SourceBuffer || window.WebKitSourceBuffer, + r = t && "function" == typeof t.isTypeSupported && t.isTypeSupported('video/mp4; codecs="avc1.42E01E,mp4a.40.2"'), + i = !e || e.prototype && "function" == typeof e.prototype.appendBuffer && "function" == typeof e.prototype.remove; + return !!r && !!i + } + e.a = i; + var a = r(14) + }, function(t, e, r) { + "use strict"; + r.d(e, "a", function() { + return g + }); + var i = r(53), + a = r(56), + n = r(57), + o = r(58), + s = r(59), + l = r(60), + u = r(61), + d = r(62), + c = r(64), + h = r(68), + f = r(69), + p = r(70), + v = r(71), + g = { + autoStartLoad: !0, + startPosition: -1, + defaultAudioCodec: void 0, + debug: !1, + capLevelOnFPSDrop: !1, + capLevelToPlayerSize: !1, + initialLiveManifestSize: 1, + maxBufferLength: 30, + maxBufferSize: 6e7, + maxBufferHole: .5, + lowBufferWatchdogPeriod: .5, + highBufferWatchdogPeriod: 3, + nudgeOffset: .1, + nudgeMaxRetry: 3, + maxFragLookUpTolerance: .25, + liveSyncDurationCount: 3, + liveMaxLatencyDurationCount: 1 / 0, + liveSyncDuration: void 0, + liveMaxLatencyDuration: void 0, + liveDurationInfinity: !1, + maxMaxBufferLength: 600, + enableWorker: !0, + enableSoftwareAES: !0, + manifestLoadingTimeOut: 1e4, + manifestLoadingMaxRetry: 1, + manifestLoadingRetryDelay: 1e3, + manifestLoadingMaxRetryTimeout: 64e3, + startLevel: void 0, + levelLoadingTimeOut: 1e4, + levelLoadingMaxRetry: 4, + levelLoadingRetryDelay: 1e3, + levelLoadingMaxRetryTimeout: 64e3, + fragLoadingTimeOut: 2e4, + fragLoadingMaxRetry: 6, + fragLoadingRetryDelay: 1e3, + fragLoadingMaxRetryTimeout: 64e3, + startFragPrefetch: !1, + fpsDroppedMonitoringPeriod: 5e3, + fpsDroppedMonitoringThreshold: .2, + appendErrorMaxRetry: 3, + loader: s.a, + fLoader: void 0, + pLoader: void 0, + xhrSetup: void 0, + licenseXhrSetup: void 0, + abrController: i.a, + bufferController: a.a, + capLevelController: n.a, + fpsController: o.a, + stretchShortVideoTrack: !1, + maxAudioFramesDrift: 1, + forceKeyFrameOnDiscontinuity: !0, + abrEwmaFastLive: 3, + abrEwmaSlowLive: 9, + abrEwmaFastVoD: 3, + abrEwmaSlowVoD: 9, + abrEwmaDefaultEstimate: 5e5, + abrBandWidthFactor: .95, + abrBandWidthUpFactor: .7, + abrMaxWithRealBitrate: !1, + maxStarvationDelay: 4, + maxLoadingDelay: 4, + minAutoBitrate: 0, + emeEnabled: !1, + widevineLicenseUrl: void 0, + requestMediaKeySystemAccessFunc: v.a + }; + g.subtitleStreamController = f.a, g.subtitleTrackController = h.a, g.timelineController = c.a, g.cueHandler = d, g.enableCEA708Captions = !0, g.enableWebVTT = !0, g.captionsTextTrack1Label = "English", g.captionsTextTrack1LanguageCode = "en", g.captionsTextTrack2Label = "Spanish", g.captionsTextTrack2LanguageCode = "es", g.audioStreamController = u.a, g.audioTrackController = l.a, g.emeController = p.a + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + + function a(t, e) { + if (!t) throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); + return !e || "object" != typeof e && "function" != typeof e ? t : e + } + + function n(t, e) { + if ("function" != typeof e && null !== e) throw new TypeError("Super expression must either be null or a function, not " + typeof e); + t.prototype = Object.create(e && e.prototype, { + constructor: { + value: t, + enumerable: !1, + writable: !0, + configurable: !0 + } + }), e && (Object.setPrototypeOf ? Object.setPrototypeOf(t, e) : t.__proto__ = e) + } + var o = r(1), + s = r(3), + l = r(11), + u = r(2), + d = r(0), + c = r(54), + h = function() { + function t(t, e) { + for (var r = 0; r < e.length; r++) { + var i = e[r]; + i.enumerable = i.enumerable || !1, i.configurable = !0, "value" in i && (i.writable = !0), Object.defineProperty(t, i.key, i) + } + } + return function(e, r, i) { + return r && t(e.prototype, r), i && t(e, i), e + } + }(), + f = window, + p = f.performance, + v = function(t) { + function e(r) { + i(this, e); + var n = a(this, t.call(this, r, o.a.FRAG_LOADING, o.a.FRAG_LOADED, o.a.FRAG_BUFFERED, o.a.ERROR)); + return n.lastLoadedFragLevel = 0, n._nextAutoLevel = -1, n.hls = r, n.timer = null, n._bwEstimator = null, n.onCheck = n._abandonRulesCheck.bind(n), n + } + return n(e, t), e.prototype.destroy = function() { + this.clearTimer(), s.a.prototype.destroy.call(this) + }, e.prototype.onFragLoading = function(t) { + var e = t.frag; + if ("main" === e.type && (this.timer || (this.fragCurrent = e, this.timer = setInterval(this.onCheck, 100)), !this._bwEstimator)) { + var r = this.hls, + i = r.config, + a = e.level, + n = r.levels[a].details.live, + o = void 0, + s = void 0; + n ? (o = i.abrEwmaFastLive, s = i.abrEwmaSlowLive) : (o = i.abrEwmaFastVoD, s = i.abrEwmaSlowVoD), this._bwEstimator = new c.a(r, s, o, i.abrEwmaDefaultEstimate) + } + }, e.prototype._abandonRulesCheck = function() { + var t = this.hls, + e = t.media, + r = this.fragCurrent; + if (r) { + var i = r.loader, + a = t.minAutoLevel; + if (!i || i.stats && i.stats.aborted) return d.b.warn("frag loader destroy or aborted, disarm abandonRules"), this.clearTimer(), void(this._nextAutoLevel = -1); + var n = i.stats; + if (e && n && (!e.paused && 0 !== e.playbackRate || !e.readyState) && r.autoLevel && r.level) { + var s = p.now() - n.trequest, + u = Math.abs(e.playbackRate); + if (s > 500 * r.duration / u) { + var c = t.levels, + h = Math.max(1, n.bw ? n.bw / 8 : 1e3 * n.loaded / s), + f = c[r.level], + v = f.realBitrate ? Math.max(f.realBitrate, f.bitrate) : f.bitrate, + g = n.total ? n.total : Math.max(n.loaded, Math.round(r.duration * v / 8)), + y = e.currentTime, + m = (g - n.loaded) / h, + b = (l.a.bufferInfo(e, y, t.config.maxBufferHole).end - y) / u; + if (b < 2 * r.duration / u && m > b) { + var E = void 0, + T = void 0; + for (T = r.level - 1; T > a; T--) { + var S = c[T].realBitrate ? Math.max(c[T].realBitrate, c[T].bitrate) : c[T].bitrate; + if ((E = r.duration * S / (6.4 * h)) < b) break + } + E < m && (d.b.warn("loading too slow, abort fragment loading and switch to level " + T + ":fragLoadedDelay[" + T + "]= i; u--) { + var c = l[u], + h = c.details, + f = h ? h.totalduration / h.fragments.length : e, + p = !!h && h.live, + v = void 0; + v = u <= t ? o * r : s * r; + var g = l[u].realBitrate ? Math.max(l[u].realBitrate, l[u].bitrate) : l[u].bitrate, + y = g * f / v; + if (d.b.trace("level/adjustedbw/bitrate/avgDuration/maxFetchDuration/fetchDuration: " + u + "/" + Math.round(v) + "/" + g + "/" + f + "/" + n + "/" + y), v > g && (!y || p && !this.bitrateTestDelay || y < n)) return u + } + return -1 + }, h(e, [{ + key: "nextAutoLevel", + get: function() { + var t = this._nextAutoLevel, + e = this._bwEstimator; + if (!(-1 === t || e && e.canEstimate())) return t; + var r = this._nextABRAutoLevel; + return -1 !== t && (r = Math.min(t, r)), r + }, + set: function(t) { + this._nextAutoLevel = t + } + }, { + key: "_nextABRAutoLevel", + get: function() { + var t = this.hls, + e = t.maxAutoLevel, + r = t.levels, + i = t.config, + a = t.minAutoLevel, + n = t.media, + o = this.lastLoadedFragLevel, + s = this.fragCurrent ? this.fragCurrent.duration : 0, + u = n ? n.currentTime : 0, + c = n && 0 !== n.playbackRate ? Math.abs(n.playbackRate) : 1, + h = this._bwEstimator ? this._bwEstimator.getEstimate() : i.abrEwmaDefaultEstimate, + f = (l.a.bufferInfo(n, u, i.maxBufferHole).end - u) / c, + p = this._findBestLevel(o, s, h, a, e, f, i.abrBandWidthFactor, i.abrBandWidthUpFactor, r); + if (p >= 0) return p; + d.b.trace("rebuffering expected to happen, lets try to find a quality level minimizing the rebuffering"); + var v = s ? Math.min(s, i.maxStarvationDelay) : i.maxStarvationDelay, + g = i.abrBandWidthFactor, + y = i.abrBandWidthUpFactor; + if (0 === f) { + var m = this.bitrateTestDelay; + if (m) { + v = (s ? Math.min(s, i.maxLoadingDelay) : i.maxLoadingDelay) - m, d.b.trace("bitrate test took " + Math.round(1e3 * m) + "ms, set first fragment max fetchDuration to " + Math.round(1e3 * v) + " ms"), g = y = 1 + } + } + return p = this._findBestLevel(o, s, h, a, e, f + v, g, y, r), Math.max(p, 0) + } + }]), e + }(s.a); + e.a = v + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + var a = r(55), + n = function() { + function t(e, r, n, o) { + i(this, t), this.hls = e, this.defaultEstimate_ = o, this.minWeight_ = .001, this.minDelayMs_ = 50, this.slow_ = new a.a(r), this.fast_ = new a.a(n) + } + return t.prototype.sample = function(t, e) { + t = Math.max(t, this.minDelayMs_); + var r = 8e3 * e / t, + i = t / 1e3; + this.fast_.sample(i, r), this.slow_.sample(i, r) + }, t.prototype.canEstimate = function() { + var t = this.fast_; + return t && t.getTotalWeight() >= this.minWeight_ + }, t.prototype.getEstimate = function() { + return this.canEstimate() ? Math.min(this.fast_.getEstimate(), this.slow_.getEstimate()) : this.defaultEstimate_ + }, t.prototype.destroy = function() {}, t + }(); + e.a = n + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + var a = function() { + function t(e) { + i(this, t), this.alpha_ = e ? Math.exp(Math.log(.5) / e) : 0, this.estimate_ = 0, this.totalWeight_ = 0 + } + return t.prototype.sample = function(t, e) { + var r = Math.pow(this.alpha_, t); + this.estimate_ = e * (1 - r) + r * this.estimate_, this.totalWeight_ += t + }, t.prototype.getTotalWeight = function() { + return this.totalWeight_ + }, t.prototype.getEstimate = function() { + if (this.alpha_) { + var t = 1 - Math.pow(this.alpha_, this.totalWeight_); + return this.estimate_ / t + } + return this.estimate_ + }, t + }(); + e.a = a + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + + function a(t, e) { + if (!t) throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); + return !e || "object" != typeof e && "function" != typeof e ? t : e + } + + function n(t, e) { + if ("function" != typeof e && null !== e) throw new TypeError("Super expression must either be null or a function, not " + typeof e); + t.prototype = Object.create(e && e.prototype, { + constructor: { + value: t, + enumerable: !1, + writable: !0, + configurable: !0 + } + }), e && (Object.setPrototypeOf ? Object.setPrototypeOf(t, e) : t.__proto__ = e) + } + var o = r(1), + s = r(3), + l = r(0), + u = r(2), + d = r(14), + c = Object(d.a)(), + h = function(t) { + function e(r) { + i(this, e); + var n = a(this, t.call(this, r, o.a.MEDIA_ATTACHING, o.a.MEDIA_DETACHING, o.a.MANIFEST_PARSED, o.a.BUFFER_RESET, o.a.BUFFER_APPENDING, o.a.BUFFER_CODECS, o.a.BUFFER_EOS, o.a.BUFFER_FLUSHING, o.a.LEVEL_PTS_UPDATED, o.a.LEVEL_UPDATED)); + return n._msDuration = null, n._levelDuration = null, n._live = null, n._objectUrl = null, n.onsbue = n.onSBUpdateEnd.bind(n), n.onsbe = n.onSBUpdateError.bind(n), n.pendingTracks = {}, n.tracks = {}, n + } + return n(e, t), e.prototype.destroy = function() { + s.a.prototype.destroy.call(this) + }, e.prototype.onLevelPtsUpdated = function(t) { + var e = t.type, + r = this.tracks.audio; + if ("audio" === e && r && "audio/mpeg" === r.container) { + var i = this.sourceBuffer.audio; + if (Math.abs(i.timestampOffset - t.start) > .1) { + var a = i.updating; + try { + i.abort() + } catch (t) { + a = !0, l.b.warn("can not abort audio buffer: " + t) + } + a ? this.audioTimestampOffset = t.start : (l.b.warn("change mpeg audio timestamp offset from " + i.timestampOffset + " to " + t.start), i.timestampOffset = t.start) + } + } + }, e.prototype.onManifestParsed = function(t) { + var e = t.audio, + r = t.video || t.levels.length && t.altAudio, + i = 0; + t.altAudio && (e || r) && (i = (e ? 1 : 0) + (r ? 1 : 0), l.b.log(i + " sourceBuffer(s) expected")), this.sourceBufferNb = i + }, e.prototype.onMediaAttaching = function(t) { + var e = this.media = t.media; + if (e) { + var r = this.mediaSource = new c; + this.onmso = this.onMediaSourceOpen.bind(this), this.onmse = this.onMediaSourceEnded.bind(this), this.onmsc = this.onMediaSourceClose.bind(this), r.addEventListener("sourceopen", this.onmso), r.addEventListener("sourceended", this.onmse), r.addEventListener("sourceclose", this.onmsc), e.src = window.URL.createObjectURL(r), this._objectUrl = e.src + } + }, e.prototype.onMediaDetaching = function() { + l.b.log("media source detaching"); + var t = this.mediaSource; + if (t) { + if ("open" === t.readyState) try { + t.endOfStream() + } catch (t) { + l.b.warn("onMediaDetaching:" + t.message + " while calling endOfStream") + } + t.removeEventListener("sourceopen", this.onmso), t.removeEventListener("sourceended", this.onmse), t.removeEventListener("sourceclose", this.onmsc), this.media && (window.URL.revokeObjectURL(this._objectUrl), this.media.src === this._objectUrl ? (this.media.removeAttribute("src"), this.media.load()) : l.b.warn("media.src was changed by a third party - skip cleanup")), this.mediaSource = null, this.media = null, this._objectUrl = null, this.pendingTracks = {}, this.tracks = {}, this.sourceBuffer = {}, this.flushRange = [], this.segments = [], this.appended = 0 + } + this.onmso = this.onmse = this.onmsc = null, this.hls.trigger(o.a.MEDIA_DETACHED) + }, e.prototype.onMediaSourceOpen = function() { + l.b.log("media source opened"), this.hls.trigger(o.a.MEDIA_ATTACHED, { + media: this.media + }); + var t = this.mediaSource; + t && t.removeEventListener("sourceopen", this.onmso), this.checkPendingTracks() + }, e.prototype.checkPendingTracks = function() { + var t = this.pendingTracks, + e = Object.keys(t).length; + e && (this.sourceBufferNb <= e || 0 === this.sourceBufferNb) && (this.createSourceBuffers(t), this.pendingTracks = {}, this.doAppending()) + }, e.prototype.onMediaSourceClose = function() { + l.b.log("media source closed") + }, e.prototype.onMediaSourceEnded = function() { + l.b.log("media source ended") + }, e.prototype.onSBUpdateEnd = function() { + if (this.audioTimestampOffset) { + var t = this.sourceBuffer.audio; + l.b.warn("change mpeg audio timestamp offset from " + t.timestampOffset + " to " + this.audioTimestampOffset), t.timestampOffset = this.audioTimestampOffset, delete this.audioTimestampOffset + } + this._needsFlush && this.doFlush(), this._needsEos && this.checkEos(), this.appending = !1; + var e = this.parent, + r = this.segments.reduce(function(t, r) { + return r.parent === e ? t + 1 : t + }, 0), + i = {}, + a = this.sourceBuffer; + for (var n in a) i[n] = a[n].buffered; + this.hls.trigger(o.a.BUFFER_APPENDED, { + parent: e, + pending: r, + timeRanges: i + }), this._needsFlush || this.doAppending(), this.updateMediaElementDuration() + }, e.prototype.onSBUpdateError = function(t) { + l.b.error("sourceBuffer error:", t), this.hls.trigger(o.a.ERROR, { + type: u.b.MEDIA_ERROR, + details: u.a.BUFFER_APPENDING_ERROR, + fatal: !1 + }) + }, e.prototype.onBufferReset = function() { + var t = this.sourceBuffer; + for (var e in t) { + var r = t[e]; + try { + this.mediaSource.removeSourceBuffer(r), r.removeEventListener("updateend", this.onsbue), r.removeEventListener("error", this.onsbe) + } catch (t) {} + } + this.sourceBuffer = {}, this.flushRange = [], this.segments = [], this.appended = 0 + }, e.prototype.onBufferCodecs = function(t) { + if (0 === Object.keys(this.sourceBuffer).length) { + for (var e in t) this.pendingTracks[e] = t[e]; + var r = this.mediaSource; + r && "open" === r.readyState && this.checkPendingTracks() + } + }, e.prototype.createSourceBuffers = function(t) { + var e = this.sourceBuffer, + r = this.mediaSource; + for (var i in t) + if (!e[i]) { + var a = t[i], + n = a.levelCodec || a.codec, + s = a.container + ";codecs=" + n; + l.b.log("creating sourceBuffer(" + s + ")"); + try { + var d = e[i] = r.addSourceBuffer(s); + d.addEventListener("updateend", this.onsbue), d.addEventListener("error", this.onsbe), this.tracks[i] = { + codec: n, + container: a.container + }, a.buffer = d + } catch (t) { + l.b.error("error while trying to add sourceBuffer:" + t.message), this.hls.trigger(o.a.ERROR, { + type: u.b.MEDIA_ERROR, + details: u.a.BUFFER_ADD_CODEC_ERROR, + fatal: !1, + err: t, + mimeType: s + }) + } + } this.hls.trigger(o.a.BUFFER_CREATED, { + tracks: t + }) + }, e.prototype.onBufferAppending = function(t) { + this._needsFlush || (this.segments ? this.segments.push(t) : this.segments = [t], this.doAppending()) + }, e.prototype.onBufferAppendFail = function(t) { + l.b.error("sourceBuffer error:", t.event), this.hls.trigger(o.a.ERROR, { + type: u.b.MEDIA_ERROR, + details: u.a.BUFFER_APPENDING_ERROR, + fatal: !1 + }) + }, e.prototype.onBufferEos = function(t) { + var e = this.sourceBuffer, + r = t.type; + for (var i in e) r && i !== r || e[i].ended || (e[i].ended = !0, l.b.log(i + " sourceBuffer now EOS")); + this.checkEos() + }, e.prototype.checkEos = function() { + var t = this.sourceBuffer, + e = this.mediaSource; + if (!e || "open" !== e.readyState) return void(this._needsEos = !1); + for (var r in t) { + var i = t[r]; + if (!i.ended) return; + if (i.updating) return void(this._needsEos = !0) + } + l.b.log("all media data available, signal endOfStream() to MediaSource and stop loading fragment"); + try { + e.endOfStream() + } catch (t) { + l.b.warn("exception while calling mediaSource.endOfStream()") + } + this._needsEos = !1 + }, e.prototype.onBufferFlushing = function(t) { + this.flushRange.push({ + start: t.startOffset, + end: t.endOffset, + type: t.type + }), this.flushBufferCounter = 0, this.doFlush() + }, e.prototype.onLevelUpdated = function(t) { + var e = t.details; + e.fragments.length > 0 && (this._levelDuration = e.totalduration + e.fragments[0].start, this._live = e.live, this.updateMediaElementDuration()) + }, e.prototype.updateMediaElementDuration = function() { + var t = this.hls.config, + e = void 0; + if (null !== this._levelDuration && this.media && this.mediaSource && this.sourceBuffer && 0 !== this.media.readyState && "open" === this.mediaSource.readyState) { + for (var r in this.sourceBuffer) + if (!0 === this.sourceBuffer[r].updating) return; + e = this.media.duration, null === this._msDuration && (this._msDuration = this.mediaSource.duration), !0 === this._live && !0 === t.liveDurationInfinity ? (l.b.log("Media Source duration is set to Infinity"), this._msDuration = this.mediaSource.duration = 1 / 0) : (this._levelDuration > this._msDuration && this._levelDuration > e || e === 1 / 0 || isNaN(e)) && (l.b.log("Updating Media Source duration to " + this._levelDuration.toFixed(3)), this._msDuration = this.mediaSource.duration = this._levelDuration) + } + }, e.prototype.doFlush = function() { + for (; this.flushRange.length;) { + var t = this.flushRange[0]; + if (!this.flushBuffer(t.start, t.end, t.type)) return void(this._needsFlush = !0); + this.flushRange.shift(), this.flushBufferCounter = 0 + } + if (0 === this.flushRange.length) { + this._needsFlush = !1; + var e = 0, + r = this.sourceBuffer; + try { + for (var i in r) e += r[i].buffered.length + } catch (t) { + l.b.error("error while accessing sourceBuffer.buffered") + } + this.appended = e, this.hls.trigger(o.a.BUFFER_FLUSHED) + } + }, e.prototype.doAppending = function() { + var t = this.hls, + e = this.sourceBuffer, + r = this.segments; + if (Object.keys(e).length) { + if (this.media.error) return this.segments = [], void l.b.error("trying to append although a media error occured, flush segment and abort"); + if (this.appending) return; + if (r && r.length) { + var i = r.shift(); + try { + var a = i.type, + n = e[a]; + n ? n.updating ? r.unshift(i) : (n.ended = !1, this.parent = i.parent, n.appendBuffer(i.data), this.appendError = 0, this.appended++, this.appending = !0) : this.onSBUpdateEnd() + } catch (e) { + l.b.error("error while trying to append buffer:" + e.message), r.unshift(i); + var s = { + type: u.b.MEDIA_ERROR, + parent: i.parent + }; + 22 !== e.code ? (this.appendError ? this.appendError++ : this.appendError = 1, s.details = u.a.BUFFER_APPEND_ERROR, this.appendError > t.config.appendErrorMaxRetry ? (l.b.log("fail " + t.config.appendErrorMaxRetry + " times to append segment in sourceBuffer"), r = [], s.fatal = !0, t.trigger(o.a.ERROR, s)) : (s.fatal = !1, t.trigger(o.a.ERROR, s))) : (this.segments = [], s.details = u.a.BUFFER_FULL_ERROR, s.fatal = !1, t.trigger(o.a.ERROR, s)) + } + } + } + }, e.prototype.flushBuffer = function(t, e, r) { + var i = void 0, + a = void 0, + n = void 0, + o = void 0, + s = void 0, + u = void 0, + d = this.sourceBuffer; + if (Object.keys(d).length) { + if (l.b.log("flushBuffer,pos/start/end: " + this.media.currentTime.toFixed(3) + "/" + t + "/" + e), this.flushBufferCounter < this.appended) { + for (var c in d) + if (!r || c === r) { + if (i = d[c], i.ended = !1, i.updating) return l.b.warn("cannot flush, sb updating in progress"), !1; + try { + for (a = 0; a < i.buffered.length; a++) + if (n = i.buffered.start(a), o = i.buffered.end(a), -1 !== navigator.userAgent.toLowerCase().indexOf("firefox") && e === Number.POSITIVE_INFINITY ? (s = t, u = e) : (s = Math.max(n, t), u = Math.min(o, e)), Math.min(u, o) - s > .5) return this.flushBufferCounter++, l.b.log("flush " + c + " [" + s + "," + u + "], of [" + n + "," + o + "], pos:" + this.media.currentTime), i.remove(s, u), !1 + } catch (t) { + l.b.warn("exception while accessing sourcebuffer, it might have been removed from MediaSource") + } + } + } else l.b.warn("abort flushing too many retries"); + l.b.log("buffer flushed") + } + return !0 + }, e + }(s.a); + e.a = h + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + + function a(t, e) { + if (!t) throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); + return !e || "object" != typeof e && "function" != typeof e ? t : e + } + + function n(t, e) { + if ("function" != typeof e && null !== e) throw new TypeError("Super expression must either be null or a function, not " + typeof e); + t.prototype = Object.create(e && e.prototype, { + constructor: { + value: t, + enumerable: !1, + writable: !0, + configurable: !0 + } + }), e && (Object.setPrototypeOf ? Object.setPrototypeOf(t, e) : t.__proto__ = e) + } + var o = r(1), + s = r(3), + l = function() { + function t(t, e) { + for (var r = 0; r < e.length; r++) { + var i = e[r]; + i.enumerable = i.enumerable || !1, i.configurable = !0, "value" in i && (i.writable = !0), Object.defineProperty(t, i.key, i) + } + } + return function(e, r, i) { + return r && t(e.prototype, r), i && t(e, i), e + } + }(), + u = function(t) { + function e(r) { + i(this, e); + var n = a(this, t.call(this, r, o.a.FPS_DROP_LEVEL_CAPPING, o.a.MEDIA_ATTACHING, o.a.MANIFEST_PARSED, o.a.BUFFER_CODECS)); + return n.autoLevelCapping = Number.POSITIVE_INFINITY, n.firstLevel = null, n.levels = [], n.media = null, n.restrictedLevels = [], n.timer = null, n + } + return n(e, t), e.prototype.destroy = function() { + this.hls.config.capLevelToPlayerSize && (this.media = null, this._stopCapping()) + }, e.prototype.onFpsDropLevelCapping = function(t) { + e.isLevelAllowed(t.droppedLevel, this.restrictedLevels) && this.restrictedLevels.push(t.droppedLevel) + }, e.prototype.onMediaAttaching = function(t) { + this.media = t.media instanceof window.HTMLVideoElement ? t.media : null + }, e.prototype.onManifestParsed = function(t) { + var e = this.hls; + this.restrictedLevels = [], this.levels = t.levels, this.firstLevel = t.firstLevel, e.config.capLevelToPlayerSize && (t.video || t.levels.length && t.altAudio) && this._startCapping() + }, e.prototype.onBufferCodecs = function(t) { + this.hls.config.capLevelToPlayerSize && t.video && this._startCapping() + }, e.prototype.onLevelsUpdated = function(t) { + this.levels = t.levels + }, e.prototype.detectPlayerSize = function() { + if (this.media) { + var t = this.levels ? this.levels.length : 0; + if (t) { + var e = this.hls; + e.autoLevelCapping = this.getMaxLevel(t - 1), e.autoLevelCapping > this.autoLevelCapping && e.streamController.nextLevelSwitch(), this.autoLevelCapping = e.autoLevelCapping + } + } + }, e.prototype.getMaxLevel = function(t) { + var r = this; + if (!this.levels) return -1; + var i = this.levels.filter(function(i, a) { + return e.isLevelAllowed(a, r.restrictedLevels) && a <= t + }); + return e.getMaxLevelByMediaSize(i, this.mediaWidth, this.mediaHeight) + }, e.prototype._startCapping = function() { + this.timer || (this.autoLevelCapping = Number.POSITIVE_INFINITY, this.hls.firstLevel = this.getMaxLevel(this.firstLevel), clearInterval(this.timer), this.timer = setInterval(this.detectPlayerSize.bind(this), 1e3), this.detectPlayerSize()) + }, e.prototype._stopCapping = function() { + this.restrictedLevels = [], this.firstLevel = null, this.autoLevelCapping = Number.POSITIVE_INFINITY, this.timer && (this.timer = clearInterval(this.timer), this.timer = null) + }, e.isLevelAllowed = function(t) { + return -1 === (arguments.length > 1 && void 0 !== arguments[1] ? arguments[1] : []).indexOf(t) + }, e.getMaxLevelByMediaSize = function(t, e, r) { + if (!t || t && !t.length) return -1; + for (var i = t.length - 1, a = 0; a < t.length; a += 1) { + var n = t[a]; + if ((n.width >= e || n.height >= r) && function(t, e) { + return !e || (t.width !== e.width || t.height !== e.height) + }(n, t[a + 1])) { + i = a; + break + } + } + return i + }, l(e, [{ + key: "mediaWidth", + get: function() { + var t = void 0, + r = this.media; + return r && (t = r.width || r.clientWidth || r.offsetWidth, t *= e.contentScaleFactor), t + } + }, { + key: "mediaHeight", + get: function() { + var t = void 0, + r = this.media; + return r && (t = r.height || r.clientHeight || r.offsetHeight, t *= e.contentScaleFactor), t + } + }], [{ + key: "contentScaleFactor", + get: function() { + var t = 1; + try { + t = window.devicePixelRatio + } catch (t) {} + return t + } + }]), e + }(s.a); + e.a = u + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + + function a(t, e) { + if (!t) throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); + return !e || "object" != typeof e && "function" != typeof e ? t : e + } + + function n(t, e) { + if ("function" != typeof e && null !== e) throw new TypeError("Super expression must either be null or a function, not " + typeof e); + t.prototype = Object.create(e && e.prototype, { + constructor: { + value: t, + enumerable: !1, + writable: !0, + configurable: !0 + } + }), e && (Object.setPrototypeOf ? Object.setPrototypeOf(t, e) : t.__proto__ = e) + } + var o = r(1), + s = r(3), + l = r(0), + u = window, + d = u.performance, + c = function(t) { + function e(r) { + return i(this, e), a(this, t.call(this, r, o.a.MEDIA_ATTACHING)) + } + return n(e, t), e.prototype.destroy = function() { + this.timer && clearInterval(this.timer), this.isVideoPlaybackQualityAvailable = !1 + }, e.prototype.onMediaAttaching = function(t) { + var e = this.hls.config; + if (e.capLevelOnFPSDrop) { + "function" == typeof(this.video = t.media instanceof window.HTMLVideoElement ? t.media : null).getVideoPlaybackQuality && (this.isVideoPlaybackQualityAvailable = !0), clearInterval(this.timer), this.timer = setInterval(this.checkFPSInterval.bind(this), e.fpsDroppedMonitoringPeriod) + } + }, e.prototype.checkFPS = function(t, e, r) { + var i = d.now(); + if (e) { + if (this.lastTime) { + var a = i - this.lastTime, + n = r - this.lastDroppedFrames, + s = e - this.lastDecodedFrames, + u = 1e3 * n / a, + c = this.hls; + if (c.trigger(o.a.FPS_DROP, { + currentDropped: n, + currentDecoded: s, + totalDroppedFrames: r + }), u > 0 && n > c.config.fpsDroppedMonitoringThreshold * s) { + var h = c.currentLevel; + l.b.warn("drop FPS ratio greater than max allowed value for currentLevel: " + h), h > 0 && (-1 === c.autoLevelCapping || c.autoLevelCapping >= h) && (h -= 1, c.trigger(o.a.FPS_DROP_LEVEL_CAPPING, { + level: h, + droppedLevel: c.currentLevel + }), c.autoLevelCapping = h, c.streamController.nextLevelSwitch()) + } + } + this.lastTime = i, this.lastDroppedFrames = r, this.lastDecodedFrames = e + } + }, e.prototype.checkFPSInterval = function() { + var t = this.video; + if (t) + if (this.isVideoPlaybackQualityAvailable) { + var e = t.getVideoPlaybackQuality(); + this.checkFPS(t, e.totalVideoFrames, e.droppedVideoFrames) + } else this.checkFPS(t, t.webkitDecodedFrameCount, t.webkitDroppedFrameCount) + }, e + }(s.a); + e.a = c + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + var a = r(0), + n = window, + o = n.performance, + s = n.XMLHttpRequest, + l = function() { + function t(e) { + i(this, t), e && e.xhrSetup && (this.xhrSetup = e.xhrSetup) + } + return t.prototype.destroy = function() { + this.abort(), this.loader = null + }, t.prototype.abort = function() { + var t = this.loader; + t && 4 !== t.readyState && (this.stats.aborted = !0, t.abort()), window.clearTimeout(this.requestTimeout), this.requestTimeout = null, window.clearTimeout(this.retryTimeout), this.retryTimeout = null + }, t.prototype.load = function(t, e, r) { + this.context = t, this.config = e, this.callbacks = r, this.stats = { + trequest: o.now(), + retry: 0 + }, this.retryDelay = e.retryDelay, this.loadInternal() + }, t.prototype.loadInternal = function() { + var t = void 0, + e = this.context; + t = this.loader = new s; + var r = this.stats; + r.tfirst = 0, r.loaded = 0; + var i = this.xhrSetup; + try { + if (i) try { + i(t, e.url) + } catch (r) { + t.open("GET", e.url, !0), i(t, e.url) + } + t.readyState || t.open("GET", e.url, !0) + } catch (r) { + return void this.callbacks.onError({ + code: t.status, + text: r.message + }, e, t) + } + e.rangeEnd && t.setRequestHeader("Range", "bytes=" + e.rangeStart + "-" + (e.rangeEnd - 1)), t.onreadystatechange = this.readystatechange.bind(this), t.onprogress = this.loadprogress.bind(this), t.responseType = e.responseType, this.requestTimeout = window.setTimeout(this.loadtimeout.bind(this), this.config.timeout), t.send() + }, t.prototype.readystatechange = function(t) { + var e = t.currentTarget, + r = e.readyState, + i = this.stats, + n = this.context, + s = this.config; + if (!i.aborted && r >= 2) + if (window.clearTimeout(this.requestTimeout), 0 === i.tfirst && (i.tfirst = Math.max(o.now(), i.trequest)), 4 === r) { + var l = e.status; + if (l >= 200 && l < 300) { + i.tload = Math.max(i.tfirst, o.now()); + var u = void 0, + d = void 0; + "arraybuffer" === n.responseType ? (u = e.response, d = u.byteLength) : (u = e.responseText, d = u.length), i.loaded = i.total = d; + var c = { + url: e.responseURL, + data: u + }; + this.callbacks.onSuccess(c, i, n, e) + } else i.retry >= s.maxRetry || l >= 400 && l < 499 ? (a.b.error(l + " while loading " + n.url), this.callbacks.onError({ + code: l, + text: e.statusText + }, n, e)) : (a.b.warn(l + " while loading " + n.url + ", retrying in " + this.retryDelay + "..."), this.destroy(), this.retryTimeout = window.setTimeout(this.loadInternal.bind(this), this.retryDelay), this.retryDelay = Math.min(2 * this.retryDelay, s.maxRetryDelay), i.retry++) + } else this.requestTimeout = window.setTimeout(this.loadtimeout.bind(this), s.timeout) + }, t.prototype.loadtimeout = function() { + a.b.warn("timeout while loading " + this.context.url), this.callbacks.onTimeout(this.stats, this.context, null) + }, t.prototype.loadprogress = function(t) { + var e = t.currentTarget, + r = this.stats; + r.loaded = t.loaded, t.lengthComputable && (r.total = t.total); + var i = this.callbacks.onProgress; + i && i(r, this.context, null, e) + }, t + }(); + e.a = l + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + + function a(t, e) { + if (!t) throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); + return !e || "object" != typeof e && "function" != typeof e ? t : e + } + + function n(t, e) { + if ("function" != typeof e && null !== e) throw new TypeError("Super expression must either be null or a function, not " + typeof e); + t.prototype = Object.create(e && e.prototype, { + constructor: { + value: t, + enumerable: !1, + writable: !0, + configurable: !0 + } + }), e && (Object.setPrototypeOf ? Object.setPrototypeOf(t, e) : t.__proto__ = e) + } + var o = r(1), + s = r(8), + l = r(0), + u = r(2), + d = function() { + function t(t, e) { + for (var r = 0; r < e.length; r++) { + var i = e[r]; + i.enumerable = i.enumerable || !1, i.configurable = !0, "value" in i && (i.writable = !0), Object.defineProperty(t, i.key, i) + } + } + return function(e, r, i) { + return r && t(e.prototype, r), i && t(e, i), e + } + }(), + c = function(t) { + function e(r) { + i(this, e); + var n = a(this, t.call(this, r, o.a.MANIFEST_LOADING, o.a.MANIFEST_PARSED, o.a.AUDIO_TRACK_LOADED, o.a.AUDIO_TRACK_SWITCHED, o.a.LEVEL_LOADED, o.a.ERROR)); + return n.trackId = -1, n.tracks = [], n.trackIdBlacklist = Object.create(null), n.audioGroupId = null, n + } + return n(e, t), e.prototype.onManifestLoading = function() { + this.tracks = [], this.trackId = -1 + }, e.prototype.onManifestParsed = function(t) { + var e = this.tracks = t.audioTracks || []; + this.hls.trigger(o.a.AUDIO_TRACKS_UPDATED, { + audioTracks: e + }) + }, e.prototype.onAudioTrackLoaded = function(t) { + if (t.id >= this.tracks.length) return void l.b.warn("Invalid audio track id:", t.id); + if (l.b.log("audioTrack " + t.id + " loaded"), this.tracks[t.id].details = t.details, t.details.live && !this.hasInterval()) { + var e = 1e3 * t.details.targetduration; + this.setInterval(e) + }!t.details.live && this.hasInterval() && this.clearInterval() + }, e.prototype.onAudioTrackSwitched = function(t) { + var e = this.tracks[t.id].groupId; + e && this.audioGroupId !== e && (this.audioGroupId = e) + }, e.prototype.onLevelLoaded = function(t) { + var e = this.hls.levels[t.level]; + if (e.audioGroupIds) { + var r = e.audioGroupIds[e.urlId]; + this.audioGroupId !== r && (this.audioGroupId = r, this._selectInitialAudioTrack()) + } + }, e.prototype.onError = function(t) { + t.type === u.b.NETWORK_ERROR && (t.fatal && this.clearInterval(), t.details === u.a.AUDIO_TRACK_LOAD_ERROR && (l.b.warn("Network failure on audio-track id:", t.context.id), this._handleLoadError())) + }, e.prototype.doTick = function() { + this._updateTrack(this.trackId) + }, e.prototype._selectInitialAudioTrack = function() { + var t = this, + e = this.tracks; + if (e.length) { + var r = this.tracks[this.trackId], + i = null; + r && (i = r.name); + var a = e.filter(function(t) { + return t.default + }); + a.length ? e = a : l.b.warn("No default audio tracks defined"); + var n = !1, + s = function() { + e.forEach(function(e) { + n || t.audioGroupId && e.groupId !== t.audioGroupId || i && i !== e.name || (t.audioTrack = e.id, n = !0) + }) + }; + s(), n || (i = null, s()), n || (l.b.error("No track found for running audio group-ID: " + this.audioGroupId), this.hls.trigger(o.a.ERROR, { + type: u.b.MEDIA_ERROR, + details: u.a.AUDIO_TRACK_LOAD_ERROR, + fatal: !0 + })) + } + }, e.prototype._needsTrackLoading = function(t) { + var e = t.details; + return !e || (!!e.live || void 0) + }, e.prototype._loadTrackDetailsIfNeeded = function(t) { + if (this._needsTrackLoading(t)) { + var e = t.url, + r = t.id; + l.b.log("loading audio-track playlist for id: " + r), this.hls.trigger(o.a.AUDIO_TRACK_LOADING, { + url: e, + id: r + }) + } + }, e.prototype._updateTrack = function(t) { + if (!(t < 0 || t >= this.tracks.length)) { + this.clearInterval(), this.trackId = t, l.b.log("trying to update audio-track " + t); + var e = this.tracks[t]; + this._loadTrackDetailsIfNeeded(e) + } + }, e.prototype._handleLoadError = function() { + this.trackIdBlacklist[this.trackId] = !0; + var t = this.trackId, + e = this.tracks[t], + r = e.name, + i = e.language, + a = e.groupId; + l.b.warn("Loading failed on audio track id: " + t + ", group-id: " + a + ', name/language: "' + r + '" / "' + i + '"'); + for (var n = t, o = 0; o < this.tracks.length; o++) + if (!this.trackIdBlacklist[o]) { + var s = this.tracks[o]; + if (s.name === r) { + n = o; + break + } + } if (n === t) return void l.b.warn('No fallback audio-track found for name/language: "' + r + '" / "' + i + '"'); + l.b.log("Attempting audio-track fallback id:", n, "group-id:", this.tracks[n].groupId), this.audioTrack = n + }, d(e, [{ + key: "audioTracks", + get: function() { + return this.tracks + } + }, { + key: "audioTrack", + get: function() { + return this.trackId + }, + set: function(t) { + if (this.trackId === t && this.tracks[this.trackId].details) return void l.b.debug("Same id as current audio-track passed, and track details available -> no-op"); + if (t < 0 || t >= this.tracks.length) return void l.b.warn("Invalid id passed to audio-track controller"); + var e = this.tracks[t]; + l.b.log("Now switching to audio-track index " + t), this.clearInterval(), this.trackId = t; + var r = e.url, + i = e.type, + a = e.id; + this.hls.trigger(o.a.AUDIO_TRACK_SWITCHING, { + id: a, + type: i, + url: r + }), this._loadTrackDetailsIfNeeded(e) + } + }]), e + }(s.a); + e.a = c + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + + function a(t, e) { + if (!t) throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); + return !e || "object" != typeof e && "function" != typeof e ? t : e + } + + function n(t, e) { + if ("function" != typeof e && null !== e) throw new TypeError("Super expression must either be null or a function, not " + typeof e); + t.prototype = Object.create(e && e.prototype, { + constructor: { + value: t, + enumerable: !1, + writable: !0, + configurable: !0 + } + }), e && (Object.setPrototypeOf ? Object.setPrototypeOf(t, e) : t.__proto__ = e) + } + var o = r(6), + s = r(11), + l = r(20), + u = r(1), + d = r(15), + c = r(24), + h = r(2), + f = r(0), + p = r(25), + v = r(8), + g = r(10), + y = r(9), + m = function() { + function t(t, e) { + for (var r = 0; r < e.length; r++) { + var i = e[r]; + i.enumerable = i.enumerable || !1, i.configurable = !0, "value" in i && (i.writable = !0), Object.defineProperty(t, i.key, i) + } + } + return function(e, r, i) { + return r && t(e.prototype, r), i && t(e, i), e + } + }(), + b = window, + E = b.performance, + T = { + STOPPED: "STOPPED", + STARTING: "STARTING", + IDLE: "IDLE", + PAUSED: "PAUSED", + KEY_LOADING: "KEY_LOADING", + FRAG_LOADING: "FRAG_LOADING", + FRAG_LOADING_WAITING_RETRY: "FRAG_LOADING_WAITING_RETRY", + WAITING_TRACK: "WAITING_TRACK", + PARSING: "PARSING", + PARSED: "PARSED", + BUFFER_FLUSHING: "BUFFER_FLUSHING", + ENDED: "ENDED", + ERROR: "ERROR", + WAITING_INIT_PTS: "WAITING_INIT_PTS" + }, + S = function(t) { + function e(r, n) { + i(this, e); + var o = a(this, t.call(this, r, u.a.MEDIA_ATTACHED, u.a.MEDIA_DETACHING, u.a.AUDIO_TRACKS_UPDATED, u.a.AUDIO_TRACK_SWITCHING, u.a.AUDIO_TRACK_LOADED, u.a.KEY_LOADED, u.a.FRAG_LOADED, u.a.FRAG_PARSING_INIT_SEGMENT, u.a.FRAG_PARSING_DATA, u.a.FRAG_PARSED, u.a.ERROR, u.a.BUFFER_RESET, u.a.BUFFER_CREATED, u.a.BUFFER_APPENDED, u.a.BUFFER_FLUSHED, u.a.INIT_PTS_FOUND)); + return o.fragmentTracker = n, o.config = r.config, o.audioCodecSwap = !1, o._state = T.STOPPED, o.initPTS = [], o.waitingFragment = null, o.videoTrackCC = null, o + } + return n(e, t), e.prototype.onHandlerDestroying = function() { + this.stopLoad(), t.prototype.onHandlerDestroying.call(this) + }, e.prototype.onHandlerDestroyed = function() { + this.state = T.STOPPED, this.fragmentTracker = null, t.prototype.onHandlerDestroyed.call(this) + }, e.prototype.onInitPtsFound = function(t) { + var e = t.id, + r = t.frag.cc, + i = t.initPTS; + "main" === e && (this.initPTS[r] = i, this.videoTrackCC = r, f.b.log("InitPTS for cc: " + r + " found from video track: " + i), this.state === T.WAITING_INIT_PTS && this.tick()) + }, e.prototype.startLoad = function(t) { + if (this.tracks) { + var e = this.lastCurrentTime; + this.stopLoad(), this.setInterval(100), this.fragLoadError = 0, e > 0 && -1 === t ? (f.b.log("audio:override startPosition with lastCurrentTime @" + e.toFixed(3)), this.state = T.IDLE) : (this.lastCurrentTime = this.startPosition ? this.startPosition : t, this.state = T.STARTING), this.nextLoadPosition = this.startPosition = this.lastCurrentTime, this.tick() + } else this.startPosition = t, this.state = T.STOPPED + }, e.prototype.stopLoad = function() { + var t = this.fragCurrent; + t && (t.loader && t.loader.abort(), this.fragmentTracker.removeFragment(t), this.fragCurrent = null), this.fragPrevious = null, this.demuxer && (this.demuxer.destroy(), this.demuxer = null), this.state = T.STOPPED + }, e.prototype.doTick = function() { + var t = void 0, + e = void 0, + r = void 0, + i = this.hls, + a = i.config; + switch (this.state) { + case T.ERROR: + case T.PAUSED: + case T.BUFFER_FLUSHING: + break; + case T.STARTING: + this.state = T.WAITING_TRACK, this.loadedmetadata = !1; + break; + case T.IDLE: + var n = this.tracks; + if (!n) break; + if (!this.media && (this.startFragRequested || !a.startFragPrefetch)) break; + if (this.loadedmetadata) t = this.media.currentTime; + else if (void 0 === (t = this.nextLoadPosition)) break; + var l = this.mediaBuffer ? this.mediaBuffer : this.media, + d = this.videoBuffer ? this.videoBuffer : this.media, + c = s.a.bufferInfo(l, t, a.maxBufferHole), + h = s.a.bufferInfo(d, t, a.maxBufferHole), + v = c.len, + y = c.end, + m = this.fragPrevious, + b = Math.min(a.maxBufferLength, a.maxMaxBufferLength), + S = Math.max(b, h.len), + R = this.audioSwitch, + A = this.trackId; + if ((v < S || R) && A < n.length) { + if (void 0 === (r = n[A].details)) { + this.state = T.WAITING_TRACK; + break + } + if (!R && !r.live && m && m.sn === r.endSN && !c.nextStart && (!this.media.seeking || this.media.duration - y < m.duration / 2)) { + this.hls.trigger(u.a.BUFFER_EOS, { + type: "audio" + }), this.state = T.ENDED; + break + } + var _ = r.fragments, + w = _.length, + L = _[0].start, + D = _[w - 1].start + _[w - 1].duration, + I = void 0; + if (R) + if (r.live && !r.PTSKnown) f.b.log("switching audiotrack, live stream, unknown PTS,load first fragment"), y = 0; + else if (y = t, r.PTSKnown && t < L) { + if (!(c.end > L || c.nextStart)) return; + f.b.log("alt audio track ahead of main track, seek to start of alt audio track"), this.media.currentTime = L + .05 + } + if (r.initSegment && !r.initSegment.data) I = r.initSegment; + else if (y <= L) { + if (I = _[0], null !== this.videoTrackCC && I.cc !== this.videoTrackCC && (I = Object(p.b)(_, this.videoTrackCC)), r.live && I.loadIdx && I.loadIdx === this.fragLoadIdx) { + var k = c.nextStart ? c.nextStart : L; + return f.b.log("no alt audio available @currentTime:" + this.media.currentTime + ", seeking @" + (k + .05)), void(this.media.currentTime = k + .05) + } + } else { + var O = void 0, + C = a.maxFragLookUpTolerance, + P = m ? _[m.sn - _[0].sn + 1] : void 0, + x = function(t) { + var e = Math.min(C, t.duration); + return t.start + t.duration - e <= y ? 1 : t.start - e > y && t.start ? -1 : 0 + }; + y < D ? (y > D - C && (C = 0), O = P && !x(P) ? P : o.a.search(_, x)) : O = _[w - 1], O && (I = O, L = O.start, m && I.level === m.level && I.sn === m.sn && (I.sn < r.endSN ? (I = _[I.sn + 1 - r.startSN], f.b.log("SN just loaded, load next one: " + I.sn)) : I = null)) + } + I && (I.encrypted ? (f.b.log("Loading key for " + I.sn + " of [" + r.startSN + " ," + r.endSN + "],track " + A), this.state = T.KEY_LOADING, i.trigger(u.a.KEY_LOADING, { + frag: I + })) : (f.b.log("Loading " + I.sn + ", cc: " + I.cc + " of [" + r.startSN + " ," + r.endSN + "],track " + A + ", currentTime:" + t + ",bufferEnd:" + y.toFixed(3)), (R || this.fragmentTracker.getState(I) === g.a.NOT_LOADED) && (this.fragCurrent = I, this.startFragRequested = !0, isNaN(I.sn) || (this.nextLoadPosition = I.start + I.duration), i.trigger(u.a.FRAG_LOADING, { + frag: I + }), this.state = T.FRAG_LOADING))) + } + break; + case T.WAITING_TRACK: + e = this.tracks[this.trackId], e && e.details && (this.state = T.IDLE); + break; + case T.FRAG_LOADING_WAITING_RETRY: + var F = E.now(), + N = this.retryDate; + l = this.media; + var M = l && l.seeking; + (!N || F >= N || M) && (f.b.log("audioStreamController: retryDate reached, switch back to IDLE state"), this.state = T.IDLE); + break; + case T.WAITING_INIT_PTS: + var U = this.videoTrackCC; + if (void 0 === this.initPTS[U]) break; + var B = this.waitingFragment; + if (B) { + var G = B.frag.cc; + U !== G ? (e = this.tracks[this.trackId], e.details && e.details.live && (f.b.warn("Waiting fragment CC (" + G + ") does not match video track CC (" + U + ")"), this.waitingFragment = null, this.state = T.IDLE)) : (this.state = T.FRAG_LOADING, this.onFragLoaded(this.waitingFragment), this.waitingFragment = null) + } else this.state = T.IDLE; + break; + case T.STOPPED: + case T.FRAG_LOADING: + case T.PARSING: + case T.PARSED: + case T.ENDED: + } + }, e.prototype.onMediaAttached = function(t) { + var e = this.media = this.mediaBuffer = t.media; + this.onvseeking = this.onMediaSeeking.bind(this), this.onvended = this.onMediaEnded.bind(this), e.addEventListener("seeking", this.onvseeking), e.addEventListener("ended", this.onvended); + var r = this.config; + this.tracks && r.autoStartLoad && this.startLoad(r.startPosition) + }, e.prototype.onMediaDetaching = function() { + var t = this.media; + t && t.ended && (f.b.log("MSE detaching and video ended, reset startPosition"), this.startPosition = this.lastCurrentTime = 0), t && (t.removeEventListener("seeking", this.onvseeking), t.removeEventListener("ended", this.onvended), this.onvseeking = this.onvseeked = this.onvended = null), this.media = this.mediaBuffer = this.videoBuffer = null, this.loadedmetadata = !1, this.stopLoad() + }, e.prototype.onMediaSeeking = function() { + this.state === T.ENDED && (this.state = T.IDLE), this.media && (this.lastCurrentTime = this.media.currentTime), this.tick() + }, e.prototype.onMediaEnded = function() { + this.startPosition = this.lastCurrentTime = 0 + }, e.prototype.onAudioTracksUpdated = function(t) { + f.b.log("audio tracks updated"), this.tracks = t.audioTracks + }, e.prototype.onAudioTrackSwitching = function(t) { + var e = !!t.url; + this.trackId = t.id, this.fragCurrent = null, this.state = T.PAUSED, this.waitingFragment = null, e ? this.setInterval(100) : this.demuxer && (this.demuxer.destroy(), this.demuxer = null), e && (this.audioSwitch = !0, this.state = T.IDLE), this.tick() + }, e.prototype.onAudioTrackLoaded = function(t) { + var e = t.details, + r = t.id, + i = this.tracks[r], + a = e.totalduration, + n = 0; + if (f.b.log("track " + r + " loaded [" + e.startSN + "," + e.endSN + "],duration:" + a), e.live) { + var o = i.details; + o && e.fragments.length > 0 ? (d.b(o, e), n = e.fragments[0].start, e.PTSKnown ? f.b.log("live audio playlist sliding:" + n.toFixed(3)) : f.b.log("live audio playlist - outdated PTS, unknown sliding")) : (e.PTSKnown = !1, f.b.log("live audio playlist - first load, unknown sliding")) + } else e.PTSKnown = !1; + if (i.details = e, !this.startFragRequested) { + if (-1 === this.startPosition) { + var s = e.startTimeOffset; + isNaN(s) ? this.startPosition = 0 : (f.b.log("start time offset found in playlist, adjust startPosition to " + s), this.startPosition = s) + } + this.nextLoadPosition = this.startPosition + } + this.state === T.WAITING_TRACK && (this.state = T.IDLE), this.tick() + }, e.prototype.onKeyLoaded = function() { + this.state === T.KEY_LOADING && (this.state = T.IDLE, this.tick()) + }, e.prototype.onFragLoaded = function(t) { + var e = this.fragCurrent, + r = t.frag; + if (this.state === T.FRAG_LOADING && e && "audio" === r.type && r.level === e.level && r.sn === e.sn) { + var i = this.tracks[this.trackId], + a = i.details, + n = a.totalduration, + o = e.level, + s = e.sn, + d = e.cc, + c = this.config.defaultAudioCodec || i.audioCodec || "mp4a.40.2", + h = this.stats = t.stats; + if ("initSegment" === s) this.state = T.IDLE, h.tparsed = h.tbuffered = E.now(), a.initSegment.data = t.payload, this.hls.trigger(u.a.FRAG_BUFFERED, { + stats: h, + frag: e, + id: "audio" + }), this.tick(); + else { + this.state = T.PARSING, this.appended = !1, this.demuxer || (this.demuxer = new l.a(this.hls, "audio")); + var p = this.initPTS[d], + v = a.initSegment ? a.initSegment.data : []; + if (a.initSegment || void 0 !== p) { + this.pendingBuffering = !0, f.b.log("Demuxing " + s + " of [" + a.startSN + " ," + a.endSN + "],track " + o); + this.demuxer.push(t.payload, v, c, null, e, n, !1, p) + } else f.b.log("unknown video PTS for continuity counter " + d + ", waiting for video PTS before demuxing audio frag " + s + " of [" + a.startSN + " ," + a.endSN + "],track " + o), this.waitingFragment = t, this.state = T.WAITING_INIT_PTS + } + } + this.fragLoadError = 0 + }, e.prototype.onFragParsingInitSegment = function(t) { + var e = this.fragCurrent, + r = t.frag; + if (e && "audio" === t.id && r.sn === e.sn && r.level === e.level && this.state === T.PARSING) { + var i = t.tracks, + a = void 0; + if (i.video && delete i.video, a = i.audio) { + a.levelCodec = a.codec, a.id = t.id, this.hls.trigger(u.a.BUFFER_CODECS, i), f.b.log("audio track:audio,container:" + a.container + ",codecs[level/parsed]=[" + a.levelCodec + "/" + a.codec + "]"); + var n = a.initSegment; + if (n) { + var o = { + type: "audio", + data: n, + parent: "audio", + content: "initSegment" + }; + this.audioSwitch ? this.pendingData = [o] : (this.appended = !0, this.pendingBuffering = !0, this.hls.trigger(u.a.BUFFER_APPENDING, o)) + } + this.tick() + } + } + }, e.prototype.onFragParsingData = function(t) { + var e = this, + r = this.fragCurrent, + i = t.frag; + if (r && "audio" === t.id && "audio" === t.type && i.sn === r.sn && i.level === r.level && this.state === T.PARSING) { + var a = this.trackId, + n = this.tracks[a], + o = this.hls; + isNaN(t.endPTS) && (t.endPTS = t.startPTS + r.duration, t.endDTS = t.startDTS + r.duration), r.addElementaryStream(y.a.ElementaryStreamTypes.AUDIO), f.b.log("parsed " + t.type + ",PTS:[" + t.startPTS.toFixed(3) + "," + t.endPTS.toFixed(3) + "],DTS:[" + t.startDTS.toFixed(3) + "/" + t.endDTS.toFixed(3) + "],nb:" + t.nb), d.c(n.details, r, t.startPTS, t.endPTS); + var s = this.audioSwitch, + l = this.media, + c = !1; + if (s && l) + if (l.readyState) { + var p = l.currentTime; + f.b.log("switching audio track : currentTime:" + p), p >= t.startPTS && (f.b.log("switching audio track : flushing all audio"), this.state = T.BUFFER_FLUSHING, o.trigger(u.a.BUFFER_FLUSHING, { + startOffset: 0, + endOffset: Number.POSITIVE_INFINITY, + type: "audio" + }), c = !0, this.audioSwitch = !1, o.trigger(u.a.AUDIO_TRACK_SWITCHED, { + id: a + })) + } else this.audioSwitch = !1, o.trigger(u.a.AUDIO_TRACK_SWITCHED, { + id: a + }); + var v = this.pendingData; + if (!v) return f.b.warn("Apparently attempt to enqueue media payload without codec initialization data upfront"), void o.trigger(u.a.ERROR, { + type: h.b.MEDIA_ERROR, + details: null, + fatal: !0 + }); + this.audioSwitch || ([t.data1, t.data2].forEach(function(e) { + e && e.length && v.push({ + type: t.type, + data: e, + parent: "audio", + content: "data" + }) + }), !c && v.length && (v.forEach(function(t) { + e.state === T.PARSING && (e.pendingBuffering = !0, e.hls.trigger(u.a.BUFFER_APPENDING, t)) + }), this.pendingData = [], this.appended = !0)), this.tick() + } + }, e.prototype.onFragParsed = function(t) { + var e = this.fragCurrent, + r = t.frag; + e && "audio" === t.id && r.sn === e.sn && r.level === e.level && this.state === T.PARSING && (this.stats.tparsed = E.now(), this.state = T.PARSED, this._checkAppendedParsed()) + }, e.prototype.onBufferReset = function() { + this.mediaBuffer = this.videoBuffer = null, this.loadedmetadata = !1 + }, e.prototype.onBufferCreated = function(t) { + var e = t.tracks.audio; + e && (this.mediaBuffer = e.buffer, this.loadedmetadata = !0), t.tracks.video && (this.videoBuffer = t.tracks.video.buffer) + }, e.prototype.onBufferAppended = function(t) { + if ("audio" === t.parent) { + var e = this.state; + e !== T.PARSING && e !== T.PARSED || (this.pendingBuffering = t.pending > 0, this._checkAppendedParsed()) + } + }, e.prototype._checkAppendedParsed = function() { + if (!(this.state !== T.PARSED || this.appended && this.pendingBuffering)) { + var t = this.fragCurrent, + e = this.stats, + r = this.hls; + if (t) { + this.fragPrevious = t, e.tbuffered = E.now(), r.trigger(u.a.FRAG_BUFFERED, { + stats: e, + frag: t, + id: "audio" + }); + var i = this.mediaBuffer ? this.mediaBuffer : this.media; + f.b.log("audio buffered : " + c.a.toString(i.buffered)), this.audioSwitch && this.appended && (this.audioSwitch = !1, r.trigger(u.a.AUDIO_TRACK_SWITCHED, { + id: this.trackId + })), this.state = T.IDLE + } + this.tick() + } + }, e.prototype.onError = function(t) { + var e = t.frag; + if (!e || "audio" === e.type) switch (t.details) { + case h.a.FRAG_LOAD_ERROR: + case h.a.FRAG_LOAD_TIMEOUT: + var r = t.frag; + if (r && "audio" !== r.type) break; + if (!t.fatal) { + var i = this.fragLoadError; + i ? i++ : i = 1; + var a = this.config; + if (i <= a.fragLoadingMaxRetry) { + this.fragLoadError = i; + var n = Math.min(Math.pow(2, i - 1) * a.fragLoadingRetryDelay, a.fragLoadingMaxRetryTimeout); + f.b.warn("AudioStreamController: frag loading failed, retry in " + n + " ms"), this.retryDate = E.now() + n, this.state = T.FRAG_LOADING_WAITING_RETRY + } else f.b.error("AudioStreamController: " + t.details + " reaches max retry, redispatch as fatal ..."), t.fatal = !0, this.state = T.ERROR + } + break; + case h.a.AUDIO_TRACK_LOAD_ERROR: + case h.a.AUDIO_TRACK_LOAD_TIMEOUT: + case h.a.KEY_LOAD_ERROR: + case h.a.KEY_LOAD_TIMEOUT: + this.state !== T.ERROR && (this.state = t.fatal ? T.ERROR : T.IDLE, f.b.warn("AudioStreamController: " + t.details + " while loading frag, now switching to " + this.state + " state ...")); + break; + case h.a.BUFFER_FULL_ERROR: + if ("audio" === t.parent && (this.state === T.PARSING || this.state === T.PARSED)) { + var o = this.mediaBuffer, + l = this.media.currentTime; + if (o && s.a.isBuffered(o, l) && s.a.isBuffered(o, l + .5)) { + var d = this.config; + d.maxMaxBufferLength >= d.maxBufferLength && (d.maxMaxBufferLength /= 2, f.b.warn("AudioStreamController: reduce max buffer length to " + d.maxMaxBufferLength + "s")), this.state = T.IDLE + } else f.b.warn("AudioStreamController: buffer full error also media.currentTime is not buffered, flush audio buffer"), this.fragCurrent = null, this.state = T.BUFFER_FLUSHING, this.hls.trigger(u.a.BUFFER_FLUSHING, { + startOffset: 0, + endOffset: Number.POSITIVE_INFINITY, + type: "audio" + }) + } + } + }, e.prototype.onBufferFlushed = function() { + var t = this, + e = this.pendingData; + e && e.length ? (f.b.log("AudioStreamController: appending pending audio data after buffer flushed"), e.forEach(function(e) { + t.hls.trigger(u.a.BUFFER_APPENDING, e) + }), this.appended = !0, this.pendingData = [], this.state = T.PARSED) : (this.state = T.IDLE, this.fragPrevious = null, this.tick()) + }, m(e, [{ + key: "state", + set: function(t) { + if (this.state !== t) { + var e = this.state; + this._state = t, f.b.log("audio stream:" + e + "->" + t) + } + }, + get: function() { + return this._state + } + }]), e + }(v.a); + e.a = S + }, function(t, e, r) { + "use strict"; + + function i(t, e, r, i) { + for (var n = void 0, o = void 0, s = void 0, l = void 0, u = void 0, d = window.VTTCue || window.TextTrackCue, c = 0; c < i.rows.length; c++) + if (n = i.rows[c], s = !0, l = 0, u = "", !n.isEmpty()) { + for (var h = 0; h < n.chars.length; h++) n.chars[h].uchar.match(/\s/) && s ? l++ : (u += n.chars[h].uchar, s = !1); + n.cueStartTime = e, e === r && (r += 1e-4), o = new d(e, r, Object(a.b)(u.trim())), l >= 16 ? l-- : l++, navigator.userAgent.match(/Firefox\//) ? o.line = c + 1 : o.line = c > 7 ? c - 2 : c + 1, o.align = "left", o.position = Math.max(0, Math.min(100, l / 32 * 100 + (navigator.userAgent.match(/Firefox\//) ? 50 : 0))), t.addCue(o) + } + } + Object.defineProperty(e, "__esModule", { + value: !0 + }), e.newCue = i; + var a = r(27) + }, function(t, e, r) { + "use strict"; + e.a = function() { + function t(t) { + return "string" == typeof t && (!!n[t.toLowerCase()] && t.toLowerCase()) + } + + function e(t) { + return "string" == typeof t && (!!o[t.toLowerCase()] && t.toLowerCase()) + } + + function r(t) { + for (var e = 1; e < arguments.length; e++) { + var r = arguments[e]; + for (var i in r) t[i] = r[i] + } + return t + } + + function i(i, n, o) { + var s = this, + l = function() { + if ("undefined" != typeof navigator) return /MSIE\s8\.0/.test(navigator.userAgent) + }(), + u = {}; + l ? s = document.createElement("custom") : u.enumerable = !0, s.hasBeenReset = !1; + var d = "", + c = !1, + h = i, + f = n, + p = o, + v = null, + g = "", + y = !0, + m = "auto", + b = "start", + E = 50, + T = "middle", + S = 50, + R = "middle"; + if (Object.defineProperty(s, "id", r({}, u, { + get: function() { + return d + }, + set: function(t) { + d = "" + t + } + })), Object.defineProperty(s, "pauseOnExit", r({}, u, { + get: function() { + return c + }, + set: function(t) { + c = !!t + } + })), Object.defineProperty(s, "startTime", r({}, u, { + get: function() { + return h + }, + set: function(t) { + if ("number" != typeof t) throw new TypeError("Start time must be set to a number."); + h = t, this.hasBeenReset = !0 + } + })), Object.defineProperty(s, "endTime", r({}, u, { + get: function() { + return f + }, + set: function(t) { + if ("number" != typeof t) throw new TypeError("End time must be set to a number."); + f = t, this.hasBeenReset = !0 + } + })), Object.defineProperty(s, "text", r({}, u, { + get: function() { + return p + }, + set: function(t) { + p = "" + t, this.hasBeenReset = !0 + } + })), Object.defineProperty(s, "region", r({}, u, { + get: function() { + return v + }, + set: function(t) { + v = t, this.hasBeenReset = !0 + } + })), Object.defineProperty(s, "vertical", r({}, u, { + get: function() { + return g + }, + set: function(e) { + var r = t(e); + if (!1 === r) throw new SyntaxError("An invalid or illegal string was specified."); + g = r, this.hasBeenReset = !0 + } + })), Object.defineProperty(s, "snapToLines", r({}, u, { + get: function() { + return y + }, + set: function(t) { + y = !!t, this.hasBeenReset = !0 + } + })), Object.defineProperty(s, "line", r({}, u, { + get: function() { + return m + }, + set: function(t) { + if ("number" != typeof t && t !== a) throw new SyntaxError("An invalid number or illegal string was specified."); + m = t, this.hasBeenReset = !0 + } + })), Object.defineProperty(s, "lineAlign", r({}, u, { + get: function() { + return b + }, + set: function(t) { + var r = e(t); + if (!r) throw new SyntaxError("An invalid or illegal string was specified."); + b = r, this.hasBeenReset = !0 + } + })), Object.defineProperty(s, "position", r({}, u, { + get: function() { + return E + }, + set: function(t) { + if (t < 0 || t > 100) throw new Error("Position must be between 0 and 100."); + E = t, this.hasBeenReset = !0 + } + })), Object.defineProperty(s, "positionAlign", r({}, u, { + get: function() { + return T + }, + set: function(t) { + var r = e(t); + if (!r) throw new SyntaxError("An invalid or illegal string was specified."); + T = r, this.hasBeenReset = !0 + } + })), Object.defineProperty(s, "size", r({}, u, { + get: function() { + return S + }, + set: function(t) { + if (t < 0 || t > 100) throw new Error("Size must be between 0 and 100."); + S = t, this.hasBeenReset = !0 + } + })), Object.defineProperty(s, "align", r({}, u, { + get: function() { + return R + }, + set: function(t) { + var r = e(t); + if (!r) throw new SyntaxError("An invalid or illegal string was specified."); + R = r, this.hasBeenReset = !0 + } + })), s.displayState = void 0, l) return s + } + if ("undefined" != typeof window && window.VTTCue) return window.VTTCue; + var a = "auto", + n = { + "": !0, + lr: !0, + rl: !0 + }, + o = { + start: !0, + middle: !0, + end: !0, + left: !0, + right: !0 + }; + return i.prototype.getCueAsHTML = function() { + return window.WebVTT.convertCueToDOMTree(window, this.text) + }, i + }() + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + + function a(t, e) { + if (!t) throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); + return !e || "object" != typeof e && "function" != typeof e ? t : e + } + + function n(t, e) { + if ("function" != typeof e && null !== e) throw new TypeError("Super expression must either be null or a function, not " + typeof e); + t.prototype = Object.create(e && e.prototype, { + constructor: { + value: t, + enumerable: !1, + writable: !0, + configurable: !0 + } + }), e && (Object.setPrototypeOf ? Object.setPrototypeOf(t, e) : t.__proto__ = e) + } + + function o(t, e) { + return t && t.label === e.name && !(t.textTrack1 || t.textTrack2) + } + + function s(t, e, r, i) { + return Math.min(e, i) - Math.max(t, r) + } + var l = r(1), + u = r(3), + d = r(65), + c = r(66), + h = r(67), + f = r(0), + p = r(26), + v = function(t) { + function e(r) { + i(this, e); + var n = a(this, t.call(this, r, l.a.MEDIA_ATTACHING, l.a.MEDIA_DETACHING, l.a.FRAG_PARSING_USERDATA, l.a.FRAG_DECRYPTED, l.a.MANIFEST_LOADING, l.a.MANIFEST_LOADED, l.a.FRAG_LOADED, l.a.LEVEL_SWITCHING, l.a.INIT_PTS_FOUND)); + if (n.hls = r, n.config = r.config, n.enabled = !0, n.Cues = r.config.cueHandler, n.textTracks = [], n.tracks = [], n.unparsedVttFrags = [], n.initPTS = void 0, n.cueRanges = [], n.captionsTracks = {}, n.captionsProperties = { + textTrack1: { + label: n.config.captionsTextTrack1Label, + languageCode: n.config.captionsTextTrack1LanguageCode + }, + textTrack2: { + label: n.config.captionsTextTrack2Label, + languageCode: n.config.captionsTextTrack2LanguageCode + } + }, n.config.enableCEA708Captions) { + var o = new c.a(n, "textTrack1"), + s = new c.a(n, "textTrack2"); + n.cea608Parser = new d.a(0, o, s) + } + return n + } + return n(e, t), e.prototype.addCues = function(t, e, r, i) { + for (var a = this.cueRanges, n = !1, o = a.length; o--;) { + var l = a[o], + u = s(l[0], l[1], e, r); + if (u >= 0 && (l[0] = Math.min(l[0], e), l[1] = Math.max(l[1], r), n = !0, u / (r - e) > .5)) return + } + n || a.push([e, r]), this.Cues.newCue(this.captionsTracks[t], e, r, i) + }, e.prototype.onInitPtsFound = function(t) { + var e = this; + void 0 === this.initPTS && (this.initPTS = t.initPTS), this.unparsedVttFrags.length && (this.unparsedVttFrags.forEach(function(t) { + e.onFragLoaded(t) + }), this.unparsedVttFrags = []) + }, e.prototype.getExistingTrack = function(t) { + var e = this.media; + if (e) + for (var r = 0; r < e.textTracks.length; r++) { + var i = e.textTracks[r]; + if (i[t]) return i + } + return null + }, e.prototype.createCaptionsTrack = function(t) { + var e = this.captionsProperties[t], + r = e.label, + i = e.languageCode, + a = this.captionsTracks; + if (!a[t]) { + var n = this.getExistingTrack(t); + if (n) a[t] = n, Object(p.a)(a[t]), Object(p.b)(a[t], this.media); + else { + var o = this.createTextTrack("captions", r, i); + o && (o[t] = !0, a[t] = o) + } + } + }, e.prototype.createTextTrack = function(t, e, r) { + var i = this.media; + if (i) return i.addTextTrack(t, e, r) + }, e.prototype.destroy = function() { + u.a.prototype.destroy.call(this) + }, e.prototype.onMediaAttaching = function(t) { + this.media = t.media, this._cleanTracks() + }, e.prototype.onMediaDetaching = function() { + var t = this.captionsTracks; + Object.keys(t).forEach(function(e) { + Object(p.a)(t[e]), delete t[e] + }) + }, e.prototype.onManifestLoading = function() { + this.lastSn = -1, this.prevCC = -1, this.vttCCs = { + ccOffset: 0, + presentationOffset: 0 + }, this._cleanTracks() + }, e.prototype._cleanTracks = function() { + var t = this.media; + if (t) { + var e = t.textTracks; + if (e) + for (var r = 0; r < e.length; r++) Object(p.a)(e[r]) + } + }, e.prototype.onManifestLoaded = function(t) { + var e = this; + if (this.textTracks = [], this.unparsedVttFrags = this.unparsedVttFrags || [], this.initPTS = void 0, this.cueRanges = [], this.config.enableWebVTT) { + this.tracks = t.subtitles || []; + var r = this.media ? this.media.textTracks : []; + this.tracks.forEach(function(t, i) { + var a = void 0; + if (i < r.length) { + var n = r[i]; + o(n, t) && (a = n) + } + a || (a = e.createTextTrack("subtitles", t.name, t.lang)), t.default ? a.mode = e.hls.subtitleDisplay ? "showing" : "hidden" : a.mode = "disabled", e.textTracks.push(a) + }) + } + }, e.prototype.onLevelSwitching = function() { + this.enabled = "NONE" !== this.hls.currentLevel.closedCaptions + }, e.prototype.onFragLoaded = function(t) { + var e = t.frag, + r = t.payload; + if ("main" === e.type) { + var i = e.sn; + if (i !== this.lastSn + 1) { + var a = this.cea608Parser; + a && a.reset() + } + this.lastSn = i + } else if ("subtitle" === e.type) + if (r.byteLength) { + if (void 0 === this.initPTS) return void this.unparsedVttFrags.push(t); + var n = e.decryptdata; + null != n && null != n.key && "AES-128" === n.method || this._parseVTTs(e, r) + } else this.hls.trigger(l.a.SUBTITLE_FRAG_PROCESSED, { + success: !1, + frag: e + }) + }, e.prototype._parseVTTs = function(t, e) { + var r = this.vttCCs; + r[t.cc] || (r[t.cc] = { + start: t.start, + prevCC: this.prevCC, + new: !0 + }, this.prevCC = t.cc); + var i = this.textTracks, + a = this.hls; + h.a.parse(e, this.initPTS, r, t.cc, function(e) { + var r = i[t.trackId]; + if ("disabled" === r.mode) return void a.trigger(l.a.SUBTITLE_FRAG_PROCESSED, { + success: !1, + frag: t + }); + e.forEach(function(t) { + if (!r.cues.getCueById(t.id)) try { + r.addCue(t) + } catch (i) { + var e = new window.TextTrackCue(t.startTime, t.endTime, t.text); + e.id = t.id, r.addCue(e) + } + }), a.trigger(l.a.SUBTITLE_FRAG_PROCESSED, { + success: !0, + frag: t + }) + }, function(e) { + f.b.log("Failed to parse VTT cue: " + e), a.trigger(l.a.SUBTITLE_FRAG_PROCESSED, { + success: !1, + frag: t + }) + }) + }, e.prototype.onFragDecrypted = function(t) { + var e = t.payload, + r = t.frag; + if ("subtitle" === r.type) { + if (void 0 === this.initPTS) return void this.unparsedVttFrags.push(t); + this._parseVTTs(r, e) + } + }, e.prototype.onFragParsingUserdata = function(t) { + if (this.enabled && this.config.enableCEA708Captions) + for (var e = 0; e < t.samples.length; e++) { + var r = this.extractCea608Data(t.samples[e].bytes); + this.cea608Parser.addData(t.samples[e].pts, r) + } + }, e.prototype.extractCea608Data = function(t) { + for (var e = 31 & t[0], r = 2, i = void 0, a = void 0, n = void 0, o = void 0, s = void 0, l = [], u = 0; u < e; u++) i = t[r++], a = 127 & t[r++], n = 127 & t[r++], o = 0 != (4 & i), s = 3 & i, 0 === a && 0 === n || o && 0 === s && (l.push(a), l.push(n)); + return l + }, e + }(u.a); + e.a = v + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + var a = { + 42: 225, + 92: 233, + 94: 237, + 95: 243, + 96: 250, + 123: 231, + 124: 247, + 125: 209, + 126: 241, + 127: 9608, + 128: 174, + 129: 176, + 130: 189, + 131: 191, + 132: 8482, + 133: 162, + 134: 163, + 135: 9834, + 136: 224, + 137: 32, + 138: 232, + 139: 226, + 140: 234, + 141: 238, + 142: 244, + 143: 251, + 144: 193, + 145: 201, + 146: 211, + 147: 218, + 148: 220, + 149: 252, + 150: 8216, + 151: 161, + 152: 42, + 153: 8217, + 154: 9473, + 155: 169, + 156: 8480, + 157: 8226, + 158: 8220, + 159: 8221, + 160: 192, + 161: 194, + 162: 199, + 163: 200, + 164: 202, + 165: 203, + 166: 235, + 167: 206, + 168: 207, + 169: 239, + 170: 212, + 171: 217, + 172: 249, + 173: 219, + 174: 171, + 175: 187, + 176: 195, + 177: 227, + 178: 205, + 179: 204, + 180: 236, + 181: 210, + 182: 242, + 183: 213, + 184: 245, + 185: 123, + 186: 125, + 187: 92, + 188: 94, + 189: 95, + 190: 124, + 191: 8764, + 192: 196, + 193: 228, + 194: 214, + 195: 246, + 196: 223, + 197: 165, + 198: 164, + 199: 9475, + 200: 197, + 201: 229, + 202: 216, + 203: 248, + 204: 9487, + 205: 9491, + 206: 9495, + 207: 9499 + }, + n = function(t) { + var e = t; + return a.hasOwnProperty(t) && (e = a[t]), String.fromCharCode(e) + }, + o = 15, + s = 100, + l = { + 17: 1, + 18: 3, + 21: 5, + 22: 7, + 23: 9, + 16: 11, + 19: 12, + 20: 14 + }, + u = { + 17: 2, + 18: 4, + 21: 6, + 22: 8, + 23: 10, + 19: 13, + 20: 15 + }, + d = { + 25: 1, + 26: 3, + 29: 5, + 30: 7, + 31: 9, + 24: 11, + 27: 12, + 28: 14 + }, + c = { + 25: 2, + 26: 4, + 29: 6, + 30: 8, + 31: 10, + 27: 13, + 28: 15 + }, + h = ["white", "green", "blue", "cyan", "red", "yellow", "magenta", "black", "transparent"], + f = { + verboseFilter: { + DATA: 3, + DEBUG: 3, + INFO: 2, + WARNING: 2, + TEXT: 1, + ERROR: 0 + }, + time: null, + verboseLevel: 0, + setTime: function(t) { + this.time = t + }, + log: function(t, e) { + this.verboseFilter[t]; + this.verboseLevel + } + }, + p = function(t) { + for (var e = [], r = 0; r < t.length; r++) e.push(t[r].toString(16)); + return e + }, + v = function() { + function t(e, r, a, n, o) { + i(this, t), this.foreground = e || "white", this.underline = r || !1, this.italics = a || !1, this.background = n || "black", this.flash = o || !1 + } + return t.prototype.reset = function() { + this.foreground = "white", this.underline = !1, this.italics = !1, this.background = "black", this.flash = !1 + }, t.prototype.setStyles = function(t) { + for (var e = ["foreground", "underline", "italics", "background", "flash"], r = 0; r < e.length; r++) { + var i = e[r]; + t.hasOwnProperty(i) && (this[i] = t[i]) + } + }, t.prototype.isDefault = function() { + return "white" === this.foreground && !this.underline && !this.italics && "black" === this.background && !this.flash + }, t.prototype.equals = function(t) { + return this.foreground === t.foreground && this.underline === t.underline && this.italics === t.italics && this.background === t.background && this.flash === t.flash + }, t.prototype.copy = function(t) { + this.foreground = t.foreground, this.underline = t.underline, this.italics = t.italics, this.background = t.background, this.flash = t.flash + }, t.prototype.toString = function() { + return "color=" + this.foreground + ", underline=" + this.underline + ", italics=" + this.italics + ", background=" + this.background + ", flash=" + this.flash + }, t + }(), + g = function() { + function t(e, r, a, n, o, s) { + i(this, t), this.uchar = e || " ", this.penState = new v(r, a, n, o, s) + } + return t.prototype.reset = function() { + this.uchar = " ", this.penState.reset() + }, t.prototype.setChar = function(t, e) { + this.uchar = t, this.penState.copy(e) + }, t.prototype.setPenState = function(t) { + this.penState.copy(t) + }, t.prototype.equals = function(t) { + return this.uchar === t.uchar && this.penState.equals(t.penState) + }, t.prototype.copy = function(t) { + this.uchar = t.uchar, this.penState.copy(t.penState) + }, t.prototype.isEmpty = function() { + return " " === this.uchar && this.penState.isDefault() + }, t + }(), + y = function() { + function t() { + i(this, t), this.chars = []; + for (var e = 0; e < s; e++) this.chars.push(new g); + this.pos = 0, this.currPenState = new v + } + return t.prototype.equals = function(t) { + for (var e = !0, r = 0; r < s; r++) + if (!this.chars[r].equals(t.chars[r])) { + e = !1; + break + } return e + }, t.prototype.copy = function(t) { + for (var e = 0; e < s; e++) this.chars[e].copy(t.chars[e]) + }, t.prototype.isEmpty = function() { + for (var t = !0, e = 0; e < s; e++) + if (!this.chars[e].isEmpty()) { + t = !1; + break + } return t + }, t.prototype.setCursor = function(t) { + this.pos !== t && (this.pos = t), this.pos < 0 ? (f.log("ERROR", "Negative cursor position " + this.pos), this.pos = 0) : this.pos > s && (f.log("ERROR", "Too large cursor position " + this.pos), this.pos = s) + }, t.prototype.moveCursor = function(t) { + var e = this.pos + t; + if (t > 1) + for (var r = this.pos + 1; r < e + 1; r++) this.chars[r].setPenState(this.currPenState); + this.setCursor(e) + }, t.prototype.backSpace = function() { + this.moveCursor(-1), this.chars[this.pos].setChar(" ", this.currPenState) + }, t.prototype.insertChar = function(t) { + t >= 144 && this.backSpace(); + var e = n(t); + if (this.pos >= s) return void f.log("ERROR", "Cannot insert " + t.toString(16) + " (" + e + ") at position " + this.pos + ". Skipping it!"); + this.chars[this.pos].setChar(e, this.currPenState), this.moveCursor(1) + }, t.prototype.clearFromPos = function(t) { + var e = void 0; + for (e = t; e < s; e++) this.chars[e].reset() + }, t.prototype.clear = function() { + this.clearFromPos(0), this.pos = 0, this.currPenState.reset() + }, t.prototype.clearToEndOfRow = function() { + this.clearFromPos(this.pos) + }, t.prototype.getTextString = function() { + for (var t = [], e = !0, r = 0; r < s; r++) { + var i = this.chars[r].uchar; + " " !== i && (e = !1), t.push(i) + } + return e ? "" : t.join("") + }, t.prototype.setPenStyles = function(t) { + this.currPenState.setStyles(t), this.chars[this.pos].setPenState(this.currPenState) + }, t + }(), + m = function() { + function t() { + i(this, t), this.rows = []; + for (var e = 0; e < o; e++) this.rows.push(new y); + this.currRow = o - 1, this.nrRollUpRows = null, this.reset() + } + return t.prototype.reset = function() { + for (var t = 0; t < o; t++) this.rows[t].clear(); + this.currRow = o - 1 + }, t.prototype.equals = function(t) { + for (var e = !0, r = 0; r < o; r++) + if (!this.rows[r].equals(t.rows[r])) { + e = !1; + break + } return e + }, t.prototype.copy = function(t) { + for (var e = 0; e < o; e++) this.rows[e].copy(t.rows[e]) + }, t.prototype.isEmpty = function() { + for (var t = !0, e = 0; e < o; e++) + if (!this.rows[e].isEmpty()) { + t = !1; + break + } return t + }, t.prototype.backSpace = function() { + this.rows[this.currRow].backSpace() + }, t.prototype.clearToEndOfRow = function() { + this.rows[this.currRow].clearToEndOfRow() + }, t.prototype.insertChar = function(t) { + this.rows[this.currRow].insertChar(t) + }, t.prototype.setPen = function(t) { + this.rows[this.currRow].setPenStyles(t) + }, t.prototype.moveCursor = function(t) { + this.rows[this.currRow].moveCursor(t) + }, t.prototype.setCursor = function(t) { + f.log("INFO", "setCursor: " + t), this.rows[this.currRow].setCursor(t) + }, t.prototype.setPAC = function(t) { + f.log("INFO", "pacData = " + JSON.stringify(t)); + var e = t.row - 1; + if (this.nrRollUpRows && e < this.nrRollUpRows - 1 && (e = this.nrRollUpRows - 1), this.nrRollUpRows && this.currRow !== e) { + for (var r = 0; r < o; r++) this.rows[r].clear(); + var i = this.currRow + 1 - this.nrRollUpRows, + a = this.lastOutputScreen; + if (a) { + var n = a.rows[i].cueStartTime; + if (n && n < f.time) + for (var s = 0; s < this.nrRollUpRows; s++) this.rows[e - this.nrRollUpRows + s + 1].copy(a.rows[i + s]) + } + } + this.currRow = e; + var l = this.rows[this.currRow]; + if (null !== t.indent) { + var u = t.indent, + d = Math.max(u - 1, 0); + l.setCursor(t.indent), t.color = l.chars[d].penState.foreground + } + var c = { + foreground: t.color, + underline: t.underline, + italics: t.italics, + background: "black", + flash: !1 + }; + this.setPen(c) + }, t.prototype.setBkgData = function(t) { + f.log("INFO", "bkgData = " + JSON.stringify(t)), this.backSpace(), this.setPen(t), this.insertChar(32) + }, t.prototype.setRollUpRows = function(t) { + this.nrRollUpRows = t + }, t.prototype.rollUp = function() { + if (null === this.nrRollUpRows) return void f.log("DEBUG", "roll_up but nrRollUpRows not set yet"); + f.log("TEXT", this.getDisplayText()); + var t = this.currRow + 1 - this.nrRollUpRows, + e = this.rows.splice(t, 1)[0]; + e.clear(), this.rows.splice(this.currRow, 0, e), f.log("INFO", "Rolling up") + }, t.prototype.getDisplayText = function(t) { + t = t || !1; + for (var e = [], r = "", i = -1, a = 0; a < o; a++) { + var n = this.rows[a].getTextString(); + n && (i = a + 1, t ? e.push("Row " + i + ": '" + n + "'") : e.push(n.trim())) + } + return e.length > 0 && (r = t ? "[" + e.join(" | ") + "]" : e.join("\n")), r + }, t.prototype.getTextAndFormat = function() { + return this.rows + }, t + }(), + b = function() { + function t(e, r) { + i(this, t), this.chNr = e, this.outputFilter = r, this.mode = null, this.verbose = 0, this.displayedMemory = new m, this.nonDisplayedMemory = new m, this.lastOutputScreen = new m, this.currRollUpRow = this.displayedMemory.rows[o - 1], this.writeScreen = this.displayedMemory, this.mode = null, this.cueStartTime = null + } + return t.prototype.reset = function() { + this.mode = null, this.displayedMemory.reset(), this.nonDisplayedMemory.reset(), this.lastOutputScreen.reset(), this.currRollUpRow = this.displayedMemory.rows[o - 1], this.writeScreen = this.displayedMemory, this.mode = null, this.cueStartTime = null, this.lastCueEndTime = null + }, t.prototype.getHandler = function() { + return this.outputFilter + }, t.prototype.setHandler = function(t) { + this.outputFilter = t + }, t.prototype.setPAC = function(t) { + this.writeScreen.setPAC(t) + }, t.prototype.setBkgData = function(t) { + this.writeScreen.setBkgData(t) + }, t.prototype.setMode = function(t) { + t !== this.mode && (this.mode = t, f.log("INFO", "MODE=" + t), "MODE_POP-ON" === this.mode ? this.writeScreen = this.nonDisplayedMemory : (this.writeScreen = this.displayedMemory, this.writeScreen.reset()), "MODE_ROLL-UP" !== this.mode && (this.displayedMemory.nrRollUpRows = null, this.nonDisplayedMemory.nrRollUpRows = null), this.mode = t) + }, t.prototype.insertChars = function(t) { + for (var e = 0; e < t.length; e++) this.writeScreen.insertChar(t[e]); + var r = this.writeScreen === this.displayedMemory ? "DISP" : "NON_DISP"; + f.log("INFO", r + ": " + this.writeScreen.getDisplayText(!0)), "MODE_PAINT-ON" !== this.mode && "MODE_ROLL-UP" !== this.mode || (f.log("TEXT", "DISPLAYED: " + this.displayedMemory.getDisplayText(!0)), this.outputDataUpdate()) + }, t.prototype.ccRCL = function() { + f.log("INFO", "RCL - Resume Caption Loading"), this.setMode("MODE_POP-ON") + }, t.prototype.ccBS = function() { + f.log("INFO", "BS - BackSpace"), "MODE_TEXT" !== this.mode && (this.writeScreen.backSpace(), this.writeScreen === this.displayedMemory && this.outputDataUpdate()) + }, t.prototype.ccAOF = function() {}, t.prototype.ccAON = function() {}, t.prototype.ccDER = function() { + f.log("INFO", "DER- Delete to End of Row"), this.writeScreen.clearToEndOfRow(), this.outputDataUpdate() + }, t.prototype.ccRU = function(t) { + f.log("INFO", "RU(" + t + ") - Roll Up"), this.writeScreen = this.displayedMemory, this.setMode("MODE_ROLL-UP"), this.writeScreen.setRollUpRows(t) + }, t.prototype.ccFON = function() { + f.log("INFO", "FON - Flash On"), this.writeScreen.setPen({ + flash: !0 + }) + }, t.prototype.ccRDC = function() { + f.log("INFO", "RDC - Resume Direct Captioning"), this.setMode("MODE_PAINT-ON") + }, t.prototype.ccTR = function() { + f.log("INFO", "TR"), this.setMode("MODE_TEXT") + }, t.prototype.ccRTD = function() { + f.log("INFO", "RTD"), this.setMode("MODE_TEXT") + }, t.prototype.ccEDM = function() { + f.log("INFO", "EDM - Erase Displayed Memory"), this.displayedMemory.reset(), this.outputDataUpdate(!0) + }, t.prototype.ccCR = function() { + f.log("CR - Carriage Return"), this.writeScreen.rollUp(), this.outputDataUpdate(!0) + }, t.prototype.ccENM = function() { + f.log("INFO", "ENM - Erase Non-displayed Memory"), this.nonDisplayedMemory.reset() + }, t.prototype.ccEOC = function() { + if (f.log("INFO", "EOC - End Of Caption"), "MODE_POP-ON" === this.mode) { + var t = this.displayedMemory; + this.displayedMemory = this.nonDisplayedMemory, this.nonDisplayedMemory = t, this.writeScreen = this.nonDisplayedMemory, f.log("TEXT", "DISP: " + this.displayedMemory.getDisplayText()) + } + this.outputDataUpdate(!0) + }, t.prototype.ccTO = function(t) { + f.log("INFO", "TO(" + t + ") - Tab Offset"), this.writeScreen.moveCursor(t) + }, t.prototype.ccMIDROW = function(t) { + var e = { + flash: !1 + }; + if (e.underline = t % 2 == 1, e.italics = t >= 46, e.italics) e.foreground = "white"; + else { + var r = Math.floor(t / 2) - 16, + i = ["white", "green", "blue", "cyan", "red", "yellow", "magenta"]; + e.foreground = i[r] + } + f.log("INFO", "MIDROW: " + JSON.stringify(e)), this.writeScreen.setPen(e) + }, t.prototype.outputDataUpdate = function() { + var t = arguments.length > 0 && void 0 !== arguments[0] && arguments[0], + e = f.time; + null !== e && this.outputFilter && (null !== this.cueStartTime || this.displayedMemory.isEmpty() ? this.displayedMemory.equals(this.lastOutputScreen) || (this.outputFilter.newCue && (this.outputFilter.newCue(this.cueStartTime, e, this.lastOutputScreen), !0 === t && this.outputFilter.dispatchCue && this.outputFilter.dispatchCue()), this.cueStartTime = this.displayedMemory.isEmpty() ? null : e) : this.cueStartTime = e, this.lastOutputScreen.copy(this.displayedMemory)) + }, t.prototype.cueSplitAtTime = function(t) { + this.outputFilter && (this.displayedMemory.isEmpty() || (this.outputFilter.newCue && this.outputFilter.newCue(this.cueStartTime, t, this.displayedMemory), this.cueStartTime = t)) + }, t + }(), + E = function() { + function t(e, r, a) { + i(this, t), this.field = e || 1, this.outputs = [r, a], this.channels = [new b(1, r), new b(2, a)], this.currChNr = -1, this.lastCmdA = null, this.lastCmdB = null, this.bufferedData = [], this.startTime = null, this.lastTime = null, this.dataCounters = { + padding: 0, + char: 0, + cmd: 0, + other: 0 + } + } + return t.prototype.getHandler = function(t) { + return this.channels[t].getHandler() + }, t.prototype.setHandler = function(t, e) { + this.channels[t].setHandler(e) + }, t.prototype.addData = function(t, e) { + var r = void 0, + i = void 0, + a = void 0, + n = !1; + this.lastTime = t, f.setTime(t); + for (var o = 0; o < e.length; o += 2) + if (i = 127 & e[o], a = 127 & e[o + 1], 0 !== i || 0 !== a) { + if (f.log("DATA", "[" + p([e[o], e[o + 1]]) + "] -> (" + p([i, a]) + ")"), r = this.parseCmd(i, a), r || (r = this.parseMidrow(i, a)), r || (r = this.parsePAC(i, a)), r || (r = this.parseBackgroundAttributes(i, a)), !r && (n = this.parseChars(i, a))) + if (this.currChNr && this.currChNr >= 0) { + var s = this.channels[this.currChNr - 1]; + s.insertChars(n) + } else f.log("WARNING", "No channel found yet. TEXT-MODE?"); + r ? this.dataCounters.cmd += 2 : n ? this.dataCounters.char += 2 : (this.dataCounters.other += 2, f.log("WARNING", "Couldn't parse cleaned data " + p([i, a]) + " orig: " + p([e[o], e[o + 1]]))) + } else this.dataCounters.padding += 2 + }, t.prototype.parseCmd = function(t, e) { + var r = null, + i = (20 === t || 28 === t) && e >= 32 && e <= 47, + a = (23 === t || 31 === t) && e >= 33 && e <= 35; + if (!i && !a) return !1; + if (t === this.lastCmdA && e === this.lastCmdB) return this.lastCmdA = null, this.lastCmdB = null, f.log("DEBUG", "Repeated command (" + p([t, e]) + ") is dropped"), !0; + r = 20 === t || 23 === t ? 1 : 2; + var n = this.channels[r - 1]; + return 20 === t || 28 === t ? 32 === e ? n.ccRCL() : 33 === e ? n.ccBS() : 34 === e ? n.ccAOF() : 35 === e ? n.ccAON() : 36 === e ? n.ccDER() : 37 === e ? n.ccRU(2) : 38 === e ? n.ccRU(3) : 39 === e ? n.ccRU(4) : 40 === e ? n.ccFON() : 41 === e ? n.ccRDC() : 42 === e ? n.ccTR() : 43 === e ? n.ccRTD() : 44 === e ? n.ccEDM() : 45 === e ? n.ccCR() : 46 === e ? n.ccENM() : 47 === e && n.ccEOC() : n.ccTO(e - 32), this.lastCmdA = t, this.lastCmdB = e, this.currChNr = r, !0 + }, t.prototype.parseMidrow = function(t, e) { + var r = null; + if ((17 === t || 25 === t) && e >= 32 && e <= 47) { + if ((r = 17 === t ? 1 : 2) !== this.currChNr) return f.log("ERROR", "Mismatch channel in midrow parsing"), !1; + return this.channels[r - 1].ccMIDROW(e), f.log("DEBUG", "MIDROW (" + p([t, e]) + ")"), !0 + } + return !1 + }, t.prototype.parsePAC = function(t, e) { + var r = null, + i = null, + a = (t >= 17 && t <= 23 || t >= 25 && t <= 31) && e >= 64 && e <= 127, + n = (16 === t || 24 === t) && e >= 64 && e <= 95; + if (!a && !n) return !1; + if (t === this.lastCmdA && e === this.lastCmdB) return this.lastCmdA = null, this.lastCmdB = null, !0; + r = t <= 23 ? 1 : 2, i = e >= 64 && e <= 95 ? 1 === r ? l[t] : d[t] : 1 === r ? u[t] : c[t]; + var o = this.interpretPAC(i, e); + return this.channels[r - 1].setPAC(o), this.lastCmdA = t, this.lastCmdB = e, this.currChNr = r, !0 + }, t.prototype.interpretPAC = function(t, e) { + var r = e, + i = { + color: null, + italics: !1, + indent: null, + underline: !1, + row: t + }; + return r = e > 95 ? e - 96 : e - 64, i.underline = 1 == (1 & r), r <= 13 ? i.color = ["white", "green", "blue", "cyan", "red", "yellow", "magenta", "white"][Math.floor(r / 2)] : r <= 15 ? (i.italics = !0, i.color = "white") : i.indent = 4 * Math.floor((r - 16) / 2), i + }, t.prototype.parseChars = function(t, e) { + var r = null, + i = null, + a = null; + if (t >= 25 ? (r = 2, a = t - 8) : (r = 1, a = t), a >= 17 && a <= 19) { + var o = e; + o = 17 === a ? e + 80 : 18 === a ? e + 112 : e + 144, f.log("INFO", "Special char '" + n(o) + "' in channel " + r), i = [o] + } else t >= 32 && t <= 127 && (i = 0 === e ? [t] : [t, e]); + if (i) { + var s = p(i); + f.log("DEBUG", "Char codes = " + s.join(",")), this.lastCmdA = null, this.lastCmdB = null + } + return i + }, t.prototype.parseBackgroundAttributes = function(t, e) { + var r = void 0, + i = void 0, + a = void 0, + n = void 0, + o = (16 === t || 24 === t) && e >= 32 && e <= 47, + s = (23 === t || 31 === t) && e >= 45 && e <= 47; + return !(!o && !s) && (r = {}, 16 === t || 24 === t ? (i = Math.floor((e - 32) / 2), r.background = h[i], e % 2 == 1 && (r.background = r.background + "_semi")) : 45 === e ? r.background = "transparent" : (r.foreground = "black", 47 === e && (r.underline = !0)), a = t < 24 ? 1 : 2, n = this.channels[a - 1], n.setBkgData(r), this.lastCmdA = null, this.lastCmdB = null, !0) + }, t.prototype.reset = function() { + for (var t = 0; t < this.channels.length; t++) this.channels[t] && this.channels[t].reset(); + this.lastCmdA = null, this.lastCmdB = null + }, t.prototype.cueSplitAtTime = function(t) { + for (var e = 0; e < this.channels.length; e++) this.channels[e] && this.channels[e].cueSplitAtTime(t) + }, t + }(); + e.a = E + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + var a = function() { + function t(e, r) { + i(this, t), this.timelineController = e, this.trackName = r, this.startTime = null, this.endTime = null, this.screen = null + } + return t.prototype.dispatchCue = function() { + null !== this.startTime && (this.timelineController.addCues(this.trackName, this.startTime, this.endTime, this.screen), this.startTime = null) + }, t.prototype.newCue = function(t, e, r) { + (null === this.startTime || this.startTime > t) && (this.startTime = t), this.endTime = e, this.screen = r, this.timelineController.createCaptionsTrack(this.trackName) + }, t + }(); + e.a = a + }, function(t, e, r) { + "use strict"; + var i = r(27), + a = r(7), + n = function(t, e, r) { + return t.substr(r || 0, e.length) === e + }, + o = function(t) { + var e = parseInt(t.substr(-3)), + r = parseInt(t.substr(-6, 2)), + i = parseInt(t.substr(-9, 2)), + a = t.length > 9 ? parseInt(t.substr(0, t.indexOf(":"))) : 0; + return isNaN(e) || isNaN(r) || isNaN(i) || isNaN(a) ? -1 : (e += 1e3 * r, e += 6e4 * i, e += 36e5 * a) + }, + s = function(t) { + for (var e = 5381, r = t.length; r;) e = 33 * e ^ t.charCodeAt(--r); + return (e >>> 0).toString() + }, + l = function(t, e, r) { + var i = t[e], + a = t[i.prevCC]; + if (!a || !a.new && i.new) return t.ccOffset = t.presentationOffset = i.start, void(i.new = !1); + for (; a && a.new;) t.ccOffset += i.start - a.start, i.new = !1, i = a, a = t[i.prevCC]; + t.presentationOffset = r + }, + u = { + parse: function(t, e, r, u, d, c) { + var h = /\r\n|\n\r|\n|\r/g, + f = Object(a.b)(new Uint8Array(t)).trim().replace(h, "\n").split("\n"), + p = "00:00.000", + v = 0, + g = 0, + y = 0, + m = [], + b = void 0, + E = !0, + T = new i.a; + T.oncue = function(t) { + var e = r[u], + i = r.ccOffset; + e && e.new && (void 0 !== g ? i = r.ccOffset = e.start : l(r, u, y)), y && (i = y + r.ccOffset - r.presentationOffset), t.startTime += i - g, t.endTime += i - g, t.id = s(t.startTime.toString()) + s(t.endTime.toString()) + s(t.text), t.text = decodeURIComponent(encodeURIComponent(t.text)), t.endTime > 0 && m.push(t) + }, T.onparsingerror = function(t) { + b = t + }, T.onflush = function() { + if (b && c) return void c(b); + d(m) + }, f.forEach(function(t) { + if (E) { + if (n(t, "X-TIMESTAMP-MAP=")) { + E = !1, t.substr(16).split(",").forEach(function(t) { + n(t, "LOCAL:") ? p = t.substr(6) : n(t, "MPEGTS:") && (v = parseInt(t.substr(7))) + }); + try { + e = e < 0 ? e + 8589934592 : e, v -= e, g = o(p) / 1e3, y = v / 9e4, -1 === g && (b = new Error("Malformed X-TIMESTAMP-MAP: " + t)) + } catch (e) { + b = new Error("Malformed X-TIMESTAMP-MAP: " + t) + } + return + } + "" === t && (E = !1) + } + T.parse(t + "\n") + }), T.flush() + } + }; + e.a = u + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + + function a(t, e) { + if (!t) throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); + return !e || "object" != typeof e && "function" != typeof e ? t : e + } + + function n(t, e) { + if ("function" != typeof e && null !== e) throw new TypeError("Super expression must either be null or a function, not " + typeof e); + t.prototype = Object.create(e && e.prototype, { + constructor: { + value: t, + enumerable: !1, + writable: !0, + configurable: !0 + } + }), e && (Object.setPrototypeOf ? Object.setPrototypeOf(t, e) : t.__proto__ = e) + } + + function o(t) { + for (var e = [], r = 0; r < t.length; r++) "subtitles" === t[r].kind && e.push(t[r]); + return e + } + var s = r(1), + l = r(3), + u = r(0), + d = function() { + function t(t, e) { + for (var r = 0; r < e.length; r++) { + var i = e[r]; + i.enumerable = i.enumerable || !1, i.configurable = !0, "value" in i && (i.writable = !0), Object.defineProperty(t, i.key, i) + } + } + return function(e, r, i) { + return r && t(e.prototype, r), i && t(e, i), e + } + }(), + c = function(t) { + function e(r) { + i(this, e); + var n = a(this, t.call(this, r, s.a.MEDIA_ATTACHED, s.a.MEDIA_DETACHING, s.a.MANIFEST_LOADING, s.a.MANIFEST_LOADED, s.a.SUBTITLE_TRACK_LOADED)); + return n.tracks = [], n.trackId = -1, n.media = null, n.subtitleDisplay = !0, n + } + return n(e, t), e.prototype._onTextTracksChanged = function() { + if (this.media) { + for (var t = -1, e = o(this.media.textTracks), r = 0; r < e.length; r++) + if ("hidden" === e[r].mode) t = r; + else if ("showing" === e[r].mode) { + t = r; + break + } + this.subtitleTrack = t + } + }, e.prototype.destroy = function() { + l.a.prototype.destroy.call(this) + }, e.prototype.onMediaAttached = function(t) { + var e = this; + this.media = t.media, this.media && (this.queuedDefaultTrack && (this.subtitleTrack = this.queuedDefaultTrack, delete this.queuedDefaultTrack), this.trackChangeListener = this._onTextTracksChanged.bind(this), this.useTextTrackPolling = !(this.media.textTracks && "onchange" in this.media.textTracks), this.useTextTrackPolling ? this.subtitlePollingInterval = setInterval(function() { + e.trackChangeListener() + }, 500) : this.media.textTracks.addEventListener("change", this.trackChangeListener)) + }, e.prototype.onMediaDetaching = function() { + this.media && (this.useTextTrackPolling ? clearInterval(this.subtitlePollingInterval) : this.media.textTracks.removeEventListener("change", this.trackChangeListener), this.media = null) + }, e.prototype.onManifestLoading = function() { + this.tracks = [], this.trackId = -1 + }, e.prototype.onManifestLoaded = function(t) { + var e = this, + r = t.subtitles || []; + this.tracks = r, this.trackId = -1, this.hls.trigger(s.a.SUBTITLE_TRACKS_UPDATED, { + subtitleTracks: r + }), r.forEach(function(t) { + t.default && (e.media ? e.subtitleTrack = t.id : e.queuedDefaultTrack = t.id) + }) + }, e.prototype.onTick = function() { + var t = this.trackId, + e = this.tracks[t]; + if (e) { + var r = e.details; + r && !r.live || (u.b.log("(re)loading playlist for subtitle track " + t), this.hls.trigger(s.a.SUBTITLE_TRACK_LOADING, { + url: e.url, + id: t + })) + } + }, e.prototype.onSubtitleTrackLoaded = function(t) { + var e = this; + t.id < this.tracks.length && (u.b.log("subtitle track " + t.id + " loaded"), this.tracks[t.id].details = t.details, t.details.live && !this.timer && (this.timer = setInterval(function() { + e.onTick() + }, 1e3 * t.details.targetduration, this)), !t.details.live && this.timer && this._stopTimer()) + }, e.prototype.setSubtitleTrackInternal = function(t) { + var e = this.hls, + r = this.tracks; + if (!("number" != typeof t || t < -1 || t >= r.length) && (this._stopTimer(), this.trackId = t, u.b.log("switching to subtitle track " + t), e.trigger(s.a.SUBTITLE_TRACK_SWITCH, { + id: t + }), -1 !== t)) { + var i = r[t], + a = i.details; + a && !a.live || (u.b.log("(re)loading playlist for subtitle track " + t), e.trigger(s.a.SUBTITLE_TRACK_LOADING, { + url: i.url, + id: t + })) + } + }, e.prototype._stopTimer = function() { + this.timer && (clearInterval(this.timer), this.timer = null) + }, e.prototype._toggleTrackModes = function(t) { + var e = this.media, + r = this.subtitleDisplay, + i = this.trackId; + if (e) { + var a = o(e.textTracks); + if (-1 === t)[].slice.call(a).forEach(function(t) { + t.mode = "disabled" + }); + else { + var n = a[i]; + n && (n.mode = "disabled") + } + var s = a[t]; + s && (s.mode = r ? "showing" : "hidden") + } + }, d(e, [{ + key: "subtitleTracks", + get: function() { + return this.tracks + } + }, { + key: "subtitleTrack", + get: function() { + return this.trackId + }, + set: function(t) { + this.trackId !== t && (this._toggleTrackModes(t), this.setSubtitleTrackInternal(t)) + } + }]), e + }(l.a); + e.a = c + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + + function a(t, e) { + if (!t) throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); + return !e || "object" != typeof e && "function" != typeof e ? t : e + } + + function n(t, e) { + if ("function" != typeof e && null !== e) throw new TypeError("Super expression must either be null or a function, not " + typeof e); + t.prototype = Object.create(e && e.prototype, { + constructor: { + value: t, + enumerable: !1, + writable: !0, + configurable: !0 + } + }), e && (Object.setPrototypeOf ? Object.setPrototypeOf(t, e) : t.__proto__ = e) + } + var o = r(1), + s = r(0), + l = r(13), + u = r(8), + d = window, + c = d.performance, + h = { + STOPPED: "STOPPED", + IDLE: "IDLE", + KEY_LOADING: "KEY_LOADING", + FRAG_LOADING: "FRAG_LOADING" + }, + f = function(t) { + function e(r) { + i(this, e); + var n = a(this, t.call(this, r, o.a.MEDIA_ATTACHED, o.a.ERROR, o.a.KEY_LOADED, o.a.FRAG_LOADED, o.a.SUBTITLE_TRACKS_UPDATED, o.a.SUBTITLE_TRACK_SWITCH, o.a.SUBTITLE_TRACK_LOADED, o.a.SUBTITLE_FRAG_PROCESSED)); + return n.config = r.config, n.vttFragSNsProcessed = {}, n.vttFragQueues = void 0, n.currentlyProcessing = null, n.state = h.STOPPED, n.currentTrackId = -1, n.decrypter = new l.a(r.observer, r.config), n + } + return n(e, t), e.prototype.onHandlerDestroyed = function() { + this.state = h.STOPPED + }, e.prototype.clearVttFragQueues = function() { + var t = this; + this.vttFragQueues = {}, this.tracks.forEach(function(e) { + t.vttFragQueues[e.id] = [] + }) + }, e.prototype.nextFrag = function() { + if (null === this.currentlyProcessing && this.currentTrackId > -1 && this.vttFragQueues[this.currentTrackId].length) { + var t = this.currentlyProcessing = this.vttFragQueues[this.currentTrackId].shift(); + this.fragCurrent = t, this.hls.trigger(o.a.FRAG_LOADING, { + frag: t + }), this.state = h.FRAG_LOADING + } + }, e.prototype.onSubtitleFragProcessed = function(t) { + t.success && this.vttFragSNsProcessed[t.frag.trackId].push(t.frag.sn), this.currentlyProcessing = null, this.state = h.IDLE, this.nextFrag() + }, e.prototype.onMediaAttached = function() { + this.state = h.IDLE + }, e.prototype.onError = function(t) { + var e = t.frag; + e && "subtitle" !== e.type || this.currentlyProcessing && (this.currentlyProcessing = null, this.nextFrag()) + }, e.prototype.doTick = function() { + var t = this; + switch (this.state) { + case h.IDLE: + var e = this.tracks, + r = this.currentTrackId, + i = this.vttFragSNsProcessed[r], + a = this.vttFragQueues[r], + n = this.currentlyProcessing ? this.currentlyProcessing.sn : -1, + l = function(t) { + return i.indexOf(t.sn) > -1 + }, + u = function(t) { + return a.some(function(e) { + return e.sn === t.sn + }) + }; + if (!e) break; + var d; + if (r < e.length && (d = e[r].details), void 0 === d) break; + d.fragments.forEach(function(e) { + l(e) || e.sn === n || u(e) || (e.encrypted ? (s.b.log("Loading key for " + e.sn), t.state = h.KEY_LOADING, t.hls.trigger(o.a.KEY_LOADING, { + frag: e + })) : (e.trackId = r, a.push(e), t.nextFrag())) + }) + } + }, e.prototype.onSubtitleTracksUpdated = function(t) { + var e = this; + s.b.log("subtitle tracks updated"), this.tracks = t.subtitleTracks, this.clearVttFragQueues(), this.vttFragSNsProcessed = {}, this.tracks.forEach(function(t) { + e.vttFragSNsProcessed[t.id] = [] + }) + }, e.prototype.onSubtitleTrackSwitch = function(t) { + if (this.currentTrackId = t.id, this.tracks && -1 !== this.currentTrackId) { + var e = this.tracks[this.currentTrackId]; + e && e.details && this.tick() + } + }, e.prototype.onSubtitleTrackLoaded = function() { + this.tick() + }, e.prototype.onKeyLoaded = function() { + this.state === h.KEY_LOADING && (this.state = h.IDLE, this.tick()) + }, e.prototype.onFragLoaded = function(t) { + var e = this.fragCurrent, + r = t.frag.decryptdata, + i = t.frag, + a = this.hls; + if (this.state === h.FRAG_LOADING && e && "subtitle" === t.frag.type && e.sn === t.frag.sn && t.payload.byteLength > 0 && null != r && null != r.key && "AES-128" === r.method) { + var n = void 0; + try { + n = c.now() + } catch (t) { + n = Date.now() + } + this.decrypter.decrypt(t.payload, r.key.buffer, r.iv.buffer, function(t) { + var e = void 0; + try { + e = c.now() + } catch (t) { + e = Date.now() + } + a.trigger(o.a.FRAG_DECRYPTED, { + frag: i, + payload: t, + stats: { + tstart: n, + tdecrypt: e + } + }) + }) + } + }, e + }(u.a); + e.a = f + }, function(t, e, r) { + "use strict"; + + function i(t, e) { + if (!(t instanceof e)) throw new TypeError("Cannot call a class as a function") + } + + function a(t, e) { + if (!t) throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); + return !e || "object" != typeof e && "function" != typeof e ? t : e + } + + function n(t, e) { + if ("function" != typeof e && null !== e) throw new TypeError("Super expression must either be null or a function, not " + typeof e); + t.prototype = Object.create(e && e.prototype, { + constructor: { + value: t, + enumerable: !1, + writable: !0, + configurable: !0 + } + }), e && (Object.setPrototypeOf ? Object.setPrototypeOf(t, e) : t.__proto__ = e) + } + var o = r(3), + s = r(1), + l = r(2), + u = r(0), + d = function() { + function t(t, e) { + for (var r = 0; r < e.length; r++) { + var i = e[r]; + i.enumerable = i.enumerable || !1, i.configurable = !0, "value" in i && (i.writable = !0), Object.defineProperty(t, i.key, i) + } + } + return function(e, r, i) { + return r && t(e.prototype, r), i && t(e, i), e + } + }(), + c = window, + h = c.XMLHttpRequest, + f = { + WIDEVINE: "com.widevine.alpha", + PLAYREADY: "com.microsoft.playready" + }, + p = function(t, e, r) { + var i = { + videoCapabilities: [] + }; + return e.forEach(function(t) { + i.videoCapabilities.push({ + contentType: 'video/mp4; codecs="' + t + '"' + }) + }), [i] + }, + v = function(t, e, r) { + switch (t) { + case f.WIDEVINE: + return p(0, r); + default: + throw Error("Unknown key-system: " + t) + } + }, + g = function(t) { + function e(r) { + i(this, e); + var n = a(this, t.call(this, r, s.a.MEDIA_ATTACHED, s.a.MANIFEST_PARSED)); + return n._widevineLicenseUrl = r.config.widevineLicenseUrl, n._licenseXhrSetup = r.config.licenseXhrSetup, n._emeEnabled = r.config.emeEnabled, n._requestMediaKeySystemAccess = r.config.requestMediaKeySystemAccessFunc, n._mediaKeysList = [], n._media = null, n._hasSetMediaKeys = !1, n._isMediaEncrypted = !1, n._requestLicenseFailureCount = 0, n + } + return n(e, t), e.prototype.getLicenseServerUrl = function(t) { + var e = void 0; + switch (t) { + case f.WIDEVINE: + e = this._widevineLicenseUrl; + break; + default: + e = null + } + return e || (u.b.error('No license server URL configured for key-system "' + t + '"'), this.hls.trigger(s.a.ERROR, { + type: l.b.KEY_SYSTEM_ERROR, + details: l.a.KEY_SYSTEM_LICENSE_REQUEST_FAILED, + fatal: !0 + })), e + }, e.prototype._attemptKeySystemAccess = function(t, e, r) { + var i = this, + a = v(t, 0, r); + if (!a) return void u.b.warn("Can not create config for key-system (maybe because platform is not supported):", t); + u.b.log("Requesting encrypted media key-system access"), this.requestMediaKeySystemAccess(t, a).then(function(e) { + i._onMediaKeySystemAccessObtained(t, e) + }).catch(function(e) { + u.b.error('Failed to obtain key-system "' + t + '" access:', e) + }) + }, e.prototype._onMediaKeySystemAccessObtained = function(t, e) { + var r = this; + u.b.log('Access for key-system "' + t + '" obtained'); + var i = { + mediaKeys: null, + mediaKeysSession: null, + mediaKeysSessionInitialized: !1, + mediaKeySystemAccess: e, + mediaKeySystemDomain: t + }; + this._mediaKeysList.push(i), e.createMediaKeys().then(function(e) { + i.mediaKeys = e, u.b.log('Media-keys created for key-system "' + t + '"'), r._onMediaKeysCreated() + }).catch(function(t) { + u.b.error("Failed to create media-keys:", t) + }) + }, e.prototype._onMediaKeysCreated = function() { + var t = this; + this._mediaKeysList.forEach(function(e) { + e.mediaKeysSession || (e.mediaKeysSession = e.mediaKeys.createSession(), t._onNewMediaKeySession(e.mediaKeysSession)) + }) + }, e.prototype._onNewMediaKeySession = function(t) { + var e = this; + u.b.log("New key-system session " + t.sessionId), t.addEventListener("message", function(r) { + e._onKeySessionMessage(t, r.message) + }, !1) + }, e.prototype._onKeySessionMessage = function(t, e) { + u.b.log("Got EME message event, creating license request"), this._requestLicense(e, function(e) { + u.b.log("Received license data, updating key-session"), t.update(e) + }) + }, e.prototype._onMediaEncrypted = function(t, e) { + u.b.log('Media is encrypted using "' + t + '" init data type'), this._isMediaEncrypted = !0, this._mediaEncryptionInitDataType = t, this._mediaEncryptionInitData = e, this._attemptSetMediaKeys(), this._generateRequestWithPreferredKeySession() + }, e.prototype._attemptSetMediaKeys = function() { + if (!this._hasSetMediaKeys) { + var t = this._mediaKeysList[0]; + if (!t || !t.mediaKeys) return u.b.error("Fatal: Media is encrypted but no CDM access or no keys have been obtained yet"), void this.hls.trigger(s.a.ERROR, { + type: l.b.KEY_SYSTEM_ERROR, + details: l.a.KEY_SYSTEM_NO_KEYS, + fatal: !0 + }); + u.b.log("Setting keys for encrypted media"), this._media.setMediaKeys(t.mediaKeys), this._hasSetMediaKeys = !0 + } + }, e.prototype._generateRequestWithPreferredKeySession = function() { + var t = this, + e = this._mediaKeysList[0]; + if (!e) return u.b.error("Fatal: Media is encrypted but not any key-system access has been obtained yet"), void this.hls.trigger(s.a.ERROR, { + type: l.b.KEY_SYSTEM_ERROR, + details: l.a.KEY_SYSTEM_NO_ACCESS, + fatal: !0 + }); + if (e.mediaKeysSessionInitialized) return void u.b.warn("Key-Session already initialized but requested again"); + var r = e.mediaKeysSession; + r || (u.b.error("Fatal: Media is encrypted but no key-session existing"), this.hls.trigger(s.a.ERROR, { + type: l.b.KEY_SYSTEM_ERROR, + details: l.a.KEY_SYSTEM_NO_SESSION, + fatal: !0 + })); + var i = this._mediaEncryptionInitDataType, + a = this._mediaEncryptionInitData; + u.b.log('Generating key-session request for "' + i + '" init data type'), e.mediaKeysSessionInitialized = !0, r.generateRequest(i, a).then(function() { + u.b.debug("Key-session generation succeeded") + }).catch(function(e) { + u.b.error("Error generating key-session request:", e), t.hls.trigger(s.a.ERROR, { + type: l.b.KEY_SYSTEM_ERROR, + details: l.a.KEY_SYSTEM_NO_SESSION, + fatal: !1 + }) + }) + }, e.prototype._createLicenseXhr = function(t, e, r) { + var i = new h, + a = this._licenseXhrSetup; + try { + if (a) try { + a(i, t) + } catch (e) { + i.open("POST", t, !0), a(i, t) + } + i.readyState || i.open("POST", t, !0) + } catch (t) { + return u.b.error("Error setting up key-system license XHR", t), void this.hls.trigger(s.a.ERROR, { + type: l.b.KEY_SYSTEM_ERROR, + details: l.a.KEY_SYSTEM_LICENSE_REQUEST_FAILED, + fatal: !0 + }) + } + return i.responseType = "arraybuffer", i.onreadystatechange = this._onLicenseRequestReadyStageChange.bind(this, i, t, e, r), i + }, e.prototype._onLicenseRequestReadyStageChange = function(t, e, r, i) { + switch (t.readyState) { + case 4: + if (200 === t.status) this._requestLicenseFailureCount = 0, u.b.log("License request succeeded"), i(t.response); + else { + if (u.b.error("License Request XHR failed (" + e + "). Status: " + t.status + " (" + t.statusText + ")"), ++this._requestLicenseFailureCount <= 3) { + var a = 3 - this._requestLicenseFailureCount + 1; + return u.b.warn("Retrying license request, " + a + " attempts left"), void this._requestLicense(r, i) + } + this.hls.trigger(s.a.ERROR, { + type: l.b.KEY_SYSTEM_ERROR, + details: l.a.KEY_SYSTEM_LICENSE_REQUEST_FAILED, + fatal: !0 + }) + } + } + }, e.prototype._generateLicenseRequestChallenge = function(t, e) { + var r = void 0; + return t.mediaKeySystemDomain === f.PLAYREADY ? u.b.error("PlayReady is not supported (yet)") : t.mediaKeySystemDomain === f.WIDEVINE ? r = e : u.b.error("Unsupported key-system:", t.mediaKeySystemDomain), r + }, e.prototype._requestLicense = function(t, e) { + u.b.log("Requesting content license for key-system"); + var r = this._mediaKeysList[0]; + if (!r) return u.b.error("Fatal error: Media is encrypted but no key-system access has been obtained yet"), void this.hls.trigger(s.a.ERROR, { + type: l.b.KEY_SYSTEM_ERROR, + details: l.a.KEY_SYSTEM_NO_ACCESS, + fatal: !0 + }); + var i = this.getLicenseServerUrl(r.mediaKeySystemDomain), + a = this._createLicenseXhr(i, t, e); + u.b.log("Sending license request to URL: " + i), a.send(this._generateLicenseRequestChallenge(r, t)) + }, e.prototype.onMediaAttached = function(t) { + var e = this; + if (this._emeEnabled) { + var r = t.media; + this._media = r, r.addEventListener("encrypted", function(t) { + e._onMediaEncrypted(t.initDataType, t.initData) + }) + } + }, e.prototype.onManifestParsed = function(t) { + if (this._emeEnabled) { + var e = t.levels.map(function(t) { + return t.audioCodec + }), + r = t.levels.map(function(t) { + return t.videoCodec + }); + this._attemptKeySystemAccess(f.WIDEVINE, e, r) + } + }, d(e, [{ + key: "requestMediaKeySystemAccess", + get: function() { + if (!this._requestMediaKeySystemAccess) throw new Error("No requestMediaKeySystemAccess function configured"); + return this._requestMediaKeySystemAccess + } + }]), e + }(o.a); + e.a = g + }, function(t, e, r) { + "use strict"; + r.d(e, "a", function() { + return i + }); + var i = function() { + return "undefined" != typeof window && window.navigator && window.navigator.requestMediaKeySystemAccess ? window.navigator.requestMediaKeySystemAccess.bind(window.navigator) : null + }() + }, function(t, e) { /*! http://mths.be/endswith v0.2.0 by @mathias */ + String.prototype.endsWith || function() { + "use strict"; + var t = function() { + try { + var t = {}, + e = Object.defineProperty, + r = e(t, t, t) && e + } catch (t) {} + return r + }(), + e = {}.toString, + r = function(t) { + if (null == this) throw TypeError(); + var r = String(this); + if (t && "[object RegExp]" == e.call(t)) throw TypeError(); + var i = r.length, + a = String(t), + n = a.length, + o = i; + if (arguments.length > 1) { + var s = arguments[1]; + void 0 !== s && (o = s ? Number(s) : 0) != o && (o = 0) + } + var l = Math.min(Math.max(o, 0), i), + u = l - n; + if (u < 0) return !1; + for (var d = -1; ++d < n;) + if (r.charCodeAt(u + d) != a.charCodeAt(d)) return !1; + return !0 + }; + t ? t(String.prototype, "endsWith", { + value: r, + configurable: !0, + writable: !0 + }) : String.prototype.endsWith = r + }() + }]).default +}); //# sourceMappingURL=hls.min.js.map \ No newline at end of file diff --git a/dashboard-ui/bower_components/howlerjs/dist/howler.min.js b/dashboard-ui/bower_components/howlerjs/dist/howler.min.js index 13aba88692..4896ac8ece 100644 --- a/dashboard-ui/bower_components/howlerjs/dist/howler.min.js +++ b/dashboard-ui/bower_components/howlerjs/dist/howler.min.js @@ -1,4 +1,853 @@ -/*! howler.js v2.0.14 | (c) 2013-2018, James Simpson of GoldFire Studios | MIT License | howlerjs.com */ -!function(){"use strict";var e=function(){this.init()};e.prototype={init:function(){var e=this||n;return e._counter=1e3,e._codecs={},e._howls=[],e._muted=!1,e._volume=1,e._canPlayEvent="canplaythrough",e._navigator="undefined"!=typeof window&&window.navigator?window.navigator:null,e.masterGain=null,e.noAudio=!1,e.usingWebAudio=!0,e.autoSuspend=!0,e.ctx=null,e.mobileAutoEnable=!0,e._setup(),e},volume:function(e){var o=this||n;if(e=parseFloat(e),o.ctx||_(),void 0!==e&&e>=0&&e<=1){if(o._volume=e,o._muted)return o;o.usingWebAudio&&o.masterGain.gain.setValueAtTime(e,n.ctx.currentTime);for(var t=0;t=0;o--)e._howls[o].unload();return e.usingWebAudio&&e.ctx&&void 0!==e.ctx.close&&(e.ctx.close(),e.ctx=null,_()),e},codecs:function(e){return(this||n)._codecs[e.replace(/^x-/,"")]},_setup:function(){var e=this||n;if(e.state=e.ctx?e.ctx.state||"running":"running",e._autoSuspend(),!e.usingWebAudio)if("undefined"!=typeof Audio)try{var o=new Audio;void 0===o.oncanplaythrough&&(e._canPlayEvent="canplay")}catch(n){e.noAudio=!0}else e.noAudio=!0;try{var o=new Audio;o.muted&&(e.noAudio=!0)}catch(e){}return e.noAudio||e._setupCodecs(),e},_setupCodecs:function(){var e=this||n,o=null;try{o="undefined"!=typeof Audio?new Audio:null}catch(n){return e}if(!o||"function"!=typeof o.canPlayType)return e;var t=o.canPlayType("audio/mpeg;").replace(/^no$/,""),r=e._navigator&&e._navigator.userAgent.match(/OPR\/([0-6].)/g),a=r&&parseInt(r[0].split("/")[1],10)<33;return e._codecs={mp3:!(a||!t&&!o.canPlayType("audio/mp3;").replace(/^no$/,"")),mpeg:!!t,opus:!!o.canPlayType('audio/ogg; codecs="opus"').replace(/^no$/,""),ogg:!!o.canPlayType('audio/ogg; codecs="vorbis"').replace(/^no$/,""),oga:!!o.canPlayType('audio/ogg; codecs="vorbis"').replace(/^no$/,""),wav:!!o.canPlayType('audio/wav; codecs="1"').replace(/^no$/,""),aac:!!o.canPlayType("audio/aac;").replace(/^no$/,""),caf:!!o.canPlayType("audio/x-caf;").replace(/^no$/,""),m4a:!!(o.canPlayType("audio/x-m4a;")||o.canPlayType("audio/m4a;")||o.canPlayType("audio/aac;")).replace(/^no$/,""),mp4:!!(o.canPlayType("audio/x-mp4;")||o.canPlayType("audio/mp4;")||o.canPlayType("audio/aac;")).replace(/^no$/,""),weba:!!o.canPlayType('audio/webm; codecs="vorbis"').replace(/^no$/,""),webm:!!o.canPlayType('audio/webm; codecs="vorbis"').replace(/^no$/,""),dolby:!!o.canPlayType('audio/mp4; codecs="ec-3"').replace(/^no$/,""),flac:!!(o.canPlayType("audio/x-flac;")||o.canPlayType("audio/flac;")).replace(/^no$/,"")},e},_enableMobileAudio:function(){var e=this||n,o=/iPhone|iPad|iPod|Android|BlackBerry|BB10|Silk|Mobi|Chrome/i.test(e._navigator&&e._navigator.userAgent);if(!e._mobileEnabled&&e.ctx&&o){e._mobileEnabled=!1,e.mobileAutoEnable=!1,e._mobileUnloaded||44100===e.ctx.sampleRate||(e._mobileUnloaded=!0,e.unload()),e._scratchBuffer=e.ctx.createBuffer(1,1,22050);var t=function(o){o.preventDefault(),n._autoResume();var r=e.ctx.createBufferSource();r.buffer=e._scratchBuffer,r.connect(e.ctx.destination),void 0===r.start?r.noteOn(0):r.start(0),"function"==typeof e.ctx.resume&&e.ctx.resume(),r.onended=function(){r.disconnect(0),e._mobileEnabled=!0,document.removeEventListener("touchstart",t,!0),document.removeEventListener("touchend",t,!0),document.removeEventListener("click",t,!0);for(var n=0;n0?i._seek:t._sprite[e][0]/1e3),s=Math.max(0,(t._sprite[e][0]+t._sprite[e][1])/1e3-_),l=1e3*s/Math.abs(i._rate);if(i._paused=!1,i._ended=!1,i._sprite=e,i._seek=_,i._start=t._sprite[e][0]/1e3,i._stop=(t._sprite[e][0]+t._sprite[e][1])/1e3,i._loop=!(!i._loop&&!t._sprite[e][2]),i._seek>=i._stop)return void t._ended(i);var c=i._node;if(t._webAudio){var f=function(){t._refreshBuffer(i);var e=i._muted||t._muted?0:i._volume;c.gain.setValueAtTime(e,n.ctx.currentTime),i._playStart=n.ctx.currentTime,void 0===c.bufferSource.start?i._loop?c.bufferSource.noteGrainOn(0,_,86400):c.bufferSource.noteGrainOn(0,_,s):i._loop?c.bufferSource.start(0,_,86400):c.bufferSource.start(0,_,s),l!==1/0&&(t._endTimers[i._id]=setTimeout(t._ended.bind(t,i),l)),o||setTimeout(function(){t._emit("play",i._id)},0)};"running"===n.state?f():(t.once("resume",f),t._clearTimer(i._id))}else{var p=function(){c.currentTime=_,c.muted=i._muted||t._muted||n._muted||c.muted,c.volume=i._volume*n.volume(),c.playbackRate=i._rate;try{var r=c.play();if("undefined"!=typeof Promise&&(r instanceof Promise||"function"==typeof r.then)?(t._playLock=!0,r.then(function(){t._playLock=!1,o||t._emit("play",i._id)}).catch(function(){t._playLock=!1,t._emit("playerror",i._id,"Playback was unable to start. This is most commonly an issue on mobile devices and Chrome where playback was not within a user interaction.")})):o||t._emit("play",i._id),c.playbackRate=i._rate,c.paused)return void t._emit("playerror",i._id,"Playback was unable to start. This is most commonly an issue on mobile devices and Chrome where playback was not within a user interaction.");"__default"!==e||i._loop?t._endTimers[i._id]=setTimeout(t._ended.bind(t,i),l):(t._endTimers[i._id]=function(){t._ended(i),c.removeEventListener("ended",t._endTimers[i._id],!1)},c.addEventListener("ended",t._endTimers[i._id],!1))}catch(e){t._emit("playerror",i._id,e)}},m=window&&window.ejecta||!c.readyState&&n._navigator.isCocoonJS;if(c.readyState>=3||m)p();else{var v=function(){p(),c.removeEventListener(n._canPlayEvent,v,!1)};c.addEventListener(n._canPlayEvent,v,!1),t._clearTimer(i._id)}}return i._id},pause:function(e){var n=this;if("loaded"!==n._state||n._playLock)return n._queue.push({event:"pause",action:function(){n.pause(e)}}),n;for(var o=n._getSoundIds(e),t=0;t=0?o=parseInt(r[0],10):e=parseFloat(r[0])}else r.length>=2&&(e=parseFloat(r[0]),o=parseInt(r[1],10));var a;if(!(void 0!==e&&e>=0&&e<=1))return a=o?t._soundById(o):t._sounds[0],a?a._volume:0;if("loaded"!==t._state||t._playLock)return t._queue.push({event:"volume",action:function(){t.volume.apply(t,r)}}),t;void 0===o&&(t._volume=e),o=t._getSoundIds(o);for(var u=0;u0?t/_:t),l=Date.now();e._fadeTo=o,e._interval=setInterval(function(){var r=(Date.now()-l)/t;l=Date.now(),i+=d*r,i=Math.max(0,i),i=Math.min(1,i),i=Math.round(100*i)/100,u._webAudio?e._volume=i:u.volume(i,e._id,!0),a&&(u._volume=i),(on&&i>=o)&&(clearInterval(e._interval),e._interval=null,e._fadeTo=null,u.volume(o,e._id),u._emit("fade",e._id))},s)},_stopFade:function(e){var o=this,t=o._soundById(e);return t&&t._interval&&(o._webAudio&&t._node.gain.cancelScheduledValues(n.ctx.currentTime),clearInterval(t._interval),t._interval=null,o.volume(t._fadeTo,e),t._fadeTo=null,o._emit("fade",e)),o},loop:function(){var e,n,o,t=this,r=arguments;if(0===r.length)return t._loop;if(1===r.length){if("boolean"!=typeof r[0])return!!(o=t._soundById(parseInt(r[0],10)))&&o._loop;e=r[0],t._loop=e}else 2===r.length&&(e=r[0],n=parseInt(r[1],10));for(var a=t._getSoundIds(n),u=0;u=0?o=parseInt(r[0],10):e=parseFloat(r[0])}else 2===r.length&&(e=parseFloat(r[0]),o=parseInt(r[1],10));var i;if("number"!=typeof e)return i=t._soundById(o),i?i._rate:t._rate;if("loaded"!==t._state||t._playLock)return t._queue.push({event:"rate",action:function(){t.rate.apply(t,r)}}),t;void 0===o&&(t._rate=e),o=t._getSoundIds(o);for(var d=0;d=0?o=parseInt(r[0],10):t._sounds.length&&(o=t._sounds[0]._id,e=parseFloat(r[0]))}else 2===r.length&&(e=parseFloat(r[0]),o=parseInt(r[1],10));if(void 0===o)return t;if("loaded"!==t._state||t._playLock)return t._queue.push({event:"seek",action:function(){t.seek.apply(t,r)}}),t;var i=t._soundById(o);if(i){if(!("number"==typeof e&&e>=0)){if(t._webAudio){var d=t.playing(o)?n.ctx.currentTime-i._playStart:0,_=i._rateSeek?i._rateSeek-i._seek:0;return i._seek+(_+d*Math.abs(i._rate))}return i._node.currentTime}var s=t.playing(o);s&&t.pause(o,!0),i._seek=e,i._ended=!1,t._clearTimer(o),!t._webAudio&&i._node&&(i._node.currentTime=e);var l=function(){t._emit("seek",o),s&&t.play(o,!0)};if(s&&!t._webAudio){var c=function(){t._playLock?setTimeout(c,0):l()};setTimeout(c,0)}else l()}return t},playing:function(e){var n=this;if("number"==typeof e){var o=n._soundById(e);return!!o&&!o._paused}for(var t=0;t=0&&n._howls.splice(a,1);var u=!0;for(t=0;t=0;a--)r[a].id&&r[a].id!==n&&"load"!==e||(setTimeout(function(e){e.call(this,n,o)}.bind(t,r[a].fn),0),r[a].once&&t.off(e,r[a].fn,r[a].id));return t._loadQueue(e),t},_loadQueue:function(e){var n=this;if(n._queue.length>0){var o=n._queue[0];o.event===e&&(n._queue.shift(),n._loadQueue()),e||o.action()}return n},_ended:function(e){var o=this,t=e._sprite;if(!o._webAudio&&e._node&&!e._node.paused&&!e._node.ended&&e._node.currentTime=0;t--){if(o<=n)return;e._sounds[t]._ended&&(e._webAudio&&e._sounds[t]._node&&e._sounds[t]._node.disconnect(0),e._sounds.splice(t,1),o--)}}},_getSoundIds:function(e){var n=this;if(void 0===e){for(var o=[],t=0;t0?(r[o._src]=e,d(o,e)):onError()},a=function(){o._emit("loaderror",null,"Decoding audio data failed.")};"undefined"!=typeof Promise&&1===n.ctx.decodeAudioData.length?n.ctx.decodeAudioData(e).then(t).catch(a):n.ctx.decodeAudioData(e,t,a)},d=function(e,n){n&&!e._duration&&(e._duration=n.duration),0===Object.keys(e._sprite).length&&(e._sprite={__default:[0,1e3*e._duration]}),"loaded"!==e._state&&(e._state="loaded",e._emit("load"),e._loadQueue())},_=function(){try{"undefined"!=typeof AudioContext?n.ctx=new AudioContext:"undefined"!=typeof webkitAudioContext?n.ctx=new webkitAudioContext:n.usingWebAudio=!1}catch(e){n.usingWebAudio=!1}var e=/iP(hone|od|ad)/.test(n._navigator&&n._navigator.platform),o=n._navigator&&n._navigator.appVersion.match(/OS (\d+)_(\d+)_?(\d+)?/),t=o?parseInt(o[1],10):null;if(e&&t&&t<9){var r=/safari/.test(n._navigator&&n._navigator.userAgent.toLowerCase());(n._navigator&&n._navigator.standalone&&!r||n._navigator&&!n._navigator.standalone&&!r)&&(n.usingWebAudio=!1)}n.usingWebAudio&&(n.masterGain=void 0===n.ctx.createGain?n.ctx.createGainNode():n.ctx.createGain(),n.masterGain.gain.setValueAtTime(n._muted?0:1,n.ctx.currentTime),n.masterGain.connect(n.ctx.destination)),n._setup()};"function"==typeof define&&define.amd&&define([],function(){return{Howler:n,Howl:o}}),"undefined"!=typeof exports&&(exports.Howler=n,exports.Howl=o),"undefined"!=typeof window?(window.HowlerGlobal=e,window.Howler=n,window.Howl=o,window.Sound=t):"undefined"!=typeof global&&(global.HowlerGlobal=e,global.Howler=n,global.Howl=o,global.Sound=t)}(); +/*! howler.js v2.0.14 | (c) 2013-2018, James Simpson of GoldFire Studios | MIT License | howlerjs.com */ ! function() { + "use strict"; + var e = function() { + this.init() + }; + e.prototype = { + init: function() { + var e = this || n; + return e._counter = 1e3, e._codecs = {}, e._howls = [], e._muted = !1, e._volume = 1, e._canPlayEvent = "canplaythrough", e._navigator = "undefined" != typeof window && window.navigator ? window.navigator : null, e.masterGain = null, e.noAudio = !1, e.usingWebAudio = !0, e.autoSuspend = !0, e.ctx = null, e.mobileAutoEnable = !0, e._setup(), e + }, + volume: function(e) { + var o = this || n; + if (e = parseFloat(e), o.ctx || _(), void 0 !== e && e >= 0 && e <= 1) { + if (o._volume = e, o._muted) return o; + o.usingWebAudio && o.masterGain.gain.setValueAtTime(e, n.ctx.currentTime); + for (var t = 0; t < o._howls.length; t++) + if (!o._howls[t]._webAudio) + for (var r = o._howls[t]._getSoundIds(), a = 0; a < r.length; a++) { + var u = o._howls[t]._soundById(r[a]); + u && u._node && (u._node.volume = u._volume * e) + } + return o + } + return o._volume + }, + mute: function(e) { + var o = this || n; + o.ctx || _(), o._muted = e, o.usingWebAudio && o.masterGain.gain.setValueAtTime(e ? 0 : o._volume, n.ctx.currentTime); + for (var t = 0; t < o._howls.length; t++) + if (!o._howls[t]._webAudio) + for (var r = o._howls[t]._getSoundIds(), a = 0; a < r.length; a++) { + var u = o._howls[t]._soundById(r[a]); + u && u._node && (u._node.muted = !!e || u._muted) + } + return o + }, + unload: function() { + for (var e = this || n, o = e._howls.length - 1; o >= 0; o--) e._howls[o].unload(); + return e.usingWebAudio && e.ctx && void 0 !== e.ctx.close && (e.ctx.close(), e.ctx = null, _()), e + }, + codecs: function(e) { + return (this || n)._codecs[e.replace(/^x-/, "")] + }, + _setup: function() { + var e = this || n; + if (e.state = e.ctx ? e.ctx.state || "running" : "running", e._autoSuspend(), !e.usingWebAudio) + if ("undefined" != typeof Audio) try { + var o = new Audio; + void 0 === o.oncanplaythrough && (e._canPlayEvent = "canplay") + } catch (n) { + e.noAudio = !0 + } else e.noAudio = !0; + try { + var o = new Audio; + o.muted && (e.noAudio = !0) + } catch (e) {} + return e.noAudio || e._setupCodecs(), e + }, + _setupCodecs: function() { + var e = this || n, + o = null; + try { + o = "undefined" != typeof Audio ? new Audio : null + } catch (n) { + return e + } + if (!o || "function" != typeof o.canPlayType) return e; + var t = o.canPlayType("audio/mpeg;").replace(/^no$/, ""), + r = e._navigator && e._navigator.userAgent.match(/OPR\/([0-6].)/g), + a = r && parseInt(r[0].split("/")[1], 10) < 33; + return e._codecs = { + mp3: !(a || !t && !o.canPlayType("audio/mp3;").replace(/^no$/, "")), + mpeg: !!t, + opus: !!o.canPlayType('audio/ogg; codecs="opus"').replace(/^no$/, ""), + ogg: !!o.canPlayType('audio/ogg; codecs="vorbis"').replace(/^no$/, ""), + oga: !!o.canPlayType('audio/ogg; codecs="vorbis"').replace(/^no$/, ""), + wav: !!o.canPlayType('audio/wav; codecs="1"').replace(/^no$/, ""), + aac: !!o.canPlayType("audio/aac;").replace(/^no$/, ""), + caf: !!o.canPlayType("audio/x-caf;").replace(/^no$/, ""), + m4a: !!(o.canPlayType("audio/x-m4a;") || o.canPlayType("audio/m4a;") || o.canPlayType("audio/aac;")).replace(/^no$/, ""), + mp4: !!(o.canPlayType("audio/x-mp4;") || o.canPlayType("audio/mp4;") || o.canPlayType("audio/aac;")).replace(/^no$/, ""), + weba: !!o.canPlayType('audio/webm; codecs="vorbis"').replace(/^no$/, ""), + webm: !!o.canPlayType('audio/webm; codecs="vorbis"').replace(/^no$/, ""), + dolby: !!o.canPlayType('audio/mp4; codecs="ec-3"').replace(/^no$/, ""), + flac: !!(o.canPlayType("audio/x-flac;") || o.canPlayType("audio/flac;")).replace(/^no$/, "") + }, e + }, + _enableMobileAudio: function() { + var e = this || n, + o = /iPhone|iPad|iPod|Android|BlackBerry|BB10|Silk|Mobi|Chrome/i.test(e._navigator && e._navigator.userAgent); + if (!e._mobileEnabled && e.ctx && o) { + e._mobileEnabled = !1, e.mobileAutoEnable = !1, e._mobileUnloaded || 44100 === e.ctx.sampleRate || (e._mobileUnloaded = !0, e.unload()), e._scratchBuffer = e.ctx.createBuffer(1, 1, 22050); + var t = function(o) { + o.preventDefault(), n._autoResume(); + var r = e.ctx.createBufferSource(); + r.buffer = e._scratchBuffer, r.connect(e.ctx.destination), void 0 === r.start ? r.noteOn(0) : r.start(0), "function" == typeof e.ctx.resume && e.ctx.resume(), r.onended = function() { + r.disconnect(0), e._mobileEnabled = !0, document.removeEventListener("touchstart", t, !0), document.removeEventListener("touchend", t, !0), document.removeEventListener("click", t, !0); + for (var n = 0; n < e._howls.length; n++) e._howls[n]._emit("unlock") + } + }; + return document.addEventListener("touchstart", t, !0), document.addEventListener("touchend", t, !0), document.addEventListener("click", t, !0), e + } + }, + _autoSuspend: function() { + var e = this; + if (e.autoSuspend && e.ctx && void 0 !== e.ctx.suspend && n.usingWebAudio) { + for (var o = 0; o < e._howls.length; o++) + if (e._howls[o]._webAudio) + for (var t = 0; t < e._howls[o]._sounds.length; t++) + if (!e._howls[o]._sounds[t]._paused) return e; + return e._suspendTimer && clearTimeout(e._suspendTimer), e._suspendTimer = setTimeout(function() { + e.autoSuspend && (e._suspendTimer = null, e.state = "suspending", e.ctx.suspend().then(function() { + e.state = "suspended", e._resumeAfterSuspend && (delete e._resumeAfterSuspend, e._autoResume()) + })) + }, 3e4), e + } + }, + _autoResume: function() { + var e = this; + if (e.ctx && void 0 !== e.ctx.resume && n.usingWebAudio) return "running" === e.state && e._suspendTimer ? (clearTimeout(e._suspendTimer), e._suspendTimer = null) : "suspended" === e.state ? (e.ctx.resume().then(function() { + e.state = "running"; + for (var n = 0; n < e._howls.length; n++) e._howls[n]._emit("resume") + }), e._suspendTimer && (clearTimeout(e._suspendTimer), e._suspendTimer = null)) : "suspending" === e.state && (e._resumeAfterSuspend = !0), e + } + }; + var n = new e, + o = function(e) { + var n = this; + if (!e.src || 0 === e.src.length) return void console.error("An array of source files must be passed with any new Howl."); + n.init(e) + }; + o.prototype = { + init: function(e) { + var o = this; + return n.ctx || _(), o._autoplay = e.autoplay || !1, o._format = "string" != typeof e.format ? e.format : [e.format], o._html5 = e.html5 || !1, o._muted = e.mute || !1, o._loop = e.loop || !1, o._pool = e.pool || 5, o._preload = "boolean" != typeof e.preload || e.preload, o._rate = e.rate || 1, o._sprite = e.sprite || {}, o._src = "string" != typeof e.src ? e.src : [e.src], o._volume = void 0 !== e.volume ? e.volume : 1, o._xhrWithCredentials = e.xhrWithCredentials || !1, o._duration = 0, o._state = "unloaded", o._sounds = [], o._endTimers = {}, o._queue = [], o._playLock = !1, o._onend = e.onend ? [{ + fn: e.onend + }] : [], o._onfade = e.onfade ? [{ + fn: e.onfade + }] : [], o._onload = e.onload ? [{ + fn: e.onload + }] : [], o._onloaderror = e.onloaderror ? [{ + fn: e.onloaderror + }] : [], o._onplayerror = e.onplayerror ? [{ + fn: e.onplayerror + }] : [], o._onpause = e.onpause ? [{ + fn: e.onpause + }] : [], o._onplay = e.onplay ? [{ + fn: e.onplay + }] : [], o._onstop = e.onstop ? [{ + fn: e.onstop + }] : [], o._onmute = e.onmute ? [{ + fn: e.onmute + }] : [], o._onvolume = e.onvolume ? [{ + fn: e.onvolume + }] : [], o._onrate = e.onrate ? [{ + fn: e.onrate + }] : [], o._onseek = e.onseek ? [{ + fn: e.onseek + }] : [], o._onunlock = e.onunlock ? [{ + fn: e.onunlock + }] : [], o._onresume = [], o._webAudio = n.usingWebAudio && !o._html5, void 0 !== n.ctx && n.ctx && n.mobileAutoEnable && n._enableMobileAudio(), n._howls.push(o), o._autoplay && o._queue.push({ + event: "play", + action: function() { + o.play() + } + }), o._preload && o.load(), o + }, + load: function() { + var e = this, + o = null; + if (n.noAudio) return void e._emit("loaderror", null, "No audio support."); + "string" == typeof e._src && (e._src = [e._src]); + for (var r = 0; r < e._src.length; r++) { + var u, i; + if (e._format && e._format[r]) u = e._format[r]; + else { + if ("string" != typeof(i = e._src[r])) { + e._emit("loaderror", null, "Non-string found in selected audio sources - ignoring."); + continue + } + u = /^data:audio\/([^;,]+);/i.exec(i), u || (u = /\.([^.]+)$/.exec(i.split("?", 1)[0])), u && (u = u[1].toLowerCase()) + } + if (u || console.warn('No file extension was found. Consider using the "format" property or specify an extension.'), u && n.codecs(u)) { + o = e._src[r]; + break + } + } + return o ? (e._src = o, e._state = "loading", "https:" === window.location.protocol && "http:" === o.slice(0, 5) && (e._html5 = !0, e._webAudio = !1), new t(e), e._webAudio && a(e), e) : void e._emit("loaderror", null, "No codec support for selected audio sources.") + }, + play: function(e, o) { + var t = this, + r = null; + if ("number" == typeof e) r = e, e = null; + else { + if ("string" == typeof e && "loaded" === t._state && !t._sprite[e]) return null; + if (void 0 === e) { + e = "__default"; + for (var a = 0, u = 0; u < t._sounds.length; u++) t._sounds[u]._paused && !t._sounds[u]._ended && (a++, r = t._sounds[u]._id); + 1 === a ? e = null : r = null + } + } + var i = r ? t._soundById(r) : t._inactiveSound(); + if (!i) return null; + if (r && !e && (e = i._sprite || "__default"), "loaded" !== t._state) { + i._sprite = e, i._ended = !1; + var d = i._id; + return t._queue.push({ + event: "play", + action: function() { + t.play(d) + } + }), d + } + if (r && !i._paused) return o || t._loadQueue("play"), i._id; + t._webAudio && n._autoResume(); + var _ = Math.max(0, i._seek > 0 ? i._seek : t._sprite[e][0] / 1e3), + s = Math.max(0, (t._sprite[e][0] + t._sprite[e][1]) / 1e3 - _), + l = 1e3 * s / Math.abs(i._rate); + if (i._paused = !1, i._ended = !1, i._sprite = e, i._seek = _, i._start = t._sprite[e][0] / 1e3, i._stop = (t._sprite[e][0] + t._sprite[e][1]) / 1e3, i._loop = !(!i._loop && !t._sprite[e][2]), i._seek >= i._stop) return void t._ended(i); + var c = i._node; + if (t._webAudio) { + var f = function() { + t._refreshBuffer(i); + var e = i._muted || t._muted ? 0 : i._volume; + c.gain.setValueAtTime(e, n.ctx.currentTime), i._playStart = n.ctx.currentTime, void 0 === c.bufferSource.start ? i._loop ? c.bufferSource.noteGrainOn(0, _, 86400) : c.bufferSource.noteGrainOn(0, _, s) : i._loop ? c.bufferSource.start(0, _, 86400) : c.bufferSource.start(0, _, s), l !== 1 / 0 && (t._endTimers[i._id] = setTimeout(t._ended.bind(t, i), l)), o || setTimeout(function() { + t._emit("play", i._id) + }, 0) + }; + "running" === n.state ? f() : (t.once("resume", f), t._clearTimer(i._id)) + } else { + var p = function() { + c.currentTime = _, c.muted = i._muted || t._muted || n._muted || c.muted, c.volume = i._volume * n.volume(), c.playbackRate = i._rate; + try { + var r = c.play(); + if ("undefined" != typeof Promise && (r instanceof Promise || "function" == typeof r.then) ? (t._playLock = !0, r.then(function() { + t._playLock = !1, o || t._emit("play", i._id) + }).catch(function() { + t._playLock = !1, t._emit("playerror", i._id, "Playback was unable to start. This is most commonly an issue on mobile devices and Chrome where playback was not within a user interaction.") + })) : o || t._emit("play", i._id), c.playbackRate = i._rate, c.paused) return void t._emit("playerror", i._id, "Playback was unable to start. This is most commonly an issue on mobile devices and Chrome where playback was not within a user interaction."); + "__default" !== e || i._loop ? t._endTimers[i._id] = setTimeout(t._ended.bind(t, i), l) : (t._endTimers[i._id] = function() { + t._ended(i), c.removeEventListener("ended", t._endTimers[i._id], !1) + }, c.addEventListener("ended", t._endTimers[i._id], !1)) + } catch (e) { + t._emit("playerror", i._id, e) + } + }, + m = window && window.ejecta || !c.readyState && n._navigator.isCocoonJS; + if (c.readyState >= 3 || m) p(); + else { + var v = function() { + p(), c.removeEventListener(n._canPlayEvent, v, !1) + }; + c.addEventListener(n._canPlayEvent, v, !1), t._clearTimer(i._id) + } + } + return i._id + }, + pause: function(e) { + var n = this; + if ("loaded" !== n._state || n._playLock) return n._queue.push({ + event: "pause", + action: function() { + n.pause(e) + } + }), n; + for (var o = n._getSoundIds(e), t = 0; t < o.length; t++) { + n._clearTimer(o[t]); + var r = n._soundById(o[t]); + if (r && !r._paused && (r._seek = n.seek(o[t]), r._rateSeek = 0, r._paused = !0, n._stopFade(o[t]), r._node)) + if (n._webAudio) { + if (!r._node.bufferSource) continue; + void 0 === r._node.bufferSource.stop ? r._node.bufferSource.noteOff(0) : r._node.bufferSource.stop(0), n._cleanBuffer(r._node) + } else isNaN(r._node.duration) && r._node.duration !== 1 / 0 || r._node.pause(); + arguments[1] || n._emit("pause", r ? r._id : null) + } + return n + }, + stop: function(e, n) { + var o = this; + if ("loaded" !== o._state || o._playLock) return o._queue.push({ + event: "stop", + action: function() { + o.stop(e) + } + }), o; + for (var t = o._getSoundIds(e), r = 0; r < t.length; r++) { + o._clearTimer(t[r]); + var a = o._soundById(t[r]); + a && (a._seek = a._start || 0, a._rateSeek = 0, a._paused = !0, a._ended = !0, o._stopFade(t[r]), a._node && (o._webAudio ? a._node.bufferSource && (void 0 === a._node.bufferSource.stop ? a._node.bufferSource.noteOff(0) : a._node.bufferSource.stop(0), o._cleanBuffer(a._node)) : isNaN(a._node.duration) && a._node.duration !== 1 / 0 || (a._node.currentTime = a._start || 0, a._node.pause())), n || o._emit("stop", a._id)) + } + return o + }, + mute: function(e, o) { + var t = this; + if ("loaded" !== t._state || t._playLock) return t._queue.push({ + event: "mute", + action: function() { + t.mute(e, o) + } + }), t; + if (void 0 === o) { + if ("boolean" != typeof e) return t._muted; + t._muted = e + } + for (var r = t._getSoundIds(o), a = 0; a < r.length; a++) { + var u = t._soundById(r[a]); + u && (u._muted = e, u._interval && t._stopFade(u._id), t._webAudio && u._node ? u._node.gain.setValueAtTime(e ? 0 : u._volume, n.ctx.currentTime) : u._node && (u._node.muted = !!n._muted || e), t._emit("mute", u._id)) + } + return t + }, + volume: function() { + var e, o, t = this, + r = arguments; + if (0 === r.length) return t._volume; + if (1 === r.length || 2 === r.length && void 0 === r[1]) { + t._getSoundIds().indexOf(r[0]) >= 0 ? o = parseInt(r[0], 10) : e = parseFloat(r[0]) + } else r.length >= 2 && (e = parseFloat(r[0]), o = parseInt(r[1], 10)); + var a; + if (!(void 0 !== e && e >= 0 && e <= 1)) return a = o ? t._soundById(o) : t._sounds[0], a ? a._volume : 0; + if ("loaded" !== t._state || t._playLock) return t._queue.push({ + event: "volume", + action: function() { + t.volume.apply(t, r) + } + }), t; + void 0 === o && (t._volume = e), o = t._getSoundIds(o); + for (var u = 0; u < o.length; u++)(a = t._soundById(o[u])) && (a._volume = e, r[2] || t._stopFade(o[u]), t._webAudio && a._node && !a._muted ? a._node.gain.setValueAtTime(e, n.ctx.currentTime) : a._node && !a._muted && (a._node.volume = e * n.volume()), t._emit("volume", a._id)); + return t + }, + fade: function(e, o, t, r) { + var a = this; + if ("loaded" !== a._state || a._playLock) return a._queue.push({ + event: "fade", + action: function() { + a.fade(e, o, t, r) + } + }), a; + a.volume(e, r); + for (var u = a._getSoundIds(r), i = 0; i < u.length; i++) { + var d = a._soundById(u[i]); + if (d) { + if (r || a._stopFade(u[i]), a._webAudio && !d._muted) { + var _ = n.ctx.currentTime, + s = _ + t / 1e3; + d._volume = e, d._node.gain.setValueAtTime(e, _), d._node.gain.linearRampToValueAtTime(o, s) + } + a._startFadeInterval(d, e, o, t, u[i], void 0 === r) + } + } + return a + }, + _startFadeInterval: function(e, n, o, t, r, a) { + var u = this, + i = n, + d = o - n, + _ = Math.abs(d / .01), + s = Math.max(4, _ > 0 ? t / _ : t), + l = Date.now(); + e._fadeTo = o, e._interval = setInterval(function() { + var r = (Date.now() - l) / t; + l = Date.now(), i += d * r, i = Math.max(0, i), i = Math.min(1, i), i = Math.round(100 * i) / 100, u._webAudio ? e._volume = i : u.volume(i, e._id, !0), a && (u._volume = i), (o < n && i <= o || o > n && i >= o) && (clearInterval(e._interval), e._interval = null, e._fadeTo = null, u.volume(o, e._id), u._emit("fade", e._id)) + }, s) + }, + _stopFade: function(e) { + var o = this, + t = o._soundById(e); + return t && t._interval && (o._webAudio && t._node.gain.cancelScheduledValues(n.ctx.currentTime), clearInterval(t._interval), t._interval = null, o.volume(t._fadeTo, e), t._fadeTo = null, o._emit("fade", e)), o + }, + loop: function() { + var e, n, o, t = this, + r = arguments; + if (0 === r.length) return t._loop; + if (1 === r.length) { + if ("boolean" != typeof r[0]) return !!(o = t._soundById(parseInt(r[0], 10))) && o._loop; + e = r[0], t._loop = e + } else 2 === r.length && (e = r[0], n = parseInt(r[1], 10)); + for (var a = t._getSoundIds(n), u = 0; u < a.length; u++)(o = t._soundById(a[u])) && (o._loop = e, t._webAudio && o._node && o._node.bufferSource && (o._node.bufferSource.loop = e, e && (o._node.bufferSource.loopStart = o._start || 0, o._node.bufferSource.loopEnd = o._stop))); + return t + }, + rate: function() { + var e, o, t = this, + r = arguments; + if (0 === r.length) o = t._sounds[0]._id; + else if (1 === r.length) { + var a = t._getSoundIds(), + u = a.indexOf(r[0]); + u >= 0 ? o = parseInt(r[0], 10) : e = parseFloat(r[0]) + } else 2 === r.length && (e = parseFloat(r[0]), o = parseInt(r[1], 10)); + var i; + if ("number" != typeof e) return i = t._soundById(o), i ? i._rate : t._rate; + if ("loaded" !== t._state || t._playLock) return t._queue.push({ + event: "rate", + action: function() { + t.rate.apply(t, r) + } + }), t; + void 0 === o && (t._rate = e), o = t._getSoundIds(o); + for (var d = 0; d < o.length; d++) + if (i = t._soundById(o[d])) { + i._rateSeek = t.seek(o[d]), i._playStart = t._webAudio ? n.ctx.currentTime : i._playStart, i._rate = e, t._webAudio && i._node && i._node.bufferSource ? i._node.bufferSource.playbackRate.setValueAtTime(e, n.ctx.currentTime) : i._node && (i._node.playbackRate = e); + var _ = t.seek(o[d]), + s = (t._sprite[i._sprite][0] + t._sprite[i._sprite][1]) / 1e3 - _, + l = 1e3 * s / Math.abs(i._rate); + !t._endTimers[o[d]] && i._paused || (t._clearTimer(o[d]), t._endTimers[o[d]] = setTimeout(t._ended.bind(t, i), l)), t._emit("rate", i._id) + } return t + }, + seek: function() { + var e, o, t = this, + r = arguments; + if (0 === r.length) o = t._sounds[0]._id; + else if (1 === r.length) { + var a = t._getSoundIds(), + u = a.indexOf(r[0]); + u >= 0 ? o = parseInt(r[0], 10) : t._sounds.length && (o = t._sounds[0]._id, e = parseFloat(r[0])) + } else 2 === r.length && (e = parseFloat(r[0]), o = parseInt(r[1], 10)); + if (void 0 === o) return t; + if ("loaded" !== t._state || t._playLock) return t._queue.push({ + event: "seek", + action: function() { + t.seek.apply(t, r) + } + }), t; + var i = t._soundById(o); + if (i) { + if (!("number" == typeof e && e >= 0)) { + if (t._webAudio) { + var d = t.playing(o) ? n.ctx.currentTime - i._playStart : 0, + _ = i._rateSeek ? i._rateSeek - i._seek : 0; + return i._seek + (_ + d * Math.abs(i._rate)) + } + return i._node.currentTime + } + var s = t.playing(o); + s && t.pause(o, !0), i._seek = e, i._ended = !1, t._clearTimer(o), !t._webAudio && i._node && (i._node.currentTime = e); + var l = function() { + t._emit("seek", o), s && t.play(o, !0) + }; + if (s && !t._webAudio) { + var c = function() { + t._playLock ? setTimeout(c, 0) : l() + }; + setTimeout(c, 0) + } else l() + } + return t + }, + playing: function(e) { + var n = this; + if ("number" == typeof e) { + var o = n._soundById(e); + return !!o && !o._paused + } + for (var t = 0; t < n._sounds.length; t++) + if (!n._sounds[t]._paused) return !0; + return !1 + }, + duration: function(e) { + var n = this, + o = n._duration, + t = n._soundById(e); + return t && (o = n._sprite[t._sprite][1] / 1e3), o + }, + state: function() { + return this._state + }, + unload: function() { + for (var e = this, o = e._sounds, t = 0; t < o.length; t++) { + if (o[t]._paused || e.stop(o[t]._id), !e._webAudio) { + /MSIE |Trident\//.test(n._navigator && n._navigator.userAgent) || (o[t]._node.src = "data:audio/wav;base64,UklGRigAAABXQVZFZm10IBIAAAABAAEARKwAAIhYAQACABAAAABkYXRhAgAAAAEA"), o[t]._node.removeEventListener("error", o[t]._errorFn, !1), o[t]._node.removeEventListener(n._canPlayEvent, o[t]._loadFn, !1) + } + delete o[t]._node, e._clearTimer(o[t]._id) + } + var a = n._howls.indexOf(e); + a >= 0 && n._howls.splice(a, 1); + var u = !0; + for (t = 0; t < n._howls.length; t++) + if (n._howls[t]._src === e._src) { + u = !1; + break + } return r && u && delete r[e._src], n.noAudio = !1, e._state = "unloaded", e._sounds = [], e = null, null + }, + on: function(e, n, o, t) { + var r = this, + a = r["_on" + e]; + return "function" == typeof n && a.push(t ? { + id: o, + fn: n, + once: t + } : { + id: o, + fn: n + }), r + }, + off: function(e, n, o) { + var t = this, + r = t["_on" + e], + a = 0; + if ("number" == typeof n && (o = n, n = null), n || o) + for (a = 0; a < r.length; a++) { + var u = o === r[a].id; + if (n === r[a].fn && u || !n && u) { + r.splice(a, 1); + break + } + } else if (e) t["_on" + e] = []; + else { + var i = Object.keys(t); + for (a = 0; a < i.length; a++) 0 === i[a].indexOf("_on") && Array.isArray(t[i[a]]) && (t[i[a]] = []) + } return t + }, + once: function(e, n, o) { + var t = this; + return t.on(e, n, o, 1), t + }, + _emit: function(e, n, o) { + for (var t = this, r = t["_on" + e], a = r.length - 1; a >= 0; a--) r[a].id && r[a].id !== n && "load" !== e || (setTimeout(function(e) { + e.call(this, n, o) + }.bind(t, r[a].fn), 0), r[a].once && t.off(e, r[a].fn, r[a].id)); + return t._loadQueue(e), t + }, + _loadQueue: function(e) { + var n = this; + if (n._queue.length > 0) { + var o = n._queue[0]; + o.event === e && (n._queue.shift(), n._loadQueue()), e || o.action() + } + return n + }, + _ended: function(e) { + var o = this, + t = e._sprite; + if (!o._webAudio && e._node && !e._node.paused && !e._node.ended && e._node.currentTime < e._stop) return setTimeout(o._ended.bind(o, e), 100), o; + var r = !(!e._loop && !o._sprite[t][2]); + if (o._emit("end", e._id), !o._webAudio && r && o.stop(e._id, !0).play(e._id), o._webAudio && r) { + o._emit("play", e._id), e._seek = e._start || 0, e._rateSeek = 0, e._playStart = n.ctx.currentTime; + var a = 1e3 * (e._stop - e._start) / Math.abs(e._rate); + o._endTimers[e._id] = setTimeout(o._ended.bind(o, e), a) + } + return o._webAudio && !r && (e._paused = !0, e._ended = !0, e._seek = e._start || 0, e._rateSeek = 0, o._clearTimer(e._id), o._cleanBuffer(e._node), n._autoSuspend()), o._webAudio || r || o.stop(e._id, !0), o + }, + _clearTimer: function(e) { + var n = this; + if (n._endTimers[e]) { + if ("function" != typeof n._endTimers[e]) clearTimeout(n._endTimers[e]); + else { + var o = n._soundById(e); + o && o._node && o._node.removeEventListener("ended", n._endTimers[e], !1) + } + delete n._endTimers[e] + } + return n + }, + _soundById: function(e) { + for (var n = this, o = 0; o < n._sounds.length; o++) + if (e === n._sounds[o]._id) return n._sounds[o]; + return null + }, + _inactiveSound: function() { + var e = this; + e._drain(); + for (var n = 0; n < e._sounds.length; n++) + if (e._sounds[n]._ended) return e._sounds[n].reset(); + return new t(e) + }, + _drain: function() { + var e = this, + n = e._pool, + o = 0, + t = 0; + if (!(e._sounds.length < n)) { + for (t = 0; t < e._sounds.length; t++) e._sounds[t]._ended && o++; + for (t = e._sounds.length - 1; t >= 0; t--) { + if (o <= n) return; + e._sounds[t]._ended && (e._webAudio && e._sounds[t]._node && e._sounds[t]._node.disconnect(0), e._sounds.splice(t, 1), o--) + } + } + }, + _getSoundIds: function(e) { + var n = this; + if (void 0 === e) { + for (var o = [], t = 0; t < n._sounds.length; t++) o.push(n._sounds[t]._id); + return o + } + return [e] + }, + _refreshBuffer: function(e) { + var o = this; + return e._node.bufferSource = n.ctx.createBufferSource(), e._node.bufferSource.buffer = r[o._src], e._panner ? e._node.bufferSource.connect(e._panner) : e._node.bufferSource.connect(e._node), e._node.bufferSource.loop = e._loop, e._loop && (e._node.bufferSource.loopStart = e._start || 0, e._node.bufferSource.loopEnd = e._stop || 0), e._node.bufferSource.playbackRate.setValueAtTime(e._rate, n.ctx.currentTime), o + }, + _cleanBuffer: function(e) { + var o = this; + if (n._scratchBuffer && e.bufferSource) { + e.bufferSource.onended = null, e.bufferSource.disconnect(0); + try { + e.bufferSource.buffer = n._scratchBuffer + } catch (e) {} + } + return e.bufferSource = null, o + } + }; + var t = function(e) { + this._parent = e, this.init() + }; + t.prototype = { + init: function() { + var e = this, + o = e._parent; + return e._muted = o._muted, e._loop = o._loop, e._volume = o._volume, e._rate = o._rate, e._seek = 0, e._paused = !0, e._ended = !0, e._sprite = "__default", e._id = ++n._counter, o._sounds.push(e), e.create(), e + }, + create: function() { + var e = this, + o = e._parent, + t = n._muted || e._muted || e._parent._muted ? 0 : e._volume; + return o._webAudio ? (e._node = void 0 === n.ctx.createGain ? n.ctx.createGainNode() : n.ctx.createGain(), e._node.gain.setValueAtTime(t, n.ctx.currentTime), e._node.paused = !0, e._node.connect(n.masterGain)) : (e._node = new Audio, e._errorFn = e._errorListener.bind(e), e._node.addEventListener("error", e._errorFn, !1), e._loadFn = e._loadListener.bind(e), e._node.addEventListener(n._canPlayEvent, e._loadFn, !1), e._node.src = o._src, e._node.preload = "auto", e._node.volume = t * n.volume(), e._node.load()), e + }, + reset: function() { + var e = this, + o = e._parent; + return e._muted = o._muted, e._loop = o._loop, e._volume = o._volume, e._rate = o._rate, e._seek = 0, e._rateSeek = 0, e._paused = !0, e._ended = !0, e._sprite = "__default", e._id = ++n._counter, e + }, + _errorListener: function() { + var e = this; + e._parent._emit("loaderror", e._id, e._node.error ? e._node.error.code : 0), e._node.removeEventListener("error", e._errorFn, !1) + }, + _loadListener: function() { + var e = this, + o = e._parent; + o._duration = Math.ceil(10 * e._node.duration) / 10, 0 === Object.keys(o._sprite).length && (o._sprite = { + __default: [0, 1e3 * o._duration] + }), "loaded" !== o._state && (o._state = "loaded", o._emit("load"), o._loadQueue()), e._node.removeEventListener(n._canPlayEvent, e._loadFn, !1) + } + }; + var r = {}, + a = function(e) { + var n = e._src; + if (r[n]) return e._duration = r[n].duration, void d(e); + if (/^data:[^;]+;base64,/.test(n)) { + for (var o = atob(n.split(",")[1]), t = new Uint8Array(o.length), a = 0; a < o.length; ++a) t[a] = o.charCodeAt(a); + i(t.buffer, e) + } else { + var _ = new XMLHttpRequest; + _.open("GET", n, !0), _.withCredentials = e._xhrWithCredentials, _.responseType = "arraybuffer", _.onload = function() { + var n = (_.status + "")[0]; + if ("0" !== n && "2" !== n && "3" !== n) return void e._emit("loaderror", null, "Failed loading audio file with status: " + _.status + "."); + i(_.response, e) + }, _.onerror = function() { + e._webAudio && (e._html5 = !0, e._webAudio = !1, e._sounds = [], delete r[n], e.load()) + }, u(_) + } + }, + u = function(e) { + try { + e.send() + } catch (n) { + e.onerror() + } + }, + i = function(e, o) { + var t = function(e) { + e && o._sounds.length > 0 ? (r[o._src] = e, d(o, e)) : onError() + }, + a = function() { + o._emit("loaderror", null, "Decoding audio data failed.") + }; + "undefined" != typeof Promise && 1 === n.ctx.decodeAudioData.length ? n.ctx.decodeAudioData(e).then(t).catch(a) : n.ctx.decodeAudioData(e, t, a) + }, + d = function(e, n) { + n && !e._duration && (e._duration = n.duration), 0 === Object.keys(e._sprite).length && (e._sprite = { + __default: [0, 1e3 * e._duration] + }), "loaded" !== e._state && (e._state = "loaded", e._emit("load"), e._loadQueue()) + }, + _ = function() { + try { + "undefined" != typeof AudioContext ? n.ctx = new AudioContext : "undefined" != typeof webkitAudioContext ? n.ctx = new webkitAudioContext : n.usingWebAudio = !1 + } catch (e) { + n.usingWebAudio = !1 + } + var e = /iP(hone|od|ad)/.test(n._navigator && n._navigator.platform), + o = n._navigator && n._navigator.appVersion.match(/OS (\d+)_(\d+)_?(\d+)?/), + t = o ? parseInt(o[1], 10) : null; + if (e && t && t < 9) { + var r = /safari/.test(n._navigator && n._navigator.userAgent.toLowerCase()); + (n._navigator && n._navigator.standalone && !r || n._navigator && !n._navigator.standalone && !r) && (n.usingWebAudio = !1) + } + n.usingWebAudio && (n.masterGain = void 0 === n.ctx.createGain ? n.ctx.createGainNode() : n.ctx.createGain(), n.masterGain.gain.setValueAtTime(n._muted ? 0 : 1, n.ctx.currentTime), n.masterGain.connect(n.ctx.destination)), n._setup() + }; + "function" == typeof define && define.amd && define([], function() { + return { + Howler: n, + Howl: o + } + }), "undefined" != typeof exports && (exports.Howler = n, exports.Howl = o), "undefined" != typeof window ? (window.HowlerGlobal = e, window.Howler = n, window.Howl = o, window.Sound = t) : "undefined" != typeof global && (global.HowlerGlobal = e, global.Howler = n, global.Howl = o, global.Sound = t) +}(); /*! Spatial Plugin */ -!function(){"use strict";HowlerGlobal.prototype._pos=[0,0,0],HowlerGlobal.prototype._orientation=[0,0,-1,0,1,0],HowlerGlobal.prototype.stereo=function(e){var n=this;if(!n.ctx||!n.ctx.listener)return n;for(var t=n._howls.length-1;t>=0;t--)n._howls[t].stereo(e);return n},HowlerGlobal.prototype.pos=function(e,n,t){var r=this;return r.ctx&&r.ctx.listener?(n="number"!=typeof n?r._pos[1]:n,t="number"!=typeof t?r._pos[2]:t,"number"!=typeof e?r._pos:(r._pos=[e,n,t],void 0!==r.ctx.listener.positionX?(r.ctx.listener.positionX.setTargetAtTime(r._pos[0],Howler.ctx.currentTime,.1),r.ctx.listener.positionY.setTargetAtTime(r._pos[1],Howler.ctx.currentTime,.1),r.ctx.listener.positionZ.setTargetAtTime(r._pos[2],Howler.ctx.currentTime,.1)):r.ctx.listener.setPosition(r._pos[0],r._pos[1],r._pos[2]),r)):r},HowlerGlobal.prototype.orientation=function(e,n,t,r,o,i){var a=this;if(!a.ctx||!a.ctx.listener)return a;var p=a._orientation;return n="number"!=typeof n?p[1]:n,t="number"!=typeof t?p[2]:t,r="number"!=typeof r?p[3]:r,o="number"!=typeof o?p[4]:o,i="number"!=typeof i?p[5]:i,"number"!=typeof e?p:(a._orientation=[e,n,t,r,o,i],void 0!==a.ctx.listener.forwardX?(a.ctx.listener.forwardX.setTargetAtTime(e,Howler.ctx.currentTime,.1),a.ctx.listener.forwardY.setTargetAtTime(n,Howler.ctx.currentTime,.1),a.ctx.listener.forwardZ.setTargetAtTime(t,Howler.ctx.currentTime,.1),a.ctx.listener.upX.setTargetAtTime(e,Howler.ctx.currentTime,.1),a.ctx.listener.upY.setTargetAtTime(n,Howler.ctx.currentTime,.1),a.ctx.listener.upZ.setTargetAtTime(t,Howler.ctx.currentTime,.1)):a.ctx.listener.setOrientation(e,n,t,r,o,i),a)},Howl.prototype.init=function(e){return function(n){var t=this;return t._orientation=n.orientation||[1,0,0],t._stereo=n.stereo||null,t._pos=n.pos||null,t._pannerAttr={coneInnerAngle:void 0!==n.coneInnerAngle?n.coneInnerAngle:360,coneOuterAngle:void 0!==n.coneOuterAngle?n.coneOuterAngle:360,coneOuterGain:void 0!==n.coneOuterGain?n.coneOuterGain:0,distanceModel:void 0!==n.distanceModel?n.distanceModel:"inverse",maxDistance:void 0!==n.maxDistance?n.maxDistance:1e4,panningModel:void 0!==n.panningModel?n.panningModel:"HRTF",refDistance:void 0!==n.refDistance?n.refDistance:1,rolloffFactor:void 0!==n.rolloffFactor?n.rolloffFactor:1},t._onstereo=n.onstereo?[{fn:n.onstereo}]:[],t._onpos=n.onpos?[{fn:n.onpos}]:[],t._onorientation=n.onorientation?[{fn:n.onorientation}]:[],e.call(this,n)}}(Howl.prototype.init),Howl.prototype.stereo=function(n,t){var r=this;if(!r._webAudio)return r;if("loaded"!==r._state)return r._queue.push({event:"stereo",action:function(){r.stereo(n,t)}}),r;var o=void 0===Howler.ctx.createStereoPanner?"spatial":"stereo";if(void 0===t){if("number"!=typeof n)return r._stereo;r._stereo=n,r._pos=[n,0,0]}for(var i=r._getSoundIds(t),a=0;a= 0; t--) n._howls[t].stereo(e); + return n + }, HowlerGlobal.prototype.pos = function(e, n, t) { + var r = this; + return r.ctx && r.ctx.listener ? (n = "number" != typeof n ? r._pos[1] : n, t = "number" != typeof t ? r._pos[2] : t, "number" != typeof e ? r._pos : (r._pos = [e, n, t], void 0 !== r.ctx.listener.positionX ? (r.ctx.listener.positionX.setTargetAtTime(r._pos[0], Howler.ctx.currentTime, .1), r.ctx.listener.positionY.setTargetAtTime(r._pos[1], Howler.ctx.currentTime, .1), r.ctx.listener.positionZ.setTargetAtTime(r._pos[2], Howler.ctx.currentTime, .1)) : r.ctx.listener.setPosition(r._pos[0], r._pos[1], r._pos[2]), r)) : r + }, HowlerGlobal.prototype.orientation = function(e, n, t, r, o, i) { + var a = this; + if (!a.ctx || !a.ctx.listener) return a; + var p = a._orientation; + return n = "number" != typeof n ? p[1] : n, t = "number" != typeof t ? p[2] : t, r = "number" != typeof r ? p[3] : r, o = "number" != typeof o ? p[4] : o, i = "number" != typeof i ? p[5] : i, "number" != typeof e ? p : (a._orientation = [e, n, t, r, o, i], void 0 !== a.ctx.listener.forwardX ? (a.ctx.listener.forwardX.setTargetAtTime(e, Howler.ctx.currentTime, .1), a.ctx.listener.forwardY.setTargetAtTime(n, Howler.ctx.currentTime, .1), a.ctx.listener.forwardZ.setTargetAtTime(t, Howler.ctx.currentTime, .1), a.ctx.listener.upX.setTargetAtTime(e, Howler.ctx.currentTime, .1), a.ctx.listener.upY.setTargetAtTime(n, Howler.ctx.currentTime, .1), a.ctx.listener.upZ.setTargetAtTime(t, Howler.ctx.currentTime, .1)) : a.ctx.listener.setOrientation(e, n, t, r, o, i), a) + }, Howl.prototype.init = function(e) { + return function(n) { + var t = this; + return t._orientation = n.orientation || [1, 0, 0], t._stereo = n.stereo || null, t._pos = n.pos || null, t._pannerAttr = { + coneInnerAngle: void 0 !== n.coneInnerAngle ? n.coneInnerAngle : 360, + coneOuterAngle: void 0 !== n.coneOuterAngle ? n.coneOuterAngle : 360, + coneOuterGain: void 0 !== n.coneOuterGain ? n.coneOuterGain : 0, + distanceModel: void 0 !== n.distanceModel ? n.distanceModel : "inverse", + maxDistance: void 0 !== n.maxDistance ? n.maxDistance : 1e4, + panningModel: void 0 !== n.panningModel ? n.panningModel : "HRTF", + refDistance: void 0 !== n.refDistance ? n.refDistance : 1, + rolloffFactor: void 0 !== n.rolloffFactor ? n.rolloffFactor : 1 + }, t._onstereo = n.onstereo ? [{ + fn: n.onstereo + }] : [], t._onpos = n.onpos ? [{ + fn: n.onpos + }] : [], t._onorientation = n.onorientation ? [{ + fn: n.onorientation + }] : [], e.call(this, n) + } + }(Howl.prototype.init), Howl.prototype.stereo = function(n, t) { + var r = this; + if (!r._webAudio) return r; + if ("loaded" !== r._state) return r._queue.push({ + event: "stereo", + action: function() { + r.stereo(n, t) + } + }), r; + var o = void 0 === Howler.ctx.createStereoPanner ? "spatial" : "stereo"; + if (void 0 === t) { + if ("number" != typeof n) return r._stereo; + r._stereo = n, r._pos = [n, 0, 0] + } + for (var i = r._getSoundIds(t), a = 0; a < i.length; a++) { + var p = r._soundById(i[a]); + if (p) { + if ("number" != typeof n) return p._stereo; + p._stereo = n, p._pos = [n, 0, 0], p._node && (p._pannerAttr.panningModel = "equalpower", p._panner && p._panner.pan || e(p, o), "spatial" === o ? void 0 !== p._panner.positionX ? (p._panner.positionX.setValueAtTime(n, Howler.ctx.currentTime), p._panner.positionY.setValueAtTime(0, Howler.ctx.currentTime), p._panner.positionZ.setValueAtTime(0, Howler.ctx.currentTime)) : p._panner.setPosition(n, 0, 0) : p._panner.pan.setValueAtTime(n, Howler.ctx.currentTime)), r._emit("stereo", p._id) + } + } + return r + }, Howl.prototype.pos = function(n, t, r, o) { + var i = this; + if (!i._webAudio) return i; + if ("loaded" !== i._state) return i._queue.push({ + event: "pos", + action: function() { + i.pos(n, t, r, o) + } + }), i; + if (t = "number" != typeof t ? 0 : t, r = "number" != typeof r ? -.5 : r, void 0 === o) { + if ("number" != typeof n) return i._pos; + i._pos = [n, t, r] + } + for (var a = i._getSoundIds(o), p = 0; p < a.length; p++) { + var s = i._soundById(a[p]); + if (s) { + if ("number" != typeof n) return s._pos; + s._pos = [n, t, r], s._node && (s._panner && !s._panner.pan || e(s, "spatial"), void 0 !== s._panner.positionX ? (s._panner.positionX.setValueAtTime(n, Howler.ctx.currentTime), s._panner.positionY.setValueAtTime(t, Howler.ctx.currentTime), s._panner.positionZ.setValueAtTime(r, Howler.ctx.currentTime)) : s._panner.setOrientation(n, t, r)), i._emit("pos", s._id) + } + } + return i + }, Howl.prototype.orientation = function(n, t, r, o) { + var i = this; + if (!i._webAudio) return i; + if ("loaded" !== i._state) return i._queue.push({ + event: "orientation", + action: function() { + i.orientation(n, t, r, o) + } + }), i; + if (t = "number" != typeof t ? i._orientation[1] : t, r = "number" != typeof r ? i._orientation[2] : r, void 0 === o) { + if ("number" != typeof n) return i._orientation; + i._orientation = [n, t, r] + } + for (var a = i._getSoundIds(o), p = 0; p < a.length; p++) { + var s = i._soundById(a[p]); + if (s) { + if ("number" != typeof n) return s._orientation; + s._orientation = [n, t, r], s._node && (s._panner || (s._pos || (s._pos = i._pos || [0, 0, -.5]), e(s, "spatial")), void 0 !== s._panner.orientationX ? (s._panner.orientationX.setValueAtTime(n, Howler.ctx.currentTime), s._panner.orientationY.setValueAtTime(t, Howler.ctx.currentTime), s._panner.orientationZ.setValueAtTime(r, Howler.ctx.currentTime)) : s._panner.setOrientation(n, t, r)), i._emit("orientation", s._id) + } + } + return i + }, Howl.prototype.pannerAttr = function() { + var n, t, r, o = this, + i = arguments; + if (!o._webAudio) return o; + if (0 === i.length) return o._pannerAttr; + if (1 === i.length) { + if ("object" != typeof i[0]) return r = o._soundById(parseInt(i[0], 10)), r ? r._pannerAttr : o._pannerAttr; + n = i[0], void 0 === t && (n.pannerAttr || (n.pannerAttr = { + coneInnerAngle: n.coneInnerAngle, + coneOuterAngle: n.coneOuterAngle, + coneOuterGain: n.coneOuterGain, + distanceModel: n.distanceModel, + maxDistance: n.maxDistance, + refDistance: n.refDistance, + rolloffFactor: n.rolloffFactor, + panningModel: n.panningModel + }), o._pannerAttr = { + coneInnerAngle: void 0 !== n.pannerAttr.coneInnerAngle ? n.pannerAttr.coneInnerAngle : o._coneInnerAngle, + coneOuterAngle: void 0 !== n.pannerAttr.coneOuterAngle ? n.pannerAttr.coneOuterAngle : o._coneOuterAngle, + coneOuterGain: void 0 !== n.pannerAttr.coneOuterGain ? n.pannerAttr.coneOuterGain : o._coneOuterGain, + distanceModel: void 0 !== n.pannerAttr.distanceModel ? n.pannerAttr.distanceModel : o._distanceModel, + maxDistance: void 0 !== n.pannerAttr.maxDistance ? n.pannerAttr.maxDistance : o._maxDistance, + refDistance: void 0 !== n.pannerAttr.refDistance ? n.pannerAttr.refDistance : o._refDistance, + rolloffFactor: void 0 !== n.pannerAttr.rolloffFactor ? n.pannerAttr.rolloffFactor : o._rolloffFactor, + panningModel: void 0 !== n.pannerAttr.panningModel ? n.pannerAttr.panningModel : o._panningModel + }) + } else 2 === i.length && (n = i[0], t = parseInt(i[1], 10)); + for (var a = o._getSoundIds(t), p = 0; p < a.length; p++) + if (r = o._soundById(a[p])) { + var s = r._pannerAttr; + s = { + coneInnerAngle: void 0 !== n.coneInnerAngle ? n.coneInnerAngle : s.coneInnerAngle, + coneOuterAngle: void 0 !== n.coneOuterAngle ? n.coneOuterAngle : s.coneOuterAngle, + coneOuterGain: void 0 !== n.coneOuterGain ? n.coneOuterGain : s.coneOuterGain, + distanceModel: void 0 !== n.distanceModel ? n.distanceModel : s.distanceModel, + maxDistance: void 0 !== n.maxDistance ? n.maxDistance : s.maxDistance, + refDistance: void 0 !== n.refDistance ? n.refDistance : s.refDistance, + rolloffFactor: void 0 !== n.rolloffFactor ? n.rolloffFactor : s.rolloffFactor, + panningModel: void 0 !== n.panningModel ? n.panningModel : s.panningModel + }; + var c = r._panner; + c ? (c.coneInnerAngle = s.coneInnerAngle, c.coneOuterAngle = s.coneOuterAngle, c.coneOuterGain = s.coneOuterGain, c.distanceModel = s.distanceModel, c.maxDistance = s.maxDistance, c.refDistance = s.refDistance, c.rolloffFactor = s.rolloffFactor, c.panningModel = s.panningModel) : (r._pos || (r._pos = o._pos || [0, 0, -.5]), e(r, "spatial")) + } return o + }, Sound.prototype.init = function(e) { + return function() { + var n = this, + t = n._parent; + n._orientation = t._orientation, n._stereo = t._stereo, n._pos = t._pos, n._pannerAttr = t._pannerAttr, e.call(this), n._stereo ? t.stereo(n._stereo) : n._pos && t.pos(n._pos[0], n._pos[1], n._pos[2], n._id) + } + }(Sound.prototype.init), Sound.prototype.reset = function(e) { + return function() { + var n = this, + t = n._parent; + return n._orientation = t._orientation, n._stereo = t._stereo, n._pos = t._pos, n._pannerAttr = t._pannerAttr, n._stereo ? t.stereo(n._stereo) : n._pos ? t.pos(n._pos[0], n._pos[1], n._pos[2], n._id) : n._panner && (n._panner.disconnect(0), n._panner = void 0, t._refreshBuffer(n)), e.call(this) + } + }(Sound.prototype.reset); + var e = function(e, n) { + n = n || "spatial", "spatial" === n ? (e._panner = Howler.ctx.createPanner(), e._panner.coneInnerAngle = e._pannerAttr.coneInnerAngle, e._panner.coneOuterAngle = e._pannerAttr.coneOuterAngle, e._panner.coneOuterGain = e._pannerAttr.coneOuterGain, e._panner.distanceModel = e._pannerAttr.distanceModel, e._panner.maxDistance = e._pannerAttr.maxDistance, e._panner.refDistance = e._pannerAttr.refDistance, e._panner.rolloffFactor = e._pannerAttr.rolloffFactor, e._panner.panningModel = e._pannerAttr.panningModel, void 0 !== e._panner.positionX ? (e._panner.positionX.setValueAtTime(e._pos[0], Howler.ctx.currentTime), e._panner.positionY.setValueAtTime(e._pos[1], Howler.ctx.currentTime), e._panner.positionZ.setValueAtTime(e._pos[2], Howler.ctx.currentTime)) : e._panner.setPosition(e._pos[0], e._pos[1], e._pos[2]), void 0 !== e._panner.orientationX ? (e._panner.orientationX.setValueAtTime(e._orientation[0], Howler.ctx.currentTime), e._panner.orientationY.setValueAtTime(e._orientation[1], Howler.ctx.currentTime), e._panner.orientationZ.setValueAtTime(e._orientation[2], Howler.ctx.currentTime)) : e._panner.setOrientation(e._orientation[0], e._orientation[1], e._orientation[2])) : (e._panner = Howler.ctx.createStereoPanner(), e._panner.pan.setValueAtTime(e._stereo, Howler.ctx.currentTime)), e._panner.connect(e._node), e._paused || e._parent.pause(e._id, !0).play(e._id, !0) + } +}(); \ No newline at end of file diff --git a/dashboard-ui/bower_components/jquery/dist/jquery.slim.min.js b/dashboard-ui/bower_components/jquery/dist/jquery.slim.min.js index f4ca9b24ba..f1e8170650 100644 --- a/dashboard-ui/bower_components/jquery/dist/jquery.slim.min.js +++ b/dashboard-ui/bower_components/jquery/dist/jquery.slim.min.js @@ -1,2 +1,2607 @@ -/*! jQuery v3.3.1 -ajax,-ajax/jsonp,-ajax/load,-ajax/parseXML,-ajax/script,-ajax/var/location,-ajax/var/nonce,-ajax/var/rquery,-ajax/xhr,-manipulation/_evalUrl,-event/ajax,-effects,-effects/Tween,-effects/animatedSelector | (c) JS Foundation and other contributors | jquery.org/license */ -!function(e,t){"use strict";"object"==typeof module&&"object"==typeof module.exports?module.exports=e.document?t(e,!0):function(e){if(!e.document)throw new Error("jQuery requires a window with a document");return t(e)}:t(e)}("undefined"!=typeof window?window:this,function(e,t){"use strict";var n=[],r=e.document,i=Object.getPrototypeOf,o=n.slice,a=n.concat,u=n.push,s=n.indexOf,l={},c=l.toString,f=l.hasOwnProperty,d=f.toString,p=d.call(Object),h={},g=function e(t){return"function"==typeof t&&"number"!=typeof t.nodeType},v=function e(t){return null!=t&&t===t.window},y={type:!0,src:!0,noModule:!0};function m(e,t,n){var i,o=(t=t||r).createElement("script");if(o.text=e,n)for(i in y)n[i]&&(o[i]=n[i]);t.head.appendChild(o).parentNode.removeChild(o)}function b(e){return null==e?e+"":"object"==typeof e||"function"==typeof e?l[c.call(e)]||"object":typeof e}var x="3.3.1 -ajax,-ajax/jsonp,-ajax/load,-ajax/parseXML,-ajax/script,-ajax/var/location,-ajax/var/nonce,-ajax/var/rquery,-ajax/xhr,-manipulation/_evalUrl,-event/ajax,-effects,-effects/Tween,-effects/animatedSelector",w=function(e,t){return new w.fn.init(e,t)},C=/^[\s\uFEFF\xA0]+|[\s\uFEFF\xA0]+$/g;w.fn=w.prototype={jquery:x,constructor:w,length:0,toArray:function(){return o.call(this)},get:function(e){return null==e?o.call(this):e<0?this[e+this.length]:this[e]},pushStack:function(e){var t=w.merge(this.constructor(),e);return t.prevObject=this,t},each:function(e){return w.each(this,e)},map:function(e){return this.pushStack(w.map(this,function(t,n){return e.call(t,n,t)}))},slice:function(){return this.pushStack(o.apply(this,arguments))},first:function(){return this.eq(0)},last:function(){return this.eq(-1)},eq:function(e){var t=this.length,n=+e+(e<0?t:0);return this.pushStack(n>=0&&n0&&t-1 in e)}var E=function(e){var t,n,r,i,o,a,u,s,l,c,f,d,p,h,g,v,y,m,b,x="sizzle"+1*new Date,w=e.document,C=0,T=0,E=ae(),N=ae(),k=ae(),A=function(e,t){return e===t&&(f=!0),0},D={}.hasOwnProperty,S=[],L=S.pop,j=S.push,q=S.push,O=S.slice,P=function(e,t){for(var n=0,r=e.length;n+~]|"+I+")"+I+"*"),_=new RegExp("="+I+"*([^\\]'\"]*?)"+I+"*\\]","g"),U=new RegExp(M),V=new RegExp("^"+R+"$"),X={ID:new RegExp("^#("+R+")"),CLASS:new RegExp("^\\.("+R+")"),TAG:new RegExp("^("+R+"|[*])"),ATTR:new RegExp("^"+B),PSEUDO:new RegExp("^"+M),CHILD:new RegExp("^:(only|first|last|nth|nth-last)-(child|of-type)(?:\\("+I+"*(even|odd|(([+-]|)(\\d*)n|)"+I+"*(?:([+-]|)"+I+"*(\\d+)|))"+I+"*\\)|)","i"),bool:new RegExp("^(?:"+H+")$","i"),needsContext:new RegExp("^"+I+"*[>+~]|:(even|odd|eq|gt|lt|nth|first|last)(?:\\("+I+"*((?:-\\d)?\\d*)"+I+"*\\)|)(?=[^-]|$)","i")},Q=/^(?:input|select|textarea|button)$/i,Y=/^h\d$/i,G=/^[^{]+\{\s*\[native \w/,K=/^(?:#([\w-]+)|(\w+)|\.([\w-]+))$/,J=/[+~]/,Z=new RegExp("\\\\([\\da-f]{1,6}"+I+"?|("+I+")|.)","ig"),ee=function(e,t,n){var r="0x"+t-65536;return r!==r||n?t:r<0?String.fromCharCode(r+65536):String.fromCharCode(r>>10|55296,1023&r|56320)},te=/([\0-\x1f\x7f]|^-?\d)|^-$|[^\0-\x1f\x7f-\uFFFF\w-]/g,ne=function(e,t){return t?"\0"===e?"\ufffd":e.slice(0,-1)+"\\"+e.charCodeAt(e.length-1).toString(16)+" ":"\\"+e},re=function(){d()},ie=me(function(e){return!0===e.disabled&&("form"in e||"label"in e)},{dir:"parentNode",next:"legend"});try{q.apply(S=O.call(w.childNodes),w.childNodes),S[w.childNodes.length].nodeType}catch(e){q={apply:S.length?function(e,t){j.apply(e,O.call(t))}:function(e,t){var n=e.length,r=0;while(e[n++]=t[r++]);e.length=n-1}}}function oe(e,t,r,i){var o,u,l,c,f,h,y,m=t&&t.ownerDocument,C=t?t.nodeType:9;if(r=r||[],"string"!=typeof e||!e||1!==C&&9!==C&&11!==C)return r;if(!i&&((t?t.ownerDocument||t:w)!==p&&d(t),t=t||p,g)){if(11!==C&&(f=K.exec(e)))if(o=f[1]){if(9===C){if(!(l=t.getElementById(o)))return r;if(l.id===o)return r.push(l),r}else if(m&&(l=m.getElementById(o))&&b(t,l)&&l.id===o)return r.push(l),r}else{if(f[2])return q.apply(r,t.getElementsByTagName(e)),r;if((o=f[3])&&n.getElementsByClassName&&t.getElementsByClassName)return q.apply(r,t.getElementsByClassName(o)),r}if(n.qsa&&!k[e+" "]&&(!v||!v.test(e))){if(1!==C)m=t,y=e;else if("object"!==t.nodeName.toLowerCase()){(c=t.getAttribute("id"))?c=c.replace(te,ne):t.setAttribute("id",c=x),u=(h=a(e)).length;while(u--)h[u]="#"+c+" "+ye(h[u]);y=h.join(","),m=J.test(e)&&ge(t.parentNode)||t}if(y)try{return q.apply(r,m.querySelectorAll(y)),r}catch(e){}finally{c===x&&t.removeAttribute("id")}}}return s(e.replace($,"$1"),t,r,i)}function ae(){var e=[];function t(n,i){return e.push(n+" ")>r.cacheLength&&delete t[e.shift()],t[n+" "]=i}return t}function ue(e){return e[x]=!0,e}function se(e){var t=p.createElement("fieldset");try{return!!e(t)}catch(e){return!1}finally{t.parentNode&&t.parentNode.removeChild(t),t=null}}function le(e,t){var n=e.split("|"),i=n.length;while(i--)r.attrHandle[n[i]]=t}function ce(e,t){var n=t&&e,r=n&&1===e.nodeType&&1===t.nodeType&&e.sourceIndex-t.sourceIndex;if(r)return r;if(n)while(n=n.nextSibling)if(n===t)return-1;return e?1:-1}function fe(e){return function(t){return"input"===t.nodeName.toLowerCase()&&t.type===e}}function de(e){return function(t){var n=t.nodeName.toLowerCase();return("input"===n||"button"===n)&&t.type===e}}function pe(e){return function(t){return"form"in t?t.parentNode&&!1===t.disabled?"label"in t?"label"in t.parentNode?t.parentNode.disabled===e:t.disabled===e:t.isDisabled===e||t.isDisabled!==!e&&ie(t)===e:t.disabled===e:"label"in t&&t.disabled===e}}function he(e){return ue(function(t){return t=+t,ue(function(n,r){var i,o=e([],n.length,t),a=o.length;while(a--)n[i=o[a]]&&(n[i]=!(r[i]=n[i]))})})}function ge(e){return e&&"undefined"!=typeof e.getElementsByTagName&&e}n=oe.support={},o=oe.isXML=function(e){var t=e&&(e.ownerDocument||e).documentElement;return!!t&&"HTML"!==t.nodeName},d=oe.setDocument=function(e){var t,i,a=e?e.ownerDocument||e:w;return a!==p&&9===a.nodeType&&a.documentElement?(p=a,h=p.documentElement,g=!o(p),w!==p&&(i=p.defaultView)&&i.top!==i&&(i.addEventListener?i.addEventListener("unload",re,!1):i.attachEvent&&i.attachEvent("onunload",re)),n.attributes=se(function(e){return e.className="i",!e.getAttribute("className")}),n.getElementsByTagName=se(function(e){return e.appendChild(p.createComment("")),!e.getElementsByTagName("*").length}),n.getElementsByClassName=G.test(p.getElementsByClassName),n.getById=se(function(e){return h.appendChild(e).id=x,!p.getElementsByName||!p.getElementsByName(x).length}),n.getById?(r.filter.ID=function(e){var t=e.replace(Z,ee);return function(e){return e.getAttribute("id")===t}},r.find.ID=function(e,t){if("undefined"!=typeof t.getElementById&&g){var n=t.getElementById(e);return n?[n]:[]}}):(r.filter.ID=function(e){var t=e.replace(Z,ee);return function(e){var n="undefined"!=typeof e.getAttributeNode&&e.getAttributeNode("id");return n&&n.value===t}},r.find.ID=function(e,t){if("undefined"!=typeof t.getElementById&&g){var n,r,i,o=t.getElementById(e);if(o){if((n=o.getAttributeNode("id"))&&n.value===e)return[o];i=t.getElementsByName(e),r=0;while(o=i[r++])if((n=o.getAttributeNode("id"))&&n.value===e)return[o]}return[]}}),r.find.TAG=n.getElementsByTagName?function(e,t){return"undefined"!=typeof t.getElementsByTagName?t.getElementsByTagName(e):n.qsa?t.querySelectorAll(e):void 0}:function(e,t){var n,r=[],i=0,o=t.getElementsByTagName(e);if("*"===e){while(n=o[i++])1===n.nodeType&&r.push(n);return r}return o},r.find.CLASS=n.getElementsByClassName&&function(e,t){if("undefined"!=typeof t.getElementsByClassName&&g)return t.getElementsByClassName(e)},y=[],v=[],(n.qsa=G.test(p.querySelectorAll))&&(se(function(e){h.appendChild(e).innerHTML="",e.querySelectorAll("[msallowcapture^='']").length&&v.push("[*^$]="+I+"*(?:''|\"\")"),e.querySelectorAll("[selected]").length||v.push("\\["+I+"*(?:value|"+H+")"),e.querySelectorAll("[id~="+x+"-]").length||v.push("~="),e.querySelectorAll(":checked").length||v.push(":checked"),e.querySelectorAll("a#"+x+"+*").length||v.push(".#.+[+~]")}),se(function(e){e.innerHTML="";var t=p.createElement("input");t.setAttribute("type","hidden"),e.appendChild(t).setAttribute("name","D"),e.querySelectorAll("[name=d]").length&&v.push("name"+I+"*[*^$|!~]?="),2!==e.querySelectorAll(":enabled").length&&v.push(":enabled",":disabled"),h.appendChild(e).disabled=!0,2!==e.querySelectorAll(":disabled").length&&v.push(":enabled",":disabled"),e.querySelectorAll("*,:x"),v.push(",.*:")})),(n.matchesSelector=G.test(m=h.matches||h.webkitMatchesSelector||h.mozMatchesSelector||h.oMatchesSelector||h.msMatchesSelector))&&se(function(e){n.disconnectedMatch=m.call(e,"*"),m.call(e,"[s!='']:x"),y.push("!=",M)}),v=v.length&&new RegExp(v.join("|")),y=y.length&&new RegExp(y.join("|")),t=G.test(h.compareDocumentPosition),b=t||G.test(h.contains)?function(e,t){var n=9===e.nodeType?e.documentElement:e,r=t&&t.parentNode;return e===r||!(!r||1!==r.nodeType||!(n.contains?n.contains(r):e.compareDocumentPosition&&16&e.compareDocumentPosition(r)))}:function(e,t){if(t)while(t=t.parentNode)if(t===e)return!0;return!1},A=t?function(e,t){if(e===t)return f=!0,0;var r=!e.compareDocumentPosition-!t.compareDocumentPosition;return r||(1&(r=(e.ownerDocument||e)===(t.ownerDocument||t)?e.compareDocumentPosition(t):1)||!n.sortDetached&&t.compareDocumentPosition(e)===r?e===p||e.ownerDocument===w&&b(w,e)?-1:t===p||t.ownerDocument===w&&b(w,t)?1:c?P(c,e)-P(c,t):0:4&r?-1:1)}:function(e,t){if(e===t)return f=!0,0;var n,r=0,i=e.parentNode,o=t.parentNode,a=[e],u=[t];if(!i||!o)return e===p?-1:t===p?1:i?-1:o?1:c?P(c,e)-P(c,t):0;if(i===o)return ce(e,t);n=e;while(n=n.parentNode)a.unshift(n);n=t;while(n=n.parentNode)u.unshift(n);while(a[r]===u[r])r++;return r?ce(a[r],u[r]):a[r]===w?-1:u[r]===w?1:0},p):p},oe.matches=function(e,t){return oe(e,null,null,t)},oe.matchesSelector=function(e,t){if((e.ownerDocument||e)!==p&&d(e),t=t.replace(_,"='$1']"),n.matchesSelector&&g&&!k[t+" "]&&(!y||!y.test(t))&&(!v||!v.test(t)))try{var r=m.call(e,t);if(r||n.disconnectedMatch||e.document&&11!==e.document.nodeType)return r}catch(e){}return oe(t,p,null,[e]).length>0},oe.contains=function(e,t){return(e.ownerDocument||e)!==p&&d(e),b(e,t)},oe.attr=function(e,t){(e.ownerDocument||e)!==p&&d(e);var i=r.attrHandle[t.toLowerCase()],o=i&&D.call(r.attrHandle,t.toLowerCase())?i(e,t,!g):void 0;return void 0!==o?o:n.attributes||!g?e.getAttribute(t):(o=e.getAttributeNode(t))&&o.specified?o.value:null},oe.escape=function(e){return(e+"").replace(te,ne)},oe.error=function(e){throw new Error("Syntax error, unrecognized expression: "+e)},oe.uniqueSort=function(e){var t,r=[],i=0,o=0;if(f=!n.detectDuplicates,c=!n.sortStable&&e.slice(0),e.sort(A),f){while(t=e[o++])t===e[o]&&(i=r.push(o));while(i--)e.splice(r[i],1)}return c=null,e},i=oe.getText=function(e){var t,n="",r=0,o=e.nodeType;if(o){if(1===o||9===o||11===o){if("string"==typeof e.textContent)return e.textContent;for(e=e.firstChild;e;e=e.nextSibling)n+=i(e)}else if(3===o||4===o)return e.nodeValue}else while(t=e[r++])n+=i(t);return n},(r=oe.selectors={cacheLength:50,createPseudo:ue,match:X,attrHandle:{},find:{},relative:{">":{dir:"parentNode",first:!0}," ":{dir:"parentNode"},"+":{dir:"previousSibling",first:!0},"~":{dir:"previousSibling"}},preFilter:{ATTR:function(e){return e[1]=e[1].replace(Z,ee),e[3]=(e[3]||e[4]||e[5]||"").replace(Z,ee),"~="===e[2]&&(e[3]=" "+e[3]+" "),e.slice(0,4)},CHILD:function(e){return e[1]=e[1].toLowerCase(),"nth"===e[1].slice(0,3)?(e[3]||oe.error(e[0]),e[4]=+(e[4]?e[5]+(e[6]||1):2*("even"===e[3]||"odd"===e[3])),e[5]=+(e[7]+e[8]||"odd"===e[3])):e[3]&&oe.error(e[0]),e},PSEUDO:function(e){var t,n=!e[6]&&e[2];return X.CHILD.test(e[0])?null:(e[3]?e[2]=e[4]||e[5]||"":n&&U.test(n)&&(t=a(n,!0))&&(t=n.indexOf(")",n.length-t)-n.length)&&(e[0]=e[0].slice(0,t),e[2]=n.slice(0,t)),e.slice(0,3))}},filter:{TAG:function(e){var t=e.replace(Z,ee).toLowerCase();return"*"===e?function(){return!0}:function(e){return e.nodeName&&e.nodeName.toLowerCase()===t}},CLASS:function(e){var t=E[e+" "];return t||(t=new RegExp("(^|"+I+")"+e+"("+I+"|$)"))&&E(e,function(e){return t.test("string"==typeof e.className&&e.className||"undefined"!=typeof e.getAttribute&&e.getAttribute("class")||"")})},ATTR:function(e,t,n){return function(r){var i=oe.attr(r,e);return null==i?"!="===t:!t||(i+="","="===t?i===n:"!="===t?i!==n:"^="===t?n&&0===i.indexOf(n):"*="===t?n&&i.indexOf(n)>-1:"$="===t?n&&i.slice(-n.length)===n:"~="===t?(" "+i.replace(W," ")+" ").indexOf(n)>-1:"|="===t&&(i===n||i.slice(0,n.length+1)===n+"-"))}},CHILD:function(e,t,n,r,i){var o="nth"!==e.slice(0,3),a="last"!==e.slice(-4),u="of-type"===t;return 1===r&&0===i?function(e){return!!e.parentNode}:function(t,n,s){var l,c,f,d,p,h,g=o!==a?"nextSibling":"previousSibling",v=t.parentNode,y=u&&t.nodeName.toLowerCase(),m=!s&&!u,b=!1;if(v){if(o){while(g){d=t;while(d=d[g])if(u?d.nodeName.toLowerCase()===y:1===d.nodeType)return!1;h=g="only"===e&&!h&&"nextSibling"}return!0}if(h=[a?v.firstChild:v.lastChild],a&&m){b=(p=(l=(c=(f=(d=v)[x]||(d[x]={}))[d.uniqueID]||(f[d.uniqueID]={}))[e]||[])[0]===C&&l[1])&&l[2],d=p&&v.childNodes[p];while(d=++p&&d&&d[g]||(b=p=0)||h.pop())if(1===d.nodeType&&++b&&d===t){c[e]=[C,p,b];break}}else if(m&&(b=p=(l=(c=(f=(d=t)[x]||(d[x]={}))[d.uniqueID]||(f[d.uniqueID]={}))[e]||[])[0]===C&&l[1]),!1===b)while(d=++p&&d&&d[g]||(b=p=0)||h.pop())if((u?d.nodeName.toLowerCase()===y:1===d.nodeType)&&++b&&(m&&((c=(f=d[x]||(d[x]={}))[d.uniqueID]||(f[d.uniqueID]={}))[e]=[C,b]),d===t))break;return(b-=i)===r||b%r==0&&b/r>=0}}},PSEUDO:function(e,t){var n,i=r.pseudos[e]||r.setFilters[e.toLowerCase()]||oe.error("unsupported pseudo: "+e);return i[x]?i(t):i.length>1?(n=[e,e,"",t],r.setFilters.hasOwnProperty(e.toLowerCase())?ue(function(e,n){var r,o=i(e,t),a=o.length;while(a--)e[r=P(e,o[a])]=!(n[r]=o[a])}):function(e){return i(e,0,n)}):i}},pseudos:{not:ue(function(e){var t=[],n=[],r=u(e.replace($,"$1"));return r[x]?ue(function(e,t,n,i){var o,a=r(e,null,i,[]),u=e.length;while(u--)(o=a[u])&&(e[u]=!(t[u]=o))}):function(e,i,o){return t[0]=e,r(t,null,o,n),t[0]=null,!n.pop()}}),has:ue(function(e){return function(t){return oe(e,t).length>0}}),contains:ue(function(e){return e=e.replace(Z,ee),function(t){return(t.textContent||t.innerText||i(t)).indexOf(e)>-1}}),lang:ue(function(e){return V.test(e||"")||oe.error("unsupported lang: "+e),e=e.replace(Z,ee).toLowerCase(),function(t){var n;do{if(n=g?t.lang:t.getAttribute("xml:lang")||t.getAttribute("lang"))return(n=n.toLowerCase())===e||0===n.indexOf(e+"-")}while((t=t.parentNode)&&1===t.nodeType);return!1}}),target:function(t){var n=e.location&&e.location.hash;return n&&n.slice(1)===t.id},root:function(e){return e===h},focus:function(e){return e===p.activeElement&&(!p.hasFocus||p.hasFocus())&&!!(e.type||e.href||~e.tabIndex)},enabled:pe(!1),disabled:pe(!0),checked:function(e){var t=e.nodeName.toLowerCase();return"input"===t&&!!e.checked||"option"===t&&!!e.selected},selected:function(e){return e.parentNode&&e.parentNode.selectedIndex,!0===e.selected},empty:function(e){for(e=e.firstChild;e;e=e.nextSibling)if(e.nodeType<6)return!1;return!0},parent:function(e){return!r.pseudos.empty(e)},header:function(e){return Y.test(e.nodeName)},input:function(e){return Q.test(e.nodeName)},button:function(e){var t=e.nodeName.toLowerCase();return"input"===t&&"button"===e.type||"button"===t},text:function(e){var t;return"input"===e.nodeName.toLowerCase()&&"text"===e.type&&(null==(t=e.getAttribute("type"))||"text"===t.toLowerCase())},first:he(function(){return[0]}),last:he(function(e,t){return[t-1]}),eq:he(function(e,t,n){return[n<0?n+t:n]}),even:he(function(e,t){for(var n=0;n=0;)e.push(r);return e}),gt:he(function(e,t,n){for(var r=n<0?n+t:n;++r1?function(t,n,r){var i=e.length;while(i--)if(!e[i](t,n,r))return!1;return!0}:e[0]}function xe(e,t,n){for(var r=0,i=t.length;r-1&&(o[l]=!(a[l]=f))}}else y=we(y===a?y.splice(h,y.length):y),i?i(null,a,y,s):q.apply(a,y)})}function Te(e){for(var t,n,i,o=e.length,a=r.relative[e[0].type],u=a||r.relative[" "],s=a?1:0,c=me(function(e){return e===t},u,!0),f=me(function(e){return P(t,e)>-1},u,!0),d=[function(e,n,r){var i=!a&&(r||n!==l)||((t=n).nodeType?c(e,n,r):f(e,n,r));return t=null,i}];s1&&be(d),s>1&&ye(e.slice(0,s-1).concat({value:" "===e[s-2].type?"*":""})).replace($,"$1"),n,s0,i=e.length>0,o=function(o,a,u,s,c){var f,h,v,y=0,m="0",b=o&&[],x=[],w=l,T=o||i&&r.find.TAG("*",c),E=C+=null==w?1:Math.random()||.1,N=T.length;for(c&&(l=a===p||a||c);m!==N&&null!=(f=T[m]);m++){if(i&&f){h=0,a||f.ownerDocument===p||(d(f),u=!g);while(v=e[h++])if(v(f,a||p,u)){s.push(f);break}c&&(C=E)}n&&((f=!v&&f)&&y--,o&&b.push(f))}if(y+=m,n&&m!==y){h=0;while(v=t[h++])v(b,x,a,u);if(o){if(y>0)while(m--)b[m]||x[m]||(x[m]=L.call(s));x=we(x)}q.apply(s,x),c&&!o&&x.length>0&&y+t.length>1&&oe.uniqueSort(s)}return c&&(C=E,l=w),b};return n?ue(o):o}return u=oe.compile=function(e,t){var n,r=[],i=[],o=k[e+" "];if(!o){t||(t=a(e)),n=t.length;while(n--)(o=Te(t[n]))[x]?r.push(o):i.push(o);(o=k(e,Ee(i,r))).selector=e}return o},s=oe.select=function(e,t,n,i){var o,s,l,c,f,d="function"==typeof e&&e,p=!i&&a(e=d.selector||e);if(n=n||[],1===p.length){if((s=p[0]=p[0].slice(0)).length>2&&"ID"===(l=s[0]).type&&9===t.nodeType&&g&&r.relative[s[1].type]){if(!(t=(r.find.ID(l.matches[0].replace(Z,ee),t)||[])[0]))return n;d&&(t=t.parentNode),e=e.slice(s.shift().value.length)}o=X.needsContext.test(e)?0:s.length;while(o--){if(l=s[o],r.relative[c=l.type])break;if((f=r.find[c])&&(i=f(l.matches[0].replace(Z,ee),J.test(s[0].type)&&ge(t.parentNode)||t))){if(s.splice(o,1),!(e=i.length&&ye(s)))return q.apply(n,i),n;break}}}return(d||u(e,p))(i,t,!g,n,!t||J.test(e)&&ge(t.parentNode)||t),n},n.sortStable=x.split("").sort(A).join("")===x,n.detectDuplicates=!!f,d(),n.sortDetached=se(function(e){return 1&e.compareDocumentPosition(p.createElement("fieldset"))}),se(function(e){return e.innerHTML="","#"===e.firstChild.getAttribute("href")})||le("type|href|height|width",function(e,t,n){if(!n)return e.getAttribute(t,"type"===t.toLowerCase()?1:2)}),n.attributes&&se(function(e){return e.innerHTML="",e.firstChild.setAttribute("value",""),""===e.firstChild.getAttribute("value")})||le("value",function(e,t,n){if(!n&&"input"===e.nodeName.toLowerCase())return e.defaultValue}),se(function(e){return null==e.getAttribute("disabled")})||le(H,function(e,t,n){var r;if(!n)return!0===e[t]?t.toLowerCase():(r=e.getAttributeNode(t))&&r.specified?r.value:null}),oe}(e);w.find=E,w.expr=E.selectors,w.expr[":"]=w.expr.pseudos,w.uniqueSort=w.unique=E.uniqueSort,w.text=E.getText,w.isXMLDoc=E.isXML,w.contains=E.contains,w.escapeSelector=E.escape;var N=function(e,t,n){var r=[],i=void 0!==n;while((e=e[t])&&9!==e.nodeType)if(1===e.nodeType){if(i&&w(e).is(n))break;r.push(e)}return r},k=function(e,t){for(var n=[];e;e=e.nextSibling)1===e.nodeType&&e!==t&&n.push(e);return n},A=w.expr.match.needsContext;function D(e,t){return e.nodeName&&e.nodeName.toLowerCase()===t.toLowerCase()}var S=/^<([a-z][^\/\0>:\x20\t\r\n\f]*)[\x20\t\r\n\f]*\/?>(?:<\/\1>|)$/i;function L(e,t,n){return g(t)?w.grep(e,function(e,r){return!!t.call(e,r,e)!==n}):t.nodeType?w.grep(e,function(e){return e===t!==n}):"string"!=typeof t?w.grep(e,function(e){return s.call(t,e)>-1!==n}):w.filter(t,e,n)}w.filter=function(e,t,n){var r=t[0];return n&&(e=":not("+e+")"),1===t.length&&1===r.nodeType?w.find.matchesSelector(r,e)?[r]:[]:w.find.matches(e,w.grep(t,function(e){return 1===e.nodeType}))},w.fn.extend({find:function(e){var t,n,r=this.length,i=this;if("string"!=typeof e)return this.pushStack(w(e).filter(function(){for(t=0;t1?w.uniqueSort(n):n},filter:function(e){return this.pushStack(L(this,e||[],!1))},not:function(e){return this.pushStack(L(this,e||[],!0))},is:function(e){return!!L(this,"string"==typeof e&&A.test(e)?w(e):e||[],!1).length}});var j,q=/^(?:\s*(<[\w\W]+>)[^>]*|#([\w-]+))$/;(w.fn.init=function(e,t,n){var i,o;if(!e)return this;if(n=n||j,"string"==typeof e){if(!(i="<"===e[0]&&">"===e[e.length-1]&&e.length>=3?[null,e,null]:q.exec(e))||!i[1]&&t)return!t||t.jquery?(t||n).find(e):this.constructor(t).find(e);if(i[1]){if(t=t instanceof w?t[0]:t,w.merge(this,w.parseHTML(i[1],t&&t.nodeType?t.ownerDocument||t:r,!0)),S.test(i[1])&&w.isPlainObject(t))for(i in t)g(this[i])?this[i](t[i]):this.attr(i,t[i]);return this}return(o=r.getElementById(i[2]))&&(this[0]=o,this.length=1),this}return e.nodeType?(this[0]=e,this.length=1,this):g(e)?void 0!==n.ready?n.ready(e):e(w):w.makeArray(e,this)}).prototype=w.fn,j=w(r);var O=/^(?:parents|prev(?:Until|All))/,P={children:!0,contents:!0,next:!0,prev:!0};w.fn.extend({has:function(e){var t=w(e,this),n=t.length;return this.filter(function(){for(var e=0;e-1:1===n.nodeType&&w.find.matchesSelector(n,e))){o.push(n);break}return this.pushStack(o.length>1?w.uniqueSort(o):o)},index:function(e){return e?"string"==typeof e?s.call(w(e),this[0]):s.call(this,e.jquery?e[0]:e):this[0]&&this[0].parentNode?this.first().prevAll().length:-1},add:function(e,t){return this.pushStack(w.uniqueSort(w.merge(this.get(),w(e,t))))},addBack:function(e){return this.add(null==e?this.prevObject:this.prevObject.filter(e))}});function H(e,t){while((e=e[t])&&1!==e.nodeType);return e}w.each({parent:function(e){var t=e.parentNode;return t&&11!==t.nodeType?t:null},parents:function(e){return N(e,"parentNode")},parentsUntil:function(e,t,n){return N(e,"parentNode",n)},next:function(e){return H(e,"nextSibling")},prev:function(e){return H(e,"previousSibling")},nextAll:function(e){return N(e,"nextSibling")},prevAll:function(e){return N(e,"previousSibling")},nextUntil:function(e,t,n){return N(e,"nextSibling",n)},prevUntil:function(e,t,n){return N(e,"previousSibling",n)},siblings:function(e){return k((e.parentNode||{}).firstChild,e)},children:function(e){return k(e.firstChild)},contents:function(e){return D(e,"iframe")?e.contentDocument:(D(e,"template")&&(e=e.content||e),w.merge([],e.childNodes))}},function(e,t){w.fn[e]=function(n,r){var i=w.map(this,t,n);return"Until"!==e.slice(-5)&&(r=n),r&&"string"==typeof r&&(i=w.filter(r,i)),this.length>1&&(P[e]||w.uniqueSort(i),O.test(e)&&i.reverse()),this.pushStack(i)}});var I=/[^\x20\t\r\n\f]+/g;function R(e){var t={};return w.each(e.match(I)||[],function(e,n){t[n]=!0}),t}w.Callbacks=function(e){e="string"==typeof e?R(e):w.extend({},e);var t,n,r,i,o=[],a=[],u=-1,s=function(){for(i=i||e.once,r=t=!0;a.length;u=-1){n=a.shift();while(++u-1)o.splice(n,1),n<=u&&u--}),this},has:function(e){return e?w.inArray(e,o)>-1:o.length>0},empty:function(){return o&&(o=[]),this},disable:function(){return i=a=[],o=n="",this},disabled:function(){return!o},lock:function(){return i=a=[],n||t||(o=n=""),this},locked:function(){return!!i},fireWith:function(e,n){return i||(n=[e,(n=n||[]).slice?n.slice():n],a.push(n),t||s()),this},fire:function(){return l.fireWith(this,arguments),this},fired:function(){return!!r}};return l};function B(e){return e}function M(e){throw e}function W(e,t,n,r){var i;try{e&&g(i=e.promise)?i.call(e).done(t).fail(n):e&&g(i=e.then)?i.call(e,t,n):t.apply(void 0,[e].slice(r))}catch(e){n.apply(void 0,[e])}}w.extend({Deferred:function(t){var n=[["notify","progress",w.Callbacks("memory"),w.Callbacks("memory"),2],["resolve","done",w.Callbacks("once memory"),w.Callbacks("once memory"),0,"resolved"],["reject","fail",w.Callbacks("once memory"),w.Callbacks("once memory"),1,"rejected"]],r="pending",i={state:function(){return r},always:function(){return o.done(arguments).fail(arguments),this},"catch":function(e){return i.then(null,e)},pipe:function(){var e=arguments;return w.Deferred(function(t){w.each(n,function(n,r){var i=g(e[r[4]])&&e[r[4]];o[r[1]](function(){var e=i&&i.apply(this,arguments);e&&g(e.promise)?e.promise().progress(t.notify).done(t.resolve).fail(t.reject):t[r[0]+"With"](this,i?[e]:arguments)})}),e=null}).promise()},then:function(t,r,i){var o=0;function a(t,n,r,i){return function(){var u=this,s=arguments,l=function(){var e,l;if(!(t=o&&(r!==M&&(u=void 0,s=[e]),n.rejectWith(u,s))}};t?c():(w.Deferred.getStackHook&&(c.stackTrace=w.Deferred.getStackHook()),e.setTimeout(c))}}return w.Deferred(function(e){n[0][3].add(a(0,e,g(i)?i:B,e.notifyWith)),n[1][3].add(a(0,e,g(t)?t:B)),n[2][3].add(a(0,e,g(r)?r:M))}).promise()},promise:function(e){return null!=e?w.extend(e,i):i}},o={};return w.each(n,function(e,t){var a=t[2],u=t[5];i[t[1]]=a.add,u&&a.add(function(){r=u},n[3-e][2].disable,n[3-e][3].disable,n[0][2].lock,n[0][3].lock),a.add(t[3].fire),o[t[0]]=function(){return o[t[0]+"With"](this===o?void 0:this,arguments),this},o[t[0]+"With"]=a.fireWith}),i.promise(o),t&&t.call(o,o),o},when:function(e){var t=arguments.length,n=t,r=Array(n),i=o.call(arguments),a=w.Deferred(),u=function(e){return function(n){r[e]=this,i[e]=arguments.length>1?o.call(arguments):n,--t||a.resolveWith(r,i)}};if(t<=1&&(W(e,a.done(u(n)).resolve,a.reject,!t),"pending"===a.state()||g(i[n]&&i[n].then)))return a.then();while(n--)W(i[n],u(n),a.reject);return a.promise()}});var $=/^(Eval|Internal|Range|Reference|Syntax|Type|URI)Error$/;w.Deferred.exceptionHook=function(t,n){e.console&&e.console.warn&&t&&$.test(t.name)&&e.console.warn("jQuery.Deferred exception: "+t.message,t.stack,n)},w.readyException=function(t){e.setTimeout(function(){throw t})};var F=w.Deferred();w.fn.ready=function(e){return F.then(e)["catch"](function(e){w.readyException(e)}),this},w.extend({isReady:!1,readyWait:1,ready:function(e){(!0===e?--w.readyWait:w.isReady)||(w.isReady=!0,!0!==e&&--w.readyWait>0||F.resolveWith(r,[w]))}}),w.ready.then=F.then;function z(){r.removeEventListener("DOMContentLoaded",z),e.removeEventListener("load",z),w.ready()}"complete"===r.readyState||"loading"!==r.readyState&&!r.documentElement.doScroll?e.setTimeout(w.ready):(r.addEventListener("DOMContentLoaded",z),e.addEventListener("load",z));var _=function(e,t,n,r,i,o,a){var u=0,s=e.length,l=null==n;if("object"===b(n)){i=!0;for(u in n)_(e,t,u,n[u],!0,o,a)}else if(void 0!==r&&(i=!0,g(r)||(a=!0),l&&(a?(t.call(e,r),t=null):(l=t,t=function(e,t,n){return l.call(w(e),n)})),t))for(;u1,null,!0)},removeData:function(e){return this.each(function(){J.remove(this,e)})}}),w.extend({queue:function(e,t,n){var r;if(e)return t=(t||"fx")+"queue",r=K.get(e,t),n&&(!r||Array.isArray(n)?r=K.access(e,t,w.makeArray(n)):r.push(n)),r||[]},dequeue:function(e,t){t=t||"fx";var n=w.queue(e,t),r=n.length,i=n.shift(),o=w._queueHooks(e,t),a=function(){w.dequeue(e,t)};"inprogress"===i&&(i=n.shift(),r--),i&&("fx"===t&&n.unshift("inprogress"),delete o.stop,i.call(e,a,o)),!r&&o&&o.empty.fire()},_queueHooks:function(e,t){var n=t+"queueHooks";return K.get(e,n)||K.access(e,n,{empty:w.Callbacks("once memory").add(function(){K.remove(e,[t+"queue",n])})})}}),w.fn.extend({queue:function(e,t){var n=2;return"string"!=typeof e&&(t=e,e="fx",n--),arguments.length\x20\t\r\n\f]+)/i,he=/^$|^module$|\/(?:java|ecma)script/i,ge={option:[1,""],thead:[1,"","
    "],col:[2,"","
    "],tr:[2,"","
    "],td:[3,"","
    "],_default:[0,"",""]};ge.optgroup=ge.option,ge.tbody=ge.tfoot=ge.colgroup=ge.caption=ge.thead,ge.th=ge.td;function ve(e,t){var n;return n="undefined"!=typeof e.getElementsByTagName?e.getElementsByTagName(t||"*"):"undefined"!=typeof e.querySelectorAll?e.querySelectorAll(t||"*"):[],void 0===t||t&&D(e,t)?w.merge([e],n):n}function ye(e,t){for(var n=0,r=e.length;n-1)i&&i.push(o);else if(l=w.contains(o.ownerDocument,o),a=ve(f.appendChild(o),"script"),l&&ye(a),n){c=0;while(o=a[c++])he.test(o.type||"")&&n.push(o)}return f}!function(){var e=r.createDocumentFragment().appendChild(r.createElement("div")),t=r.createElement("input");t.setAttribute("type","radio"),t.setAttribute("checked","checked"),t.setAttribute("name","t"),e.appendChild(t),h.checkClone=e.cloneNode(!0).cloneNode(!0).lastChild.checked,e.innerHTML="",h.noCloneChecked=!!e.cloneNode(!0).lastChild.defaultValue}();var xe=r.documentElement,we=/^key/,Ce=/^(?:mouse|pointer|contextmenu|drag|drop)|click/,Te=/^([^.]*)(?:\.(.+)|)/;function Ee(){return!0}function Ne(){return!1}function ke(){try{return r.activeElement}catch(e){}}function Ae(e,t,n,r,i,o){var a,u;if("object"==typeof t){"string"!=typeof n&&(r=r||n,n=void 0);for(u in t)Ae(e,u,n,r,t[u],o);return e}if(null==r&&null==i?(i=n,r=n=void 0):null==i&&("string"==typeof n?(i=r,r=void 0):(i=r,r=n,n=void 0)),!1===i)i=Ne;else if(!i)return e;return 1===o&&(a=i,(i=function(e){return w().off(e),a.apply(this,arguments)}).guid=a.guid||(a.guid=w.guid++)),e.each(function(){w.event.add(this,t,i,r,n)})}w.event={global:{},add:function(e,t,n,r,i){var o,a,u,s,l,c,f,d,p,h,g,v=K.get(e);if(v){n.handler&&(n=(o=n).handler,i=o.selector),i&&w.find.matchesSelector(xe,i),n.guid||(n.guid=w.guid++),(s=v.events)||(s=v.events={}),(a=v.handle)||(a=v.handle=function(t){return"undefined"!=typeof w&&w.event.triggered!==t.type?w.event.dispatch.apply(e,arguments):void 0}),l=(t=(t||"").match(I)||[""]).length;while(l--)p=g=(u=Te.exec(t[l])||[])[1],h=(u[2]||"").split(".").sort(),p&&(f=w.event.special[p]||{},p=(i?f.delegateType:f.bindType)||p,f=w.event.special[p]||{},c=w.extend({type:p,origType:g,data:r,handler:n,guid:n.guid,selector:i,needsContext:i&&w.expr.match.needsContext.test(i),namespace:h.join(".")},o),(d=s[p])||((d=s[p]=[]).delegateCount=0,f.setup&&!1!==f.setup.call(e,r,h,a)||e.addEventListener&&e.addEventListener(p,a)),f.add&&(f.add.call(e,c),c.handler.guid||(c.handler.guid=n.guid)),i?d.splice(d.delegateCount++,0,c):d.push(c),w.event.global[p]=!0)}},remove:function(e,t,n,r,i){var o,a,u,s,l,c,f,d,p,h,g,v=K.hasData(e)&&K.get(e);if(v&&(s=v.events)){l=(t=(t||"").match(I)||[""]).length;while(l--)if(u=Te.exec(t[l])||[],p=g=u[1],h=(u[2]||"").split(".").sort(),p){f=w.event.special[p]||{},d=s[p=(r?f.delegateType:f.bindType)||p]||[],u=u[2]&&new RegExp("(^|\\.)"+h.join("\\.(?:.*\\.|)")+"(\\.|$)"),a=o=d.length;while(o--)c=d[o],!i&&g!==c.origType||n&&n.guid!==c.guid||u&&!u.test(c.namespace)||r&&r!==c.selector&&("**"!==r||!c.selector)||(d.splice(o,1),c.selector&&d.delegateCount--,f.remove&&f.remove.call(e,c));a&&!d.length&&(f.teardown&&!1!==f.teardown.call(e,h,v.handle)||w.removeEvent(e,p,v.handle),delete s[p])}else for(p in s)w.event.remove(e,p+t[l],n,r,!0);w.isEmptyObject(s)&&K.remove(e,"handle events")}},dispatch:function(e){var t=w.event.fix(e),n,r,i,o,a,u,s=new Array(arguments.length),l=(K.get(this,"events")||{})[t.type]||[],c=w.event.special[t.type]||{};for(s[0]=t,n=1;n=1))for(;l!==this;l=l.parentNode||this)if(1===l.nodeType&&("click"!==e.type||!0!==l.disabled)){for(o=[],a={},n=0;n-1:w.find(i,this,null,[l]).length),a[i]&&o.push(r);o.length&&u.push({elem:l,handlers:o})}return l=this,s\x20\t\r\n\f]*)[^>]*)\/>/gi,Se=/\s*$/g;function qe(e,t){return D(e,"table")&&D(11!==t.nodeType?t:t.firstChild,"tr")?w(e).children("tbody")[0]||e:e}function Oe(e){return e.type=(null!==e.getAttribute("type"))+"/"+e.type,e}function Pe(e){return"true/"===(e.type||"").slice(0,5)?e.type=e.type.slice(5):e.removeAttribute("type"),e}function He(e,t){var n,r,i,o,a,u,s,l;if(1===t.nodeType){if(K.hasData(e)&&(o=K.access(e),a=K.set(t,o),l=o.events)){delete a.handle,a.events={};for(i in l)for(n=0,r=l[i].length;n1&&"string"==typeof v&&!h.checkClone&&Le.test(v))return e.each(function(i){var o=e.eq(i);y&&(t[0]=v.call(this,i,o.html())),Re(o,t,n,r)});if(d&&(i=be(t,e[0].ownerDocument,!1,e,r),o=i.firstChild,1===i.childNodes.length&&(i=o),o||r)){for(s=(u=w.map(ve(i,"script"),Oe)).length;f")},clone:function(e,t,n){var r,i,o,a,u=e.cloneNode(!0),s=w.contains(e.ownerDocument,e);if(!(h.noCloneChecked||1!==e.nodeType&&11!==e.nodeType||w.isXMLDoc(e)))for(a=ve(u),r=0,i=(o=ve(e)).length;r0&&ye(a,!s&&ve(e,"script")),u},cleanData:function(e){for(var t,n,r,i=w.event.special,o=0;void 0!==(n=e[o]);o++)if(Y(n)){if(t=n[K.expando]){if(t.events)for(r in t.events)i[r]?w.event.remove(n,r):w.removeEvent(n,r,t.handle);n[K.expando]=void 0}n[J.expando]&&(n[J.expando]=void 0)}}}),w.fn.extend({detach:function(e){return Be(this,e,!0)},remove:function(e){return Be(this,e)},text:function(e){return _(this,function(e){return void 0===e?w.text(this):this.empty().each(function(){1!==this.nodeType&&11!==this.nodeType&&9!==this.nodeType||(this.textContent=e)})},null,e,arguments.length)},append:function(){return Re(this,arguments,function(e){1!==this.nodeType&&11!==this.nodeType&&9!==this.nodeType||qe(this,e).appendChild(e)})},prepend:function(){return Re(this,arguments,function(e){if(1===this.nodeType||11===this.nodeType||9===this.nodeType){var t=qe(this,e);t.insertBefore(e,t.firstChild)}})},before:function(){return Re(this,arguments,function(e){this.parentNode&&this.parentNode.insertBefore(e,this)})},after:function(){return Re(this,arguments,function(e){this.parentNode&&this.parentNode.insertBefore(e,this.nextSibling)})},empty:function(){for(var e,t=0;null!=(e=this[t]);t++)1===e.nodeType&&(w.cleanData(ve(e,!1)),e.textContent="");return this},clone:function(e,t){return e=null!=e&&e,t=null==t?e:t,this.map(function(){return w.clone(this,e,t)})},html:function(e){return _(this,function(e){var t=this[0]||{},n=0,r=this.length;if(void 0===e&&1===t.nodeType)return t.innerHTML;if("string"==typeof e&&!Se.test(e)&&!ge[(pe.exec(e)||["",""])[1].toLowerCase()]){e=w.htmlPrefilter(e);try{for(;n=0&&(s+=Math.max(0,Math.ceil(e["offset"+t[0].toUpperCase()+t.slice(1)]-o-s-u-.5))),s}function et(e,t,n){var r=We(e),i=Fe(e,t,r),o="border-box"===w.css(e,"boxSizing",!1,r),a=o;if(Me.test(i)){if(!n)return i;i="auto"}return a=a&&(h.boxSizingReliable()||i===e.style[t]),("auto"===i||!parseFloat(i)&&"inline"===w.css(e,"display",!1,r))&&(i=e["offset"+t[0].toUpperCase()+t.slice(1)],a=!0),(i=parseFloat(i)||0)+Ze(e,t,n||(o?"border":"content"),a,r,i)+"px"}w.extend({cssHooks:{opacity:{get:function(e,t){if(t){var n=Fe(e,"opacity");return""===n?"1":n}}}},cssNumber:{animationIterationCount:!0,columnCount:!0,fillOpacity:!0,flexGrow:!0,flexShrink:!0,fontWeight:!0,lineHeight:!0,opacity:!0,order:!0,orphans:!0,widows:!0,zIndex:!0,zoom:!0},cssProps:{},style:function(e,t,n,r){if(e&&3!==e.nodeType&&8!==e.nodeType&&e.style){var i,o,a,u=Q(t),s=Ue.test(t),l=e.style;if(s||(t=Ke(u)),a=w.cssHooks[t]||w.cssHooks[u],void 0===n)return a&&"get"in a&&void 0!==(i=a.get(e,!1,r))?i:l[t];"string"==(o=typeof n)&&(i=ie.exec(n))&&i[1]&&(n=se(e,t,i),o="number"),null!=n&&n===n&&("number"===o&&(n+=i&&i[3]||(w.cssNumber[u]?"":"px")),h.clearCloneStyle||""!==n||0!==t.indexOf("background")||(l[t]="inherit"),a&&"set"in a&&void 0===(n=a.set(e,n,r))||(s?l.setProperty(t,n):l[t]=n))}},css:function(e,t,n,r){var i,o,a,u=Q(t);return Ue.test(t)||(t=Ke(u)),(a=w.cssHooks[t]||w.cssHooks[u])&&"get"in a&&(i=a.get(e,!0,n)),void 0===i&&(i=Fe(e,t,r)),"normal"===i&&t in Xe&&(i=Xe[t]),""===n||n?(o=parseFloat(i),!0===n||isFinite(o)?o||0:i):i}}),w.each(["height","width"],function(e,t){w.cssHooks[t]={get:function(e,n,r){if(n)return!_e.test(w.css(e,"display"))||e.getClientRects().length&&e.getBoundingClientRect().width?et(e,t,r):ue(e,Ve,function(){return et(e,t,r)})},set:function(e,n,r){var i,o=We(e),a="border-box"===w.css(e,"boxSizing",!1,o),u=r&&Ze(e,t,r,a,o);return a&&h.scrollboxSize()===o.position&&(u-=Math.ceil(e["offset"+t[0].toUpperCase()+t.slice(1)]-parseFloat(o[t])-Ze(e,t,"border",!1,o)-.5)),u&&(i=ie.exec(n))&&"px"!==(i[3]||"px")&&(e.style[t]=n,n=w.css(e,t)),Je(e,n,u)}}}),w.cssHooks.marginLeft=ze(h.reliableMarginLeft,function(e,t){if(t)return(parseFloat(Fe(e,"marginLeft"))||e.getBoundingClientRect().left-ue(e,{marginLeft:0},function(){return e.getBoundingClientRect().left}))+"px"}),w.each({margin:"",padding:"",border:"Width"},function(e,t){w.cssHooks[e+t]={expand:function(n){for(var r=0,i={},o="string"==typeof n?n.split(" "):[n];r<4;r++)i[e+oe[r]+t]=o[r]||o[r-2]||o[0];return i}},"margin"!==e&&(w.cssHooks[e+t].set=Je)}),w.fn.extend({css:function(e,t){return _(this,function(e,t,n){var r,i,o={},a=0;if(Array.isArray(t)){for(r=We(e),i=t.length;a1)}}),w.fn.delay=function(t,n){return t=w.fx?w.fx.speeds[t]||t:t,n=n||"fx",this.queue(n,function(n,r){var i=e.setTimeout(n,t);r.stop=function(){e.clearTimeout(i)}})},function(){var e=r.createElement("input"),t=r.createElement("select").appendChild(r.createElement("option"));e.type="checkbox",h.checkOn=""!==e.value,h.optSelected=t.selected,(e=r.createElement("input")).value="t",e.type="radio",h.radioValue="t"===e.value}();var tt,nt=w.expr.attrHandle;w.fn.extend({attr:function(e,t){return _(this,w.attr,e,t,arguments.length>1)},removeAttr:function(e){return this.each(function(){w.removeAttr(this,e)})}}),w.extend({attr:function(e,t,n){var r,i,o=e.nodeType;if(3!==o&&8!==o&&2!==o)return"undefined"==typeof e.getAttribute?w.prop(e,t,n):(1===o&&w.isXMLDoc(e)||(i=w.attrHooks[t.toLowerCase()]||(w.expr.match.bool.test(t)?tt:void 0)),void 0!==n?null===n?void w.removeAttr(e,t):i&&"set"in i&&void 0!==(r=i.set(e,n,t))?r:(e.setAttribute(t,n+""),n):i&&"get"in i&&null!==(r=i.get(e,t))?r:null==(r=w.find.attr(e,t))?void 0:r)},attrHooks:{type:{set:function(e,t){if(!h.radioValue&&"radio"===t&&D(e,"input")){var n=e.value;return e.setAttribute("type",t),n&&(e.value=n),t}}}},removeAttr:function(e,t){var n,r=0,i=t&&t.match(I);if(i&&1===e.nodeType)while(n=i[r++])e.removeAttribute(n)}}),tt={set:function(e,t,n){return!1===t?w.removeAttr(e,n):e.setAttribute(n,n),n}},w.each(w.expr.match.bool.source.match(/\w+/g),function(e,t){var n=nt[t]||w.find.attr;nt[t]=function(e,t,r){var i,o,a=t.toLowerCase();return r||(o=nt[a],nt[a]=i,i=null!=n(e,t,r)?a:null,nt[a]=o),i}});var rt=/^(?:input|select|textarea|button)$/i,it=/^(?:a|area)$/i;w.fn.extend({prop:function(e,t){return _(this,w.prop,e,t,arguments.length>1)},removeProp:function(e){return this.each(function(){delete this[w.propFix[e]||e]})}}),w.extend({prop:function(e,t,n){var r,i,o=e.nodeType;if(3!==o&&8!==o&&2!==o)return 1===o&&w.isXMLDoc(e)||(t=w.propFix[t]||t,i=w.propHooks[t]),void 0!==n?i&&"set"in i&&void 0!==(r=i.set(e,n,t))?r:e[t]=n:i&&"get"in i&&null!==(r=i.get(e,t))?r:e[t]},propHooks:{tabIndex:{get:function(e){var t=w.find.attr(e,"tabindex");return t?parseInt(t,10):rt.test(e.nodeName)||it.test(e.nodeName)&&e.href?0:-1}}},propFix:{"for":"htmlFor","class":"className"}}),h.optSelected||(w.propHooks.selected={get:function(e){var t=e.parentNode;return t&&t.parentNode&&t.parentNode.selectedIndex,null},set:function(e){var t=e.parentNode;t&&(t.selectedIndex,t.parentNode&&t.parentNode.selectedIndex)}}),w.each(["tabIndex","readOnly","maxLength","cellSpacing","cellPadding","rowSpan","colSpan","useMap","frameBorder","contentEditable"],function(){w.propFix[this.toLowerCase()]=this});function ot(e){return(e.match(I)||[]).join(" ")}function at(e){return e.getAttribute&&e.getAttribute("class")||""}function ut(e){return Array.isArray(e)?e:"string"==typeof e?e.match(I)||[]:[]}w.fn.extend({addClass:function(e){var t,n,r,i,o,a,u,s=0;if(g(e))return this.each(function(t){w(this).addClass(e.call(this,t,at(this)))});if((t=ut(e)).length)while(n=this[s++])if(i=at(n),r=1===n.nodeType&&" "+ot(i)+" "){a=0;while(o=t[a++])r.indexOf(" "+o+" ")<0&&(r+=o+" ");i!==(u=ot(r))&&n.setAttribute("class",u)}return this},removeClass:function(e){var t,n,r,i,o,a,u,s=0;if(g(e))return this.each(function(t){w(this).removeClass(e.call(this,t,at(this)))});if(!arguments.length)return this.attr("class","");if((t=ut(e)).length)while(n=this[s++])if(i=at(n),r=1===n.nodeType&&" "+ot(i)+" "){a=0;while(o=t[a++])while(r.indexOf(" "+o+" ")>-1)r=r.replace(" "+o+" "," ");i!==(u=ot(r))&&n.setAttribute("class",u)}return this},toggleClass:function(e,t){var n=typeof e,r="string"===n||Array.isArray(e);return"boolean"==typeof t&&r?t?this.addClass(e):this.removeClass(e):g(e)?this.each(function(n){w(this).toggleClass(e.call(this,n,at(this),t),t)}):this.each(function(){var t,i,o,a;if(r){i=0,o=w(this),a=ut(e);while(t=a[i++])o.hasClass(t)?o.removeClass(t):o.addClass(t)}else void 0!==e&&"boolean"!==n||((t=at(this))&&K.set(this,"__className__",t),this.setAttribute&&this.setAttribute("class",t||!1===e?"":K.get(this,"__className__")||""))})},hasClass:function(e){var t,n,r=0;t=" "+e+" ";while(n=this[r++])if(1===n.nodeType&&(" "+ot(at(n))+" ").indexOf(t)>-1)return!0;return!1}});var st=/\r/g;w.fn.extend({val:function(e){var t,n,r,i=this[0];{if(arguments.length)return r=g(e),this.each(function(n){var i;1===this.nodeType&&(null==(i=r?e.call(this,n,w(this).val()):e)?i="":"number"==typeof i?i+="":Array.isArray(i)&&(i=w.map(i,function(e){return null==e?"":e+""})),(t=w.valHooks[this.type]||w.valHooks[this.nodeName.toLowerCase()])&&"set"in t&&void 0!==t.set(this,i,"value")||(this.value=i))});if(i)return(t=w.valHooks[i.type]||w.valHooks[i.nodeName.toLowerCase()])&&"get"in t&&void 0!==(n=t.get(i,"value"))?n:"string"==typeof(n=i.value)?n.replace(st,""):null==n?"":n}}}),w.extend({valHooks:{option:{get:function(e){var t=w.find.attr(e,"value");return null!=t?t:ot(w.text(e))}},select:{get:function(e){var t,n,r,i=e.options,o=e.selectedIndex,a="select-one"===e.type,u=a?null:[],s=a?o+1:i.length;for(r=o<0?s:a?o:0;r-1)&&(n=!0);return n||(e.selectedIndex=-1),o}}}}),w.each(["radio","checkbox"],function(){w.valHooks[this]={set:function(e,t){if(Array.isArray(t))return e.checked=w.inArray(w(e).val(),t)>-1}},h.checkOn||(w.valHooks[this].get=function(e){return null===e.getAttribute("value")?"on":e.value})}),h.focusin="onfocusin"in e;var lt=/^(?:focusinfocus|focusoutblur)$/,ct=function(e){e.stopPropagation()};w.extend(w.event,{trigger:function(t,n,i,o){var a,u,s,l,c,d,p,h,y=[i||r],m=f.call(t,"type")?t.type:t,b=f.call(t,"namespace")?t.namespace.split("."):[];if(u=h=s=i=i||r,3!==i.nodeType&&8!==i.nodeType&&!lt.test(m+w.event.triggered)&&(m.indexOf(".")>-1&&(m=(b=m.split(".")).shift(),b.sort()),c=m.indexOf(":")<0&&"on"+m,t=t[w.expando]?t:new w.Event(m,"object"==typeof t&&t),t.isTrigger=o?2:3,t.namespace=b.join("."),t.rnamespace=t.namespace?new RegExp("(^|\\.)"+b.join("\\.(?:.*\\.|)")+"(\\.|$)"):null,t.result=void 0,t.target||(t.target=i),n=null==n?[t]:w.makeArray(n,[t]),p=w.event.special[m]||{},o||!p.trigger||!1!==p.trigger.apply(i,n))){if(!o&&!p.noBubble&&!v(i)){for(l=p.delegateType||m,lt.test(l+m)||(u=u.parentNode);u;u=u.parentNode)y.push(u),s=u;s===(i.ownerDocument||r)&&y.push(s.defaultView||s.parentWindow||e)}a=0;while((u=y[a++])&&!t.isPropagationStopped())h=u,t.type=a>1?l:p.bindType||m,(d=(K.get(u,"events")||{})[t.type]&&K.get(u,"handle"))&&d.apply(u,n),(d=c&&u[c])&&d.apply&&Y(u)&&(t.result=d.apply(u,n),!1===t.result&&t.preventDefault());return t.type=m,o||t.isDefaultPrevented()||p._default&&!1!==p._default.apply(y.pop(),n)||!Y(i)||c&&g(i[m])&&!v(i)&&((s=i[c])&&(i[c]=null),w.event.triggered=m,t.isPropagationStopped()&&h.addEventListener(m,ct),i[m](),t.isPropagationStopped()&&h.removeEventListener(m,ct),w.event.triggered=void 0,s&&(i[c]=s)),t.result}},simulate:function(e,t,n){var r=w.extend(new w.Event,n,{type:e,isSimulated:!0});w.event.trigger(r,null,t)}}),w.fn.extend({trigger:function(e,t){return this.each(function(){w.event.trigger(e,t,this)})},triggerHandler:function(e,t){var n=this[0];if(n)return w.event.trigger(e,t,n,!0)}}),h.focusin||w.each({focus:"focusin",blur:"focusout"},function(e,t){var n=function(e){w.event.simulate(t,e.target,w.event.fix(e))};w.event.special[t]={setup:function(){var r=this.ownerDocument||this,i=K.access(r,t);i||r.addEventListener(e,n,!0),K.access(r,t,(i||0)+1)},teardown:function(){var r=this.ownerDocument||this,i=K.access(r,t)-1;i?K.access(r,t,i):(r.removeEventListener(e,n,!0),K.remove(r,t))}}});var ft=/\[\]$/,dt=/\r?\n/g,pt=/^(?:submit|button|image|reset|file)$/i,ht=/^(?:input|select|textarea|keygen)/i;function gt(e,t,n,r){var i;if(Array.isArray(t))w.each(t,function(t,i){n||ft.test(e)?r(e,i):gt(e+"["+("object"==typeof i&&null!=i?t:"")+"]",i,n,r)});else if(n||"object"!==b(t))r(e,t);else for(i in t)gt(e+"["+i+"]",t[i],n,r)}w.param=function(e,t){var n,r=[],i=function(e,t){var n=g(t)?t():t;r[r.length]=encodeURIComponent(e)+"="+encodeURIComponent(null==n?"":n)};if(Array.isArray(e)||e.jquery&&!w.isPlainObject(e))w.each(e,function(){i(this.name,this.value)});else for(n in e)gt(n,e[n],t,i);return r.join("&")},w.fn.extend({serialize:function(){return w.param(this.serializeArray())},serializeArray:function(){return this.map(function(){var e=w.prop(this,"elements");return e?w.makeArray(e):this}).filter(function(){var e=this.type;return this.name&&!w(this).is(":disabled")&&ht.test(this.nodeName)&&!pt.test(e)&&(this.checked||!de.test(e))}).map(function(e,t){var n=w(this).val();return null==n?null:Array.isArray(n)?w.map(n,function(e){return{name:t.name,value:e.replace(dt,"\r\n")}}):{name:t.name,value:n.replace(dt,"\r\n")}}).get()}}),w.fn.extend({wrapAll:function(e){var t;return this[0]&&(g(e)&&(e=e.call(this[0])),t=w(e,this[0].ownerDocument).eq(0).clone(!0),this[0].parentNode&&t.insertBefore(this[0]),t.map(function(){var e=this;while(e.firstElementChild)e=e.firstElementChild;return e}).append(this)),this},wrapInner:function(e){return g(e)?this.each(function(t){w(this).wrapInner(e.call(this,t))}):this.each(function(){var t=w(this),n=t.contents();n.length?n.wrapAll(e):t.append(e)})},wrap:function(e){var t=g(e);return this.each(function(n){w(this).wrapAll(t?e.call(this,n):e)})},unwrap:function(e){return this.parent(e).not("body").each(function(){w(this).replaceWith(this.childNodes)}),this}}),w.expr.pseudos.hidden=function(e){return!w.expr.pseudos.visible(e)},w.expr.pseudos.visible=function(e){return!!(e.offsetWidth||e.offsetHeight||e.getClientRects().length)},h.createHTMLDocument=function(){var e=r.implementation.createHTMLDocument("").body;return e.innerHTML="
    ",2===e.childNodes.length}(),w.parseHTML=function(e,t,n){if("string"!=typeof e)return[];"boolean"==typeof t&&(n=t,t=!1);var i,o,a;return t||(h.createHTMLDocument?((i=(t=r.implementation.createHTMLDocument("")).createElement("base")).href=r.location.href,t.head.appendChild(i)):t=r),o=S.exec(e),a=!n&&[],o?[t.createElement(o[1])]:(o=be([e],t,a),a&&a.length&&w(a).remove(),w.merge([],o.childNodes))},w.offset={setOffset:function(e,t,n){var r,i,o,a,u,s,l,c=w.css(e,"position"),f=w(e),d={};"static"===c&&(e.style.position="relative"),u=f.offset(),o=w.css(e,"top"),s=w.css(e,"left"),(l=("absolute"===c||"fixed"===c)&&(o+s).indexOf("auto")>-1)?(a=(r=f.position()).top,i=r.left):(a=parseFloat(o)||0,i=parseFloat(s)||0),g(t)&&(t=t.call(e,n,w.extend({},u))),null!=t.top&&(d.top=t.top-u.top+a),null!=t.left&&(d.left=t.left-u.left+i),"using"in t?t.using.call(e,d):f.css(d)}},w.fn.extend({offset:function(e){if(arguments.length)return void 0===e?this:this.each(function(t){w.offset.setOffset(this,e,t)});var t,n,r=this[0];if(r)return r.getClientRects().length?(t=r.getBoundingClientRect(),n=r.ownerDocument.defaultView,{top:t.top+n.pageYOffset,left:t.left+n.pageXOffset}):{top:0,left:0}},position:function(){if(this[0]){var e,t,n,r=this[0],i={top:0,left:0};if("fixed"===w.css(r,"position"))t=r.getBoundingClientRect();else{t=this.offset(),n=r.ownerDocument,e=r.offsetParent||n.documentElement;while(e&&(e===n.body||e===n.documentElement)&&"static"===w.css(e,"position"))e=e.parentNode;e&&e!==r&&1===e.nodeType&&((i=w(e).offset()).top+=w.css(e,"borderTopWidth",!0),i.left+=w.css(e,"borderLeftWidth",!0))}return{top:t.top-i.top-w.css(r,"marginTop",!0),left:t.left-i.left-w.css(r,"marginLeft",!0)}}},offsetParent:function(){return this.map(function(){var e=this.offsetParent;while(e&&"static"===w.css(e,"position"))e=e.offsetParent;return e||xe})}}),w.each({scrollLeft:"pageXOffset",scrollTop:"pageYOffset"},function(e,t){var n="pageYOffset"===t;w.fn[e]=function(r){return _(this,function(e,r,i){var o;if(v(e)?o=e:9===e.nodeType&&(o=e.defaultView),void 0===i)return o?o[t]:e[r];o?o.scrollTo(n?o.pageXOffset:i,n?i:o.pageYOffset):e[r]=i},e,r,arguments.length)}}),w.each(["top","left"],function(e,t){w.cssHooks[t]=ze(h.pixelPosition,function(e,n){if(n)return n=Fe(e,t),Me.test(n)?w(e).position()[t]+"px":n})}),w.each({Height:"height",Width:"width"},function(e,t){w.each({padding:"inner"+e,content:t,"":"outer"+e},function(n,r){w.fn[r]=function(i,o){var a=arguments.length&&(n||"boolean"!=typeof i),u=n||(!0===i||!0===o?"margin":"border");return _(this,function(t,n,i){var o;return v(t)?0===r.indexOf("outer")?t["inner"+e]:t.document.documentElement["client"+e]:9===t.nodeType?(o=t.documentElement,Math.max(t.body["scroll"+e],o["scroll"+e],t.body["offset"+e],o["offset"+e],o["client"+e])):void 0===i?w.css(t,n,u):w.style(t,n,i,u)},t,a?i:void 0,a)}})}),w.each("blur focus focusin focusout resize scroll click dblclick mousedown mouseup mousemove mouseover mouseout mouseenter mouseleave change select submit keydown keypress keyup contextmenu".split(" "),function(e,t){w.fn[t]=function(e,n){return arguments.length>0?this.on(t,null,e,n):this.trigger(t)}}),w.fn.extend({hover:function(e,t){return this.mouseenter(e).mouseleave(t||e)}}),w.fn.extend({bind:function(e,t,n){return this.on(e,null,t,n)},unbind:function(e,t){return this.off(e,null,t)},delegate:function(e,t,n,r){return this.on(t,e,n,r)},undelegate:function(e,t,n){return 1===arguments.length?this.off(e,"**"):this.off(t,e||"**",n)}}),w.proxy=function(e,t){var n,r,i;if("string"==typeof t&&(n=e[t],t=e,e=n),g(e))return r=o.call(arguments,2),i=function(){return e.apply(t||this,r.concat(o.call(arguments)))},i.guid=e.guid=e.guid||w.guid++,i},w.holdReady=function(e){e?w.readyWait++:w.ready(!0)},w.isArray=Array.isArray,w.parseJSON=JSON.parse,w.nodeName=D,w.isFunction=g,w.isWindow=v,w.camelCase=Q,w.type=b,w.now=Date.now,w.isNumeric=function(e){var t=w.type(e);return("number"===t||"string"===t)&&!isNaN(e-parseFloat(e))},"function"==typeof define&&define.amd&&define("jquery",[],function(){return w});var vt=e.jQuery,yt=e.$;return w.noConflict=function(t){return e.$===w&&(e.$=yt),t&&e.jQuery===w&&(e.jQuery=vt),w},t||(e.jQuery=e.$=w),w}); +/*! jQuery v3.3.1 -ajax,-ajax/jsonp,-ajax/load,-ajax/parseXML,-ajax/script,-ajax/var/location,-ajax/var/nonce,-ajax/var/rquery,-ajax/xhr,-manipulation/_evalUrl,-event/ajax,-effects,-effects/Tween,-effects/animatedSelector | (c) JS Foundation and other contributors | jquery.org/license */ ! function(e, t) { + "use strict"; + "object" == typeof module && "object" == typeof module.exports ? module.exports = e.document ? t(e, !0) : function(e) { + if (!e.document) throw new Error("jQuery requires a window with a document"); + return t(e) + } : t(e) +}("undefined" != typeof window ? window : this, function(e, t) { + "use strict"; + var n = [], + r = e.document, + i = Object.getPrototypeOf, + o = n.slice, + a = n.concat, + u = n.push, + s = n.indexOf, + l = {}, + c = l.toString, + f = l.hasOwnProperty, + d = f.toString, + p = d.call(Object), + h = {}, + g = function e(t) { + return "function" == typeof t && "number" != typeof t.nodeType + }, + v = function e(t) { + return null != t && t === t.window + }, + y = { + type: !0, + src: !0, + noModule: !0 + }; + + function m(e, t, n) { + var i, o = (t = t || r).createElement("script"); + if (o.text = e, n) + for (i in y) n[i] && (o[i] = n[i]); + t.head.appendChild(o).parentNode.removeChild(o) + } + + function b(e) { + return null == e ? e + "" : "object" == typeof e || "function" == typeof e ? l[c.call(e)] || "object" : typeof e + } + var x = "3.3.1 -ajax,-ajax/jsonp,-ajax/load,-ajax/parseXML,-ajax/script,-ajax/var/location,-ajax/var/nonce,-ajax/var/rquery,-ajax/xhr,-manipulation/_evalUrl,-event/ajax,-effects,-effects/Tween,-effects/animatedSelector", + w = function(e, t) { + return new w.fn.init(e, t) + }, + C = /^[\s\uFEFF\xA0]+|[\s\uFEFF\xA0]+$/g; + w.fn = w.prototype = { + jquery: x, + constructor: w, + length: 0, + toArray: function() { + return o.call(this) + }, + get: function(e) { + return null == e ? o.call(this) : e < 0 ? this[e + this.length] : this[e] + }, + pushStack: function(e) { + var t = w.merge(this.constructor(), e); + return t.prevObject = this, t + }, + each: function(e) { + return w.each(this, e) + }, + map: function(e) { + return this.pushStack(w.map(this, function(t, n) { + return e.call(t, n, t) + })) + }, + slice: function() { + return this.pushStack(o.apply(this, arguments)) + }, + first: function() { + return this.eq(0) + }, + last: function() { + return this.eq(-1) + }, + eq: function(e) { + var t = this.length, + n = +e + (e < 0 ? t : 0); + return this.pushStack(n >= 0 && n < t ? [this[n]] : []) + }, + end: function() { + return this.prevObject || this.constructor() + }, + push: u, + sort: n.sort, + splice: n.splice + }, w.extend = w.fn.extend = function() { + var e, t, n, r, i, o, a = arguments[0] || {}, + u = 1, + s = arguments.length, + l = !1; + for ("boolean" == typeof a && (l = a, a = arguments[u] || {}, u++), "object" == typeof a || g(a) || (a = {}), u === s && (a = this, u--); u < s; u++) + if (null != (e = arguments[u])) + for (t in e) n = a[t], a !== (r = e[t]) && (l && r && (w.isPlainObject(r) || (i = Array.isArray(r))) ? (i ? (i = !1, o = n && Array.isArray(n) ? n : []) : o = n && w.isPlainObject(n) ? n : {}, a[t] = w.extend(l, o, r)) : void 0 !== r && (a[t] = r)); + return a + }, w.extend({ + expando: "jQuery" + (x + Math.random()).replace(/\D/g, ""), + isReady: !0, + error: function(e) { + throw new Error(e) + }, + noop: function() {}, + isPlainObject: function(e) { + var t, n; + return !(!e || "[object Object]" !== c.call(e)) && (!(t = i(e)) || "function" == typeof(n = f.call(t, "constructor") && t.constructor) && d.call(n) === p) + }, + isEmptyObject: function(e) { + var t; + for (t in e) return !1; + return !0 + }, + globalEval: function(e) { + m(e) + }, + each: function(e, t) { + var n, r = 0; + if (T(e)) { + for (n = e.length; r < n; r++) + if (!1 === t.call(e[r], r, e[r])) break + } else + for (r in e) + if (!1 === t.call(e[r], r, e[r])) break; + return e + }, + trim: function(e) { + return null == e ? "" : (e + "").replace(C, "") + }, + makeArray: function(e, t) { + var n = t || []; + return null != e && (T(Object(e)) ? w.merge(n, "string" == typeof e ? [e] : e) : u.call(n, e)), n + }, + inArray: function(e, t, n) { + return null == t ? -1 : s.call(t, e, n) + }, + merge: function(e, t) { + for (var n = +t.length, r = 0, i = e.length; r < n; r++) e[i++] = t[r]; + return e.length = i, e + }, + grep: function(e, t, n) { + for (var r, i = [], o = 0, a = e.length, u = !n; o < a; o++)(r = !t(e[o], o)) !== u && i.push(e[o]); + return i + }, + map: function(e, t, n) { + var r, i, o = 0, + u = []; + if (T(e)) + for (r = e.length; o < r; o++) null != (i = t(e[o], o, n)) && u.push(i); + else + for (o in e) null != (i = t(e[o], o, n)) && u.push(i); + return a.apply([], u) + }, + guid: 1, + support: h + }), "function" == typeof Symbol && (w.fn[Symbol.iterator] = n[Symbol.iterator]), w.each("Boolean Number String Function Array Date RegExp Object Error Symbol".split(" "), function(e, t) { + l["[object " + t + "]"] = t.toLowerCase() + }); + + function T(e) { + var t = !!e && "length" in e && e.length, + n = b(e); + return !g(e) && !v(e) && ("array" === n || 0 === t || "number" == typeof t && t > 0 && t - 1 in e) + } + var E = function(e) { + var t, n, r, i, o, a, u, s, l, c, f, d, p, h, g, v, y, m, b, x = "sizzle" + 1 * new Date, + w = e.document, + C = 0, + T = 0, + E = ae(), + N = ae(), + k = ae(), + A = function(e, t) { + return e === t && (f = !0), 0 + }, + D = {}.hasOwnProperty, + S = [], + L = S.pop, + j = S.push, + q = S.push, + O = S.slice, + P = function(e, t) { + for (var n = 0, r = e.length; n < r; n++) + if (e[n] === t) return n; + return -1 + }, + H = "checked|selected|async|autofocus|autoplay|controls|defer|disabled|hidden|ismap|loop|multiple|open|readonly|required|scoped", + I = "[\\x20\\t\\r\\n\\f]", + R = "(?:\\\\.|[\\w-]|[^\0-\\xa0])+", + B = "\\[" + I + "*(" + R + ")(?:" + I + "*([*^$|!~]?=)" + I + "*(?:'((?:\\\\.|[^\\\\'])*)'|\"((?:\\\\.|[^\\\\\"])*)\"|(" + R + "))|)" + I + "*\\]", + M = ":(" + R + ")(?:\\((('((?:\\\\.|[^\\\\'])*)'|\"((?:\\\\.|[^\\\\\"])*)\")|((?:\\\\.|[^\\\\()[\\]]|" + B + ")*)|.*)\\)|)", + W = new RegExp(I + "+", "g"), + $ = new RegExp("^" + I + "+|((?:^|[^\\\\])(?:\\\\.)*)" + I + "+$", "g"), + F = new RegExp("^" + I + "*," + I + "*"), + z = new RegExp("^" + I + "*([>+~]|" + I + ")" + I + "*"), + _ = new RegExp("=" + I + "*([^\\]'\"]*?)" + I + "*\\]", "g"), + U = new RegExp(M), + V = new RegExp("^" + R + "$"), + X = { + ID: new RegExp("^#(" + R + ")"), + CLASS: new RegExp("^\\.(" + R + ")"), + TAG: new RegExp("^(" + R + "|[*])"), + ATTR: new RegExp("^" + B), + PSEUDO: new RegExp("^" + M), + CHILD: new RegExp("^:(only|first|last|nth|nth-last)-(child|of-type)(?:\\(" + I + "*(even|odd|(([+-]|)(\\d*)n|)" + I + "*(?:([+-]|)" + I + "*(\\d+)|))" + I + "*\\)|)", "i"), + bool: new RegExp("^(?:" + H + ")$", "i"), + needsContext: new RegExp("^" + I + "*[>+~]|:(even|odd|eq|gt|lt|nth|first|last)(?:\\(" + I + "*((?:-\\d)?\\d*)" + I + "*\\)|)(?=[^-]|$)", "i") + }, + Q = /^(?:input|select|textarea|button)$/i, + Y = /^h\d$/i, + G = /^[^{]+\{\s*\[native \w/, + K = /^(?:#([\w-]+)|(\w+)|\.([\w-]+))$/, + J = /[+~]/, + Z = new RegExp("\\\\([\\da-f]{1,6}" + I + "?|(" + I + ")|.)", "ig"), + ee = function(e, t, n) { + var r = "0x" + t - 65536; + return r !== r || n ? t : r < 0 ? String.fromCharCode(r + 65536) : String.fromCharCode(r >> 10 | 55296, 1023 & r | 56320) + }, + te = /([\0-\x1f\x7f]|^-?\d)|^-$|[^\0-\x1f\x7f-\uFFFF\w-]/g, + ne = function(e, t) { + return t ? "\0" === e ? "\ufffd" : e.slice(0, -1) + "\\" + e.charCodeAt(e.length - 1).toString(16) + " " : "\\" + e + }, + re = function() { + d() + }, + ie = me(function(e) { + return !0 === e.disabled && ("form" in e || "label" in e) + }, { + dir: "parentNode", + next: "legend" + }); + try { + q.apply(S = O.call(w.childNodes), w.childNodes), S[w.childNodes.length].nodeType + } catch (e) { + q = { + apply: S.length ? function(e, t) { + j.apply(e, O.call(t)) + } : function(e, t) { + var n = e.length, + r = 0; + while (e[n++] = t[r++]); + e.length = n - 1 + } + } + } + + function oe(e, t, r, i) { + var o, u, l, c, f, h, y, m = t && t.ownerDocument, + C = t ? t.nodeType : 9; + if (r = r || [], "string" != typeof e || !e || 1 !== C && 9 !== C && 11 !== C) return r; + if (!i && ((t ? t.ownerDocument || t : w) !== p && d(t), t = t || p, g)) { + if (11 !== C && (f = K.exec(e))) + if (o = f[1]) { + if (9 === C) { + if (!(l = t.getElementById(o))) return r; + if (l.id === o) return r.push(l), r + } else if (m && (l = m.getElementById(o)) && b(t, l) && l.id === o) return r.push(l), r + } else { + if (f[2]) return q.apply(r, t.getElementsByTagName(e)), r; + if ((o = f[3]) && n.getElementsByClassName && t.getElementsByClassName) return q.apply(r, t.getElementsByClassName(o)), r + } if (n.qsa && !k[e + " "] && (!v || !v.test(e))) { + if (1 !== C) m = t, y = e; + else if ("object" !== t.nodeName.toLowerCase()) { + (c = t.getAttribute("id")) ? c = c.replace(te, ne): t.setAttribute("id", c = x), u = (h = a(e)).length; + while (u--) h[u] = "#" + c + " " + ye(h[u]); + y = h.join(","), m = J.test(e) && ge(t.parentNode) || t + } + if (y) try { + return q.apply(r, m.querySelectorAll(y)), r + } catch (e) {} finally { + c === x && t.removeAttribute("id") + } + } + } + return s(e.replace($, "$1"), t, r, i) + } + + function ae() { + var e = []; + + function t(n, i) { + return e.push(n + " ") > r.cacheLength && delete t[e.shift()], t[n + " "] = i + } + return t + } + + function ue(e) { + return e[x] = !0, e + } + + function se(e) { + var t = p.createElement("fieldset"); + try { + return !!e(t) + } catch (e) { + return !1 + } finally { + t.parentNode && t.parentNode.removeChild(t), t = null + } + } + + function le(e, t) { + var n = e.split("|"), + i = n.length; + while (i--) r.attrHandle[n[i]] = t + } + + function ce(e, t) { + var n = t && e, + r = n && 1 === e.nodeType && 1 === t.nodeType && e.sourceIndex - t.sourceIndex; + if (r) return r; + if (n) + while (n = n.nextSibling) + if (n === t) return -1; + return e ? 1 : -1 + } + + function fe(e) { + return function(t) { + return "input" === t.nodeName.toLowerCase() && t.type === e + } + } + + function de(e) { + return function(t) { + var n = t.nodeName.toLowerCase(); + return ("input" === n || "button" === n) && t.type === e + } + } + + function pe(e) { + return function(t) { + return "form" in t ? t.parentNode && !1 === t.disabled ? "label" in t ? "label" in t.parentNode ? t.parentNode.disabled === e : t.disabled === e : t.isDisabled === e || t.isDisabled !== !e && ie(t) === e : t.disabled === e : "label" in t && t.disabled === e + } + } + + function he(e) { + return ue(function(t) { + return t = +t, ue(function(n, r) { + var i, o = e([], n.length, t), + a = o.length; + while (a--) n[i = o[a]] && (n[i] = !(r[i] = n[i])) + }) + }) + } + + function ge(e) { + return e && "undefined" != typeof e.getElementsByTagName && e + } + n = oe.support = {}, o = oe.isXML = function(e) { + var t = e && (e.ownerDocument || e).documentElement; + return !!t && "HTML" !== t.nodeName + }, d = oe.setDocument = function(e) { + var t, i, a = e ? e.ownerDocument || e : w; + return a !== p && 9 === a.nodeType && a.documentElement ? (p = a, h = p.documentElement, g = !o(p), w !== p && (i = p.defaultView) && i.top !== i && (i.addEventListener ? i.addEventListener("unload", re, !1) : i.attachEvent && i.attachEvent("onunload", re)), n.attributes = se(function(e) { + return e.className = "i", !e.getAttribute("className") + }), n.getElementsByTagName = se(function(e) { + return e.appendChild(p.createComment("")), !e.getElementsByTagName("*").length + }), n.getElementsByClassName = G.test(p.getElementsByClassName), n.getById = se(function(e) { + return h.appendChild(e).id = x, !p.getElementsByName || !p.getElementsByName(x).length + }), n.getById ? (r.filter.ID = function(e) { + var t = e.replace(Z, ee); + return function(e) { + return e.getAttribute("id") === t + } + }, r.find.ID = function(e, t) { + if ("undefined" != typeof t.getElementById && g) { + var n = t.getElementById(e); + return n ? [n] : [] + } + }) : (r.filter.ID = function(e) { + var t = e.replace(Z, ee); + return function(e) { + var n = "undefined" != typeof e.getAttributeNode && e.getAttributeNode("id"); + return n && n.value === t + } + }, r.find.ID = function(e, t) { + if ("undefined" != typeof t.getElementById && g) { + var n, r, i, o = t.getElementById(e); + if (o) { + if ((n = o.getAttributeNode("id")) && n.value === e) return [o]; + i = t.getElementsByName(e), r = 0; + while (o = i[r++]) + if ((n = o.getAttributeNode("id")) && n.value === e) return [o] + } + return [] + } + }), r.find.TAG = n.getElementsByTagName ? function(e, t) { + return "undefined" != typeof t.getElementsByTagName ? t.getElementsByTagName(e) : n.qsa ? t.querySelectorAll(e) : void 0 + } : function(e, t) { + var n, r = [], + i = 0, + o = t.getElementsByTagName(e); + if ("*" === e) { + while (n = o[i++]) 1 === n.nodeType && r.push(n); + return r + } + return o + }, r.find.CLASS = n.getElementsByClassName && function(e, t) { + if ("undefined" != typeof t.getElementsByClassName && g) return t.getElementsByClassName(e) + }, y = [], v = [], (n.qsa = G.test(p.querySelectorAll)) && (se(function(e) { + h.appendChild(e).innerHTML = "", e.querySelectorAll("[msallowcapture^='']").length && v.push("[*^$]=" + I + "*(?:''|\"\")"), e.querySelectorAll("[selected]").length || v.push("\\[" + I + "*(?:value|" + H + ")"), e.querySelectorAll("[id~=" + x + "-]").length || v.push("~="), e.querySelectorAll(":checked").length || v.push(":checked"), e.querySelectorAll("a#" + x + "+*").length || v.push(".#.+[+~]") + }), se(function(e) { + e.innerHTML = ""; + var t = p.createElement("input"); + t.setAttribute("type", "hidden"), e.appendChild(t).setAttribute("name", "D"), e.querySelectorAll("[name=d]").length && v.push("name" + I + "*[*^$|!~]?="), 2 !== e.querySelectorAll(":enabled").length && v.push(":enabled", ":disabled"), h.appendChild(e).disabled = !0, 2 !== e.querySelectorAll(":disabled").length && v.push(":enabled", ":disabled"), e.querySelectorAll("*,:x"), v.push(",.*:") + })), (n.matchesSelector = G.test(m = h.matches || h.webkitMatchesSelector || h.mozMatchesSelector || h.oMatchesSelector || h.msMatchesSelector)) && se(function(e) { + n.disconnectedMatch = m.call(e, "*"), m.call(e, "[s!='']:x"), y.push("!=", M) + }), v = v.length && new RegExp(v.join("|")), y = y.length && new RegExp(y.join("|")), t = G.test(h.compareDocumentPosition), b = t || G.test(h.contains) ? function(e, t) { + var n = 9 === e.nodeType ? e.documentElement : e, + r = t && t.parentNode; + return e === r || !(!r || 1 !== r.nodeType || !(n.contains ? n.contains(r) : e.compareDocumentPosition && 16 & e.compareDocumentPosition(r))) + } : function(e, t) { + if (t) + while (t = t.parentNode) + if (t === e) return !0; + return !1 + }, A = t ? function(e, t) { + if (e === t) return f = !0, 0; + var r = !e.compareDocumentPosition - !t.compareDocumentPosition; + return r || (1 & (r = (e.ownerDocument || e) === (t.ownerDocument || t) ? e.compareDocumentPosition(t) : 1) || !n.sortDetached && t.compareDocumentPosition(e) === r ? e === p || e.ownerDocument === w && b(w, e) ? -1 : t === p || t.ownerDocument === w && b(w, t) ? 1 : c ? P(c, e) - P(c, t) : 0 : 4 & r ? -1 : 1) + } : function(e, t) { + if (e === t) return f = !0, 0; + var n, r = 0, + i = e.parentNode, + o = t.parentNode, + a = [e], + u = [t]; + if (!i || !o) return e === p ? -1 : t === p ? 1 : i ? -1 : o ? 1 : c ? P(c, e) - P(c, t) : 0; + if (i === o) return ce(e, t); + n = e; + while (n = n.parentNode) a.unshift(n); + n = t; + while (n = n.parentNode) u.unshift(n); + while (a[r] === u[r]) r++; + return r ? ce(a[r], u[r]) : a[r] === w ? -1 : u[r] === w ? 1 : 0 + }, p) : p + }, oe.matches = function(e, t) { + return oe(e, null, null, t) + }, oe.matchesSelector = function(e, t) { + if ((e.ownerDocument || e) !== p && d(e), t = t.replace(_, "='$1']"), n.matchesSelector && g && !k[t + " "] && (!y || !y.test(t)) && (!v || !v.test(t))) try { + var r = m.call(e, t); + if (r || n.disconnectedMatch || e.document && 11 !== e.document.nodeType) return r + } catch (e) {} + return oe(t, p, null, [e]).length > 0 + }, oe.contains = function(e, t) { + return (e.ownerDocument || e) !== p && d(e), b(e, t) + }, oe.attr = function(e, t) { + (e.ownerDocument || e) !== p && d(e); + var i = r.attrHandle[t.toLowerCase()], + o = i && D.call(r.attrHandle, t.toLowerCase()) ? i(e, t, !g) : void 0; + return void 0 !== o ? o : n.attributes || !g ? e.getAttribute(t) : (o = e.getAttributeNode(t)) && o.specified ? o.value : null + }, oe.escape = function(e) { + return (e + "").replace(te, ne) + }, oe.error = function(e) { + throw new Error("Syntax error, unrecognized expression: " + e) + }, oe.uniqueSort = function(e) { + var t, r = [], + i = 0, + o = 0; + if (f = !n.detectDuplicates, c = !n.sortStable && e.slice(0), e.sort(A), f) { + while (t = e[o++]) t === e[o] && (i = r.push(o)); + while (i--) e.splice(r[i], 1) + } + return c = null, e + }, i = oe.getText = function(e) { + var t, n = "", + r = 0, + o = e.nodeType; + if (o) { + if (1 === o || 9 === o || 11 === o) { + if ("string" == typeof e.textContent) return e.textContent; + for (e = e.firstChild; e; e = e.nextSibling) n += i(e) + } else if (3 === o || 4 === o) return e.nodeValue + } else + while (t = e[r++]) n += i(t); + return n + }, (r = oe.selectors = { + cacheLength: 50, + createPseudo: ue, + match: X, + attrHandle: {}, + find: {}, + relative: { + ">": { + dir: "parentNode", + first: !0 + }, + " ": { + dir: "parentNode" + }, + "+": { + dir: "previousSibling", + first: !0 + }, + "~": { + dir: "previousSibling" + } + }, + preFilter: { + ATTR: function(e) { + return e[1] = e[1].replace(Z, ee), e[3] = (e[3] || e[4] || e[5] || "").replace(Z, ee), "~=" === e[2] && (e[3] = " " + e[3] + " "), e.slice(0, 4) + }, + CHILD: function(e) { + return e[1] = e[1].toLowerCase(), "nth" === e[1].slice(0, 3) ? (e[3] || oe.error(e[0]), e[4] = +(e[4] ? e[5] + (e[6] || 1) : 2 * ("even" === e[3] || "odd" === e[3])), e[5] = +(e[7] + e[8] || "odd" === e[3])) : e[3] && oe.error(e[0]), e + }, + PSEUDO: function(e) { + var t, n = !e[6] && e[2]; + return X.CHILD.test(e[0]) ? null : (e[3] ? e[2] = e[4] || e[5] || "" : n && U.test(n) && (t = a(n, !0)) && (t = n.indexOf(")", n.length - t) - n.length) && (e[0] = e[0].slice(0, t), e[2] = n.slice(0, t)), e.slice(0, 3)) + } + }, + filter: { + TAG: function(e) { + var t = e.replace(Z, ee).toLowerCase(); + return "*" === e ? function() { + return !0 + } : function(e) { + return e.nodeName && e.nodeName.toLowerCase() === t + } + }, + CLASS: function(e) { + var t = E[e + " "]; + return t || (t = new RegExp("(^|" + I + ")" + e + "(" + I + "|$)")) && E(e, function(e) { + return t.test("string" == typeof e.className && e.className || "undefined" != typeof e.getAttribute && e.getAttribute("class") || "") + }) + }, + ATTR: function(e, t, n) { + return function(r) { + var i = oe.attr(r, e); + return null == i ? "!=" === t : !t || (i += "", "=" === t ? i === n : "!=" === t ? i !== n : "^=" === t ? n && 0 === i.indexOf(n) : "*=" === t ? n && i.indexOf(n) > -1 : "$=" === t ? n && i.slice(-n.length) === n : "~=" === t ? (" " + i.replace(W, " ") + " ").indexOf(n) > -1 : "|=" === t && (i === n || i.slice(0, n.length + 1) === n + "-")) + } + }, + CHILD: function(e, t, n, r, i) { + var o = "nth" !== e.slice(0, 3), + a = "last" !== e.slice(-4), + u = "of-type" === t; + return 1 === r && 0 === i ? function(e) { + return !!e.parentNode + } : function(t, n, s) { + var l, c, f, d, p, h, g = o !== a ? "nextSibling" : "previousSibling", + v = t.parentNode, + y = u && t.nodeName.toLowerCase(), + m = !s && !u, + b = !1; + if (v) { + if (o) { + while (g) { + d = t; + while (d = d[g]) + if (u ? d.nodeName.toLowerCase() === y : 1 === d.nodeType) return !1; + h = g = "only" === e && !h && "nextSibling" + } + return !0 + } + if (h = [a ? v.firstChild : v.lastChild], a && m) { + b = (p = (l = (c = (f = (d = v)[x] || (d[x] = {}))[d.uniqueID] || (f[d.uniqueID] = {}))[e] || [])[0] === C && l[1]) && l[2], d = p && v.childNodes[p]; + while (d = ++p && d && d[g] || (b = p = 0) || h.pop()) + if (1 === d.nodeType && ++b && d === t) { + c[e] = [C, p, b]; + break + } + } else if (m && (b = p = (l = (c = (f = (d = t)[x] || (d[x] = {}))[d.uniqueID] || (f[d.uniqueID] = {}))[e] || [])[0] === C && l[1]), !1 === b) + while (d = ++p && d && d[g] || (b = p = 0) || h.pop()) + if ((u ? d.nodeName.toLowerCase() === y : 1 === d.nodeType) && ++b && (m && ((c = (f = d[x] || (d[x] = {}))[d.uniqueID] || (f[d.uniqueID] = {}))[e] = [C, b]), d === t)) break; + return (b -= i) === r || b % r == 0 && b / r >= 0 + } + } + }, + PSEUDO: function(e, t) { + var n, i = r.pseudos[e] || r.setFilters[e.toLowerCase()] || oe.error("unsupported pseudo: " + e); + return i[x] ? i(t) : i.length > 1 ? (n = [e, e, "", t], r.setFilters.hasOwnProperty(e.toLowerCase()) ? ue(function(e, n) { + var r, o = i(e, t), + a = o.length; + while (a--) e[r = P(e, o[a])] = !(n[r] = o[a]) + }) : function(e) { + return i(e, 0, n) + }) : i + } + }, + pseudos: { + not: ue(function(e) { + var t = [], + n = [], + r = u(e.replace($, "$1")); + return r[x] ? ue(function(e, t, n, i) { + var o, a = r(e, null, i, []), + u = e.length; + while (u--)(o = a[u]) && (e[u] = !(t[u] = o)) + }) : function(e, i, o) { + return t[0] = e, r(t, null, o, n), t[0] = null, !n.pop() + } + }), + has: ue(function(e) { + return function(t) { + return oe(e, t).length > 0 + } + }), + contains: ue(function(e) { + return e = e.replace(Z, ee), + function(t) { + return (t.textContent || t.innerText || i(t)).indexOf(e) > -1 + } + }), + lang: ue(function(e) { + return V.test(e || "") || oe.error("unsupported lang: " + e), e = e.replace(Z, ee).toLowerCase(), + function(t) { + var n; + do { + if (n = g ? t.lang : t.getAttribute("xml:lang") || t.getAttribute("lang")) return (n = n.toLowerCase()) === e || 0 === n.indexOf(e + "-") + } while ((t = t.parentNode) && 1 === t.nodeType); + return !1 + } + }), + target: function(t) { + var n = e.location && e.location.hash; + return n && n.slice(1) === t.id + }, + root: function(e) { + return e === h + }, + focus: function(e) { + return e === p.activeElement && (!p.hasFocus || p.hasFocus()) && !!(e.type || e.href || ~e.tabIndex) + }, + enabled: pe(!1), + disabled: pe(!0), + checked: function(e) { + var t = e.nodeName.toLowerCase(); + return "input" === t && !!e.checked || "option" === t && !!e.selected + }, + selected: function(e) { + return e.parentNode && e.parentNode.selectedIndex, !0 === e.selected + }, + empty: function(e) { + for (e = e.firstChild; e; e = e.nextSibling) + if (e.nodeType < 6) return !1; + return !0 + }, + parent: function(e) { + return !r.pseudos.empty(e) + }, + header: function(e) { + return Y.test(e.nodeName) + }, + input: function(e) { + return Q.test(e.nodeName) + }, + button: function(e) { + var t = e.nodeName.toLowerCase(); + return "input" === t && "button" === e.type || "button" === t + }, + text: function(e) { + var t; + return "input" === e.nodeName.toLowerCase() && "text" === e.type && (null == (t = e.getAttribute("type")) || "text" === t.toLowerCase()) + }, + first: he(function() { + return [0] + }), + last: he(function(e, t) { + return [t - 1] + }), + eq: he(function(e, t, n) { + return [n < 0 ? n + t : n] + }), + even: he(function(e, t) { + for (var n = 0; n < t; n += 2) e.push(n); + return e + }), + odd: he(function(e, t) { + for (var n = 1; n < t; n += 2) e.push(n); + return e + }), + lt: he(function(e, t, n) { + for (var r = n < 0 ? n + t : n; --r >= 0;) e.push(r); + return e + }), + gt: he(function(e, t, n) { + for (var r = n < 0 ? n + t : n; ++r < t;) e.push(r); + return e + }) + } + }).pseudos.nth = r.pseudos.eq; + for (t in { + radio: !0, + checkbox: !0, + file: !0, + password: !0, + image: !0 + }) r.pseudos[t] = fe(t); + for (t in { + submit: !0, + reset: !0 + }) r.pseudos[t] = de(t); + + function ve() {} + ve.prototype = r.filters = r.pseudos, r.setFilters = new ve, a = oe.tokenize = function(e, t) { + var n, i, o, a, u, s, l, c = N[e + " "]; + if (c) return t ? 0 : c.slice(0); + u = e, s = [], l = r.preFilter; + while (u) { + n && !(i = F.exec(u)) || (i && (u = u.slice(i[0].length) || u), s.push(o = [])), n = !1, (i = z.exec(u)) && (n = i.shift(), o.push({ + value: n, + type: i[0].replace($, " ") + }), u = u.slice(n.length)); + for (a in r.filter) !(i = X[a].exec(u)) || l[a] && !(i = l[a](i)) || (n = i.shift(), o.push({ + value: n, + type: a, + matches: i + }), u = u.slice(n.length)); + if (!n) break + } + return t ? u.length : u ? oe.error(e) : N(e, s).slice(0) + }; + + function ye(e) { + for (var t = 0, n = e.length, r = ""; t < n; t++) r += e[t].value; + return r + } + + function me(e, t, n) { + var r = t.dir, + i = t.next, + o = i || r, + a = n && "parentNode" === o, + u = T++; + return t.first ? function(t, n, i) { + while (t = t[r]) + if (1 === t.nodeType || a) return e(t, n, i); + return !1 + } : function(t, n, s) { + var l, c, f, d = [C, u]; + if (s) { + while (t = t[r]) + if ((1 === t.nodeType || a) && e(t, n, s)) return !0 + } else + while (t = t[r]) + if (1 === t.nodeType || a) + if (f = t[x] || (t[x] = {}), c = f[t.uniqueID] || (f[t.uniqueID] = {}), i && i === t.nodeName.toLowerCase()) t = t[r] || t; + else { + if ((l = c[o]) && l[0] === C && l[1] === u) return d[2] = l[2]; + if (c[o] = d, d[2] = e(t, n, s)) return !0 + } return !1 + } + } + + function be(e) { + return e.length > 1 ? function(t, n, r) { + var i = e.length; + while (i--) + if (!e[i](t, n, r)) return !1; + return !0 + } : e[0] + } + + function xe(e, t, n) { + for (var r = 0, i = t.length; r < i; r++) oe(e, t[r], n); + return n + } + + function we(e, t, n, r, i) { + for (var o, a = [], u = 0, s = e.length, l = null != t; u < s; u++)(o = e[u]) && (n && !n(o, r, i) || (a.push(o), l && t.push(u))); + return a + } + + function Ce(e, t, n, r, i, o) { + return r && !r[x] && (r = Ce(r)), i && !i[x] && (i = Ce(i, o)), ue(function(o, a, u, s) { + var l, c, f, d = [], + p = [], + h = a.length, + g = o || xe(t || "*", u.nodeType ? [u] : u, []), + v = !e || !o && t ? g : we(g, d, e, u, s), + y = n ? i || (o ? e : h || r) ? [] : a : v; + if (n && n(v, y, u, s), r) { + l = we(y, p), r(l, [], u, s), c = l.length; + while (c--)(f = l[c]) && (y[p[c]] = !(v[p[c]] = f)) + } + if (o) { + if (i || e) { + if (i) { + l = [], c = y.length; + while (c--)(f = y[c]) && l.push(v[c] = f); + i(null, y = [], l, s) + } + c = y.length; + while (c--)(f = y[c]) && (l = i ? P(o, f) : d[c]) > -1 && (o[l] = !(a[l] = f)) + } + } else y = we(y === a ? y.splice(h, y.length) : y), i ? i(null, a, y, s) : q.apply(a, y) + }) + } + + function Te(e) { + for (var t, n, i, o = e.length, a = r.relative[e[0].type], u = a || r.relative[" "], s = a ? 1 : 0, c = me(function(e) { + return e === t + }, u, !0), f = me(function(e) { + return P(t, e) > -1 + }, u, !0), d = [function(e, n, r) { + var i = !a && (r || n !== l) || ((t = n).nodeType ? c(e, n, r) : f(e, n, r)); + return t = null, i + }]; s < o; s++) + if (n = r.relative[e[s].type]) d = [me(be(d), n)]; + else { + if ((n = r.filter[e[s].type].apply(null, e[s].matches))[x]) { + for (i = ++s; i < o; i++) + if (r.relative[e[i].type]) break; + return Ce(s > 1 && be(d), s > 1 && ye(e.slice(0, s - 1).concat({ + value: " " === e[s - 2].type ? "*" : "" + })).replace($, "$1"), n, s < i && Te(e.slice(s, i)), i < o && Te(e = e.slice(i)), i < o && ye(e)) + } + d.push(n) + } return be(d) + } + + function Ee(e, t) { + var n = t.length > 0, + i = e.length > 0, + o = function(o, a, u, s, c) { + var f, h, v, y = 0, + m = "0", + b = o && [], + x = [], + w = l, + T = o || i && r.find.TAG("*", c), + E = C += null == w ? 1 : Math.random() || .1, + N = T.length; + for (c && (l = a === p || a || c); m !== N && null != (f = T[m]); m++) { + if (i && f) { + h = 0, a || f.ownerDocument === p || (d(f), u = !g); + while (v = e[h++]) + if (v(f, a || p, u)) { + s.push(f); + break + } c && (C = E) + } + n && ((f = !v && f) && y--, o && b.push(f)) + } + if (y += m, n && m !== y) { + h = 0; + while (v = t[h++]) v(b, x, a, u); + if (o) { + if (y > 0) + while (m--) b[m] || x[m] || (x[m] = L.call(s)); + x = we(x) + } + q.apply(s, x), c && !o && x.length > 0 && y + t.length > 1 && oe.uniqueSort(s) + } + return c && (C = E, l = w), b + }; + return n ? ue(o) : o + } + return u = oe.compile = function(e, t) { + var n, r = [], + i = [], + o = k[e + " "]; + if (!o) { + t || (t = a(e)), n = t.length; + while (n--)(o = Te(t[n]))[x] ? r.push(o) : i.push(o); + (o = k(e, Ee(i, r))).selector = e + } + return o + }, s = oe.select = function(e, t, n, i) { + var o, s, l, c, f, d = "function" == typeof e && e, + p = !i && a(e = d.selector || e); + if (n = n || [], 1 === p.length) { + if ((s = p[0] = p[0].slice(0)).length > 2 && "ID" === (l = s[0]).type && 9 === t.nodeType && g && r.relative[s[1].type]) { + if (!(t = (r.find.ID(l.matches[0].replace(Z, ee), t) || [])[0])) return n; + d && (t = t.parentNode), e = e.slice(s.shift().value.length) + } + o = X.needsContext.test(e) ? 0 : s.length; + while (o--) { + if (l = s[o], r.relative[c = l.type]) break; + if ((f = r.find[c]) && (i = f(l.matches[0].replace(Z, ee), J.test(s[0].type) && ge(t.parentNode) || t))) { + if (s.splice(o, 1), !(e = i.length && ye(s))) return q.apply(n, i), n; + break + } + } + } + return (d || u(e, p))(i, t, !g, n, !t || J.test(e) && ge(t.parentNode) || t), n + }, n.sortStable = x.split("").sort(A).join("") === x, n.detectDuplicates = !!f, d(), n.sortDetached = se(function(e) { + return 1 & e.compareDocumentPosition(p.createElement("fieldset")) + }), se(function(e) { + return e.innerHTML = "", "#" === e.firstChild.getAttribute("href") + }) || le("type|href|height|width", function(e, t, n) { + if (!n) return e.getAttribute(t, "type" === t.toLowerCase() ? 1 : 2) + }), n.attributes && se(function(e) { + return e.innerHTML = "", e.firstChild.setAttribute("value", ""), "" === e.firstChild.getAttribute("value") + }) || le("value", function(e, t, n) { + if (!n && "input" === e.nodeName.toLowerCase()) return e.defaultValue + }), se(function(e) { + return null == e.getAttribute("disabled") + }) || le(H, function(e, t, n) { + var r; + if (!n) return !0 === e[t] ? t.toLowerCase() : (r = e.getAttributeNode(t)) && r.specified ? r.value : null + }), oe + }(e); + w.find = E, w.expr = E.selectors, w.expr[":"] = w.expr.pseudos, w.uniqueSort = w.unique = E.uniqueSort, w.text = E.getText, w.isXMLDoc = E.isXML, w.contains = E.contains, w.escapeSelector = E.escape; + var N = function(e, t, n) { + var r = [], + i = void 0 !== n; + while ((e = e[t]) && 9 !== e.nodeType) + if (1 === e.nodeType) { + if (i && w(e).is(n)) break; + r.push(e) + } return r + }, + k = function(e, t) { + for (var n = []; e; e = e.nextSibling) 1 === e.nodeType && e !== t && n.push(e); + return n + }, + A = w.expr.match.needsContext; + + function D(e, t) { + return e.nodeName && e.nodeName.toLowerCase() === t.toLowerCase() + } + var S = /^<([a-z][^\/\0>:\x20\t\r\n\f]*)[\x20\t\r\n\f]*\/?>(?:<\/\1>|)$/i; + + function L(e, t, n) { + return g(t) ? w.grep(e, function(e, r) { + return !!t.call(e, r, e) !== n + }) : t.nodeType ? w.grep(e, function(e) { + return e === t !== n + }) : "string" != typeof t ? w.grep(e, function(e) { + return s.call(t, e) > -1 !== n + }) : w.filter(t, e, n) + } + w.filter = function(e, t, n) { + var r = t[0]; + return n && (e = ":not(" + e + ")"), 1 === t.length && 1 === r.nodeType ? w.find.matchesSelector(r, e) ? [r] : [] : w.find.matches(e, w.grep(t, function(e) { + return 1 === e.nodeType + })) + }, w.fn.extend({ + find: function(e) { + var t, n, r = this.length, + i = this; + if ("string" != typeof e) return this.pushStack(w(e).filter(function() { + for (t = 0; t < r; t++) + if (w.contains(i[t], this)) return !0 + })); + for (n = this.pushStack([]), t = 0; t < r; t++) w.find(e, i[t], n); + return r > 1 ? w.uniqueSort(n) : n + }, + filter: function(e) { + return this.pushStack(L(this, e || [], !1)) + }, + not: function(e) { + return this.pushStack(L(this, e || [], !0)) + }, + is: function(e) { + return !!L(this, "string" == typeof e && A.test(e) ? w(e) : e || [], !1).length + } + }); + var j, q = /^(?:\s*(<[\w\W]+>)[^>]*|#([\w-]+))$/; + (w.fn.init = function(e, t, n) { + var i, o; + if (!e) return this; + if (n = n || j, "string" == typeof e) { + if (!(i = "<" === e[0] && ">" === e[e.length - 1] && e.length >= 3 ? [null, e, null] : q.exec(e)) || !i[1] && t) return !t || t.jquery ? (t || n).find(e) : this.constructor(t).find(e); + if (i[1]) { + if (t = t instanceof w ? t[0] : t, w.merge(this, w.parseHTML(i[1], t && t.nodeType ? t.ownerDocument || t : r, !0)), S.test(i[1]) && w.isPlainObject(t)) + for (i in t) g(this[i]) ? this[i](t[i]) : this.attr(i, t[i]); + return this + } + return (o = r.getElementById(i[2])) && (this[0] = o, this.length = 1), this + } + return e.nodeType ? (this[0] = e, this.length = 1, this) : g(e) ? void 0 !== n.ready ? n.ready(e) : e(w) : w.makeArray(e, this) + }).prototype = w.fn, j = w(r); + var O = /^(?:parents|prev(?:Until|All))/, + P = { + children: !0, + contents: !0, + next: !0, + prev: !0 + }; + w.fn.extend({ + has: function(e) { + var t = w(e, this), + n = t.length; + return this.filter(function() { + for (var e = 0; e < n; e++) + if (w.contains(this, t[e])) return !0 + }) + }, + closest: function(e, t) { + var n, r = 0, + i = this.length, + o = [], + a = "string" != typeof e && w(e); + if (!A.test(e)) + for (; r < i; r++) + for (n = this[r]; n && n !== t; n = n.parentNode) + if (n.nodeType < 11 && (a ? a.index(n) > -1 : 1 === n.nodeType && w.find.matchesSelector(n, e))) { + o.push(n); + break + } return this.pushStack(o.length > 1 ? w.uniqueSort(o) : o) + }, + index: function(e) { + return e ? "string" == typeof e ? s.call(w(e), this[0]) : s.call(this, e.jquery ? e[0] : e) : this[0] && this[0].parentNode ? this.first().prevAll().length : -1 + }, + add: function(e, t) { + return this.pushStack(w.uniqueSort(w.merge(this.get(), w(e, t)))) + }, + addBack: function(e) { + return this.add(null == e ? this.prevObject : this.prevObject.filter(e)) + } + }); + + function H(e, t) { + while ((e = e[t]) && 1 !== e.nodeType); + return e + } + w.each({ + parent: function(e) { + var t = e.parentNode; + return t && 11 !== t.nodeType ? t : null + }, + parents: function(e) { + return N(e, "parentNode") + }, + parentsUntil: function(e, t, n) { + return N(e, "parentNode", n) + }, + next: function(e) { + return H(e, "nextSibling") + }, + prev: function(e) { + return H(e, "previousSibling") + }, + nextAll: function(e) { + return N(e, "nextSibling") + }, + prevAll: function(e) { + return N(e, "previousSibling") + }, + nextUntil: function(e, t, n) { + return N(e, "nextSibling", n) + }, + prevUntil: function(e, t, n) { + return N(e, "previousSibling", n) + }, + siblings: function(e) { + return k((e.parentNode || {}).firstChild, e) + }, + children: function(e) { + return k(e.firstChild) + }, + contents: function(e) { + return D(e, "iframe") ? e.contentDocument : (D(e, "template") && (e = e.content || e), w.merge([], e.childNodes)) + } + }, function(e, t) { + w.fn[e] = function(n, r) { + var i = w.map(this, t, n); + return "Until" !== e.slice(-5) && (r = n), r && "string" == typeof r && (i = w.filter(r, i)), this.length > 1 && (P[e] || w.uniqueSort(i), O.test(e) && i.reverse()), this.pushStack(i) + } + }); + var I = /[^\x20\t\r\n\f]+/g; + + function R(e) { + var t = {}; + return w.each(e.match(I) || [], function(e, n) { + t[n] = !0 + }), t + } + w.Callbacks = function(e) { + e = "string" == typeof e ? R(e) : w.extend({}, e); + var t, n, r, i, o = [], + a = [], + u = -1, + s = function() { + for (i = i || e.once, r = t = !0; a.length; u = -1) { + n = a.shift(); + while (++u < o.length) !1 === o[u].apply(n[0], n[1]) && e.stopOnFalse && (u = o.length, n = !1) + } + e.memory || (n = !1), t = !1, i && (o = n ? [] : "") + }, + l = { + add: function() { + return o && (n && !t && (u = o.length - 1, a.push(n)), function t(n) { + w.each(n, function(n, r) { + g(r) ? e.unique && l.has(r) || o.push(r) : r && r.length && "string" !== b(r) && t(r) + }) + }(arguments), n && !t && s()), this + }, + remove: function() { + return w.each(arguments, function(e, t) { + var n; + while ((n = w.inArray(t, o, n)) > -1) o.splice(n, 1), n <= u && u-- + }), this + }, + has: function(e) { + return e ? w.inArray(e, o) > -1 : o.length > 0 + }, + empty: function() { + return o && (o = []), this + }, + disable: function() { + return i = a = [], o = n = "", this + }, + disabled: function() { + return !o + }, + lock: function() { + return i = a = [], n || t || (o = n = ""), this + }, + locked: function() { + return !!i + }, + fireWith: function(e, n) { + return i || (n = [e, (n = n || []).slice ? n.slice() : n], a.push(n), t || s()), this + }, + fire: function() { + return l.fireWith(this, arguments), this + }, + fired: function() { + return !!r + } + }; + return l + }; + + function B(e) { + return e + } + + function M(e) { + throw e + } + + function W(e, t, n, r) { + var i; + try { + e && g(i = e.promise) ? i.call(e).done(t).fail(n) : e && g(i = e.then) ? i.call(e, t, n) : t.apply(void 0, [e].slice(r)) + } catch (e) { + n.apply(void 0, [e]) + } + } + w.extend({ + Deferred: function(t) { + var n = [ + ["notify", "progress", w.Callbacks("memory"), w.Callbacks("memory"), 2], + ["resolve", "done", w.Callbacks("once memory"), w.Callbacks("once memory"), 0, "resolved"], + ["reject", "fail", w.Callbacks("once memory"), w.Callbacks("once memory"), 1, "rejected"] + ], + r = "pending", + i = { + state: function() { + return r + }, + always: function() { + return o.done(arguments).fail(arguments), this + }, + "catch": function(e) { + return i.then(null, e) + }, + pipe: function() { + var e = arguments; + return w.Deferred(function(t) { + w.each(n, function(n, r) { + var i = g(e[r[4]]) && e[r[4]]; + o[r[1]](function() { + var e = i && i.apply(this, arguments); + e && g(e.promise) ? e.promise().progress(t.notify).done(t.resolve).fail(t.reject) : t[r[0] + "With"](this, i ? [e] : arguments) + }) + }), e = null + }).promise() + }, + then: function(t, r, i) { + var o = 0; + + function a(t, n, r, i) { + return function() { + var u = this, + s = arguments, + l = function() { + var e, l; + if (!(t < o)) { + if ((e = r.apply(u, s)) === n.promise()) throw new TypeError("Thenable self-resolution"); + l = e && ("object" == typeof e || "function" == typeof e) && e.then, g(l) ? i ? l.call(e, a(o, n, B, i), a(o, n, M, i)) : (o++, l.call(e, a(o, n, B, i), a(o, n, M, i), a(o, n, B, n.notifyWith))) : (r !== B && (u = void 0, s = [e]), (i || n.resolveWith)(u, s)) + } + }, + c = i ? l : function() { + try { + l() + } catch (e) { + w.Deferred.exceptionHook && w.Deferred.exceptionHook(e, c.stackTrace), t + 1 >= o && (r !== M && (u = void 0, s = [e]), n.rejectWith(u, s)) + } + }; + t ? c() : (w.Deferred.getStackHook && (c.stackTrace = w.Deferred.getStackHook()), e.setTimeout(c)) + } + } + return w.Deferred(function(e) { + n[0][3].add(a(0, e, g(i) ? i : B, e.notifyWith)), n[1][3].add(a(0, e, g(t) ? t : B)), n[2][3].add(a(0, e, g(r) ? r : M)) + }).promise() + }, + promise: function(e) { + return null != e ? w.extend(e, i) : i + } + }, + o = {}; + return w.each(n, function(e, t) { + var a = t[2], + u = t[5]; + i[t[1]] = a.add, u && a.add(function() { + r = u + }, n[3 - e][2].disable, n[3 - e][3].disable, n[0][2].lock, n[0][3].lock), a.add(t[3].fire), o[t[0]] = function() { + return o[t[0] + "With"](this === o ? void 0 : this, arguments), this + }, o[t[0] + "With"] = a.fireWith + }), i.promise(o), t && t.call(o, o), o + }, + when: function(e) { + var t = arguments.length, + n = t, + r = Array(n), + i = o.call(arguments), + a = w.Deferred(), + u = function(e) { + return function(n) { + r[e] = this, i[e] = arguments.length > 1 ? o.call(arguments) : n, --t || a.resolveWith(r, i) + } + }; + if (t <= 1 && (W(e, a.done(u(n)).resolve, a.reject, !t), "pending" === a.state() || g(i[n] && i[n].then))) return a.then(); + while (n--) W(i[n], u(n), a.reject); + return a.promise() + } + }); + var $ = /^(Eval|Internal|Range|Reference|Syntax|Type|URI)Error$/; + w.Deferred.exceptionHook = function(t, n) { + e.console && e.console.warn && t && $.test(t.name) && e.console.warn("jQuery.Deferred exception: " + t.message, t.stack, n) + }, w.readyException = function(t) { + e.setTimeout(function() { + throw t + }) + }; + var F = w.Deferred(); + w.fn.ready = function(e) { + return F.then(e)["catch"](function(e) { + w.readyException(e) + }), this + }, w.extend({ + isReady: !1, + readyWait: 1, + ready: function(e) { + (!0 === e ? --w.readyWait : w.isReady) || (w.isReady = !0, !0 !== e && --w.readyWait > 0 || F.resolveWith(r, [w])) + } + }), w.ready.then = F.then; + + function z() { + r.removeEventListener("DOMContentLoaded", z), e.removeEventListener("load", z), w.ready() + } + "complete" === r.readyState || "loading" !== r.readyState && !r.documentElement.doScroll ? e.setTimeout(w.ready) : (r.addEventListener("DOMContentLoaded", z), e.addEventListener("load", z)); + var _ = function(e, t, n, r, i, o, a) { + var u = 0, + s = e.length, + l = null == n; + if ("object" === b(n)) { + i = !0; + for (u in n) _(e, t, u, n[u], !0, o, a) + } else if (void 0 !== r && (i = !0, g(r) || (a = !0), l && (a ? (t.call(e, r), t = null) : (l = t, t = function(e, t, n) { + return l.call(w(e), n) + })), t)) + for (; u < s; u++) t(e[u], n, a ? r : r.call(e[u], u, t(e[u], n))); + return i ? e : l ? t.call(e) : s ? t(e[0], n) : o + }, + U = /^-ms-/, + V = /-([a-z])/g; + + function X(e, t) { + return t.toUpperCase() + } + + function Q(e) { + return e.replace(U, "ms-").replace(V, X) + } + var Y = function(e) { + return 1 === e.nodeType || 9 === e.nodeType || !+e.nodeType + }; + + function G() { + this.expando = w.expando + G.uid++ + } + G.uid = 1, G.prototype = { + cache: function(e) { + var t = e[this.expando]; + return t || (t = {}, Y(e) && (e.nodeType ? e[this.expando] = t : Object.defineProperty(e, this.expando, { + value: t, + configurable: !0 + }))), t + }, + set: function(e, t, n) { + var r, i = this.cache(e); + if ("string" == typeof t) i[Q(t)] = n; + else + for (r in t) i[Q(r)] = t[r]; + return i + }, + get: function(e, t) { + return void 0 === t ? this.cache(e) : e[this.expando] && e[this.expando][Q(t)] + }, + access: function(e, t, n) { + return void 0 === t || t && "string" == typeof t && void 0 === n ? this.get(e, t) : (this.set(e, t, n), void 0 !== n ? n : t) + }, + remove: function(e, t) { + var n, r = e[this.expando]; + if (void 0 !== r) { + if (void 0 !== t) { + n = (t = Array.isArray(t) ? t.map(Q) : (t = Q(t)) in r ? [t] : t.match(I) || []).length; + while (n--) delete r[t[n]] + }(void 0 === t || w.isEmptyObject(r)) && (e.nodeType ? e[this.expando] = void 0 : delete e[this.expando]) + } + }, + hasData: function(e) { + var t = e[this.expando]; + return void 0 !== t && !w.isEmptyObject(t) + } + }; + var K = new G, + J = new G, + Z = /^(?:\{[\w\W]*\}|\[[\w\W]*\])$/, + ee = /[A-Z]/g; + + function te(e) { + return "true" === e || "false" !== e && ("null" === e ? null : e === +e + "" ? +e : Z.test(e) ? JSON.parse(e) : e) + } + + function ne(e, t, n) { + var r; + if (void 0 === n && 1 === e.nodeType) + if (r = "data-" + t.replace(ee, "-$&").toLowerCase(), "string" == typeof(n = e.getAttribute(r))) { + try { + n = te(n) + } catch (e) {} + J.set(e, t, n) + } else n = void 0; + return n + } + w.extend({ + hasData: function(e) { + return J.hasData(e) || K.hasData(e) + }, + data: function(e, t, n) { + return J.access(e, t, n) + }, + removeData: function(e, t) { + J.remove(e, t) + }, + _data: function(e, t, n) { + return K.access(e, t, n) + }, + _removeData: function(e, t) { + K.remove(e, t) + } + }), w.fn.extend({ + data: function(e, t) { + var n, r, i, o = this[0], + a = o && o.attributes; + if (void 0 === e) { + if (this.length && (i = J.get(o), 1 === o.nodeType && !K.get(o, "hasDataAttrs"))) { + n = a.length; + while (n--) a[n] && 0 === (r = a[n].name).indexOf("data-") && (r = Q(r.slice(5)), ne(o, r, i[r])); + K.set(o, "hasDataAttrs", !0) + } + return i + } + return "object" == typeof e ? this.each(function() { + J.set(this, e) + }) : _(this, function(t) { + var n; + if (o && void 0 === t) { + if (void 0 !== (n = J.get(o, e))) return n; + if (void 0 !== (n = ne(o, e))) return n + } else this.each(function() { + J.set(this, e, t) + }) + }, null, t, arguments.length > 1, null, !0) + }, + removeData: function(e) { + return this.each(function() { + J.remove(this, e) + }) + } + }), w.extend({ + queue: function(e, t, n) { + var r; + if (e) return t = (t || "fx") + "queue", r = K.get(e, t), n && (!r || Array.isArray(n) ? r = K.access(e, t, w.makeArray(n)) : r.push(n)), r || [] + }, + dequeue: function(e, t) { + t = t || "fx"; + var n = w.queue(e, t), + r = n.length, + i = n.shift(), + o = w._queueHooks(e, t), + a = function() { + w.dequeue(e, t) + }; + "inprogress" === i && (i = n.shift(), r--), i && ("fx" === t && n.unshift("inprogress"), delete o.stop, i.call(e, a, o)), !r && o && o.empty.fire() + }, + _queueHooks: function(e, t) { + var n = t + "queueHooks"; + return K.get(e, n) || K.access(e, n, { + empty: w.Callbacks("once memory").add(function() { + K.remove(e, [t + "queue", n]) + }) + }) + } + }), w.fn.extend({ + queue: function(e, t) { + var n = 2; + return "string" != typeof e && (t = e, e = "fx", n--), arguments.length < n ? w.queue(this[0], e) : void 0 === t ? this : this.each(function() { + var n = w.queue(this, e, t); + w._queueHooks(this, e), "fx" === e && "inprogress" !== n[0] && w.dequeue(this, e) + }) + }, + dequeue: function(e) { + return this.each(function() { + w.dequeue(this, e) + }) + }, + clearQueue: function(e) { + return this.queue(e || "fx", []) + }, + promise: function(e, t) { + var n, r = 1, + i = w.Deferred(), + o = this, + a = this.length, + u = function() { + --r || i.resolveWith(o, [o]) + }; + "string" != typeof e && (t = e, e = void 0), e = e || "fx"; + while (a--)(n = K.get(o[a], e + "queueHooks")) && n.empty && (r++, n.empty.add(u)); + return u(), i.promise(t) + } + }); + var re = /[+-]?(?:\d*\.|)\d+(?:[eE][+-]?\d+|)/.source, + ie = new RegExp("^(?:([+-])=|)(" + re + ")([a-z%]*)$", "i"), + oe = ["Top", "Right", "Bottom", "Left"], + ae = function(e, t) { + return "none" === (e = t || e).style.display || "" === e.style.display && w.contains(e.ownerDocument, e) && "none" === w.css(e, "display") + }, + ue = function(e, t, n, r) { + var i, o, a = {}; + for (o in t) a[o] = e.style[o], e.style[o] = t[o]; + i = n.apply(e, r || []); + for (o in t) e.style[o] = a[o]; + return i + }; + + function se(e, t, n, r) { + var i, o, a = 20, + u = r ? function() { + return r.cur() + } : function() { + return w.css(e, t, "") + }, + s = u(), + l = n && n[3] || (w.cssNumber[t] ? "" : "px"), + c = (w.cssNumber[t] || "px" !== l && +s) && ie.exec(w.css(e, t)); + if (c && c[3] !== l) { + s /= 2, l = l || c[3], c = +s || 1; + while (a--) w.style(e, t, c + l), (1 - o) * (1 - (o = u() / s || .5)) <= 0 && (a = 0), c /= o; + c *= 2, w.style(e, t, c + l), n = n || [] + } + return n && (c = +c || +s || 0, i = n[1] ? c + (n[1] + 1) * n[2] : +n[2], r && (r.unit = l, r.start = c, r.end = i)), i + } + var le = {}; + + function ce(e) { + var t, n = e.ownerDocument, + r = e.nodeName, + i = le[r]; + return i || (t = n.body.appendChild(n.createElement(r)), i = w.css(t, "display"), t.parentNode.removeChild(t), "none" === i && (i = "block"), le[r] = i, i) + } + + function fe(e, t) { + for (var n, r, i = [], o = 0, a = e.length; o < a; o++)(r = e[o]).style && (n = r.style.display, t ? ("none" === n && (i[o] = K.get(r, "display") || null, i[o] || (r.style.display = "")), "" === r.style.display && ae(r) && (i[o] = ce(r))) : "none" !== n && (i[o] = "none", K.set(r, "display", n))); + for (o = 0; o < a; o++) null != i[o] && (e[o].style.display = i[o]); + return e + } + w.fn.extend({ + show: function() { + return fe(this, !0) + }, + hide: function() { + return fe(this) + }, + toggle: function(e) { + return "boolean" == typeof e ? e ? this.show() : this.hide() : this.each(function() { + ae(this) ? w(this).show() : w(this).hide() + }) + } + }); + var de = /^(?:checkbox|radio)$/i, + pe = /<([a-z][^\/\0>\x20\t\r\n\f]+)/i, + he = /^$|^module$|\/(?:java|ecma)script/i, + ge = { + option: [1, ""], + thead: [1, "", "
    "], + col: [2, "", "
    "], + tr: [2, "", "
    "], + td: [3, "", "
    "], + _default: [0, "", ""] + }; + ge.optgroup = ge.option, ge.tbody = ge.tfoot = ge.colgroup = ge.caption = ge.thead, ge.th = ge.td; + + function ve(e, t) { + var n; + return n = "undefined" != typeof e.getElementsByTagName ? e.getElementsByTagName(t || "*") : "undefined" != typeof e.querySelectorAll ? e.querySelectorAll(t || "*") : [], void 0 === t || t && D(e, t) ? w.merge([e], n) : n + } + + function ye(e, t) { + for (var n = 0, r = e.length; n < r; n++) K.set(e[n], "globalEval", !t || K.get(t[n], "globalEval")) + } + var me = /<|&#?\w+;/; + + function be(e, t, n, r, i) { + for (var o, a, u, s, l, c, f = t.createDocumentFragment(), d = [], p = 0, h = e.length; p < h; p++) + if ((o = e[p]) || 0 === o) + if ("object" === b(o)) w.merge(d, o.nodeType ? [o] : o); + else if (me.test(o)) { + a = a || f.appendChild(t.createElement("div")), u = (pe.exec(o) || ["", ""])[1].toLowerCase(), s = ge[u] || ge._default, a.innerHTML = s[1] + w.htmlPrefilter(o) + s[2], c = s[0]; + while (c--) a = a.lastChild; + w.merge(d, a.childNodes), (a = f.firstChild).textContent = "" + } else d.push(t.createTextNode(o)); + f.textContent = "", p = 0; + while (o = d[p++]) + if (r && w.inArray(o, r) > -1) i && i.push(o); + else if (l = w.contains(o.ownerDocument, o), a = ve(f.appendChild(o), "script"), l && ye(a), n) { + c = 0; + while (o = a[c++]) he.test(o.type || "") && n.push(o) + } + return f + }! function() { + var e = r.createDocumentFragment().appendChild(r.createElement("div")), + t = r.createElement("input"); + t.setAttribute("type", "radio"), t.setAttribute("checked", "checked"), t.setAttribute("name", "t"), e.appendChild(t), h.checkClone = e.cloneNode(!0).cloneNode(!0).lastChild.checked, e.innerHTML = "", h.noCloneChecked = !!e.cloneNode(!0).lastChild.defaultValue + }(); + var xe = r.documentElement, + we = /^key/, + Ce = /^(?:mouse|pointer|contextmenu|drag|drop)|click/, + Te = /^([^.]*)(?:\.(.+)|)/; + + function Ee() { + return !0 + } + + function Ne() { + return !1 + } + + function ke() { + try { + return r.activeElement + } catch (e) {} + } + + function Ae(e, t, n, r, i, o) { + var a, u; + if ("object" == typeof t) { + "string" != typeof n && (r = r || n, n = void 0); + for (u in t) Ae(e, u, n, r, t[u], o); + return e + } + if (null == r && null == i ? (i = n, r = n = void 0) : null == i && ("string" == typeof n ? (i = r, r = void 0) : (i = r, r = n, n = void 0)), !1 === i) i = Ne; + else if (!i) return e; + return 1 === o && (a = i, (i = function(e) { + return w().off(e), a.apply(this, arguments) + }).guid = a.guid || (a.guid = w.guid++)), e.each(function() { + w.event.add(this, t, i, r, n) + }) + } + w.event = { + global: {}, + add: function(e, t, n, r, i) { + var o, a, u, s, l, c, f, d, p, h, g, v = K.get(e); + if (v) { + n.handler && (n = (o = n).handler, i = o.selector), i && w.find.matchesSelector(xe, i), n.guid || (n.guid = w.guid++), (s = v.events) || (s = v.events = {}), (a = v.handle) || (a = v.handle = function(t) { + return "undefined" != typeof w && w.event.triggered !== t.type ? w.event.dispatch.apply(e, arguments) : void 0 + }), l = (t = (t || "").match(I) || [""]).length; + while (l--) p = g = (u = Te.exec(t[l]) || [])[1], h = (u[2] || "").split(".").sort(), p && (f = w.event.special[p] || {}, p = (i ? f.delegateType : f.bindType) || p, f = w.event.special[p] || {}, c = w.extend({ + type: p, + origType: g, + data: r, + handler: n, + guid: n.guid, + selector: i, + needsContext: i && w.expr.match.needsContext.test(i), + namespace: h.join(".") + }, o), (d = s[p]) || ((d = s[p] = []).delegateCount = 0, f.setup && !1 !== f.setup.call(e, r, h, a) || e.addEventListener && e.addEventListener(p, a)), f.add && (f.add.call(e, c), c.handler.guid || (c.handler.guid = n.guid)), i ? d.splice(d.delegateCount++, 0, c) : d.push(c), w.event.global[p] = !0) + } + }, + remove: function(e, t, n, r, i) { + var o, a, u, s, l, c, f, d, p, h, g, v = K.hasData(e) && K.get(e); + if (v && (s = v.events)) { + l = (t = (t || "").match(I) || [""]).length; + while (l--) + if (u = Te.exec(t[l]) || [], p = g = u[1], h = (u[2] || "").split(".").sort(), p) { + f = w.event.special[p] || {}, d = s[p = (r ? f.delegateType : f.bindType) || p] || [], u = u[2] && new RegExp("(^|\\.)" + h.join("\\.(?:.*\\.|)") + "(\\.|$)"), a = o = d.length; + while (o--) c = d[o], !i && g !== c.origType || n && n.guid !== c.guid || u && !u.test(c.namespace) || r && r !== c.selector && ("**" !== r || !c.selector) || (d.splice(o, 1), c.selector && d.delegateCount--, f.remove && f.remove.call(e, c)); + a && !d.length && (f.teardown && !1 !== f.teardown.call(e, h, v.handle) || w.removeEvent(e, p, v.handle), delete s[p]) + } else + for (p in s) w.event.remove(e, p + t[l], n, r, !0); + w.isEmptyObject(s) && K.remove(e, "handle events") + } + }, + dispatch: function(e) { + var t = w.event.fix(e), + n, r, i, o, a, u, s = new Array(arguments.length), + l = (K.get(this, "events") || {})[t.type] || [], + c = w.event.special[t.type] || {}; + for (s[0] = t, n = 1; n < arguments.length; n++) s[n] = arguments[n]; + if (t.delegateTarget = this, !c.preDispatch || !1 !== c.preDispatch.call(this, t)) { + u = w.event.handlers.call(this, t, l), n = 0; + while ((o = u[n++]) && !t.isPropagationStopped()) { + t.currentTarget = o.elem, r = 0; + while ((a = o.handlers[r++]) && !t.isImmediatePropagationStopped()) t.rnamespace && !t.rnamespace.test(a.namespace) || (t.handleObj = a, t.data = a.data, void 0 !== (i = ((w.event.special[a.origType] || {}).handle || a.handler).apply(o.elem, s)) && !1 === (t.result = i) && (t.preventDefault(), t.stopPropagation())) + } + return c.postDispatch && c.postDispatch.call(this, t), t.result + } + }, + handlers: function(e, t) { + var n, r, i, o, a, u = [], + s = t.delegateCount, + l = e.target; + if (s && l.nodeType && !("click" === e.type && e.button >= 1)) + for (; l !== this; l = l.parentNode || this) + if (1 === l.nodeType && ("click" !== e.type || !0 !== l.disabled)) { + for (o = [], a = {}, n = 0; n < s; n++) void 0 === a[i = (r = t[n]).selector + " "] && (a[i] = r.needsContext ? w(i, this).index(l) > -1 : w.find(i, this, null, [l]).length), a[i] && o.push(r); + o.length && u.push({ + elem: l, + handlers: o + }) + } return l = this, s < t.length && u.push({ + elem: l, + handlers: t.slice(s) + }), u + }, + addProp: function(e, t) { + Object.defineProperty(w.Event.prototype, e, { + enumerable: !0, + configurable: !0, + get: g(t) ? function() { + if (this.originalEvent) return t(this.originalEvent) + } : function() { + if (this.originalEvent) return this.originalEvent[e] + }, + set: function(t) { + Object.defineProperty(this, e, { + enumerable: !0, + configurable: !0, + writable: !0, + value: t + }) + } + }) + }, + fix: function(e) { + return e[w.expando] ? e : new w.Event(e) + }, + special: { + load: { + noBubble: !0 + }, + focus: { + trigger: function() { + if (this !== ke() && this.focus) return this.focus(), !1 + }, + delegateType: "focusin" + }, + blur: { + trigger: function() { + if (this === ke() && this.blur) return this.blur(), !1 + }, + delegateType: "focusout" + }, + click: { + trigger: function() { + if ("checkbox" === this.type && this.click && D(this, "input")) return this.click(), !1 + }, + _default: function(e) { + return D(e.target, "a") + } + }, + beforeunload: { + postDispatch: function(e) { + void 0 !== e.result && e.originalEvent && (e.originalEvent.returnValue = e.result) + } + } + } + }, w.removeEvent = function(e, t, n) { + e.removeEventListener && e.removeEventListener(t, n) + }, w.Event = function(e, t) { + if (!(this instanceof w.Event)) return new w.Event(e, t); + e && e.type ? (this.originalEvent = e, this.type = e.type, this.isDefaultPrevented = e.defaultPrevented || void 0 === e.defaultPrevented && !1 === e.returnValue ? Ee : Ne, this.target = e.target && 3 === e.target.nodeType ? e.target.parentNode : e.target, this.currentTarget = e.currentTarget, this.relatedTarget = e.relatedTarget) : this.type = e, t && w.extend(this, t), this.timeStamp = e && e.timeStamp || Date.now(), this[w.expando] = !0 + }, w.Event.prototype = { + constructor: w.Event, + isDefaultPrevented: Ne, + isPropagationStopped: Ne, + isImmediatePropagationStopped: Ne, + isSimulated: !1, + preventDefault: function() { + var e = this.originalEvent; + this.isDefaultPrevented = Ee, e && !this.isSimulated && e.preventDefault() + }, + stopPropagation: function() { + var e = this.originalEvent; + this.isPropagationStopped = Ee, e && !this.isSimulated && e.stopPropagation() + }, + stopImmediatePropagation: function() { + var e = this.originalEvent; + this.isImmediatePropagationStopped = Ee, e && !this.isSimulated && e.stopImmediatePropagation(), this.stopPropagation() + } + }, w.each({ + altKey: !0, + bubbles: !0, + cancelable: !0, + changedTouches: !0, + ctrlKey: !0, + detail: !0, + eventPhase: !0, + metaKey: !0, + pageX: !0, + pageY: !0, + shiftKey: !0, + view: !0, + "char": !0, + charCode: !0, + key: !0, + keyCode: !0, + button: !0, + buttons: !0, + clientX: !0, + clientY: !0, + offsetX: !0, + offsetY: !0, + pointerId: !0, + pointerType: !0, + screenX: !0, + screenY: !0, + targetTouches: !0, + toElement: !0, + touches: !0, + which: function(e) { + var t = e.button; + return null == e.which && we.test(e.type) ? null != e.charCode ? e.charCode : e.keyCode : !e.which && void 0 !== t && Ce.test(e.type) ? 1 & t ? 1 : 2 & t ? 3 : 4 & t ? 2 : 0 : e.which + } + }, w.event.addProp), w.each({ + mouseenter: "mouseover", + mouseleave: "mouseout", + pointerenter: "pointerover", + pointerleave: "pointerout" + }, function(e, t) { + w.event.special[e] = { + delegateType: t, + bindType: t, + handle: function(e) { + var n, r = this, + i = e.relatedTarget, + o = e.handleObj; + return i && (i === r || w.contains(r, i)) || (e.type = o.origType, n = o.handler.apply(this, arguments), e.type = t), n + } + } + }), w.fn.extend({ + on: function(e, t, n, r) { + return Ae(this, e, t, n, r) + }, + one: function(e, t, n, r) { + return Ae(this, e, t, n, r, 1) + }, + off: function(e, t, n) { + var r, i; + if (e && e.preventDefault && e.handleObj) return r = e.handleObj, w(e.delegateTarget).off(r.namespace ? r.origType + "." + r.namespace : r.origType, r.selector, r.handler), this; + if ("object" == typeof e) { + for (i in e) this.off(i, t, e[i]); + return this + } + return !1 !== t && "function" != typeof t || (n = t, t = void 0), !1 === n && (n = Ne), this.each(function() { + w.event.remove(this, e, n, t) + }) + } + }); + var De = /<(?!area|br|col|embed|hr|img|input|link|meta|param)(([a-z][^\/\0>\x20\t\r\n\f]*)[^>]*)\/>/gi, + Se = /\s*$/g; + + function qe(e, t) { + return D(e, "table") && D(11 !== t.nodeType ? t : t.firstChild, "tr") ? w(e).children("tbody")[0] || e : e + } + + function Oe(e) { + return e.type = (null !== e.getAttribute("type")) + "/" + e.type, e + } + + function Pe(e) { + return "true/" === (e.type || "").slice(0, 5) ? e.type = e.type.slice(5) : e.removeAttribute("type"), e + } + + function He(e, t) { + var n, r, i, o, a, u, s, l; + if (1 === t.nodeType) { + if (K.hasData(e) && (o = K.access(e), a = K.set(t, o), l = o.events)) { + delete a.handle, a.events = {}; + for (i in l) + for (n = 0, r = l[i].length; n < r; n++) w.event.add(t, i, l[i][n]) + } + J.hasData(e) && (u = J.access(e), s = w.extend({}, u), J.set(t, s)) + } + } + + function Ie(e, t) { + var n = t.nodeName.toLowerCase(); + "input" === n && de.test(e.type) ? t.checked = e.checked : "input" !== n && "textarea" !== n || (t.defaultValue = e.defaultValue) + } + + function Re(e, t, n, r) { + t = a.apply([], t); + var i, o, u, s, l, c, f = 0, + d = e.length, + p = d - 1, + v = t[0], + y = g(v); + if (y || d > 1 && "string" == typeof v && !h.checkClone && Le.test(v)) return e.each(function(i) { + var o = e.eq(i); + y && (t[0] = v.call(this, i, o.html())), Re(o, t, n, r) + }); + if (d && (i = be(t, e[0].ownerDocument, !1, e, r), o = i.firstChild, 1 === i.childNodes.length && (i = o), o || r)) { + for (s = (u = w.map(ve(i, "script"), Oe)).length; f < d; f++) l = i, f !== p && (l = w.clone(l, !0, !0), s && w.merge(u, ve(l, "script"))), n.call(e[f], l, f); + if (s) + for (c = u[u.length - 1].ownerDocument, w.map(u, Pe), f = 0; f < s; f++) l = u[f], he.test(l.type || "") && !K.access(l, "globalEval") && w.contains(c, l) && (l.src && "module" !== (l.type || "").toLowerCase() ? w._evalUrl && w._evalUrl(l.src) : m(l.textContent.replace(je, ""), c, l)) + } + return e + } + + function Be(e, t, n) { + for (var r, i = t ? w.filter(t, e) : e, o = 0; null != (r = i[o]); o++) n || 1 !== r.nodeType || w.cleanData(ve(r)), r.parentNode && (n && w.contains(r.ownerDocument, r) && ye(ve(r, "script")), r.parentNode.removeChild(r)); + return e + } + w.extend({ + htmlPrefilter: function(e) { + return e.replace(De, "<$1>") + }, + clone: function(e, t, n) { + var r, i, o, a, u = e.cloneNode(!0), + s = w.contains(e.ownerDocument, e); + if (!(h.noCloneChecked || 1 !== e.nodeType && 11 !== e.nodeType || w.isXMLDoc(e))) + for (a = ve(u), r = 0, i = (o = ve(e)).length; r < i; r++) Ie(o[r], a[r]); + if (t) + if (n) + for (o = o || ve(e), a = a || ve(u), r = 0, i = o.length; r < i; r++) He(o[r], a[r]); + else He(e, u); + return (a = ve(u, "script")).length > 0 && ye(a, !s && ve(e, "script")), u + }, + cleanData: function(e) { + for (var t, n, r, i = w.event.special, o = 0; void 0 !== (n = e[o]); o++) + if (Y(n)) { + if (t = n[K.expando]) { + if (t.events) + for (r in t.events) i[r] ? w.event.remove(n, r) : w.removeEvent(n, r, t.handle); + n[K.expando] = void 0 + } + n[J.expando] && (n[J.expando] = void 0) + } + } + }), w.fn.extend({ + detach: function(e) { + return Be(this, e, !0) + }, + remove: function(e) { + return Be(this, e) + }, + text: function(e) { + return _(this, function(e) { + return void 0 === e ? w.text(this) : this.empty().each(function() { + 1 !== this.nodeType && 11 !== this.nodeType && 9 !== this.nodeType || (this.textContent = e) + }) + }, null, e, arguments.length) + }, + append: function() { + return Re(this, arguments, function(e) { + 1 !== this.nodeType && 11 !== this.nodeType && 9 !== this.nodeType || qe(this, e).appendChild(e) + }) + }, + prepend: function() { + return Re(this, arguments, function(e) { + if (1 === this.nodeType || 11 === this.nodeType || 9 === this.nodeType) { + var t = qe(this, e); + t.insertBefore(e, t.firstChild) + } + }) + }, + before: function() { + return Re(this, arguments, function(e) { + this.parentNode && this.parentNode.insertBefore(e, this) + }) + }, + after: function() { + return Re(this, arguments, function(e) { + this.parentNode && this.parentNode.insertBefore(e, this.nextSibling) + }) + }, + empty: function() { + for (var e, t = 0; null != (e = this[t]); t++) 1 === e.nodeType && (w.cleanData(ve(e, !1)), e.textContent = ""); + return this + }, + clone: function(e, t) { + return e = null != e && e, t = null == t ? e : t, this.map(function() { + return w.clone(this, e, t) + }) + }, + html: function(e) { + return _(this, function(e) { + var t = this[0] || {}, + n = 0, + r = this.length; + if (void 0 === e && 1 === t.nodeType) return t.innerHTML; + if ("string" == typeof e && !Se.test(e) && !ge[(pe.exec(e) || ["", ""])[1].toLowerCase()]) { + e = w.htmlPrefilter(e); + try { + for (; n < r; n++) 1 === (t = this[n] || {}).nodeType && (w.cleanData(ve(t, !1)), t.innerHTML = e); + t = 0 + } catch (e) {} + } + t && this.empty().append(e) + }, null, e, arguments.length) + }, + replaceWith: function() { + var e = []; + return Re(this, arguments, function(t) { + var n = this.parentNode; + w.inArray(this, e) < 0 && (w.cleanData(ve(this)), n && n.replaceChild(t, this)) + }, e) + } + }), w.each({ + appendTo: "append", + prependTo: "prepend", + insertBefore: "before", + insertAfter: "after", + replaceAll: "replaceWith" + }, function(e, t) { + w.fn[e] = function(e) { + for (var n, r = [], i = w(e), o = i.length - 1, a = 0; a <= o; a++) n = a === o ? this : this.clone(!0), w(i[a])[t](n), u.apply(r, n.get()); + return this.pushStack(r) + } + }); + var Me = new RegExp("^(" + re + ")(?!px)[a-z%]+$", "i"), + We = function(t) { + var n = t.ownerDocument.defaultView; + return n && n.opener || (n = e), n.getComputedStyle(t) + }, + $e = new RegExp(oe.join("|"), "i"); + ! function() { + function t() { + if (c) { + l.style.cssText = "position:absolute;left:-11111px;width:60px;margin-top:1px;padding:0;border:0", c.style.cssText = "position:relative;display:block;box-sizing:border-box;overflow:scroll;margin:auto;border:1px;padding:1px;width:60%;top:1%", xe.appendChild(l).appendChild(c); + var t = e.getComputedStyle(c); + i = "1%" !== t.top, s = 12 === n(t.marginLeft), c.style.right = "60%", u = 36 === n(t.right), o = 36 === n(t.width), c.style.position = "absolute", a = 36 === c.offsetWidth || "absolute", xe.removeChild(l), c = null + } + } + + function n(e) { + return Math.round(parseFloat(e)) + } + var i, o, a, u, s, l = r.createElement("div"), + c = r.createElement("div"); + c.style && (c.style.backgroundClip = "content-box", c.cloneNode(!0).style.backgroundClip = "", h.clearCloneStyle = "content-box" === c.style.backgroundClip, w.extend(h, { + boxSizingReliable: function() { + return t(), o + }, + pixelBoxStyles: function() { + return t(), u + }, + pixelPosition: function() { + return t(), i + }, + reliableMarginLeft: function() { + return t(), s + }, + scrollboxSize: function() { + return t(), a + } + })) + }(); + + function Fe(e, t, n) { + var r, i, o, a, u = e.style; + return (n = n || We(e)) && ("" !== (a = n.getPropertyValue(t) || n[t]) || w.contains(e.ownerDocument, e) || (a = w.style(e, t)), !h.pixelBoxStyles() && Me.test(a) && $e.test(t) && (r = u.width, i = u.minWidth, o = u.maxWidth, u.minWidth = u.maxWidth = u.width = a, a = n.width, u.width = r, u.minWidth = i, u.maxWidth = o)), void 0 !== a ? a + "" : a + } + + function ze(e, t) { + return { + get: function() { + if (!e()) return (this.get = t).apply(this, arguments); + delete this.get + } + } + } + var _e = /^(none|table(?!-c[ea]).+)/, + Ue = /^--/, + Ve = { + position: "absolute", + visibility: "hidden", + display: "block" + }, + Xe = { + letterSpacing: "0", + fontWeight: "400" + }, + Qe = ["Webkit", "Moz", "ms"], + Ye = r.createElement("div").style; + + function Ge(e) { + if (e in Ye) return e; + var t = e[0].toUpperCase() + e.slice(1), + n = Qe.length; + while (n--) + if ((e = Qe[n] + t) in Ye) return e + } + + function Ke(e) { + var t = w.cssProps[e]; + return t || (t = w.cssProps[e] = Ge(e) || e), t + } + + function Je(e, t, n) { + var r = ie.exec(t); + return r ? Math.max(0, r[2] - (n || 0)) + (r[3] || "px") : t + } + + function Ze(e, t, n, r, i, o) { + var a = "width" === t ? 1 : 0, + u = 0, + s = 0; + if (n === (r ? "border" : "content")) return 0; + for (; a < 4; a += 2) "margin" === n && (s += w.css(e, n + oe[a], !0, i)), r ? ("content" === n && (s -= w.css(e, "padding" + oe[a], !0, i)), "margin" !== n && (s -= w.css(e, "border" + oe[a] + "Width", !0, i))) : (s += w.css(e, "padding" + oe[a], !0, i), "padding" !== n ? s += w.css(e, "border" + oe[a] + "Width", !0, i) : u += w.css(e, "border" + oe[a] + "Width", !0, i)); + return !r && o >= 0 && (s += Math.max(0, Math.ceil(e["offset" + t[0].toUpperCase() + t.slice(1)] - o - s - u - .5))), s + } + + function et(e, t, n) { + var r = We(e), + i = Fe(e, t, r), + o = "border-box" === w.css(e, "boxSizing", !1, r), + a = o; + if (Me.test(i)) { + if (!n) return i; + i = "auto" + } + return a = a && (h.boxSizingReliable() || i === e.style[t]), ("auto" === i || !parseFloat(i) && "inline" === w.css(e, "display", !1, r)) && (i = e["offset" + t[0].toUpperCase() + t.slice(1)], a = !0), (i = parseFloat(i) || 0) + Ze(e, t, n || (o ? "border" : "content"), a, r, i) + "px" + } + w.extend({ + cssHooks: { + opacity: { + get: function(e, t) { + if (t) { + var n = Fe(e, "opacity"); + return "" === n ? "1" : n + } + } + } + }, + cssNumber: { + animationIterationCount: !0, + columnCount: !0, + fillOpacity: !0, + flexGrow: !0, + flexShrink: !0, + fontWeight: !0, + lineHeight: !0, + opacity: !0, + order: !0, + orphans: !0, + widows: !0, + zIndex: !0, + zoom: !0 + }, + cssProps: {}, + style: function(e, t, n, r) { + if (e && 3 !== e.nodeType && 8 !== e.nodeType && e.style) { + var i, o, a, u = Q(t), + s = Ue.test(t), + l = e.style; + if (s || (t = Ke(u)), a = w.cssHooks[t] || w.cssHooks[u], void 0 === n) return a && "get" in a && void 0 !== (i = a.get(e, !1, r)) ? i : l[t]; + "string" == (o = typeof n) && (i = ie.exec(n)) && i[1] && (n = se(e, t, i), o = "number"), null != n && n === n && ("number" === o && (n += i && i[3] || (w.cssNumber[u] ? "" : "px")), h.clearCloneStyle || "" !== n || 0 !== t.indexOf("background") || (l[t] = "inherit"), a && "set" in a && void 0 === (n = a.set(e, n, r)) || (s ? l.setProperty(t, n) : l[t] = n)) + } + }, + css: function(e, t, n, r) { + var i, o, a, u = Q(t); + return Ue.test(t) || (t = Ke(u)), (a = w.cssHooks[t] || w.cssHooks[u]) && "get" in a && (i = a.get(e, !0, n)), void 0 === i && (i = Fe(e, t, r)), "normal" === i && t in Xe && (i = Xe[t]), "" === n || n ? (o = parseFloat(i), !0 === n || isFinite(o) ? o || 0 : i) : i + } + }), w.each(["height", "width"], function(e, t) { + w.cssHooks[t] = { + get: function(e, n, r) { + if (n) return !_e.test(w.css(e, "display")) || e.getClientRects().length && e.getBoundingClientRect().width ? et(e, t, r) : ue(e, Ve, function() { + return et(e, t, r) + }) + }, + set: function(e, n, r) { + var i, o = We(e), + a = "border-box" === w.css(e, "boxSizing", !1, o), + u = r && Ze(e, t, r, a, o); + return a && h.scrollboxSize() === o.position && (u -= Math.ceil(e["offset" + t[0].toUpperCase() + t.slice(1)] - parseFloat(o[t]) - Ze(e, t, "border", !1, o) - .5)), u && (i = ie.exec(n)) && "px" !== (i[3] || "px") && (e.style[t] = n, n = w.css(e, t)), Je(e, n, u) + } + } + }), w.cssHooks.marginLeft = ze(h.reliableMarginLeft, function(e, t) { + if (t) return (parseFloat(Fe(e, "marginLeft")) || e.getBoundingClientRect().left - ue(e, { + marginLeft: 0 + }, function() { + return e.getBoundingClientRect().left + })) + "px" + }), w.each({ + margin: "", + padding: "", + border: "Width" + }, function(e, t) { + w.cssHooks[e + t] = { + expand: function(n) { + for (var r = 0, i = {}, o = "string" == typeof n ? n.split(" ") : [n]; r < 4; r++) i[e + oe[r] + t] = o[r] || o[r - 2] || o[0]; + return i + } + }, "margin" !== e && (w.cssHooks[e + t].set = Je) + }), w.fn.extend({ + css: function(e, t) { + return _(this, function(e, t, n) { + var r, i, o = {}, + a = 0; + if (Array.isArray(t)) { + for (r = We(e), i = t.length; a < i; a++) o[t[a]] = w.css(e, t[a], !1, r); + return o + } + return void 0 !== n ? w.style(e, t, n) : w.css(e, t) + }, e, t, arguments.length > 1) + } + }), w.fn.delay = function(t, n) { + return t = w.fx ? w.fx.speeds[t] || t : t, n = n || "fx", this.queue(n, function(n, r) { + var i = e.setTimeout(n, t); + r.stop = function() { + e.clearTimeout(i) + } + }) + }, + function() { + var e = r.createElement("input"), + t = r.createElement("select").appendChild(r.createElement("option")); + e.type = "checkbox", h.checkOn = "" !== e.value, h.optSelected = t.selected, (e = r.createElement("input")).value = "t", e.type = "radio", h.radioValue = "t" === e.value + }(); + var tt, nt = w.expr.attrHandle; + w.fn.extend({ + attr: function(e, t) { + return _(this, w.attr, e, t, arguments.length > 1) + }, + removeAttr: function(e) { + return this.each(function() { + w.removeAttr(this, e) + }) + } + }), w.extend({ + attr: function(e, t, n) { + var r, i, o = e.nodeType; + if (3 !== o && 8 !== o && 2 !== o) return "undefined" == typeof e.getAttribute ? w.prop(e, t, n) : (1 === o && w.isXMLDoc(e) || (i = w.attrHooks[t.toLowerCase()] || (w.expr.match.bool.test(t) ? tt : void 0)), void 0 !== n ? null === n ? void w.removeAttr(e, t) : i && "set" in i && void 0 !== (r = i.set(e, n, t)) ? r : (e.setAttribute(t, n + ""), n) : i && "get" in i && null !== (r = i.get(e, t)) ? r : null == (r = w.find.attr(e, t)) ? void 0 : r) + }, + attrHooks: { + type: { + set: function(e, t) { + if (!h.radioValue && "radio" === t && D(e, "input")) { + var n = e.value; + return e.setAttribute("type", t), n && (e.value = n), t + } + } + } + }, + removeAttr: function(e, t) { + var n, r = 0, + i = t && t.match(I); + if (i && 1 === e.nodeType) + while (n = i[r++]) e.removeAttribute(n) + } + }), tt = { + set: function(e, t, n) { + return !1 === t ? w.removeAttr(e, n) : e.setAttribute(n, n), n + } + }, w.each(w.expr.match.bool.source.match(/\w+/g), function(e, t) { + var n = nt[t] || w.find.attr; + nt[t] = function(e, t, r) { + var i, o, a = t.toLowerCase(); + return r || (o = nt[a], nt[a] = i, i = null != n(e, t, r) ? a : null, nt[a] = o), i + } + }); + var rt = /^(?:input|select|textarea|button)$/i, + it = /^(?:a|area)$/i; + w.fn.extend({ + prop: function(e, t) { + return _(this, w.prop, e, t, arguments.length > 1) + }, + removeProp: function(e) { + return this.each(function() { + delete this[w.propFix[e] || e] + }) + } + }), w.extend({ + prop: function(e, t, n) { + var r, i, o = e.nodeType; + if (3 !== o && 8 !== o && 2 !== o) return 1 === o && w.isXMLDoc(e) || (t = w.propFix[t] || t, i = w.propHooks[t]), void 0 !== n ? i && "set" in i && void 0 !== (r = i.set(e, n, t)) ? r : e[t] = n : i && "get" in i && null !== (r = i.get(e, t)) ? r : e[t] + }, + propHooks: { + tabIndex: { + get: function(e) { + var t = w.find.attr(e, "tabindex"); + return t ? parseInt(t, 10) : rt.test(e.nodeName) || it.test(e.nodeName) && e.href ? 0 : -1 + } + } + }, + propFix: { + "for": "htmlFor", + "class": "className" + } + }), h.optSelected || (w.propHooks.selected = { + get: function(e) { + var t = e.parentNode; + return t && t.parentNode && t.parentNode.selectedIndex, null + }, + set: function(e) { + var t = e.parentNode; + t && (t.selectedIndex, t.parentNode && t.parentNode.selectedIndex) + } + }), w.each(["tabIndex", "readOnly", "maxLength", "cellSpacing", "cellPadding", "rowSpan", "colSpan", "useMap", "frameBorder", "contentEditable"], function() { + w.propFix[this.toLowerCase()] = this + }); + + function ot(e) { + return (e.match(I) || []).join(" ") + } + + function at(e) { + return e.getAttribute && e.getAttribute("class") || "" + } + + function ut(e) { + return Array.isArray(e) ? e : "string" == typeof e ? e.match(I) || [] : [] + } + w.fn.extend({ + addClass: function(e) { + var t, n, r, i, o, a, u, s = 0; + if (g(e)) return this.each(function(t) { + w(this).addClass(e.call(this, t, at(this))) + }); + if ((t = ut(e)).length) + while (n = this[s++]) + if (i = at(n), r = 1 === n.nodeType && " " + ot(i) + " ") { + a = 0; + while (o = t[a++]) r.indexOf(" " + o + " ") < 0 && (r += o + " "); + i !== (u = ot(r)) && n.setAttribute("class", u) + } return this + }, + removeClass: function(e) { + var t, n, r, i, o, a, u, s = 0; + if (g(e)) return this.each(function(t) { + w(this).removeClass(e.call(this, t, at(this))) + }); + if (!arguments.length) return this.attr("class", ""); + if ((t = ut(e)).length) + while (n = this[s++]) + if (i = at(n), r = 1 === n.nodeType && " " + ot(i) + " ") { + a = 0; + while (o = t[a++]) + while (r.indexOf(" " + o + " ") > -1) r = r.replace(" " + o + " ", " "); + i !== (u = ot(r)) && n.setAttribute("class", u) + } return this + }, + toggleClass: function(e, t) { + var n = typeof e, + r = "string" === n || Array.isArray(e); + return "boolean" == typeof t && r ? t ? this.addClass(e) : this.removeClass(e) : g(e) ? this.each(function(n) { + w(this).toggleClass(e.call(this, n, at(this), t), t) + }) : this.each(function() { + var t, i, o, a; + if (r) { + i = 0, o = w(this), a = ut(e); + while (t = a[i++]) o.hasClass(t) ? o.removeClass(t) : o.addClass(t) + } else void 0 !== e && "boolean" !== n || ((t = at(this)) && K.set(this, "__className__", t), this.setAttribute && this.setAttribute("class", t || !1 === e ? "" : K.get(this, "__className__") || "")) + }) + }, + hasClass: function(e) { + var t, n, r = 0; + t = " " + e + " "; + while (n = this[r++]) + if (1 === n.nodeType && (" " + ot(at(n)) + " ").indexOf(t) > -1) return !0; + return !1 + } + }); + var st = /\r/g; + w.fn.extend({ + val: function(e) { + var t, n, r, i = this[0]; { + if (arguments.length) return r = g(e), this.each(function(n) { + var i; + 1 === this.nodeType && (null == (i = r ? e.call(this, n, w(this).val()) : e) ? i = "" : "number" == typeof i ? i += "" : Array.isArray(i) && (i = w.map(i, function(e) { + return null == e ? "" : e + "" + })), (t = w.valHooks[this.type] || w.valHooks[this.nodeName.toLowerCase()]) && "set" in t && void 0 !== t.set(this, i, "value") || (this.value = i)) + }); + if (i) return (t = w.valHooks[i.type] || w.valHooks[i.nodeName.toLowerCase()]) && "get" in t && void 0 !== (n = t.get(i, "value")) ? n : "string" == typeof(n = i.value) ? n.replace(st, "") : null == n ? "" : n + } + } + }), w.extend({ + valHooks: { + option: { + get: function(e) { + var t = w.find.attr(e, "value"); + return null != t ? t : ot(w.text(e)) + } + }, + select: { + get: function(e) { + var t, n, r, i = e.options, + o = e.selectedIndex, + a = "select-one" === e.type, + u = a ? null : [], + s = a ? o + 1 : i.length; + for (r = o < 0 ? s : a ? o : 0; r < s; r++) + if (((n = i[r]).selected || r === o) && !n.disabled && (!n.parentNode.disabled || !D(n.parentNode, "optgroup"))) { + if (t = w(n).val(), a) return t; + u.push(t) + } return u + }, + set: function(e, t) { + var n, r, i = e.options, + o = w.makeArray(t), + a = i.length; + while (a--)((r = i[a]).selected = w.inArray(w.valHooks.option.get(r), o) > -1) && (n = !0); + return n || (e.selectedIndex = -1), o + } + } + } + }), w.each(["radio", "checkbox"], function() { + w.valHooks[this] = { + set: function(e, t) { + if (Array.isArray(t)) return e.checked = w.inArray(w(e).val(), t) > -1 + } + }, h.checkOn || (w.valHooks[this].get = function(e) { + return null === e.getAttribute("value") ? "on" : e.value + }) + }), h.focusin = "onfocusin" in e; + var lt = /^(?:focusinfocus|focusoutblur)$/, + ct = function(e) { + e.stopPropagation() + }; + w.extend(w.event, { + trigger: function(t, n, i, o) { + var a, u, s, l, c, d, p, h, y = [i || r], + m = f.call(t, "type") ? t.type : t, + b = f.call(t, "namespace") ? t.namespace.split(".") : []; + if (u = h = s = i = i || r, 3 !== i.nodeType && 8 !== i.nodeType && !lt.test(m + w.event.triggered) && (m.indexOf(".") > -1 && (m = (b = m.split(".")).shift(), b.sort()), c = m.indexOf(":") < 0 && "on" + m, t = t[w.expando] ? t : new w.Event(m, "object" == typeof t && t), t.isTrigger = o ? 2 : 3, t.namespace = b.join("."), t.rnamespace = t.namespace ? new RegExp("(^|\\.)" + b.join("\\.(?:.*\\.|)") + "(\\.|$)") : null, t.result = void 0, t.target || (t.target = i), n = null == n ? [t] : w.makeArray(n, [t]), p = w.event.special[m] || {}, o || !p.trigger || !1 !== p.trigger.apply(i, n))) { + if (!o && !p.noBubble && !v(i)) { + for (l = p.delegateType || m, lt.test(l + m) || (u = u.parentNode); u; u = u.parentNode) y.push(u), s = u; + s === (i.ownerDocument || r) && y.push(s.defaultView || s.parentWindow || e) + } + a = 0; + while ((u = y[a++]) && !t.isPropagationStopped()) h = u, t.type = a > 1 ? l : p.bindType || m, (d = (K.get(u, "events") || {})[t.type] && K.get(u, "handle")) && d.apply(u, n), (d = c && u[c]) && d.apply && Y(u) && (t.result = d.apply(u, n), !1 === t.result && t.preventDefault()); + return t.type = m, o || t.isDefaultPrevented() || p._default && !1 !== p._default.apply(y.pop(), n) || !Y(i) || c && g(i[m]) && !v(i) && ((s = i[c]) && (i[c] = null), w.event.triggered = m, t.isPropagationStopped() && h.addEventListener(m, ct), i[m](), t.isPropagationStopped() && h.removeEventListener(m, ct), w.event.triggered = void 0, s && (i[c] = s)), t.result + } + }, + simulate: function(e, t, n) { + var r = w.extend(new w.Event, n, { + type: e, + isSimulated: !0 + }); + w.event.trigger(r, null, t) + } + }), w.fn.extend({ + trigger: function(e, t) { + return this.each(function() { + w.event.trigger(e, t, this) + }) + }, + triggerHandler: function(e, t) { + var n = this[0]; + if (n) return w.event.trigger(e, t, n, !0) + } + }), h.focusin || w.each({ + focus: "focusin", + blur: "focusout" + }, function(e, t) { + var n = function(e) { + w.event.simulate(t, e.target, w.event.fix(e)) + }; + w.event.special[t] = { + setup: function() { + var r = this.ownerDocument || this, + i = K.access(r, t); + i || r.addEventListener(e, n, !0), K.access(r, t, (i || 0) + 1) + }, + teardown: function() { + var r = this.ownerDocument || this, + i = K.access(r, t) - 1; + i ? K.access(r, t, i) : (r.removeEventListener(e, n, !0), K.remove(r, t)) + } + } + }); + var ft = /\[\]$/, + dt = /\r?\n/g, + pt = /^(?:submit|button|image|reset|file)$/i, + ht = /^(?:input|select|textarea|keygen)/i; + + function gt(e, t, n, r) { + var i; + if (Array.isArray(t)) w.each(t, function(t, i) { + n || ft.test(e) ? r(e, i) : gt(e + "[" + ("object" == typeof i && null != i ? t : "") + "]", i, n, r) + }); + else if (n || "object" !== b(t)) r(e, t); + else + for (i in t) gt(e + "[" + i + "]", t[i], n, r) + } + w.param = function(e, t) { + var n, r = [], + i = function(e, t) { + var n = g(t) ? t() : t; + r[r.length] = encodeURIComponent(e) + "=" + encodeURIComponent(null == n ? "" : n) + }; + if (Array.isArray(e) || e.jquery && !w.isPlainObject(e)) w.each(e, function() { + i(this.name, this.value) + }); + else + for (n in e) gt(n, e[n], t, i); + return r.join("&") + }, w.fn.extend({ + serialize: function() { + return w.param(this.serializeArray()) + }, + serializeArray: function() { + return this.map(function() { + var e = w.prop(this, "elements"); + return e ? w.makeArray(e) : this + }).filter(function() { + var e = this.type; + return this.name && !w(this).is(":disabled") && ht.test(this.nodeName) && !pt.test(e) && (this.checked || !de.test(e)) + }).map(function(e, t) { + var n = w(this).val(); + return null == n ? null : Array.isArray(n) ? w.map(n, function(e) { + return { + name: t.name, + value: e.replace(dt, "\r\n") + } + }) : { + name: t.name, + value: n.replace(dt, "\r\n") + } + }).get() + } + }), w.fn.extend({ + wrapAll: function(e) { + var t; + return this[0] && (g(e) && (e = e.call(this[0])), t = w(e, this[0].ownerDocument).eq(0).clone(!0), this[0].parentNode && t.insertBefore(this[0]), t.map(function() { + var e = this; + while (e.firstElementChild) e = e.firstElementChild; + return e + }).append(this)), this + }, + wrapInner: function(e) { + return g(e) ? this.each(function(t) { + w(this).wrapInner(e.call(this, t)) + }) : this.each(function() { + var t = w(this), + n = t.contents(); + n.length ? n.wrapAll(e) : t.append(e) + }) + }, + wrap: function(e) { + var t = g(e); + return this.each(function(n) { + w(this).wrapAll(t ? e.call(this, n) : e) + }) + }, + unwrap: function(e) { + return this.parent(e).not("body").each(function() { + w(this).replaceWith(this.childNodes) + }), this + } + }), w.expr.pseudos.hidden = function(e) { + return !w.expr.pseudos.visible(e) + }, w.expr.pseudos.visible = function(e) { + return !!(e.offsetWidth || e.offsetHeight || e.getClientRects().length) + }, h.createHTMLDocument = function() { + var e = r.implementation.createHTMLDocument("").body; + return e.innerHTML = "
    ", 2 === e.childNodes.length + }(), w.parseHTML = function(e, t, n) { + if ("string" != typeof e) return []; + "boolean" == typeof t && (n = t, t = !1); + var i, o, a; + return t || (h.createHTMLDocument ? ((i = (t = r.implementation.createHTMLDocument("")).createElement("base")).href = r.location.href, t.head.appendChild(i)) : t = r), o = S.exec(e), a = !n && [], o ? [t.createElement(o[1])] : (o = be([e], t, a), a && a.length && w(a).remove(), w.merge([], o.childNodes)) + }, w.offset = { + setOffset: function(e, t, n) { + var r, i, o, a, u, s, l, c = w.css(e, "position"), + f = w(e), + d = {}; + "static" === c && (e.style.position = "relative"), u = f.offset(), o = w.css(e, "top"), s = w.css(e, "left"), (l = ("absolute" === c || "fixed" === c) && (o + s).indexOf("auto") > -1) ? (a = (r = f.position()).top, i = r.left) : (a = parseFloat(o) || 0, i = parseFloat(s) || 0), g(t) && (t = t.call(e, n, w.extend({}, u))), null != t.top && (d.top = t.top - u.top + a), null != t.left && (d.left = t.left - u.left + i), "using" in t ? t.using.call(e, d) : f.css(d) + } + }, w.fn.extend({ + offset: function(e) { + if (arguments.length) return void 0 === e ? this : this.each(function(t) { + w.offset.setOffset(this, e, t) + }); + var t, n, r = this[0]; + if (r) return r.getClientRects().length ? (t = r.getBoundingClientRect(), n = r.ownerDocument.defaultView, { + top: t.top + n.pageYOffset, + left: t.left + n.pageXOffset + }) : { + top: 0, + left: 0 + } + }, + position: function() { + if (this[0]) { + var e, t, n, r = this[0], + i = { + top: 0, + left: 0 + }; + if ("fixed" === w.css(r, "position")) t = r.getBoundingClientRect(); + else { + t = this.offset(), n = r.ownerDocument, e = r.offsetParent || n.documentElement; + while (e && (e === n.body || e === n.documentElement) && "static" === w.css(e, "position")) e = e.parentNode; + e && e !== r && 1 === e.nodeType && ((i = w(e).offset()).top += w.css(e, "borderTopWidth", !0), i.left += w.css(e, "borderLeftWidth", !0)) + } + return { + top: t.top - i.top - w.css(r, "marginTop", !0), + left: t.left - i.left - w.css(r, "marginLeft", !0) + } + } + }, + offsetParent: function() { + return this.map(function() { + var e = this.offsetParent; + while (e && "static" === w.css(e, "position")) e = e.offsetParent; + return e || xe + }) + } + }), w.each({ + scrollLeft: "pageXOffset", + scrollTop: "pageYOffset" + }, function(e, t) { + var n = "pageYOffset" === t; + w.fn[e] = function(r) { + return _(this, function(e, r, i) { + var o; + if (v(e) ? o = e : 9 === e.nodeType && (o = e.defaultView), void 0 === i) return o ? o[t] : e[r]; + o ? o.scrollTo(n ? o.pageXOffset : i, n ? i : o.pageYOffset) : e[r] = i + }, e, r, arguments.length) + } + }), w.each(["top", "left"], function(e, t) { + w.cssHooks[t] = ze(h.pixelPosition, function(e, n) { + if (n) return n = Fe(e, t), Me.test(n) ? w(e).position()[t] + "px" : n + }) + }), w.each({ + Height: "height", + Width: "width" + }, function(e, t) { + w.each({ + padding: "inner" + e, + content: t, + "": "outer" + e + }, function(n, r) { + w.fn[r] = function(i, o) { + var a = arguments.length && (n || "boolean" != typeof i), + u = n || (!0 === i || !0 === o ? "margin" : "border"); + return _(this, function(t, n, i) { + var o; + return v(t) ? 0 === r.indexOf("outer") ? t["inner" + e] : t.document.documentElement["client" + e] : 9 === t.nodeType ? (o = t.documentElement, Math.max(t.body["scroll" + e], o["scroll" + e], t.body["offset" + e], o["offset" + e], o["client" + e])) : void 0 === i ? w.css(t, n, u) : w.style(t, n, i, u) + }, t, a ? i : void 0, a) + } + }) + }), w.each("blur focus focusin focusout resize scroll click dblclick mousedown mouseup mousemove mouseover mouseout mouseenter mouseleave change select submit keydown keypress keyup contextmenu".split(" "), function(e, t) { + w.fn[t] = function(e, n) { + return arguments.length > 0 ? this.on(t, null, e, n) : this.trigger(t) + } + }), w.fn.extend({ + hover: function(e, t) { + return this.mouseenter(e).mouseleave(t || e) + } + }), w.fn.extend({ + bind: function(e, t, n) { + return this.on(e, null, t, n) + }, + unbind: function(e, t) { + return this.off(e, null, t) + }, + delegate: function(e, t, n, r) { + return this.on(t, e, n, r) + }, + undelegate: function(e, t, n) { + return 1 === arguments.length ? this.off(e, "**") : this.off(t, e || "**", n) + } + }), w.proxy = function(e, t) { + var n, r, i; + if ("string" == typeof t && (n = e[t], t = e, e = n), g(e)) return r = o.call(arguments, 2), i = function() { + return e.apply(t || this, r.concat(o.call(arguments))) + }, i.guid = e.guid = e.guid || w.guid++, i + }, w.holdReady = function(e) { + e ? w.readyWait++ : w.ready(!0) + }, w.isArray = Array.isArray, w.parseJSON = JSON.parse, w.nodeName = D, w.isFunction = g, w.isWindow = v, w.camelCase = Q, w.type = b, w.now = Date.now, w.isNumeric = function(e) { + var t = w.type(e); + return ("number" === t || "string" === t) && !isNaN(e - parseFloat(e)) + }, "function" == typeof define && define.amd && define("jquery", [], function() { + return w + }); + var vt = e.jQuery, + yt = e.$; + return w.noConflict = function(t) { + return e.$ === w && (e.$ = yt), t && e.jQuery === w && (e.jQuery = vt), w + }, t || (e.jQuery = e.$ = w), w +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/libjass/libjass.min.js b/dashboard-ui/bower_components/libjass/libjass.min.js index f24eea86b7..91852a830a 100644 --- a/dashboard-ui/bower_components/libjass/libjass.min.js +++ b/dashboard-ui/bower_components/libjass/libjass.min.js @@ -17,8 +17,4169 @@ * See the License for the specific language governing permissions and * limitations under the License. */ -!function(e,t){var r=this;"function"==typeof define&&define.amd?define([],function(){return t(r)}):"object"==typeof exports&&"object"==typeof module?module.exports=t(r):"object"==typeof exports?exports.libjass=t(r):e.libjass=t(r)}(this,function(e){"use strict";return function(e){function t(n){if(r[n])return r[n];var i=r[n]=Object.create(null);return e[n](i,t),i}var r=Object.create(null);return t(0)}([function(e,t){var r=t(23),n=t(23);e.debugMode=n.debugMode,e.verboseMode=n.verboseMode;var i=t(33),o=t(33);e.Set=o.Set;var a=t(30),l=t(30);e.Map=l.Map;var s=t(32),u=t(32);e.Promise=u.Promise,e.DeferredPromise=u.DeferredPromise;var p=t(37);e.webworker=p;var c=t(8);e.parts=c;var h=t(1);e.parser=h;var f=t(14);e.renderers=f;var d=t(24);e.ASS=d.ASS;var _=t(25);e.Attachment=_.Attachment,e.AttachmentType=_.AttachmentType;var g=t(26);e.Dialogue=g.Dialogue;var v=t(28);e.ScriptProperties=v.ScriptProperties;var y=t(29);e.Style=y.Style;var m=t(27);e.BorderStyle=m.BorderStyle,e.Format=m.Format,e.WrappingStyle=m.WrappingStyle,Object.defineProperties(e,{debugMode:{get:function(){return r.debugMode},set:r.setDebugMode},verboseMode:{get:function(){return r.verboseMode},set:r.setVerboseMode},Set:{get:function(){return i.Set},set:i.setImplementation},Map:{get:function(){return a.Map},set:a.setImplementation},Promise:{get:function(){return s.Promise},set:s.setImplementation}})},function(e,t){var r=t(3);e.parse=r.parse;var n=t(5);e.BrowserReadableStream=n.BrowserReadableStream,e.StringStream=n.StringStream,e.XhrStream=n.XhrStream;var i=t(4);e.StreamParser=i.StreamParser,e.SrtStreamParser=i.SrtStreamParser},function(e,t){function r(e){var t=e.indexOf(":");if(-1===t)return null;var r=e.substr(0,t),n=e.substr(t+1).replace(/^\s+/,"");return{name:r,value:n}}function n(e,t){var n=r(e);if(null===n)return null;var o=n.value.split(",");o.length>t.length&&(o[t.length-1]=o.slice(t.length-1).join(","));var a=new i.Map;return t.forEach(function(e,t){a.set(e,o[t])}),{type:n.name,template:a}}var i=t(30);e.parseLineIntoProperty=r,e.parseLineIntoTypedTemplate=n},function(e,t){function r(e,t){var r=new s(e,t);if(null===r.result||r.result.end!==e.length)throw o.debugMode&&console.error("Parse failed. %s %s %o",t,e,r.result),new Error("Parse failed.");return r.result.value}function n(e,t,r,n){s.prototype["parse_tag_"+e]=function(i){var o=this,a=new h(i);if(null===o.read(a,e))return i.pop(),null;var l=r.call(o,a);if(null!==l)a.value=new t(l.value);else{if(n)return i.pop(),null;a.value=new t(null)}return a}}var i=t(8),o=t(23),a=t(30),l=new a.Map;e.parse=r;var s=function(){function e(e,t){this.e=e,this.t=new h(null),this.r=l.get(t).call(this,this.t)}return Object.defineProperty(e.prototype,"result",{get:function(){return this.r},enumerable:!0,configurable:!0}),e.prototype.parse_dialogueParts=function(e){var t,n=new h(e);for(n.value=[];this.n();){var o=this.parse_enclosedTags(n);if(null!==o)(t=n.value).push.apply(t,o.value);else{var a=this.parse_newline(n)||this.parse_hardspace(n)||this.parse_text(n);if(null===a)return e.pop(),null;if(a.value instanceof i.Text&&n.value[n.value.length-1]instanceof i.Text){var l=n.value[n.value.length-1];n.value[n.value.length-1]=new i.Text(l.value+a.value.value)}else n.value.push(a.value)}}var s=!1;return n.value.forEach(function(e,t){e instanceof i.DrawingMode?s=0!==e.scale:e instanceof i.Text&&s&&(n.value[t]=new i.DrawingInstructions(r(e.value,"drawingInstructions")))}),n},e.prototype.parse_enclosedTags=function(e){var t=new h(e);if(t.value=[],null===this.read(t,"{"))return e.pop(),null;for(var r=this.i();this.n()&&"}"!==r;r=this.i()){var n=null;if(null!==this.read(t,"\\")&&(n=this.parse_tag_alpha(t)||this.parse_tag_iclip(t)||this.parse_tag_xbord(t)||this.parse_tag_ybord(t)||this.parse_tag_xshad(t)||this.parse_tag_yshad(t)||this.parse_tag_blur(t)||this.parse_tag_bord(t)||this.parse_tag_clip(t)||this.parse_tag_fade(t)||this.parse_tag_fscx(t)||this.parse_tag_fscy(t)||this.parse_tag_move(t)||this.parse_tag_shad(t)||this.parse_tag_fad(t)||this.parse_tag_fax(t)||this.parse_tag_fay(t)||this.parse_tag_frx(t)||this.parse_tag_fry(t)||this.parse_tag_frz(t)||this.parse_tag_fsp(t)||this.parse_tag_fsplus(t)||this.parse_tag_fsminus(t)||this.parse_tag_org(t)||this.parse_tag_pbo(t)||this.parse_tag_pos(t)||this.parse_tag_an(t)||this.parse_tag_be(t)||this.parse_tag_fn(t)||this.parse_tag_fr(t)||this.parse_tag_fs(t)||this.parse_tag_kf(t)||this.parse_tag_ko(t)||this.parse_tag_1a(t)||this.parse_tag_1c(t)||this.parse_tag_2a(t)||this.parse_tag_2c(t)||this.parse_tag_3a(t)||this.parse_tag_3c(t)||this.parse_tag_4a(t)||this.parse_tag_4c(t)||this.parse_tag_a(t)||this.parse_tag_b(t)||this.parse_tag_c(t)||this.parse_tag_i(t)||this.parse_tag_k(t)||this.parse_tag_K(t)||this.parse_tag_p(t)||this.parse_tag_q(t)||this.parse_tag_r(t)||this.parse_tag_s(t)||this.parse_tag_t(t)||this.parse_tag_u(t),null===n&&t.pop()),null===n&&(n=this.parse_comment(t)),null===n)return e.pop(),null;n.value instanceof i.Comment&&t.value[t.value.length-1]instanceof i.Comment?t.value[t.value.length-1]=new i.Comment(t.value[t.value.length-1].value+n.value.value):t.value.push(n.value)}return null===this.read(t,"}")?(e.pop(),null):t},e.prototype.parse_newline=function(e){var t=new h(e);return null===this.read(t,"\\N")?(e.pop(),null):(t.value=new i.NewLine,t)},e.prototype.parse_hardspace=function(e){var t=new h(e);return null===this.read(t,"\\h")?(e.pop(),null):(t.value=new i.Text(" "),t)},e.prototype.parse_text=function(e){var t=this.i(),r=new h(e),n=new h(r,t);return r.value=new i.Text(n.value),r},e.prototype.parse_comment=function(e){var t=this.i(),r=new h(e),n=new h(r,t);return r.value=new i.Comment(n.value),r},e.prototype.parse_tag_a=function(e){var t=new h(e);if(null===this.read(t,"a"))return e.pop(),null;var r=this.i();switch(r){case"1":var n=this.i(2);switch(n){case"10":case"11":r=n}break;case"2":case"3":case"5":case"6":case"7":case"9":break;default:return e.pop(),null}var o=new h(t,r),a=null;switch(o.value){case"1":a=1;break;case"2":a=2;break;case"3":a=3;break;case"5":a=7;break;case"6":a=8;break;case"7":a=9;break;case"9":a=4;break;case"10":a=5;break;case"11":a=6}return t.value=new i.Alignment(a),t},e.prototype.parse_tag_alpha=function(){throw new Error("Method not implemented.")},e.prototype.parse_tag_an=function(e){var t=new h(e);if(null===this.read(t,"an"))return e.pop(),null;var r=this.i();if("1">r||r>"9")return e.pop(),null;var n=new h(t,r);return t.value=new i.Alignment(parseInt(n.value)),t},e.prototype.parse_tag_b=function(e){var t=new h(e);if(null===this.read(t,"b"))return e.pop(),null;var r=null,n=this.i();return n>="1"&&"9">=n&&(n=this.i(3),"00"===n.substr(1)&&(r=new h(t,n),r.value=parseInt(r.value))),null===r&&(r=this.parse_enableDisable(t)),null!==r?t.value=new i.Bold(r.value):t.value=new i.Bold(null),t},e.prototype.parse_tag_be=function(){throw new Error("Method not implemented.")},e.prototype.parse_tag_blur=function(){throw new Error("Method not implemented.")},e.prototype.parse_tag_bord=function(){throw new Error("Method not implemented.")},e.prototype.parse_tag_c=function(){throw new Error("Method not implemented.")},e.prototype.parse_tag_clip=function(e){return this.o("clip",e)},e.prototype.parse_tag_fad=function(e){var t=new h(e);if(null===this.read(t,"fad"))return e.pop(),null;if(null===this.read(t,"("))return e.pop(),null;var r=this.parse_decimal(t);if(null===r)return e.pop(),null;if(null===this.read(t,","))return e.pop(),null;var n=this.parse_decimal(t);return null===n?(e.pop(),null):null===this.read(t,")")?(e.pop(),null):(t.value=new i.Fade(r.value/1e3,n.value/1e3),t)},e.prototype.parse_tag_fade=function(e){var t=new h(e);if(null===this.read(t,"fade"))return e.pop(),null;if(null===this.read(t,"("))return e.pop(),null;var r=this.parse_decimal(t);if(null===r)return e.pop(),null;if(null===this.read(t,","))return e.pop(),null;var n=this.parse_decimal(t);if(null===n)return e.pop(),null;if(null===this.read(t,","))return e.pop(),null;var o=this.parse_decimal(t);if(null===o)return e.pop(),null;if(null===this.read(t,","))return e.pop(),null;var a=this.parse_decimal(t);if(null===a)return e.pop(),null;if(null===this.read(t,","))return e.pop(),null;var l=this.parse_decimal(t);if(null===l)return e.pop(),null;if(null===this.read(t,","))return e.pop(),null;var s=this.parse_decimal(t);if(null===s)return e.pop(),null;if(null===this.read(t,","))return e.pop(),null;var u=this.parse_decimal(t);return null===u?(e.pop(),null):null===this.read(t,")")?(e.pop(),null):(t.value=new i.ComplexFade(1-r.value/255,1-n.value/255,1-o.value/255,a.value/1e3,l.value/1e3,s.value/1e3,u.value/1e3),t)},e.prototype.parse_tag_fax=function(){throw new Error("Method not implemented.")},e.prototype.parse_tag_fay=function(){throw new Error("Method not implemented.")},e.prototype.parse_tag_fn=function(e){var t=new h(e);if(null===this.read(t,"fn"))return e.pop(),null;for(var r=new h(t,""),n=this.i();this.n()&&"\\"!==n&&"}"!==n;n=this.i())r.value+=n;return r.value.length>0?t.value=new i.FontName(r.value):t.value=new i.FontName(null),t},e.prototype.parse_tag_fr=function(){throw new Error("Method not implemented.")},e.prototype.parse_tag_frx=function(){throw new Error("Method not implemented.")},e.prototype.parse_tag_fry=function(){throw new Error("Method not implemented.")},e.prototype.parse_tag_frz=function(){throw new Error("Method not implemented.")},e.prototype.parse_tag_fs=function(){throw new Error("Method not implemented.")},e.prototype.parse_tag_fsplus=function(e){var t=new h(e);if(null===this.read(t,"fs+"))return e.pop(),null;var r=this.parse_decimal(t);return null===r?(e.pop(),null):(t.value=new i.FontSizePlus(r.value),t)},e.prototype.parse_tag_fsminus=function(e){var t=new h(e);if(null===this.read(t,"fs-"))return e.pop(),null;var r=this.parse_decimal(t);return null===r?(e.pop(),null):(t.value=new i.FontSizeMinus(r.value),t)},e.prototype.parse_tag_fscx=function(e){var t=new h(e);if(null===this.read(t,"fscx"))return e.pop(),null;var r=this.parse_decimal(t);return null!==r?t.value=new i.FontScaleX(r.value/100):t.value=new i.FontScaleX(null),t},e.prototype.parse_tag_fscy=function(e){var t=new h(e);if(null===this.read(t,"fscy"))return e.pop(),null;var r=this.parse_decimal(t);return null!==r?t.value=new i.FontScaleY(r.value/100):t.value=new i.FontScaleY(null),t},e.prototype.parse_tag_fsp=function(){throw new Error("Method not implemented.")},e.prototype.parse_tag_i=function(){throw new Error("Method not implemented.")},e.prototype.parse_tag_iclip=function(e){return this.o("iclip",e)},e.prototype.parse_tag_k=function(e){var t=new h(e);if(null===this.read(t,"k"))return e.pop(),null;var r=this.parse_decimal(t);return null===r?(e.pop(),null):(t.value=new i.ColorKaraoke(r.value/100),t)},e.prototype.parse_tag_K=function(e){var t=new h(e);if(null===this.read(t,"K"))return e.pop(),null;var r=this.parse_decimal(t);return null===r?(e.pop(),null):(t.value=new i.SweepingColorKaraoke(r.value/100),t)},e.prototype.parse_tag_kf=function(e){var t=new h(e);if(null===this.read(t,"kf"))return e.pop(),null;var r=this.parse_decimal(t);return null===r?(e.pop(),null):(t.value=new i.SweepingColorKaraoke(r.value/100),t)},e.prototype.parse_tag_ko=function(e){var t=new h(e);if(null===this.read(t,"ko"))return e.pop(),null;var r=this.parse_decimal(t);return null===r?(e.pop(),null):(t.value=new i.OutlineKaraoke(r.value/100),t)},e.prototype.parse_tag_move=function(e){var t=new h(e);if(null===this.read(t,"move"))return e.pop(),null;if(null===this.read(t,"("))return e.pop(),null;var r=this.parse_decimal(t);if(null===r)return e.pop(),null;if(null===this.read(t,","))return e.pop(),null;var n=this.parse_decimal(t);if(null===n)return e.pop(),null;if(null===this.read(t,","))return e.pop(),null;var o=this.parse_decimal(t);if(null===o)return e.pop(),null;if(null===this.read(t,","))return e.pop(),null;var a=this.parse_decimal(t);if(null===a)return e.pop(),null;var l=null,s=null;if(null!==this.read(t,",")){if(l=this.parse_decimal(t),null===l)return e.pop(),null;if(null===this.read(t,","))return e.pop(),null;if(s=this.parse_decimal(t),null===s)return e.pop(),null}return null===this.read(t,")")?(e.pop(),null):(t.value=new i.Move(r.value,n.value,o.value,a.value,null!==l?l.value/1e3:null,null!==s?s.value/1e3:null),t)},e.prototype.parse_tag_org=function(e){var t=new h(e);if(null===this.read(t,"org"))return e.pop(),null;if(null===this.read(t,"("))return e.pop(),null;var r=this.parse_decimal(t);if(null===r)return e.pop(),null;if(null===this.read(t,","))return e.pop(),null;var n=this.parse_decimal(t);return null===n?(e.pop(),null):null===this.read(t,")")?(e.pop(),null):(t.value=new i.RotationOrigin(r.value,n.value),t)},e.prototype.parse_tag_p=function(){throw new Error("Method not implemented.")},e.prototype.parse_tag_pbo=function(){throw new Error("Method not implemented.")},e.prototype.parse_tag_pos=function(e){var t=new h(e);if(null===this.read(t,"pos"))return e.pop(),null;if(null===this.read(t,"("))return e.pop(),null;var r=this.parse_decimal(t);if(null===r)return e.pop(),null;if(null===this.read(t,","))return e.pop(),null;var n=this.parse_decimal(t);return null===n?(e.pop(),null):null===this.read(t,")")?(e.pop(),null):(t.value=new i.Position(r.value,n.value),t)},e.prototype.parse_tag_q=function(e){var t=new h(e);if(null===this.read(t,"q"))return e.pop(),null;var r=this.i();if("0">r||r>"3")return e.pop(),null;var n=new h(t,r);return t.value=new i.WrappingStyle(parseInt(n.value)),t},e.prototype.parse_tag_r=function(e){var t=new h(e);if(null===this.read(t,"r"))return e.pop(),null;for(var r=new h(t,""),n=this.i();this.n()&&"\\"!==n&&"}"!==n;n=this.i())r.value+=n;return r.value.length>0?t.value=new i.Reset(r.value):t.value=new i.Reset(null),t},e.prototype.parse_tag_s=function(){throw new Error("Method not implemented.")},e.prototype.parse_tag_shad=function(){throw new Error("Method not implemented.")},e.prototype.parse_tag_t=function(e){var t=new h(e);if(null===this.read(t,"t"))return e.pop(),null;if(null===this.read(t,"("))return e.pop(),null;var r=null,n=null,o=null,a=this.parse_decimal(t);if(null!==a){if(null===this.read(t,","))return e.pop(),null;var l=this.parse_decimal(t);if(null!==l){if(r=a,n=l,null===this.read(t,","))return e.pop(),null;var s=this.parse_decimal(t);if(null!==s&&(o=s,null===this.read(t,",")))return e.pop(),null}else if(o=a,null===this.read(t,","))return e.pop(),null}for(var u=[],p=this.i();this.n()&&")"!==p&&"}"!==p;p=this.i()){var c=null;if(null!==this.read(t,"\\")&&(c=this.parse_tag_alpha(t)||this.parse_tag_iclip(t)||this.parse_tag_xbord(t)||this.parse_tag_ybord(t)||this.parse_tag_xshad(t)||this.parse_tag_yshad(t)||this.parse_tag_blur(t)||this.parse_tag_bord(t)||this.parse_tag_clip(t)||this.parse_tag_fscx(t)||this.parse_tag_fscy(t)||this.parse_tag_shad(t)||this.parse_tag_fax(t)||this.parse_tag_fay(t)||this.parse_tag_frx(t)||this.parse_tag_fry(t)||this.parse_tag_frz(t)||this.parse_tag_fsp(t)||this.parse_tag_fsplus(t)||this.parse_tag_fsminus(t)||this.parse_tag_be(t)||this.parse_tag_fr(t)||this.parse_tag_fs(t)||this.parse_tag_1a(t)||this.parse_tag_1c(t)||this.parse_tag_2a(t)||this.parse_tag_2c(t)||this.parse_tag_3a(t)||this.parse_tag_3c(t)||this.parse_tag_4a(t)||this.parse_tag_4c(t)||this.parse_tag_c(t),null===c&&t.pop()),null===c&&(c=this.parse_comment(t)),null===c)return e.pop(),null;c.value instanceof i.Comment&&u[u.length-1]instanceof i.Comment?u[u.length-1]=new i.Comment(u[u.length-1].value+c.value.value):u.push(c.value)}return this.read(t,")"),t.value=new i.Transform(null!==r?r.value/1e3:null,null!==n?n.value/1e3:null,null!==o?o.value/1e3:null,u),t},e.prototype.parse_tag_u=function(){throw new Error("Method not implemented.")},e.prototype.parse_tag_xbord=function(){throw new Error("Method not implemented.")},e.prototype.parse_tag_xshad=function(){throw new Error("Method not implemented.")},e.prototype.parse_tag_ybord=function(){throw new Error("Method not implemented.")},e.prototype.parse_tag_yshad=function(){throw new Error("Method not implemented.")},e.prototype.parse_tag_1a=function(){throw new Error("Method not implemented.")},e.prototype.parse_tag_1c=function(){throw new Error("Method not implemented.")},e.prototype.parse_tag_2a=function(){throw new Error("Method not implemented.")},e.prototype.parse_tag_2c=function(){throw new Error("Method not implemented.")},e.prototype.parse_tag_3a=function(){throw new Error("Method not implemented.")},e.prototype.parse_tag_3c=function(){throw new Error("Method not implemented.")},e.prototype.parse_tag_4a=function(){throw new Error("Method not implemented.")},e.prototype.parse_tag_4c=function(){throw new Error("Method not implemented.")},e.prototype.parse_drawingInstructions=function(e){var t=new h(e),r=null,n=[];for(t.value=[];this.n();){for(;null!==this.read(t," "););if(!this.n())break;if(null!==r){var o=this.parse_decimal(t);if(null!==o){n.push(o),"m"===r&&2===n.length?(t.value.push(new i.drawing.MoveInstruction(n[0].value,n[1].value)),n.splice(0,n.length)):"l"===r&&2===n.length?(t.value.push(new i.drawing.LineInstruction(n[0].value,n[1].value)),n.splice(0,n.length)):"b"===r&&6===n.length&&(t.value.push(new i.drawing.CubicBezierCurveInstruction(n[0].value,n[1].value,n[2].value,n[3].value,n[4].value,n[5].value)),n.splice(0,n.length));continue}}var a=this.parse_text(t);if(null===a)break;var l=a.value.value;switch(l){case"m":case"l":case"b":r=l,n.splice(0,n.length)}}for(;null!==this.read(t," "););return t},e.prototype.parse_decimalInt32=function(e){for(var t=new h(e),r=null!==this.read(t,"-"),n=new h(t,""),i=this.i();this.n()&&i>="0"&&"9">=i;i=this.i())n.value+=i;if(0===n.value.length)return e.pop(),null;var o=parseInt(n.value);return o>=4294967295?o=4294967295:r&&(o=-o),t.value=o,t},e.prototype.parse_hexInt32=function(e){for(var t=new h(e),r=null!==this.read(t,"-"),n=new h(t,""),i=this.i();this.n()&&(i>="0"&&"9">=i||i>="a"&&"f">=i||i>="A"&&"F">=i);i=this.i())n.value+=i;if(0===n.value.length)return e.pop(),null;var o=parseInt(n.value,16);return o>=4294967295?o=4294967295:r&&(o=-o),t.value=o,t},e.prototype.parse_decimalOrHexInt32=function(e){var t=new h(e),r=null!==this.read(t,"&H")||null!==this.read(t,"&h")?this.parse_hexInt32(t):this.parse_decimalInt32(t);return null===r?(e.pop(),null):(t.value=r.value,t)},e.prototype.parse_decimal=function(e){var t=new h(e),r=null!==this.read(t,"-"),n=this.parse_unsignedDecimal(t);return null===n?(e.pop(),null):(t.value=n.value,r&&(t.value=-t.value),t)},e.prototype.parse_unsignedDecimal=function(e){for(var t=new h(e),r=new h(t,""),n=null,i=this.i();this.n()&&i>="0"&&"9">=i;i=this.i())r.value+=i;if(0===r.value.length)return e.pop(),null;if(null!==this.read(t,".")){n=new h(t,"");for(var i=this.i();this.n()&&i>="0"&&"9">=i;i=this.i())n.value+=i;if(0===n.value.length)return e.pop(),null}return t.value=parseFloat(r.value+(null!==n?"."+n.value:"")),t},e.prototype.parse_enableDisable=function(e){var t=this.i();if("0"===t||"1"===t){var r=new h(e,t);return r.value="1"===r.value,r}return null},e.prototype.parse_color=function(e){for(var t=new h(e);null!==this.read(t,"&")||null!==this.read(t,"H"););var r=this.parse_hexInt32(t);if(null===r)return e.pop(),null;var n=r.value;for(t.value=new i.Color(255&n,n>>8&255,n>>16&255);null!==this.read(t,"&")||null!==this.read(t,"H"););return t},e.prototype.parse_alpha=function(e){for(var t=new h(e);null!==this.read(t,"&")||null!==this.read(t,"H"););var r=this.parse_hexInt32(t);if(null===r)return e.pop(),null;var n=r.value;for(t.value=1-(255&n)/255;null!==this.read(t,"&")||null!==this.read(t,"H"););return t},e.prototype.parse_colorWithAlpha=function(e){var t=new h(e),r=this.parse_decimalOrHexInt32(t);if(null===r)return e.pop(),null;var n=r.value;return t.value=new i.Color(255&n,n>>8&255,n>>16&255,1-(n>>24&255)/255),t},e.prototype.read=function(e,t){return this.i(t.length)!==t?null:new h(e,t)},e.prototype.i=function(e){return void 0===e&&(e=1),1===e?this.e[this.t.end]:this.e.substr(this.t.end,e)},e.prototype.n=function(){return this.t.end0?this.c(this.l[this.l.length-1].end):this.c(this.start)},e.prototype.c=function(e){this.u=e,null!==this.a&&this.a.end!==this.u&&this.a.c(this.u)},e}(),f=t(32),d=t(36),_=t(38);_.registerWorkerCommand(d.WorkerCommands.Parse,function(e){return new f.Promise(function(t){t(r(e.input,e.rule))})})},function(e,t){function r(e){for(var t="",r=0;rn||n>63)throw new Error("Out-of-range character code "+n+" at index "+r+" in string "+e);t+=26>n?String.fromCharCode("A".charCodeAt(0)+n):52>n?String.fromCharCode("a".charCodeAt(0)+n-26):62>n?String.fromCharCode("0".charCodeAt(0)+n-52):62===n?"+":"/"}return t}var n,i=t(23),o=t(24),a=t(29),l=t(26),s=t(25),u=t(30),p=t(32),c=t(2);!function(e){e[e.ScriptInfo=0]="ScriptInfo",e[e.Styles=1]="Styles",e[e.Events=2]="Events",e[e.Fonts=3]="Fonts",e[e.Graphics=4]="Graphics",e[e.Other=5]="Other",e[e.EOF=6]="EOF"}(n||(n={}));var h=function(){function e(e){var t=this;this.h=e,this.f=new o.ASS,this.d=new p.DeferredPromise,this._=new p.DeferredPromise,this.g=!0,this.v=n.ScriptInfo,this.y=null,this.h.nextLine().then(function(e){return t.m(e)},function(e){t.d.reject(e),t._.reject(e)})}return Object.defineProperty(e.prototype,"minimalASS",{get:function(){return this.d.promise},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"ass",{get:function(){return this._.promise},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"currentSection",{get:function(){return this.v},set:function(e){if(null!==this.y&&(this.f.addAttachment(this.y),this.y=null),this.v===n.ScriptInfo&&e!==n.ScriptInfo&&this.d.resolve(this.f),e===n.EOF){var t=this.f.properties;void 0===t.resolutionX||void 0===t.resolutionY?(this.d.reject("Malformed ASS script."),this._.reject("Malformed ASS script.")):(this.d.resolve(this.f),this._.resolve(this.f))}this.v=e},enumerable:!0,configurable:!0}),e.prototype.m=function(e){var t=this;if(null===e)return void(this.currentSection=n.EOF);if("\r"===e[e.length-1]&&(e=e.substr(0,e.length-1)),65279===e.charCodeAt(0)&&this.g&&(e=e.substr(1)),this.g=!1,""===e);else if(";"===e[0]&&null===this.y);else if("[Script Info]"===e)this.currentSection=n.ScriptInfo;else if("[V4+ Styles]"===e||"[V4 Styles]"===e)this.currentSection=n.Styles;else if("[Events]"===e)this.currentSection=n.Events;else if("[Fonts]"===e)this.currentSection=n.Fonts;else if("[Graphics]"===e)this.currentSection=n.Graphics;else switch(null===this.y&&"["===e[0]&&"]"===e[e.length-1]&&(this.currentSection=n.Other),this.currentSection){case n.ScriptInfo:var o=c.parseLineIntoProperty(e);if(null!==o)switch(o.name){case"PlayResX":this.f.properties.resolutionX=parseInt(o.value);break;case"PlayResY":this.f.properties.resolutionY=parseInt(o.value);break;case"WrapStyle":this.f.properties.wrappingStyle=parseInt(o.value);break;case"ScaledBorderAndShadow":this.f.properties.scaleBorderAndShadow="yes"===o.value}break;case n.Styles:if(null===this.f.stylesFormatSpecifier){var a=c.parseLineIntoProperty(e);null!==a&&"Format"===a.name&&(this.f.stylesFormatSpecifier=a.value.split(",").map(function(e){return e.trim()}))}else try{this.f.addStyle(e)}catch(t){i.debugMode&&console.error("Could not parse style from line "+e+" - "+(t.stack||t))}break;case n.Events:if(null===this.f.dialoguesFormatSpecifier){var l=c.parseLineIntoProperty(e);null!==l&&"Format"===l.name&&(this.f.dialoguesFormatSpecifier=l.value.split(",").map(function(e){return e.trim()}))}else try{this.f.addEvent(e)}catch(t){i.debugMode&&console.error("Could not parse event from line "+e+" - "+(t.stack||t))}break;case n.Fonts:case n.Graphics:var u=this.currentSection===n.Fonts?/^fontname:(.+)/:/^filename:(.+)/,p=u.exec(e);if(null!==p)null!==this.y&&(this.f.addAttachment(this.y),this.y=null),this.y=new s.Attachment(p[1].trim(),this.currentSection===n.Fonts?s.AttachmentType.Font:s.AttachmentType.Graphic);else if(null!==this.y)try{this.y.contents+=r(e)}catch(e){i.debugMode&&console.error("Encountered error while reading font "+this.y.filename+": %o",e),this.y=null}break;case n.Other:break;default:throw new Error("Unhandled state "+this.currentSection)}this.h.nextLine().then(function(e){return t.m(e)},function(e){t.d.reject(e),t._.reject(e)})},e}();e.StreamParser=h;var f=function(){function e(e){var t=this;this.h=e,this.f=new o.ASS,this._=new p.DeferredPromise,this.g=!0,this.b=null,this.w=null,this.S=null,this.O=null,this.h.nextLine().then(function(e){return t.m(e)},function(e){t._.reject(e)}),this.f.properties.resolutionX=1280,this.f.properties.resolutionY=720,this.f.properties.wrappingStyle=1,this.f.properties.scaleBorderAndShadow=!0;var r=new a.Style(new u.Map([["Name","Default"],["FontSize","36"]]));this.f.styles.set(r.name,r)}return Object.defineProperty(e.prototype,"ass",{get:function(){return this._.promise},enumerable:!0,configurable:!0}),e.prototype.m=function(e){var t=this;if(null===e)return null!==this.b&&null!==this.w&&null!==this.S&&null!==this.O&&this.f.dialogues.push(new l.Dialogue(new u.Map([["Style","Default"],["Start",this.w],["End",this.S],["Text",this.O]]),this.f)),void this._.resolve(this.f);if("\r"===e[e.length-1]&&(e=e.substr(0,e.length-1)),65279===e.charCodeAt(0)&&this.g&&(e=e.substr(1)),this.g=!1,""===e)null!==this.b&&null!==this.w&&null!==this.S&&null!==this.O&&this.f.dialogues.push(new l.Dialogue(new u.Map([["Style","Default"],["Start",this.w],["End",this.S],["Text",this.O]]),this.f)),this.b=this.w=this.S=this.O=null;else if(null===this.b)/^\d+$/.test(e)&&(this.b=e);else if(null===this.w&&null===this.S){var r=/^(\d\d:\d\d:\d\d,\d\d\d) --> (\d\d:\d\d:\d\d,\d\d\d)/.exec(e);null!==r&&(this.w=r[1].replace(",","."),this.S=r[2].replace(",","."))}else e=e.replace(//g,"{\\b1}").replace(/\{b\}/g,"{\\b1}").replace(/<\/b>/g,"{\\b0}").replace(/\{\/b\}/g,"{\\b0}").replace(//g,"{\\i1}").replace(/\{i\}/g,"{\\i1}").replace(/<\/i>/g,"{\\i0}").replace(/\{\/i\}/g,"{\\i0}").replace(//g,"{\\u1}").replace(/\{u\}/g,"{\\u1}").replace(/<\/u>/g,"{\\u0}").replace(/\{\/u\}/g,"{\\u0}").replace(//g,function(e,t,r,n){return"{c&H"+n+r+t+"&}"}).replace(/<\/font>/g,"{\\c}"),null!==this.O?this.O+="\\N"+e:this.O=e;this.h.nextLine().then(function(e){return t.m(e)},function(e){t._.reject(e)})},e}();e.SrtStreamParser=f},function(t,r){var n=r(32),i=function(){function e(e){this.P=e,this.C=0}return e.prototype.nextLine=function(){var e=null;if(this.C0?" ":"")+"}"}}},ie=t(38),oe=0,ae=Object.keys(e);oethis.ce?(this._e=null,this.he.pause()):this.he.tick((e-this._e)/1e3*this.he.rate+this.de):(this.de=i,this._e=e,this.he.tick(i)),this.fe=requestAnimationFrame(function(e){return t.ye(e)})},e.prototype.ge=function(){var e=this;null===this.fe&&(this.fe=requestAnimationFrame(function(t){return e.ye(t)}))},e.prototype.ve=function(){null!==this.fe&&(cancelAnimationFrame(this.fe),this.fe=null)},e}();e.AutoClock=i},function(e){var t=function(){function e(){}return e.prototype.addEventListener=function(e,t){var r=this.me.get(e);void 0===r&&this.me.set(e,r=[]),r.push(t)},e.prototype.be=function(e,t){var r=this.me.get(e);if(void 0!==r)for(var n=0;na)return null;var u=document.createElement("div");u.style.marginLeft=(this.ot*e.style.marginLeft).toFixed(3)+"px",u.style.marginRight=(this.ot*e.style.marginRight).toFixed(3)+"px",u.style.marginTop=u.style.marginBottom=(this.at*e.style.marginVertical).toFixed(3)+"px",u.style.minWidth=(this.it-this.ot*(e.style.marginLeft+e.style.marginRight)).toFixed(3)+"px";var p=document.createElement("style");p.id="libjass-animation-styles-"+this.id+"-"+e.id,p.type="text/css";var c=new i.AnimationCollection(this,p),d=document.createElementNS("http://www.w3.org/2000/svg","svg");d.setAttribute("version","1.1"),d.setAttribute("class","libjass-filters"),d.width.baseVal.valueAsString="0",d.height.baseVal.valueAsString="0";var g=document.createElementNS("http://www.w3.org/2000/svg","defs");d.appendChild(g);var y=null,m=new s.SpanStyles(this,e,this.ot,this.at,this.settings,this.tt,g,this.Je),b=null,w=!1,S=function(e){null!==y&&y.hasChildNodes()&&u.appendChild(m.setStylesOnSpan(y,b)),null!==b&&b.animationDelays.forEach(function(e,t){return c.animationDelays.set(t,e)}),e&&(w?u.appendChild(m.makeNewLine()):u.appendChild(document.createElement("br"))),y=document.createElement("span"),b=new i.AnimationCollection(t,p),w=e};S(!1);for(var O=new o.DrawingStyles(this.ot,this.at),P=this.ass.properties.wrappingStyle,C=0,k=0,E=e.parts;k=x.end?1:Math.pow((a-x.start)/(x.end-x.start),x.accel),A=0,T=x.tags;Ar||n.end0||r>0){var l=0,s=!this.De.preciseOutlines&&this.It>0?this.It:1;!function(e){if(r>=t)if(t>0){var n;for(n=0;t>=n;n+=s)e(n,r/t*Math.sqrt(t*t-n*n));n!==t+s&&e(t,0)}else e(0,r);else if(r>0){var i;for(i=0;r>=i;i+=s)e(t/r*Math.sqrt(r*r-i*i),i);i!==r+s&&e(0,r)}else e(t,0)}(function(e,t){var r=document.createElementNS("http://www.w3.org/2000/svg","feMorphology");a.appendChild(r),r.in1.baseVal="source",r.operator.baseVal=SVGFEMorphologyElement.SVG_MORPHOLOGY_OPERATOR_DILATE,r.radiusX.baseVal=e,r.radiusY.baseVal=t,r.result.baseVal="outline"+l,l++});var u=document.createElementNS("http://www.w3.org/2000/svg","feComponentTransfer");a.insertBefore(u,a.firstElementChild),u.in1.baseVal="SourceAlpha",u.result.baseVal="source";var p=document.createElementNS("http://www.w3.org/2000/svg","feFuncA");u.appendChild(p),p.type.baseVal=SVGComponentTransferFunctionElement.SVG_FECOMPONENTTRANSFER_TYPE_LINEAR,p.slope.baseVal=0===i?1:1/i,p.intercept.baseVal=0;var c=document.createElementNS("http://www.w3.org/2000/svg","feMerge");a.appendChild(c);for(var h=0;l>h;h++){var f=document.createElementNS("http://www.w3.org/2000/svg","feMergeNode");c.appendChild(f),f.in1.baseVal="outline"+h}var d=document.createElementNS("http://www.w3.org/2000/svg","feComponentTransfer");a.appendChild(d),d.setAttribute("color-interpolation-filters","sRGB");var _=document.createElementNS("http://www.w3.org/2000/svg","feFuncR");d.appendChild(_),_.type.baseVal=SVGComponentTransferFunctionElement.SVG_FECOMPONENTTRANSFER_TYPE_LINEAR,_.slope.baseVal=0,_.intercept.baseVal=n.red/255*n.alpha;var g=document.createElementNS("http://www.w3.org/2000/svg","feFuncG");d.appendChild(g),g.type.baseVal=SVGComponentTransferFunctionElement.SVG_FECOMPONENTTRANSFER_TYPE_LINEAR,g.slope.baseVal=0,g.intercept.baseVal=n.green/255*n.alpha;var v=document.createElementNS("http://www.w3.org/2000/svg","feFuncB");d.appendChild(v),v.type.baseVal=SVGComponentTransferFunctionElement.SVG_FECOMPONENTTRANSFER_TYPE_LINEAR,v.slope.baseVal=0,v.intercept.baseVal=n.blue/255*n.alpha;var y=document.createElementNS("http://www.w3.org/2000/svg","feFuncA");if(d.appendChild(y),y.type.baseVal=SVGComponentTransferFunctionElement.SVG_FECOMPONENTTRANSFER_TYPE_LINEAR,y.slope.baseVal=n.alpha,y.intercept.baseVal=0,this.It>0){var m=document.createElementNS("http://www.w3.org/2000/svg","feGaussianBlur");a.appendChild(m),m.stdDeviationX.baseVal=this.It,m.stdDeviationY.baseVal=this.It}for(var h=0;h0){var m=document.createElementNS("http://www.w3.org/2000/svg","feGaussianBlur");a.appendChild(m),m.stdDeviationX.baseVal=this.It,m.stdDeviationY.baseVal=this.It}for(var h=0;h0&&(this.ut.appendChild(a),e.style.webkitFilter='url("#'+o+'")',e.style.filter='url("#'+o+'")')},e.prototype.Lt=function(e,t,r,n){var i=this;if(t>0||r>0){var o="";!function(e){for(var n=0;t>=n;n++)for(var i=0===t?r:r*Math.sqrt(1-n*n/(t*t)),o=0;i>=o;o++)e(n,o),0!==n&&e(-n,o),0!==o&&e(n,-o),0!==n&&0!==o&&e(-n,-o)}(function(e,t){o+=", "+n.toString()+" "+e+"px "+t+"px "+i.It.toFixed(3)+"px"}),e.style.textShadow=o.substr(", ".length)}},e.prototype.makeNewLine=function(){var e=document.createElement("br");return e.style.lineHeight=(this.at*this.bt).toFixed(3)+"px",e},Object.defineProperty(e.prototype,"italic",{set:function(t){this.vt=e.Ct(t,this.ct.italic)},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"bold",{set:function(t){this.yt=e.Ct(t,this.ct.bold)},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"underline",{set:function(t){this.St=e.Ct(t,this.ct.underline)},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"strikeThrough",{set:function(t){this.Ot=e.Ct(t,this.ct.strikeThrough)},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"outlineWidth",{get:function(){return this.Et},set:function(t){this.Et=e.Ct(t,this.ct.outlineThickness)},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"outlineHeight",{get:function(){return this.Et},set:function(t){this.xt=e.Ct(t,this.ct.outlineThickness)},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"shadowDepthX",{get:function(){return this.Rt},set:function(t){this.Rt=e.Ct(t,this.ct.shadowDepth)},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"shadowDepthY",{get:function(){return this.Nt},set:function(t){this.Nt=e.Ct(t,this.ct.shadowDepth)},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"blur",{get:function(){return this.Xt},set:function(t){this.Xt=e.Ct(t,0)},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"gaussianBlur",{get:function(){return this.It},set:function(t){this.It=e.Ct(t,0)},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"fontName",{set:function(t){this.mt=e.Ct(t,this.ct.fontName)},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"fontSize",{get:function(){return this.bt},set:function(t){this.bt=e.Ct(t,this.ct.fontSize)},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"fontScaleX",{get:function(){return this.wt},set:function(t){this.wt=e.Ct(t,this.ct.fontScaleX)},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"fontScaleY",{get:function(){return this.Pt},set:function(t){this.Pt=e.Ct(t,this.ct.fontScaleY)},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"letterSpacing",{get:function(){return this.kt},set:function(t){this.kt=e.Ct(t,this.ct.letterSpacing)},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"rotationX",{get:function(){return this.ht},set:function(e){this.ht=e},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"rotationY",{get:function(){return this.ft},set:function(e){this.ft=e},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"rotationZ",{get:function(){return this.dt},set:function(t){this.dt=e.Ct(t,this.ct.rotationZ)},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"skewX",{get:function(){return this._t},set:function(e){this._t=e},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"skewY",{get:function(){return this.gt},set:function(e){this.gt=e},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"primaryColor",{get:function(){return this.jt},set:function(t){this.jt=e.Ct(t,this.ct.primaryColor)},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"secondaryColor",{get:function(){return this.Yt},set:function(t){this.Yt=e.Ct(t,this.ct.secondaryColor)},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"outlineColor",{get:function(){return this.Tt},set:function(t){this.Tt=e.Ct(t,this.ct.outlineColor)},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"shadowColor",{get:function(){return this.Ft},set:function(t){this.Ft=e.Ct(t,this.ct.shadowColor)},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"primaryAlpha",{get:function(){return this.At},set:function(t){this.At=e.Ct(t,this.ct.primaryColor.alpha)},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"secondaryAlpha",{get:function(){return this.Vt},set:function(t){this.Vt=e.Ct(t,this.ct.secondaryColor.alpha)},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"outlineAlpha",{get:function(){return this.Dt},set:function(t){this.Dt=e.Ct(t,this.ct.outlineColor.alpha)},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"shadowAlpha",{get:function(){return this.Mt},set:function(t){this.Mt=e.Ct(t,this.ct.shadowColor.alpha)},enumerable:!0,configurable:!0}),e.Ct=function(e,t){return null!==e?e:t},e}();e.SpanStyles=n},function(e){function t(t){e.debugMode=t}function r(t){e.verboseMode=t}e.debugMode=!1,e.verboseMode=!1,e.setDebugMode=t,e.setVerboseMode=r},function(t,r){var n=r(26),i=r(29),o=r(28),a=r(27),l=r(23),s=r(1),u=r(2),p=r(30),c=r(32),h=function(){function t(){if(this.Ue=new o.ScriptProperties,this.Bt=new p.Map,this.zt=[],this.Gt=[],this.qt=null,this.Ut=null,1===arguments.length)throw new Error("Constructor `new ASS(rawASS)` has been deprecated. Use `ASS.fromString(rawASS)` instead.");this.Bt.set("Default",new i.Style(new p.Map([["Name","Default"]])))}return Object.defineProperty(t.prototype,"properties",{get:function(){return this.Ue},enumerable:!0,configurable:!0}),Object.defineProperty(t.prototype,"styles",{get:function(){return this.Bt},enumerable:!0,configurable:!0}),Object.defineProperty(t.prototype,"dialogues",{get:function(){return this.zt},enumerable:!0,configurable:!0}),Object.defineProperty(t.prototype,"attachments",{get:function(){return this.Gt},enumerable:!0,configurable:!0}),Object.defineProperty(t.prototype,"stylesFormatSpecifier",{get:function(){return this.qt},set:function(e){this.qt=e},enumerable:!0,configurable:!0}),Object.defineProperty(t.prototype,"dialoguesFormatSpecifier",{get:function(){return this.Ut},set:function(e){this.Ut=e},enumerable:!0,configurable:!0}),t.prototype.addStyle=function(e){var t=u.parseLineIntoTypedTemplate(e,this.qt);if(null!==t&&"Style"===t.type){var r=t.template;if(l.verboseMode){var n="";r.forEach(function(e,t){return n+=t+" = "+e+", "}),console.log("Read style: "+n)}var o=new i.Style(r);this.Bt.set(o.name,o)}},t.prototype.addEvent=function(e){var t=u.parseLineIntoTypedTemplate(e,this.Ut);if(null!==t&&"Dialogue"===t.type){var r=t.template;if(l.verboseMode){var i="";r.forEach(function(e,t){return i+=t+" = "+e+", "}),console.log("Read dialogue: "+i)}this.dialogues.push(new n.Dialogue(r,this))}},t.prototype.addAttachment=function(e){this.Gt.push(e)},t.fromString=function(e,r){return void 0===r&&(r=a.Format.ASS),t.fromStream(new s.StringStream(e),r)},t.fromStream=function(e,t){switch(void 0===t&&(t=a.Format.ASS),t){case a.Format.ASS:return new s.StreamParser(e).ass;case a.Format.SRT:return new s.SrtStreamParser(e).ass;default:throw new Error("Illegal value of type: "+t)}},t.fromUrl=function(r,n){void 0===n&&(n=a.Format.ASS);var i;return i="function"==typeof e.fetch&&"function"==typeof e.ReadableStream&&"function"==typeof e.ReadableStream.prototype.getReader&&"function"==typeof e.TextDecoder?e.fetch(r).then(function(e){if(e.ok===!1||void 0===e.ok&&(e.status<200||e.status>299))throw new Error("HTTP request for "+r+" failed with status code "+e.status);return t.fromReadableStream(e.body,"utf-8",n)}):c.Promise.reject(new Error("Not supported.")),i.catch(function(e){console.warn("fetch() failed, falling back to XHR: %o",e);var i=new XMLHttpRequest,o=t.fromStream(new s.XhrStream(i),n);return i.open("GET",r,!0),i.send(),o})},t.fromReadableStream=function(e,r,n){return void 0===r&&(r="utf-8"),void 0===n&&(n=a.Format.ASS),t.fromStream(new s.BrowserReadableStream(e,r),n)},t}();t.ASS=h},function(e){!function(e){e[e.Font=0]="Font",e[e.Graphic=1]="Graphic"}(e.AttachmentType||(e.AttachmentType={}));var t=function(){function e(e,t){this.Ht=e,this.Kt=t,this.Zt=""}return Object.defineProperty(e.prototype,"filename",{get:function(){return this.Ht},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"type",{get:function(){return this.Kt},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"contents",{get:function(){return this.Zt},set:function(e){this.Zt=e},enumerable:!0,configurable:!0}),e}();e.Attachment=t},function(e,t){var r=t(27),n=t(3),i=t(8),o=t(23),a=t(30),l=function(){function e(t,n){this.Jt=null,this.$t=!1;var i=new a.Map;t.forEach(function(e,t){i.set(t.toLowerCase(),e)}),t=i,this.Ae=++e.Qt;var l=t.get("style");if(void 0!==l&&null!==l&&l.constructor===String&&(l=l.replace(/^\*+/,""),null!==l.match(/^Default$/i)&&(l="Default")),this.Le=n.styles.get(l),void 0===this.Le&&(o.debugMode&&console.warn("Unrecognized style "+l+'. Falling back to "Default"'),this.Le=n.styles.get("Default")),void 0===this.Le)throw new Error("Unrecognized style "+l);if(this.s=e.er(t.get("start")),this.u=e.er(t.get("end")),this.tr=Math.max(r.valueOrDefault(t,"layer",parseInt,function(e){return!isNaN(e)},"0"),0),this.rr=t.get("text"),void 0===this.rr||null===this.rr||this.rr.constructor!==String)throw new Error("Dialogue doesn't have any text.")}return Object.defineProperty(e.prototype,"id",{get:function(){return this.Ae},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"start",{get:function(){return this.s},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"end",{get:function(){return this.u},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"style",{get:function(){return this.Le},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"alignment",{get:function(){return null===this.Jt&&this.nr(),this.ir},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"layer",{get:function(){return this.tr},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"parts",{get:function(){return null===this.Jt&&this.nr(),this.Jt},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"containsTransformTag",{get:function(){return null===this.Jt&&this.nr(),this.$t},enumerable:!0,configurable:!0}),e.prototype.toString=function(){return"#"+this.Ae+" ["+this.s.toFixed(3)+"-"+this.u.toFixed(3)+"] "+(null!==this.Jt?this.Jt.join(", "):this.rr)},e.prototype.nr=function(){var e=this;if(this.Jt=n.parse(this.rr,"dialogueParts"),this.ir=this.Le.alignment,this.Jt.forEach(function(t,r){t instanceof i.Alignment?e.ir=t.value:t instanceof i.Move?(null===t.t1||null===t.t2)&&(e.Jt[r]=new i.Move(t.x1,t.y1,t.x2,t.y2,0,e.u-e.s)):t instanceof i.Transform&&((null===t.start||null===t.end||null===t.accel)&&(e.Jt[r]=new i.Transform(null===t.start?0:t.start,null===t.end?e.u-e.s:t.end,null===t.accel?1:t.accel,t.tags)),e.$t=!0)}),o.debugMode){var t=this.Jt.filter(function(e){return e instanceof i.Comment&&-1!==e.value.indexOf("\\")});t.length>0&&console.warn("Possible incorrect parse:\n"+this.rr+"\nwas parsed as\n"+this.toString()+"\nThe possibly incorrect parses are:\n"+t.join("\n"))}},e.er=function(e){return e.split(":").reduce(function(e,t){return 60*e+parseFloat(t)},0)},e.Qt=-1,e}();e.Dialogue=l},function(e){function t(e,t,r,n,i){var o=e.get(t);if(void 0===o)return r(i);try{var a=r(o);if(null!==n&&!n(a))throw new Error("Validation failed.");return a}catch(e){throw new Error("Property "+t+" has invalid value "+o+" - "+e.stack)}}!function(e){e[e.ASS=0]="ASS",e[e.SRT=1]="SRT"}(e.Format||(e.Format={})),function(e){e[e.SmartWrappingWithWiderTopLine=0]="SmartWrappingWithWiderTopLine",e[e.SmartWrappingWithWiderBottomLine=3]="SmartWrappingWithWiderBottomLine",e[e.EndOfLineWrapping=1]="EndOfLineWrapping",e[e.NoLineWrapping=2]="NoLineWrapping"}(e.WrappingStyle||(e.WrappingStyle={})),function(e){e[e.Outline=1]="Outline",e[e.OpaqueBox=3]="OpaqueBox"}(e.BorderStyle||(e.BorderStyle={})),e.valueOrDefault=t},function(e){var t=function(){function e(){}return Object.defineProperty(e.prototype,"resolutionX",{get:function(){return this.or},set:function(e){this.or=e},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"resolutionY",{get:function(){return this.ar},set:function(e){this.ar=e},enumerable:!0, -configurable:!0}),Object.defineProperty(e.prototype,"wrappingStyle",{get:function(){return this.lr},set:function(e){this.lr=e},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"scaleBorderAndShadow",{get:function(){return this.sr},set:function(e){this.sr=e},enumerable:!0,configurable:!0}),e}();e.ScriptProperties=t},function(e,t){var r=t(27),n=t(3),i=t(30),o=function(){function e(e){var t=new i.Map;if(e.forEach(function(e,r){t.set(r.toLowerCase(),e)}),e=t,this.ur=e.get("name"),void 0===this.ur||null===this.ur||this.ur.constructor!==String)throw new Error("Style doesn't have a name.");this.ur=this.ur.replace(/^\*+/,""),this.vt=!!r.valueOrDefault(e,"italic",parseFloat,function(e){return!isNaN(e)},"0"),this.yt=!!r.valueOrDefault(e,"bold",parseFloat,function(e){return!isNaN(e)},"0"),this.St=!!r.valueOrDefault(e,"underline",parseFloat,function(e){return!isNaN(e)},"0"),this.Ot=!!r.valueOrDefault(e,"strikeout",parseFloat,function(e){return!isNaN(e)},"0"),this.mt=r.valueOrDefault(e,"fontname",function(e){return e},function(e){return e.constructor===String},"sans-serif"),this.bt=r.valueOrDefault(e,"fontsize",parseFloat,function(e){return!isNaN(e)},"18"),this.wt=r.valueOrDefault(e,"scalex",parseFloat,function(e){return e>=0},"100")/100,this.Pt=r.valueOrDefault(e,"scaley",parseFloat,function(e){return e>=0},"100")/100,this.kt=r.valueOrDefault(e,"spacing",parseFloat,function(e){return e>=0},"0"),this.dt=r.valueOrDefault(e,"angle",parseFloat,function(e){return!isNaN(e)},"0"),this.jt=r.valueOrDefault(e,"primarycolour",function(e){return n.parse(e,"colorWithAlpha")},null,"&H00FFFFFF"),this.Yt=r.valueOrDefault(e,"secondarycolour",function(e){return n.parse(e,"colorWithAlpha")},null,"&H00FFFF00"),this.Tt=r.valueOrDefault(e,"outlinecolour",function(e){return n.parse(e,"colorWithAlpha")},null,"&H00000000"),this.Ft=r.valueOrDefault(e,"backcolour",function(e){return n.parse(e,"colorWithAlpha")},null,"&H80000000"),this.pr=r.valueOrDefault(e,"outline",parseFloat,function(e){return e>=0},"2"),this.cr=r.valueOrDefault(e,"borderstyle",parseInt,function(e){return r.BorderStyle[r.BorderStyle[e]]===e},"1"),this.hr=r.valueOrDefault(e,"shadow",parseFloat,function(e){return e>=0},"3"),this.ir=r.valueOrDefault(e,"alignment",parseInt,function(e){return e>=1&&9>=e},"2"),this.fr=r.valueOrDefault(e,"marginl",parseFloat,function(e){return!isNaN(e)},"20"),this.dr=r.valueOrDefault(e,"marginr",parseFloat,function(e){return!isNaN(e)},"20"),this._r=r.valueOrDefault(e,"marginv",parseFloat,function(e){return!isNaN(e)},"20")}return Object.defineProperty(e.prototype,"name",{get:function(){return this.ur},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"italic",{get:function(){return this.vt},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"bold",{get:function(){return this.yt},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"underline",{get:function(){return this.St},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"strikeThrough",{get:function(){return this.Ot},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"fontName",{get:function(){return this.mt},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"fontSize",{get:function(){return this.bt},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"fontScaleX",{get:function(){return this.wt},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"fontScaleY",{get:function(){return this.Pt},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"letterSpacing",{get:function(){return this.kt},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"rotationZ",{get:function(){return this.dt},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"primaryColor",{get:function(){return this.jt},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"secondaryColor",{get:function(){return this.Yt},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"outlineColor",{get:function(){return this.Tt},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"shadowColor",{get:function(){return this.Ft},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"outlineThickness",{get:function(){return this.pr},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"borderStyle",{get:function(){return this.cr},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"shadowDepth",{get:function(){return this.hr},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"alignment",{get:function(){return this.ir},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"marginLeft",{get:function(){return this.fr},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"marginRight",{get:function(){return this.dr},enumerable:!0,configurable:!0}),Object.defineProperty(e.prototype,"marginVertical",{get:function(){return this._r},enumerable:!0,configurable:!0}),e}();e.Style=o},function(t){function r(e){null!==e?t.Map=e:t.Map=n}t.Map=e.Map;var n=function(){function e(e){if(this.clear(),void 0!==e){if(!Array.isArray(e))throw new Error("Non-array iterables are not supported by the SimpleMap constructor.");for(var t=0;t0&&(i.classList.toggle("foo"),n=!0)});return o.observe(i,{attributes:!0}),function(e){r.push(e),n||(i.classList.toggle("foo"),n=!0)}}return function(e){return setTimeout(e,0)}}(),s=function(){function e(e){if(this.br=u.PENDING,this.wr=[],this.Sr=[],this.Or=null,this.Pr=null,"function"!=typeof e)throw new TypeError('typeof executor !== "function"');var t=this.Cr(),r=t.resolve,n=t.reject;try{e(r,n)}catch(e){n(e)}}return e.prototype.then=function(e,t){var r=new p;"function"!=typeof e&&(e=function(e){return e}),"function"!=typeof t&&(t=function(e){throw e});var n={capabilities:r,handler:e},i={capabilities:r,handler:t};switch(this.br){case u.PENDING:this.wr.push(n),this.Sr.push(i);break;case u.FULFILLED:this.kr(n,this.Or);break;case u.REJECTED:this.Er(i,this.Pr)}return r.promise},e.prototype.catch=function(e){return this.then(null,e)},e.resolve=function(r){return r instanceof e?r:new t.Promise(function(e){return e(r)})},e.reject=function(e){return new t.Promise(function(t,r){return r(e)})},e.all=function(e){return new t.Promise(function(r,n){var i=[],o=e.length;return 0===o?void r(i):void e.forEach(function(e,a){return t.Promise.resolve(e).then(function(e){i[a]=e,o--,0===o&&r(i)},n)})})},e.race=function(e){return new t.Promise(function(r,n){for(var i=0;i t.length && (o[t.length - 1] = o.slice(t.length - 1).join(",")); + var a = new i.Map; + return t.forEach(function(e, t) { + a.set(e, o[t]) + }), { + type: n.name, + template: a + } + } + var i = t(30); + e.parseLineIntoProperty = r, e.parseLineIntoTypedTemplate = n + }, function(e, t) { + function r(e, t) { + var r = new s(e, t); + if (null === r.result || r.result.end !== e.length) throw o.debugMode && console.error("Parse failed. %s %s %o", t, e, r.result), new Error("Parse failed."); + return r.result.value + } + + function n(e, t, r, n) { + s.prototype["parse_tag_" + e] = function(i) { + var o = this, + a = new h(i); + if (null === o.read(a, e)) return i.pop(), null; + var l = r.call(o, a); + if (null !== l) a.value = new t(l.value); + else { + if (n) return i.pop(), null; + a.value = new t(null) + } + return a + } + } + var i = t(8), + o = t(23), + a = t(30), + l = new a.Map; + e.parse = r; + var s = function() { + function e(e, t) { + this.e = e, this.t = new h(null), this.r = l.get(t).call(this, this.t) + } + return Object.defineProperty(e.prototype, "result", { + get: function() { + return this.r + }, + enumerable: !0, + configurable: !0 + }), e.prototype.parse_dialogueParts = function(e) { + var t, n = new h(e); + for (n.value = []; this.n();) { + var o = this.parse_enclosedTags(n); + if (null !== o)(t = n.value).push.apply(t, o.value); + else { + var a = this.parse_newline(n) || this.parse_hardspace(n) || this.parse_text(n); + if (null === a) return e.pop(), null; + if (a.value instanceof i.Text && n.value[n.value.length - 1] instanceof i.Text) { + var l = n.value[n.value.length - 1]; + n.value[n.value.length - 1] = new i.Text(l.value + a.value.value) + } else n.value.push(a.value) + } + } + var s = !1; + return n.value.forEach(function(e, t) { + e instanceof i.DrawingMode ? s = 0 !== e.scale : e instanceof i.Text && s && (n.value[t] = new i.DrawingInstructions(r(e.value, "drawingInstructions"))) + }), n + }, e.prototype.parse_enclosedTags = function(e) { + var t = new h(e); + if (t.value = [], null === this.read(t, "{")) return e.pop(), null; + for (var r = this.i(); this.n() && "}" !== r; r = this.i()) { + var n = null; + if (null !== this.read(t, "\\") && (n = this.parse_tag_alpha(t) || this.parse_tag_iclip(t) || this.parse_tag_xbord(t) || this.parse_tag_ybord(t) || this.parse_tag_xshad(t) || this.parse_tag_yshad(t) || this.parse_tag_blur(t) || this.parse_tag_bord(t) || this.parse_tag_clip(t) || this.parse_tag_fade(t) || this.parse_tag_fscx(t) || this.parse_tag_fscy(t) || this.parse_tag_move(t) || this.parse_tag_shad(t) || this.parse_tag_fad(t) || this.parse_tag_fax(t) || this.parse_tag_fay(t) || this.parse_tag_frx(t) || this.parse_tag_fry(t) || this.parse_tag_frz(t) || this.parse_tag_fsp(t) || this.parse_tag_fsplus(t) || this.parse_tag_fsminus(t) || this.parse_tag_org(t) || this.parse_tag_pbo(t) || this.parse_tag_pos(t) || this.parse_tag_an(t) || this.parse_tag_be(t) || this.parse_tag_fn(t) || this.parse_tag_fr(t) || this.parse_tag_fs(t) || this.parse_tag_kf(t) || this.parse_tag_ko(t) || this.parse_tag_1a(t) || this.parse_tag_1c(t) || this.parse_tag_2a(t) || this.parse_tag_2c(t) || this.parse_tag_3a(t) || this.parse_tag_3c(t) || this.parse_tag_4a(t) || this.parse_tag_4c(t) || this.parse_tag_a(t) || this.parse_tag_b(t) || this.parse_tag_c(t) || this.parse_tag_i(t) || this.parse_tag_k(t) || this.parse_tag_K(t) || this.parse_tag_p(t) || this.parse_tag_q(t) || this.parse_tag_r(t) || this.parse_tag_s(t) || this.parse_tag_t(t) || this.parse_tag_u(t), null === n && t.pop()), null === n && (n = this.parse_comment(t)), null === n) return e.pop(), null; + n.value instanceof i.Comment && t.value[t.value.length - 1] instanceof i.Comment ? t.value[t.value.length - 1] = new i.Comment(t.value[t.value.length - 1].value + n.value.value) : t.value.push(n.value) + } + return null === this.read(t, "}") ? (e.pop(), null) : t + }, e.prototype.parse_newline = function(e) { + var t = new h(e); + return null === this.read(t, "\\N") ? (e.pop(), null) : (t.value = new i.NewLine, t) + }, e.prototype.parse_hardspace = function(e) { + var t = new h(e); + return null === this.read(t, "\\h") ? (e.pop(), null) : (t.value = new i.Text(" "), t) + }, e.prototype.parse_text = function(e) { + var t = this.i(), + r = new h(e), + n = new h(r, t); + return r.value = new i.Text(n.value), r + }, e.prototype.parse_comment = function(e) { + var t = this.i(), + r = new h(e), + n = new h(r, t); + return r.value = new i.Comment(n.value), r + }, e.prototype.parse_tag_a = function(e) { + var t = new h(e); + if (null === this.read(t, "a")) return e.pop(), null; + var r = this.i(); + switch (r) { + case "1": + var n = this.i(2); + switch (n) { + case "10": + case "11": + r = n + } + break; + case "2": + case "3": + case "5": + case "6": + case "7": + case "9": + break; + default: + return e.pop(), null + } + var o = new h(t, r), + a = null; + switch (o.value) { + case "1": + a = 1; + break; + case "2": + a = 2; + break; + case "3": + a = 3; + break; + case "5": + a = 7; + break; + case "6": + a = 8; + break; + case "7": + a = 9; + break; + case "9": + a = 4; + break; + case "10": + a = 5; + break; + case "11": + a = 6 + } + return t.value = new i.Alignment(a), t + }, e.prototype.parse_tag_alpha = function() { + throw new Error("Method not implemented.") + }, e.prototype.parse_tag_an = function(e) { + var t = new h(e); + if (null === this.read(t, "an")) return e.pop(), null; + var r = this.i(); + if ("1" > r || r > "9") return e.pop(), null; + var n = new h(t, r); + return t.value = new i.Alignment(parseInt(n.value)), t + }, e.prototype.parse_tag_b = function(e) { + var t = new h(e); + if (null === this.read(t, "b")) return e.pop(), null; + var r = null, + n = this.i(); + return n >= "1" && "9" >= n && (n = this.i(3), "00" === n.substr(1) && (r = new h(t, n), r.value = parseInt(r.value))), null === r && (r = this.parse_enableDisable(t)), null !== r ? t.value = new i.Bold(r.value) : t.value = new i.Bold(null), t + }, e.prototype.parse_tag_be = function() { + throw new Error("Method not implemented.") + }, e.prototype.parse_tag_blur = function() { + throw new Error("Method not implemented.") + }, e.prototype.parse_tag_bord = function() { + throw new Error("Method not implemented.") + }, e.prototype.parse_tag_c = function() { + throw new Error("Method not implemented.") + }, e.prototype.parse_tag_clip = function(e) { + return this.o("clip", e) + }, e.prototype.parse_tag_fad = function(e) { + var t = new h(e); + if (null === this.read(t, "fad")) return e.pop(), null; + if (null === this.read(t, "(")) return e.pop(), null; + var r = this.parse_decimal(t); + if (null === r) return e.pop(), null; + if (null === this.read(t, ",")) return e.pop(), null; + var n = this.parse_decimal(t); + return null === n ? (e.pop(), null) : null === this.read(t, ")") ? (e.pop(), null) : (t.value = new i.Fade(r.value / 1e3, n.value / 1e3), t) + }, e.prototype.parse_tag_fade = function(e) { + var t = new h(e); + if (null === this.read(t, "fade")) return e.pop(), null; + if (null === this.read(t, "(")) return e.pop(), null; + var r = this.parse_decimal(t); + if (null === r) return e.pop(), null; + if (null === this.read(t, ",")) return e.pop(), null; + var n = this.parse_decimal(t); + if (null === n) return e.pop(), null; + if (null === this.read(t, ",")) return e.pop(), null; + var o = this.parse_decimal(t); + if (null === o) return e.pop(), null; + if (null === this.read(t, ",")) return e.pop(), null; + var a = this.parse_decimal(t); + if (null === a) return e.pop(), null; + if (null === this.read(t, ",")) return e.pop(), null; + var l = this.parse_decimal(t); + if (null === l) return e.pop(), null; + if (null === this.read(t, ",")) return e.pop(), null; + var s = this.parse_decimal(t); + if (null === s) return e.pop(), null; + if (null === this.read(t, ",")) return e.pop(), null; + var u = this.parse_decimal(t); + return null === u ? (e.pop(), null) : null === this.read(t, ")") ? (e.pop(), null) : (t.value = new i.ComplexFade(1 - r.value / 255, 1 - n.value / 255, 1 - o.value / 255, a.value / 1e3, l.value / 1e3, s.value / 1e3, u.value / 1e3), t) + }, e.prototype.parse_tag_fax = function() { + throw new Error("Method not implemented.") + }, e.prototype.parse_tag_fay = function() { + throw new Error("Method not implemented.") + }, e.prototype.parse_tag_fn = function(e) { + var t = new h(e); + if (null === this.read(t, "fn")) return e.pop(), null; + for (var r = new h(t, ""), n = this.i(); this.n() && "\\" !== n && "}" !== n; n = this.i()) r.value += n; + return r.value.length > 0 ? t.value = new i.FontName(r.value) : t.value = new i.FontName(null), t + }, e.prototype.parse_tag_fr = function() { + throw new Error("Method not implemented.") + }, e.prototype.parse_tag_frx = function() { + throw new Error("Method not implemented.") + }, e.prototype.parse_tag_fry = function() { + throw new Error("Method not implemented.") + }, e.prototype.parse_tag_frz = function() { + throw new Error("Method not implemented.") + }, e.prototype.parse_tag_fs = function() { + throw new Error("Method not implemented.") + }, e.prototype.parse_tag_fsplus = function(e) { + var t = new h(e); + if (null === this.read(t, "fs+")) return e.pop(), null; + var r = this.parse_decimal(t); + return null === r ? (e.pop(), null) : (t.value = new i.FontSizePlus(r.value), t) + }, e.prototype.parse_tag_fsminus = function(e) { + var t = new h(e); + if (null === this.read(t, "fs-")) return e.pop(), null; + var r = this.parse_decimal(t); + return null === r ? (e.pop(), null) : (t.value = new i.FontSizeMinus(r.value), t) + }, e.prototype.parse_tag_fscx = function(e) { + var t = new h(e); + if (null === this.read(t, "fscx")) return e.pop(), null; + var r = this.parse_decimal(t); + return null !== r ? t.value = new i.FontScaleX(r.value / 100) : t.value = new i.FontScaleX(null), t + }, e.prototype.parse_tag_fscy = function(e) { + var t = new h(e); + if (null === this.read(t, "fscy")) return e.pop(), null; + var r = this.parse_decimal(t); + return null !== r ? t.value = new i.FontScaleY(r.value / 100) : t.value = new i.FontScaleY(null), t + }, e.prototype.parse_tag_fsp = function() { + throw new Error("Method not implemented.") + }, e.prototype.parse_tag_i = function() { + throw new Error("Method not implemented.") + }, e.prototype.parse_tag_iclip = function(e) { + return this.o("iclip", e) + }, e.prototype.parse_tag_k = function(e) { + var t = new h(e); + if (null === this.read(t, "k")) return e.pop(), null; + var r = this.parse_decimal(t); + return null === r ? (e.pop(), null) : (t.value = new i.ColorKaraoke(r.value / 100), t) + }, e.prototype.parse_tag_K = function(e) { + var t = new h(e); + if (null === this.read(t, "K")) return e.pop(), null; + var r = this.parse_decimal(t); + return null === r ? (e.pop(), null) : (t.value = new i.SweepingColorKaraoke(r.value / 100), t) + }, e.prototype.parse_tag_kf = function(e) { + var t = new h(e); + if (null === this.read(t, "kf")) return e.pop(), null; + var r = this.parse_decimal(t); + return null === r ? (e.pop(), null) : (t.value = new i.SweepingColorKaraoke(r.value / 100), t) + }, e.prototype.parse_tag_ko = function(e) { + var t = new h(e); + if (null === this.read(t, "ko")) return e.pop(), null; + var r = this.parse_decimal(t); + return null === r ? (e.pop(), null) : (t.value = new i.OutlineKaraoke(r.value / 100), t) + }, e.prototype.parse_tag_move = function(e) { + var t = new h(e); + if (null === this.read(t, "move")) return e.pop(), null; + if (null === this.read(t, "(")) return e.pop(), null; + var r = this.parse_decimal(t); + if (null === r) return e.pop(), null; + if (null === this.read(t, ",")) return e.pop(), null; + var n = this.parse_decimal(t); + if (null === n) return e.pop(), null; + if (null === this.read(t, ",")) return e.pop(), null; + var o = this.parse_decimal(t); + if (null === o) return e.pop(), null; + if (null === this.read(t, ",")) return e.pop(), null; + var a = this.parse_decimal(t); + if (null === a) return e.pop(), null; + var l = null, + s = null; + if (null !== this.read(t, ",")) { + if (l = this.parse_decimal(t), null === l) return e.pop(), null; + if (null === this.read(t, ",")) return e.pop(), null; + if (s = this.parse_decimal(t), null === s) return e.pop(), null + } + return null === this.read(t, ")") ? (e.pop(), null) : (t.value = new i.Move(r.value, n.value, o.value, a.value, null !== l ? l.value / 1e3 : null, null !== s ? s.value / 1e3 : null), t) + }, e.prototype.parse_tag_org = function(e) { + var t = new h(e); + if (null === this.read(t, "org")) return e.pop(), null; + if (null === this.read(t, "(")) return e.pop(), null; + var r = this.parse_decimal(t); + if (null === r) return e.pop(), null; + if (null === this.read(t, ",")) return e.pop(), null; + var n = this.parse_decimal(t); + return null === n ? (e.pop(), null) : null === this.read(t, ")") ? (e.pop(), null) : (t.value = new i.RotationOrigin(r.value, n.value), t) + }, e.prototype.parse_tag_p = function() { + throw new Error("Method not implemented.") + }, e.prototype.parse_tag_pbo = function() { + throw new Error("Method not implemented.") + }, e.prototype.parse_tag_pos = function(e) { + var t = new h(e); + if (null === this.read(t, "pos")) return e.pop(), null; + if (null === this.read(t, "(")) return e.pop(), null; + var r = this.parse_decimal(t); + if (null === r) return e.pop(), null; + if (null === this.read(t, ",")) return e.pop(), null; + var n = this.parse_decimal(t); + return null === n ? (e.pop(), null) : null === this.read(t, ")") ? (e.pop(), null) : (t.value = new i.Position(r.value, n.value), t) + }, e.prototype.parse_tag_q = function(e) { + var t = new h(e); + if (null === this.read(t, "q")) return e.pop(), null; + var r = this.i(); + if ("0" > r || r > "3") return e.pop(), null; + var n = new h(t, r); + return t.value = new i.WrappingStyle(parseInt(n.value)), t + }, e.prototype.parse_tag_r = function(e) { + var t = new h(e); + if (null === this.read(t, "r")) return e.pop(), null; + for (var r = new h(t, ""), n = this.i(); this.n() && "\\" !== n && "}" !== n; n = this.i()) r.value += n; + return r.value.length > 0 ? t.value = new i.Reset(r.value) : t.value = new i.Reset(null), t + }, e.prototype.parse_tag_s = function() { + throw new Error("Method not implemented.") + }, e.prototype.parse_tag_shad = function() { + throw new Error("Method not implemented.") + }, e.prototype.parse_tag_t = function(e) { + var t = new h(e); + if (null === this.read(t, "t")) return e.pop(), null; + if (null === this.read(t, "(")) return e.pop(), null; + var r = null, + n = null, + o = null, + a = this.parse_decimal(t); + if (null !== a) { + if (null === this.read(t, ",")) return e.pop(), null; + var l = this.parse_decimal(t); + if (null !== l) { + if (r = a, n = l, null === this.read(t, ",")) return e.pop(), null; + var s = this.parse_decimal(t); + if (null !== s && (o = s, null === this.read(t, ","))) return e.pop(), null + } else if (o = a, null === this.read(t, ",")) return e.pop(), null + } + for (var u = [], p = this.i(); this.n() && ")" !== p && "}" !== p; p = this.i()) { + var c = null; + if (null !== this.read(t, "\\") && (c = this.parse_tag_alpha(t) || this.parse_tag_iclip(t) || this.parse_tag_xbord(t) || this.parse_tag_ybord(t) || this.parse_tag_xshad(t) || this.parse_tag_yshad(t) || this.parse_tag_blur(t) || this.parse_tag_bord(t) || this.parse_tag_clip(t) || this.parse_tag_fscx(t) || this.parse_tag_fscy(t) || this.parse_tag_shad(t) || this.parse_tag_fax(t) || this.parse_tag_fay(t) || this.parse_tag_frx(t) || this.parse_tag_fry(t) || this.parse_tag_frz(t) || this.parse_tag_fsp(t) || this.parse_tag_fsplus(t) || this.parse_tag_fsminus(t) || this.parse_tag_be(t) || this.parse_tag_fr(t) || this.parse_tag_fs(t) || this.parse_tag_1a(t) || this.parse_tag_1c(t) || this.parse_tag_2a(t) || this.parse_tag_2c(t) || this.parse_tag_3a(t) || this.parse_tag_3c(t) || this.parse_tag_4a(t) || this.parse_tag_4c(t) || this.parse_tag_c(t), null === c && t.pop()), null === c && (c = this.parse_comment(t)), null === c) return e.pop(), null; + c.value instanceof i.Comment && u[u.length - 1] instanceof i.Comment ? u[u.length - 1] = new i.Comment(u[u.length - 1].value + c.value.value) : u.push(c.value) + } + return this.read(t, ")"), t.value = new i.Transform(null !== r ? r.value / 1e3 : null, null !== n ? n.value / 1e3 : null, null !== o ? o.value / 1e3 : null, u), t + }, e.prototype.parse_tag_u = function() { + throw new Error("Method not implemented.") + }, e.prototype.parse_tag_xbord = function() { + throw new Error("Method not implemented.") + }, e.prototype.parse_tag_xshad = function() { + throw new Error("Method not implemented.") + }, e.prototype.parse_tag_ybord = function() { + throw new Error("Method not implemented.") + }, e.prototype.parse_tag_yshad = function() { + throw new Error("Method not implemented.") + }, e.prototype.parse_tag_1a = function() { + throw new Error("Method not implemented.") + }, e.prototype.parse_tag_1c = function() { + throw new Error("Method not implemented.") + }, e.prototype.parse_tag_2a = function() { + throw new Error("Method not implemented.") + }, e.prototype.parse_tag_2c = function() { + throw new Error("Method not implemented.") + }, e.prototype.parse_tag_3a = function() { + throw new Error("Method not implemented.") + }, e.prototype.parse_tag_3c = function() { + throw new Error("Method not implemented.") + }, e.prototype.parse_tag_4a = function() { + throw new Error("Method not implemented.") + }, e.prototype.parse_tag_4c = function() { + throw new Error("Method not implemented.") + }, e.prototype.parse_drawingInstructions = function(e) { + var t = new h(e), + r = null, + n = []; + for (t.value = []; this.n();) { + for (; null !== this.read(t, " ");); + if (!this.n()) break; + if (null !== r) { + var o = this.parse_decimal(t); + if (null !== o) { + n.push(o), "m" === r && 2 === n.length ? (t.value.push(new i.drawing.MoveInstruction(n[0].value, n[1].value)), n.splice(0, n.length)) : "l" === r && 2 === n.length ? (t.value.push(new i.drawing.LineInstruction(n[0].value, n[1].value)), n.splice(0, n.length)) : "b" === r && 6 === n.length && (t.value.push(new i.drawing.CubicBezierCurveInstruction(n[0].value, n[1].value, n[2].value, n[3].value, n[4].value, n[5].value)), n.splice(0, n.length)); + continue + } + } + var a = this.parse_text(t); + if (null === a) break; + var l = a.value.value; + switch (l) { + case "m": + case "l": + case "b": + r = l, n.splice(0, n.length) + } + } + for (; null !== this.read(t, " ");); + return t + }, e.prototype.parse_decimalInt32 = function(e) { + for (var t = new h(e), r = null !== this.read(t, "-"), n = new h(t, ""), i = this.i(); this.n() && i >= "0" && "9" >= i; i = this.i()) n.value += i; + if (0 === n.value.length) return e.pop(), null; + var o = parseInt(n.value); + return o >= 4294967295 ? o = 4294967295 : r && (o = -o), t.value = o, t + }, e.prototype.parse_hexInt32 = function(e) { + for (var t = new h(e), r = null !== this.read(t, "-"), n = new h(t, ""), i = this.i(); this.n() && (i >= "0" && "9" >= i || i >= "a" && "f" >= i || i >= "A" && "F" >= i); i = this.i()) n.value += i; + if (0 === n.value.length) return e.pop(), null; + var o = parseInt(n.value, 16); + return o >= 4294967295 ? o = 4294967295 : r && (o = -o), t.value = o, t + }, e.prototype.parse_decimalOrHexInt32 = function(e) { + var t = new h(e), + r = null !== this.read(t, "&H") || null !== this.read(t, "&h") ? this.parse_hexInt32(t) : this.parse_decimalInt32(t); + return null === r ? (e.pop(), null) : (t.value = r.value, t) + }, e.prototype.parse_decimal = function(e) { + var t = new h(e), + r = null !== this.read(t, "-"), + n = this.parse_unsignedDecimal(t); + return null === n ? (e.pop(), null) : (t.value = n.value, r && (t.value = -t.value), t) + }, e.prototype.parse_unsignedDecimal = function(e) { + for (var t = new h(e), r = new h(t, ""), n = null, i = this.i(); this.n() && i >= "0" && "9" >= i; i = this.i()) r.value += i; + if (0 === r.value.length) return e.pop(), null; + if (null !== this.read(t, ".")) { + n = new h(t, ""); + for (var i = this.i(); this.n() && i >= "0" && "9" >= i; i = this.i()) n.value += i; + if (0 === n.value.length) return e.pop(), null + } + return t.value = parseFloat(r.value + (null !== n ? "." + n.value : "")), t + }, e.prototype.parse_enableDisable = function(e) { + var t = this.i(); + if ("0" === t || "1" === t) { + var r = new h(e, t); + return r.value = "1" === r.value, r + } + return null + }, e.prototype.parse_color = function(e) { + for (var t = new h(e); null !== this.read(t, "&") || null !== this.read(t, "H");); + var r = this.parse_hexInt32(t); + if (null === r) return e.pop(), null; + var n = r.value; + for (t.value = new i.Color(255 & n, n >> 8 & 255, n >> 16 & 255); null !== this.read(t, "&") || null !== this.read(t, "H");); + return t + }, e.prototype.parse_alpha = function(e) { + for (var t = new h(e); null !== this.read(t, "&") || null !== this.read(t, "H");); + var r = this.parse_hexInt32(t); + if (null === r) return e.pop(), null; + var n = r.value; + for (t.value = 1 - (255 & n) / 255; null !== this.read(t, "&") || null !== this.read(t, "H");); + return t + }, e.prototype.parse_colorWithAlpha = function(e) { + var t = new h(e), + r = this.parse_decimalOrHexInt32(t); + if (null === r) return e.pop(), null; + var n = r.value; + return t.value = new i.Color(255 & n, n >> 8 & 255, n >> 16 & 255, 1 - (n >> 24 & 255) / 255), t + }, e.prototype.read = function(e, t) { + return this.i(t.length) !== t ? null : new h(e, t) + }, e.prototype.i = function(e) { + return void 0 === e && (e = 1), 1 === e ? this.e[this.t.end] : this.e.substr(this.t.end, e) + }, e.prototype.n = function() { + return this.t.end < this.e.length + }, e.prototype.o = function(e, t) { + var n = new h(t); + if (null === this.read(n, e)) return t.pop(), null; + if (null === this.read(n, "(")) return t.pop(), null; + var o = null, + a = null, + l = null, + s = null, + u = null, + p = null, + c = this.parse_decimal(n); + if (null !== c) { + if (null === this.read(n, ",")) return t.pop(), null; + var f = this.parse_decimal(n); + null !== f ? (o = c, l = f) : u = c + } + if (null !== o && null !== l) { + if (null === this.read(n, ",")) return t.pop(), null; + if (a = this.parse_decimal(n), null === this.read(n, ",")) return t.pop(), null; + s = this.parse_decimal(n), n.value = new i.RectangularClip(o.value, l.value, a.value, s.value, "clip" === e) + } else { + p = new h(n, ""); + for (var d = this.i(); this.n() && ")" !== d && "}" !== d; d = this.i()) p.value += d; + n.value = new i.VectorClip(null !== u ? u.value : 1, r(p.value, "drawingInstructions"), "clip" === e) + } + return null === this.read(n, ")") ? (t.pop(), null) : n + }, e + }(); + n("alpha", i.Alpha, s.prototype.parse_alpha, !1), n("be", i.Blur, s.prototype.parse_decimal, !1), n("blur", i.GaussianBlur, s.prototype.parse_decimal, !1), n("bord", i.Border, s.prototype.parse_decimal, !1), n("c", i.PrimaryColor, s.prototype.parse_color, !1), n("fax", i.SkewX, s.prototype.parse_decimal, !1), n("fay", i.SkewY, s.prototype.parse_decimal, !1), n("fr", i.RotateZ, s.prototype.parse_decimal, !1), n("frx", i.RotateX, s.prototype.parse_decimal, !1), n("fry", i.RotateY, s.prototype.parse_decimal, !1), n("frz", i.RotateZ, s.prototype.parse_decimal, !1), n("fs", i.FontSize, s.prototype.parse_decimal, !1), n("fsp", i.LetterSpacing, s.prototype.parse_decimal, !1), n("i", i.Italic, s.prototype.parse_enableDisable, !1), n("p", i.DrawingMode, s.prototype.parse_decimal, !0), n("pbo", i.DrawingBaselineOffset, s.prototype.parse_decimal, !0), n("s", i.StrikeThrough, s.prototype.parse_enableDisable, !1), n("shad", i.Shadow, s.prototype.parse_decimal, !1), n("u", i.Underline, s.prototype.parse_enableDisable, !1), n("xbord", i.BorderX, s.prototype.parse_decimal, !1), n("xshad", i.ShadowX, s.prototype.parse_decimal, !1), n("ybord", i.BorderY, s.prototype.parse_decimal, !1), n("yshad", i.ShadowY, s.prototype.parse_decimal, !1), n("1a", i.PrimaryAlpha, s.prototype.parse_alpha, !1), n("1c", i.PrimaryColor, s.prototype.parse_color, !1), n("2a", i.SecondaryAlpha, s.prototype.parse_alpha, !1), n("2c", i.SecondaryColor, s.prototype.parse_color, !1), n("3a", i.OutlineAlpha, s.prototype.parse_alpha, !1), n("3c", i.OutlineColor, s.prototype.parse_color, !1), n("4a", i.ShadowAlpha, s.prototype.parse_alpha, !1), n("4c", i.ShadowColor, s.prototype.parse_color, !1); + for (var u = 0, p = Object.keys(s.prototype); u < p.length; u++) { + var c = p[u]; + 0 === c.indexOf("parse_") && "function" == typeof s.prototype[c] && l.set(c.substr("parse_".length), s.prototype[c]) + } + var h = function() { + function e(e, t) { + void 0 === t && (t = null), this.a = e, this.l = [], null !== e && e.children.push(this), this.s = null !== e ? e.end : 0, this.u = this.s, this.value = t + } + return Object.defineProperty(e.prototype, "start", { + get: function() { + return this.s + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "end", { + get: function() { + return this.u + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "parent", { + get: function() { + return this.a + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "children", { + get: function() { + return this.l + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "value", { + get: function() { + return this.p + }, + set: function(e) { + this.p = e, null !== this.p && this.p.constructor === String && 0 === this.l.length && this.c(this.s + this.p.length) + }, + enumerable: !0, + configurable: !0 + }), e.prototype.pop = function() { + this.l.splice(this.l.length - 1, 1), this.l.length > 0 ? this.c(this.l[this.l.length - 1].end) : this.c(this.start) + }, e.prototype.c = function(e) { + this.u = e, null !== this.a && this.a.end !== this.u && this.a.c(this.u) + }, e + }(), + f = t(32), + d = t(36), + _ = t(38); + _.registerWorkerCommand(d.WorkerCommands.Parse, function(e) { + return new f.Promise(function(t) { + t(r(e.input, e.rule)) + }) + }) + }, function(e, t) { + function r(e) { + for (var t = "", r = 0; r < e.length; r++) { + var n = e.charCodeAt(r) - 33; + if (0 > n || n > 63) throw new Error("Out-of-range character code " + n + " at index " + r + " in string " + e); + t += 26 > n ? String.fromCharCode("A".charCodeAt(0) + n) : 52 > n ? String.fromCharCode("a".charCodeAt(0) + n - 26) : 62 > n ? String.fromCharCode("0".charCodeAt(0) + n - 52) : 62 === n ? "+" : "/" + } + return t + } + var n, i = t(23), + o = t(24), + a = t(29), + l = t(26), + s = t(25), + u = t(30), + p = t(32), + c = t(2); + ! function(e) { + e[e.ScriptInfo = 0] = "ScriptInfo", e[e.Styles = 1] = "Styles", e[e.Events = 2] = "Events", e[e.Fonts = 3] = "Fonts", e[e.Graphics = 4] = "Graphics", e[e.Other = 5] = "Other", e[e.EOF = 6] = "EOF" + }(n || (n = {})); + var h = function() { + function e(e) { + var t = this; + this.h = e, this.f = new o.ASS, this.d = new p.DeferredPromise, this._ = new p.DeferredPromise, this.g = !0, this.v = n.ScriptInfo, this.y = null, this.h.nextLine().then(function(e) { + return t.m(e) + }, function(e) { + t.d.reject(e), t._.reject(e) + }) + } + return Object.defineProperty(e.prototype, "minimalASS", { + get: function() { + return this.d.promise + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "ass", { + get: function() { + return this._.promise + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "currentSection", { + get: function() { + return this.v + }, + set: function(e) { + if (null !== this.y && (this.f.addAttachment(this.y), this.y = null), this.v === n.ScriptInfo && e !== n.ScriptInfo && this.d.resolve(this.f), e === n.EOF) { + var t = this.f.properties; + void 0 === t.resolutionX || void 0 === t.resolutionY ? (this.d.reject("Malformed ASS script."), this._.reject("Malformed ASS script.")) : (this.d.resolve(this.f), this._.resolve(this.f)) + } + this.v = e + }, + enumerable: !0, + configurable: !0 + }), e.prototype.m = function(e) { + var t = this; + if (null === e) return void(this.currentSection = n.EOF); + if ("\r" === e[e.length - 1] && (e = e.substr(0, e.length - 1)), 65279 === e.charCodeAt(0) && this.g && (e = e.substr(1)), this.g = !1, "" === e); + else if (";" === e[0] && null === this.y); + else if ("[Script Info]" === e) this.currentSection = n.ScriptInfo; + else if ("[V4+ Styles]" === e || "[V4 Styles]" === e) this.currentSection = n.Styles; + else if ("[Events]" === e) this.currentSection = n.Events; + else if ("[Fonts]" === e) this.currentSection = n.Fonts; + else if ("[Graphics]" === e) this.currentSection = n.Graphics; + else switch (null === this.y && "[" === e[0] && "]" === e[e.length - 1] && (this.currentSection = n.Other), this.currentSection) { + case n.ScriptInfo: + var o = c.parseLineIntoProperty(e); + if (null !== o) switch (o.name) { + case "PlayResX": + this.f.properties.resolutionX = parseInt(o.value); + break; + case "PlayResY": + this.f.properties.resolutionY = parseInt(o.value); + break; + case "WrapStyle": + this.f.properties.wrappingStyle = parseInt(o.value); + break; + case "ScaledBorderAndShadow": + this.f.properties.scaleBorderAndShadow = "yes" === o.value + } + break; + case n.Styles: + if (null === this.f.stylesFormatSpecifier) { + var a = c.parseLineIntoProperty(e); + null !== a && "Format" === a.name && (this.f.stylesFormatSpecifier = a.value.split(",").map(function(e) { + return e.trim() + })) + } else try { + this.f.addStyle(e) + } catch (t) { + i.debugMode && console.error("Could not parse style from line " + e + " - " + (t.stack || t)) + } + break; + case n.Events: + if (null === this.f.dialoguesFormatSpecifier) { + var l = c.parseLineIntoProperty(e); + null !== l && "Format" === l.name && (this.f.dialoguesFormatSpecifier = l.value.split(",").map(function(e) { + return e.trim() + })) + } else try { + this.f.addEvent(e) + } catch (t) { + i.debugMode && console.error("Could not parse event from line " + e + " - " + (t.stack || t)) + } + break; + case n.Fonts: + case n.Graphics: + var u = this.currentSection === n.Fonts ? /^fontname:(.+)/ : /^filename:(.+)/, + p = u.exec(e); + if (null !== p) null !== this.y && (this.f.addAttachment(this.y), this.y = null), this.y = new s.Attachment(p[1].trim(), this.currentSection === n.Fonts ? s.AttachmentType.Font : s.AttachmentType.Graphic); + else if (null !== this.y) try { + this.y.contents += r(e) + } catch (e) { + i.debugMode && console.error("Encountered error while reading font " + this.y.filename + ": %o", e), this.y = null + } + break; + case n.Other: + break; + default: + throw new Error("Unhandled state " + this.currentSection) + } + this.h.nextLine().then(function(e) { + return t.m(e) + }, function(e) { + t.d.reject(e), t._.reject(e) + }) + }, e + }(); + e.StreamParser = h; + var f = function() { + function e(e) { + var t = this; + this.h = e, this.f = new o.ASS, this._ = new p.DeferredPromise, this.g = !0, this.b = null, this.w = null, this.S = null, this.O = null, this.h.nextLine().then(function(e) { + return t.m(e) + }, function(e) { + t._.reject(e) + }), this.f.properties.resolutionX = 1280, this.f.properties.resolutionY = 720, this.f.properties.wrappingStyle = 1, this.f.properties.scaleBorderAndShadow = !0; + var r = new a.Style(new u.Map([ + ["Name", "Default"], + ["FontSize", "36"] + ])); + this.f.styles.set(r.name, r) + } + return Object.defineProperty(e.prototype, "ass", { + get: function() { + return this._.promise + }, + enumerable: !0, + configurable: !0 + }), e.prototype.m = function(e) { + var t = this; + if (null === e) return null !== this.b && null !== this.w && null !== this.S && null !== this.O && this.f.dialogues.push(new l.Dialogue(new u.Map([ + ["Style", "Default"], + ["Start", this.w], + ["End", this.S], + ["Text", this.O] + ]), this.f)), void this._.resolve(this.f); + if ("\r" === e[e.length - 1] && (e = e.substr(0, e.length - 1)), 65279 === e.charCodeAt(0) && this.g && (e = e.substr(1)), this.g = !1, "" === e) null !== this.b && null !== this.w && null !== this.S && null !== this.O && this.f.dialogues.push(new l.Dialogue(new u.Map([ + ["Style", "Default"], + ["Start", this.w], + ["End", this.S], + ["Text", this.O] + ]), this.f)), this.b = this.w = this.S = this.O = null; + else if (null === this.b) /^\d+$/.test(e) && (this.b = e); + else if (null === this.w && null === this.S) { + var r = /^(\d\d:\d\d:\d\d,\d\d\d) --> (\d\d:\d\d:\d\d,\d\d\d)/.exec(e); + null !== r && (this.w = r[1].replace(",", "."), this.S = r[2].replace(",", ".")) + } else e = e.replace(//g, "{\\b1}").replace(/\{b\}/g, "{\\b1}").replace(/<\/b>/g, "{\\b0}").replace(/\{\/b\}/g, "{\\b0}").replace(//g, "{\\i1}").replace(/\{i\}/g, "{\\i1}").replace(/<\/i>/g, "{\\i0}").replace(/\{\/i\}/g, "{\\i0}").replace(//g, "{\\u1}").replace(/\{u\}/g, "{\\u1}").replace(/<\/u>/g, "{\\u0}").replace(/\{\/u\}/g, "{\\u0}").replace(//g, function(e, t, r, n) { + return "{c&H" + n + r + t + "&}" + }).replace(/<\/font>/g, "{\\c}"), null !== this.O ? this.O += "\\N" + e : this.O = e; + this.h.nextLine().then(function(e) { + return t.m(e) + }, function(e) { + t._.reject(e) + }) + }, e + }(); + e.SrtStreamParser = f + }, function(t, r) { + var n = r(32), + i = function() { + function e(e) { + this.P = e, this.C = 0 + } + return e.prototype.nextLine = function() { + var e = null; + if (this.C < this.P.length) { + var t = this.P.indexOf("\n", this.C); - 1 !== t ? (e = n.Promise.resolve(this.P.substring(this.C, t)), this.C = t + 1) : (e = n.Promise.resolve(this.P.substr(this.C)), this.C = this.P.length) + } else e = n.Promise.resolve(null); + return e + }, e + }(); + t.StringStream = i; + var o = function() { + function e(e) { + var t = this; + this.k = e, this.C = 0, this.x = null, this.j = null, e.addEventListener("progress", function() { + return t.A() + }, !1), e.addEventListener("load", function() { + return t.T() + }, !1), e.addEventListener("error", function(e) { + return t.D(e) + }, !1) + } + return e.prototype.nextLine = function() { + if (null !== this.x) throw new Error("XhrStream only supports one pending unfulfilled read at a time."); + var e = this.x = new n.DeferredPromise; + return this.F(), e.promise + }, e.prototype.A = function() { + null !== this.x && this.k.readyState !== XMLHttpRequest.DONE && this.F() + }, e.prototype.T = function() { + null !== this.x && this.F() + }, e.prototype.D = function(e) { + this.j = e, null !== this.x && this.F() + }, e.prototype.F = function() { + if (null !== this.j) return void this.x.reject(this.j); + var e = this.k.responseText, + t = e.indexOf("\n", this.C); - 1 !== t ? (this.x.resolve(e.substring(this.C, t)), this.C = t + 1, this.x = null) : this.k.readyState === XMLHttpRequest.DONE && (null !== this.j ? this.x.reject(this.j) : this.C < e.length ? (this.x.resolve(e.substr(this.C)), this.C = e.length) : this.x.resolve(null), this.x = null) + }, e + }(); + t.XhrStream = o; + var a = function() { + function t(t, r) { + this.M = "", this.x = null, this.R = t.getReader(), this.N = new e.TextDecoder(r, { + ignoreBOM: !0 + }) + } + return t.prototype.nextLine = function() { + if (null !== this.x) throw new Error("BrowserReadableStream only supports one pending unfulfilled read at a time."); + var e = this.x = new n.DeferredPromise; + return this.F(), e.promise + }, t.prototype.F = function() { + var e = this, + t = this.M.indexOf("\n"); - 1 !== t ? (this.x.resolve(this.M.substr(0, t)), this.M = this.M.substr(t + 1), this.x = null) : this.R.read().then(function(t) { + var r = t.value, + n = t.done; + n ? (0 === e.M.length ? e.x.resolve(null) : (e.x.resolve(e.M), e.M = ""), e.x = null) : (e.M += e.N.decode(r, { + stream: !0 + }), e.F()) + }) + }, t + }(); + t.BrowserReadableStream = a + }, function(e, t) { + function r(e) { + for (var t = atob(e.contents), r = new Uint8Array(new ArrayBuffer(t.length)), n = 0; n < t.length; n++) r[n] = t.charCodeAt(n); + for (var i = { + dataView: new DataView(r.buffer), + position: 0 + }, o = p.read(i), a = null, n = 0; n < o.numTables; n++) { + var l = c.read(i); + if (l.c1 + l.c2 + l.c3 + l.c4 === "name") { + a = l; + break + } + } + i.position = a.offset; + for (var u = h.read(i), d = new s.Set, n = 0; n < u.count; n++) { + var _ = f.read(i); + switch (_.nameId) { + case 1: + case 4: + case 6: + var g = a.offset + u.stringOffset + _.offset, + v = r.subarray(g, g + _.length); + switch (_.platformId) { + case 1: + for (var y = "", m = 0; m < v.length; m++) y += String.fromCharCode(v[m]); + d.add(y); + break; + case 3: + for (var b = "", m = 0; m < v.length; m += 2) b += String.fromCharCode((v[m] << 8) + v[m + 1]); + d.add(b) + } + } + } + return d + } + + function n(e) { + var t = e.W; + return e.read = function(r) { + for (var n = new e, i = 0; i < t.length; i++) { + var a = t[i], + l = void 0; + switch (a.type) { + case o.Char: + l = String.fromCharCode(r.dataView.getInt8(r.position)), r.position += 1; + break; + case o.Uint16: + l = r.dataView.getUint16(r.position), r.position += 2; + break; + case o.Uint32: + l = r.dataView.getUint32(r.position), r.position += 4 + } + n[a.field] = l + } + return n + }, e + } + + function i(e) { + var t = u.get(e); + return void 0 === t && (t = function(t, r) { + var n = t.constructor; + void 0 === n.W && (n.W = []), n.W.push({ + type: e, + field: r + }) + }, u.set(e, t)), t + } + var o, a = t(34).L, + l = t(30), + s = t(33); + ! function(e) { + e[e.Char = 0] = "Char", e[e.Uint16 = 1] = "Uint16", e[e.Uint32 = 2] = "Uint32" + }(o || (o = {})); + var u = new l.Map, + p = function() { + function e() {} + return a([i(o.Uint16)], e.prototype, "majorVersion", void 0), a([i(o.Uint16)], e.prototype, "minorVersion", void 0), a([i(o.Uint16)], e.prototype, "numTables", void 0), a([i(o.Uint16)], e.prototype, "searchRange", void 0), a([i(o.Uint16)], e.prototype, "entrySelector", void 0), a([i(o.Uint16)], e.prototype, "rangeShift", void 0), e = a([n], e) + }(), + c = function() { + function e() {} + return a([i(o.Char)], e.prototype, "c1", void 0), a([i(o.Char)], e.prototype, "c2", void 0), a([i(o.Char)], e.prototype, "c3", void 0), a([i(o.Char)], e.prototype, "c4", void 0), a([i(o.Uint32)], e.prototype, "checksum", void 0), a([i(o.Uint32)], e.prototype, "offset", void 0), a([i(o.Uint32)], e.prototype, "length", void 0), e = a([n], e) + }(), + h = function() { + function e() {} + return a([i(o.Uint16)], e.prototype, "formatSelector", void 0), a([i(o.Uint16)], e.prototype, "count", void 0), a([i(o.Uint16)], e.prototype, "stringOffset", void 0), e = a([n], e) + }(), + f = function() { + function e() {} + return a([i(o.Uint16)], e.prototype, "platformId", void 0), a([i(o.Uint16)], e.prototype, "encodingId", void 0), a([i(o.Uint16)], e.prototype, "languageId", void 0), a([i(o.Uint16)], e.prototype, "nameId", void 0), a([i(o.Uint16)], e.prototype, "length", void 0), a([i(o.Uint16)], e.prototype, "offset", void 0), e = a([n], e) + }(); + e.getTtfNames = r + }, function(e) { + var t = function() { + function e(e, t) { + this.I = e, this.X = t + } + return Object.defineProperty(e.prototype, "x", { + get: function() { + return this.I + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "y", { + get: function() { + return this.X + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.MoveInstruction = t; + var r = function() { + function e(e, t) { + this.I = e, this.X = t + } + return Object.defineProperty(e.prototype, "x", { + get: function() { + return this.I + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "y", { + get: function() { + return this.X + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.LineInstruction = r; + var n = function() { + function e(e, t, r, n, i, o) { + this.Y = e, this.V = t, this.B = r, this.z = n, this.G = i, this.q = o + } + return Object.defineProperty(e.prototype, "x1", { + get: function() { + return this.Y + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "y1", { + get: function() { + return this.V + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "x2", { + get: function() { + return this.B + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "y2", { + get: function() { + return this.z + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "x3", { + get: function() { + return this.G + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "y3", { + get: function() { + return this.q + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.CubicBezierCurveInstruction = n + }, function(e, t) { + var r = t(7); + e.drawing = r; + var n = function() { + function e(e, t, r, n) { + void 0 === n && (n = 1), this.U = e, this.H = t, this.K = r, this.Z = n + } + return Object.defineProperty(e.prototype, "red", { + get: function() { + return this.U + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "green", { + get: function() { + return this.H + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "blue", { + get: function() { + return this.K + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "alpha", { + get: function() { + return this.Z + }, + enumerable: !0, + configurable: !0 + }), e.prototype.withAlpha = function(t) { + return null !== t ? new e(this.U, this.H, this.K, t) : this + }, e.prototype.toString = function() { + return "rgba(" + this.U + ", " + this.H + ", " + this.K + ", " + this.Z.toFixed(3) + ")" + }, e.prototype.interpolate = function(t, r) { + return new e(this.U + r * (t.red - this.U), this.H + r * (t.green - this.H), this.K + r * (t.blue - this.K), this.Z + r * (t.alpha - this.Z)) + }, e + }(); + e.Color = n; + var i = function() { + function e(e) { + this.p = e + } + return Object.defineProperty(e.prototype, "value", { + get: function() { + return this.p + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.Comment = i; + var o = function() { + function e(e) { + this.p = e + } + return Object.defineProperty(e.prototype, "value", { + get: function() { + return this.p + }, + enumerable: !0, + configurable: !0 + }), e.prototype.toString = function() { + return "Text { value: " + this.p.replace(/\u00A0/g, "\\h") + " }" + }, e + }(); + e.Text = o; + var a = function() { + function e() {} + return e + }(); + e.NewLine = a; + var l = function() { + function e(e) { + this.p = e + } + return Object.defineProperty(e.prototype, "value", { + get: function() { + return this.p + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.Italic = l; + var s = function() { + function e(e) { + this.p = e + } + return Object.defineProperty(e.prototype, "value", { + get: function() { + return this.p + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.Bold = s; + var u = function() { + function e(e) { + this.p = e + } + return Object.defineProperty(e.prototype, "value", { + get: function() { + return this.p + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.Underline = u; + var p = function() { + function e(e) { + this.p = e + } + return Object.defineProperty(e.prototype, "value", { + get: function() { + return this.p + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.StrikeThrough = p; + var c = function() { + function e(e) { + this.p = e + } + return Object.defineProperty(e.prototype, "value", { + get: function() { + return this.p + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.Border = c; + var h = function() { + function e(e) { + this.p = e + } + return Object.defineProperty(e.prototype, "value", { + get: function() { + return this.p + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.BorderX = h; + var f = function() { + function e(e) { + this.p = e + } + return Object.defineProperty(e.prototype, "value", { + get: function() { + return this.p + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.BorderY = f; + var d = function() { + function e(e) { + this.p = e + } + return Object.defineProperty(e.prototype, "value", { + get: function() { + return this.p + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.Shadow = d; + var _ = function() { + function e(e) { + this.p = e + } + return Object.defineProperty(e.prototype, "value", { + get: function() { + return this.p + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.ShadowX = _; + var g = function() { + function e(e) { + this.p = e + } + return Object.defineProperty(e.prototype, "value", { + get: function() { + return this.p + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.ShadowY = g; + var v = function() { + function e(e) { + this.p = e + } + return Object.defineProperty(e.prototype, "value", { + get: function() { + return this.p + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.Blur = v; + var y = function() { + function e(e) { + this.p = e + } + return Object.defineProperty(e.prototype, "value", { + get: function() { + return this.p + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.GaussianBlur = y; + var m = function() { + function e(e) { + this.p = e + } + return Object.defineProperty(e.prototype, "value", { + get: function() { + return this.p + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.FontName = m; + var b = function() { + function e(e) { + this.p = e + } + return Object.defineProperty(e.prototype, "value", { + get: function() { + return this.p + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.FontSize = b; + var w = function() { + function e(e) { + this.p = e + } + return Object.defineProperty(e.prototype, "value", { + get: function() { + return this.p + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.FontSizePlus = w; + var S = function() { + function e(e) { + this.p = e + } + return Object.defineProperty(e.prototype, "value", { + get: function() { + return this.p + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.FontSizeMinus = S; + var O = function() { + function e(e) { + this.p = e + } + return Object.defineProperty(e.prototype, "value", { + get: function() { + return this.p + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.FontScaleX = O; + var P = function() { + function e(e) { + this.p = e + } + return Object.defineProperty(e.prototype, "value", { + get: function() { + return this.p + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.FontScaleY = P; + var C = function() { + function e(e) { + this.p = e + } + return Object.defineProperty(e.prototype, "value", { + get: function() { + return this.p + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.LetterSpacing = C; + var k = function() { + function e(e) { + this.p = e + } + return Object.defineProperty(e.prototype, "value", { + get: function() { + return this.p + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.RotateX = k; + var E = function() { + function e(e) { + this.p = e + } + return Object.defineProperty(e.prototype, "value", { + get: function() { + return this.p + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.RotateY = E; + var x = function() { + function e(e) { + this.p = e + } + return Object.defineProperty(e.prototype, "value", { + get: function() { + return this.p + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.RotateZ = x; + var j = function() { + function e(e) { + this.p = e + } + return Object.defineProperty(e.prototype, "value", { + get: function() { + return this.p + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.SkewX = j; + var A = function() { + function e(e) { + this.p = e + } + return Object.defineProperty(e.prototype, "value", { + get: function() { + return this.p + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.SkewY = A; + var T = function() { + function e(e) { + this.p = e + } + return Object.defineProperty(e.prototype, "value", { + get: function() { + return this.p + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.PrimaryColor = T; + var D = function() { + function e(e) { + this.p = e + } + return Object.defineProperty(e.prototype, "value", { + get: function() { + return this.p + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.SecondaryColor = D; + var F = function() { + function e(e) { + this.p = e + } + return Object.defineProperty(e.prototype, "value", { + get: function() { + return this.p + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.OutlineColor = F; + var M = function() { + function e(e) { + this.p = e + } + return Object.defineProperty(e.prototype, "value", { + get: function() { + return this.p + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.ShadowColor = M; + var R = function() { + function e(e) { + this.p = e + } + return Object.defineProperty(e.prototype, "value", { + get: function() { + return this.p + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.Alpha = R; + var N = function() { + function e(e) { + this.p = e + } + return Object.defineProperty(e.prototype, "value", { + get: function() { + return this.p + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.PrimaryAlpha = N; + var W = function() { + function e(e) { + this.p = e + } + return Object.defineProperty(e.prototype, "value", { + get: function() { + return this.p + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.SecondaryAlpha = W; + var L = function() { + function e(e) { + this.p = e + } + return Object.defineProperty(e.prototype, "value", { + get: function() { + return this.p + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.OutlineAlpha = L; + var I = function() { + function e(e) { + this.p = e + } + return Object.defineProperty(e.prototype, "value", { + get: function() { + return this.p + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.ShadowAlpha = I; + var X = function() { + function e(e) { + this.p = e + } + return Object.defineProperty(e.prototype, "value", { + get: function() { + return this.p + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.Alignment = X; + var Y = function() { + function e(e) { + this.J = e + } + return Object.defineProperty(e.prototype, "duration", { + get: function() { + return this.J + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.ColorKaraoke = Y; + var V = function() { + function e(e) { + this.J = e + } + return Object.defineProperty(e.prototype, "duration", { + get: function() { + return this.J + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.SweepingColorKaraoke = V; + var B = function() { + function e(e) { + this.J = e + } + return Object.defineProperty(e.prototype, "duration", { + get: function() { + return this.J + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.OutlineKaraoke = B; + var z = function() { + function e(e) { + this.p = e + } + return Object.defineProperty(e.prototype, "value", { + get: function() { + return this.p + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.WrappingStyle = z; + var G = function() { + function e(e) { + this.p = e + } + return Object.defineProperty(e.prototype, "value", { + get: function() { + return this.p + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.Reset = G; + var q = function() { + function e(e, t) { + this.I = e, this.X = t + } + return Object.defineProperty(e.prototype, "x", { + get: function() { + return this.I + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "y", { + get: function() { + return this.X + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.Position = q; + var U = function() { + function e(e, t, r, n, i, o) { + this.Y = e, this.V = t, this.B = r, this.z = n, this.$ = i, this.Q = o + } + return Object.defineProperty(e.prototype, "x1", { + get: function() { + return this.Y + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "y1", { + get: function() { + return this.V + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "x2", { + get: function() { + return this.B + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "y2", { + get: function() { + return this.z + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "t1", { + get: function() { + return this.$ + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "t2", { + get: function() { + return this.Q + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.Move = U; + var H = function() { + function e(e, t) { + this.I = e, this.X = t + } + return Object.defineProperty(e.prototype, "x", { + get: function() { + return this.I + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "y", { + get: function() { + return this.X + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.RotationOrigin = H; + var K = function() { + function e(e, t) { + this.s = e, this.u = t + } + return Object.defineProperty(e.prototype, "start", { + get: function() { + return this.s + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "end", { + get: function() { + return this.u + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.Fade = K; + var Z = function() { + function e(e, t, r, n, i, o, a) { + this.ee = e, this.te = t, this.re = r, this.$ = n, this.Q = i, this.ne = o, this.ie = a + } + return Object.defineProperty(e.prototype, "a1", { + get: function() { + return this.ee + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "a2", { + get: function() { + return this.te + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "a3", { + get: function() { + return this.re + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "t1", { + get: function() { + return this.$ + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "t2", { + get: function() { + return this.Q + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "t3", { + get: function() { + return this.ne + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "t4", { + get: function() { + return this.ie + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.ComplexFade = Z; + var J = function() { + function e(e, t, r, n) { + this.s = e, this.u = t, this.oe = r, this.ae = n + } + return Object.defineProperty(e.prototype, "start", { + get: function() { + return this.s + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "end", { + get: function() { + return this.u + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "accel", { + get: function() { + return this.oe + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "tags", { + get: function() { + return this.ae + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.Transform = J; + var $ = function() { + function e(e, t, r, n, i) { + this.Y = e, this.V = t, this.B = r, this.z = n, this.le = i + } + return Object.defineProperty(e.prototype, "x1", { + get: function() { + return this.Y + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "y1", { + get: function() { + return this.V + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "x2", { + get: function() { + return this.B + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "y2", { + get: function() { + return this.z + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "inside", { + get: function() { + return this.le + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.RectangularClip = $; + var Q = function() { + function e(e, t, r) { + this.se = e, this.ue = t, this.le = r + } + return Object.defineProperty(e.prototype, "scale", { + get: function() { + return this.se + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "instructions", { + get: function() { + return this.ue + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "inside", { + get: function() { + return this.le + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.VectorClip = Q; + var ee = function() { + function e(e) { + this.se = e + } + return Object.defineProperty(e.prototype, "scale", { + get: function() { + return this.se + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.DrawingMode = ee; + var te = function() { + function e(e) { + this.p = e + } + return Object.defineProperty(e.prototype, "value", { + get: function() { + return this.p + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.DrawingBaselineOffset = te; + var re = function() { + function e(e) { + this.ue = e + } + return Object.defineProperty(e.prototype, "instructions", { + get: function() { + return this.ue + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.DrawingInstructions = re; + for (var ne = function(e, t) { + if (!e.prototype.hasOwnProperty("toString")) { + var r = Object.getOwnPropertyNames(e.prototype).filter(function(e) { + return "constructor" !== e + }); + e.prototype.toString = function() { + var e = this; + return t + " { " + r.map(function(t) { + return t + ": " + e[t] + }).join(", ") + (r.length > 0 ? " " : "") + "}" + } + } + }, ie = t(38), oe = 0, ae = Object.keys(e); oe < ae.length; oe++) { + var le = ae[oe], + se = e[le]; + se instanceof Function && (ne(se, le), ie.registerClassPrototype(se.prototype)) + } + for (var ue = 0, pe = Object.keys(r); ue < pe.length; ue++) { + var le = pe[ue], + se = r[le]; + se instanceof Function && (ne(se, "Drawing" + le), ie.registerClassPrototype(se.prototype)) + } + }, function(e, t) { + var r = t(23), + n = t(11), + i = function() { + function e(e, t) { + this.pe = e, this.ce = t, this.he = new n.ManualClock, this.fe = null, this.de = null, this._e = null + } + return e.prototype.play = function() { + this.he.enabled && (this.ge(), this.he.play()) + }, e.prototype.pause = function() { + if (this.he.enabled) { + if (null === this.fe) return void(r.debugMode && console.warn("AutoClock.pause: Abnormal state detected. AutoClock._nextAnimationFrameRequestId should not have been null.")); + this.ve(), this.he.pause() + } + }, e.prototype.seeking = function() { + this.he.seek(this.pe()) + }, Object.defineProperty(e.prototype, "currentTime", { + get: function() { + return this.he.currentTime + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "enabled", { + get: function() { + return this.he.enabled + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "paused", { + get: function() { + return this.he.paused + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "rate", { + get: function() { + return this.he.rate + }, + enumerable: !0, + configurable: !0 + }), e.prototype.setRate = function(e) { + this.he.setRate(e) + }, e.prototype.enable = function() { + return this.he.enable() ? (this.ge(), !0) : !1 + }, e.prototype.disable = function() { + return this.he.disable() ? (this.ve(), !0) : !1 + }, e.prototype.toggle = function() { + this.he.enabled ? this.disable() : this.enable() + }, e.prototype.setEnabled = function(e) { + return e ? this.enable() : this.disable() + }, e.prototype.addEventListener = function(e, t) { + this.he.addEventListener(e, t) + }, e.prototype.ye = function(e) { + var t = this; + if (!this.he.enabled) return void(r.debugMode && console.warn("AutoClock._onTimerTick: Called when disabled.")); + var n = this.he.currentTime, + i = this.pe(); + this.he.paused ? n !== i && (this.de = i, this._e = e, this.he.tick(i)) : null !== this.de && i === this.de ? e - this._e > this.ce ? (this._e = null, this.he.pause()) : this.he.tick((e - this._e) / 1e3 * this.he.rate + this.de) : (this.de = i, this._e = e, this.he.tick(i)), this.fe = requestAnimationFrame(function(e) { + return t.ye(e) + }) + }, e.prototype.ge = function() { + var e = this; + null === this.fe && (this.fe = requestAnimationFrame(function(t) { + return e.ye(t) + })) + }, e.prototype.ve = function() { + null !== this.fe && (cancelAnimationFrame(this.fe), this.fe = null) + }, e + }(); + e.AutoClock = i + }, function(e) { + var t = function() { + function e() {} + return e.prototype.addEventListener = function(e, t) { + var r = this.me.get(e); + void 0 === r && this.me.set(e, r = []), r.push(t) + }, e.prototype.be = function(e, t) { + var r = this.me.get(e); + if (void 0 !== r) + for (var n = 0; n < r.length; n++) { + var i = r[n]; + i.apply(this, t) + } + }, e + }(); + e.EventSource = t, + function(e) { + e[e.Play = 0] = "Play", e[e.Tick = 1] = "Tick", e[e.Pause = 2] = "Pause", e[e.Stop = 3] = "Stop", e[e.RateChange = 4] = "RateChange" + }(e.ClockEvent || (e.ClockEvent = {})) + }, function(e, t) { + var r = t(31), + n = t(30), + i = t(10), + o = function() { + function e() { + this.we = -1, this.Se = 1, this.Oe = !0, this.Pe = !0, this.me = new n.Map + } + return e.prototype.play = function() { + this.Oe && this.Pe && (this.Pe = !1, this.be(i.ClockEvent.Play, [])) + }, e.prototype.tick = function(e) { + this.Oe && this.we !== e && (this.play(), this.we = e, this.be(i.ClockEvent.Tick, [])) + }, e.prototype.seek = function(e) { + this.Oe && (this.pause(), this.we !== e && (this.stop(), this.tick(e), this.pause())) + }, e.prototype.pause = function() { + this.Oe && (this.Pe || (this.Pe = !0, this.be(i.ClockEvent.Pause, []))) + }, e.prototype.stop = function() { + this.be(i.ClockEvent.Stop, []) + }, Object.defineProperty(e.prototype, "currentTime", { + get: function() { + return this.we + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "enabled", { + get: function() { + return this.Oe + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "paused", { + get: function() { + return this.Pe + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "rate", { + get: function() { + return this.Se + }, + enumerable: !0, + configurable: !0 + }), e.prototype.setRate = function(e) { + this.Se !== e && (this.Se = e, this.be(i.ClockEvent.RateChange, [])) + }, e.prototype.enable = function() { + return this.Oe ? !1 : (this.Oe = !0, !0) + }, e.prototype.disable = function() { + return this.Oe ? (this.pause(), this.stop(), this.Oe = !1, !0) : !1 + }, e.prototype.toggle = function() { + this.Oe ? this.disable() : this.enable() + }, e.prototype.setEnabled = function(e) { + return e ? this.enable() : this.disable() + }, e + }(); + e.ManualClock = o, r.mixin(o, [i.EventSource]) + }, function(e, t) { + var r = t(9), + n = function() { + function e(e) { + var t = this; + this.Ce = new r.AutoClock(function() { + return e.currentTime + }, 100), e.addEventListener("playing", function() { + return t.Ce.play() + }, !1), e.addEventListener("pause", function() { + return t.Ce.pause() + }, !1), e.addEventListener("seeking", function() { + return t.Ce.seeking() + }, !1), e.addEventListener("ratechange", function() { + return t.Ce.setRate(e.playbackRate) + }, !1) + } + return Object.defineProperty(e.prototype, "currentTime", { + get: function() { + return this.Ce.currentTime + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "enabled", { + get: function() { + return this.Ce.enabled + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "paused", { + get: function() { + return this.Ce.paused + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "rate", { + get: function() { + return this.Ce.rate + }, + enumerable: !0, + configurable: !0 + }), e.prototype.enable = function() { + return this.Ce.enable() + }, e.prototype.disable = function() { + return this.Ce.disable() + }, e.prototype.toggle = function() { + this.Ce.enabled ? this.disable() : this.enable() + }, e.prototype.setEnabled = function(e) { + return e ? this.enable() : this.disable() + }, e.prototype.addEventListener = function(e, t) { + this.Ce.addEventListener(e, t) + }, e + }(); + e.VideoClock = n + }, function(e, t) { + var r = t(34).ke, + n = t(12), + i = t(21), + o = function(e) { + function t(t, r, i) { + e.call(this, r, new n.VideoClock(t), document.createElement("div"), i), this.Ee = t, this.Ee.parentElement.replaceChild(this.libjassSubsWrapper, this.Ee), this.libjassSubsWrapper.insertBefore(this.Ee, this.libjassSubsWrapper.firstElementChild) + } + return r(t, e), t.prototype.resize = function() { + var t = this.Ee.videoWidth, + r = this.Ee.videoHeight, + n = this.Ee.offsetWidth, + i = this.Ee.offsetHeight, + o = Math.min(n / t, i / r), + a = t * o, + l = r * o, + s = (n - a) / 2, + u = (i - l) / 2; + e.prototype.resize.call(this, a, l, s, u) + }, t.prototype.resizeVideo = function() { + console.warn("`DefaultRenderer.resizeVideo(width, height)` has been deprecated. Use `DefaultRenderer.resize()` instead."), this.resize() + }, t.prototype.xe = function() { + this.resize(), e.prototype.xe.call(this) + }, t + }(i.WebRenderer); + e.DefaultRenderer = o + }, function(e, t) { + var r = t(10); + e.ClockEvent = r.ClockEvent, e.EventSource = r.EventSource; + var n = t(9); + e.AutoClock = n.AutoClock; + var i = t(11); + e.ManualClock = i.ManualClock; + var o = t(12); + e.VideoClock = o.VideoClock; + var a = t(13); + e.DefaultRenderer = a.DefaultRenderer; + var l = t(15); + e.NullRenderer = l.NullRenderer; + var s = t(21); + e.WebRenderer = s.WebRenderer; + var u = t(16); + e.RendererSettings = u.RendererSettings + }, function(e, t) { + var r = t(10), + n = t(16), + i = t(23), + o = function() { + function e(t, i, o) { + var a = this; + this.f = t, this.je = i, this.Ae = ++e.Te, this.De = n.RendererSettings.from(o), this.je.addEventListener(r.ClockEvent.Play, function() { + return a.Fe() + }), this.je.addEventListener(r.ClockEvent.Tick, function() { + return a.Me() + }), this.je.addEventListener(r.ClockEvent.Pause, function() { + return a.Re() + }), this.je.addEventListener(r.ClockEvent.Stop, function() { + return a.Ne() + }), this.je.addEventListener(r.ClockEvent.RateChange, function() { + return a.We() + }) + } + return Object.defineProperty(e.prototype, "id", { + get: function() { + return this.Ae + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "ass", { + get: function() { + return this.f + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "clock", { + get: function() { + return this.je + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "settings", { + get: function() { + return this.De + }, + enumerable: !0, + configurable: !0 + }), e.prototype.preRender = function() {}, e.prototype.draw = function() {}, e.prototype.enable = function() { + return this.je.enable() + }, e.prototype.disable = function() { + return this.je.disable() + }, e.prototype.toggle = function() { + this.je.toggle() + }, e.prototype.setEnabled = function(e) { + return this.je.setEnabled(e) + }, Object.defineProperty(e.prototype, "enabled", { + get: function() { + return this.je.enabled + }, + enumerable: !0, + configurable: !0 + }), e.prototype.Fe = function() { + i.verboseMode && console.log("NullRenderer._onClockPlay") + }, e.prototype.Me = function() { + var e = this.je.currentTime; + i.verboseMode && console.log("NullRenderer._onClockTick: currentTime = " + e); + for (var t = 0, r = this.f.dialogues; t < r.length; t++) { + var n = r[t]; + n.end > e && (n.start <= e ? this.draw(n) : n.start <= e + this.De.preRenderTime && this.preRender(n)) + } + }, e.prototype.Re = function() { + i.verboseMode && console.log("NullRenderer._onClockPause") + }, e.prototype.Ne = function() { + i.verboseMode && console.log("NullRenderer._onClockStop") + }, e.prototype.We = function() { + i.verboseMode && console.log("NullRenderer._onClockRateChange") + }, e.Te = -1, e + }(); + e.NullRenderer = o + }, function(e, t) { + function r(e) { + return e.type === CSSRule.FONT_FACE_RULE + } + var n = t(30), + i = function() { + function e() {} + return e.makeFontMapFromStyleElement = function(e) { + for (var t = new n.Map, i = e.sheet, o = 0; o < i.cssRules.length; o++) { + var a = i.cssRules[o]; + if (r(a)) { + var l = a.style.getPropertyValue("font-family").match(/^["']?(.*?)["']?$/)[1], + s = a.style.getPropertyValue("src"); + s || (s = a.cssText.split("\n").map(function(e) { + return e.match(/src:\s*([^;]+?)\s*;/) + }).filter(function(e) { + return null !== e + }).map(function(e) { + return e[1] + })[0]), t.set(l, s) + } + } + return t + }, e.from = function(t) { + (void 0 === t || null === t) && (t = {}); + var r = t, + n = r.fontMap, + i = void 0 === n ? null : n, + o = r.preRenderTime, + a = void 0 === o ? 5 : o, + l = r.preciseOutlines, + s = void 0 === l ? !1 : l, + u = r.enableSvg, + p = void 0 === u ? !0 : u, + c = r.fallbackFonts, + h = void 0 === c ? 'Arial, Helvetica, sans-serif, "Segoe UI Symbol"' : c, + f = r.useAttachedFonts, + d = void 0 === f ? !1 : f, + _ = new e; + return _.fontMap = i, _.preRenderTime = a, _.preciseOutlines = s, _.enableSvg = p, _.fallbackFonts = h, _.useAttachedFonts = d, _ + }, e + }(); + e.RendererSettings = i + }, function(e, t) { + var r = t(30), + n = function() { + function e(t, n) { + this.Le = n, this.Ie = "", this.Xe = new r.Map, this.Ye = 0, this.Ae = t.id + "-" + e.Ve++, this.Se = t.clock.rate + } + return Object.defineProperty(e.prototype, "animationStyle", { + get: function() { + return this.Ie + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "animationDelays", { + get: function() { + return this.Xe + }, + enumerable: !0, + configurable: !0 + }), e.prototype.add = function(e, t) { + for (var r = null, n = null, i = 0; i < t.length; i++) { + var o = t[i]; + null === r && (r = o.time), n = o.time + } + for (var a = "", l = 0; l < t.length; l++) { + var o = t[l]; + a += " " + (100 * (n - r === 0 ? 1 : (o.time - r) / (n - r))).toFixed(3) + "% {\n", o.properties.forEach(function(e, t) { + a += " " + t + ": " + e + ";\n" + }), a += " }\n" + } + var s = "animation-" + this.Ae + "-" + this.Ye++; + this.Le.appendChild(document.createTextNode("@-webkit-keyframes " + s + " {\n" + a + "\n}")), this.Le.appendChild(document.createTextNode("@keyframes " + s + " {\n" + a + "\n}")), "" !== this.Ie && (this.Ie += ","), this.Ie += s + " " + ((n - r) / this.Se).toFixed(3) + "s " + e, this.Xe.set(s, r) + }, e.Ve = 0, e + }(); + e.AnimationCollection = n + }, function(e, t) { + var r = t(8), + n = function() { + function e(e, t) { + this.Be = e, this.ze = t, this.se = 1, this.Ge = 0 + } + return Object.defineProperty(e.prototype, "scale", { + set: function(e) { + this.se = e + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "baselineOffset", { + set: function(e) { + this.Ge = e + }, + enumerable: !0, + configurable: !0 + }), e.prototype.toSVG = function(e, t) { + for (var n = Math.pow(2, this.se - 1), i = this.Be / n, o = this.ze / n, a = document.createElementNS("http://www.w3.org/2000/svg", "path"), l = 0, s = 0, u = 0, p = e.instructions; u < p.length; u++) { + var c = p[u]; + c instanceof r.drawing.MoveInstruction ? (a.pathSegList.appendItem(a.createSVGPathSegMovetoAbs(c.x, c.y + this.Ge)), l = Math.max(l, c.x), s = Math.max(s, c.y + this.Ge)) : c instanceof r.drawing.LineInstruction ? (a.pathSegList.appendItem(a.createSVGPathSegLinetoAbs(c.x, c.y + this.Ge)), l = Math.max(l, c.x), s = Math.max(s, c.y + this.Ge)) : c instanceof r.drawing.CubicBezierCurveInstruction && (a.pathSegList.appendItem(a.createSVGPathSegCurvetoCubicAbs(c.x3, c.y3 + this.Ge, c.x1, c.y1 + this.Ge, c.x2, c.y2 + this.Ge)), l = Math.max(l, c.x1, c.x2, c.x3), s = Math.max(s, c.y1 + this.Ge, c.y2 + this.Ge, c.y3 + this.Ge)) + } + var h = document.createElementNS("http://www.w3.org/2000/svg", "svg"); + h.setAttribute("version", "1.1"), h.width.baseVal.valueAsString = (l * i).toFixed(3) + "px", h.height.baseVal.valueAsString = (s * o).toFixed(3) + "px"; + var f = document.createElementNS("http://www.w3.org/2000/svg", "g"); + return h.appendChild(f), f.setAttribute("transform", "scale(" + i.toFixed(3) + " " + o.toFixed(3) + ")"), f.appendChild(a), a.setAttribute("fill", t.toString()), h + }, e + }(); + e.DrawingStyles = n + }, function(e, t) { + function r(e, t, r, n) { + var i = '"' + e + '"'; + "" !== r && (i += ", " + r), n.style.fontFamily = i, n.style.fontSize = t + "px" + } + + function n(e, t, n, i) { + return r(e, t, n, i), new u.Promise(function(e) { + return setTimeout(function() { + return e(i.offsetHeight) + }, 1e3) + }) + } + + function i(e, t, n, i) { + return r(e, t, n, i), i.offsetHeight + } + + function o(e, t) { + return [e, 180 / (t - e)] + } + + function a(e, t, r) { + return n(e, 180, t, r).then(function(i) { + return n(e, 360, t, r).then(function(e) { + return o(i, e) + }) + }) + } + + function l(e, t, r) { + return 180 + (e - t) * r + } + + function s(e, t, r, n, a) { + var s = a.get(e); + if (void 0 === s) { + var u = i(e, 180, r, n), + p = i(e, 360, r, n); + a.set(e, s = o(u, p)) + } + var c = s[0], + h = s[1]; + return l(t, c, h) + } + var u = t(32); + e.calculateFontMetrics = a, e.fontSizeForLineHeight = s + }, function(e) { + var t = function() { + function e(e, t) { + this.qe = e, this.Ue = t + } + return Object.defineProperty(e.prototype, "time", { + get: function() { + return this.qe + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "properties", { + get: function() { + return this.Ue + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.Keyframe = t + }, function(t, r) { + var n = r(34).ke, + i = r(17), + o = r(18), + a = r(19), + l = r(20), + s = r(22), + u = r(10), + p = r(15), + c = r(6), + h = r(8), + f = r(23), + d = r(25), + _ = r(27), + g = r(31), + v = r(30), + y = r(32), + m = /^(url|local)\(["']?(.+?)["']?\)$/, + b = function(t) { + function r(r, n, i, o) { + var a = this; + t.call(this, r, n, function() { + if (!(i instanceof HTMLDivElement)) { + var e = o; + o = i, i = e, console.warn("WebRenderer's constructor now takes libjassSubsWrapper as the third parameter and settings as the fourth parameter. Please update the caller.") + } + return o + }()), this.He = i, this.Ke = [], this.Ze = [], this.Je = new v.Map, this.$e = new v.Map, this.Qe = new v.Map, this.me = new v.Map, this.He.classList.add("libjass-wrapper"), this.et = document.createElement("div"), this.He.appendChild(this.et), this.et.className = "libjass-subs", this.tt = document.createElement("div"), this.He.appendChild(this.tt), this.tt.className = "libjass-font-measure", this.tt.appendChild(document.createTextNode("M")), f.debugMode && console.log("Preloading fonts..."); + var l = [], + s = new v.Map, + u = null === this.settings.fontMap ? new v.Map : this.settings.fontMap, + p = new v.Map; + this.settings.useAttachedFonts && r.attachments.forEach(function(e) { + if (e.type === d.AttachmentType.Font) { + var t = null; + try { + t = c.getTtfNames(e) + } catch (e) { + return void console.error(e) + } + var r = "data:application/x-font-ttf;base64," + e.contents; + t.forEach(function(e) { + var t = u.get(e); + if (void 0 !== t) + if ("string" != typeof t) t.push(r); + else { + var n = p.get(e); + void 0 === n && p.set(e, n = []), n.push(r) + } + else u.set(e, [r]) + }) + } + }), u.forEach(function(t, r) { + var n; + if (e.document.fonts && e.document.fonts.add) { + var i = "string" == typeof t ? t : t.map(function(e) { + return null !== e.match(m) ? e : 'url("' + e + '")' + }).join(", "), + o = p.get(r); + if (void 0 !== o) + for (var u = 0; u < o.length; u++) { + var c = o[u]; + i += ', url("' + c + '")' + } + var h = []; + e.document.fonts.forEach(function(e) { + (e.family === r || e.family === '"' + r + '"') && h.push(e) + }); + var d; + if (0 === h.length) { + var _ = new FontFace(r, i), + g = new FontFace('"' + r + '"', i); + e.document.fonts.add(_), e.document.fonts.add(g), d = y.any([_.load(), g.load()]) + } else d = y.any(h.map(function(e) { + return e.load() + })); + n = a.rt(r, d.catch(function(e) { + return console.warn("Fetching fonts for " + r + " at " + i + " failed: %o", e), null + })) + } else { + var v = ("string" == typeof t ? t.split(/,/) : t).map(function(e) { + return e.trim() + }).map(function(e) { + var t = e.match(m); + return null === t ? e : "local" === t[1] ? null : t[2]; + }).filter(function(e) { + return null !== e + }), + o = p.get(r); + void 0 !== o && (v = v.concat(o)); + var b = v.map(function(e) { + var t = s.get(e); + return void 0 === t && (t = new y.Promise(function(t, r) { + var n = new XMLHttpRequest; + n.addEventListener("load", function() { + f.debugMode && console.log("Preloaded " + e + "."), t(null) + }), n.addEventListener("error", function(e) { + r(e) + }), n.open("GET", e, !0), n.send() + }), s.set(e, t)), t + }), + w = 0 === b.length ? y.Promise.resolve(null) : y.first(b).catch(function(e) { + return console.warn("Fetching fonts for " + r + " at " + v.join(", ") + " failed: %o", e), null + }); + n = a.rt(r, w) + } + l.push(n.then(function(e) { + return a.Je.set(r, e) + })) + }), y.Promise.all(l).then(function() { + f.debugMode && console.log("All fonts have been preloaded."), a.xe() + }) + } + return n(r, t), Object.defineProperty(r.prototype, "libjassSubsWrapper", { + get: function() { + return this.He + }, + enumerable: !0, + configurable: !0 + }), r.prototype.resize = function(e, t, r, n) { + void 0 === r && (r = 0), void 0 === n && (n = 0), this.nt(), this.et.style.width = e.toFixed(3) + "px", this.et.style.height = t.toFixed(3) + "px", this.et.style.left = r.toFixed(3) + "px", this.et.style.top = n.toFixed(3) + "px", this.it = e, this.ot = e / this.ass.properties.resolutionX, this.at = t / this.ass.properties.resolutionY, this.Qe.clear(), -1 !== this.clock.currentTime && this.Me() + }, r.prototype.preRender = function(e) { + var t = this, + n = this.Qe.get(e.id); + if (n) return n; + var a = this.clock.currentTime - e.start; + if (e.containsTransformTag && 0 > a) return null; + var u = document.createElement("div"); + u.style.marginLeft = (this.ot * e.style.marginLeft).toFixed(3) + "px", u.style.marginRight = (this.ot * e.style.marginRight).toFixed(3) + "px", u.style.marginTop = u.style.marginBottom = (this.at * e.style.marginVertical).toFixed(3) + "px", u.style.minWidth = (this.it - this.ot * (e.style.marginLeft + e.style.marginRight)).toFixed(3) + "px"; + var p = document.createElement("style"); + p.id = "libjass-animation-styles-" + this.id + "-" + e.id, p.type = "text/css"; + var c = new i.AnimationCollection(this, p), + d = document.createElementNS("http://www.w3.org/2000/svg", "svg"); + d.setAttribute("version", "1.1"), d.setAttribute("class", "libjass-filters"), d.width.baseVal.valueAsString = "0", d.height.baseVal.valueAsString = "0"; + var g = document.createElementNS("http://www.w3.org/2000/svg", "defs"); + d.appendChild(g); + var y = null, + m = new s.SpanStyles(this, e, this.ot, this.at, this.settings, this.tt, g, this.Je), + b = null, + w = !1, + S = function(e) { + null !== y && y.hasChildNodes() && u.appendChild(m.setStylesOnSpan(y, b)), null !== b && b.animationDelays.forEach(function(e, t) { + return c.animationDelays.set(t, e) + }), e && (w ? u.appendChild(m.makeNewLine()) : u.appendChild(document.createElement("br"))), y = document.createElement("span"), b = new i.AnimationCollection(t, p), w = e + }; + S(!1); + for (var O = new o.DrawingStyles(this.ot, this.at), P = this.ass.properties.wrappingStyle, C = 0, k = 0, E = e.parts; k < E.length; k++) { + var x = E[k]; + if (x instanceof h.Italic) m.italic = x.value; + else if (x instanceof h.Bold) m.bold = x.value; + else if (x instanceof h.Underline) m.underline = x.value; + else if (x instanceof h.StrikeThrough) m.strikeThrough = x.value; + else if (x instanceof h.Border) m.outlineWidth = x.value, m.outlineHeight = x.value; + else if (x instanceof h.BorderX) m.outlineWidth = x.value; + else if (x instanceof h.BorderY) m.outlineHeight = x.value; + else if (x instanceof h.Shadow) m.shadowDepthX = x.value, m.shadowDepthY = x.value; + else if (x instanceof h.ShadowX) m.shadowDepthX = x.value; + else if (x instanceof h.ShadowY) m.shadowDepthY = x.value; + else if (x instanceof h.Blur) m.blur = x.value; + else if (x instanceof h.GaussianBlur) m.gaussianBlur = x.value; + else if (x instanceof h.FontName) m.fontName = x.value; + else if (x instanceof h.FontSize) m.fontSize = x.value; + else if (x instanceof h.FontSizePlus) m.fontSize += x.value; + else if (x instanceof h.FontSizeMinus) m.fontSize -= x.value; + else if (x instanceof h.FontScaleX) m.fontScaleX = x.value; + else if (x instanceof h.FontScaleY) m.fontScaleY = x.value; + else if (x instanceof h.LetterSpacing) m.letterSpacing = x.value; + else if (x instanceof h.RotateX) m.rotationX = x.value; + else if (x instanceof h.RotateY) m.rotationY = x.value; + else if (x instanceof h.RotateZ) m.rotationZ = x.value; + else if (x instanceof h.SkewX) m.skewX = x.value; + else if (x instanceof h.SkewY) m.skewY = x.value; + else if (x instanceof h.PrimaryColor) m.primaryColor = x.value; + else if (x instanceof h.SecondaryColor) m.secondaryColor = x.value; + else if (x instanceof h.OutlineColor) m.outlineColor = x.value; + else if (x instanceof h.ShadowColor) m.shadowColor = x.value; + else if (x instanceof h.Alpha) m.primaryAlpha = x.value, m.secondaryAlpha = x.value, m.outlineAlpha = x.value, m.shadowAlpha = x.value; + else if (x instanceof h.PrimaryAlpha) m.primaryAlpha = x.value; + else if (x instanceof h.SecondaryAlpha) m.secondaryAlpha = x.value; + else if (x instanceof h.OutlineAlpha) m.outlineAlpha = x.value; + else if (x instanceof h.ShadowAlpha) m.shadowAlpha = x.value; + else if (x instanceof h.Alignment); + else if (x instanceof h.ColorKaraoke) S(!1), b.add("step-end", [new l.Keyframe(0, new v.Map([ + ["color", m.secondaryColor.withAlpha(m.secondaryAlpha).toString()] + ])), new l.Keyframe(C, new v.Map([ + ["color", m.primaryColor.withAlpha(m.primaryAlpha).toString()] + ]))]), C += x.duration; + else if (x instanceof h.WrappingStyle) P = x.value; + else if (x instanceof h.Reset) m.reset(this.ass.styles.get(x.value)); + else if (x instanceof h.Position) u.style.position = "absolute", u.style.left = (this.ot * x.x).toFixed(3) + "px", u.style.top = (this.at * x.y).toFixed(3) + "px"; + else if (x instanceof h.Move) u.style.position = "absolute", c.add("linear", [new l.Keyframe(0, new v.Map([ + ["left", (this.ot * x.x1).toFixed(3) + "px"], + ["top", (this.at * x.y1).toFixed(3) + "px"] + ])), new l.Keyframe(x.t1, new v.Map([ + ["left", (this.ot * x.x1).toFixed(3) + "px"], + ["top", (this.at * x.y1).toFixed(3) + "px"] + ])), new l.Keyframe(x.t2, new v.Map([ + ["left", (this.ot * x.x2).toFixed(3) + "px"], + ["top", (this.at * x.y2).toFixed(3) + "px"] + ])), new l.Keyframe(e.end - e.start, new v.Map([ + ["left", (this.ot * x.x2).toFixed(3) + "px"], + ["top", (this.at * x.y2).toFixed(3) + "px"] + ]))]); + else if (x instanceof h.Fade) c.add("linear", [new l.Keyframe(0, new v.Map([ + ["opacity", "0"] + ])), new l.Keyframe(x.start, new v.Map([ + ["opacity", "1"] + ])), new l.Keyframe(e.end - e.start - x.end, new v.Map([ + ["opacity", "1"] + ])), new l.Keyframe(e.end - e.start, new v.Map([ + ["opacity", "0"] + ]))]); + else if (x instanceof h.ComplexFade) c.add("linear", [new l.Keyframe(0, new v.Map([ + ["opacity", x.a1.toFixed(3)] + ])), new l.Keyframe(x.t1, new v.Map([ + ["opacity", x.a1.toFixed(3)] + ])), new l.Keyframe(x.t2, new v.Map([ + ["opacity", x.a2.toFixed(3)] + ])), new l.Keyframe(x.t3, new v.Map([ + ["opacity", x.a2.toFixed(3)] + ])), new l.Keyframe(x.t4, new v.Map([ + ["opacity", x.a3.toFixed(3)] + ])), new l.Keyframe(e.end - e.start, new v.Map([ + ["opacity", x.a3.toFixed(3)] + ]))]); + else if (x instanceof h.Transform) + for (var j = a <= x.start ? 0 : a >= x.end ? 1 : Math.pow((a - x.start) / (x.end - x.start), x.accel), A = 0, T = x.tags; A < T.length; A++) { + var D = T[A]; + D instanceof h.Border ? (m.outlineWidth += j * (D.value - m.outlineWidth), m.outlineHeight += j * (D.value - m.outlineHeight)) : D instanceof h.BorderX ? m.outlineWidth += j * (D.value - m.outlineWidth) : D instanceof h.BorderY ? m.outlineHeight += j * (D.value - m.outlineHeight) : D instanceof h.Shadow ? (m.shadowDepthX += j * (D.value - m.shadowDepthX), m.shadowDepthY += j * (D.value - m.shadowDepthY)) : D instanceof h.ShadowX ? m.shadowDepthX += j * (D.value - m.shadowDepthX) : D instanceof h.ShadowY ? m.shadowDepthY += j * (D.value - m.shadowDepthY) : D instanceof h.Blur ? m.blur += j * (D.value - m.blur) : D instanceof h.GaussianBlur ? m.gaussianBlur += j * (D.value - m.gaussianBlur) : D instanceof h.FontSize ? m.fontSize += j * (D.value - m.fontSize) : D instanceof h.FontSizePlus ? m.fontSize += j * D.value : D instanceof h.FontSizeMinus ? m.fontSize -= j * D.value : D instanceof h.FontScaleX ? m.fontScaleX += j * (D.value - m.fontScaleX) : D instanceof h.FontScaleY ? m.fontScaleY += j * (D.value - m.fontScaleY) : D instanceof h.LetterSpacing ? m.letterSpacing += j * (D.value - m.letterSpacing) : D instanceof h.RotateX ? m.rotationX += j * (D.value - m.rotationX) : D instanceof h.RotateY ? m.rotationY += j * (D.value - m.rotationY) : D instanceof h.RotateZ ? m.rotationZ += j * (D.value - m.rotationZ) : D instanceof h.SkewX ? m.skewX += j * (D.value - m.skewX) : D instanceof h.SkewY ? m.skewY += j * (D.value - m.skewY) : D instanceof h.PrimaryColor ? m.primaryColor = m.primaryColor.interpolate(D.value, j) : D instanceof h.SecondaryColor ? m.secondaryColor = m.secondaryColor.interpolate(D.value, j) : D instanceof h.OutlineColor ? m.outlineColor = m.outlineColor.interpolate(D.value, j) : D instanceof h.ShadowColor ? m.shadowColor = m.shadowColor.interpolate(D.value, j) : D instanceof h.Alpha ? (m.primaryAlpha += j * (D.value - m.primaryAlpha), m.secondaryAlpha += j * (D.value - m.secondaryAlpha), m.outlineAlpha += j * (D.value - m.outlineAlpha), m.shadowAlpha += j * (D.value - m.shadowAlpha)) : D instanceof h.PrimaryAlpha ? m.primaryAlpha += j * (D.value - m.primaryAlpha) : D instanceof h.SecondaryAlpha ? m.secondaryAlpha += j * (D.value - m.secondaryAlpha) : D instanceof h.OutlineAlpha ? m.outlineAlpha += j * (D.value - m.outlineAlpha) : D instanceof h.ShadowAlpha && (m.shadowAlpha += j * (D.value - m.shadowAlpha)) + } else x instanceof h.DrawingMode ? 0 !== x.scale && (O.scale = x.scale) : x instanceof h.DrawingBaselineOffset ? O.baselineOffset = x.value : x instanceof h.DrawingInstructions ? (y.appendChild(O.toSVG(x, m.primaryColor.withAlpha(m.primaryAlpha))), S(!1)) : x instanceof h.Text ? (y.appendChild(document.createTextNode(x.value + "‌")), S(!1)) : f.debugMode && x instanceof h.Comment ? (y.appendChild(document.createTextNode(x.value)), S(!1)) : x instanceof h.NewLine && S(!0) + } + for (var F = 0, M = e.parts; F < M.length; F++) { + var x = M[F]; + if (x instanceof h.Position || x instanceof h.Move) { + var R = r.lt[e.alignment], + N = "translate(" + -R[0] + "%, " + -R[1] + "%) translate(-" + u.style.marginLeft + ", -" + u.style.marginTop + ")", + W = R[0] + "% " + R[1] + "%"; + u.style.webkitTransform = N, u.style.webkitTransformOrigin = W, u.style.transform = N, u.style.transformOrigin = W; + break + } + } + switch (P) { + case _.WrappingStyle.EndOfLineWrapping: + u.style.whiteSpace = "pre-wrap"; + break; + case _.WrappingStyle.NoLineWrapping: + u.style.whiteSpace = "pre"; + break; + case _.WrappingStyle.SmartWrappingWithWiderTopLine: + case _.WrappingStyle.SmartWrappingWithWiderBottomLine: + u.style.whiteSpace = "pre-wrap" + } + if ("" !== u.style.position) switch (e.alignment) { + case 1: + case 4: + case 7: + u.style.textAlign = "left"; + break; + case 2: + case 5: + case 8: + u.style.textAlign = "center"; + break; + case 3: + case 6: + case 9: + u.style.textAlign = "right" + } + u.style.webkitAnimation = c.animationStyle, u.style.animation = c.animationStyle, u.setAttribute("data-dialogue-id", this.id + "-" + e.id), "" !== p.textContent && u.appendChild(p), g.hasChildNodes() && u.appendChild(d); + var L = { + sub: u, + animationDelays: c.animationDelays + }; + return e.containsTransformTag || this.Qe.set(e.id, L), L + }, r.prototype.draw = function(e) { + var t = this; + if (!this.$e.has(e) || e.containsTransformTag) { + f.debugMode && console.log(e.toString()); + var r = this.Qe.get(e.id); + void 0 === r && (r = this.preRender(e), f.debugMode && console.log(e.toString())); + var n = r.sub.cloneNode(!0), + i = function(n) { + var i = n.style.animationName || n.style.webkitAnimationName; + if (void 0 !== i && "" !== i) { + var o = i.split(",").map(function(n) { + n = n.trim(); + var i = r.animationDelays.get(n); + return ((i + e.start - t.clock.currentTime) / t.clock.rate).toFixed(3) + "s" + }).join(", "); + n.style.webkitAnimationDelay = o, n.style.animationDelay = o + } + }; + i(n); + for (var o = n.querySelectorAll('[style*="animation:"]'), a = 0; a < o.length; a++) i(o[a]); + var l = e.layer, + s = "absolute" === n.style.position ? 0 : e.alignment; + if (void 0 === this.Ke[l]) { + var u = document.createElement("div"); + u.className = "layer layer" + l; + for (var p = null, c = l + 1; c < this.Ke.length && null === p; c++) void 0 !== this.Ke[c] && (p = this.Ke[c]); + this.et.insertBefore(u, p), this.Ke[l] = u, this.Ze[l] = [] + } + if (void 0 === this.Ze[l][s]) { + var h = document.createElement("div"); + h.className = "an an" + s; + for (var u = this.Ke[l], p = null, d = s + 1; d < this.Ze[l].length && null === p; d++) void 0 !== this.Ze[l][d] && (p = this.Ze[l][d]); + u.insertBefore(h, p), this.Ze[l][s] = h + } + this.Ze[l][s].appendChild(n); + var _ = n.getElementsByTagName("style")[0]; + if (void 0 !== _) { + var g = _.sheet; + 0 === g.cssRules.length && (g.cssText = _.textContent) + } + this.$e.set(e, n) + } + }, r.prototype.Fe = function() { + t.prototype.Fe.call(this), this.nt(), this.et.style.display = "", this.et.classList.remove("paused") + }, r.prototype.Me = function() { + var e = this, + r = this.clock.currentTime; + this.$e.forEach(function(t, n) { + (n.start > r || n.end < r || n.containsTransformTag) && (e.$e.delete(n), e.st(t)) + }), t.prototype.Me.call(this) + }, r.prototype.Re = function() { + t.prototype.Re.call(this), this.et.classList.add("paused") + }, r.prototype.Ne = function() { + t.prototype.Ne.call(this), this.et.style.display = "none" + }, r.prototype.We = function() { + t.prototype.We.call(this), this.Qe.clear() + }, r.prototype.xe = function() { + this.be("ready", []) + }, r.prototype.rt = function(e, t) { + var r = this; + return t.then(function() { + var t = r.tt.cloneNode(!0); + return r.He.appendChild(t), y.lastly(a.calculateFontMetrics(e, r.settings.fallbackFonts, t), function() { + r.He.removeChild(t) + }) + }) + }, r.prototype.st = function(e) { + e.parentNode.removeChild(e) + }, r.prototype.nt = function() { + var e = this; + this.$e.forEach(function(t) { + return e.st(t) + }), this.$e.clear() + }, r.lt = [null, [0, 100], + [50, 100], + [100, 100], + [0, 50], + [50, 50], + [100, 50], + [0, 0], + [50, 0], + [100, 0] + ], r + }(p.NullRenderer); + t.WebRenderer = b, g.mixin(b, [u.EventSource]) + }, function(e, t) { + var r = t(19), + n = function() { + function e(e, t, r, n, i, o, a, l) { + this.ot = r, this.at = n, this.De = i, this.tt = o, this.ut = a, this.Je = l, this.pt = 0, this.Ae = e.id + "-" + t.id, this.ct = t.style, this.reset(null) + } + return e.prototype.reset = function(e) { + (void 0 === e || null === e) && (e = this.ct), this.italic = e.italic, this.bold = e.bold, this.underline = e.underline, this.strikeThrough = e.strikeThrough, this.outlineWidth = e.outlineThickness, this.outlineHeight = e.outlineThickness, this.shadowDepthX = e.shadowDepth, this.shadowDepthY = e.shadowDepth, this.fontName = e.fontName, this.fontSize = e.fontSize, this.fontScaleX = e.fontScaleX, this.fontScaleY = e.fontScaleY, this.letterSpacing = e.letterSpacing, this.ht = null, this.ft = null, this.dt = e.rotationZ, this._t = null, this.gt = null, this.primaryColor = e.primaryColor, this.secondaryColor = e.secondaryColor, this.outlineColor = e.outlineColor, this.shadowColor = e.shadowColor, this.primaryAlpha = e.primaryColor.alpha, this.secondaryAlpha = e.secondaryColor.alpha, this.outlineAlpha = e.outlineColor.alpha, this.shadowAlpha = e.shadowColor.alpha, this.blur = null, this.gaussianBlur = null + }, e.prototype.setStylesOnSpan = function(t, n) { + var i = t.childNodes[0] instanceof Text, + o = ""; + this.vt && (o += "italic "), this.yt === !0 ? o += "bold " : this.yt !== !1 && (o += this.yt + " "); + var a = (this.at * r.fontSizeForLineHeight(this.mt, this.bt * (i ? this.wt : 1), this.De.fallbackFonts, this.tt, this.Je)).toFixed(3), + l = (this.at * this.bt).toFixed(3), + s = this.mt; + switch (s) { + case "cursive": + case "fantasy": + case "monospace": + case "sans-serif": + case "serif": + break; + default: + s = '"' + s + '"' + } + "" !== this.De.fallbackFonts && (s += ", " + this.De.fallbackFonts), t.style.font = "" + o + a + "px/" + l + "px " + s; + var u = ""; + this.St && (u = "underline"), this.Ot && (u += " line-through"), t.style.textDecoration = u.trim(); + var p = ""; + if (i ? this.Pt !== this.wt && (p += "scaleY(" + (this.Pt / this.wt).toFixed(3) + ") ") : (1 !== this.wt && (p += "scaleX(" + this.wt + ") "), 1 !== this.Pt && (p += "scaleY(" + this.Pt + ") ")), null !== this.ft && (p += "rotateY(" + this.ft + "deg) "), null !== this.ht && (p += "rotateX(" + this.ht + "deg) "), 0 !== this.dt && (p += "rotateZ(" + -1 * this.dt + "deg) "), null !== this._t || null !== this.gt) { + var c = e.Ct(this._t, 0), + h = e.Ct(this.gt, 0); + p += "matrix(1, " + h + ", " + c + ", 1, 0, 0) " + } + "" !== p && (t.style.webkitTransform = p, t.style.webkitTransformOrigin = "50% 50%", t.style.transform = p, t.style.transformOrigin = "50% 50%", t.style.display = "inline-block"), t.style.letterSpacing = (this.ot * this.kt).toFixed(3) + "px"; + var f = this.ot * this.Et, + d = this.at * this.xt, + _ = document.createElement("span"); + _.appendChild(t); + var g = this.jt.withAlpha(this.At), + v = this.Tt.withAlpha(this.Dt), + y = this.Ft.withAlpha(this.Mt); + if (this.De.enableSvg || (0 !== f || 0 !== d) && v.alpha !== g.alpha || (0 !== this.Rt || 0 !== this.Nt) && y.alpha !== g.alpha || (g = this.jt.withAlpha(1), v = this.Tt.withAlpha(1), y = this.Ft.withAlpha(1), t.style.opacity = this.At.toFixed(3)), t.style.color = g.toString(), this.De.enableSvg ? this.Wt(_, f, d, v, this.At) : this.Lt(t, f, d, v), 0 !== this.Rt || 0 !== this.Nt) { + var m = y.toString() + " " + (this.Rt * this.ot).toFixed(3) + "px " + (this.Nt * this.at).toFixed(3) + "px 0px"; + "" === t.style.textShadow ? t.style.textShadow = m : t.style.textShadow += ", " + m + } + return (0 !== this.ht || 0 !== this.ft) && (_.style.display = "inline-block"), t.style.webkitAnimation = n.animationStyle, t.style.animation = n.animationStyle, _ + }, e.prototype.Wt = function(e, t, r, n, i) { + var o = "svg-filter-" + this.Ae + "-" + this.pt++, + a = document.createElementNS("http://www.w3.org/2000/svg", "filter"); + if (a.id = o, a.x.baseVal.valueAsString = "-50%", a.width.baseVal.valueAsString = "200%", a.y.baseVal.valueAsString = "-50%", a.height.baseVal.valueAsString = "200%", t > 0 || r > 0) { + var l = 0, + s = !this.De.preciseOutlines && this.It > 0 ? this.It : 1; + ! function(e) { + if (r >= t) + if (t > 0) { + var n; + for (n = 0; t >= n; n += s) e(n, r / t * Math.sqrt(t * t - n * n)); + n !== t + s && e(t, 0) + } else e(0, r); + else if (r > 0) { + var i; + for (i = 0; r >= i; i += s) e(t / r * Math.sqrt(r * r - i * i), i); + i !== r + s && e(0, r) + } else e(t, 0) + }(function(e, t) { + var r = document.createElementNS("http://www.w3.org/2000/svg", "feMorphology"); + a.appendChild(r), r.in1.baseVal = "source", r.operator.baseVal = SVGFEMorphologyElement.SVG_MORPHOLOGY_OPERATOR_DILATE, r.radiusX.baseVal = e, r.radiusY.baseVal = t, r.result.baseVal = "outline" + l, l++ + }); + var u = document.createElementNS("http://www.w3.org/2000/svg", "feComponentTransfer"); + a.insertBefore(u, a.firstElementChild), u.in1.baseVal = "SourceAlpha", u.result.baseVal = "source"; + var p = document.createElementNS("http://www.w3.org/2000/svg", "feFuncA"); + u.appendChild(p), p.type.baseVal = SVGComponentTransferFunctionElement.SVG_FECOMPONENTTRANSFER_TYPE_LINEAR, p.slope.baseVal = 0 === i ? 1 : 1 / i, p.intercept.baseVal = 0; + var c = document.createElementNS("http://www.w3.org/2000/svg", "feMerge"); + a.appendChild(c); + for (var h = 0; l > h; h++) { + var f = document.createElementNS("http://www.w3.org/2000/svg", "feMergeNode"); + c.appendChild(f), f.in1.baseVal = "outline" + h + } + var d = document.createElementNS("http://www.w3.org/2000/svg", "feComponentTransfer"); + a.appendChild(d), d.setAttribute("color-interpolation-filters", "sRGB"); + var _ = document.createElementNS("http://www.w3.org/2000/svg", "feFuncR"); + d.appendChild(_), _.type.baseVal = SVGComponentTransferFunctionElement.SVG_FECOMPONENTTRANSFER_TYPE_LINEAR, _.slope.baseVal = 0, _.intercept.baseVal = n.red / 255 * n.alpha; + var g = document.createElementNS("http://www.w3.org/2000/svg", "feFuncG"); + d.appendChild(g), g.type.baseVal = SVGComponentTransferFunctionElement.SVG_FECOMPONENTTRANSFER_TYPE_LINEAR, g.slope.baseVal = 0, g.intercept.baseVal = n.green / 255 * n.alpha; + var v = document.createElementNS("http://www.w3.org/2000/svg", "feFuncB"); + d.appendChild(v), v.type.baseVal = SVGComponentTransferFunctionElement.SVG_FECOMPONENTTRANSFER_TYPE_LINEAR, v.slope.baseVal = 0, v.intercept.baseVal = n.blue / 255 * n.alpha; + var y = document.createElementNS("http://www.w3.org/2000/svg", "feFuncA"); + if (d.appendChild(y), y.type.baseVal = SVGComponentTransferFunctionElement.SVG_FECOMPONENTTRANSFER_TYPE_LINEAR, y.slope.baseVal = n.alpha, y.intercept.baseVal = 0, this.It > 0) { + var m = document.createElementNS("http://www.w3.org/2000/svg", "feGaussianBlur"); + a.appendChild(m), m.stdDeviationX.baseVal = this.It, m.stdDeviationY.baseVal = this.It + } + for (var h = 0; h < this.Xt; h++) { + var b = document.createElementNS("http://www.w3.org/2000/svg", "feConvolveMatrix"); + a.appendChild(b), b.setAttribute("kernelMatrix", "1 2 1 2 4 2 1 2 1"), b.edgeMode.baseVal = SVGFEConvolveMatrixElement.SVG_EDGEMODE_NONE + } + var w = document.createElementNS("http://www.w3.org/2000/svg", "feComposite"); + a.appendChild(w), w.in2.baseVal = "source", w.operator.baseVal = SVGFECompositeElement.SVG_FECOMPOSITE_OPERATOR_OUT; + var S = document.createElementNS("http://www.w3.org/2000/svg", "feMerge"); + a.appendChild(S); + var O = document.createElementNS("http://www.w3.org/2000/svg", "feMergeNode"); + S.appendChild(O); + var P = document.createElementNS("http://www.w3.org/2000/svg", "feMergeNode"); + S.appendChild(P), P.in1.baseVal = "SourceGraphic" + } else { + if (this.It > 0) { + var m = document.createElementNS("http://www.w3.org/2000/svg", "feGaussianBlur"); + a.appendChild(m), m.stdDeviationX.baseVal = this.It, m.stdDeviationY.baseVal = this.It + } + for (var h = 0; h < this.Xt; h++) { + var b = document.createElementNS("http://www.w3.org/2000/svg", "feConvolveMatrix"); + a.appendChild(b), b.setAttribute("kernelMatrix", "1 2 1 2 4 2 1 2 1"), b.edgeMode.baseVal = SVGFEConvolveMatrixElement.SVG_EDGEMODE_NONE + } + } + a.childElementCount > 0 && (this.ut.appendChild(a), e.style.webkitFilter = 'url("#' + o + '")', e.style.filter = 'url("#' + o + '")') + }, e.prototype.Lt = function(e, t, r, n) { + var i = this; + if (t > 0 || r > 0) { + var o = ""; + ! function(e) { + for (var n = 0; t >= n; n++) + for (var i = 0 === t ? r : r * Math.sqrt(1 - n * n / (t * t)), o = 0; i >= o; o++) e(n, o), 0 !== n && e(-n, o), 0 !== o && e(n, -o), 0 !== n && 0 !== o && e(-n, -o) + }(function(e, t) { + o += ", " + n.toString() + " " + e + "px " + t + "px " + i.It.toFixed(3) + "px" + }), e.style.textShadow = o.substr(", ".length) + } + }, e.prototype.makeNewLine = function() { + var e = document.createElement("br"); + return e.style.lineHeight = (this.at * this.bt).toFixed(3) + "px", e + }, Object.defineProperty(e.prototype, "italic", { + set: function(t) { + this.vt = e.Ct(t, this.ct.italic) + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "bold", { + set: function(t) { + this.yt = e.Ct(t, this.ct.bold) + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "underline", { + set: function(t) { + this.St = e.Ct(t, this.ct.underline) + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "strikeThrough", { + set: function(t) { + this.Ot = e.Ct(t, this.ct.strikeThrough) + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "outlineWidth", { + get: function() { + return this.Et + }, + set: function(t) { + this.Et = e.Ct(t, this.ct.outlineThickness) + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "outlineHeight", { + get: function() { + return this.Et + }, + set: function(t) { + this.xt = e.Ct(t, this.ct.outlineThickness) + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "shadowDepthX", { + get: function() { + return this.Rt + }, + set: function(t) { + this.Rt = e.Ct(t, this.ct.shadowDepth) + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "shadowDepthY", { + get: function() { + return this.Nt + }, + set: function(t) { + this.Nt = e.Ct(t, this.ct.shadowDepth) + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "blur", { + get: function() { + return this.Xt + }, + set: function(t) { + this.Xt = e.Ct(t, 0) + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "gaussianBlur", { + get: function() { + return this.It + }, + set: function(t) { + this.It = e.Ct(t, 0) + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "fontName", { + set: function(t) { + this.mt = e.Ct(t, this.ct.fontName) + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "fontSize", { + get: function() { + return this.bt + }, + set: function(t) { + this.bt = e.Ct(t, this.ct.fontSize) + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "fontScaleX", { + get: function() { + return this.wt + }, + set: function(t) { + this.wt = e.Ct(t, this.ct.fontScaleX) + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "fontScaleY", { + get: function() { + return this.Pt + }, + set: function(t) { + this.Pt = e.Ct(t, this.ct.fontScaleY) + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "letterSpacing", { + get: function() { + return this.kt + }, + set: function(t) { + this.kt = e.Ct(t, this.ct.letterSpacing) + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "rotationX", { + get: function() { + return this.ht + }, + set: function(e) { + this.ht = e + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "rotationY", { + get: function() { + return this.ft + }, + set: function(e) { + this.ft = e + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "rotationZ", { + get: function() { + return this.dt + }, + set: function(t) { + this.dt = e.Ct(t, this.ct.rotationZ) + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "skewX", { + get: function() { + return this._t + }, + set: function(e) { + this._t = e + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "skewY", { + get: function() { + return this.gt + }, + set: function(e) { + this.gt = e + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "primaryColor", { + get: function() { + return this.jt + }, + set: function(t) { + this.jt = e.Ct(t, this.ct.primaryColor) + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "secondaryColor", { + get: function() { + return this.Yt + }, + set: function(t) { + this.Yt = e.Ct(t, this.ct.secondaryColor) + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "outlineColor", { + get: function() { + return this.Tt + }, + set: function(t) { + this.Tt = e.Ct(t, this.ct.outlineColor) + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "shadowColor", { + get: function() { + return this.Ft + }, + set: function(t) { + this.Ft = e.Ct(t, this.ct.shadowColor) + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "primaryAlpha", { + get: function() { + return this.At + }, + set: function(t) { + this.At = e.Ct(t, this.ct.primaryColor.alpha) + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "secondaryAlpha", { + get: function() { + return this.Vt + }, + set: function(t) { + this.Vt = e.Ct(t, this.ct.secondaryColor.alpha) + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "outlineAlpha", { + get: function() { + return this.Dt + }, + set: function(t) { + this.Dt = e.Ct(t, this.ct.outlineColor.alpha) + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "shadowAlpha", { + get: function() { + return this.Mt + }, + set: function(t) { + this.Mt = e.Ct(t, this.ct.shadowColor.alpha) + }, + enumerable: !0, + configurable: !0 + }), e.Ct = function(e, t) { + return null !== e ? e : t + }, e + }(); + e.SpanStyles = n + }, function(e) { + function t(t) { + e.debugMode = t + } + + function r(t) { + e.verboseMode = t + } + e.debugMode = !1, e.verboseMode = !1, e.setDebugMode = t, e.setVerboseMode = r + }, function(t, r) { + var n = r(26), + i = r(29), + o = r(28), + a = r(27), + l = r(23), + s = r(1), + u = r(2), + p = r(30), + c = r(32), + h = function() { + function t() { + if (this.Ue = new o.ScriptProperties, this.Bt = new p.Map, this.zt = [], this.Gt = [], this.qt = null, this.Ut = null, 1 === arguments.length) throw new Error("Constructor `new ASS(rawASS)` has been deprecated. Use `ASS.fromString(rawASS)` instead."); + this.Bt.set("Default", new i.Style(new p.Map([ + ["Name", "Default"] + ]))) + } + return Object.defineProperty(t.prototype, "properties", { + get: function() { + return this.Ue + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(t.prototype, "styles", { + get: function() { + return this.Bt + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(t.prototype, "dialogues", { + get: function() { + return this.zt + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(t.prototype, "attachments", { + get: function() { + return this.Gt + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(t.prototype, "stylesFormatSpecifier", { + get: function() { + return this.qt + }, + set: function(e) { + this.qt = e + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(t.prototype, "dialoguesFormatSpecifier", { + get: function() { + return this.Ut + }, + set: function(e) { + this.Ut = e + }, + enumerable: !0, + configurable: !0 + }), t.prototype.addStyle = function(e) { + var t = u.parseLineIntoTypedTemplate(e, this.qt); + if (null !== t && "Style" === t.type) { + var r = t.template; + if (l.verboseMode) { + var n = ""; + r.forEach(function(e, t) { + return n += t + " = " + e + ", " + }), console.log("Read style: " + n) + } + var o = new i.Style(r); + this.Bt.set(o.name, o) + } + }, t.prototype.addEvent = function(e) { + var t = u.parseLineIntoTypedTemplate(e, this.Ut); + if (null !== t && "Dialogue" === t.type) { + var r = t.template; + if (l.verboseMode) { + var i = ""; + r.forEach(function(e, t) { + return i += t + " = " + e + ", " + }), console.log("Read dialogue: " + i) + } + this.dialogues.push(new n.Dialogue(r, this)) + } + }, t.prototype.addAttachment = function(e) { + this.Gt.push(e) + }, t.fromString = function(e, r) { + return void 0 === r && (r = a.Format.ASS), t.fromStream(new s.StringStream(e), r) + }, t.fromStream = function(e, t) { + switch (void 0 === t && (t = a.Format.ASS), t) { + case a.Format.ASS: + return new s.StreamParser(e).ass; + case a.Format.SRT: + return new s.SrtStreamParser(e).ass; + default: + throw new Error("Illegal value of type: " + t) + } + }, t.fromUrl = function(r, n) { + void 0 === n && (n = a.Format.ASS); + var i; + return i = "function" == typeof e.fetch && "function" == typeof e.ReadableStream && "function" == typeof e.ReadableStream.prototype.getReader && "function" == typeof e.TextDecoder ? e.fetch(r).then(function(e) { + if (e.ok === !1 || void 0 === e.ok && (e.status < 200 || e.status > 299)) throw new Error("HTTP request for " + r + " failed with status code " + e.status); + return t.fromReadableStream(e.body, "utf-8", n) + }) : c.Promise.reject(new Error("Not supported.")), i.catch(function(e) { + console.warn("fetch() failed, falling back to XHR: %o", e); + var i = new XMLHttpRequest, + o = t.fromStream(new s.XhrStream(i), n); + return i.open("GET", r, !0), i.send(), o + }) + }, t.fromReadableStream = function(e, r, n) { + return void 0 === r && (r = "utf-8"), void 0 === n && (n = a.Format.ASS), t.fromStream(new s.BrowserReadableStream(e, r), n) + }, t + }(); + t.ASS = h + }, function(e) { + ! function(e) { + e[e.Font = 0] = "Font", e[e.Graphic = 1] = "Graphic" + }(e.AttachmentType || (e.AttachmentType = {})); + var t = function() { + function e(e, t) { + this.Ht = e, this.Kt = t, this.Zt = "" + } + return Object.defineProperty(e.prototype, "filename", { + get: function() { + return this.Ht + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "type", { + get: function() { + return this.Kt + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "contents", { + get: function() { + return this.Zt + }, + set: function(e) { + this.Zt = e + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.Attachment = t + }, function(e, t) { + var r = t(27), + n = t(3), + i = t(8), + o = t(23), + a = t(30), + l = function() { + function e(t, n) { + this.Jt = null, this.$t = !1; + var i = new a.Map; + t.forEach(function(e, t) { + i.set(t.toLowerCase(), e) + }), t = i, this.Ae = ++e.Qt; + var l = t.get("style"); + if (void 0 !== l && null !== l && l.constructor === String && (l = l.replace(/^\*+/, ""), null !== l.match(/^Default$/i) && (l = "Default")), this.Le = n.styles.get(l), void 0 === this.Le && (o.debugMode && console.warn("Unrecognized style " + l + '. Falling back to "Default"'), this.Le = n.styles.get("Default")), void 0 === this.Le) throw new Error("Unrecognized style " + l); + if (this.s = e.er(t.get("start")), this.u = e.er(t.get("end")), this.tr = Math.max(r.valueOrDefault(t, "layer", parseInt, function(e) { + return !isNaN(e) + }, "0"), 0), this.rr = t.get("text"), void 0 === this.rr || null === this.rr || this.rr.constructor !== String) throw new Error("Dialogue doesn't have any text.") + } + return Object.defineProperty(e.prototype, "id", { + get: function() { + return this.Ae + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "start", { + get: function() { + return this.s + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "end", { + get: function() { + return this.u + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "style", { + get: function() { + return this.Le + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "alignment", { + get: function() { + return null === this.Jt && this.nr(), this.ir + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "layer", { + get: function() { + return this.tr + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "parts", { + get: function() { + return null === this.Jt && this.nr(), this.Jt + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "containsTransformTag", { + get: function() { + return null === this.Jt && this.nr(), this.$t + }, + enumerable: !0, + configurable: !0 + }), e.prototype.toString = function() { + return "#" + this.Ae + " [" + this.s.toFixed(3) + "-" + this.u.toFixed(3) + "] " + (null !== this.Jt ? this.Jt.join(", ") : this.rr) + }, e.prototype.nr = function() { + var e = this; + if (this.Jt = n.parse(this.rr, "dialogueParts"), this.ir = this.Le.alignment, this.Jt.forEach(function(t, r) { + t instanceof i.Alignment ? e.ir = t.value : t instanceof i.Move ? (null === t.t1 || null === t.t2) && (e.Jt[r] = new i.Move(t.x1, t.y1, t.x2, t.y2, 0, e.u - e.s)) : t instanceof i.Transform && ((null === t.start || null === t.end || null === t.accel) && (e.Jt[r] = new i.Transform(null === t.start ? 0 : t.start, null === t.end ? e.u - e.s : t.end, null === t.accel ? 1 : t.accel, t.tags)), e.$t = !0) + }), o.debugMode) { + var t = this.Jt.filter(function(e) { + return e instanceof i.Comment && -1 !== e.value.indexOf("\\") + }); + t.length > 0 && console.warn("Possible incorrect parse:\n" + this.rr + "\nwas parsed as\n" + this.toString() + "\nThe possibly incorrect parses are:\n" + t.join("\n")) + } + }, e.er = function(e) { + return e.split(":").reduce(function(e, t) { + return 60 * e + parseFloat(t) + }, 0) + }, e.Qt = -1, e + }(); + e.Dialogue = l + }, function(e) { + function t(e, t, r, n, i) { + var o = e.get(t); + if (void 0 === o) return r(i); + try { + var a = r(o); + if (null !== n && !n(a)) throw new Error("Validation failed."); + return a + } catch (e) { + throw new Error("Property " + t + " has invalid value " + o + " - " + e.stack) + } + }! function(e) { + e[e.ASS = 0] = "ASS", e[e.SRT = 1] = "SRT" + }(e.Format || (e.Format = {})), + function(e) { + e[e.SmartWrappingWithWiderTopLine = 0] = "SmartWrappingWithWiderTopLine", e[e.SmartWrappingWithWiderBottomLine = 3] = "SmartWrappingWithWiderBottomLine", e[e.EndOfLineWrapping = 1] = "EndOfLineWrapping", e[e.NoLineWrapping = 2] = "NoLineWrapping" + }(e.WrappingStyle || (e.WrappingStyle = {})), + function(e) { + e[e.Outline = 1] = "Outline", e[e.OpaqueBox = 3] = "OpaqueBox" + }(e.BorderStyle || (e.BorderStyle = {})), e.valueOrDefault = t + }, function(e) { + var t = function() { + function e() {} + return Object.defineProperty(e.prototype, "resolutionX", { + get: function() { + return this.or + }, + set: function(e) { + this.or = e + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "resolutionY", { + get: function() { + return this.ar + }, + set: function(e) { + this.ar = e + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "wrappingStyle", { + get: function() { + return this.lr + }, + set: function(e) { + this.lr = e + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "scaleBorderAndShadow", { + get: function() { + return this.sr + }, + set: function(e) { + this.sr = e + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.ScriptProperties = t + }, function(e, t) { + var r = t(27), + n = t(3), + i = t(30), + o = function() { + function e(e) { + var t = new i.Map; + if (e.forEach(function(e, r) { + t.set(r.toLowerCase(), e) + }), e = t, this.ur = e.get("name"), void 0 === this.ur || null === this.ur || this.ur.constructor !== String) throw new Error("Style doesn't have a name."); + this.ur = this.ur.replace(/^\*+/, ""), this.vt = !!r.valueOrDefault(e, "italic", parseFloat, function(e) { + return !isNaN(e) + }, "0"), this.yt = !!r.valueOrDefault(e, "bold", parseFloat, function(e) { + return !isNaN(e) + }, "0"), this.St = !!r.valueOrDefault(e, "underline", parseFloat, function(e) { + return !isNaN(e) + }, "0"), this.Ot = !!r.valueOrDefault(e, "strikeout", parseFloat, function(e) { + return !isNaN(e) + }, "0"), this.mt = r.valueOrDefault(e, "fontname", function(e) { + return e + }, function(e) { + return e.constructor === String + }, "sans-serif"), this.bt = r.valueOrDefault(e, "fontsize", parseFloat, function(e) { + return !isNaN(e) + }, "18"), this.wt = r.valueOrDefault(e, "scalex", parseFloat, function(e) { + return e >= 0 + }, "100") / 100, this.Pt = r.valueOrDefault(e, "scaley", parseFloat, function(e) { + return e >= 0 + }, "100") / 100, this.kt = r.valueOrDefault(e, "spacing", parseFloat, function(e) { + return e >= 0 + }, "0"), this.dt = r.valueOrDefault(e, "angle", parseFloat, function(e) { + return !isNaN(e) + }, "0"), this.jt = r.valueOrDefault(e, "primarycolour", function(e) { + return n.parse(e, "colorWithAlpha") + }, null, "&H00FFFFFF"), this.Yt = r.valueOrDefault(e, "secondarycolour", function(e) { + return n.parse(e, "colorWithAlpha") + }, null, "&H00FFFF00"), this.Tt = r.valueOrDefault(e, "outlinecolour", function(e) { + return n.parse(e, "colorWithAlpha") + }, null, "&H00000000"), this.Ft = r.valueOrDefault(e, "backcolour", function(e) { + return n.parse(e, "colorWithAlpha") + }, null, "&H80000000"), this.pr = r.valueOrDefault(e, "outline", parseFloat, function(e) { + return e >= 0 + }, "2"), this.cr = r.valueOrDefault(e, "borderstyle", parseInt, function(e) { + return r.BorderStyle[r.BorderStyle[e]] === e + }, "1"), this.hr = r.valueOrDefault(e, "shadow", parseFloat, function(e) { + return e >= 0 + }, "3"), this.ir = r.valueOrDefault(e, "alignment", parseInt, function(e) { + return e >= 1 && 9 >= e + }, "2"), this.fr = r.valueOrDefault(e, "marginl", parseFloat, function(e) { + return !isNaN(e) + }, "20"), this.dr = r.valueOrDefault(e, "marginr", parseFloat, function(e) { + return !isNaN(e) + }, "20"), this._r = r.valueOrDefault(e, "marginv", parseFloat, function(e) { + return !isNaN(e) + }, "20") + } + return Object.defineProperty(e.prototype, "name", { + get: function() { + return this.ur + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "italic", { + get: function() { + return this.vt + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "bold", { + get: function() { + return this.yt + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "underline", { + get: function() { + return this.St + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "strikeThrough", { + get: function() { + return this.Ot + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "fontName", { + get: function() { + return this.mt + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "fontSize", { + get: function() { + return this.bt + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "fontScaleX", { + get: function() { + return this.wt + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "fontScaleY", { + get: function() { + return this.Pt + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "letterSpacing", { + get: function() { + return this.kt + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "rotationZ", { + get: function() { + return this.dt + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "primaryColor", { + get: function() { + return this.jt + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "secondaryColor", { + get: function() { + return this.Yt + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "outlineColor", { + get: function() { + return this.Tt + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "shadowColor", { + get: function() { + return this.Ft + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "outlineThickness", { + get: function() { + return this.pr + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "borderStyle", { + get: function() { + return this.cr + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "shadowDepth", { + get: function() { + return this.hr + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "alignment", { + get: function() { + return this.ir + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "marginLeft", { + get: function() { + return this.fr + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "marginRight", { + get: function() { + return this.dr + }, + enumerable: !0, + configurable: !0 + }), Object.defineProperty(e.prototype, "marginVertical", { + get: function() { + return this._r + }, + enumerable: !0, + configurable: !0 + }), e + }(); + e.Style = o + }, function(t) { + function r(e) { + null !== e ? t.Map = e : t.Map = n + } + t.Map = e.Map; + var n = function() { + function e(e) { + if (this.clear(), void 0 !== e) { + if (!Array.isArray(e)) throw new Error("Non-array iterables are not supported by the SimpleMap constructor."); + for (var t = 0; t < e.length; t++) { + var r = e[t]; + this.set(r[0], r[1]) + } + } + } + return e.prototype.get = function(e) { + var t = this.gr(e); + if (null !== t) return this.vr[t] + }, e.prototype.has = function(e) { + var t = this.gr(e); + return null === t ? !1 : t in this.yr + }, e.prototype.set = function(e, t) { + var r = this.gr(e); + if (null === r) throw new Error("This Map implementation only supports Number and String keys, or keys with an id property."); + return r in this.yr || this.mr++, this.yr[r] = e, this.vr[r] = t, this + }, e.prototype.delete = function(e) { + var t = this.gr(e); + if (null === t) return !1; + var r = t in this.yr; + return r && (delete this.yr[t], delete this.vr[t], this.mr--), r + }, e.prototype.clear = function() { + this.yr = Object.create(null), this.vr = Object.create(null), this.mr = 0 + }, e.prototype.forEach = function(e, t) { + for (var r = 0, n = Object.keys(this.yr); r < n.length; r++) { + var i = n[r]; + e.call(t, this.vr[i], this.yr[i], this) + } + }, Object.defineProperty(e.prototype, "size", { + get: function() { + return this.mr + }, + enumerable: !0, + configurable: !0 + }), e.prototype.gr = function(e) { + return "number" == typeof e ? "#" + e : "string" == typeof e ? "'" + e : void 0 !== e.id ? "!" + e.id : null + }, e + }(); + (void 0 === t.Map || "function" != typeof t.Map.prototype.forEach || function() { + try { + return 2 !== new t.Map([ + [1, "foo"], + [2, "bar"] + ]).size + } catch (e) { + return !0 + } + }()) && (t.Map = n), t.setImplementation = r + }, function(e) { + function t(e, t) { + for (var r = 0; r < t.length; r++) + for (var n = t[r], i = 0, o = Object.getOwnPropertyNames(n.prototype); i < o.length; i++) { + var a = o[i]; + e.prototype[a] = n.prototype[a] + } + } + e.mixin = t + }, function(t) { + function r(e) { + null !== e ? t.Promise = e : t.Promise = s + } + + function n(e) { + return i(e, []) + } + + function i(e, r) { + if (0 === e.length) return t.Promise.reject(r); + var n = e[0], + o = e.slice(1); + return n.catch(function(e) { + return i(o, r.concat(e)) + }) + } + + function o(e) { + return new t.Promise(function(r, n) { + return t.Promise.all(e.map(function(e) { + return e.then(r, function(e) { + return e + }) + })).then(n) + }) + } + + function a(e, t) { + return e.then(function(e) { + return t(), e + }, function(e) { + throw t(), e + }) + } + t.Promise = e.Promise; + var l = function() { + var t = e.MutationObserver || e.WebkitMutationObserver; + if (void 0 !== e.process && "function" == typeof e.process.nextTick) return function(t) { + e.process.nextTick(t) + }; + if (void 0 !== t) { + var r = [], + n = !1, + i = document.createElement("div"), + o = new t(function() { + for (var e = r.splice(0, r.length), t = 0; t < e.length; t++) { + var o = e[t]; + o() + } + n = !1, r.length > 0 && (i.classList.toggle("foo"), n = !0) + }); + return o.observe(i, { + attributes: !0 + }), + function(e) { + r.push(e), n || (i.classList.toggle("foo"), n = !0) + } + } + return function(e) { + return setTimeout(e, 0) + } + }(), + s = function() { + function e(e) { + if (this.br = u.PENDING, this.wr = [], this.Sr = [], this.Or = null, this.Pr = null, "function" != typeof e) throw new TypeError('typeof executor !== "function"'); + var t = this.Cr(), + r = t.resolve, + n = t.reject; + try { + e(r, n) + } catch (e) { + n(e) + } + } + return e.prototype.then = function(e, t) { + var r = new p; + "function" != typeof e && (e = function(e) { + return e + }), "function" != typeof t && (t = function(e) { + throw e + }); + var n = { + capabilities: r, + handler: e + }, + i = { + capabilities: r, + handler: t + }; + switch (this.br) { + case u.PENDING: + this.wr.push(n), this.Sr.push(i); + break; + case u.FULFILLED: + this.kr(n, this.Or); + break; + case u.REJECTED: + this.Er(i, this.Pr) + } + return r.promise + }, e.prototype.catch = function(e) { + return this.then(null, e) + }, e.resolve = function(r) { + return r instanceof e ? r : new t.Promise(function(e) { + return e(r) + }) + }, e.reject = function(e) { + return new t.Promise(function(t, r) { + return r(e) + }) + }, e.all = function(e) { + return new t.Promise(function(r, n) { + var i = [], + o = e.length; + return 0 === o ? void r(i) : void e.forEach(function(e, a) { + return t.Promise.resolve(e).then(function(e) { + i[a] = e, o--, 0 === o && r(i) + }, n) + }) + }) + }, e.race = function(e) { + return new t.Promise(function(r, n) { + for (var i = 0; i < e.length; i++) { + var o = e[i]; + t.Promise.resolve(o).then(r, n) + } + }) + }, e.prototype.Cr = function() { + var e = this, + t = !1, + r = function(r) { + if (!t) { + if (t = !0, r === e) return void e.xr(new TypeError("resolution === this")); + if (null === r || "object" != typeof r && "function" != typeof r) return void e.jr(r); + try { + var n = r.then + } catch (t) { + return void e.xr(t) + } + return "function" != typeof n ? void e.jr(r) : void l(function() { + return e.Ar(r, n) + }) + } + }, + n = function(r) { + t || (t = !0, e.xr(r)) + }; + return { + resolve: r, + reject: n + } + }, e.prototype.Ar = function(e, t) { + var r = this.Cr(), + n = r.resolve, + i = r.reject; + try { + t.call(e, n, i) + } catch (e) { + i(e) + } + }, e.prototype.jr = function(e) { + var t = this.wr; + this.Or = e, this.wr = void 0, this.Sr = void 0, this.br = u.FULFILLED; + for (var r = 0; r < t.length; r++) { + var n = t[r]; + this.kr(n, e) + } + }, e.prototype.xr = function(e) { + var t = this.Sr; + this.Pr = e, this.wr = void 0, this.Sr = void 0, this.br = u.REJECTED; + for (var r = 0; r < t.length; r++) { + var n = t[r]; + this.Er(n, e) + } + }, e.prototype.kr = function(e, t) { + l(function() { + var r, n = e.capabilities, + i = n.resolve, + o = n.reject, + a = e.handler; + try { + r = a(t) + } catch (e) { + return void o(e) + } + i(r) + }) + }, e.prototype.Er = function(e, t) { + l(function() { + var r, n = e.capabilities, + i = n.resolve, + o = n.reject, + a = e.handler; + try { + r = a(t) + } catch (e) { + return void o(e) + } + i(r) + }) + }, e + }(); + void 0 === t.Promise && (t.Promise = s); + var u; + ! function(e) { + e[e.PENDING = 0] = "PENDING", e[e.FULFILLED = 1] = "FULFILLED", e[e.REJECTED = 2] = "REJECTED" + }(u || (u = {})), t.setImplementation = r; + var p = function() { + function e() { + var e = this; + this.Tr = new t.Promise(function(t, r) { + Object.defineProperties(e, { + resolve: { + value: t, + enumerable: !0 + }, + reject: { + value: r, + enumerable: !0 + } + }) + }) + } + return Object.defineProperty(e.prototype, "promise", { + get: function() { + return this.Tr + }, + enumerable: !0, + configurable: !0 + }), e + }(); + t.DeferredPromise = p, t.first = n, t.any = o, t.lastly = a + }, function(t) { + function r(e) { + null !== e ? t.Set = e : t.Set = n + } + t.Set = e.Set; + var n = function() { + function e(e) { + if (this.clear(), void 0 !== e) { + if (!Array.isArray(e)) throw new Error("Non-array iterables are not supported by the SimpleSet constructor."); + for (var t = 0; t < e.length; t++) { + var r = e[t]; + this.add(r) + } + } + } + return e.prototype.add = function(e) { + var t = this.Dr(e); + if (null === t) throw new Error("This Set implementation only supports Number and String values."); + return t in this.Fr || this.mr++, this.Fr[t] = e, this + }, e.prototype.clear = function() { + this.Fr = Object.create(null), this.mr = 0 + }, e.prototype.has = function(e) { + var t = this.Dr(e); + return null === t ? !1 : t in this.Fr + }, e.prototype.forEach = function(e, t) { + for (var r = 0, n = Object.keys(this.Fr); r < n.length; r++) { + var i = n[r], + o = this.Fr[i]; + e.call(t, o, o, this) + } + }, Object.defineProperty(e.prototype, "size", { + get: function() { + return this.mr + }, + enumerable: !0, + configurable: !0 + }), e.prototype.Dr = function(e) { + return "number" == typeof e ? "#" + e : "string" == typeof e ? "'" + e : null + }, e + }(); + (void 0 === t.Set || "function" != typeof t.Set.prototype.forEach || function() { + try { + return 2 !== new t.Set([1, 2]).size + } catch (e) { + return !0 + } + }()) && (t.Set = n), t.setImplementation = r + }, function(e) { + function t(e, t) { + function r() { + this.constructor = e + } + for (var n in t) t.hasOwnProperty(n) && (e[n] = t[n]); + r.prototype = t.prototype, e.prototype = new r + } + + function r(e, t, r) { + return arguments.length < 3 ? n(e.reverse(), t) : void i(e.reverse(), t, r) + } + + function n(e, t) { + for (var r = 0; r < e.length; r++) { + var n = e[r]; + t = n(t) || t + } + return t + } + + function i(e, t, r) { + for (var n = 0; n < e.length; n++) { + var i = e[n]; + i(t, r) + } + } + e.ke = t, e.L = r + }, function(e, t) { + var r = t(30), + n = t(32), + i = t(36), + o = t(38), + a = function() { + function e(e) { + var t = this; + this.Mr = e, this.Rr = new r.Map, this.Mr.addEventListener("message", function(e) { + return t.Nr(e.data) + }, !1) + } + return e.prototype.request = function(t, r) { + var i = new n.DeferredPromise, + a = ++e.Wr; + this.Rr.set(a, i); + var l = { + requestId: a, + command: t, + parameters: r + }; + return this.Mr.postMessage(o.serialize(l)), i.promise + }, e.prototype.cancelRequest = function(e) { + var t = this.Rr.get(e); + void 0 !== t && (this.Rr.delete(e), t.reject(new Error("Cancelled."))) + }, e.prototype.Lr = function(e) { + var t = e.requestId, + r = e.error, + n = e.result; + r instanceof Error && (r = { + message: r.message, + stack: r.stack + }), this.Mr.postMessage(o.serialize({ + command: i.WorkerCommands.Response, + requestId: t, + error: r, + result: n + })) + }, e.prototype.Nr = function(e) { + var t = this, + r = o.deserialize(e); + if (r.command === i.WorkerCommands.Response) { + var n = r, + a = this.Rr.get(n.requestId); + void 0 !== a && (this.Rr.delete(n.requestId), null === n.error ? a.resolve(n.result) : a.reject(n.error)) + } else { + var l = r, + s = l.requestId, + u = o.getWorkerCommandHandler(l.command); + if (void 0 === u) return void this.Lr({ + requestId: s, + error: new Error("No handler registered for command " + l.command), + result: null + }); + u(l.parameters).then(function(e) { + return { + requestId: s, + error: null, + result: e + } + }, function(e) { + return { + requestId: s, + error: e, + result: null + } + }).then(function(e) { + return t.Lr(e) + }) + } + }, e.Wr = -1, e + }(); + e.WorkerChannelImpl = a, o.registerWorkerCommand(i.WorkerCommands.Ping, function() { + return new n.Promise(function(e) { + return e(null) + }) + }) + }, function(e) { + ! function(e) { + e[e.Response = 0] = "Response", e[e.Parse = 1] = "Parse", e[e.Ping = 2] = "Ping" + }(e.WorkerCommands || (e.WorkerCommands = {})) + }, function(t, r) { + function n(e) { + return void 0 === e && (e = a.src), new i.WorkerChannelImpl(new Worker(e)) + } + var i = r(35), + o = r(36); + t.WorkerCommands = o.WorkerCommands, t.supported = "undefined" != typeof Worker; + var a = "undefined" != typeof document && void 0 !== document.currentScript ? document.currentScript : null; + t.createWorker = n, "undefined" != typeof WorkerGlobalScope && e instanceof WorkerGlobalScope && new i.WorkerChannelImpl(e) + }, function(e, t) { + function r(e, t) { + s.set(e, t) + } + + function n(e) { + return s.get(e) + } + + function i(e) { + e.Ir = u.size, u.set(e.Ir, e) + } + + function o(e) { + return JSON.stringify(e, function(e, t) { + return t && void 0 !== t.Ir && (t.Ir = t.Ir), t + }) + } + + function a(e) { + return JSON.parse(e, function(e, t) { + if (t && void 0 !== t.Ir) { + for (var r = Object.create(u.get(t.Ir)), n = 0, i = Object.keys(t); n < i.length; n++) { + var o = i[n]; + "_classTag" !== o && (r[o] = t[o]) + } + t = r + } + return t + }) + } + var l = t(30), + s = new l.Map, + u = new l.Map; + e.registerWorkerCommand = r, e.getWorkerCommandHandler = n, e.registerClassPrototype = i, e.serialize = o, e.deserialize = a + }]) +}); //# sourceMappingURL=libjass.min.js.map \ No newline at end of file diff --git a/dashboard-ui/bower_components/query-string/index.js b/dashboard-ui/bower_components/query-string/index.js index 9b2c41e8f8..515b745bf3 100644 --- a/dashboard-ui/bower_components/query-string/index.js +++ b/dashboard-ui/bower_components/query-string/index.js @@ -1 +1,18 @@ -"use strict";window.queryString={},window.queryString.extract=function(maybeUrl){return maybeUrl.split("?")[1]||""},window.queryString.parse=function(str){return"string"!=typeof str?{}:(str=str.trim().replace(/^(\?|#|&)/,""),str?str.split("&").reduce(function(ret,param){var parts=param.replace(/\+/g," ").split("="),key=parts[0],val=parts[1];return key=decodeURIComponent(key),val=void 0===val?null:decodeURIComponent(val),ret.hasOwnProperty(key)?Array.isArray(ret[key])?ret[key].push(val):ret[key]=[ret[key],val]:ret[key]=val,ret},{}):{})},window.queryString.stringify=function(obj){return obj?Object.keys(obj).sort().map(function(key){var val=obj[key];return Array.isArray(val)?val.sort().map(function(val2){return encodeURIComponent(key)+"="+encodeURIComponent(val2)}).join("&"):encodeURIComponent(key)+"="+encodeURIComponent(val)}).join("&"):""}; \ No newline at end of file +"use strict"; +window.queryString = {}, window.queryString.extract = function(maybeUrl) { + return maybeUrl.split("?")[1] || "" +}, window.queryString.parse = function(str) { + return "string" != typeof str ? {} : (str = str.trim().replace(/^(\?|#|&)/, ""), str ? str.split("&").reduce(function(ret, param) { + var parts = param.replace(/\+/g, " ").split("="), + key = parts[0], + val = parts[1]; + return key = decodeURIComponent(key), val = void 0 === val ? null : decodeURIComponent(val), ret.hasOwnProperty(key) ? Array.isArray(ret[key]) ? ret[key].push(val) : ret[key] = [ret[key], val] : ret[key] = val, ret + }, {}) : {}) +}, window.queryString.stringify = function(obj) { + return obj ? Object.keys(obj).sort().map(function(key) { + var val = obj[key]; + return Array.isArray(val) ? val.sort().map(function(val2) { + return encodeURIComponent(key) + "=" + encodeURIComponent(val2) + }).join("&") : encodeURIComponent(key) + "=" + encodeURIComponent(val) + }).join("&") : "" +}; \ No newline at end of file diff --git a/dashboard-ui/bower_components/query-string/test.js b/dashboard-ui/bower_components/query-string/test.js index 8fe0307a03..4e16ad17c1 100644 --- a/dashboard-ui/bower_components/query-string/test.js +++ b/dashboard-ui/bower_components/query-string/test.js @@ -1 +1,83 @@ -"use strict";var assert=require("assert"),qs=require("./");describe(".parse()",function(){it("query strings starting with a `?`",function(){assert.deepEqual(qs.parse("?foo=bar"),{foo:"bar"})}),it("query strings starting with a `#`",function(){assert.deepEqual(qs.parse("#foo=bar"),{foo:"bar"})}),it("query strings starting with a `&",function(){assert.deepEqual(qs.parse("&foo=bar&foo=baz"),{foo:["bar","baz"]})}),it("parse a query string",function(){assert.deepEqual(qs.parse("foo=bar"),{foo:"bar"})}),it("parse multiple query string",function(){assert.deepEqual(qs.parse("foo=bar&key=val"),{foo:"bar",key:"val"})}),it("parse query string without a value",function(){assert.deepEqual(qs.parse("foo"),{foo:null}),assert.deepEqual(qs.parse("foo&key"),{foo:null,key:null}),assert.deepEqual(qs.parse("foo=bar&key"),{foo:"bar",key:null})}),it("return empty object if no qss can be found",function(){assert.deepEqual(qs.parse("?"),{}),assert.deepEqual(qs.parse("&"),{}),assert.deepEqual(qs.parse("#"),{}),assert.deepEqual(qs.parse(" "),{})}),it("handle `+` correctly",function(){assert.deepEqual(qs.parse("foo+faz=bar+baz++"),{"foo faz":"bar baz "})}),it("handle multiple of the same key",function(){assert.deepEqual(qs.parse("foo=bar&foo=baz"),{foo:["bar","baz"]})}),it("query strings params including embedded `=`",function(){assert.deepEqual(qs.parse("?param=http%3A%2F%2Fsomeurl%3Fid%3D2837"),{param:"http://someurl?id=2837"})})}),describe(".stringify()",function(){it("stringify",function(){assert.strictEqual(qs.stringify({foo:"bar"}),"foo=bar"),assert.strictEqual(qs.stringify({foo:"bar",bar:"baz"}),"bar=baz&foo=bar")}),it("different types",function(){assert.strictEqual(qs.stringify(),""),assert.strictEqual(qs.stringify(0),"")}),it("URI encode",function(){assert.strictEqual(qs.stringify({"foo bar":"baz faz"}),"foo%20bar=baz%20faz")}),it("handle array value",function(){assert.strictEqual(qs.stringify({abc:"abc",foo:["bar","baz"]}),"abc=abc&foo=bar&foo=baz")})}),describe(".extract()",function(){it("should extract qs from url",function(){assert.equal(qs.extract("http://foo.bar/?abc=def&hij=klm"),"abc=def&hij=klm"),assert.equal(qs.extract("http://foo.bar/?"),"")}),it("should handle strings not containing qs",function(){assert.equal(qs.extract("http://foo.bar/"),""),assert.equal(qs.extract(""),"")}),it("should throw for invalid values",function(){assert.throws(function(){qs.extract(null)},TypeError),assert.throws(function(){qs.extract(void 0)},TypeError)})}); \ No newline at end of file +"use strict"; +var assert = require("assert"), + qs = require("./"); +describe(".parse()", function() { + it("query strings starting with a `?`", function() { + assert.deepEqual(qs.parse("?foo=bar"), { + foo: "bar" + }) + }), it("query strings starting with a `#`", function() { + assert.deepEqual(qs.parse("#foo=bar"), { + foo: "bar" + }) + }), it("query strings starting with a `&", function() { + assert.deepEqual(qs.parse("&foo=bar&foo=baz"), { + foo: ["bar", "baz"] + }) + }), it("parse a query string", function() { + assert.deepEqual(qs.parse("foo=bar"), { + foo: "bar" + }) + }), it("parse multiple query string", function() { + assert.deepEqual(qs.parse("foo=bar&key=val"), { + foo: "bar", + key: "val" + }) + }), it("parse query string without a value", function() { + assert.deepEqual(qs.parse("foo"), { + foo: null + }), assert.deepEqual(qs.parse("foo&key"), { + foo: null, + key: null + }), assert.deepEqual(qs.parse("foo=bar&key"), { + foo: "bar", + key: null + }) + }), it("return empty object if no qss can be found", function() { + assert.deepEqual(qs.parse("?"), {}), assert.deepEqual(qs.parse("&"), {}), assert.deepEqual(qs.parse("#"), {}), assert.deepEqual(qs.parse(" "), {}) + }), it("handle `+` correctly", function() { + assert.deepEqual(qs.parse("foo+faz=bar+baz++"), { + "foo faz": "bar baz " + }) + }), it("handle multiple of the same key", function() { + assert.deepEqual(qs.parse("foo=bar&foo=baz"), { + foo: ["bar", "baz"] + }) + }), it("query strings params including embedded `=`", function() { + assert.deepEqual(qs.parse("?param=http%3A%2F%2Fsomeurl%3Fid%3D2837"), { + param: "http://someurl?id=2837" + }) + }) +}), describe(".stringify()", function() { + it("stringify", function() { + assert.strictEqual(qs.stringify({ + foo: "bar" + }), "foo=bar"), assert.strictEqual(qs.stringify({ + foo: "bar", + bar: "baz" + }), "bar=baz&foo=bar") + }), it("different types", function() { + assert.strictEqual(qs.stringify(), ""), assert.strictEqual(qs.stringify(0), "") + }), it("URI encode", function() { + assert.strictEqual(qs.stringify({ + "foo bar": "baz faz" + }), "foo%20bar=baz%20faz") + }), it("handle array value", function() { + assert.strictEqual(qs.stringify({ + abc: "abc", + foo: ["bar", "baz"] + }), "abc=abc&foo=bar&foo=baz") + }) +}), describe(".extract()", function() { + it("should extract qs from url", function() { + assert.equal(qs.extract("http://foo.bar/?abc=def&hij=klm"), "abc=def&hij=klm"), assert.equal(qs.extract("http://foo.bar/?"), "") + }), it("should handle strings not containing qs", function() { + assert.equal(qs.extract("http://foo.bar/"), ""), assert.equal(qs.extract(""), "") + }), it("should throw for invalid values", function() { + assert.throws(function() { + qs.extract(null) + }, TypeError), assert.throws(function() { + qs.extract(void 0) + }, TypeError) + }) +}); \ No newline at end of file diff --git a/dashboard-ui/bower_components/requirejs/require.js b/dashboard-ui/bower_components/requirejs/require.js index e984fa964c..71ac94c3b5 100644 --- a/dashboard-ui/bower_components/requirejs/require.js +++ b/dashboard-ui/bower_components/requirejs/require.js @@ -1 +1,607 @@ -var requirejs,require,define;!function(global,setTimeout){function commentReplace(match,singlePrefix){return singlePrefix||""}function isFunction(it){return"[object Function]"===ostring.call(it)}function isArray(it){return"[object Array]"===ostring.call(it)}function each(ary,func){if(ary){var i;for(i=0;i-1&&(!ary[i]||!func(ary[i],i,ary));i-=1);}}function hasProp(obj,prop){return hasOwn.call(obj,prop)}function getOwn(obj,prop){return hasProp(obj,prop)&&obj[prop]}function eachProp(obj,func){var prop;for(prop in obj)if(hasProp(obj,prop)&&func(obj[prop],prop))break}function mixin(target,source,force,deepStringMixin){return source&&eachProp(source,function(value,prop){!force&&hasProp(target,prop)||(!deepStringMixin||"object"!=typeof value||!value||isArray(value)||isFunction(value)||value instanceof RegExp?target[prop]=value:(target[prop]||(target[prop]={}),mixin(target[prop],value,force,deepStringMixin)))}),target}function bind(obj,fn){return function(){return fn.apply(obj,arguments)}}function scripts(){return document.getElementsByTagName("script")}function defaultOnError(err){throw err}function getGlobal(value){if(!value)return value;var g=global;return each(value.split("."),function(part){g=g[part]}),g}function makeError(id,msg,err,requireModules){var e=new Error(msg+"\nhttp://requirejs.org/docs/errors.html#"+id);return e.requireType=id,e.requireModules=requireModules,err&&(e.originalError=err),e}function newContext(contextName){function trimDots(ary){var i,part;for(i=0;i0&&(ary.splice(i-1,2),i-=2)}}function normalize(name,baseName,applyMap){var mapValue,nameParts,i,j,nameSegment,lastIndex,foundMap,foundI,foundStarMap,starI,normalizedBaseParts,baseParts=baseName&&baseName.split("/"),map=config.map,starMap=map&&map["*"];if(name&&(name=name.split("/"),lastIndex=name.length-1,config.nodeIdCompat&&jsSuffixRegExp.test(name[lastIndex])&&(name[lastIndex]=name[lastIndex].replace(jsSuffixRegExp,"")),"."===name[0].charAt(0)&&baseParts&&(normalizedBaseParts=baseParts.slice(0,baseParts.length-1),name=normalizedBaseParts.concat(name)),trimDots(name),name=name.join("/")),applyMap&&map&&(baseParts||starMap)){nameParts=name.split("/");outerLoop:for(i=nameParts.length;i>0;i-=1){if(nameSegment=nameParts.slice(0,i).join("/"),baseParts)for(j=baseParts.length;j>0;j-=1)if((mapValue=getOwn(map,baseParts.slice(0,j).join("/")))&&(mapValue=getOwn(mapValue,nameSegment))){foundMap=mapValue,foundI=i;break outerLoop}!foundStarMap&&starMap&&getOwn(starMap,nameSegment)&&(foundStarMap=getOwn(starMap,nameSegment),starI=i)}!foundMap&&foundStarMap&&(foundMap=foundStarMap,foundI=starI),foundMap&&(nameParts.splice(0,foundI,foundMap),name=nameParts.join("/"))}return getOwn(config.pkgs,name)||name}function removeScript(name){isBrowser&&each(scripts(),function(scriptNode){if(scriptNode.getAttribute("data-requiremodule")===name&&scriptNode.getAttribute("data-requirecontext")===context.contextName)return scriptNode.parentNode.removeChild(scriptNode),!0})}function hasPathFallback(id){var pathConfig=getOwn(config.paths,id);if(pathConfig&&isArray(pathConfig)&&pathConfig.length>1)return pathConfig.shift(),context.require.undef(id),context.makeRequire(null,{skipMap:!0})([id]),!0}function splitPrefix(name){var prefix,index=name?name.indexOf("!"):-1;return index>-1&&(prefix=name.substring(0,index),name=name.substring(index+1,name.length)),[prefix,name]}function makeModuleMap(name,parentModuleMap,isNormalized,applyMap){var url,pluginModule,suffix,nameParts,prefix=null,parentName=parentModuleMap?parentModuleMap.name:null,originalName=name,isDefine=!0,normalizedName="";return name||(isDefine=!1,name="_@r"+(requireCounter+=1)),nameParts=splitPrefix(name),prefix=nameParts[0],name=nameParts[1],prefix&&(prefix=normalize(prefix,parentName,applyMap),pluginModule=getOwn(defined,prefix)),name&&(prefix?normalizedName=isNormalized?name:pluginModule&&pluginModule.normalize?pluginModule.normalize(name,function(name){return normalize(name,parentName,applyMap)}):-1===name.indexOf("!")?normalize(name,parentName,applyMap):name:(normalizedName=normalize(name,parentName,applyMap),nameParts=splitPrefix(normalizedName),prefix=nameParts[0],normalizedName=nameParts[1],isNormalized=!0,url=context.nameToUrl(normalizedName))),suffix=!prefix||pluginModule||isNormalized?"":"_unnormalized"+(unnormalizedCounter+=1),{prefix:prefix,name:normalizedName,parentMap:parentModuleMap,unnormalized:!!suffix,url:url,originalName:originalName,isDefine:isDefine,id:(prefix?prefix+"!"+normalizedName:normalizedName)+suffix}}function getModule(depMap){var id=depMap.id,mod=getOwn(registry,id);return mod||(mod=registry[id]=new context.Module(depMap)),mod}function on(depMap,name,fn){var id=depMap.id,mod=getOwn(registry,id);!hasProp(defined,id)||mod&&!mod.defineEmitComplete?(mod=getModule(depMap),mod.error&&"error"===name?fn(mod.error):mod.on(name,fn)):"defined"===name&&fn(defined[id])}function onError(err,errback){var ids=err.requireModules,notified=!1;errback?errback(err):(each(ids,function(id){var mod=getOwn(registry,id);mod&&(mod.error=err,mod.events.error&&(notified=!0,mod.emit("error",err)))}),notified||req.onError(err))}function takeGlobalQueue(){globalDefQueue.length&&(each(globalDefQueue,function(queueItem){var id=queueItem[0];"string"==typeof id&&(context.defQueueMap[id]=!0),defQueue.push(queueItem)}),globalDefQueue=[])}function cleanRegistry(id){delete registry[id],delete enabledRegistry[id]}function breakCycle(mod,traced,processed){var id=mod.map.id;mod.error?mod.emit("error",mod.error):(traced[id]=!0,each(mod.depMaps,function(depMap,i){var depId=depMap.id,dep=getOwn(registry,depId);!dep||mod.depMatched[i]||processed[depId]||(getOwn(traced,depId)?(mod.defineDep(i,defined[depId]),mod.check()):breakCycle(dep,traced,processed))}),processed[id]=!0)}function checkLoaded(){var err,usingPathFallback,waitInterval=1e3*config.waitSeconds,expired=waitInterval&&context.startTime+waitInterval<(new Date).getTime(),noLoads=[],reqCalls=[],stillLoading=!1,needCycleCheck=!0;if(!inCheckLoaded){if(inCheckLoaded=!0,eachProp(enabledRegistry,function(mod){var map=mod.map,modId=map.id;if(mod.enabled&&(map.isDefine||reqCalls.push(mod),!mod.error))if(!mod.inited&&expired)hasPathFallback(modId)?(usingPathFallback=!0,stillLoading=!0):(noLoads.push(modId),removeScript(modId));else if(!mod.inited&&mod.fetched&&map.isDefine&&(stillLoading=!0,!map.prefix))return needCycleCheck=!1}),expired&&noLoads.length)return err=makeError("timeout","Load timeout for modules: "+noLoads,null,noLoads),err.contextName=context.contextName,onError(err);needCycleCheck&&each(reqCalls,function(mod){breakCycle(mod,{},{})}),expired&&!usingPathFallback||!stillLoading||!isBrowser&&!isWebWorker||checkLoadedTimeoutId||(checkLoadedTimeoutId=setTimeout(function(){checkLoadedTimeoutId=0,checkLoaded()},50)),inCheckLoaded=!1}}function callGetModule(args){hasProp(defined,args[0])||getModule(makeModuleMap(args[0],null,!0)).init(args[1],args[2])}function removeListener(node,func,name,ieName){node.detachEvent&&!isOpera?ieName&&node.detachEvent(ieName,func):node.removeEventListener(name,func,!1)}function getScriptData(evt){var node=evt.currentTarget||evt.srcElement;return removeListener(node,context.onScriptLoad,"load","onreadystatechange"),removeListener(node,context.onScriptError,"error"),{node:node,id:node&&node.getAttribute("data-requiremodule")}}function intakeDefines(){var args;for(takeGlobalQueue();defQueue.length;){if(args=defQueue.shift(),null===args[0])return onError(makeError("mismatch","Mismatched anonymous define() module: "+args[args.length-1]));callGetModule(args)}context.defQueueMap={}}var inCheckLoaded,Module,context,handlers,checkLoadedTimeoutId,config={waitSeconds:7,baseUrl:"./",paths:{},bundles:{},pkgs:{},shim:{},config:{}},registry={},enabledRegistry={},undefEvents={},defQueue=[],defined={},urlFetched={},bundlesMap={},requireCounter=1,unnormalizedCounter=1;return handlers={require:function(mod){return mod.require?mod.require:mod.require=context.makeRequire(mod.map)},exports:function(mod){if(mod.usingExports=!0,mod.map.isDefine)return mod.exports?defined[mod.map.id]=mod.exports:mod.exports=defined[mod.map.id]={}},module:function(mod){return mod.module?mod.module:mod.module={id:mod.map.id,uri:mod.map.url,config:function(){return getOwn(config.config,mod.map.id)||{}},exports:mod.exports||(mod.exports={})}}},Module=function(map){this.events=getOwn(undefEvents,map.id)||{},this.map=map,this.shim=getOwn(config.shim,map.id),this.depExports=[],this.depMaps=[],this.depMatched=[],this.pluginMaps={},this.depCount=0},Module.prototype={init:function(depMaps,factory,errback,options){options=options||{},this.inited||(this.factory=factory,errback?this.on("error",errback):this.events.error&&(errback=bind(this,function(err){this.emit("error",err)})),this.depMaps=depMaps&&depMaps.slice(0),this.errback=errback,this.inited=!0,this.ignore=options.ignore,options.enabled||this.enabled?this.enable():this.check())},defineDep:function(i,depExports){this.depMatched[i]||(this.depMatched[i]=!0,this.depCount-=1,this.depExports[i]=depExports)},fetch:function(){if(!this.fetched){this.fetched=!0,context.startTime=(new Date).getTime();var map=this.map;if(!this.shim)return map.prefix?this.callPlugin():this.load();context.makeRequire(this.map,{enableBuildCallback:!0})(this.shim.deps||[],bind(this,function(){return map.prefix?this.callPlugin():this.load()}))}},load:function(){var url=this.map.url;urlFetched[url]||(urlFetched[url]=!0,context.load(this.map.id,url))},check:function(){if(this.enabled&&!this.enabling){var err,cjsModule,id=this.map.id,depExports=this.depExports,exports=this.exports,factory=this.factory;if(this.inited){if(this.error)this.emit("error",this.error);else if(!this.defining){if(this.defining=!0,this.depCount<1&&!this.defined){if(isFunction(factory)){if(this.events.error&&this.map.isDefine||req.onError!==defaultOnError)try{exports=context.execCb(id,factory,depExports,exports)}catch(e){err=e}else exports=context.execCb(id,factory,depExports,exports);if(this.map.isDefine&&void 0===exports&&(cjsModule=this.module,cjsModule?exports=cjsModule.exports:this.usingExports&&(exports=this.exports)),err)return err.requireMap=this.map,err.requireModules=this.map.isDefine?[this.map.id]:null,err.requireType=this.map.isDefine?"define":"require",onError(this.error=err)}else exports=factory;if(this.exports=exports,this.map.isDefine&&!this.ignore&&(defined[id]=exports,req.onResourceLoad)){var resLoadMaps=[];each(this.depMaps,function(depMap){resLoadMaps.push(depMap.normalizedMap||depMap)}),req.onResourceLoad(context,this.map,resLoadMaps)}cleanRegistry(id),this.defined=!0}this.defining=!1,this.defined&&!this.defineEmitted&&(this.defineEmitted=!0,this.emit("defined",this.exports),this.defineEmitComplete=!0)}}else hasProp(context.defQueueMap,id)||this.fetch()}},callPlugin:function(){var map=this.map,id=map.id,pluginMap=makeModuleMap(map.prefix);this.depMaps.push(pluginMap),on(pluginMap,"defined",bind(this,function(plugin){var load,normalizedMap,normalizedMod,bundleId=getOwn(bundlesMap,this.map.id),name=this.map.name,parentName=this.map.parentMap?this.map.parentMap.name:null,localRequire=context.makeRequire(map.parentMap,{enableBuildCallback:!0});return this.map.unnormalized?(plugin.normalize&&(name=plugin.normalize(name,function(name){return normalize(name,parentName,!0)})||""),normalizedMap=makeModuleMap(map.prefix+"!"+name,this.map.parentMap,!0),on(normalizedMap,"defined",bind(this,function(value){this.map.normalizedMap=normalizedMap,this.init([],function(){return value},null,{enabled:!0,ignore:!0})})),void((normalizedMod=getOwn(registry,normalizedMap.id))&&(this.depMaps.push(normalizedMap),this.events.error&&normalizedMod.on("error",bind(this,function(err){this.emit("error",err)})),normalizedMod.enable()))):bundleId?(this.map.url=context.nameToUrl(bundleId),void this.load()):(load=bind(this,function(value){this.init([],function(){return value},null,{enabled:!0})}),load.error=bind(this,function(err){this.inited=!0,this.error=err,err.requireModules=[id],eachProp(registry,function(mod){0===mod.map.id.indexOf(id+"_unnormalized")&&cleanRegistry(mod.map.id)}),onError(err)}),load.fromText=bind(this,function(text,textAlt){var moduleName=map.name,moduleMap=makeModuleMap(moduleName),hasInteractive=useInteractive;textAlt&&(text=textAlt),hasInteractive&&(useInteractive=!1),getModule(moduleMap),hasProp(config.config,id)&&(config.config[moduleName]=config.config[id]);try{req.exec(text)}catch(e){return onError(makeError("fromtexteval","fromText eval for "+id+" failed: "+e,e,[id]))}hasInteractive&&(useInteractive=!0),this.depMaps.push(moduleMap),context.completeLoad(moduleName),localRequire([moduleName],load)}),void plugin.load(map.name,localRequire,load,config))})),context.enable(pluginMap,this),this.pluginMaps[pluginMap.id]=pluginMap},enable:function(){enabledRegistry[this.map.id]=this,this.enabled=!0,this.enabling=!0,each(this.depMaps,bind(this,function(depMap,i){var id,mod,handler;if("string"==typeof depMap){if(depMap=makeModuleMap(depMap,this.map.isDefine?this.map:this.map.parentMap,!1,!this.skipMap),this.depMaps[i]=depMap,handler=getOwn(handlers,depMap.id))return void(this.depExports[i]=handler(this));this.depCount+=1,on(depMap,"defined",bind(this,function(depExports){this.undefed||(this.defineDep(i,depExports),this.check())})),this.errback?on(depMap,"error",bind(this,this.errback)):this.events.error&&on(depMap,"error",bind(this,function(err){this.emit("error",err)}))}id=depMap.id,mod=registry[id],hasProp(handlers,id)||!mod||mod.enabled||context.enable(depMap,this)})),eachProp(this.pluginMaps,bind(this,function(pluginMap){var mod=getOwn(registry,pluginMap.id);mod&&!mod.enabled&&context.enable(pluginMap,this)})),this.enabling=!1,this.check()},on:function(name,cb){var cbs=this.events[name];cbs||(cbs=this.events[name]=[]),cbs.push(cb)},emit:function(name,evt){each(this.events[name],function(cb){cb(evt)}),"error"===name&&delete this.events[name]}},context={config:config,contextName:contextName,registry:registry,defined:defined,urlFetched:urlFetched,defQueue:defQueue,defQueueMap:{},Module:Module,makeModuleMap:makeModuleMap,nextTick:req.nextTick,onError:onError,configure:function(cfg){if(cfg.baseUrl&&"/"!==cfg.baseUrl.charAt(cfg.baseUrl.length-1)&&(cfg.baseUrl+="/"),"string"==typeof cfg.urlArgs){var urlArgs=cfg.urlArgs;cfg.urlArgs=function(id,url){return(-1===url.indexOf("?")?"?":"&")+urlArgs}}var shim=config.shim,objs={paths:!0,bundles:!0,config:!0,map:!0};eachProp(cfg,function(value,prop){objs[prop]?(config[prop]||(config[prop]={}),mixin(config[prop],value,!0,!0)):config[prop]=value}),cfg.bundles&&eachProp(cfg.bundles,function(value,prop){each(value,function(v){v!==prop&&(bundlesMap[v]=prop)})}),cfg.shim&&(eachProp(cfg.shim,function(value,id){isArray(value)&&(value={deps:value}),!value.exports&&!value.init||value.exportsFn||(value.exportsFn=context.makeShimExports(value)),shim[id]=value}),config.shim=shim),cfg.packages&&each(cfg.packages,function(pkgObj){var location,name;pkgObj="string"==typeof pkgObj?{name:pkgObj}:pkgObj,name=pkgObj.name,location=pkgObj.location,location&&(config.paths[name]=pkgObj.location),config.pkgs[name]=pkgObj.name+"/"+(pkgObj.main||"main").replace(currDirRegExp,"").replace(jsSuffixRegExp,"")}),eachProp(registry,function(mod,id){mod.inited||mod.map.unnormalized||(mod.map=makeModuleMap(id,null,!0))}),(cfg.deps||cfg.callback)&&context.require(cfg.deps||[],cfg.callback)},makeShimExports:function(value){function fn(){var ret;return value.init&&(ret=value.init.apply(global,arguments)),ret||value.exports&&getGlobal(value.exports)}return fn},makeRequire:function(relMap,options){function localRequire(deps,callback,errback){var id,map,requireMod;return options.enableBuildCallback&&callback&&isFunction(callback)&&(callback.__requireJsBuild=!0),"string"==typeof deps?isFunction(callback)?onError(makeError("requireargs","Invalid require call"),errback):relMap&&hasProp(handlers,deps)?handlers[deps](registry[relMap.id]):req.get?req.get(context,deps,relMap,localRequire):(map=makeModuleMap(deps,relMap,!1,!0),id=map.id,hasProp(defined,id)?defined[id]:onError(makeError("notloaded",'Module name "'+id+'" has not been loaded yet for context: '+contextName+(relMap?"":". Use require([])")))):(intakeDefines(),context.nextTick(function(){intakeDefines(),requireMod=getModule(makeModuleMap(null,relMap)),requireMod.skipMap=options.skipMap,requireMod.init(deps,callback,errback,{enabled:!0}),checkLoaded()}),localRequire)}return options=options||{},mixin(localRequire,{isBrowser:isBrowser,toUrl:function(moduleNamePlusExt){var ext,index=moduleNamePlusExt.lastIndexOf("."),segment=moduleNamePlusExt.split("/")[0],isRelative="."===segment||".."===segment;return-1!==index&&(!isRelative||index>1)&&(ext=moduleNamePlusExt.substring(index,moduleNamePlusExt.length),moduleNamePlusExt=moduleNamePlusExt.substring(0,index)),context.nameToUrl(normalize(moduleNamePlusExt,relMap&&relMap.id,!0),ext,!0)},defined:function(id){return hasProp(defined,makeModuleMap(id,relMap,!1,!0).id)},specified:function(id){return id=makeModuleMap(id,relMap,!1,!0).id,hasProp(defined,id)||hasProp(registry,id)}}),relMap||(localRequire.undef=function(id){takeGlobalQueue();var map=makeModuleMap(id,relMap,!0),mod=getOwn(registry,id);mod.undefed=!0,removeScript(id),delete defined[id],delete urlFetched[map.url],delete undefEvents[id],eachReverse(defQueue,function(args,i){args[0]===id&&defQueue.splice(i,1)}),delete context.defQueueMap[id],mod&&(mod.events.defined&&(undefEvents[id]=mod.events),cleanRegistry(id))}),localRequire},enable:function(depMap){getOwn(registry,depMap.id)&&getModule(depMap).enable()},completeLoad:function(moduleName){var found,args,mod,shim=getOwn(config.shim,moduleName)||{},shExports=shim.exports;for(takeGlobalQueue();defQueue.length;){if(args=defQueue.shift(),null===args[0]){if(args[0]=moduleName,found)break;found=!0}else args[0]===moduleName&&(found=!0);callGetModule(args)}if(context.defQueueMap={},mod=getOwn(registry,moduleName),!found&&!hasProp(defined,moduleName)&&mod&&!mod.inited){if(!(!config.enforceDefine||shExports&&getGlobal(shExports)))return hasPathFallback(moduleName)?void 0:onError(makeError("nodefine","No define call for "+moduleName,null,[moduleName]));callGetModule([moduleName,shim.deps||[],shim.exportsFn])}checkLoaded()},nameToUrl:function(moduleName,ext,skipExt){var paths,syms,i,parentModule,url,parentPath,bundleId,pkgMain=getOwn(config.pkgs,moduleName);if(pkgMain&&(moduleName=pkgMain),bundleId=getOwn(bundlesMap,moduleName))return context.nameToUrl(bundleId,ext,skipExt);if(req.jsExtRegExp.test(moduleName))url=moduleName+(ext||"");else{for(paths=config.paths,syms=moduleName.split("/"),i=syms.length;i>0;i-=1)if(parentModule=syms.slice(0,i).join("/"),parentPath=getOwn(paths,parentModule)){isArray(parentPath)&&(parentPath=parentPath[0]),syms.splice(0,i,parentPath);break}url=syms.join("/"),url+=ext||(/^data\:|^blob\:|\?/.test(url)||skipExt?"":".js"),url=("/"===url.charAt(0)||url.match(/^[\w\+\.\-]+:/)?"":config.baseUrl)+url}return config.urlArgs&&!/^blob\:/.test(url)?url+config.urlArgs(moduleName,url):url},load:function(id,url){req.load(context,id,url)},execCb:function(name,callback,args,exports){return callback.apply(exports,args)},onScriptLoad:function(evt){if("load"===evt.type||readyRegExp.test((evt.currentTarget||evt.srcElement).readyState)){interactiveScript=null;var data=getScriptData(evt);context.completeLoad(data.id)}},onScriptError:function(evt){var data=getScriptData(evt);if(!hasPathFallback(data.id)){var parents=[];return eachProp(registry,function(value,key){0!==key.indexOf("_@r")&&each(value.depMaps,function(depMap){if(depMap.id===data.id)return parents.push(key),!0})}),onError(makeError("scripterror",'Script error for "'+data.id+(parents.length?'", needed by: '+parents.join(", "):'"'),evt,[data.id]))}}},context.require=context.makeRequire(),context}function getInteractiveScript(){return interactiveScript&&"interactive"===interactiveScript.readyState?interactiveScript:(eachReverse(scripts(),function(script){if("interactive"===script.readyState)return interactiveScript=script}),interactiveScript)}var req,s,head,baseElement,dataMain,src,interactiveScript,currentlyAddingScript,mainScript,subPath,version="2.3.5",commentRegExp=/\/\*[\s\S]*?\*\/|([^:"'=]|^)\/\/.*$/gm,cjsRequireRegExp=/[^.]\s*require\s*\(\s*["']([^'"\s]+)["']\s*\)/g,jsSuffixRegExp=/\.js$/,currDirRegExp=/^\.\//,op=Object.prototype,ostring=op.toString,hasOwn=op.hasOwnProperty,isBrowser=!("undefined"==typeof window||"undefined"==typeof navigator||!window.document),isWebWorker=!isBrowser&&"undefined"!=typeof importScripts,readyRegExp=isBrowser&&"PLAYSTATION 3"===navigator.platform?/^complete$/:/^(complete|loaded)$/,defContextName="_",isOpera="undefined"!=typeof opera&&"[object Opera]"===opera.toString(),contexts={},cfg={},globalDefQueue=[],useInteractive=!1;if(void 0===define){if(void 0!==requirejs){if(isFunction(requirejs))return;cfg=requirejs,requirejs=void 0}void 0===require||isFunction(require)||(cfg=require,require=void 0),req=requirejs=function(deps,callback,errback,optional){var context,config,contextName=defContextName;return isArray(deps)||"string"==typeof deps||(config=deps,isArray(callback)?(deps=callback,callback=errback,errback=optional):deps=[]),config&&config.context&&(contextName=config.context),context=getOwn(contexts,contextName),context||(context=contexts[contextName]=req.s.newContext(contextName)),config&&context.configure(config),context.require(deps,callback,errback)},req.config=function(config){return req(config)},req.nextTick=void 0!==setTimeout?function(fn){setTimeout(fn,4)}:function(fn){fn()},require||(require=req),req.version=version,req.jsExtRegExp=/^\/|:|\?|\.js$/,req.isBrowser=isBrowser,s=req.s={contexts:contexts,newContext:newContext},req({}),each(["toUrl","undef","defined","specified"],function(prop){req[prop]=function(){var ctx=contexts[defContextName];return ctx.require[prop].apply(ctx,arguments)}}),isBrowser&&(head=s.head=document.getElementsByTagName("head")[0],(baseElement=document.getElementsByTagName("base")[0])&&(head=s.head=baseElement.parentNode)),req.onError=defaultOnError,req.createNode=function(config,moduleName,url){var node=config.xhtml?document.createElementNS("http://www.w3.org/1999/xhtml","html:script"):document.createElement("script");return node.type=config.scriptType||"text/javascript",node.charset="utf-8",node.async=!0,node},req.load=function(context,moduleName,url){var node,config=context&&context.config||{};if(isBrowser)return node=req.createNode(config,moduleName,url),node.setAttribute("data-requirecontext",context.contextName),node.setAttribute("data-requiremodule",moduleName),!node.attachEvent||node.attachEvent.toString&&node.attachEvent.toString().indexOf("[native code")<0||isOpera?(node.addEventListener("load",context.onScriptLoad,!1),node.addEventListener("error",context.onScriptError,!1)):(useInteractive=!0,node.attachEvent("onreadystatechange",context.onScriptLoad)),node.src=url,config.onNodeCreated&&config.onNodeCreated(node,config,moduleName,url),currentlyAddingScript=node,baseElement?head.insertBefore(node,baseElement):head.appendChild(node),currentlyAddingScript=null,node;if(isWebWorker)try{setTimeout(function(){},0),importScripts(url),context.completeLoad(moduleName)}catch(e){context.onError(makeError("importscripts","importScripts failed for "+moduleName+" at "+url,e,[moduleName]))}},isBrowser&&!cfg.skipDataMain&&eachReverse(scripts(),function(script){if(head||(head=script.parentNode),dataMain=script.getAttribute("data-main"))return mainScript=dataMain,cfg.baseUrl||-1!==mainScript.indexOf("!")||(src=mainScript.split("/"),mainScript=src.pop(),subPath=src.length?src.join("/")+"/":"./",cfg.baseUrl=subPath),mainScript=mainScript.replace(jsSuffixRegExp,""),req.jsExtRegExp.test(mainScript)&&(mainScript=dataMain),cfg.deps=cfg.deps?cfg.deps.concat(mainScript):[mainScript],!0}),define=function(name,deps,callback){var node,context;"string"!=typeof name&&(callback=deps,deps=name,name=null),isArray(deps)||(callback=deps,deps=null),!deps&&isFunction(callback)&&(deps=[],callback.length&&(callback.toString().replace(commentRegExp,commentReplace).replace(cjsRequireRegExp,function(match,dep){deps.push(dep)}),deps=(1===callback.length?["require"]:["require","exports","module"]).concat(deps))),useInteractive&&(node=currentlyAddingScript||getInteractiveScript())&&(name||(name=node.getAttribute("data-requiremodule")),context=contexts[node.getAttribute("data-requirecontext")]),context?(context.defQueue.push([name,deps,callback]),context.defQueueMap[name]=!0):globalDefQueue.push([name,deps,callback])},define.amd={jQuery:!0},req.exec=function(text){return eval(text)},req(cfg)}}(this,"undefined"==typeof setTimeout?void 0:setTimeout); \ No newline at end of file +var requirejs, require, define; +! function(global, setTimeout) { + function commentReplace(match, singlePrefix) { + return singlePrefix || "" + } + + function isFunction(it) { + return "[object Function]" === ostring.call(it) + } + + function isArray(it) { + return "[object Array]" === ostring.call(it) + } + + function each(ary, func) { + if (ary) { + var i; + for (i = 0; i < ary.length && (!ary[i] || !func(ary[i], i, ary)); i += 1); + } + } + + function eachReverse(ary, func) { + if (ary) { + var i; + for (i = ary.length - 1; i > -1 && (!ary[i] || !func(ary[i], i, ary)); i -= 1); + } + } + + function hasProp(obj, prop) { + return hasOwn.call(obj, prop) + } + + function getOwn(obj, prop) { + return hasProp(obj, prop) && obj[prop] + } + + function eachProp(obj, func) { + var prop; + for (prop in obj) + if (hasProp(obj, prop) && func(obj[prop], prop)) break + } + + function mixin(target, source, force, deepStringMixin) { + return source && eachProp(source, function(value, prop) { + !force && hasProp(target, prop) || (!deepStringMixin || "object" != typeof value || !value || isArray(value) || isFunction(value) || value instanceof RegExp ? target[prop] = value : (target[prop] || (target[prop] = {}), mixin(target[prop], value, force, deepStringMixin))) + }), target + } + + function bind(obj, fn) { + return function() { + return fn.apply(obj, arguments) + } + } + + function scripts() { + return document.getElementsByTagName("script") + } + + function defaultOnError(err) { + throw err + } + + function getGlobal(value) { + if (!value) return value; + var g = global; + return each(value.split("."), function(part) { + g = g[part] + }), g + } + + function makeError(id, msg, err, requireModules) { + var e = new Error(msg + "\nhttp://requirejs.org/docs/errors.html#" + id); + return e.requireType = id, e.requireModules = requireModules, err && (e.originalError = err), e + } + + function newContext(contextName) { + function trimDots(ary) { + var i, part; + for (i = 0; i < ary.length; i++) + if ("." === (part = ary[i])) ary.splice(i, 1), i -= 1; + else if (".." === part) { + if (0 === i || 1 === i && ".." === ary[2] || ".." === ary[i - 1]) continue; + i > 0 && (ary.splice(i - 1, 2), i -= 2) + } + } + + function normalize(name, baseName, applyMap) { + var mapValue, nameParts, i, j, nameSegment, lastIndex, foundMap, foundI, foundStarMap, starI, normalizedBaseParts, baseParts = baseName && baseName.split("/"), + map = config.map, + starMap = map && map["*"]; + if (name && (name = name.split("/"), lastIndex = name.length - 1, config.nodeIdCompat && jsSuffixRegExp.test(name[lastIndex]) && (name[lastIndex] = name[lastIndex].replace(jsSuffixRegExp, "")), "." === name[0].charAt(0) && baseParts && (normalizedBaseParts = baseParts.slice(0, baseParts.length - 1), name = normalizedBaseParts.concat(name)), trimDots(name), name = name.join("/")), applyMap && map && (baseParts || starMap)) { + nameParts = name.split("/"); + outerLoop: for (i = nameParts.length; i > 0; i -= 1) { + if (nameSegment = nameParts.slice(0, i).join("/"), baseParts) + for (j = baseParts.length; j > 0; j -= 1) + if ((mapValue = getOwn(map, baseParts.slice(0, j).join("/"))) && (mapValue = getOwn(mapValue, nameSegment))) { + foundMap = mapValue, foundI = i; + break outerLoop + }! foundStarMap && starMap && getOwn(starMap, nameSegment) && (foundStarMap = getOwn(starMap, nameSegment), starI = i) + }!foundMap && foundStarMap && (foundMap = foundStarMap, foundI = starI), foundMap && (nameParts.splice(0, foundI, foundMap), name = nameParts.join("/")) + } + return getOwn(config.pkgs, name) || name + } + + function removeScript(name) { + isBrowser && each(scripts(), function(scriptNode) { + if (scriptNode.getAttribute("data-requiremodule") === name && scriptNode.getAttribute("data-requirecontext") === context.contextName) return scriptNode.parentNode.removeChild(scriptNode), !0 + }) + } + + function hasPathFallback(id) { + var pathConfig = getOwn(config.paths, id); + if (pathConfig && isArray(pathConfig) && pathConfig.length > 1) return pathConfig.shift(), context.require.undef(id), context.makeRequire(null, { + skipMap: !0 + })([id]), !0 + } + + function splitPrefix(name) { + var prefix, index = name ? name.indexOf("!") : -1; + return index > -1 && (prefix = name.substring(0, index), name = name.substring(index + 1, name.length)), [prefix, name] + } + + function makeModuleMap(name, parentModuleMap, isNormalized, applyMap) { + var url, pluginModule, suffix, nameParts, prefix = null, + parentName = parentModuleMap ? parentModuleMap.name : null, + originalName = name, + isDefine = !0, + normalizedName = ""; + return name || (isDefine = !1, name = "_@r" + (requireCounter += 1)), nameParts = splitPrefix(name), prefix = nameParts[0], name = nameParts[1], prefix && (prefix = normalize(prefix, parentName, applyMap), pluginModule = getOwn(defined, prefix)), name && (prefix ? normalizedName = isNormalized ? name : pluginModule && pluginModule.normalize ? pluginModule.normalize(name, function(name) { + return normalize(name, parentName, applyMap) + }) : -1 === name.indexOf("!") ? normalize(name, parentName, applyMap) : name : (normalizedName = normalize(name, parentName, applyMap), nameParts = splitPrefix(normalizedName), prefix = nameParts[0], normalizedName = nameParts[1], isNormalized = !0, url = context.nameToUrl(normalizedName))), suffix = !prefix || pluginModule || isNormalized ? "" : "_unnormalized" + (unnormalizedCounter += 1), { + prefix: prefix, + name: normalizedName, + parentMap: parentModuleMap, + unnormalized: !!suffix, + url: url, + originalName: originalName, + isDefine: isDefine, + id: (prefix ? prefix + "!" + normalizedName : normalizedName) + suffix + } + } + + function getModule(depMap) { + var id = depMap.id, + mod = getOwn(registry, id); + return mod || (mod = registry[id] = new context.Module(depMap)), mod + } + + function on(depMap, name, fn) { + var id = depMap.id, + mod = getOwn(registry, id); + !hasProp(defined, id) || mod && !mod.defineEmitComplete ? (mod = getModule(depMap), mod.error && "error" === name ? fn(mod.error) : mod.on(name, fn)) : "defined" === name && fn(defined[id]) + } + + function onError(err, errback) { + var ids = err.requireModules, + notified = !1; + errback ? errback(err) : (each(ids, function(id) { + var mod = getOwn(registry, id); + mod && (mod.error = err, mod.events.error && (notified = !0, mod.emit("error", err))) + }), notified || req.onError(err)) + } + + function takeGlobalQueue() { + globalDefQueue.length && (each(globalDefQueue, function(queueItem) { + var id = queueItem[0]; + "string" == typeof id && (context.defQueueMap[id] = !0), defQueue.push(queueItem) + }), globalDefQueue = []) + } + + function cleanRegistry(id) { + delete registry[id], delete enabledRegistry[id] + } + + function breakCycle(mod, traced, processed) { + var id = mod.map.id; + mod.error ? mod.emit("error", mod.error) : (traced[id] = !0, each(mod.depMaps, function(depMap, i) { + var depId = depMap.id, + dep = getOwn(registry, depId); + !dep || mod.depMatched[i] || processed[depId] || (getOwn(traced, depId) ? (mod.defineDep(i, defined[depId]), mod.check()) : breakCycle(dep, traced, processed)) + }), processed[id] = !0) + } + + function checkLoaded() { + var err, usingPathFallback, waitInterval = 1e3 * config.waitSeconds, + expired = waitInterval && context.startTime + waitInterval < (new Date).getTime(), + noLoads = [], + reqCalls = [], + stillLoading = !1, + needCycleCheck = !0; + if (!inCheckLoaded) { + if (inCheckLoaded = !0, eachProp(enabledRegistry, function(mod) { + var map = mod.map, + modId = map.id; + if (mod.enabled && (map.isDefine || reqCalls.push(mod), !mod.error)) + if (!mod.inited && expired) hasPathFallback(modId) ? (usingPathFallback = !0, stillLoading = !0) : (noLoads.push(modId), removeScript(modId)); + else if (!mod.inited && mod.fetched && map.isDefine && (stillLoading = !0, !map.prefix)) return needCycleCheck = !1 + }), expired && noLoads.length) return err = makeError("timeout", "Load timeout for modules: " + noLoads, null, noLoads), err.contextName = context.contextName, onError(err); + needCycleCheck && each(reqCalls, function(mod) { + breakCycle(mod, {}, {}) + }), expired && !usingPathFallback || !stillLoading || !isBrowser && !isWebWorker || checkLoadedTimeoutId || (checkLoadedTimeoutId = setTimeout(function() { + checkLoadedTimeoutId = 0, checkLoaded() + }, 50)), inCheckLoaded = !1 + } + } + + function callGetModule(args) { + hasProp(defined, args[0]) || getModule(makeModuleMap(args[0], null, !0)).init(args[1], args[2]) + } + + function removeListener(node, func, name, ieName) { + node.detachEvent && !isOpera ? ieName && node.detachEvent(ieName, func) : node.removeEventListener(name, func, !1) + } + + function getScriptData(evt) { + var node = evt.currentTarget || evt.srcElement; + return removeListener(node, context.onScriptLoad, "load", "onreadystatechange"), removeListener(node, context.onScriptError, "error"), { + node: node, + id: node && node.getAttribute("data-requiremodule") + } + } + + function intakeDefines() { + var args; + for (takeGlobalQueue(); defQueue.length;) { + if (args = defQueue.shift(), null === args[0]) return onError(makeError("mismatch", "Mismatched anonymous define() module: " + args[args.length - 1])); + callGetModule(args) + } + context.defQueueMap = {} + } + var inCheckLoaded, Module, context, handlers, checkLoadedTimeoutId, config = { + waitSeconds: 7, + baseUrl: "./", + paths: {}, + bundles: {}, + pkgs: {}, + shim: {}, + config: {} + }, + registry = {}, + enabledRegistry = {}, + undefEvents = {}, + defQueue = [], + defined = {}, + urlFetched = {}, + bundlesMap = {}, + requireCounter = 1, + unnormalizedCounter = 1; + return handlers = { + require: function(mod) { + return mod.require ? mod.require : mod.require = context.makeRequire(mod.map) + }, + exports: function(mod) { + if (mod.usingExports = !0, mod.map.isDefine) return mod.exports ? defined[mod.map.id] = mod.exports : mod.exports = defined[mod.map.id] = {} + }, + module: function(mod) { + return mod.module ? mod.module : mod.module = { + id: mod.map.id, + uri: mod.map.url, + config: function() { + return getOwn(config.config, mod.map.id) || {} + }, + exports: mod.exports || (mod.exports = {}) + } + } + }, Module = function(map) { + this.events = getOwn(undefEvents, map.id) || {}, this.map = map, this.shim = getOwn(config.shim, map.id), this.depExports = [], this.depMaps = [], this.depMatched = [], this.pluginMaps = {}, this.depCount = 0 + }, Module.prototype = { + init: function(depMaps, factory, errback, options) { + options = options || {}, this.inited || (this.factory = factory, errback ? this.on("error", errback) : this.events.error && (errback = bind(this, function(err) { + this.emit("error", err) + })), this.depMaps = depMaps && depMaps.slice(0), this.errback = errback, this.inited = !0, this.ignore = options.ignore, options.enabled || this.enabled ? this.enable() : this.check()) + }, + defineDep: function(i, depExports) { + this.depMatched[i] || (this.depMatched[i] = !0, this.depCount -= 1, this.depExports[i] = depExports) + }, + fetch: function() { + if (!this.fetched) { + this.fetched = !0, context.startTime = (new Date).getTime(); + var map = this.map; + if (!this.shim) return map.prefix ? this.callPlugin() : this.load(); + context.makeRequire(this.map, { + enableBuildCallback: !0 + })(this.shim.deps || [], bind(this, function() { + return map.prefix ? this.callPlugin() : this.load() + })) + } + }, + load: function() { + var url = this.map.url; + urlFetched[url] || (urlFetched[url] = !0, context.load(this.map.id, url)) + }, + check: function() { + if (this.enabled && !this.enabling) { + var err, cjsModule, id = this.map.id, + depExports = this.depExports, + exports = this.exports, + factory = this.factory; + if (this.inited) { + if (this.error) this.emit("error", this.error); + else if (!this.defining) { + if (this.defining = !0, this.depCount < 1 && !this.defined) { + if (isFunction(factory)) { + if (this.events.error && this.map.isDefine || req.onError !== defaultOnError) try { + exports = context.execCb(id, factory, depExports, exports) + } catch (e) { + err = e + } else exports = context.execCb(id, factory, depExports, exports); + if (this.map.isDefine && void 0 === exports && (cjsModule = this.module, cjsModule ? exports = cjsModule.exports : this.usingExports && (exports = this.exports)), err) return err.requireMap = this.map, err.requireModules = this.map.isDefine ? [this.map.id] : null, err.requireType = this.map.isDefine ? "define" : "require", onError(this.error = err) + } else exports = factory; + if (this.exports = exports, this.map.isDefine && !this.ignore && (defined[id] = exports, req.onResourceLoad)) { + var resLoadMaps = []; + each(this.depMaps, function(depMap) { + resLoadMaps.push(depMap.normalizedMap || depMap) + }), req.onResourceLoad(context, this.map, resLoadMaps) + } + cleanRegistry(id), this.defined = !0 + } + this.defining = !1, this.defined && !this.defineEmitted && (this.defineEmitted = !0, this.emit("defined", this.exports), this.defineEmitComplete = !0) + } + } else hasProp(context.defQueueMap, id) || this.fetch() + } + }, + callPlugin: function() { + var map = this.map, + id = map.id, + pluginMap = makeModuleMap(map.prefix); + this.depMaps.push(pluginMap), on(pluginMap, "defined", bind(this, function(plugin) { + var load, normalizedMap, normalizedMod, bundleId = getOwn(bundlesMap, this.map.id), + name = this.map.name, + parentName = this.map.parentMap ? this.map.parentMap.name : null, + localRequire = context.makeRequire(map.parentMap, { + enableBuildCallback: !0 + }); + return this.map.unnormalized ? (plugin.normalize && (name = plugin.normalize(name, function(name) { + return normalize(name, parentName, !0) + }) || ""), normalizedMap = makeModuleMap(map.prefix + "!" + name, this.map.parentMap, !0), on(normalizedMap, "defined", bind(this, function(value) { + this.map.normalizedMap = normalizedMap, this.init([], function() { + return value + }, null, { + enabled: !0, + ignore: !0 + }) + })), void((normalizedMod = getOwn(registry, normalizedMap.id)) && (this.depMaps.push(normalizedMap), this.events.error && normalizedMod.on("error", bind(this, function(err) { + this.emit("error", err) + })), normalizedMod.enable()))) : bundleId ? (this.map.url = context.nameToUrl(bundleId), void this.load()) : (load = bind(this, function(value) { + this.init([], function() { + return value + }, null, { + enabled: !0 + }) + }), load.error = bind(this, function(err) { + this.inited = !0, this.error = err, err.requireModules = [id], eachProp(registry, function(mod) { + 0 === mod.map.id.indexOf(id + "_unnormalized") && cleanRegistry(mod.map.id) + }), onError(err) + }), load.fromText = bind(this, function(text, textAlt) { + var moduleName = map.name, + moduleMap = makeModuleMap(moduleName), + hasInteractive = useInteractive; + textAlt && (text = textAlt), hasInteractive && (useInteractive = !1), getModule(moduleMap), hasProp(config.config, id) && (config.config[moduleName] = config.config[id]); + try { + req.exec(text) + } catch (e) { + return onError(makeError("fromtexteval", "fromText eval for " + id + " failed: " + e, e, [id])) + } + hasInteractive && (useInteractive = !0), this.depMaps.push(moduleMap), context.completeLoad(moduleName), localRequire([moduleName], load) + }), void plugin.load(map.name, localRequire, load, config)) + })), context.enable(pluginMap, this), this.pluginMaps[pluginMap.id] = pluginMap + }, + enable: function() { + enabledRegistry[this.map.id] = this, this.enabled = !0, this.enabling = !0, each(this.depMaps, bind(this, function(depMap, i) { + var id, mod, handler; + if ("string" == typeof depMap) { + if (depMap = makeModuleMap(depMap, this.map.isDefine ? this.map : this.map.parentMap, !1, !this.skipMap), this.depMaps[i] = depMap, handler = getOwn(handlers, depMap.id)) return void(this.depExports[i] = handler(this)); + this.depCount += 1, on(depMap, "defined", bind(this, function(depExports) { + this.undefed || (this.defineDep(i, depExports), this.check()) + })), this.errback ? on(depMap, "error", bind(this, this.errback)) : this.events.error && on(depMap, "error", bind(this, function(err) { + this.emit("error", err) + })) + } + id = depMap.id, mod = registry[id], hasProp(handlers, id) || !mod || mod.enabled || context.enable(depMap, this) + })), eachProp(this.pluginMaps, bind(this, function(pluginMap) { + var mod = getOwn(registry, pluginMap.id); + mod && !mod.enabled && context.enable(pluginMap, this) + })), this.enabling = !1, this.check() + }, + on: function(name, cb) { + var cbs = this.events[name]; + cbs || (cbs = this.events[name] = []), cbs.push(cb) + }, + emit: function(name, evt) { + each(this.events[name], function(cb) { + cb(evt) + }), "error" === name && delete this.events[name] + } + }, context = { + config: config, + contextName: contextName, + registry: registry, + defined: defined, + urlFetched: urlFetched, + defQueue: defQueue, + defQueueMap: {}, + Module: Module, + makeModuleMap: makeModuleMap, + nextTick: req.nextTick, + onError: onError, + configure: function(cfg) { + if (cfg.baseUrl && "/" !== cfg.baseUrl.charAt(cfg.baseUrl.length - 1) && (cfg.baseUrl += "/"), "string" == typeof cfg.urlArgs) { + var urlArgs = cfg.urlArgs; + cfg.urlArgs = function(id, url) { + return (-1 === url.indexOf("?") ? "?" : "&") + urlArgs + } + } + var shim = config.shim, + objs = { + paths: !0, + bundles: !0, + config: !0, + map: !0 + }; + eachProp(cfg, function(value, prop) { + objs[prop] ? (config[prop] || (config[prop] = {}), mixin(config[prop], value, !0, !0)) : config[prop] = value + }), cfg.bundles && eachProp(cfg.bundles, function(value, prop) { + each(value, function(v) { + v !== prop && (bundlesMap[v] = prop) + }) + }), cfg.shim && (eachProp(cfg.shim, function(value, id) { + isArray(value) && (value = { + deps: value + }), !value.exports && !value.init || value.exportsFn || (value.exportsFn = context.makeShimExports(value)), shim[id] = value + }), config.shim = shim), cfg.packages && each(cfg.packages, function(pkgObj) { + var location, name; + pkgObj = "string" == typeof pkgObj ? { + name: pkgObj + } : pkgObj, name = pkgObj.name, location = pkgObj.location, location && (config.paths[name] = pkgObj.location), config.pkgs[name] = pkgObj.name + "/" + (pkgObj.main || "main").replace(currDirRegExp, "").replace(jsSuffixRegExp, "") + }), eachProp(registry, function(mod, id) { + mod.inited || mod.map.unnormalized || (mod.map = makeModuleMap(id, null, !0)) + }), (cfg.deps || cfg.callback) && context.require(cfg.deps || [], cfg.callback) + }, + makeShimExports: function(value) { + function fn() { + var ret; + return value.init && (ret = value.init.apply(global, arguments)), ret || value.exports && getGlobal(value.exports) + } + return fn + }, + makeRequire: function(relMap, options) { + function localRequire(deps, callback, errback) { + var id, map, requireMod; + return options.enableBuildCallback && callback && isFunction(callback) && (callback.__requireJsBuild = !0), "string" == typeof deps ? isFunction(callback) ? onError(makeError("requireargs", "Invalid require call"), errback) : relMap && hasProp(handlers, deps) ? handlers[deps](registry[relMap.id]) : req.get ? req.get(context, deps, relMap, localRequire) : (map = makeModuleMap(deps, relMap, !1, !0), id = map.id, hasProp(defined, id) ? defined[id] : onError(makeError("notloaded", 'Module name "' + id + '" has not been loaded yet for context: ' + contextName + (relMap ? "" : ". Use require([])")))) : (intakeDefines(), context.nextTick(function() { + intakeDefines(), requireMod = getModule(makeModuleMap(null, relMap)), requireMod.skipMap = options.skipMap, requireMod.init(deps, callback, errback, { + enabled: !0 + }), checkLoaded() + }), localRequire) + } + return options = options || {}, mixin(localRequire, { + isBrowser: isBrowser, + toUrl: function(moduleNamePlusExt) { + var ext, index = moduleNamePlusExt.lastIndexOf("."), + segment = moduleNamePlusExt.split("/")[0], + isRelative = "." === segment || ".." === segment; + return -1 !== index && (!isRelative || index > 1) && (ext = moduleNamePlusExt.substring(index, moduleNamePlusExt.length), moduleNamePlusExt = moduleNamePlusExt.substring(0, index)), context.nameToUrl(normalize(moduleNamePlusExt, relMap && relMap.id, !0), ext, !0) + }, + defined: function(id) { + return hasProp(defined, makeModuleMap(id, relMap, !1, !0).id) + }, + specified: function(id) { + return id = makeModuleMap(id, relMap, !1, !0).id, hasProp(defined, id) || hasProp(registry, id) + } + }), relMap || (localRequire.undef = function(id) { + takeGlobalQueue(); + var map = makeModuleMap(id, relMap, !0), + mod = getOwn(registry, id); + mod.undefed = !0, removeScript(id), delete defined[id], delete urlFetched[map.url], delete undefEvents[id], eachReverse(defQueue, function(args, i) { + args[0] === id && defQueue.splice(i, 1) + }), delete context.defQueueMap[id], mod && (mod.events.defined && (undefEvents[id] = mod.events), cleanRegistry(id)) + }), localRequire + }, + enable: function(depMap) { + getOwn(registry, depMap.id) && getModule(depMap).enable() + }, + completeLoad: function(moduleName) { + var found, args, mod, shim = getOwn(config.shim, moduleName) || {}, + shExports = shim.exports; + for (takeGlobalQueue(); defQueue.length;) { + if (args = defQueue.shift(), null === args[0]) { + if (args[0] = moduleName, found) break; + found = !0 + } else args[0] === moduleName && (found = !0); + callGetModule(args) + } + if (context.defQueueMap = {}, mod = getOwn(registry, moduleName), !found && !hasProp(defined, moduleName) && mod && !mod.inited) { + if (!(!config.enforceDefine || shExports && getGlobal(shExports))) return hasPathFallback(moduleName) ? void 0 : onError(makeError("nodefine", "No define call for " + moduleName, null, [moduleName])); + callGetModule([moduleName, shim.deps || [], shim.exportsFn]) + } + checkLoaded() + }, + nameToUrl: function(moduleName, ext, skipExt) { + var paths, syms, i, parentModule, url, parentPath, bundleId, pkgMain = getOwn(config.pkgs, moduleName); + if (pkgMain && (moduleName = pkgMain), bundleId = getOwn(bundlesMap, moduleName)) return context.nameToUrl(bundleId, ext, skipExt); + if (req.jsExtRegExp.test(moduleName)) url = moduleName + (ext || ""); + else { + for (paths = config.paths, syms = moduleName.split("/"), i = syms.length; i > 0; i -= 1) + if (parentModule = syms.slice(0, i).join("/"), parentPath = getOwn(paths, parentModule)) { + isArray(parentPath) && (parentPath = parentPath[0]), syms.splice(0, i, parentPath); + break + } url = syms.join("/"), url += ext || (/^data\:|^blob\:|\?/.test(url) || skipExt ? "" : ".js"), url = ("/" === url.charAt(0) || url.match(/^[\w\+\.\-]+:/) ? "" : config.baseUrl) + url + } + return config.urlArgs && !/^blob\:/.test(url) ? url + config.urlArgs(moduleName, url) : url + }, + load: function(id, url) { + req.load(context, id, url) + }, + execCb: function(name, callback, args, exports) { + return callback.apply(exports, args) + }, + onScriptLoad: function(evt) { + if ("load" === evt.type || readyRegExp.test((evt.currentTarget || evt.srcElement).readyState)) { + interactiveScript = null; + var data = getScriptData(evt); + context.completeLoad(data.id) + } + }, + onScriptError: function(evt) { + var data = getScriptData(evt); + if (!hasPathFallback(data.id)) { + var parents = []; + return eachProp(registry, function(value, key) { + 0 !== key.indexOf("_@r") && each(value.depMaps, function(depMap) { + if (depMap.id === data.id) return parents.push(key), !0 + }) + }), onError(makeError("scripterror", 'Script error for "' + data.id + (parents.length ? '", needed by: ' + parents.join(", ") : '"'), evt, [data.id])) + } + } + }, context.require = context.makeRequire(), context + } + + function getInteractiveScript() { + return interactiveScript && "interactive" === interactiveScript.readyState ? interactiveScript : (eachReverse(scripts(), function(script) { + if ("interactive" === script.readyState) return interactiveScript = script + }), interactiveScript) + } + var req, s, head, baseElement, dataMain, src, interactiveScript, currentlyAddingScript, mainScript, subPath, version = "2.3.5", + commentRegExp = /\/\*[\s\S]*?\*\/|([^:"'=]|^)\/\/.*$/gm, + cjsRequireRegExp = /[^.]\s*require\s*\(\s*["']([^'"\s]+)["']\s*\)/g, + jsSuffixRegExp = /\.js$/, + currDirRegExp = /^\.\//, + op = Object.prototype, + ostring = op.toString, + hasOwn = op.hasOwnProperty, + isBrowser = !("undefined" == typeof window || "undefined" == typeof navigator || !window.document), + isWebWorker = !isBrowser && "undefined" != typeof importScripts, + readyRegExp = isBrowser && "PLAYSTATION 3" === navigator.platform ? /^complete$/ : /^(complete|loaded)$/, + defContextName = "_", + isOpera = "undefined" != typeof opera && "[object Opera]" === opera.toString(), + contexts = {}, + cfg = {}, + globalDefQueue = [], + useInteractive = !1; + if (void 0 === define) { + if (void 0 !== requirejs) { + if (isFunction(requirejs)) return; + cfg = requirejs, requirejs = void 0 + } + void 0 === require || isFunction(require) || (cfg = require, require = void 0), req = requirejs = function(deps, callback, errback, optional) { + var context, config, contextName = defContextName; + return isArray(deps) || "string" == typeof deps || (config = deps, isArray(callback) ? (deps = callback, callback = errback, errback = optional) : deps = []), config && config.context && (contextName = config.context), context = getOwn(contexts, contextName), context || (context = contexts[contextName] = req.s.newContext(contextName)), config && context.configure(config), context.require(deps, callback, errback) + }, req.config = function(config) { + return req(config) + }, req.nextTick = void 0 !== setTimeout ? function(fn) { + setTimeout(fn, 4) + } : function(fn) { + fn() + }, require || (require = req), req.version = version, req.jsExtRegExp = /^\/|:|\?|\.js$/, req.isBrowser = isBrowser, s = req.s = { + contexts: contexts, + newContext: newContext + }, req({}), each(["toUrl", "undef", "defined", "specified"], function(prop) { + req[prop] = function() { + var ctx = contexts[defContextName]; + return ctx.require[prop].apply(ctx, arguments) + } + }), isBrowser && (head = s.head = document.getElementsByTagName("head")[0], (baseElement = document.getElementsByTagName("base")[0]) && (head = s.head = baseElement.parentNode)), req.onError = defaultOnError, req.createNode = function(config, moduleName, url) { + var node = config.xhtml ? document.createElementNS("http://www.w3.org/1999/xhtml", "html:script") : document.createElement("script"); + return node.type = config.scriptType || "text/javascript", node.charset = "utf-8", node.async = !0, node + }, req.load = function(context, moduleName, url) { + var node, config = context && context.config || {}; + if (isBrowser) return node = req.createNode(config, moduleName, url), node.setAttribute("data-requirecontext", context.contextName), node.setAttribute("data-requiremodule", moduleName), !node.attachEvent || node.attachEvent.toString && node.attachEvent.toString().indexOf("[native code") < 0 || isOpera ? (node.addEventListener("load", context.onScriptLoad, !1), node.addEventListener("error", context.onScriptError, !1)) : (useInteractive = !0, node.attachEvent("onreadystatechange", context.onScriptLoad)), node.src = url, config.onNodeCreated && config.onNodeCreated(node, config, moduleName, url), currentlyAddingScript = node, baseElement ? head.insertBefore(node, baseElement) : head.appendChild(node), currentlyAddingScript = null, node; + if (isWebWorker) try { + setTimeout(function() {}, 0), importScripts(url), context.completeLoad(moduleName) + } catch (e) { + context.onError(makeError("importscripts", "importScripts failed for " + moduleName + " at " + url, e, [moduleName])) + } + }, isBrowser && !cfg.skipDataMain && eachReverse(scripts(), function(script) { + if (head || (head = script.parentNode), dataMain = script.getAttribute("data-main")) return mainScript = dataMain, cfg.baseUrl || -1 !== mainScript.indexOf("!") || (src = mainScript.split("/"), mainScript = src.pop(), subPath = src.length ? src.join("/") + "/" : "./", cfg.baseUrl = subPath), mainScript = mainScript.replace(jsSuffixRegExp, ""), req.jsExtRegExp.test(mainScript) && (mainScript = dataMain), cfg.deps = cfg.deps ? cfg.deps.concat(mainScript) : [mainScript], !0 + }), define = function(name, deps, callback) { + var node, context; + "string" != typeof name && (callback = deps, deps = name, name = null), isArray(deps) || (callback = deps, deps = null), !deps && isFunction(callback) && (deps = [], callback.length && (callback.toString().replace(commentRegExp, commentReplace).replace(cjsRequireRegExp, function(match, dep) { + deps.push(dep) + }), deps = (1 === callback.length ? ["require"] : ["require", "exports", "module"]).concat(deps))), useInteractive && (node = currentlyAddingScript || getInteractiveScript()) && (name || (name = node.getAttribute("data-requiremodule")), context = contexts[node.getAttribute("data-requirecontext")]), context ? (context.defQueue.push([name, deps, callback]), context.defQueueMap[name] = !0) : globalDefQueue.push([name, deps, callback]) + }, define.amd = { + jQuery: !0 + }, req.exec = function(text) { + return eval(text) + }, req(cfg) + } +}(this, "undefined" == typeof setTimeout ? void 0 : setTimeout); \ No newline at end of file diff --git a/dashboard-ui/bower_components/webcomponentsjs/webcomponents-lite.min.js b/dashboard-ui/bower_components/webcomponentsjs/webcomponents-lite.min.js index fb9d01025f..163ef436fc 100644 --- a/dashboard-ui/bower_components/webcomponentsjs/webcomponents-lite.min.js +++ b/dashboard-ui/bower_components/webcomponentsjs/webcomponents-lite.min.js @@ -8,5 +8,1564 @@ * subject to an additional IP rights grant found at http://polymer.github.io/PATENTS.txt */ // @version 0.7.24 -!function(){window.WebComponents=window.WebComponents||{flags:{}};var e="webcomponents-lite.js",t=document.querySelector('script[src*="'+e+'"]'),n={};if(!n.noOpts){if(location.search.slice(1).split("&").forEach(function(e){var t,o=e.split("=");o[0]&&(t=o[0].match(/wc-(.+)/))&&(n[t[1]]=o[1]||!0)}),t)for(var o,r=0;o=t.attributes[r];r++)"src"!==o.name&&(n[o.name]=o.value||!0);if(n.log&&n.log.split){var i=n.log.split(",");n.log={},i.forEach(function(e){n.log[e]=!0})}else n.log={}}n.register&&(window.CustomElements=window.CustomElements||{flags:{}},window.CustomElements.flags.register=n.register),WebComponents.flags=n}(),function(e){"use strict";function t(e){return void 0!==h[e]}function n(){s.call(this),this._isInvalid=!0}function o(e){return""==e&&n.call(this),e.toLowerCase()}function r(e){var t=e.charCodeAt(0);return t>32&&t<127&&[34,35,60,62,63,96].indexOf(t)==-1?e:encodeURIComponent(e)}function i(e){var t=e.charCodeAt(0);return t>32&&t<127&&[34,35,60,62,96].indexOf(t)==-1?e:encodeURIComponent(e)}function a(e,a,s){function c(e){g.push(e)}var d=a||"scheme start",l=0,u="",w=!1,_=!1,g=[];e:for(;(e[l-1]!=p||0==l)&&!this._isInvalid;){var b=e[l];switch(d){case"scheme start":if(!b||!m.test(b)){if(a){c("Invalid scheme.");break e}u="",d="no scheme";continue}u+=b.toLowerCase(),d="scheme";break;case"scheme":if(b&&v.test(b))u+=b.toLowerCase();else{if(":"!=b){if(a){if(p==b)break e;c("Code point not allowed in scheme: "+b);break e}u="",l=0,d="no scheme";continue}if(this._scheme=u,u="",a)break e;t(this._scheme)&&(this._isRelative=!0),d="file"==this._scheme?"relative":this._isRelative&&s&&s._scheme==this._scheme?"relative or authority":this._isRelative?"authority first slash":"scheme data"}break;case"scheme data":"?"==b?(this._query="?",d="query"):"#"==b?(this._fragment="#",d="fragment"):p!=b&&"\t"!=b&&"\n"!=b&&"\r"!=b&&(this._schemeData+=r(b));break;case"no scheme":if(s&&t(s._scheme)){d="relative";continue}c("Missing scheme."),n.call(this);break;case"relative or authority":if("/"!=b||"/"!=e[l+1]){c("Expected /, got: "+b),d="relative";continue}d="authority ignore slashes";break;case"relative":if(this._isRelative=!0,"file"!=this._scheme&&(this._scheme=s._scheme),p==b){this._host=s._host,this._port=s._port,this._path=s._path.slice(),this._query=s._query,this._username=s._username,this._password=s._password;break e}if("/"==b||"\\"==b)"\\"==b&&c("\\ is an invalid code point."),d="relative slash";else if("?"==b)this._host=s._host,this._port=s._port,this._path=s._path.slice(),this._query="?",this._username=s._username,this._password=s._password,d="query";else{if("#"!=b){var y=e[l+1],E=e[l+2];("file"!=this._scheme||!m.test(b)||":"!=y&&"|"!=y||p!=E&&"/"!=E&&"\\"!=E&&"?"!=E&&"#"!=E)&&(this._host=s._host,this._port=s._port,this._username=s._username,this._password=s._password,this._path=s._path.slice(),this._path.pop()),d="relative path";continue}this._host=s._host,this._port=s._port,this._path=s._path.slice(),this._query=s._query,this._fragment="#",this._username=s._username,this._password=s._password,d="fragment"}break;case"relative slash":if("/"!=b&&"\\"!=b){"file"!=this._scheme&&(this._host=s._host,this._port=s._port,this._username=s._username,this._password=s._password),d="relative path";continue}"\\"==b&&c("\\ is an invalid code point."),d="file"==this._scheme?"file host":"authority ignore slashes";break;case"authority first slash":if("/"!=b){c("Expected '/', got: "+b),d="authority ignore slashes";continue}d="authority second slash";break;case"authority second slash":if(d="authority ignore slashes","/"!=b){c("Expected '/', got: "+b);continue}break;case"authority ignore slashes":if("/"!=b&&"\\"!=b){d="authority";continue}c("Expected authority, got: "+b);break;case"authority":if("@"==b){w&&(c("@ already seen."),u+="%40"),w=!0;for(var L=0;L>>0)+(t++ +"__")};n.prototype={set:function(t,n){var o=t[this.name];return o&&o[0]===t?o[1]=n:e(t,this.name,{value:[t,n],writable:!0}),this},get:function(e){var t;return(t=e[this.name])&&t[0]===e?t[1]:void 0},"delete":function(e){var t=e[this.name];return!(!t||t[0]!==e)&&(t[0]=t[1]=void 0,!0)},has:function(e){var t=e[this.name];return!!t&&t[0]===e}},window.WeakMap=n}(),function(e){function t(e){b.push(e),g||(g=!0,m(o))}function n(e){return window.ShadowDOMPolyfill&&window.ShadowDOMPolyfill.wrapIfNeeded(e)||e}function o(){g=!1;var e=b;b=[],e.sort(function(e,t){return e.uid_-t.uid_});var t=!1;e.forEach(function(e){var n=e.takeRecords();r(e),n.length&&(e.callback_(n,e),t=!0)}),t&&o()}function r(e){e.nodes_.forEach(function(t){var n=v.get(t);n&&n.forEach(function(t){t.observer===e&&t.removeTransientObservers()})})}function i(e,t){for(var n=e;n;n=n.parentNode){var o=v.get(n);if(o)for(var r=0;r0){var r=n[o-1],i=f(r,e);if(i)return void(n[o-1]=i)}else t(this.observer);n[o]=e},addListeners:function(){this.addListeners_(this.target)},addListeners_:function(e){var t=this.options;t.attributes&&e.addEventListener("DOMAttrModified",this,!0),t.characterData&&e.addEventListener("DOMCharacterDataModified",this,!0),t.childList&&e.addEventListener("DOMNodeInserted",this,!0),(t.childList||t.subtree)&&e.addEventListener("DOMNodeRemoved",this,!0)},removeListeners:function(){this.removeListeners_(this.target)},removeListeners_:function(e){var t=this.options;t.attributes&&e.removeEventListener("DOMAttrModified",this,!0),t.characterData&&e.removeEventListener("DOMCharacterDataModified",this,!0),t.childList&&e.removeEventListener("DOMNodeInserted",this,!0),(t.childList||t.subtree)&&e.removeEventListener("DOMNodeRemoved",this,!0)},addTransientObserver:function(e){if(e!==this.target){this.addListeners_(e),this.transientObservedNodes.push(e);var t=v.get(e);t||v.set(e,t=[]),t.push(this)}},removeTransientObservers:function(){var e=this.transientObservedNodes;this.transientObservedNodes=[],e.forEach(function(e){this.removeListeners_(e);for(var t=v.get(e),n=0;n":return">";case" ":return" "}}function t(t){return t.replace(u,e)}var n="undefined"==typeof HTMLTemplateElement;/Trident/.test(navigator.userAgent)&&!function(){var e=document.importNode;document.importNode=function(){var t=e.apply(document,arguments);if(t.nodeType===Node.DOCUMENT_FRAGMENT_NODE){var n=document.createDocumentFragment();return n.appendChild(t),n}return t}}();var o=function(){if(!n){var e=document.createElement("template"),t=document.createElement("template");t.content.appendChild(document.createElement("div")),e.content.appendChild(t);var o=e.cloneNode(!0);return 0===o.content.childNodes.length||0===o.content.firstChild.content.childNodes.length}}(),r="template",i=function(){};if(n){var a=document.implementation.createHTMLDocument("template"),s=!0,c=document.createElement("style");c.textContent=r+"{display:none;}";var d=document.head;d.insertBefore(c,d.firstElementChild),i.prototype=Object.create(HTMLElement.prototype),i.decorate=function(e){if(!e.content){e.content=a.createDocumentFragment();for(var n;n=e.firstChild;)e.content.appendChild(n);if(e.cloneNode=function(e){return i.cloneNode(this,e)},s)try{Object.defineProperty(e,"innerHTML",{get:function(){for(var e="",n=this.content.firstChild;n;n=n.nextSibling)e+=n.outerHTML||t(n.data);return e},set:function(e){for(a.body.innerHTML=e,i.bootstrap(a);this.content.firstChild;)this.content.removeChild(this.content.firstChild);for(;a.body.firstChild;)this.content.appendChild(a.body.firstChild)},configurable:!0})}catch(o){s=!1}i.bootstrap(e.content)}},i.bootstrap=function(e){for(var t,n=e.querySelectorAll(r),o=0,a=n.length;o]/g}if(n||o){var h=Node.prototype.cloneNode;i.cloneNode=function(e,t){var n=h.call(e,!1);return this.decorate&&this.decorate(n),t&&(n.content.appendChild(h.call(e.content,!0)),this.fixClonedDom(n.content,e.content)),n},i.fixClonedDom=function(e,t){if(t.querySelectorAll)for(var n,o,i=t.querySelectorAll(r),a=e.querySelectorAll(r),s=0,c=a.length;s=200&&e.status<300||304===e.status||0===e.status},load:function(n,o,r){var i=new XMLHttpRequest;return(e.flags.debug||e.flags.bust)&&(n+="?"+Math.random()),i.open("GET",n,t.async),i.addEventListener("readystatechange",function(e){if(4===i.readyState){var n=null;try{var a=i.getResponseHeader("Location");a&&(n="/"===a.substr(0,1)?location.origin+a:a)}catch(e){console.error(e.message)}o.call(r,!t.ok(i)&&i,i.response||i.responseText,n)}}),i.send(),i},loadDocument:function(e,t,n){this.load(e,t,n).responseType="document"}};e.xhr=t}),window.HTMLImports.addModule(function(e){var t=e.xhr,n=e.flags,o=function(e,t){this.cache={},this.onload=e,this.oncomplete=t,this.inflight=0,this.pending={}};o.prototype={addNodes:function(e){this.inflight+=e.length;for(var t,n=0,o=e.length;n-1?atob(a):decodeURIComponent(a),setTimeout(function(){this.receive(e,o,null,a)}.bind(this),0)}else{var s=function(t,n,r){this.receive(e,o,t,n,r)}.bind(this);t.load(e,s)}else setTimeout(function(){this.receive(e,o,{error:"href must be specified"},null)}.bind(this),0)},receive:function(e,t,n,o,r){this.cache[e]=o;for(var i,a=this.pending[e],s=0,c=a.length;s=0&&this.dynamicElements.splice(t,1)},parseImport:function(e){if(e["import"]=e.__doc,window.HTMLImports.__importsParsingHook&&window.HTMLImports.__importsParsingHook(e),e["import"]&&(e["import"].__importParsed=!0),this.markParsingComplete(e),e.__resource&&!e.__error?e.dispatchEvent(new CustomEvent("load",{bubbles:!1})):e.dispatchEvent(new CustomEvent("error",{bubbles:!1})),e.__pending)for(var t;e.__pending.length;)t=e.__pending.shift(),t&&t({target:e});this.parseNext()},parseLink:function(e){t(e)?this.parseImport(e):(e.href=e.href,this.parseGeneric(e))},parseStyle:function(e){var t=e;e=i(e),t.__appliedElement=e,e.__importElement=t,this.parseGeneric(e)},parseGeneric:function(e){this.trackElement(e),this.addElementToDocument(e)},rootImportForElement:function(e){for(var t=e;t.ownerDocument.__importLink;)t=t.ownerDocument.__importLink;return t},addElementToDocument:function(e){var t=this.rootImportForElement(e.__importElement||e);t.parentNode.insertBefore(e,t)},trackElement:function(e,t){var n=this,o=function(r){e.removeEventListener("load",o),e.removeEventListener("error",o),t&&t(r),n.markParsingComplete(e),n.parseNext()};if(e.addEventListener("load",o),e.addEventListener("error",o),d&&"style"===e.localName){var r=!1;if(e.textContent.indexOf("@import")==-1)r=!0;else if(e.sheet){r=!0;for(var i,a=e.sheet.cssRules,s=a?a.length:0,c=0;c=0},hasResource:function(e){return!t(e)||void 0!==e.__doc}};e.parser=h,e.IMPORT_SELECTOR=u}),window.HTMLImports.addModule(function(e){function t(e){return n(e,a)}function n(e,t){return"link"===e.localName&&e.getAttribute("rel")===t}function o(e){return!!Object.getOwnPropertyDescriptor(e,"baseURI")}function r(e,t){var n=document.implementation.createHTMLDocument(a);n._URL=t;var r=n.createElement("base");r.setAttribute("href",t),n.baseURI||o(n)||Object.defineProperty(n,"baseURI",{value:t});var i=n.createElement("meta");return i.setAttribute("charset","utf-8"),n.head.appendChild(i),n.head.appendChild(r),n.body.innerHTML=e,window.HTMLTemplateElement&&HTMLTemplateElement.bootstrap&&HTMLTemplateElement.bootstrap(n),n}var i=e.flags,a=e.IMPORT_LINK_TYPE,s=e.IMPORT_SELECTOR,c=e.rootDocument,d=e.Loader,l=e.Observer,u=e.parser,h={documents:{},documentPreloadSelectors:s,importsPreloadSelectors:[s].join(","),loadNode:function(e){f.addNode(e)},loadSubtree:function(e){var t=this.marshalNodes(e);f.addNodes(t)},marshalNodes:function(e){return e.querySelectorAll(this.loadSelectorsForNode(e))},loadSelectorsForNode:function(e){var t=e.ownerDocument||e;return t===c?this.documentPreloadSelectors:this.importsPreloadSelectors},loaded:function(e,n,o,a,s){if(i.load&&console.log("loaded",e,n),n.__resource=o,n.__error=a,t(n)){var c=this.documents[e];void 0===c&&(c=a?null:r(o,s||e),c&&(c.__importLink=n,this.bootDocument(c)),this.documents[e]=c),n.__doc=c}u.parseNext()},bootDocument:function(e){this.loadSubtree(e),this.observer.observe(e),u.parseNext()},loadedAll:function(){u.parseNext()}},f=new d(h.loaded.bind(h),h.loadedAll.bind(h));if(h.observer=new l,!document.baseURI){var p={get:function(){var e=document.querySelector("base");return e?e.href:window.location.href},configurable:!0};Object.defineProperty(document,"baseURI",p),Object.defineProperty(c,"baseURI",p)}e.importer=h,e.importLoader=f}),window.HTMLImports.addModule(function(e){var t=e.parser,n=e.importer,o={added:function(e){for(var o,r,i,a,s=0,c=e.length;s=0)){n.push(e);for(var o,r=e.querySelectorAll("link[rel="+a+"]"),s=0,c=r.length;s=0&&g(o,HTMLElement),o)}function p(e,t){var n=e[t];e[t]=function(){var e=n.apply(this,arguments);return w(e),e}}var m,v=(e.isIE,e.upgradeDocumentTree),w=e.upgradeAll,_=e.upgradeWithDefinition,g=e.implementPrototype,b=e.useNative,y=["annotation-xml","color-profile","font-face","font-face-src","font-face-uri","font-face-format","font-face-name","missing-glyph"],E={},L="http://www.w3.org/1999/xhtml",N=document.createElement.bind(document),M=document.createElementNS.bind(document);m=Object.__proto__||b?function(e,t){return e instanceof t}:function(e,t){if(e instanceof t)return!0;for(var n=e;n;){if(n===t.prototype)return!0;n=n.__proto__}return!1},p(Node.prototype,"cloneNode"),p(document,"importNode"),document.registerElement=t,document.createElement=f,document.createElementNS=h,e.registry=E,e["instanceof"]=m,e.reservedTagList=y,e.getRegisteredDefinition=d,document.register=document.registerElement}),function(e){function t(){i(window.wrap(document)),window.CustomElements.ready=!0;var e=window.requestAnimationFrame||function(e){setTimeout(e,16)};e(function(){setTimeout(function(){window.CustomElements.readyTime=Date.now(),window.HTMLImports&&(window.CustomElements.elapsed=window.CustomElements.readyTime-window.HTMLImports.readyTime),document.dispatchEvent(new CustomEvent("WebComponentsReady",{bubbles:!0}))})})}var n=e.useNative,o=e.initializeModules;e.isIE;if(n){var r=function(){};e.watchShadow=r,e.upgrade=r,e.upgradeAll=r,e.upgradeDocumentTree=r,e.upgradeSubtree=r,e.takeRecords=r,e["instanceof"]=function(e,t){return e instanceof t}}else o();var i=e.upgradeDocumentTree,a=e.upgradeDocument;if(window.wrap||(window.ShadowDOMPolyfill?(window.wrap=window.ShadowDOMPolyfill.wrapIfNeeded,window.unwrap=window.ShadowDOMPolyfill.unwrapIfNeeded):window.wrap=window.unwrap=function(e){return e}),window.HTMLImports&&(window.HTMLImports.__importsParsingHook=function(e){e["import"]&&a(wrap(e["import"]))}),"complete"===document.readyState||e.flags.eager)t();else if("interactive"!==document.readyState||window.attachEvent||window.HTMLImports&&!window.HTMLImports.ready){var s=window.HTMLImports&&!window.HTMLImports.ready?"HTMLImportsLoaded":"DOMContentLoaded";window.addEventListener(s,t)}else t()}(window.CustomElements),function(e){var t=document.createElement("style");t.textContent="body {transition: opacity ease-in 0.2s; } \nbody[unresolved] {opacity: 0; display: block; overflow: hidden; position: relative; } \n";var n=document.querySelector("head");n.insertBefore(t,n.firstChild)}(window.WebComponents); \ No newline at end of file +! function() { + window.WebComponents = window.WebComponents || { + flags: {} + }; + var e = "webcomponents-lite.js", + t = document.querySelector('script[src*="' + e + '"]'), + n = {}; + if (!n.noOpts) { + if (location.search.slice(1).split("&").forEach(function(e) { + var t, o = e.split("="); + o[0] && (t = o[0].match(/wc-(.+)/)) && (n[t[1]] = o[1] || !0) + }), t) + for (var o, r = 0; o = t.attributes[r]; r++) "src" !== o.name && (n[o.name] = o.value || !0); + if (n.log && n.log.split) { + var i = n.log.split(","); + n.log = {}, i.forEach(function(e) { + n.log[e] = !0 + }) + } else n.log = {} + } + n.register && (window.CustomElements = window.CustomElements || { + flags: {} + }, window.CustomElements.flags.register = n.register), WebComponents.flags = n +}(), +function(e) { + "use strict"; + + function t(e) { + return void 0 !== h[e] + } + + function n() { + s.call(this), this._isInvalid = !0 + } + + function o(e) { + return "" == e && n.call(this), e.toLowerCase() + } + + function r(e) { + var t = e.charCodeAt(0); + return t > 32 && t < 127 && [34, 35, 60, 62, 63, 96].indexOf(t) == -1 ? e : encodeURIComponent(e) + } + + function i(e) { + var t = e.charCodeAt(0); + return t > 32 && t < 127 && [34, 35, 60, 62, 96].indexOf(t) == -1 ? e : encodeURIComponent(e) + } + + function a(e, a, s) { + function c(e) { + g.push(e) + } + var d = a || "scheme start", + l = 0, + u = "", + w = !1, + _ = !1, + g = []; + e: for (; + (e[l - 1] != p || 0 == l) && !this._isInvalid;) { + var b = e[l]; + switch (d) { + case "scheme start": + if (!b || !m.test(b)) { + if (a) { + c("Invalid scheme."); + break e + } + u = "", d = "no scheme"; + continue + } + u += b.toLowerCase(), d = "scheme"; + break; + case "scheme": + if (b && v.test(b)) u += b.toLowerCase(); + else { + if (":" != b) { + if (a) { + if (p == b) break e; + c("Code point not allowed in scheme: " + b); + break e + } + u = "", l = 0, d = "no scheme"; + continue + } + if (this._scheme = u, u = "", a) break e; + t(this._scheme) && (this._isRelative = !0), d = "file" == this._scheme ? "relative" : this._isRelative && s && s._scheme == this._scheme ? "relative or authority" : this._isRelative ? "authority first slash" : "scheme data" + } + break; + case "scheme data": + "?" == b ? (this._query = "?", d = "query") : "#" == b ? (this._fragment = "#", d = "fragment") : p != b && "\t" != b && "\n" != b && "\r" != b && (this._schemeData += r(b)); + break; + case "no scheme": + if (s && t(s._scheme)) { + d = "relative"; + continue + } + c("Missing scheme."), n.call(this); + break; + case "relative or authority": + if ("/" != b || "/" != e[l + 1]) { + c("Expected /, got: " + b), d = "relative"; + continue + } + d = "authority ignore slashes"; + break; + case "relative": + if (this._isRelative = !0, "file" != this._scheme && (this._scheme = s._scheme), p == b) { + this._host = s._host, this._port = s._port, this._path = s._path.slice(), this._query = s._query, this._username = s._username, this._password = s._password; + break e + } + if ("/" == b || "\\" == b) "\\" == b && c("\\ is an invalid code point."), d = "relative slash"; + else if ("?" == b) this._host = s._host, this._port = s._port, this._path = s._path.slice(), this._query = "?", this._username = s._username, this._password = s._password, d = "query"; + else { + if ("#" != b) { + var y = e[l + 1], + E = e[l + 2]; + ("file" != this._scheme || !m.test(b) || ":" != y && "|" != y || p != E && "/" != E && "\\" != E && "?" != E && "#" != E) && (this._host = s._host, this._port = s._port, this._username = s._username, this._password = s._password, this._path = s._path.slice(), this._path.pop()), d = "relative path"; + continue + } + this._host = s._host, this._port = s._port, this._path = s._path.slice(), this._query = s._query, this._fragment = "#", this._username = s._username, this._password = s._password, d = "fragment" + } + break; + case "relative slash": + if ("/" != b && "\\" != b) { + "file" != this._scheme && (this._host = s._host, this._port = s._port, this._username = s._username, this._password = s._password), d = "relative path"; + continue + } + "\\" == b && c("\\ is an invalid code point."), d = "file" == this._scheme ? "file host" : "authority ignore slashes"; + break; + case "authority first slash": + if ("/" != b) { + c("Expected '/', got: " + b), d = "authority ignore slashes"; + continue + } + d = "authority second slash"; + break; + case "authority second slash": + if (d = "authority ignore slashes", "/" != b) { + c("Expected '/', got: " + b); + continue + } + break; + case "authority ignore slashes": + if ("/" != b && "\\" != b) { + d = "authority"; + continue + } + c("Expected authority, got: " + b); + break; + case "authority": + if ("@" == b) { + w && (c("@ already seen."), u += "%40"), w = !0; + for (var L = 0; L < u.length; L++) { + var N = u[L]; + if ("\t" != N && "\n" != N && "\r" != N) + if (":" != N || null !== this._password) { + var M = r(N); + null !== this._password ? this._password += M : this._username += M + } else this._password = ""; + else c("Invalid whitespace in authority.") + } + u = "" + } else { + if (p == b || "/" == b || "\\" == b || "?" == b || "#" == b) { + l -= u.length, u = "", d = "host"; + continue + } + u += b + } + break; + case "file host": + if (p == b || "/" == b || "\\" == b || "?" == b || "#" == b) { + 2 != u.length || !m.test(u[0]) || ":" != u[1] && "|" != u[1] ? 0 == u.length ? d = "relative path start" : (this._host = o.call(this, u), u = "", d = "relative path start") : d = "relative path"; + continue + } + "\t" == b || "\n" == b || "\r" == b ? c("Invalid whitespace in file host.") : u += b; + break; + case "host": + case "hostname": + if (":" != b || _) { + if (p == b || "/" == b || "\\" == b || "?" == b || "#" == b) { + if (this._host = o.call(this, u), u = "", d = "relative path start", a) break e; + continue + } + "\t" != b && "\n" != b && "\r" != b ? ("[" == b ? _ = !0 : "]" == b && (_ = !1), u += b) : c("Invalid code point in host/hostname: " + b) + } else if (this._host = o.call(this, u), u = "", d = "port", "hostname" == a) break e; + break; + case "port": + if (/[0-9]/.test(b)) u += b; + else { + if (p == b || "/" == b || "\\" == b || "?" == b || "#" == b || a) { + if ("" != u) { + var T = parseInt(u, 10); + T != h[this._scheme] && (this._port = T + ""), u = "" + } + if (a) break e; + d = "relative path start"; + continue + } + "\t" == b || "\n" == b || "\r" == b ? c("Invalid code point in port: " + b) : n.call(this) + } + break; + case "relative path start": + if ("\\" == b && c("'\\' not allowed in path."), d = "relative path", "/" != b && "\\" != b) continue; + break; + case "relative path": + if (p != b && "/" != b && "\\" != b && (a || "?" != b && "#" != b)) "\t" != b && "\n" != b && "\r" != b && (u += r(b)); + else { + "\\" == b && c("\\ not allowed in relative path."); + var O; + (O = f[u.toLowerCase()]) && (u = O), ".." == u ? (this._path.pop(), "/" != b && "\\" != b && this._path.push("")) : "." == u && "/" != b && "\\" != b ? this._path.push("") : "." != u && ("file" == this._scheme && 0 == this._path.length && 2 == u.length && m.test(u[0]) && "|" == u[1] && (u = u[0] + ":"), this._path.push(u)), u = "", "?" == b ? (this._query = "?", d = "query") : "#" == b && (this._fragment = "#", d = "fragment") + } + break; + case "query": + a || "#" != b ? p != b && "\t" != b && "\n" != b && "\r" != b && (this._query += i(b)) : (this._fragment = "#", d = "fragment"); + break; + case "fragment": + p != b && "\t" != b && "\n" != b && "\r" != b && (this._fragment += b) + } + l++ + } + } + + function s() { + this._scheme = "", this._schemeData = "", this._username = "", this._password = null, this._host = "", this._port = "", this._path = [], this._query = "", this._fragment = "", this._isInvalid = !1, this._isRelative = !1 + } + + function c(e, t) { + void 0 === t || t instanceof c || (t = new c(String(t))), this._url = e, s.call(this); + var n = e.replace(/^[ \t\r\n\f]+|[ \t\r\n\f]+$/g, ""); + a.call(this, n, null, t) + } + var d = !1; + if (!e.forceJURL) try { + var l = new URL("b", "http://a"); + l.pathname = "c%20d", d = "http://a/c%20d" === l.href + } catch (u) {} + if (!d) { + var h = Object.create(null); + h.ftp = 21, h.file = 0, h.gopher = 70, h.http = 80, h.https = 443, h.ws = 80, h.wss = 443; + var f = Object.create(null); + f["%2e"] = ".", f[".%2e"] = "..", f["%2e."] = "..", f["%2e%2e"] = ".."; + var p = void 0, + m = /[a-zA-Z]/, + v = /[a-zA-Z0-9\+\-\.]/; + c.prototype = { + toString: function() { + return this.href + }, + get href() { + if (this._isInvalid) return this._url; + var e = ""; + return "" == this._username && null == this._password || (e = this._username + (null != this._password ? ":" + this._password : "") + "@"), this.protocol + (this._isRelative ? "//" + e + this.host : "") + this.pathname + this._query + this._fragment + }, + set href(e) { + s.call(this), a.call(this, e) + }, + get protocol() { + return this._scheme + ":" + }, + set protocol(e) { + this._isInvalid || a.call(this, e + ":", "scheme start") + }, + get host() { + return this._isInvalid ? "" : this._port ? this._host + ":" + this._port : this._host + }, + set host(e) { + !this._isInvalid && this._isRelative && a.call(this, e, "host") + }, + get hostname() { + return this._host + }, + set hostname(e) { + !this._isInvalid && this._isRelative && a.call(this, e, "hostname") + }, + get port() { + return this._port + }, + set port(e) { + !this._isInvalid && this._isRelative && a.call(this, e, "port") + }, + get pathname() { + return this._isInvalid ? "" : this._isRelative ? "/" + this._path.join("/") : this._schemeData + }, + set pathname(e) { + !this._isInvalid && this._isRelative && (this._path = [], a.call(this, e, "relative path start")) + }, + get search() { + return this._isInvalid || !this._query || "?" == this._query ? "" : this._query + }, + set search(e) { + !this._isInvalid && this._isRelative && (this._query = "?", "?" == e[0] && (e = e.slice(1)), a.call(this, e, "query")) + }, + get hash() { + return this._isInvalid || !this._fragment || "#" == this._fragment ? "" : this._fragment + }, + set hash(e) { + this._isInvalid || (this._fragment = "#", "#" == e[0] && (e = e.slice(1)), a.call(this, e, "fragment")) + }, + get origin() { + var e; + if (this._isInvalid || !this._scheme) return ""; + switch (this._scheme) { + case "data": + case "file": + case "javascript": + case "mailto": + return "null" + } + return e = this.host, e ? this._scheme + "://" + e : "" + } + }; + var w = e.URL; + w && (c.createObjectURL = function(e) { + return w.createObjectURL.apply(w, arguments) + }, c.revokeObjectURL = function(e) { + w.revokeObjectURL(e) + }), e.URL = c + } +}(self), "undefined" == typeof WeakMap && ! function() { + var e = Object.defineProperty, + t = Date.now() % 1e9, + n = function() { + this.name = "__st" + (1e9 * Math.random() >>> 0) + (t++ + "__") + }; + n.prototype = { + set: function(t, n) { + var o = t[this.name]; + return o && o[0] === t ? o[1] = n : e(t, this.name, { + value: [t, n], + writable: !0 + }), this + }, + get: function(e) { + var t; + return (t = e[this.name]) && t[0] === e ? t[1] : void 0 + }, + "delete": function(e) { + var t = e[this.name]; + return !(!t || t[0] !== e) && (t[0] = t[1] = void 0, !0) + }, + has: function(e) { + var t = e[this.name]; + return !!t && t[0] === e + } + }, window.WeakMap = n + }(), + function(e) { + function t(e) { + b.push(e), g || (g = !0, m(o)) + } + + function n(e) { + return window.ShadowDOMPolyfill && window.ShadowDOMPolyfill.wrapIfNeeded(e) || e + } + + function o() { + g = !1; + var e = b; + b = [], e.sort(function(e, t) { + return e.uid_ - t.uid_ + }); + var t = !1; + e.forEach(function(e) { + var n = e.takeRecords(); + r(e), n.length && (e.callback_(n, e), t = !0) + }), t && o() + } + + function r(e) { + e.nodes_.forEach(function(t) { + var n = v.get(t); + n && n.forEach(function(t) { + t.observer === e && t.removeTransientObservers() + }) + }) + } + + function i(e, t) { + for (var n = e; n; n = n.parentNode) { + var o = v.get(n); + if (o) + for (var r = 0; r < o.length; r++) { + var i = o[r], + a = i.options; + if (n === e || a.subtree) { + var s = t(a); + s && i.enqueue(s) + } + } + } + } + + function a(e) { + this.callback_ = e, this.nodes_ = [], this.records_ = [], this.uid_ = ++y + } + + function s(e, t) { + this.type = e, this.target = t, this.addedNodes = [], this.removedNodes = [], this.previousSibling = null, this.nextSibling = null, this.attributeName = null, this.attributeNamespace = null, this.oldValue = null + } + + function c(e) { + var t = new s(e.type, e.target); + return t.addedNodes = e.addedNodes.slice(), t.removedNodes = e.removedNodes.slice(), t.previousSibling = e.previousSibling, t.nextSibling = e.nextSibling, t.attributeName = e.attributeName, t.attributeNamespace = e.attributeNamespace, t.oldValue = e.oldValue, t + } + + function d(e, t) { + return E = new s(e, t) + } + + function l(e) { + return L ? L : (L = c(E), L.oldValue = e, L) + } + + function u() { + E = L = void 0 + } + + function h(e) { + return e === L || e === E + } + + function f(e, t) { + return e === t ? e : L && h(e) ? L : null + } + + function p(e, t, n) { + this.observer = e, this.target = t, this.options = n, this.transientObservedNodes = [] + } + if (!e.JsMutationObserver) { + var m, v = new WeakMap; + if (/Trident|Edge/.test(navigator.userAgent)) m = setTimeout; + else if (window.setImmediate) m = window.setImmediate; + else { + var w = [], + _ = String(Math.random()); + window.addEventListener("message", function(e) { + if (e.data === _) { + var t = w; + w = [], t.forEach(function(e) { + e() + }) + } + }), m = function(e) { + w.push(e), window.postMessage(_, "*") + } + } + var g = !1, + b = [], + y = 0; + a.prototype = { + observe: function(e, t) { + if (e = n(e), !t.childList && !t.attributes && !t.characterData || t.attributeOldValue && !t.attributes || t.attributeFilter && t.attributeFilter.length && !t.attributes || t.characterDataOldValue && !t.characterData) throw new SyntaxError; + var o = v.get(e); + o || v.set(e, o = []); + for (var r, i = 0; i < o.length; i++) + if (o[i].observer === this) { + r = o[i], r.removeListeners(), r.options = t; + break + } r || (r = new p(this, e, t), o.push(r), this.nodes_.push(e)), r.addListeners() + }, + disconnect: function() { + this.nodes_.forEach(function(e) { + for (var t = v.get(e), n = 0; n < t.length; n++) { + var o = t[n]; + if (o.observer === this) { + o.removeListeners(), t.splice(n, 1); + break + } + } + }, this), this.records_ = [] + }, + takeRecords: function() { + var e = this.records_; + return this.records_ = [], e + } + }; + var E, L; + p.prototype = { + enqueue: function(e) { + var n = this.observer.records_, + o = n.length; + if (n.length > 0) { + var r = n[o - 1], + i = f(r, e); + if (i) return void(n[o - 1] = i) + } else t(this.observer); + n[o] = e + }, + addListeners: function() { + this.addListeners_(this.target) + }, + addListeners_: function(e) { + var t = this.options; + t.attributes && e.addEventListener("DOMAttrModified", this, !0), t.characterData && e.addEventListener("DOMCharacterDataModified", this, !0), t.childList && e.addEventListener("DOMNodeInserted", this, !0), (t.childList || t.subtree) && e.addEventListener("DOMNodeRemoved", this, !0) + }, + removeListeners: function() { + this.removeListeners_(this.target) + }, + removeListeners_: function(e) { + var t = this.options; + t.attributes && e.removeEventListener("DOMAttrModified", this, !0), t.characterData && e.removeEventListener("DOMCharacterDataModified", this, !0), t.childList && e.removeEventListener("DOMNodeInserted", this, !0), (t.childList || t.subtree) && e.removeEventListener("DOMNodeRemoved", this, !0) + }, + addTransientObserver: function(e) { + if (e !== this.target) { + this.addListeners_(e), this.transientObservedNodes.push(e); + var t = v.get(e); + t || v.set(e, t = []), t.push(this) + } + }, + removeTransientObservers: function() { + var e = this.transientObservedNodes; + this.transientObservedNodes = [], e.forEach(function(e) { + this.removeListeners_(e); + for (var t = v.get(e), n = 0; n < t.length; n++) + if (t[n] === this) { + t.splice(n, 1); + break + } + }, this) + }, + handleEvent: function(e) { + switch (e.stopImmediatePropagation(), e.type) { + case "DOMAttrModified": + var t = e.attrName, + n = e.relatedNode.namespaceURI, + o = e.target, + r = new d("attributes", o); + r.attributeName = t, r.attributeNamespace = n; + var a = e.attrChange === MutationEvent.ADDITION ? null : e.prevValue; + i(o, function(e) { + if (e.attributes && (!e.attributeFilter || !e.attributeFilter.length || e.attributeFilter.indexOf(t) !== -1 || e.attributeFilter.indexOf(n) !== -1)) return e.attributeOldValue ? l(a) : r + }); + break; + case "DOMCharacterDataModified": + var o = e.target, + r = d("characterData", o), + a = e.prevValue; + i(o, function(e) { + if (e.characterData) return e.characterDataOldValue ? l(a) : r + }); + break; + case "DOMNodeRemoved": + this.addTransientObserver(e.target); + case "DOMNodeInserted": + var s, c, h = e.target; + "DOMNodeInserted" === e.type ? (s = [h], c = []) : (s = [], c = [h]); + var f = h.previousSibling, + p = h.nextSibling, + r = d("childList", e.target.parentNode); + r.addedNodes = s, r.removedNodes = c, r.previousSibling = f, r.nextSibling = p, i(e.relatedNode, function(e) { + if (e.childList) return r + }) + } + u() + } + }, e.JsMutationObserver = a, e.MutationObserver || (e.MutationObserver = a, a._isPolyfilled = !0) + } + }(self), + function() { + function e(e) { + switch (e) { + case "&": + return "&"; + case "<": + return "<"; + case ">": + return ">"; + case " ": + return " " + } + } + + function t(t) { + return t.replace(u, e) + } + var n = "undefined" == typeof HTMLTemplateElement; + /Trident/.test(navigator.userAgent) && ! function() { + var e = document.importNode; + document.importNode = function() { + var t = e.apply(document, arguments); + if (t.nodeType === Node.DOCUMENT_FRAGMENT_NODE) { + var n = document.createDocumentFragment(); + return n.appendChild(t), n + } + return t + } + }(); + var o = function() { + if (!n) { + var e = document.createElement("template"), + t = document.createElement("template"); + t.content.appendChild(document.createElement("div")), e.content.appendChild(t); + var o = e.cloneNode(!0); + return 0 === o.content.childNodes.length || 0 === o.content.firstChild.content.childNodes.length + } + }(), + r = "template", + i = function() {}; + if (n) { + var a = document.implementation.createHTMLDocument("template"), + s = !0, + c = document.createElement("style"); + c.textContent = r + "{display:none;}"; + var d = document.head; + d.insertBefore(c, d.firstElementChild), i.prototype = Object.create(HTMLElement.prototype), i.decorate = function(e) { + if (!e.content) { + e.content = a.createDocumentFragment(); + for (var n; n = e.firstChild;) e.content.appendChild(n); + if (e.cloneNode = function(e) { + return i.cloneNode(this, e) + }, s) try { + Object.defineProperty(e, "innerHTML", { + get: function() { + for (var e = "", n = this.content.firstChild; n; n = n.nextSibling) e += n.outerHTML || t(n.data); + return e + }, + set: function(e) { + for (a.body.innerHTML = e, i.bootstrap(a); this.content.firstChild;) this.content.removeChild(this.content.firstChild); + for (; a.body.firstChild;) this.content.appendChild(a.body.firstChild) + }, + configurable: !0 + }) + } catch (o) { + s = !1 + } + i.bootstrap(e.content) + } + }, i.bootstrap = function(e) { + for (var t, n = e.querySelectorAll(r), o = 0, a = n.length; o < a && (t = n[o]); o++) i.decorate(t) + }, document.addEventListener("DOMContentLoaded", function() { + i.bootstrap(document) + }); + var l = document.createElement; + document.createElement = function() { + "use strict"; + var e = l.apply(document, arguments); + return "template" === e.localName && i.decorate(e), e + }; + var u = /[&\u00A0<>]/g + } + if (n || o) { + var h = Node.prototype.cloneNode; + i.cloneNode = function(e, t) { + var n = h.call(e, !1); + return this.decorate && this.decorate(n), t && (n.content.appendChild(h.call(e.content, !0)), this.fixClonedDom(n.content, e.content)), n + }, i.fixClonedDom = function(e, t) { + if (t.querySelectorAll) + for (var n, o, i = t.querySelectorAll(r), a = e.querySelectorAll(r), s = 0, c = a.length; s < c; s++) o = i[s], n = a[s], this.decorate && this.decorate(o), n.parentNode.replaceChild(o.cloneNode(!0), n) + }; + var f = document.importNode; + Node.prototype.cloneNode = function(e) { + var t = h.call(this, e); + return e && i.fixClonedDom(t, this), t + }, document.importNode = function(e, t) { + if (e.localName === r) return i.cloneNode(e, t); + var n = f.call(document, e, t); + return t && i.fixClonedDom(n, e), n + }, o && (HTMLTemplateElement.prototype.cloneNode = function(e) { + return i.cloneNode(this, e) + }) + } + n && (window.HTMLTemplateElement = i) + }(), + function(e) { + "use strict"; + if (!window.performance || !window.performance.now) { + var t = Date.now(); + window.performance = { + now: function() { + return Date.now() - t + } + } + } + window.requestAnimationFrame || (window.requestAnimationFrame = function() { + var e = window.webkitRequestAnimationFrame || window.mozRequestAnimationFrame; + return e ? function(t) { + return e(function() { + t(performance.now()) + }) + } : function(e) { + return window.setTimeout(e, 1e3 / 60) + } + }()), window.cancelAnimationFrame || (window.cancelAnimationFrame = function() { + return window.webkitCancelAnimationFrame || window.mozCancelAnimationFrame || function(e) { + clearTimeout(e) + } + }()); + var n = function() { + var e = document.createEvent("Event"); + return e.initEvent("foo", !0, !0), e.preventDefault(), e.defaultPrevented + }(); + if (!n) { + var o = Event.prototype.preventDefault; + Event.prototype.preventDefault = function() { + this.cancelable && (o.call(this), Object.defineProperty(this, "defaultPrevented", { + get: function() { + return !0 + }, + configurable: !0 + })) + } + } + var r = /Trident/.test(navigator.userAgent); + if ((!window.CustomEvent || r && "function" != typeof window.CustomEvent) && (window.CustomEvent = function(e, t) { + t = t || {}; + var n = document.createEvent("CustomEvent"); + return n.initCustomEvent(e, Boolean(t.bubbles), Boolean(t.cancelable), t.detail), n + }, window.CustomEvent.prototype = window.Event.prototype), !window.Event || r && "function" != typeof window.Event) { + var i = window.Event; + window.Event = function(e, t) { + t = t || {}; + var n = document.createEvent("Event"); + return n.initEvent(e, Boolean(t.bubbles), Boolean(t.cancelable)), n + }, window.Event.prototype = i.prototype + } + }(window.WebComponents), window.HTMLImports = window.HTMLImports || { + flags: {} + }, + function(e) { + function t(e, t) { + t = t || p, o(function() { + i(e, t) + }, t) + } + + function n(e) { + return "complete" === e.readyState || e.readyState === w + } + + function o(e, t) { + if (n(t)) e && e(); + else { + var r = function() { + "complete" !== t.readyState && t.readyState !== w || (t.removeEventListener(_, r), o(e, t)) + }; + t.addEventListener(_, r) + } + } + + function r(e) { + e.target.__loaded = !0 + } + + function i(e, t) { + function n() { + c == d && e && e({ + allImports: s, + loadedImports: l, + errorImports: u + }) + } + + function o(e) { + r(e), l.push(this), c++, n() + } + + function i(e) { + u.push(this), c++, n() + } + var s = t.querySelectorAll("link[rel=import]"), + c = 0, + d = s.length, + l = [], + u = []; + if (d) + for (var h, f = 0; f < d && (h = s[f]); f++) a(h) ? (l.push(this), c++, n()) : (h.addEventListener("load", o), h.addEventListener("error", i)); + else n() + } + + function a(e) { + return u ? e.__loaded || e["import"] && "loading" !== e["import"].readyState : e.__importParsed + } + + function s(e) { + for (var t, n = 0, o = e.length; n < o && (t = e[n]); n++) c(t) && d(t) + } + + function c(e) { + return "link" === e.localName && "import" === e.rel + } + + function d(e) { + var t = e["import"]; + t ? r({ + target: e + }) : (e.addEventListener("load", r), e.addEventListener("error", r)) + } + var l = "import", + u = Boolean(l in document.createElement("link")), + h = Boolean(window.ShadowDOMPolyfill), + f = function(e) { + return h ? window.ShadowDOMPolyfill.wrapIfNeeded(e) : e + }, + p = f(document), + m = { + get: function() { + var e = window.HTMLImports.currentScript || document.currentScript || ("complete" !== document.readyState ? document.scripts[document.scripts.length - 1] : null); + return f(e) + }, + configurable: !0 + }; + Object.defineProperty(document, "_currentScript", m), Object.defineProperty(p, "_currentScript", m); + var v = /Trident/.test(navigator.userAgent), + w = v ? "complete" : "interactive", + _ = "readystatechange"; + u && (new MutationObserver(function(e) { + for (var t, n = 0, o = e.length; n < o && (t = e[n]); n++) t.addedNodes && s(t.addedNodes) + }).observe(document.head, { + childList: !0 + }), function() { + if ("loading" === document.readyState) + for (var e, t = document.querySelectorAll("link[rel=import]"), n = 0, o = t.length; n < o && (e = t[n]); n++) d(e) + }()), t(function(e) { + window.HTMLImports.ready = !0, window.HTMLImports.readyTime = (new Date).getTime(); + var t = p.createEvent("CustomEvent"); + t.initCustomEvent("HTMLImportsLoaded", !0, !0, e), p.dispatchEvent(t) + }), e.IMPORT_LINK_TYPE = l, e.useNative = u, e.rootDocument = p, e.whenReady = t, e.isIE = v + }(window.HTMLImports), + function(e) { + var t = [], + n = function(e) { + t.push(e) + }, + o = function() { + t.forEach(function(t) { + t(e) + }) + }; + e.addModule = n, e.initializeModules = o + }(window.HTMLImports), window.HTMLImports.addModule(function(e) { + var t = /(url\()([^)]*)(\))/g, + n = /(@import[\s]+(?!url\())([^;]*)(;)/g, + o = { + resolveUrlsInStyle: function(e, t) { + var n = e.ownerDocument, + o = n.createElement("a"); + return e.textContent = this.resolveUrlsInCssText(e.textContent, t, o), e + }, + resolveUrlsInCssText: function(e, o, r) { + var i = this.replaceUrls(e, r, o, t); + return i = this.replaceUrls(i, r, o, n) + }, + replaceUrls: function(e, t, n, o) { + return e.replace(o, function(e, o, r, i) { + var a = r.replace(/["']/g, ""); + return n && (a = new URL(a, n).href), t.href = a, a = t.href, o + "'" + a + "'" + i + }) + } + }; + e.path = o + }), window.HTMLImports.addModule(function(e) { + var t = { + async: !0, + ok: function(e) { + return e.status >= 200 && e.status < 300 || 304 === e.status || 0 === e.status + }, + load: function(n, o, r) { + var i = new XMLHttpRequest; + return (e.flags.debug || e.flags.bust) && (n += "?" + Math.random()), i.open("GET", n, t.async), i.addEventListener("readystatechange", function(e) { + if (4 === i.readyState) { + var n = null; + try { + var a = i.getResponseHeader("Location"); + a && (n = "/" === a.substr(0, 1) ? location.origin + a : a) + } catch (e) { + console.error(e.message) + } + o.call(r, !t.ok(i) && i, i.response || i.responseText, n) + } + }), i.send(), i + }, + loadDocument: function(e, t, n) { + this.load(e, t, n).responseType = "document" + } + }; + e.xhr = t + }), window.HTMLImports.addModule(function(e) { + var t = e.xhr, + n = e.flags, + o = function(e, t) { + this.cache = {}, this.onload = e, this.oncomplete = t, this.inflight = 0, this.pending = {} + }; + o.prototype = { + addNodes: function(e) { + this.inflight += e.length; + for (var t, n = 0, o = e.length; n < o && (t = e[n]); n++) this.require(t); + this.checkDone() + }, + addNode: function(e) { + this.inflight++, this.require(e), this.checkDone() + }, + require: function(e) { + var t = e.src || e.href; + e.__nodeUrl = t, this.dedupe(t, e) || this.fetch(t, e) + }, + dedupe: function(e, t) { + if (this.pending[e]) return this.pending[e].push(t), !0; + return this.cache[e] ? (this.onload(e, t, this.cache[e]), this.tail(), !0) : (this.pending[e] = [t], !1) + }, + fetch: function(e, o) { + if (n.load && console.log("fetch", e, o), e) + if (e.match(/^data:/)) { + var r = e.split(","), + i = r[0], + a = r[1]; + a = i.indexOf(";base64") > -1 ? atob(a) : decodeURIComponent(a), setTimeout(function() { + this.receive(e, o, null, a) + }.bind(this), 0) + } else { + var s = function(t, n, r) { + this.receive(e, o, t, n, r) + }.bind(this); + t.load(e, s) + } + else setTimeout(function() { + this.receive(e, o, { + error: "href must be specified" + }, null) + }.bind(this), 0) + }, + receive: function(e, t, n, o, r) { + this.cache[e] = o; + for (var i, a = this.pending[e], s = 0, c = a.length; s < c && (i = a[s]); s++) this.onload(e, i, o, n, r), this.tail(); + this.pending[e] = null + }, + tail: function() { + --this.inflight, this.checkDone() + }, + checkDone: function() { + this.inflight || this.oncomplete() + } + }, e.Loader = o + }), window.HTMLImports.addModule(function(e) { + var t = function(e) { + this.addCallback = e, this.mo = new MutationObserver(this.handler.bind(this)) + }; + t.prototype = { + handler: function(e) { + for (var t, n = 0, o = e.length; n < o && (t = e[n]); n++) "childList" === t.type && t.addedNodes.length && this.addedNodes(t.addedNodes) + }, + addedNodes: function(e) { + this.addCallback && this.addCallback(e); + for (var t, n = 0, o = e.length; n < o && (t = e[n]); n++) t.children && t.children.length && this.addedNodes(t.children) + }, + observe: function(e) { + this.mo.observe(e, { + childList: !0, + subtree: !0 + }) + } + }, e.Observer = t + }), window.HTMLImports.addModule(function(e) { + function t(e) { + return "link" === e.localName && e.rel === l + } + + function n(e) { + var t = o(e); + return "data:text/javascript;charset=utf-8," + encodeURIComponent(t) + } + + function o(e) { + return e.textContent + r(e) + } + + function r(e) { + var t = e.ownerDocument; + t.__importedScripts = t.__importedScripts || 0; + var n = e.ownerDocument.baseURI, + o = t.__importedScripts ? "-" + t.__importedScripts : ""; + return t.__importedScripts++, "\n//# sourceURL=" + n + o + ".js\n" + } + + function i(e) { + var t = e.ownerDocument.createElement("style"); + return t.textContent = e.textContent, a.resolveUrlsInStyle(t), t + } + var a = e.path, + s = e.rootDocument, + c = e.flags, + d = e.isIE, + l = e.IMPORT_LINK_TYPE, + u = "link[rel=" + l + "]", + h = { + documentSelectors: u, + importsSelectors: [u, "link[rel=stylesheet]:not([type])", "style:not([type])", "script:not([type])", 'script[type="application/javascript"]', 'script[type="text/javascript"]'].join(","), + map: { + link: "parseLink", + script: "parseScript", + style: "parseStyle" + }, + dynamicElements: [], + parseNext: function() { + var e = this.nextToParse(); + e && this.parse(e) + }, + parse: function(e) { + if (this.isParsed(e)) return void(c.parse && console.log("[%s] is already parsed", e.localName)); + var t = this[this.map[e.localName]]; + t && (this.markParsing(e), t.call(this, e)) + }, + parseDynamic: function(e, t) { + this.dynamicElements.push(e), t || this.parseNext() + }, + markParsing: function(e) { + c.parse && console.log("parsing", e), this.parsingElement = e + }, + markParsingComplete: function(e) { + e.__importParsed = !0, this.markDynamicParsingComplete(e), e.__importElement && (e.__importElement.__importParsed = !0, this.markDynamicParsingComplete(e.__importElement)), this.parsingElement = null, c.parse && console.log("completed", e) + }, + markDynamicParsingComplete: function(e) { + var t = this.dynamicElements.indexOf(e); + t >= 0 && this.dynamicElements.splice(t, 1) + }, + parseImport: function(e) { + if (e["import"] = e.__doc, window.HTMLImports.__importsParsingHook && window.HTMLImports.__importsParsingHook(e), e["import"] && (e["import"].__importParsed = !0), this.markParsingComplete(e), e.__resource && !e.__error ? e.dispatchEvent(new CustomEvent("load", { + bubbles: !1 + })) : e.dispatchEvent(new CustomEvent("error", { + bubbles: !1 + })), e.__pending) + for (var t; e.__pending.length;) t = e.__pending.shift(), t && t({ + target: e + }); + this.parseNext() + }, + parseLink: function(e) { + t(e) ? this.parseImport(e) : (e.href = e.href, this.parseGeneric(e)) + }, + parseStyle: function(e) { + var t = e; + e = i(e), t.__appliedElement = e, e.__importElement = t, this.parseGeneric(e) + }, + parseGeneric: function(e) { + this.trackElement(e), this.addElementToDocument(e) + }, + rootImportForElement: function(e) { + for (var t = e; t.ownerDocument.__importLink;) t = t.ownerDocument.__importLink; + return t + }, + addElementToDocument: function(e) { + var t = this.rootImportForElement(e.__importElement || e); + t.parentNode.insertBefore(e, t) + }, + trackElement: function(e, t) { + var n = this, + o = function(r) { + e.removeEventListener("load", o), e.removeEventListener("error", o), t && t(r), n.markParsingComplete(e), n.parseNext() + }; + if (e.addEventListener("load", o), e.addEventListener("error", o), d && "style" === e.localName) { + var r = !1; + if (e.textContent.indexOf("@import") == -1) r = !0; + else if (e.sheet) { + r = !0; + for (var i, a = e.sheet.cssRules, s = a ? a.length : 0, c = 0; c < s && (i = a[c]); c++) i.type === CSSRule.IMPORT_RULE && (r = r && Boolean(i.styleSheet)) + } + r && setTimeout(function() { + e.dispatchEvent(new CustomEvent("load", { + bubbles: !1 + })) + }) + } + }, + parseScript: function(t) { + var o = document.createElement("script"); + o.__importElement = t, o.src = t.src ? t.src : n(t), e.currentScript = t, this.trackElement(o, function(t) { + o.parentNode && o.parentNode.removeChild(o), e.currentScript = null + }), this.addElementToDocument(o) + }, + nextToParse: function() { + return this._mayParse = [], !this.parsingElement && (this.nextToParseInDoc(s) || this.nextToParseDynamic()) + }, + nextToParseInDoc: function(e, n) { + if (e && this._mayParse.indexOf(e) < 0) { + this._mayParse.push(e); + for (var o, r = e.querySelectorAll(this.parseSelectorsForNode(e)), i = 0, a = r.length; i < a && (o = r[i]); i++) + if (!this.isParsed(o)) return this.hasResource(o) ? t(o) ? this.nextToParseInDoc(o.__doc, o) : o : void 0 + } + return n + }, + nextToParseDynamic: function() { + return this.dynamicElements[0] + }, + parseSelectorsForNode: function(e) { + var t = e.ownerDocument || e; + return t === s ? this.documentSelectors : this.importsSelectors + }, + isParsed: function(e) { + return e.__importParsed + }, + needsDynamicParsing: function(e) { + return this.dynamicElements.indexOf(e) >= 0 + }, + hasResource: function(e) { + return !t(e) || void 0 !== e.__doc + } + }; + e.parser = h, e.IMPORT_SELECTOR = u + }), window.HTMLImports.addModule(function(e) { + function t(e) { + return n(e, a) + } + + function n(e, t) { + return "link" === e.localName && e.getAttribute("rel") === t + } + + function o(e) { + return !!Object.getOwnPropertyDescriptor(e, "baseURI") + } + + function r(e, t) { + var n = document.implementation.createHTMLDocument(a); + n._URL = t; + var r = n.createElement("base"); + r.setAttribute("href", t), n.baseURI || o(n) || Object.defineProperty(n, "baseURI", { + value: t + }); + var i = n.createElement("meta"); + return i.setAttribute("charset", "utf-8"), n.head.appendChild(i), n.head.appendChild(r), n.body.innerHTML = e, window.HTMLTemplateElement && HTMLTemplateElement.bootstrap && HTMLTemplateElement.bootstrap(n), n + } + var i = e.flags, + a = e.IMPORT_LINK_TYPE, + s = e.IMPORT_SELECTOR, + c = e.rootDocument, + d = e.Loader, + l = e.Observer, + u = e.parser, + h = { + documents: {}, + documentPreloadSelectors: s, + importsPreloadSelectors: [s].join(","), + loadNode: function(e) { + f.addNode(e) + }, + loadSubtree: function(e) { + var t = this.marshalNodes(e); + f.addNodes(t) + }, + marshalNodes: function(e) { + return e.querySelectorAll(this.loadSelectorsForNode(e)) + }, + loadSelectorsForNode: function(e) { + var t = e.ownerDocument || e; + return t === c ? this.documentPreloadSelectors : this.importsPreloadSelectors + }, + loaded: function(e, n, o, a, s) { + if (i.load && console.log("loaded", e, n), n.__resource = o, n.__error = a, t(n)) { + var c = this.documents[e]; + void 0 === c && (c = a ? null : r(o, s || e), c && (c.__importLink = n, this.bootDocument(c)), this.documents[e] = c), n.__doc = c + } + u.parseNext() + }, + bootDocument: function(e) { + this.loadSubtree(e), this.observer.observe(e), u.parseNext() + }, + loadedAll: function() { + u.parseNext() + } + }, + f = new d(h.loaded.bind(h), h.loadedAll.bind(h)); + if (h.observer = new l, !document.baseURI) { + var p = { + get: function() { + var e = document.querySelector("base"); + return e ? e.href : window.location.href + }, + configurable: !0 + }; + Object.defineProperty(document, "baseURI", p), Object.defineProperty(c, "baseURI", p) + } + e.importer = h, e.importLoader = f + }), window.HTMLImports.addModule(function(e) { + var t = e.parser, + n = e.importer, + o = { + added: function(e) { + for (var o, r, i, a, s = 0, c = e.length; s < c && (a = e[s]); s++) o || (o = a.ownerDocument, r = t.isParsed(o)), i = this.shouldLoadNode(a), i && n.loadNode(a), this.shouldParseNode(a) && r && t.parseDynamic(a, i) + }, + shouldLoadNode: function(e) { + return 1 === e.nodeType && r.call(e, n.loadSelectorsForNode(e)) + }, + shouldParseNode: function(e) { + return 1 === e.nodeType && r.call(e, t.parseSelectorsForNode(e)) + } + }; + n.observer.addCallback = o.added.bind(o); + var r = HTMLElement.prototype.matches || HTMLElement.prototype.matchesSelector || HTMLElement.prototype.webkitMatchesSelector || HTMLElement.prototype.mozMatchesSelector || HTMLElement.prototype.msMatchesSelector + }), + function(e) { + function t() { + window.HTMLImports.importer.bootDocument(o) + } + var n = e.initializeModules; + e.isIE; + if (!e.useNative) { + n(); + var o = e.rootDocument; + "complete" === document.readyState || "interactive" === document.readyState && !window.attachEvent ? t() : document.addEventListener("DOMContentLoaded", t) + } + }(window.HTMLImports), window.CustomElements = window.CustomElements || { + flags: {} + }, + function(e) { + var t = e.flags, + n = [], + o = function(e) { + n.push(e) + }, + r = function() { + n.forEach(function(t) { + t(e) + }) + }; + e.addModule = o, e.initializeModules = r, e.hasNative = Boolean(document.registerElement), e.isIE = /Trident/.test(navigator.userAgent), e.useNative = !t.register && e.hasNative && !window.ShadowDOMPolyfill && (!window.HTMLImports || window.HTMLImports.useNative) + }(window.CustomElements), window.CustomElements.addModule(function(e) { + function t(e, t) { + n(e, function(e) { + return !!t(e) || void o(e, t) + }), o(e, t) + } + + function n(e, t, o) { + var r = e.firstElementChild; + if (!r) + for (r = e.firstChild; r && r.nodeType !== Node.ELEMENT_NODE;) r = r.nextSibling; + for (; r;) t(r, o) !== !0 && n(r, t, o), r = r.nextElementSibling; + return null + } + + function o(e, n) { + for (var o = e.shadowRoot; o;) t(o, n), o = o.olderShadowRoot + } + + function r(e, t) { + i(e, t, []) + } + + function i(e, t, n) { + if (e = window.wrap(e), !(n.indexOf(e) >= 0)) { + n.push(e); + for (var o, r = e.querySelectorAll("link[rel=" + a + "]"), s = 0, c = r.length; s < c && (o = r[s]); s++) o["import"] && i(o["import"], t, n); + t(e) + } + } + var a = window.HTMLImports ? window.HTMLImports.IMPORT_LINK_TYPE : "none"; + e.forDocumentTree = r, e.forSubtree = t + }), window.CustomElements.addModule(function(e) { + function t(e, t) { + return n(e, t) || o(e, t) + } + + function n(t, n) { + return !!e.upgrade(t, n) || void(n && a(t)) + } + + function o(e, t) { + g(e, function(e) { + if (n(e, t)) return !0 + }) + } + + function r(e) { + L.push(e), E || (E = !0, setTimeout(i)) + } + + function i() { + E = !1; + for (var e, t = L, n = 0, o = t.length; n < o && (e = t[n]); n++) e(); + L = [] + } + + function a(e) { + y ? r(function() { + s(e); + }) : s(e) + } + + function s(e) { + e.__upgraded__ && !e.__attached && (e.__attached = !0, e.attachedCallback && e.attachedCallback()) + } + + function c(e) { + d(e), g(e, function(e) { + d(e) + }) + } + + function d(e) { + y ? r(function() { + l(e) + }) : l(e) + } + + function l(e) { + e.__upgraded__ && e.__attached && (e.__attached = !1, e.detachedCallback && e.detachedCallback()) + } + + function u(e) { + for (var t = e, n = window.wrap(document); t;) { + if (t == n) return !0; + t = t.parentNode || t.nodeType === Node.DOCUMENT_FRAGMENT_NODE && t.host + } + } + + function h(e) { + if (e.shadowRoot && !e.shadowRoot.__watched) { + _.dom && console.log("watching shadow-root for: ", e.localName); + for (var t = e.shadowRoot; t;) m(t), t = t.olderShadowRoot + } + } + + function f(e, n) { + if (_.dom) { + var o = n[0]; + if (o && "childList" === o.type && o.addedNodes && o.addedNodes) { + for (var r = o.addedNodes[0]; r && r !== document && !r.host;) r = r.parentNode; + var i = r && (r.URL || r._URL || r.host && r.host.localName) || ""; + i = i.split("/?").shift().split("/").pop() + } + console.group("mutations (%d) [%s]", n.length, i || "") + } + var a = u(e); + n.forEach(function(e) { + "childList" === e.type && (N(e.addedNodes, function(e) { + e.localName && t(e, a) + }), N(e.removedNodes, function(e) { + e.localName && c(e) + })) + }), _.dom && console.groupEnd() + } + + function p(e) { + for (e = window.wrap(e), e || (e = window.wrap(document)); e.parentNode;) e = e.parentNode; + var t = e.__observer; + t && (f(e, t.takeRecords()), i()) + } + + function m(e) { + if (!e.__observer) { + var t = new MutationObserver(f.bind(this, e)); + t.observe(e, { + childList: !0, + subtree: !0 + }), e.__observer = t + } + } + + function v(e) { + e = window.wrap(e), _.dom && console.group("upgradeDocument: ", e.baseURI.split("/").pop()); + var n = e === window.wrap(document); + t(e, n), m(e), _.dom && console.groupEnd() + } + + function w(e) { + b(e, v) + } + var _ = e.flags, + g = e.forSubtree, + b = e.forDocumentTree, + y = window.MutationObserver._isPolyfilled && _["throttle-attached"]; + e.hasPolyfillMutations = y, e.hasThrottledAttached = y; + var E = !1, + L = [], + N = Array.prototype.forEach.call.bind(Array.prototype.forEach), + M = Element.prototype.createShadowRoot; + M && (Element.prototype.createShadowRoot = function() { + var e = M.call(this); + return window.CustomElements.watchShadow(this), e + }), e.watchShadow = h, e.upgradeDocumentTree = w, e.upgradeDocument = v, e.upgradeSubtree = o, e.upgradeAll = t, e.attached = a, e.takeRecords = p + }), window.CustomElements.addModule(function(e) { + function t(t, o) { + if ("template" === t.localName && window.HTMLTemplateElement && HTMLTemplateElement.decorate && HTMLTemplateElement.decorate(t), !t.__upgraded__ && t.nodeType === Node.ELEMENT_NODE) { + var r = t.getAttribute("is"), + i = e.getRegisteredDefinition(t.localName) || e.getRegisteredDefinition(r); + if (i && (r && i.tag == t.localName || !r && !i["extends"])) return n(t, i, o) + } + } + + function n(t, n, r) { + return a.upgrade && console.group("upgrade:", t.localName), n.is && t.setAttribute("is", n.is), o(t, n), t.__upgraded__ = !0, i(t), r && e.attached(t), e.upgradeSubtree(t, r), a.upgrade && console.groupEnd(), t + } + + function o(e, t) { + Object.__proto__ ? e.__proto__ = t.prototype : (r(e, t.prototype, t["native"]), e.__proto__ = t.prototype) + } + + function r(e, t, n) { + for (var o = {}, r = t; r !== n && r !== HTMLElement.prototype;) { + for (var i, a = Object.getOwnPropertyNames(r), s = 0; i = a[s]; s++) o[i] || (Object.defineProperty(e, i, Object.getOwnPropertyDescriptor(r, i)), o[i] = 1); + r = Object.getPrototypeOf(r) + } + } + + function i(e) { + e.createdCallback && e.createdCallback() + } + var a = e.flags; + e.upgrade = t, e.upgradeWithDefinition = n, e.implementPrototype = o + }), window.CustomElements.addModule(function(e) { + function t(t, o) { + var c = o || {}; + if (!t) throw new Error("document.registerElement: first argument `name` must not be empty"); + if (t.indexOf("-") < 0) throw new Error("document.registerElement: first argument ('name') must contain a dash ('-'). Argument provided was '" + String(t) + "'."); + if (r(t)) throw new Error("Failed to execute 'registerElement' on 'Document': Registration failed for type '" + String(t) + "'. The type name is invalid."); + if (d(t)) throw new Error("DuplicateDefinitionError: a type with name '" + String(t) + "' is already registered"); + return c.prototype || (c.prototype = Object.create(HTMLElement.prototype)), c.__name = t.toLowerCase(), c["extends"] && (c["extends"] = c["extends"].toLowerCase()), c.lifecycle = c.lifecycle || {}, c.ancestry = i(c["extends"]), a(c), s(c), n(c.prototype), l(c.__name, c), c.ctor = u(c), c.ctor.prototype = c.prototype, c.prototype.constructor = c.ctor, e.ready && v(document), c.ctor + } + + function n(e) { + if (!e.setAttribute._polyfilled) { + var t = e.setAttribute; + e.setAttribute = function(e, n) { + o.call(this, e, n, t) + }; + var n = e.removeAttribute; + e.removeAttribute = function(e) { + o.call(this, e, null, n) + }, e.setAttribute._polyfilled = !0 + } + } + + function o(e, t, n) { + e = e.toLowerCase(); + var o = this.getAttribute(e); + n.apply(this, arguments); + var r = this.getAttribute(e); + this.attributeChangedCallback && r !== o && this.attributeChangedCallback(e, o, r) + } + + function r(e) { + for (var t = 0; t < y.length; t++) + if (e === y[t]) return !0 + } + + function i(e) { + var t = d(e); + return t ? i(t["extends"]).concat([t]) : [] + } + + function a(e) { + for (var t, n = e["extends"], o = 0; t = e.ancestry[o]; o++) n = t.is && t.tag; + e.tag = n || e.__name, n && (e.is = e.__name) + } + + function s(e) { + if (!Object.__proto__) { + var t = HTMLElement.prototype; + if (e.is) { + var n = document.createElement(e.tag); + t = Object.getPrototypeOf(n) + } + for (var o, r = e.prototype, i = !1; r;) r == t && (i = !0), o = Object.getPrototypeOf(r), o && (r.__proto__ = o), r = o; + i || console.warn(e.tag + " prototype not found in prototype chain for " + e.is), e["native"] = t + } + } + + function c(e) { + return _(N(e.tag), e) + } + + function d(e) { + if (e) return E[e.toLowerCase()] + } + + function l(e, t) { + E[e] = t + } + + function u(e) { + return function() { + return c(e) + } + } + + function h(e, t, n) { + return e === L ? f(t, n) : M(e, t) + } + + function f(e, t) { + e && (e = e.toLowerCase()), t && (t = t.toLowerCase()); + var n = d(t || e); + if (n) { + if (e == n.tag && t == n.is) return new n.ctor; + if (!t && !n.is) return new n.ctor + } + var o; + return t ? (o = f(e), o.setAttribute("is", t), o) : (o = N(e), e.indexOf("-") >= 0 && g(o, HTMLElement), o) + } + + function p(e, t) { + var n = e[t]; + e[t] = function() { + var e = n.apply(this, arguments); + return w(e), e + } + } + var m, v = (e.isIE, e.upgradeDocumentTree), + w = e.upgradeAll, + _ = e.upgradeWithDefinition, + g = e.implementPrototype, + b = e.useNative, + y = ["annotation-xml", "color-profile", "font-face", "font-face-src", "font-face-uri", "font-face-format", "font-face-name", "missing-glyph"], + E = {}, + L = "http://www.w3.org/1999/xhtml", + N = document.createElement.bind(document), + M = document.createElementNS.bind(document); + m = Object.__proto__ || b ? function(e, t) { + return e instanceof t + } : function(e, t) { + if (e instanceof t) return !0; + for (var n = e; n;) { + if (n === t.prototype) return !0; + n = n.__proto__ + } + return !1 + }, p(Node.prototype, "cloneNode"), p(document, "importNode"), document.registerElement = t, document.createElement = f, document.createElementNS = h, e.registry = E, e["instanceof"] = m, e.reservedTagList = y, e.getRegisteredDefinition = d, document.register = document.registerElement + }), + function(e) { + function t() { + i(window.wrap(document)), window.CustomElements.ready = !0; + var e = window.requestAnimationFrame || function(e) { + setTimeout(e, 16) + }; + e(function() { + setTimeout(function() { + window.CustomElements.readyTime = Date.now(), window.HTMLImports && (window.CustomElements.elapsed = window.CustomElements.readyTime - window.HTMLImports.readyTime), document.dispatchEvent(new CustomEvent("WebComponentsReady", { + bubbles: !0 + })) + }) + }) + } + var n = e.useNative, + o = e.initializeModules; + e.isIE; + if (n) { + var r = function() {}; + e.watchShadow = r, e.upgrade = r, e.upgradeAll = r, e.upgradeDocumentTree = r, e.upgradeSubtree = r, e.takeRecords = r, e["instanceof"] = function(e, t) { + return e instanceof t + } + } else o(); + var i = e.upgradeDocumentTree, + a = e.upgradeDocument; + if (window.wrap || (window.ShadowDOMPolyfill ? (window.wrap = window.ShadowDOMPolyfill.wrapIfNeeded, window.unwrap = window.ShadowDOMPolyfill.unwrapIfNeeded) : window.wrap = window.unwrap = function(e) { + return e + }), window.HTMLImports && (window.HTMLImports.__importsParsingHook = function(e) { + e["import"] && a(wrap(e["import"])) + }), "complete" === document.readyState || e.flags.eager) t(); + else if ("interactive" !== document.readyState || window.attachEvent || window.HTMLImports && !window.HTMLImports.ready) { + var s = window.HTMLImports && !window.HTMLImports.ready ? "HTMLImportsLoaded" : "DOMContentLoaded"; + window.addEventListener(s, t) + } else t() + }(window.CustomElements), + function(e) { + var t = document.createElement("style"); + t.textContent = "body {transition: opacity ease-in 0.2s; } \nbody[unresolved] {opacity: 0; display: block; overflow: hidden; position: relative; } \n"; + var n = document.querySelector("head"); + n.insertBefore(t, n.firstChild) + }(window.WebComponents); \ No newline at end of file diff --git a/dashboard-ui/components/accessschedule/accessschedule.js b/dashboard-ui/components/accessschedule/accessschedule.js index b13330f9a6..cce626ae78 100644 --- a/dashboard-ui/components/accessschedule/accessschedule.js +++ b/dashboard-ui/components/accessschedule/accessschedule.js @@ -1 +1,51 @@ -define(["dialogHelper","datetime","emby-select","paper-icon-button-light","formDialogStyle"],function(dialogHelper,datetime){"use strict";function getDisplayTime(hours){var minutes=0,pct=hours%1;return pct&&(minutes=parseInt(60*pct)),datetime.getDisplayTime(new Date(2e3,1,1,hours,minutes,0,0))}function populateHours(context){for(var html="",i=0;i<24;i++)html+='";html+='",context.querySelector("#selectStart").innerHTML=html,context.querySelector("#selectEnd").innerHTML=html}function loadSchedule(context,schedule){context.querySelector("#selectDay").value=schedule.DayOfWeek||"Sunday",context.querySelector("#selectStart").value=schedule.StartHour||0,context.querySelector("#selectEnd").value=schedule.EndHour||0}function submitSchedule(context,options){var updatedSchedule={DayOfWeek:context.querySelector("#selectDay").value,StartHour:context.querySelector("#selectStart").value,EndHour:context.querySelector("#selectEnd").value};if(parseFloat(updatedSchedule.StartHour)>=parseFloat(updatedSchedule.EndHour))return void alert(Globalize.translate("ErrorMessageStartHourGreaterThanEnd"));context.submitted=!0,options.schedule=Object.assign(options.schedule,updatedSchedule),dialogHelper.close(context)}return{show:function(options){return new Promise(function(resolve,reject){var xhr=new XMLHttpRequest;xhr.open("GET","components/accessschedule/accessschedule.template.html",!0),xhr.onload=function(e){var template=this.response,dlg=dialogHelper.createDialog({removeOnClose:!0,size:"small"});dlg.classList.add("formDialog");var html="";html+=Globalize.translateDocument(template),dlg.innerHTML=html,populateHours(dlg),loadSchedule(dlg,options.schedule),dialogHelper.open(dlg),dlg.addEventListener("close",function(){dlg.submitted?resolve(options.schedule):reject()}),dlg.querySelector(".btnCancel").addEventListener("click",function(e){dialogHelper.close(dlg)}),dlg.querySelector("form").addEventListener("submit",function(e){return submitSchedule(dlg,options),e.preventDefault(),!1})},xhr.send()})}}}); \ No newline at end of file +define(["dialogHelper", "datetime", "emby-select", "paper-icon-button-light", "formDialogStyle"], function(dialogHelper, datetime) { + "use strict"; + + function getDisplayTime(hours) { + var minutes = 0, + pct = hours % 1; + return pct && (minutes = parseInt(60 * pct)), datetime.getDisplayTime(new Date(2e3, 1, 1, hours, minutes, 0, 0)) + } + + function populateHours(context) { + for (var html = "", i = 0; i < 24; i++) html += '"; + html += '", context.querySelector("#selectStart").innerHTML = html, context.querySelector("#selectEnd").innerHTML = html + } + + function loadSchedule(context, schedule) { + context.querySelector("#selectDay").value = schedule.DayOfWeek || "Sunday", context.querySelector("#selectStart").value = schedule.StartHour || 0, context.querySelector("#selectEnd").value = schedule.EndHour || 0 + } + + function submitSchedule(context, options) { + var updatedSchedule = { + DayOfWeek: context.querySelector("#selectDay").value, + StartHour: context.querySelector("#selectStart").value, + EndHour: context.querySelector("#selectEnd").value + }; + if (parseFloat(updatedSchedule.StartHour) >= parseFloat(updatedSchedule.EndHour)) return void alert(Globalize.translate("ErrorMessageStartHourGreaterThanEnd")); + context.submitted = !0, options.schedule = Object.assign(options.schedule, updatedSchedule), dialogHelper.close(context) + } + return { + show: function(options) { + return new Promise(function(resolve, reject) { + var xhr = new XMLHttpRequest; + xhr.open("GET", "components/accessschedule/accessschedule.template.html", !0), xhr.onload = function(e) { + var template = this.response, + dlg = dialogHelper.createDialog({ + removeOnClose: !0, + size: "small" + }); + dlg.classList.add("formDialog"); + var html = ""; + html += Globalize.translateDocument(template), dlg.innerHTML = html, populateHours(dlg), loadSchedule(dlg, options.schedule), dialogHelper.open(dlg), dlg.addEventListener("close", function() { + dlg.submitted ? resolve(options.schedule) : reject() + }), dlg.querySelector(".btnCancel").addEventListener("click", function(e) { + dialogHelper.close(dlg) + }), dlg.querySelector("form").addEventListener("submit", function(e) { + return submitSchedule(dlg, options), e.preventDefault(), !1 + }) + }, xhr.send() + }) + } + } +}); \ No newline at end of file diff --git a/dashboard-ui/components/activitylog.js b/dashboard-ui/components/activitylog.js index 323ee49187..ca2025acf3 100644 --- a/dashboard-ui/components/activitylog.js +++ b/dashboard-ui/components/activitylog.js @@ -1 +1,89 @@ -define(["events","globalize","dom","datetime","userSettings","serverNotifications","connectionManager","emby-button","listViewStyle"],function(events,globalize,dom,datetime,userSettings,serverNotifications,connectionManager){"use strict";function getEntryHtml(entry,apiClient){var html="";html+='
    ';var color="Error"==entry.Severity||"Fatal"==entry.Severity||"Warn"==entry.Severity?"#cc0000":"#52B54B";if(entry.UserId&&entry.UserPrimaryImageTag){html+='dvr"}else html+='dvr';html+='
    ',html+='
    ',html+=entry.Name,html+="
    ",html+='
    ';var date=datetime.parseISO8601Date(entry.Date,!0);return html+=datetime.toLocaleString(date).toLowerCase(),html+="
    ",html+='
    ',html+=entry.ShortOverview||"",html+="
    ",html+="
    ",entry.Overview&&(html+=''),html+="
    "}function renderList(elem,apiClient,result,startIndex,limit){elem.innerHTML=result.Items.map(function(i){return getEntryHtml(i,apiClient)}).join("")}function reloadData(instance,elem,apiClient,startIndex,limit){null==startIndex&&(startIndex=parseInt(elem.getAttribute("data-activitystartindex")||"0")),limit=limit||parseInt(elem.getAttribute("data-activitylimit")||"7");var minDate=new Date,hasUserId="false"!==elem.getAttribute("data-useractivity");hasUserId?minDate.setTime(minDate.getTime()-864e5):minDate.setTime(minDate.getTime()-6048e5),ApiClient.getJSON(ApiClient.getUrl("System/ActivityLog/Entries",{startIndex:startIndex,limit:limit,minDate:minDate.toISOString(),hasUserId:hasUserId})).then(function(result){if(elem.setAttribute("data-activitystartindex",startIndex),elem.setAttribute("data-activitylimit",limit),!startIndex){var activityContainer=dom.parentWithClass(elem,"activityContainer");activityContainer&&(result.Items.length?activityContainer.classList.remove("hide"):activityContainer.classList.add("hide"))}instance.items=result.Items,renderList(elem,apiClient,result,startIndex,limit)})}function onActivityLogUpdate(e,apiClient,data){var options=this.options;options&&options.serverId===apiClient.serverId()&&reloadData(this,options.element,apiClient)}function onListClick(e){var btnEntryInfo=dom.parentWithClass(e.target,"btnEntryInfo");if(btnEntryInfo){var id=btnEntryInfo.getAttribute("data-id"),items=this.items;if(items){var item=items.filter(function(i){return i.Id.toString()===id})[0];item&&showItemOverview(item)}}}function showItemOverview(item){require(["alert"],function(alert){alert({text:item.Overview})})}function ActivityLog(options){this.options=options;var element=options.element;element.classList.add("activityLogListWidget"),element.addEventListener("click",onListClick.bind(this));var apiClient=connectionManager.getApiClient(options.serverId);reloadData(this,element,apiClient);var onUpdate=onActivityLogUpdate.bind(this);this.updateFn=onUpdate,events.on(serverNotifications,"ActivityLogEntry",onUpdate),apiClient.sendMessage("ActivityLogEntryStart","0,1500")}return ActivityLog.prototype.destroy=function(){var options=this.options;if(options){options.element.classList.remove("activityLogListWidget");connectionManager.getApiClient(options.serverId).sendMessage("ActivityLogEntryStop","0,1500")}var onUpdate=this.updateFn;onUpdate&&events.off(serverNotifications,"ActivityLogEntry",onUpdate),this.items=null,this.options=null},ActivityLog}); \ No newline at end of file +define(["events", "globalize", "dom", "datetime", "userSettings", "serverNotifications", "connectionManager", "emby-button", "listViewStyle"], function(events, globalize, dom, datetime, userSettings, serverNotifications, connectionManager) { + "use strict"; + + function getEntryHtml(entry, apiClient) { + var html = ""; + html += '
    '; + var color = "Error" == entry.Severity || "Fatal" == entry.Severity || "Warn" == entry.Severity ? "#cc0000" : "#52B54B"; + if (entry.UserId && entry.UserPrimaryImageTag) { + html += 'dvr" + } else html += 'dvr'; + html += '
    ', html += '
    ', html += entry.Name, html += "
    ", html += '
    '; + var date = datetime.parseISO8601Date(entry.Date, !0); + return html += datetime.toLocaleString(date).toLowerCase(), html += "
    ", html += '
    ', html += entry.ShortOverview || "", html += "
    ", html += "
    ", entry.Overview && (html += ''), html += "
    " + } + + function renderList(elem, apiClient, result, startIndex, limit) { + elem.innerHTML = result.Items.map(function(i) { + return getEntryHtml(i, apiClient) + }).join("") + } + + function reloadData(instance, elem, apiClient, startIndex, limit) { + null == startIndex && (startIndex = parseInt(elem.getAttribute("data-activitystartindex") || "0")), limit = limit || parseInt(elem.getAttribute("data-activitylimit") || "7"); + var minDate = new Date, + hasUserId = "false" !== elem.getAttribute("data-useractivity"); + hasUserId ? minDate.setTime(minDate.getTime() - 864e5) : minDate.setTime(minDate.getTime() - 6048e5), ApiClient.getJSON(ApiClient.getUrl("System/ActivityLog/Entries", { + startIndex: startIndex, + limit: limit, + minDate: minDate.toISOString(), + hasUserId: hasUserId + })).then(function(result) { + if (elem.setAttribute("data-activitystartindex", startIndex), elem.setAttribute("data-activitylimit", limit), !startIndex) { + var activityContainer = dom.parentWithClass(elem, "activityContainer"); + activityContainer && (result.Items.length ? activityContainer.classList.remove("hide") : activityContainer.classList.add("hide")) + } + instance.items = result.Items, renderList(elem, apiClient, result, startIndex, limit) + }) + } + + function onActivityLogUpdate(e, apiClient, data) { + var options = this.options; + options && options.serverId === apiClient.serverId() && reloadData(this, options.element, apiClient) + } + + function onListClick(e) { + var btnEntryInfo = dom.parentWithClass(e.target, "btnEntryInfo"); + if (btnEntryInfo) { + var id = btnEntryInfo.getAttribute("data-id"), + items = this.items; + if (items) { + var item = items.filter(function(i) { + return i.Id.toString() === id + })[0]; + item && showItemOverview(item) + } + } + } + + function showItemOverview(item) { + require(["alert"], function(alert) { + alert({ + text: item.Overview + }) + }) + } + + function ActivityLog(options) { + this.options = options; + var element = options.element; + element.classList.add("activityLogListWidget"), element.addEventListener("click", onListClick.bind(this)); + var apiClient = connectionManager.getApiClient(options.serverId); + reloadData(this, element, apiClient); + var onUpdate = onActivityLogUpdate.bind(this); + this.updateFn = onUpdate, events.on(serverNotifications, "ActivityLogEntry", onUpdate), apiClient.sendMessage("ActivityLogEntryStart", "0,1500") + } + return ActivityLog.prototype.destroy = function() { + var options = this.options; + if (options) { + options.element.classList.remove("activityLogListWidget"); + connectionManager.getApiClient(options.serverId).sendMessage("ActivityLogEntryStop", "0,1500") + } + var onUpdate = this.updateFn; + onUpdate && events.off(serverNotifications, "ActivityLogEntry", onUpdate), this.items = null, this.options = null + }, ActivityLog +}); \ No newline at end of file diff --git a/dashboard-ui/components/categorysyncbuttons.js b/dashboard-ui/components/categorysyncbuttons.js index b9c3b7fb37..5a6075b196 100644 --- a/dashboard-ui/components/categorysyncbuttons.js +++ b/dashboard-ui/components/categorysyncbuttons.js @@ -1 +1,31 @@ -define(["itemHelper","libraryMenu","apphost"],function(itemHelper,libraryMenu,appHost){"use strict";function initSyncButtons(view){var apiClient=window.ApiClient;apiClient&&apiClient.getCurrentUserId()&&apiClient.getCurrentUser().then(function(user){for(var item={SupportsSync:!0},categorySyncButtons=view.querySelectorAll(".categorySyncButton"),i=0,length=categorySyncButtons.length;i",html+='
    ',channel.ProviderChannelName&&(html+=getMappingSecondaryName(channel,providerName)),html+="
    ",html+="",html+='',html+=""}function getEditorHtml(){var html="";return html+='
    ',html+='
    ',html+='
    ',html+="

    "+globalize.translate("HeaderChannels")+"

    ",html+='
    ',html+="
    ",html+="
    ",html+="
    ",html+="
    "}function initEditor(dlg,options){getChannelMappingOptions(options.serverId,options.providerId).then(function(result){currentMappingOptions=result;var channelsElement=dlg.querySelector(".channels");channelsElement.innerHTML=result.TunerChannels.map(function(channel){return getTunerChannelHtml(channel,result.ProviderName)}).join(""),channelsElement.addEventListener("click",onChannelsElementClick)})}var currentMappingOptions,self=this;self.show=function(){var dialogOptions={removeOnClose:!0};dialogOptions.size="small";var dlg=dialogHelper.createDialog(dialogOptions);dlg.classList.add("formDialog"),dlg.classList.add("ui-body-a"),dlg.classList.add("background-theme-a");var html="",title=globalize.translate("MapChannels");return html+='
    ',html+='',html+='

    ',html+=title,html+="

    ",html+="
    ",html+=getEditorHtml(),dlg.innerHTML=html,initEditor(dlg,options),dlg.querySelector(".btnCancel").addEventListener("click",function(){dialogHelper.close(dlg)}),new Promise(function(resolve,reject){dlg.addEventListener("close",resolve),dialogHelper.open(dlg)})}}}); \ No newline at end of file +define(["dialogHelper", "loading", "connectionManager", "globalize", "actionsheet", "emby-input", "paper-icon-button-light", "emby-button", "listViewStyle", "material-icons", "formDialogStyle"], function(dialogHelper, loading, connectionManager, globalize, actionsheet) { + "use strict"; + return function(options) { + function parentWithClass(elem, className) { + for (; !elem.classList || !elem.classList.contains(className);) + if (!(elem = elem.parentNode)) return null; + return elem + } + + function mapChannel(button, channelId, providerChannelId) { + loading.show(); + var providerId = options.providerId; + connectionManager.getApiClient(options.serverId).ajax({ + type: "POST", + url: ApiClient.getUrl("LiveTv/ChannelMappings"), + data: { + providerId: providerId, + tunerChannelId: channelId, + providerChannelId: providerChannelId + }, + dataType: "json" + }).then(function(mapping) { + var listItem = parentWithClass(button, "listItem"); + button.setAttribute("data-providerid", mapping.ProviderChannelId), listItem.querySelector(".secondary").innerHTML = getMappingSecondaryName(mapping, currentMappingOptions.ProviderName), loading.hide() + }) + } + + function onChannelsElementClick(e) { + var btnMap = parentWithClass(e.target, "btnMap"); + if (btnMap) { + var channelId = btnMap.getAttribute("data-id"), + providerChannelId = btnMap.getAttribute("data-providerid"), + menuItems = currentMappingOptions.ProviderChannels.map(function(m) { + return { + name: m.Name, + id: m.Id, + selected: m.Id.toLowerCase() === providerChannelId.toLowerCase() + } + }); + actionsheet.show({ + positionTo: btnMap, + items: menuItems + }).then(function(newChannelId) { + mapChannel(btnMap, channelId, newChannelId) + }) + } + } + + function getChannelMappingOptions(serverId, providerId) { + var apiClient = connectionManager.getApiClient(serverId); + return apiClient.getJSON(apiClient.getUrl("LiveTv/ChannelMappingOptions", { + providerId: providerId + })) + } + + function getMappingSecondaryName(mapping, providerName) { + return (mapping.ProviderChannelName || "") + " - " + providerName + } + + function getTunerChannelHtml(channel, providerName) { + var html = ""; + return html += '
    ', html += 'dvr', html += '
    ', html += '

    ', html += channel.Name, html += "

    ", html += '
    ', channel.ProviderChannelName && (html += getMappingSecondaryName(channel, providerName)), html += "
    ", html += "
    ", html += '', html += "
    " + } + + function getEditorHtml() { + var html = ""; + return html += '
    ', html += '
    ', html += '
    ', html += "

    " + globalize.translate("HeaderChannels") + "

    ", html += '
    ', html += "
    ", html += "
    ", html += "
    ", html += "
    " + } + + function initEditor(dlg, options) { + getChannelMappingOptions(options.serverId, options.providerId).then(function(result) { + currentMappingOptions = result; + var channelsElement = dlg.querySelector(".channels"); + channelsElement.innerHTML = result.TunerChannels.map(function(channel) { + return getTunerChannelHtml(channel, result.ProviderName) + }).join(""), channelsElement.addEventListener("click", onChannelsElementClick) + }) + } + var currentMappingOptions, self = this; + self.show = function() { + var dialogOptions = { + removeOnClose: !0 + }; + dialogOptions.size = "small"; + var dlg = dialogHelper.createDialog(dialogOptions); + dlg.classList.add("formDialog"), dlg.classList.add("ui-body-a"), dlg.classList.add("background-theme-a"); + var html = "", + title = globalize.translate("MapChannels"); + return html += '
    ', html += '', html += '

    ', html += title, html += "

    ", html += "
    ", html += getEditorHtml(), dlg.innerHTML = html, initEditor(dlg, options), dlg.querySelector(".btnCancel").addEventListener("click", function() { + dialogHelper.close(dlg) + }), new Promise(function(resolve, reject) { + dlg.addEventListener("close", resolve), dialogHelper.open(dlg) + }) + } + } +}); \ No newline at end of file diff --git a/dashboard-ui/components/directorybrowser/directorybrowser.js b/dashboard-ui/components/directorybrowser/directorybrowser.js index a4f683fd5a..567ae7e027 100644 --- a/dashboard-ui/components/directorybrowser/directorybrowser.js +++ b/dashboard-ui/components/directorybrowser/directorybrowser.js @@ -1 +1,145 @@ -define(["loading","dialogHelper","dom","listViewStyle","emby-input","emby-button","paper-icon-button-light","css!./directorybrowser","formDialogStyle","emby-linkbutton"],function(loading,dialogHelper,dom){"use strict";function getSystemInfo(){return systemInfo?Promise.resolve(systemInfo):ApiClient.getPublicSystemInfo().then(function(info){return systemInfo=info,info})}function onDialogClosed(){loading.hide()}function refreshDirectoryBrowser(page,path,fileOptions,updatePathOnError){if(path&&"string"!=typeof path)throw new Error("invalid path");loading.show();var promises=[];"Network"===path?promises.push(ApiClient.getNetworkDevices()):path?(promises.push(ApiClient.getDirectoryContents(path,fileOptions)),promises.push(ApiClient.getParentPath(path))):promises.push(ApiClient.getDrives()),Promise.all(promises).then(function(responses){var folders=responses[0],parentPath=responses[1]||"";page.querySelector("#txtDirectoryPickerPath").value=path||"";var html="";path&&(html+=getItem("lnkPath lnkDirectory","",parentPath,"..."));for(var i=0,length=folders.length;i',html+='
    ',html+='
    ',html+=name,html+="
    ",html+="
    ",html+='arrow_forward',html+=""}function getEditorHtml(options,systemInfo){var html="";if(html+='
    ',html+='
    ',!options.pathReadOnly){var instruction=options.instruction?options.instruction+"

    ":"";html+='
    ',html+=instruction,html+=Globalize.translate("MessageDirectoryPickerInstruction").replace("{0}","\\\\server").replace("{1}","\\\\192.168.1.101"),"synology"===(systemInfo.PackageName||"").toLowerCase()?(html+="
    ",html+="
    ",html+=''+Globalize.translate("LearnHowToCreateSynologyShares")+""):"bsd"===systemInfo.OperatingSystem.toLowerCase()?(html+="
    ",html+="
    ",html+=Globalize.translate("MessageDirectoryPickerBSDInstruction"),html+="
    ",html+=''+Globalize.translate("ButtonMoreInformation")+""):"linux"===systemInfo.OperatingSystem.toLowerCase()&&(html+="
    ",html+="
    ",html+=Globalize.translate("MessageDirectoryPickerLinuxInstruction"),html+="
    "),html+="
    "}html+='
    ',html+='
    ',html+='
    ';var labelKey=!0!==options.includeFiles?"LabelFolder":"LabelPath",readOnlyAttribute=options.pathReadOnly?" readonly":"";return html+='',html+="
    ",readOnlyAttribute||(html+=''),html+="
    ",readOnlyAttribute||(html+='
    '),options.enableNetworkSharePath&&(html+='
    ',html+='',html+='
    ',html+=Globalize.translate("LabelOptionalNetworkPathHelp"),html+="
    ",html+="
    "),html+='
    ',html+='",html+="
    ",html+="
    ",html+="
    ",html+="
    ",html+=""}function alertText(text){alertTextWithOptions({text:text})}function alertTextWithOptions(options){require(["alert"],function(alert){alert(options)})}function validatePath(path,validateWriteable,apiClient){return apiClient.ajax({type:"POST",url:apiClient.getUrl("Environment/ValidatePath"),data:{ValidateWriteable:validateWriteable,Path:path}}).catch(function(response){if(response){if(404===response.status)return alertText("The path could not be found. Please ensure the path is valid and try again."),Promise.reject();if(500===response.status)return alertText(validateWriteable?"Emby Server requires write access to this folder. Please ensure write access and try again.":"The path could not be found. Please ensure the path is valid and try again."),Promise.reject()}return Promise.resolve()})}function initEditor(content,options,fileOptions){content.addEventListener("click",function(e){var lnkPath=dom.parentWithClass(e.target,"lnkPath");if(lnkPath){var path=lnkPath.getAttribute("data-path");lnkPath.classList.contains("lnkFile")?content.querySelector("#txtDirectoryPickerPath").value=path:refreshDirectoryBrowser(content,path,fileOptions,!0)}}),content.addEventListener("click",function(e){if(dom.parentWithClass(e.target,"btnRefreshDirectories")){var path=content.querySelector("#txtDirectoryPickerPath").value;refreshDirectoryBrowser(content,path,fileOptions)}}),content.addEventListener("change",function(e){var txtDirectoryPickerPath=dom.parentWithTag(e.target,"INPUT");txtDirectoryPickerPath&&"txtDirectoryPickerPath"===txtDirectoryPickerPath.id&&refreshDirectoryBrowser(content,txtDirectoryPickerPath.value,fileOptions)}),content.querySelector("form").addEventListener("submit",function(e){if(options.callback){var networkSharePath=this.querySelector("#txtNetworkPath");networkSharePath=networkSharePath?networkSharePath.value:null;var path=this.querySelector("#txtDirectoryPickerPath").value;validatePath(path,options.validateWriteable,ApiClient).then(function(){options.callback(path,networkSharePath)})}return e.preventDefault(),e.stopPropagation(),!1})}function getDefaultPath(options){return options.path?Promise.resolve(options.path):ApiClient.getJSON(ApiClient.getUrl("Environment/DefaultDirectoryBrowser")).then(function(result){return result.Path||""},function(){return""})}function directoryBrowser(){var currentDialog,self=this;self.show=function(options){options=options||{};var fileOptions={includeDirectories:!0};null!=options.includeDirectories&&(fileOptions.includeDirectories=options.includeDirectories),null!=options.includeFiles&&(fileOptions.includeFiles=options.includeFiles),Promise.all([getSystemInfo(),getDefaultPath(options)]).then(function(responses){var systemInfo=responses[0],initialPath=responses[1],dlg=dialogHelper.createDialog({size:"medium-tall",removeOnClose:!0,scrollY:!1});dlg.classList.add("ui-body-a"),dlg.classList.add("background-theme-a"),dlg.classList.add("directoryPicker"),dlg.classList.add("formDialog");var html="";html+='
    ',html+='',html+='

    ',html+=options.header||Globalize.translate("HeaderSelectPath"),html+="

    ",html+="
    ",html+=getEditorHtml(options,systemInfo),dlg.innerHTML=html,initEditor(dlg,options,fileOptions),dlg.addEventListener("close",onDialogClosed),dialogHelper.open(dlg),dlg.querySelector(".btnCloseDialog").addEventListener("click",function(){dialogHelper.close(dlg)}),currentDialog=dlg,dlg.querySelector("#txtDirectoryPickerPath").value=initialPath;var txtNetworkPath=dlg.querySelector("#txtNetworkPath");txtNetworkPath&&(txtNetworkPath.value=options.networkSharePath||""),options.pathReadOnly||refreshDirectoryBrowser(dlg,initialPath,fileOptions,!0)})},self.close=function(){currentDialog&&dialogHelper.close(currentDialog)}}var systemInfo;return directoryBrowser}); \ No newline at end of file +define(["loading", "dialogHelper", "dom", "listViewStyle", "emby-input", "emby-button", "paper-icon-button-light", "css!./directorybrowser", "formDialogStyle", "emby-linkbutton"], function(loading, dialogHelper, dom) { + "use strict"; + + function getSystemInfo() { + return systemInfo ? Promise.resolve(systemInfo) : ApiClient.getPublicSystemInfo().then(function(info) { + return systemInfo = info, info + }) + } + + function onDialogClosed() { + loading.hide() + } + + function refreshDirectoryBrowser(page, path, fileOptions, updatePathOnError) { + if (path && "string" != typeof path) throw new Error("invalid path"); + loading.show(); + var promises = []; + "Network" === path ? promises.push(ApiClient.getNetworkDevices()) : path ? (promises.push(ApiClient.getDirectoryContents(path, fileOptions)), promises.push(ApiClient.getParentPath(path))) : promises.push(ApiClient.getDrives()), Promise.all(promises).then(function(responses) { + var folders = responses[0], + parentPath = responses[1] || ""; + page.querySelector("#txtDirectoryPickerPath").value = path || ""; + var html = ""; + path && (html += getItem("lnkPath lnkDirectory", "", parentPath, "...")); + for (var i = 0, length = folders.length; i < length; i++) { + var folder = folders[i]; + html += getItem("File" === folder.Type ? "lnkPath lnkFile" : "lnkPath lnkDirectory", folder.Type, folder.Path, folder.Name) + } + path || (html += getItem("lnkPath lnkDirectory", "", "Network", Globalize.translate("ButtonNetwork"))), page.querySelector(".results").innerHTML = html, loading.hide() + }, function() { + updatePathOnError && (page.querySelector("#txtDirectoryPickerPath").value = ""), page.querySelector(".results").innerHTML = "", loading.hide() + }) + } + + function getItem(cssClass, type, path, name) { + var html = ""; + return html += '
    ', html += '
    ', html += '
    ', html += name, html += "
    ", html += "
    ", html += 'arrow_forward', html += "
    " + } + + function getEditorHtml(options, systemInfo) { + var html = ""; + if (html += '
    ', html += '
    ', !options.pathReadOnly) { + var instruction = options.instruction ? options.instruction + "

    " : ""; + html += '
    ', html += instruction, html += Globalize.translate("MessageDirectoryPickerInstruction").replace("{0}", "\\\\server").replace("{1}", "\\\\192.168.1.101"), "synology" === (systemInfo.PackageName || "").toLowerCase() ? (html += "
    ", html += "
    ", html += '' + Globalize.translate("LearnHowToCreateSynologyShares") + "") : "bsd" === systemInfo.OperatingSystem.toLowerCase() ? (html += "
    ", html += "
    ", html += Globalize.translate("MessageDirectoryPickerBSDInstruction"), html += "
    ", html += '' + Globalize.translate("ButtonMoreInformation") + "") : "linux" === systemInfo.OperatingSystem.toLowerCase() && (html += "
    ", html += "
    ", html += Globalize.translate("MessageDirectoryPickerLinuxInstruction"), html += "
    "), html += "
    " + } + html += '
    ', html += '
    ', html += '
    '; + var labelKey = !0 !== options.includeFiles ? "LabelFolder" : "LabelPath", + readOnlyAttribute = options.pathReadOnly ? " readonly" : ""; + return html += '', html += "
    ", readOnlyAttribute || (html += ''), html += "
    ", readOnlyAttribute || (html += '
    '), options.enableNetworkSharePath && (html += '
    ', html += '', html += '
    ', html += Globalize.translate("LabelOptionalNetworkPathHelp"), html += "
    ", html += "
    "), html += '
    ', html += '", html += "
    ", html += "
    ", html += "
    ", html += "
    ", html += "" + } + + function alertText(text) { + alertTextWithOptions({ + text: text + }) + } + + function alertTextWithOptions(options) { + require(["alert"], function(alert) { + alert(options) + }) + } + + function validatePath(path, validateWriteable, apiClient) { + return apiClient.ajax({ + type: "POST", + url: apiClient.getUrl("Environment/ValidatePath"), + data: { + ValidateWriteable: validateWriteable, + Path: path + } + }).catch(function(response) { + if (response) { + if (404 === response.status) return alertText("The path could not be found. Please ensure the path is valid and try again."), Promise.reject(); + if (500 === response.status) return alertText(validateWriteable ? "Emby Server requires write access to this folder. Please ensure write access and try again." : "The path could not be found. Please ensure the path is valid and try again."), Promise.reject() + } + return Promise.resolve() + }) + } + + function initEditor(content, options, fileOptions) { + content.addEventListener("click", function(e) { + var lnkPath = dom.parentWithClass(e.target, "lnkPath"); + if (lnkPath) { + var path = lnkPath.getAttribute("data-path"); + lnkPath.classList.contains("lnkFile") ? content.querySelector("#txtDirectoryPickerPath").value = path : refreshDirectoryBrowser(content, path, fileOptions, !0) + } + }), content.addEventListener("click", function(e) { + if (dom.parentWithClass(e.target, "btnRefreshDirectories")) { + var path = content.querySelector("#txtDirectoryPickerPath").value; + refreshDirectoryBrowser(content, path, fileOptions) + } + }), content.addEventListener("change", function(e) { + var txtDirectoryPickerPath = dom.parentWithTag(e.target, "INPUT"); + txtDirectoryPickerPath && "txtDirectoryPickerPath" === txtDirectoryPickerPath.id && refreshDirectoryBrowser(content, txtDirectoryPickerPath.value, fileOptions) + }), content.querySelector("form").addEventListener("submit", function(e) { + if (options.callback) { + var networkSharePath = this.querySelector("#txtNetworkPath"); + networkSharePath = networkSharePath ? networkSharePath.value : null; + var path = this.querySelector("#txtDirectoryPickerPath").value; + validatePath(path, options.validateWriteable, ApiClient).then(function() { + options.callback(path, networkSharePath) + }) + } + return e.preventDefault(), e.stopPropagation(), !1 + }) + } + + function getDefaultPath(options) { + return options.path ? Promise.resolve(options.path) : ApiClient.getJSON(ApiClient.getUrl("Environment/DefaultDirectoryBrowser")).then(function(result) { + return result.Path || "" + }, function() { + return "" + }) + } + + function directoryBrowser() { + var currentDialog, self = this; + self.show = function(options) { + options = options || {}; + var fileOptions = { + includeDirectories: !0 + }; + null != options.includeDirectories && (fileOptions.includeDirectories = options.includeDirectories), null != options.includeFiles && (fileOptions.includeFiles = options.includeFiles), Promise.all([getSystemInfo(), getDefaultPath(options)]).then(function(responses) { + var systemInfo = responses[0], + initialPath = responses[1], + dlg = dialogHelper.createDialog({ + size: "medium-tall", + removeOnClose: !0, + scrollY: !1 + }); + dlg.classList.add("ui-body-a"), dlg.classList.add("background-theme-a"), dlg.classList.add("directoryPicker"), dlg.classList.add("formDialog"); + var html = ""; + html += '
    ', html += '', html += '

    ', html += options.header || Globalize.translate("HeaderSelectPath"), html += "

    ", html += "
    ", html += getEditorHtml(options, systemInfo), dlg.innerHTML = html, initEditor(dlg, options, fileOptions), dlg.addEventListener("close", onDialogClosed), dialogHelper.open(dlg), dlg.querySelector(".btnCloseDialog").addEventListener("click", function() { + dialogHelper.close(dlg) + }), currentDialog = dlg, dlg.querySelector("#txtDirectoryPickerPath").value = initialPath; + var txtNetworkPath = dlg.querySelector("#txtNetworkPath"); + txtNetworkPath && (txtNetworkPath.value = options.networkSharePath || ""), options.pathReadOnly || refreshDirectoryBrowser(dlg, initialPath, fileOptions, !0) + }) + }, self.close = function() { + currentDialog && dialogHelper.close(currentDialog) + } + } + var systemInfo; + return directoryBrowser +}); \ No newline at end of file diff --git a/dashboard-ui/components/favoriteitems.js b/dashboard-ui/components/favoriteitems.js index 476ec949a5..9091f70665 100644 --- a/dashboard-ui/components/favoriteitems.js +++ b/dashboard-ui/components/favoriteitems.js @@ -1 +1,177 @@ -define(["loading","libraryBrowser","cardBuilder","dom","apphost","imageLoader","globalize","layoutManager","scrollStyles","emby-itemscontainer"],function(loading,libraryBrowser,cardBuilder,dom,appHost,imageLoader,globalize,layoutManager){"use strict";function enableScrollX(){return!layoutManager.desktop}function getThumbShape(){return enableScrollX()?"overflowBackdrop":"backdrop"}function getPosterShape(){return enableScrollX()?"overflowPortrait":"portrait"}function getSquareShape(){return enableScrollX()?"overflowSquare":"square"}function getSections(){return[{name:"HeaderFavoriteMovies",types:"Movie",id:"favoriteMovies",shape:getPosterShape(),showTitle:!1,overlayPlayButton:!0},{name:"HeaderFavoriteShows",types:"Series",id:"favoriteShows",shape:getPosterShape(),showTitle:!1,overlayPlayButton:!0},{name:"HeaderFavoriteEpisodes",types:"Episode",id:"favoriteEpisode",shape:getThumbShape(),preferThumb:!1,showTitle:!0,showParentTitle:!0,overlayPlayButton:!0,overlayText:!1,centerText:!0},{name:"HeaderFavoriteVideos",types:"Video,MusicVideo",id:"favoriteVideos",shape:getThumbShape(),preferThumb:!0,showTitle:!0,overlayPlayButton:!0,overlayText:!1,centerText:!0},{name:"HeaderFavoriteGames",types:"Game",id:"favoriteGames",shape:getSquareShape(),preferThumb:!1,showTitle:!0},{name:"HeaderFavoriteArtists",types:"MusicArtist",id:"favoriteArtists",shape:getSquareShape(),preferThumb:!1,showTitle:!0,overlayText:!1,showParentTitle:!1,centerText:!0,overlayPlayButton:!0,coverImage:!0},{name:"HeaderFavoriteAlbums",types:"MusicAlbum",id:"favoriteAlbums",shape:getSquareShape(),preferThumb:!1,showTitle:!0,overlayText:!1,showParentTitle:!0,centerText:!0,overlayPlayButton:!0,coverImage:!0},{name:"HeaderFavoriteSongs",types:"Audio",id:"favoriteSongs",shape:getSquareShape(),preferThumb:!1,showTitle:!0,overlayText:!1,showParentTitle:!0,centerText:!0,overlayMoreButton:!0,action:"instantmix",coverImage:!0}]}function loadSection(elem,userId,topParentId,section,isSingleSection){var screenWidth=dom.getWindowSize().innerWidth,options={SortBy:"SortName",SortOrder:"Ascending",Filters:"IsFavorite",Recursive:!0,Fields:"PrimaryImageAspectRatio,BasicSyncInfo",CollapseBoxSetItems:!1,ExcludeLocationTypes:"Virtual",EnableTotalRecordCount:!1};topParentId&&(options.ParentId=topParentId),isSingleSection||(options.Limit=screenWidth>=1920?10:screenWidth>=1440?8:6,enableScrollX()&&(options.Limit=20));var promise;return"MusicArtist"===section.types?promise=ApiClient.getArtists(userId,options):(options.IncludeItemTypes=section.types,promise=ApiClient.getItems(userId,options)),promise.then(function(result){var html="";if(result.Items.length){if(html+='
    ',!layoutManager.tv&&options.Limit&&result.Items.length>=options.Limit){html+='',html+='

    ',html+=globalize.translate(section.name),html+="

    ",html+='',html+="
    "}else html+='

    '+globalize.translate(section.name)+"

    ";if(html+="
    ",enableScrollX()){var scrollXClass="scrollX hiddenScrollX";layoutManager.tv&&(scrollXClass+=" smoothScrollX"),html+='
    '}else html+='
    ';var supportsImageAnalysis=appHost.supports("imageanalysis"),cardLayout=(appHost.preferVisualCards||supportsImageAnalysis)&§ion.autoCardLayout&§ion.showTitle;cardLayout=!1,html+=cardBuilder.getCardsHtml(result.Items,{preferThumb:section.preferThumb,shape:section.shape,centerText:section.centerText&&!cardLayout,overlayText:!1!==section.overlayText,showTitle:section.showTitle,showParentTitle:section.showParentTitle,scalable:!0,coverImage:section.coverImage,overlayPlayButton:section.overlayPlayButton,overlayMoreButton:section.overlayMoreButton&&!cardLayout,action:section.action,allowBottomPadding:!enableScrollX(),cardLayout:cardLayout,vibrant:supportsImageAnalysis&&cardLayout}),html+="
    "}elem.innerHTML=html,imageLoader.lazyChildren(elem)})}function loadSections(page,userId,topParentId,types){loading.show();var sections=getSections(),sectionid=getParameterByName("sectionid");sectionid&&(sections=sections.filter(function(s){return s.id===sectionid})),types&&(sections=sections.filter(function(s){return-1!==types.indexOf(s.id)}));var i,length,elem=page.querySelector(".favoriteSections");if(!elem.innerHTML){var html="";for(i=0,length=sections.length;i
    ';elem.innerHTML=html}var promises=[];for(i=0,length=sections.length;i= 1920 ? 10 : screenWidth >= 1440 ? 8 : 6, enableScrollX() && (options.Limit = 20)); + var promise; + return "MusicArtist" === section.types ? promise = ApiClient.getArtists(userId, options) : (options.IncludeItemTypes = section.types, promise = ApiClient.getItems(userId, options)), promise.then(function(result) { + var html = ""; + if (result.Items.length) { + if (html += '
    ', !layoutManager.tv && options.Limit && result.Items.length >= options.Limit) { + html += '', html += '

    ', html += globalize.translate(section.name), html += "

    ", html += '', html += "
    " + } else html += '

    ' + globalize.translate(section.name) + "

    "; + if (html += "
    ", enableScrollX()) { + var scrollXClass = "scrollX hiddenScrollX"; + layoutManager.tv && (scrollXClass += " smoothScrollX"), html += '
    ' + } else html += '
    '; + var supportsImageAnalysis = appHost.supports("imageanalysis"), + cardLayout = (appHost.preferVisualCards || supportsImageAnalysis) && section.autoCardLayout && section.showTitle; + cardLayout = !1, html += cardBuilder.getCardsHtml(result.Items, { + preferThumb: section.preferThumb, + shape: section.shape, + centerText: section.centerText && !cardLayout, + overlayText: !1 !== section.overlayText, + showTitle: section.showTitle, + showParentTitle: section.showParentTitle, + scalable: !0, + coverImage: section.coverImage, + overlayPlayButton: section.overlayPlayButton, + overlayMoreButton: section.overlayMoreButton && !cardLayout, + action: section.action, + allowBottomPadding: !enableScrollX(), + cardLayout: cardLayout, + vibrant: supportsImageAnalysis && cardLayout + }), html += "
    " + } + elem.innerHTML = html, imageLoader.lazyChildren(elem) + }) + } + + function loadSections(page, userId, topParentId, types) { + loading.show(); + var sections = getSections(), + sectionid = getParameterByName("sectionid"); + sectionid && (sections = sections.filter(function(s) { + return s.id === sectionid + })), types && (sections = sections.filter(function(s) { + return -1 !== types.indexOf(s.id) + })); + var i, length, elem = page.querySelector(".favoriteSections"); + if (!elem.innerHTML) { + var html = ""; + for (i = 0, length = sections.length; i < length; i++) html += '
    '; + elem.innerHTML = html + } + var promises = []; + for (i = 0, length = sections.length; i < length; i++) { + var section = sections[i]; + elem = page.querySelector(".section" + section.id), promises.push(loadSection(elem, userId, topParentId, section, 1 === sections.length)) + } + Promise.all(promises).then(function() { + loading.hide() + }) + } + return { + render: loadSections + } +}); \ No newline at end of file diff --git a/dashboard-ui/components/filterdialog/filterdialog.js b/dashboard-ui/components/filterdialog/filterdialog.js index 17d79f670f..560919889e 100644 --- a/dashboard-ui/components/filterdialog/filterdialog.js +++ b/dashboard-ui/components/filterdialog/filterdialog.js @@ -1 +1,198 @@ -define(["dialogHelper","globalize","connectionManager","events","browser","require","emby-checkbox","emby-collapse","css!./style"],function(dialogHelper,globalize,connectionManager,events,browser,require){"use strict";function renderOptions(context,selector,cssClass,items,isCheckedFn){var elem=context.querySelector(selector);items.length?elem.classList.remove("hide"):elem.classList.add("hide");var html="";html+='
    ',html+=items.map(function(filter){var itemHtml="",checkedHtml=isCheckedFn(filter)?" checked":"";return itemHtml+=""}).join(""),html+="
    ",elem.querySelector(".filterOptions").innerHTML=html}function renderFilters(context,result,query){result.Tags&&(result.Tags.length=Math.min(result.Tags.length,50)),renderOptions(context,".genreFilters","chkGenreFilter",result.Genres,function(i){return-1!=("|"+(query.Genres||"")+"|").indexOf("|"+i+"|")}),renderOptions(context,".officialRatingFilters","chkOfficialRatingFilter",result.OfficialRatings,function(i){return-1!=("|"+(query.OfficialRatings||"")+"|").indexOf("|"+i+"|")}),renderOptions(context,".tagFilters","chkTagFilter",result.Tags,function(i){return-1!=("|"+(query.Tags||"")+"|").indexOf("|"+i+"|")}),renderOptions(context,".yearFilters","chkYearFilter",result.Years,function(i){return-1!=(","+(query.Years||"")+",").indexOf(","+i+",")})}function loadDynamicFilters(context,apiClient,userId,itemQuery){return apiClient.getJSON(apiClient.getUrl("Items/Filters",{UserId:userId,ParentId:itemQuery.ParentId,IncludeItemTypes:itemQuery.IncludeItemTypes})).then(function(result){renderFilters(context,result,itemQuery)})}function updateFilterControls(context,options){var elems,i,length,query=options.query;if("livetvchannels"==options.mode)context.querySelector(".chkFavorite").checked=1==query.IsFavorite,context.querySelector(".chkLikes").checked=1==query.IsLiked,context.querySelector(".chkDislikes").checked=1==query.IsDisliked;else for(elems=context.querySelectorAll(".chkStandardFilter"),i=0,length=elems.length;i', itemHtml += "" + filter + "", itemHtml += "" + }).join(""), html += "
    ", elem.querySelector(".filterOptions").innerHTML = html + } + + function renderFilters(context, result, query) { + result.Tags && (result.Tags.length = Math.min(result.Tags.length, 50)), renderOptions(context, ".genreFilters", "chkGenreFilter", result.Genres, function(i) { + return -1 != ("|" + (query.Genres || "") + "|").indexOf("|" + i + "|") + }), renderOptions(context, ".officialRatingFilters", "chkOfficialRatingFilter", result.OfficialRatings, function(i) { + return -1 != ("|" + (query.OfficialRatings || "") + "|").indexOf("|" + i + "|") + }), renderOptions(context, ".tagFilters", "chkTagFilter", result.Tags, function(i) { + return -1 != ("|" + (query.Tags || "") + "|").indexOf("|" + i + "|") + }), renderOptions(context, ".yearFilters", "chkYearFilter", result.Years, function(i) { + return -1 != ("," + (query.Years || "") + ",").indexOf("," + i + ",") + }) + } + + function loadDynamicFilters(context, apiClient, userId, itemQuery) { + return apiClient.getJSON(apiClient.getUrl("Items/Filters", { + UserId: userId, + ParentId: itemQuery.ParentId, + IncludeItemTypes: itemQuery.IncludeItemTypes + })).then(function(result) { + renderFilters(context, result, itemQuery) + }) + } + + function updateFilterControls(context, options) { + var elems, i, length, query = options.query; + if ("livetvchannels" == options.mode) context.querySelector(".chkFavorite").checked = 1 == query.IsFavorite, context.querySelector(".chkLikes").checked = 1 == query.IsLiked, context.querySelector(".chkDislikes").checked = 1 == query.IsDisliked; + else + for (elems = context.querySelectorAll(".chkStandardFilter"), i = 0, length = elems.length; i < length; i++) { + var chkStandardFilter = elems[i], + filters = "," + (query.Filters || ""), + filterName = chkStandardFilter.getAttribute("data-filter"); + chkStandardFilter.checked = -1 != filters.indexOf("," + filterName) + } + for (elems = context.querySelectorAll(".chkVideoTypeFilter"), i = 0, length = elems.length; i < length; i++) { + var chkVideoTypeFilter = elems[i], + filters = "," + (query.VideoTypes || ""), + filterName = chkVideoTypeFilter.getAttribute("data-filter"); + chkVideoTypeFilter.checked = -1 != filters.indexOf("," + filterName) + } + for (context.querySelector(".chk3DFilter").checked = 1 == query.Is3D, context.querySelector(".chkHDFilter").checked = 1 == query.IsHD, context.querySelector(".chk4KFilter").checked = 1 == query.Is4K, context.querySelector(".chkSDFilter").checked = 1 == query.IsHD, context.querySelector("#chkSubtitle").checked = 1 == query.HasSubtitles, context.querySelector("#chkTrailer").checked = 1 == query.HasTrailer, context.querySelector("#chkThemeSong").checked = 1 == query.HasThemeSong, context.querySelector("#chkThemeVideo").checked = 1 == query.HasThemeVideo, context.querySelector("#chkSpecialFeature").checked = 1 == query.HasSpecialFeature, context.querySelector("#chkSpecialEpisode").checked = 0 == query.ParentIndexNumber, context.querySelector("#chkMissingEpisode").checked = 1 == query.IsMissing, context.querySelector("#chkFutureEpisode").checked = 1 == query.IsUnaired, i = 0, length = elems.length; i < length; i++) { + var chkStatus = elems[i], + filters = "," + (query.SeriesStatus || ""), + filterName = chkStatus.getAttribute("data-filter"); + chkStatus.checked = -1 != filters.indexOf("," + filterName) + } + } + + function triggerChange(instance) { + events.trigger(instance, "filterchange") + } + + function parentWithClass(elem, className) { + for (; !elem.classList || !elem.classList.contains(className);) + if (!(elem = elem.parentNode)) return null; + return elem + } + + function setVisibility(context, options) { + "livetvchannels" != options.mode && "albums" != options.mode && "artists" != options.mode && "albumartists" != options.mode && "songs" != options.mode || hideByClass(context, "videoStandard"), enableDynamicFilters(options.mode) && (context.querySelector(".genreFilters").classList.remove("hide"), context.querySelector(".officialRatingFilters").classList.remove("hide"), context.querySelector(".tagFilters").classList.remove("hide"), context.querySelector(".yearFilters").classList.remove("hide")), "movies" != options.mode && "episodes" != options.mode || context.querySelector(".videoTypeFilters").classList.remove("hide"), options.mode, "movies" != options.mode && "series" != options.mode && "games" != options.mode && "episodes" != options.mode || context.querySelector(".features").classList.remove("hide"), "series" == options.mode && context.querySelector(".seriesStatus").classList.remove("hide"), "episodes" == options.mode && showByClass(context, "episodeFilter") + } + + function showByClass(context, className) { + for (var elems = context.querySelectorAll("." + className), i = 0, length = elems.length; i < length; i++) elems[i].classList.remove("hide") + } + + function hideByClass(context, className) { + for (var elems = context.querySelectorAll("." + className), i = 0, length = elems.length; i < length; i++) elems[i].classList.add("hide") + } + + function enableDynamicFilters(mode) { + return "movies" == mode || "games" == mode || "series" == mode || "albums" == mode || "albumartists" == mode || "artists" == mode || "songs" == mode || "episodes" == mode + } + return function(options) { + function onFavoriteChange() { + var query = options.query; + query.StartIndex = 0, query.IsFavorite = !!this.checked || null, triggerChange(self) + } + + function onStandardFilterChange() { + var query = options.query, + filterName = this.getAttribute("data-filter"), + filters = query.Filters || ""; + filters = ("," + filters).replace("," + filterName, "").substring(1), this.checked && (filters = filters ? filters + "," + filterName : filterName), query.StartIndex = 0, query.Filters = filters, triggerChange(self) + } + + function onVideoTypeFilterChange() { + var query = options.query, + filterName = this.getAttribute("data-filter"), + filters = query.VideoTypes || ""; + filters = ("," + filters).replace("," + filterName, "").substring(1), this.checked && (filters = filters ? filters + "," + filterName : filterName), query.StartIndex = 0, query.VideoTypes = filters, triggerChange(self) + } + + function onStatusChange() { + var query = options.query, + filterName = this.getAttribute("data-filter"), + filters = query.SeriesStatus || ""; + filters = ("," + filters).replace("," + filterName, "").substring(1), this.checked && (filters = filters ? filters + "," + filterName : filterName), query.SeriesStatus = filters, query.StartIndex = 0, triggerChange(self) + } + + function bindEvents(context) { + var elems, i, length, query = options.query; + if ("livetvchannels" == options.mode) { + for (elems = context.querySelectorAll(".chkFavorite"), i = 0, length = elems.length; i < length; i++) elems[i].addEventListener("change", onFavoriteChange); + context.querySelector(".chkLikes").addEventListener("change", function() { + query.StartIndex = 0, query.IsLiked = !!this.checked || null, triggerChange(self) + }), context.querySelector(".chkDislikes").addEventListener("change", function() { + query.StartIndex = 0, query.IsDisliked = !!this.checked || null, triggerChange(self) + }) + } else + for (elems = context.querySelectorAll(".chkStandardFilter"), i = 0, length = elems.length; i < length; i++) elems[i].addEventListener("change", onStandardFilterChange); + for (elems = context.querySelectorAll(".chkVideoTypeFilter"), i = 0, length = elems.length; i < length; i++) elems[i].addEventListener("change", onVideoTypeFilterChange); + for (context.querySelector(".chk3DFilter").addEventListener("change", function() { + query.StartIndex = 0, query.Is3D = !!this.checked || null, triggerChange(self) + }), context.querySelector(".chk4KFilter").addEventListener("change", function() { + query.StartIndex = 0, query.Is4K = !!this.checked || null, triggerChange(self) + }), context.querySelector(".chkHDFilter").addEventListener("change", function() { + query.StartIndex = 0, query.IsHD = !!this.checked || null, triggerChange(self) + }), context.querySelector(".chkSDFilter").addEventListener("change", function() { + query.StartIndex = 0, query.IsHD = !this.checked && null, triggerChange(self) + }), elems = context.querySelectorAll(".chkStatus"), i = 0, length = elems.length; i < length; i++) elems[i].addEventListener("change", onStatusChange); + context.querySelector("#chkTrailer").addEventListener("change", function() { + query.StartIndex = 0, query.HasTrailer = !!this.checked || null, triggerChange(self) + }), context.querySelector("#chkThemeSong").addEventListener("change", function() { + query.StartIndex = 0, query.HasThemeSong = !!this.checked || null, triggerChange(self) + }), context.querySelector("#chkSpecialFeature").addEventListener("change", function() { + query.StartIndex = 0, query.HasSpecialFeature = !!this.checked || null, triggerChange(self) + }), context.querySelector("#chkThemeVideo").addEventListener("change", function() { + query.StartIndex = 0, query.HasThemeVideo = !!this.checked || null, triggerChange(self) + }), context.querySelector("#chkMissingEpisode").addEventListener("change", function() { + query.StartIndex = 0, this.checked ? (query.IsMissing = !0, query.IsUnaired = !1) : (query.IsMissing = !1, query.IsUnaired = context.querySelector("#chkFutureEpisode").checked || null), triggerChange(self) + }), context.querySelector("#chkSpecialEpisode").addEventListener("change", function() { + query.StartIndex = 0, query.ParentIndexNumber = this.checked ? 0 : null, triggerChange(self) + }), context.querySelector("#chkFutureEpisode").addEventListener("change", function() { + query.StartIndex = 0, this.checked ? (query.IsUnaired = !0, query.IsMissing = null) : (query.IsUnaired = null, query.IsMissing = context.querySelector("#chkMissingEpisode").checked), triggerChange(self) + }), context.querySelector("#chkSubtitle").addEventListener("change", function() { + query.StartIndex = 0, query.HasSubtitles = !!this.checked || null, triggerChange(self) + }), context.addEventListener("change", function(e) { + var chkGenreFilter = parentWithClass(e.target, "chkGenreFilter"); + if (chkGenreFilter) { + var filterName = chkGenreFilter.getAttribute("data-filter"), + filters = query.Genres || "", + delimiter = "|"; + return filters = (delimiter + filters).replace(delimiter + filterName, "").substring(1), chkGenreFilter.checked && (filters = filters ? filters + delimiter + filterName : filterName), query.StartIndex = 0, query.Genres = filters, void triggerChange(self) + } + var chkTagFilter = parentWithClass(e.target, "chkTagFilter"); + if (chkTagFilter) { + var filterName = chkTagFilter.getAttribute("data-filter"), + filters = query.Tags || "", + delimiter = "|"; + return filters = (delimiter + filters).replace(delimiter + filterName, "").substring(1), chkTagFilter.checked && (filters = filters ? filters + delimiter + filterName : filterName), query.StartIndex = 0, query.Tags = filters, void triggerChange(self) + } + var chkYearFilter = parentWithClass(e.target, "chkYearFilter"); + if (chkYearFilter) { + var filterName = chkYearFilter.getAttribute("data-filter"), + filters = query.Years || "", + delimiter = ","; + return filters = (delimiter + filters).replace(delimiter + filterName, "").substring(1), chkYearFilter.checked && (filters = filters ? filters + delimiter + filterName : filterName), query.StartIndex = 0, query.Years = filters, void triggerChange(self) + } + var chkOfficialRatingFilter = parentWithClass(e.target, "chkOfficialRatingFilter"); + if (chkOfficialRatingFilter) { + var filterName = chkOfficialRatingFilter.getAttribute("data-filter"), + filters = query.OfficialRatings || "", + delimiter = "|"; + return filters = (delimiter + filters).replace(delimiter + filterName, "").substring(1), chkOfficialRatingFilter.checked && (filters = filters ? filters + delimiter + filterName : filterName), query.StartIndex = 0, query.OfficialRatings = filters, void triggerChange(self) + } + }) + } + var self = this; + self.show = function() { + return new Promise(function(resolve, reject) { + require(["text!./filterdialog.template.html"], function(template) { + var dlg = dialogHelper.createDialog({ + removeOnClose: !0, + modal: !1 + }); + if (dlg.classList.add("ui-body-a"), dlg.classList.add("background-theme-a"), dlg.classList.add("formDialog"), dlg.classList.add("filterDialog"), dlg.innerHTML = globalize.translateDocument(template), setVisibility(dlg, options), dialogHelper.open(dlg), dlg.addEventListener("close", resolve), updateFilterControls(dlg, options), bindEvents(dlg), enableDynamicFilters(options.mode)) { + dlg.classList.add("dynamicFilterDialog"); + var apiClient = connectionManager.getApiClient(options.serverId); + loadDynamicFilters(dlg, apiClient, apiClient.getCurrentUserId(), options.query) + } + }) + }) + } + } +}); \ No newline at end of file diff --git a/dashboard-ui/components/groupedcards.js b/dashboard-ui/components/groupedcards.js index 417214a1c6..a6b1946526 100644 --- a/dashboard-ui/components/groupedcards.js +++ b/dashboard-ui/components/groupedcards.js @@ -1 +1,32 @@ -define(["dom","appRouter","connectionManager"],function(dom,appRouter,connectionManager){"use strict";function onGroupedCardClick(e,card){var itemId=card.getAttribute("data-id"),serverId=card.getAttribute("data-serverid"),apiClient=connectionManager.getApiClient(serverId),userId=apiClient.getCurrentUserId(),playedIndicator=card.querySelector(".playedIndicator"),playedIndicatorHtml=playedIndicator?playedIndicator.innerHTML:null,options={Limit:parseInt(playedIndicatorHtml||"10"),Fields:"PrimaryImageAspectRatio,DateCreated",ParentId:itemId,GroupItems:!1},actionableParent=dom.parentWithTag(e.target,["A","BUTTON","INPUT"]);if(!actionableParent||actionableParent.classList.contains("cardContent"))return apiClient.getJSON(apiClient.getUrl("Users/"+userId+"/Items/Latest",options)).then(function(items){if(1===items.length)return void appRouter.showItem(items[0]);var url="itemdetails.html?id="+itemId+"&serverId="+serverId;Dashboard.navigate(url)}),e.stopPropagation(),e.preventDefault(),!1}function onItemsContainerClick(e){var groupedCard=dom.parentWithClass(e.target,"groupedCard");groupedCard&&onGroupedCardClick(e,groupedCard)}return{onItemsContainerClick:onItemsContainerClick}}); \ No newline at end of file +define(["dom", "appRouter", "connectionManager"], function(dom, appRouter, connectionManager) { + "use strict"; + + function onGroupedCardClick(e, card) { + var itemId = card.getAttribute("data-id"), + serverId = card.getAttribute("data-serverid"), + apiClient = connectionManager.getApiClient(serverId), + userId = apiClient.getCurrentUserId(), + playedIndicator = card.querySelector(".playedIndicator"), + playedIndicatorHtml = playedIndicator ? playedIndicator.innerHTML : null, + options = { + Limit: parseInt(playedIndicatorHtml || "10"), + Fields: "PrimaryImageAspectRatio,DateCreated", + ParentId: itemId, + GroupItems: !1 + }, + actionableParent = dom.parentWithTag(e.target, ["A", "BUTTON", "INPUT"]); + if (!actionableParent || actionableParent.classList.contains("cardContent")) return apiClient.getJSON(apiClient.getUrl("Users/" + userId + "/Items/Latest", options)).then(function(items) { + if (1 === items.length) return void appRouter.showItem(items[0]); + var url = "itemdetails.html?id=" + itemId + "&serverId=" + serverId; + Dashboard.navigate(url) + }), e.stopPropagation(), e.preventDefault(), !1 + } + + function onItemsContainerClick(e) { + var groupedCard = dom.parentWithClass(e.target, "groupedCard"); + groupedCard && onGroupedCardClick(e, groupedCard) + } + return { + onItemsContainerClick: onItemsContainerClick + } +}); \ No newline at end of file diff --git a/dashboard-ui/components/guestinviter/connectlink.js b/dashboard-ui/components/guestinviter/connectlink.js index 51f817f563..d226955df4 100644 --- a/dashboard-ui/components/guestinviter/connectlink.js +++ b/dashboard-ui/components/guestinviter/connectlink.js @@ -1 +1,32 @@ -define(["dialogHelper","connectHelper","emby-input","emby-button","emby-collapse","paper-icon-button-light","formDialogStyle","emby-linkbutton"],function(dialogHelper,connectHelper){"use strict";return{show:function(){return new Promise(function(resolve,reject){var xhr=new XMLHttpRequest;xhr.open("GET","components/guestinviter/connectlink.template.html",!0),xhr.onload=function(e){var template=this.response,dlg=dialogHelper.createDialog({removeOnClose:!0,size:"small"});dlg.classList.add("ui-body-a"),dlg.classList.add("background-theme-a"),dlg.classList.add("formDialog");var html="";html+=Globalize.translateDocument(template),dlg.innerHTML=html,dialogHelper.open(dlg),dlg.addEventListener("close",function(){dlg.submitted?resolve():reject()}),dlg.querySelector(".btnCancel").addEventListener("click",function(e){dialogHelper.close(dlg)}),dlg.querySelector("form").addEventListener("submit",function(e){return ApiClient.getCurrentUser().then(function(user){connectHelper.updateUserLink(ApiClient,user,dlg.querySelector("#txtConnectUsername").value).then(function(){dialogHelper.close(dlg)},function(){dialogHelper.close(dlg)})}),e.preventDefault(),!1})},xhr.send()})}}}); \ No newline at end of file +define(["dialogHelper", "connectHelper", "emby-input", "emby-button", "emby-collapse", "paper-icon-button-light", "formDialogStyle", "emby-linkbutton"], function(dialogHelper, connectHelper) { + "use strict"; + return { + show: function() { + return new Promise(function(resolve, reject) { + var xhr = new XMLHttpRequest; + xhr.open("GET", "components/guestinviter/connectlink.template.html", !0), xhr.onload = function(e) { + var template = this.response, + dlg = dialogHelper.createDialog({ + removeOnClose: !0, + size: "small" + }); + dlg.classList.add("ui-body-a"), dlg.classList.add("background-theme-a"), dlg.classList.add("formDialog"); + var html = ""; + html += Globalize.translateDocument(template), dlg.innerHTML = html, dialogHelper.open(dlg), dlg.addEventListener("close", function() { + dlg.submitted ? resolve() : reject() + }), dlg.querySelector(".btnCancel").addEventListener("click", function(e) { + dialogHelper.close(dlg) + }), dlg.querySelector("form").addEventListener("submit", function(e) { + return ApiClient.getCurrentUser().then(function(user) { + connectHelper.updateUserLink(ApiClient, user, dlg.querySelector("#txtConnectUsername").value).then(function() { + dialogHelper.close(dlg) + }, function() { + dialogHelper.close(dlg) + }) + }), e.preventDefault(), !1 + }) + }, xhr.send() + }) + } + } +}); \ No newline at end of file diff --git a/dashboard-ui/components/guestinviter/guestinviter.js b/dashboard-ui/components/guestinviter/guestinviter.js index 3af15284ee..c5a076b1d4 100644 --- a/dashboard-ui/components/guestinviter/guestinviter.js +++ b/dashboard-ui/components/guestinviter/guestinviter.js @@ -1 +1,58 @@ -define(["dialogHelper","loading","require","emby-input","emby-button","emby-checkbox","paper-icon-button-light","formDialogStyle","emby-linkbutton"],function(dialogHelper,loading,require){"use strict";function renderLibrarySharingList(context,result){var folderHtml="";folderHtml+=result.Items.map(function(i){var currentHtml="";return currentHtml+='"}).join(""),context.querySelector(".librarySharingList").innerHTML=folderHtml}function inviteUser(dlg){loading.show();var shareExcludes=Array.prototype.filter.call(dlg.querySelectorAll(".chkShareFolder"),function(i){return i.checked}).map(function(i){return i.getAttribute("data-folderid")});require(["connectHelper"],function(connectHelper){connectHelper.inviteGuest({apiClient:ApiClient,guestOptions:{ConnectUsername:dlg.querySelector("#txtConnectUsername").value,EnabledLibraries:shareExcludes.join(","),SendingUserId:Dashboard.getCurrentUserId(),EnableLiveTv:!1}}).then(function(){loading.hide(),dlg.submitted=!0,dialogHelper.close(dlg)})})}return{show:function(){return new Promise(function(resolve,reject){require(["text!./guestinviter.template.html"],function(template){var dlg=dialogHelper.createDialog({removeOnClose:!0,size:"small"});dlg.classList.add("ui-body-a"),dlg.classList.add("background-theme-a"),dlg.classList.add("formDialog");var html="";html+=Globalize.translateDocument(template),dlg.innerHTML=html,dialogHelper.open(dlg),dlg.addEventListener("close",function(){dlg.submitted?resolve():reject()}),dlg.querySelector(".btnCancel").addEventListener("click",function(e){dialogHelper.close(dlg)}),dlg.querySelector("form").addEventListener("submit",function(e){return inviteUser(dlg),e.preventDefault(),!1}),ApiClient.getJSON(ApiClient.getUrl("Library/MediaFolders",{IsHidden:!1})).then(function(result){renderLibrarySharingList(dlg,result)})})})}}}); \ No newline at end of file +define(["dialogHelper", "loading", "require", "emby-input", "emby-button", "emby-checkbox", "paper-icon-button-light", "formDialogStyle", "emby-linkbutton"], function(dialogHelper, loading, require) { + "use strict"; + + function renderLibrarySharingList(context, result) { + var folderHtml = ""; + folderHtml += result.Items.map(function(i) { + var currentHtml = ""; + return currentHtml += '" + }).join(""), context.querySelector(".librarySharingList").innerHTML = folderHtml + } + + function inviteUser(dlg) { + loading.show(); + var shareExcludes = Array.prototype.filter.call(dlg.querySelectorAll(".chkShareFolder"), function(i) { + return i.checked + }).map(function(i) { + return i.getAttribute("data-folderid") + }); + require(["connectHelper"], function(connectHelper) { + connectHelper.inviteGuest({ + apiClient: ApiClient, + guestOptions: { + ConnectUsername: dlg.querySelector("#txtConnectUsername").value, + EnabledLibraries: shareExcludes.join(","), + SendingUserId: Dashboard.getCurrentUserId(), + EnableLiveTv: !1 + } + }).then(function() { + loading.hide(), dlg.submitted = !0, dialogHelper.close(dlg) + }) + }) + } + return { + show: function() { + return new Promise(function(resolve, reject) { + require(["text!./guestinviter.template.html"], function(template) { + var dlg = dialogHelper.createDialog({ + removeOnClose: !0, + size: "small" + }); + dlg.classList.add("ui-body-a"), dlg.classList.add("background-theme-a"), dlg.classList.add("formDialog"); + var html = ""; + html += Globalize.translateDocument(template), dlg.innerHTML = html, dialogHelper.open(dlg), dlg.addEventListener("close", function() { + dlg.submitted ? resolve() : reject() + }), dlg.querySelector(".btnCancel").addEventListener("click", function(e) { + dialogHelper.close(dlg) + }), dlg.querySelector("form").addEventListener("submit", function(e) { + return inviteUser(dlg), e.preventDefault(), !1 + }), ApiClient.getJSON(ApiClient.getUrl("Library/MediaFolders", { + IsHidden: !1 + })).then(function(result) { + renderLibrarySharingList(dlg, result) + }) + }) + }) + } + } +}); \ No newline at end of file diff --git a/dashboard-ui/components/humanedate.js b/dashboard-ui/components/humanedate.js index 126f4edb4f..ac7cff1ef6 100644 --- a/dashboard-ui/components/humanedate.js +++ b/dashboard-ui/components/humanedate.js @@ -1 +1,28 @@ -define(["datetime"],function(datetime){"use strict";function humane_date(date_str){var format,time_formats=[[90,"a minute"],[3600,"minutes",60],[5400,"an hour"],[86400,"hours",3600],[129600,"a day"],[604800,"days",86400],[907200,"a week"],[2628e3,"weeks",604800],[3942e3,"a month"],[31536e3,"months",2628e3],[47304e3,"a year"],[31536e5,"years",31536e3]],dt=new Date,date=datetime.parseISO8601Date(date_str,!0),seconds=(dt-date)/1e3,i=0;for(seconds<0&&(seconds=Math.abs(seconds));format=time_formats[i++];)if(seconds47304e5?Math.round(seconds/47304e5)+" centuries ago":date_str}return window.humane_date=humane_date,humane_date}); \ No newline at end of file +define(["datetime"], function(datetime) { + "use strict"; + + function humane_date(date_str) { + var format, time_formats = [ + [90, "a minute"], + [3600, "minutes", 60], + [5400, "an hour"], + [86400, "hours", 3600], + [129600, "a day"], + [604800, "days", 86400], + [907200, "a week"], + [2628e3, "weeks", 604800], + [3942e3, "a month"], + [31536e3, "months", 2628e3], + [47304e3, "a year"], + [31536e5, "years", 31536e3] + ], + dt = new Date, + date = datetime.parseISO8601Date(date_str, !0), + seconds = (dt - date) / 1e3, + i = 0; + for (seconds < 0 && (seconds = Math.abs(seconds)); format = time_formats[i++];) + if (seconds < format[0]) return 2 == format.length ? format[1] + " ago" : Math.round(seconds / format[2]) + " " + format[1] + " ago"; + return seconds > 47304e5 ? Math.round(seconds / 47304e5) + " centuries ago" : date_str + } + return window.humane_date = humane_date, humane_date +}); \ No newline at end of file diff --git a/dashboard-ui/components/iap.js b/dashboard-ui/components/iap.js index d71a38c6db..7d1096cd9d 100644 --- a/dashboard-ui/components/iap.js +++ b/dashboard-ui/components/iap.js @@ -1 +1,57 @@ -define(["globalize","shell","browser","apphost"],function(globalize,shell,browser,appHost){"use strict";function getProductInfo(feature){return null}function getPremiumInfoUrl(){return"https://emby.media/premiere"}function beginPurchase(feature,email){appHost.supports("externalpremium")?shell.openUrl(getPremiumInfoUrl()):require(["alert"],function(alert){alert("Please visit "+getPremiumInfoUrl())})}function restorePurchase(id){return Promise.reject()}function getSubscriptionOptions(){var options=[];return options.push({id:"embypremiere",title:globalize.translate("sharedcomponents#HeaderBecomeProjectSupporter"),requiresEmail:!1}),Promise.resolve(options)}function isUnlockedByDefault(feature,options){return"playback"===feature||"livetv"===feature?Promise.resolve():Promise.reject()}function getAdminFeatureName(feature){return feature}function getRestoreButtonText(){return globalize.translate("sharedcomponents#HeaderAlreadyPaid")}function getPeriodicMessageIntervalMs(feature){return 0}return{getProductInfo:getProductInfo,beginPurchase:beginPurchase,restorePurchase:restorePurchase,getSubscriptionOptions:getSubscriptionOptions,isUnlockedByDefault:isUnlockedByDefault,getAdminFeatureName:getAdminFeatureName,getRestoreButtonText:getRestoreButtonText,getPeriodicMessageIntervalMs:getPeriodicMessageIntervalMs,getPremiumInfoUrl:getPremiumInfoUrl}}); \ No newline at end of file +define(["globalize", "shell", "browser", "apphost"], function(globalize, shell, browser, appHost) { + "use strict"; + + function getProductInfo(feature) { + return null + } + + function getPremiumInfoUrl() { + return "https://emby.media/premiere" + } + + function beginPurchase(feature, email) { + appHost.supports("externalpremium") ? shell.openUrl(getPremiumInfoUrl()) : require(["alert"], function(alert) { + alert("Please visit " + getPremiumInfoUrl()) + }) + } + + function restorePurchase(id) { + return Promise.reject() + } + + function getSubscriptionOptions() { + var options = []; + return options.push({ + id: "embypremiere", + title: globalize.translate("sharedcomponents#HeaderBecomeProjectSupporter"), + requiresEmail: !1 + }), Promise.resolve(options) + } + + function isUnlockedByDefault(feature, options) { + return "playback" === feature || "livetv" === feature ? Promise.resolve() : Promise.reject() + } + + function getAdminFeatureName(feature) { + return feature + } + + function getRestoreButtonText() { + return globalize.translate("sharedcomponents#HeaderAlreadyPaid") + } + + function getPeriodicMessageIntervalMs(feature) { + return 0 + } + return { + getProductInfo: getProductInfo, + beginPurchase: beginPurchase, + restorePurchase: restorePurchase, + getSubscriptionOptions: getSubscriptionOptions, + isUnlockedByDefault: isUnlockedByDefault, + getAdminFeatureName: getAdminFeatureName, + getRestoreButtonText: getRestoreButtonText, + getPeriodicMessageIntervalMs: getPeriodicMessageIntervalMs, + getPremiumInfoUrl: getPremiumInfoUrl + } +}); \ No newline at end of file diff --git a/dashboard-ui/components/imageoptionseditor/imageoptionseditor.js b/dashboard-ui/components/imageoptionseditor/imageoptionseditor.js index 80c54cf382..94d37d6f7f 100644 --- a/dashboard-ui/components/imageoptionseditor/imageoptionseditor.js +++ b/dashboard-ui/components/imageoptionseditor/imageoptionseditor.js @@ -1 +1,77 @@ -define(["globalize","dom","dialogHelper","emby-checkbox","emby-select","emby-input"],function(globalize,dom,dialogHelper){"use strict";function getDefaultImageConfig(itemType,type){return{Type:type,MinWidth:0,Limit:"Primary"===type?1:0}}function findImageOptions(imageOptions,type){return imageOptions.filter(function(i){return i.Type==type})[0]}function getImageConfig(options,availableOptions,imageType,itemType){return findImageOptions(options.ImageOptions||[],imageType)||findImageOptions(availableOptions.DefaultImageOptions||[],imageType)||getDefaultImageConfig(itemType,imageType)}function setVisibilityOfBackdrops(elem,visible){visible?(elem.classList.remove("hide"),elem.querySelector("input").setAttribute("required","required")):(elem.classList.add("hide"),elem.querySelector("input").setAttribute("required",""),elem.querySelector("input").removeAttribute("required"))}function loadValues(context,itemType,options,availableOptions){var supportedImageTypes=availableOptions.SupportedImageTypes||[];setVisibilityOfBackdrops(context.querySelector(".backdropFields"),-1!=supportedImageTypes.indexOf("Backdrop")),setVisibilityOfBackdrops(context.querySelector(".screenshotFields"),-1!=supportedImageTypes.indexOf("Screenshot")),Array.prototype.forEach.call(context.querySelectorAll(".imageType"),function(i){var imageType=i.getAttribute("data-imagetype"),container=dom.parentWithTag(i,"LABEL");-1==supportedImageTypes.indexOf(imageType)?container.classList.add("hide"):container.classList.remove("hide"),getImageConfig(options,availableOptions,imageType,itemType).Limit?i.checked=!0:i.checked=!1});var backdropConfig=getImageConfig(options,availableOptions,"Backdrop",itemType);context.querySelector("#txtMaxBackdrops").value=backdropConfig.Limit,context.querySelector("#txtMinBackdropDownloadWidth").value=backdropConfig.MinWidth;var screenshotConfig=getImageConfig(options,availableOptions,"Screenshot",itemType);context.querySelector("#txtMaxScreenshots").value=screenshotConfig.Limit,context.querySelector("#txtMinScreenshotDownloadWidth").value=screenshotConfig.MinWidth}function saveValues(context,options){options.ImageOptions=Array.prototype.map.call(context.querySelectorAll(".imageType:not(.hide)"),function(c){return{Type:c.getAttribute("data-imagetype"),Limit:c.checked?1:0,MinWidth:0}}),options.ImageOptions.push({Type:"Backdrop",Limit:context.querySelector("#txtMaxBackdrops").value,MinWidth:context.querySelector("#txtMinBackdropDownloadWidth").value}),options.ImageOptions.push({Type:"Screenshot",Limit:context.querySelector("#txtMaxScreenshots").value,MinWidth:context.querySelector("#txtMinScreenshotDownloadWidth").value})}function editor(){this.show=function(itemType,options,availableOptions){return new Promise(function(resolve,reject){var xhr=new XMLHttpRequest;xhr.open("GET","components/imageoptionseditor/imageoptionseditor.template.html",!0),xhr.onload=function(e){var template=this.response,dlg=dialogHelper.createDialog({size:"medium-tall",removeOnClose:!0,scrollY:!1});dlg.classList.add("formDialog"),dlg.innerHTML=globalize.translateDocument(template),dlg.addEventListener("close",function(){saveValues(dlg,options)}),loadValues(dlg,itemType,options,availableOptions),dialogHelper.open(dlg).then(resolve,resolve),dlg.querySelector(".btnCancel").addEventListener("click",function(){dialogHelper.close(dlg)})},xhr.send()})}}return editor}); \ No newline at end of file +define(["globalize", "dom", "dialogHelper", "emby-checkbox", "emby-select", "emby-input"], function(globalize, dom, dialogHelper) { + "use strict"; + + function getDefaultImageConfig(itemType, type) { + return { + Type: type, + MinWidth: 0, + Limit: "Primary" === type ? 1 : 0 + } + } + + function findImageOptions(imageOptions, type) { + return imageOptions.filter(function(i) { + return i.Type == type + })[0] + } + + function getImageConfig(options, availableOptions, imageType, itemType) { + return findImageOptions(options.ImageOptions || [], imageType) || findImageOptions(availableOptions.DefaultImageOptions || [], imageType) || getDefaultImageConfig(itemType, imageType) + } + + function setVisibilityOfBackdrops(elem, visible) { + visible ? (elem.classList.remove("hide"), elem.querySelector("input").setAttribute("required", "required")) : (elem.classList.add("hide"), elem.querySelector("input").setAttribute("required", ""), elem.querySelector("input").removeAttribute("required")) + } + + function loadValues(context, itemType, options, availableOptions) { + var supportedImageTypes = availableOptions.SupportedImageTypes || []; + setVisibilityOfBackdrops(context.querySelector(".backdropFields"), -1 != supportedImageTypes.indexOf("Backdrop")), setVisibilityOfBackdrops(context.querySelector(".screenshotFields"), -1 != supportedImageTypes.indexOf("Screenshot")), Array.prototype.forEach.call(context.querySelectorAll(".imageType"), function(i) { + var imageType = i.getAttribute("data-imagetype"), + container = dom.parentWithTag(i, "LABEL"); - 1 == supportedImageTypes.indexOf(imageType) ? container.classList.add("hide") : container.classList.remove("hide"), getImageConfig(options, availableOptions, imageType, itemType).Limit ? i.checked = !0 : i.checked = !1 + }); + var backdropConfig = getImageConfig(options, availableOptions, "Backdrop", itemType); + context.querySelector("#txtMaxBackdrops").value = backdropConfig.Limit, context.querySelector("#txtMinBackdropDownloadWidth").value = backdropConfig.MinWidth; + var screenshotConfig = getImageConfig(options, availableOptions, "Screenshot", itemType); + context.querySelector("#txtMaxScreenshots").value = screenshotConfig.Limit, context.querySelector("#txtMinScreenshotDownloadWidth").value = screenshotConfig.MinWidth + } + + function saveValues(context, options) { + options.ImageOptions = Array.prototype.map.call(context.querySelectorAll(".imageType:not(.hide)"), function(c) { + return { + Type: c.getAttribute("data-imagetype"), + Limit: c.checked ? 1 : 0, + MinWidth: 0 + } + }), options.ImageOptions.push({ + Type: "Backdrop", + Limit: context.querySelector("#txtMaxBackdrops").value, + MinWidth: context.querySelector("#txtMinBackdropDownloadWidth").value + }), options.ImageOptions.push({ + Type: "Screenshot", + Limit: context.querySelector("#txtMaxScreenshots").value, + MinWidth: context.querySelector("#txtMinScreenshotDownloadWidth").value + }) + } + + function editor() { + this.show = function(itemType, options, availableOptions) { + return new Promise(function(resolve, reject) { + var xhr = new XMLHttpRequest; + xhr.open("GET", "components/imageoptionseditor/imageoptionseditor.template.html", !0), xhr.onload = function(e) { + var template = this.response, + dlg = dialogHelper.createDialog({ + size: "medium-tall", + removeOnClose: !0, + scrollY: !1 + }); + dlg.classList.add("formDialog"), dlg.innerHTML = globalize.translateDocument(template), dlg.addEventListener("close", function() { + saveValues(dlg, options) + }), loadValues(dlg, itemType, options, availableOptions), dialogHelper.open(dlg).then(resolve, resolve), dlg.querySelector(".btnCancel").addEventListener("click", function() { + dialogHelper.close(dlg) + }) + }, xhr.send() + }) + } + } + return editor +}); \ No newline at end of file diff --git a/dashboard-ui/components/libraryoptionseditor/libraryoptionseditor.js b/dashboard-ui/components/libraryoptionseditor/libraryoptionseditor.js index d9bcb699e7..96dc083e7c 100644 --- a/dashboard-ui/components/libraryoptionseditor/libraryoptionseditor.js +++ b/dashboard-ui/components/libraryoptionseditor/libraryoptionseditor.js @@ -1 +1,344 @@ -define(["globalize","dom","emby-checkbox","emby-select","emby-input"],function(globalize,dom){"use strict";function populateLanguages(parent){return ApiClient.getCultures().then(function(languages){populateLanguagesIntoSelect(parent.querySelector("#selectLanguage"),languages),populateLanguagesIntoList(parent.querySelector(".subtitleDownloadLanguages"),languages)})}function populateLanguagesIntoSelect(select,languages){var html="";html+="";for(var i=0,length=languages.length;i"+culture.DisplayName+""}select.innerHTML=html}function populateLanguagesIntoList(element,languages){for(var html="",i=0,length=languages.length;i'+culture.DisplayName+""}element.innerHTML=html}function populateCountries(select){return ApiClient.getCountries().then(function(allCountries){var html="";html+="";for(var i=0,length=allCountries.length;i"+culture.DisplayName+""}select.innerHTML=html})}function populateRefreshInterval(select){var html="";html+="",html+=[30,60,90].map(function(val){return""}).join(""),select.innerHTML=html}function renderMetadataReaders(page,plugins){var html="",elem=page.querySelector(".metadataReaders");if(plugins.length<1)return elem.innerHTML="",elem.classList.add("hide"),!1;html+='

    '+globalize.translate("LabelMetadataReaders")+"

    ",html+='
    ';for(var i=0,length=plugins.length;i',html+='live_tv',html+='
    ',html+='

    ',html+=plugin.Name,html+="

    ",html+="
    ",i>0?html+='':plugins.length>1&&(html+=''),html+="
    "}return html+="",html+='
    '+globalize.translate("LabelMetadataReadersHelp")+"
    ",plugins.length<2?elem.classList.add("hide"):elem.classList.remove("hide"),elem.innerHTML=html,!0}function renderMetadataSavers(page,metadataSavers){var html="",elem=page.querySelector(".metadataSavers");if(!metadataSavers.length)return elem.innerHTML="",elem.classList.add("hide"),!1;html+='

    '+globalize.translate("LabelMetadataSavers")+"

    ",html+='
    ';for(var i=0,length=metadataSavers.length;i"+plugin.Name+""}return html+="
    ",html+='
    '+globalize.translate("LabelMetadataSaversHelp")+"
    ",elem.innerHTML=html,elem.classList.remove("hide"),!0}function getMetadataFetchersForTypeHtml(availableTypeOptions,libraryOptionsForType){var html="",plugins=availableTypeOptions.MetadataFetchers;if(plugins=getOrderedPlugins(plugins,libraryOptionsForType.MetadataFetcherOrder||[]),!plugins.length)return html;html+='
    ',html+='

    '+globalize.translate("LabelTypeMetadataDownloaders",availableTypeOptions.Type)+"

    ",html+='
    ';for(var i=0,length=plugins.length;i';var isChecked=libraryOptionsForType.MetadataFetchers?-1!==libraryOptionsForType.MetadataFetchers.indexOf(plugin.Name):plugin.DefaultEnabled,checkedHtml=isChecked?' checked="checked"':"";html+='",html+='
    ',html+='

    ',html+=plugin.Name,html+="

    ",html+="
    ",i>0?html+='':plugins.length>1&&(html+=''),html+="
    "}return html+="
    ",html+='
    '+globalize.translate("LabelMetadataDownloadersHelp")+"
    ",html+=""}function getTypeOptions(allOptions,type){for(var allTypeOptions=allOptions.TypeOptions||[],i=0,length=allTypeOptions.length;i",html+='
    ';for(var i=0,length=plugins.length;i';var isChecked=libraryOptions.DisabledSubtitleFetchers?-1===libraryOptions.DisabledSubtitleFetchers.indexOf(plugin.Name):plugin.DefaultEnabled,checkedHtml=isChecked?' checked="checked"':"";html+='",html+='
    ',html+='

    ',html+=plugin.Name,html+="

    ","Open Subtitles"===plugin.Name&&(html+='
    ',html+=globalize.translate("OpenSubtitleInstructions"),html+="
    "),html+="
    ",i>0?html+='':plugins.length>1&&(html+=''),html+="
    "}html+="",html+='
    '+globalize.translate("SubtitleDownloadersHelp")+"
    ",elem.innerHTML=html}catch(err){alert(err)}}function getImageFetchersForTypeHtml(availableTypeOptions,libraryOptionsForType){var html="",plugins=availableTypeOptions.ImageFetchers;if(plugins=getOrderedPlugins(plugins,libraryOptionsForType.ImageFetcherOrder||[]),!plugins.length)return html;html+='
    ',html+='
    ',html+='

    '+globalize.translate("HeaderTypeImageFetchers",availableTypeOptions.Type)+"

    ";var supportedImageTypes=availableTypeOptions.SupportedImageTypes||[];(supportedImageTypes.length>1||1===supportedImageTypes.length&&"Primary"!==supportedImageTypes[0])&&(html+='"),html+="
    ",html+='
    ';for(var i=0,length=plugins.length;i';var isChecked=libraryOptionsForType.ImageFetchers?-1!==libraryOptionsForType.ImageFetchers.indexOf(plugin.Name):plugin.DefaultEnabled,checkedHtml=isChecked?' checked="checked"':"";html+='",html+='
    ',html+='

    ',html+=plugin.Name,html+="

    ",html+="
    ",i>0?html+='':plugins.length>1&&(html+=''),html+="
    "}return html+="
    ",html+='
    '+globalize.translate("LabelImageFetchersHelp")+"
    ",html+=""}function renderImageFetchers(page,availableOptions,libraryOptions){for(var html="",elem=page.querySelector(".imageFetchers"),i=0,length=availableOptions.TypeOptions.length;ib?1:0}),plugins}function setLibraryOptions(parent,options){currentLibraryOptions=options,currentAvailableOptions=parent.availableOptions,parent.querySelector("#selectLanguage").value=options.PreferredMetadataLanguage||"",parent.querySelector("#selectCountry").value=options.MetadataCountryCode||"",parent.querySelector("#selectAutoRefreshInterval").value=options.AutomaticRefreshIntervalDays||"0",parent.querySelector("#txtSeasonZeroName").value=options.SeasonZeroDisplayName||"Specials",parent.querySelector(".chkEnablePhotos").checked=options.EnablePhotos,parent.querySelector(".chkEnableRealtimeMonitor").checked=options.EnableRealtimeMonitor,parent.querySelector(".chkExtractChaptersDuringLibraryScan").checked=options.ExtractChapterImagesDuringLibraryScan,parent.querySelector(".chkExtractChapterImages").checked=options.EnableChapterImageExtraction,parent.querySelector("#chkDownloadImagesInAdvance").checked=options.DownloadImagesInAdvance,parent.querySelector("#chkSaveLocal").checked=options.SaveLocalMetadata,parent.querySelector("#chkImportMissingEpisodes").checked=options.ImportMissingEpisodes,parent.querySelector(".chkAutomaticallyGroupSeries").checked=options.EnableAutomaticSeriesGrouping,parent.querySelector("#chkEnableEmbeddedTitles").checked=options.EnableEmbeddedTitles,parent.querySelector("#chkSkipIfGraphicalSubsPresent").checked=options.SkipSubtitlesIfEmbeddedSubtitlesPresent,parent.querySelector("#chkSaveSubtitlesLocally").checked=options.SaveSubtitlesWithMedia,parent.querySelector("#chkSkipIfAudioTrackPresent").checked=options.SkipSubtitlesIfAudioTrackMatches,parent.querySelector("#chkRequirePerfectMatch").checked=options.RequirePerfectSubtitleMatch,Array.prototype.forEach.call(parent.querySelectorAll(".chkMetadataSaver"),function(elem){elem.checked=options.MetadataSavers?-1!==options.MetadataSavers.indexOf(elem.getAttribute("data-pluginname")):"true"===elem.getAttribute("data-defaultenabled")}),Array.prototype.forEach.call(parent.querySelectorAll(".chkSubtitleLanguage"),function(elem){elem.checked=!!options.SubtitleDownloadLanguages&&-1!==options.SubtitleDownloadLanguages.indexOf(elem.getAttribute("data-lang"))}),renderMetadataReaders(parent,getOrderedPlugins(parent.availableOptions.MetadataReaders,options.LocalMetadataReaderOrder||[])),renderMetadataFetchers(parent,parent.availableOptions,options),renderImageFetchers(parent,parent.availableOptions,options),renderSubtitleFetchers(parent,parent.availableOptions,options)}var currentLibraryOptions,currentAvailableOptions;return{embed:embed,setContentType:setContentType,getLibraryOptions:getLibraryOptions,setLibraryOptions:setLibraryOptions,setAdvancedVisible:setAdvancedVisible}}); \ No newline at end of file +define(["globalize", "dom", "emby-checkbox", "emby-select", "emby-input"], function(globalize, dom) { + "use strict"; + + function populateLanguages(parent) { + return ApiClient.getCultures().then(function(languages) { + populateLanguagesIntoSelect(parent.querySelector("#selectLanguage"), languages), populateLanguagesIntoList(parent.querySelector(".subtitleDownloadLanguages"), languages) + }) + } + + function populateLanguagesIntoSelect(select, languages) { + var html = ""; + html += ""; + for (var i = 0, length = languages.length; i < length; i++) { + var culture = languages[i]; + html += "" + } + select.innerHTML = html + } + + function populateLanguagesIntoList(element, languages) { + for (var html = "", i = 0, length = languages.length; i < length; i++) { + var culture = languages[i]; + html += '" + } + element.innerHTML = html + } + + function populateCountries(select) { + return ApiClient.getCountries().then(function(allCountries) { + var html = ""; + html += ""; + for (var i = 0, length = allCountries.length; i < length; i++) { + var culture = allCountries[i]; + html += "" + } + select.innerHTML = html + }) + } + + function populateRefreshInterval(select) { + var html = ""; + html += "", html += [30, 60, 90].map(function(val) { + return "" + }).join(""), select.innerHTML = html + } + + function renderMetadataReaders(page, plugins) { + var html = "", + elem = page.querySelector(".metadataReaders"); + if (plugins.length < 1) return elem.innerHTML = "", elem.classList.add("hide"), !1; + html += '

    ' + globalize.translate("LabelMetadataReaders") + "

    ", html += '
    '; + for (var i = 0, length = plugins.length; i < length; i++) { + var plugin = plugins[i]; + html += '
    ', html += 'live_tv', html += '
    ', html += '

    ', html += plugin.Name, html += "

    ", html += "
    ", i > 0 ? html += '' : plugins.length > 1 && (html += ''), html += "
    " + } + return html += "
    ", html += '
    ' + globalize.translate("LabelMetadataReadersHelp") + "
    ", plugins.length < 2 ? elem.classList.add("hide") : elem.classList.remove("hide"), elem.innerHTML = html, !0 + } + + function renderMetadataSavers(page, metadataSavers) { + var html = "", + elem = page.querySelector(".metadataSavers"); + if (!metadataSavers.length) return elem.innerHTML = "", elem.classList.add("hide"), !1; + html += '

    ' + globalize.translate("LabelMetadataSavers") + "

    ", html += '
    '; + for (var i = 0, length = metadataSavers.length; i < length; i++) { + var plugin = metadataSavers[i]; + html += '" + } + return html += "
    ", html += '
    ' + globalize.translate("LabelMetadataSaversHelp") + "
    ", elem.innerHTML = html, elem.classList.remove("hide"), !0 + } + + function getMetadataFetchersForTypeHtml(availableTypeOptions, libraryOptionsForType) { + var html = "", + plugins = availableTypeOptions.MetadataFetchers; + if (plugins = getOrderedPlugins(plugins, libraryOptionsForType.MetadataFetcherOrder || []), !plugins.length) return html; + html += '
    ', html += '

    ' + globalize.translate("LabelTypeMetadataDownloaders", availableTypeOptions.Type) + "

    ", html += '
    '; + for (var i = 0, length = plugins.length; i < length; i++) { + var plugin = plugins[i]; + html += '
    '; + var isChecked = libraryOptionsForType.MetadataFetchers ? -1 !== libraryOptionsForType.MetadataFetchers.indexOf(plugin.Name) : plugin.DefaultEnabled, + checkedHtml = isChecked ? ' checked="checked"' : ""; + html += '", html += '
    ', html += '

    ', html += plugin.Name, html += "

    ", html += "
    ", i > 0 ? html += '' : plugins.length > 1 && (html += ''), html += "
    " + } + return html += "
    ", html += '
    ' + globalize.translate("LabelMetadataDownloadersHelp") + "
    ", html += "
    " + } + + function getTypeOptions(allOptions, type) { + for (var allTypeOptions = allOptions.TypeOptions || [], i = 0, length = allTypeOptions.length; i < length; i++) { + var typeOptions = allTypeOptions[i]; + if (typeOptions.Type === type) return typeOptions + } + return null + } + + function renderMetadataFetchers(page, availableOptions, libraryOptions) { + for (var html = "", elem = page.querySelector(".metadataFetchers"), i = 0, length = availableOptions.TypeOptions.length; i < length; i++) { + var availableTypeOptions = availableOptions.TypeOptions[i]; + html += getMetadataFetchersForTypeHtml(availableTypeOptions, getTypeOptions(libraryOptions, availableTypeOptions.Type) || {}) + } + return elem.innerHTML = html, html ? (elem.classList.remove("hide"), page.querySelector(".fldAutoRefreshInterval").classList.remove("hide"), page.querySelector(".fldMetadataLanguage").classList.remove("hide"), page.querySelector(".fldMetadataCountry").classList.remove("hide")) : (elem.classList.add("hide"), page.querySelector(".fldAutoRefreshInterval").classList.add("hide"), page.querySelector(".fldMetadataLanguage").classList.add("hide"), page.querySelector(".fldMetadataCountry").classList.add("hide")), !0 + } + + function renderSubtitleFetchers(page, availableOptions, libraryOptions) { + try { + var html = "", + elem = page.querySelector(".subtitleFetchers"), + html = "", + plugins = availableOptions.SubtitleFetchers; + if (plugins = getOrderedPlugins(plugins, libraryOptions.SubtitleFetcherOrder || []), !plugins.length) return html; + html += '

    ' + globalize.translate("LabelSubtitleDownloaders") + "

    ", html += '
    '; + for (var i = 0, length = plugins.length; i < length; i++) { + var plugin = plugins[i]; + html += '
    '; + var isChecked = libraryOptions.DisabledSubtitleFetchers ? -1 === libraryOptions.DisabledSubtitleFetchers.indexOf(plugin.Name) : plugin.DefaultEnabled, + checkedHtml = isChecked ? ' checked="checked"' : ""; + html += '", html += '
    ', html += '

    ', html += plugin.Name, html += "

    ", "Open Subtitles" === plugin.Name && (html += '
    ', html += globalize.translate("OpenSubtitleInstructions"), html += "
    "), html += "
    ", i > 0 ? html += '' : plugins.length > 1 && (html += ''), html += "
    " + } + html += "
    ", html += '
    ' + globalize.translate("SubtitleDownloadersHelp") + "
    ", elem.innerHTML = html + } catch (err) { + alert(err) + } + } + + function getImageFetchersForTypeHtml(availableTypeOptions, libraryOptionsForType) { + var html = "", + plugins = availableTypeOptions.ImageFetchers; + if (plugins = getOrderedPlugins(plugins, libraryOptionsForType.ImageFetcherOrder || []), !plugins.length) return html; + html += '
    ', html += '
    ', html += '

    ' + globalize.translate("HeaderTypeImageFetchers", availableTypeOptions.Type) + "

    "; + var supportedImageTypes = availableTypeOptions.SupportedImageTypes || []; + (supportedImageTypes.length > 1 || 1 === supportedImageTypes.length && "Primary" !== supportedImageTypes[0]) && (html += '"), html += "
    ", html += '
    '; + for (var i = 0, length = plugins.length; i < length; i++) { + var plugin = plugins[i]; + html += '
    '; + var isChecked = libraryOptionsForType.ImageFetchers ? -1 !== libraryOptionsForType.ImageFetchers.indexOf(plugin.Name) : plugin.DefaultEnabled, + checkedHtml = isChecked ? ' checked="checked"' : ""; + html += '", html += '
    ', html += '

    ', html += plugin.Name, html += "

    ", html += "
    ", i > 0 ? html += '' : plugins.length > 1 && (html += ''), html += "
    " + } + return html += "
    ", html += '
    ' + globalize.translate("LabelImageFetchersHelp") + "
    ", html += "
    " + } + + function renderImageFetchers(page, availableOptions, libraryOptions) { + for (var html = "", elem = page.querySelector(".imageFetchers"), i = 0, length = availableOptions.TypeOptions.length; i < length; i++) { + var availableTypeOptions = availableOptions.TypeOptions[i]; + html += getImageFetchersForTypeHtml(availableTypeOptions, getTypeOptions(libraryOptions, availableTypeOptions.Type) || {}) + } + return elem.innerHTML = html, html ? (elem.classList.remove("hide"), page.querySelector(".chkDownloadImagesInAdvanceContainer").classList.remove("hide"), page.querySelector(".chkSaveLocalContainer").classList.remove("hide")) : (elem.classList.add("hide"), page.querySelector(".chkDownloadImagesInAdvanceContainer").classList.add("hide"), page.querySelector(".chkSaveLocalContainer").classList.add("hide")), !0 + } + + function populateMetadataSettings(parent, contentType, isNewLibrary) { + var isNewLibrary = parent.classList.contains("newlibrary"); + return ApiClient.getJSON(ApiClient.getUrl("Libraries/AvailableOptions", { + LibraryContentType: contentType, + IsNewLibrary: isNewLibrary + })).then(function(availableOptions) { + currentAvailableOptions = availableOptions, parent.availableOptions = availableOptions, renderMetadataSavers(parent, availableOptions.MetadataSavers), renderMetadataReaders(parent, availableOptions.MetadataReaders), renderMetadataFetchers(parent, availableOptions, {}), renderSubtitleFetchers(parent, availableOptions, {}), renderImageFetchers(parent, availableOptions, {}), availableOptions.SubtitleFetchers.length ? parent.querySelector(".subtitleDownloadSettings").classList.remove("hide") : parent.querySelector(".subtitleDownloadSettings").classList.add("hide") + }).catch(function() { + return Promise.resolve() + }) + } + + function adjustSortableListElement(elem) { + var btnSortable = elem.querySelector(".btnSortable"); + elem.previousSibling ? (btnSortable.classList.add("btnSortableMoveUp"), btnSortable.classList.remove("btnSortableMoveDown"), btnSortable.querySelector("i").innerHTML = "keyboard_arrow_up") : (btnSortable.classList.remove("btnSortableMoveUp"), btnSortable.classList.add("btnSortableMoveDown"), btnSortable.querySelector("i").innerHTML = "keyboard_arrow_down") + } + + function showImageOptionsForType(type) { + require(["imageoptionseditor"], function(ImageOptionsEditor) { + var typeOptions = getTypeOptions(currentLibraryOptions, type); + typeOptions || (typeOptions = { + Type: type + }, currentLibraryOptions.TypeOptions.push(typeOptions)); + var availableOptions = getTypeOptions(currentAvailableOptions || {}, type); + (new ImageOptionsEditor).show(type, typeOptions, availableOptions) + }) + } + + function onImageFetchersContainerClick(e) { + var btnImageOptionsForType = dom.parentWithClass(e.target, "btnImageOptionsForType"); + if (btnImageOptionsForType) { + return void showImageOptionsForType(dom.parentWithClass(btnImageOptionsForType, "imageFetcher").getAttribute("data-type")) + } + onSortableContainerClick.call(this, e) + } + + function onSortableContainerClick(e) { + var btnSortable = dom.parentWithClass(e.target, "btnSortable"); + if (btnSortable) { + var li = dom.parentWithClass(btnSortable, "sortableOption"), + list = dom.parentWithClass(li, "paperList"); + if (btnSortable.classList.contains("btnSortableMoveDown")) { + var next = li.nextSibling; + next && (li.parentNode.removeChild(li), next.parentNode.insertBefore(li, next.nextSibling)) + } else { + var prev = li.previousSibling; + prev && (li.parentNode.removeChild(li), prev.parentNode.insertBefore(li, prev)) + } + Array.prototype.forEach.call(list.querySelectorAll(".sortableOption"), adjustSortableListElement) + } + } + + function bindEvents(parent) { + parent.querySelector(".metadataReaders").addEventListener("click", onSortableContainerClick), parent.querySelector(".subtitleFetchers").addEventListener("click", onSortableContainerClick), parent.querySelector(".metadataFetchers").addEventListener("click", onSortableContainerClick), parent.querySelector(".imageFetchers").addEventListener("click", onImageFetchersContainerClick) + } + + function embed(parent, contentType, libraryOptions) { + currentLibraryOptions = { + TypeOptions: [] + }, currentAvailableOptions = null; + var isNewLibrary = null == libraryOptions; + return isNewLibrary && parent.classList.add("newlibrary"), new Promise(function(resolve, reject) { + var xhr = new XMLHttpRequest; + xhr.open("GET", "components/libraryoptionseditor/libraryoptionseditor.template.html", !0), xhr.onload = function(e) { + var template = this.response; + parent.innerHTML = globalize.translateDocument(template), populateRefreshInterval(parent.querySelector("#selectAutoRefreshInterval")); + var promises = [populateLanguages(parent), populateCountries(parent.querySelector("#selectCountry"))]; + Promise.all(promises).then(function() { + return setContentType(parent, contentType).then(function() { + libraryOptions && setLibraryOptions(parent, libraryOptions), bindEvents(parent), resolve() + }) + }) + }, xhr.send() + }) + } + + function setAdvancedVisible(parent, visible) { + for (var elems = parent.querySelectorAll(".advanced"), i = 0, length = elems.length; i < length; i++) visible ? elems[i].classList.remove("advancedHide") : elems[i].classList.add("advancedHide") + } + + function setContentType(parent, contentType) { + return "homevideos" === contentType || "photos" === contentType ? parent.querySelector(".chkEnablePhotosContainer").classList.remove("hide") : parent.querySelector(".chkEnablePhotosContainer").classList.add("hide"), "tvshows" !== contentType && "movies" !== contentType && "homevideos" !== contentType && "musicvideos" !== contentType && "mixed" !== contentType && contentType ? parent.querySelector(".chapterSettingsSection").classList.add("hide") : parent.querySelector(".chapterSettingsSection").classList.remove("hide"), "tvshows" === contentType ? (parent.querySelector(".chkImportMissingEpisodesContainer").classList.remove("hide"), parent.querySelector(".chkAutomaticallyGroupSeriesContainer").classList.remove("hide"), parent.querySelector(".fldSeasonZeroDisplayName").classList.remove("hide"), parent.querySelector("#txtSeasonZeroName").setAttribute("required", "required")) : (parent.querySelector(".chkImportMissingEpisodesContainer").classList.add("hide"), parent.querySelector(".chkAutomaticallyGroupSeriesContainer").classList.add("hide"), parent.querySelector(".fldSeasonZeroDisplayName").classList.add("hide"), parent.querySelector("#txtSeasonZeroName").removeAttribute("required")), "games" === contentType || "books" === contentType || "boxsets" === contentType || "playlists" === contentType || "music" === contentType ? parent.querySelector(".chkEnableEmbeddedTitlesContainer").classList.add("hide") : parent.querySelector(".chkEnableEmbeddedTitlesContainer").classList.remove("hide"), populateMetadataSettings(parent, contentType) + } + + function setSubtitleFetchersIntoOptions(parent, options) { + options.DisabledSubtitleFetchers = Array.prototype.map.call(Array.prototype.filter.call(parent.querySelectorAll(".chkSubtitleFetcher"), function(elem) { + return !elem.checked + }), function(elem) { + return elem.getAttribute("data-pluginname") + }), options.SubtitleFetcherOrder = Array.prototype.map.call(parent.querySelectorAll(".subtitleFetcherItem"), function(elem) { + return elem.getAttribute("data-pluginname") + }) + } + + function setMetadataFetchersIntoOptions(parent, options) { + for (var sections = parent.querySelectorAll(".metadataFetcher"), i = 0, length = sections.length; i < length; i++) { + var section = sections[i], + type = section.getAttribute("data-type"), + typeOptions = getTypeOptions(options, type); + typeOptions || (typeOptions = { + Type: type + }, options.TypeOptions.push(typeOptions)), typeOptions.MetadataFetchers = Array.prototype.map.call(Array.prototype.filter.call(section.querySelectorAll(".chkMetadataFetcher"), function(elem) { + return elem.checked + }), function(elem) { + return elem.getAttribute("data-pluginname") + }), typeOptions.MetadataFetcherOrder = Array.prototype.map.call(section.querySelectorAll(".metadataFetcherItem"), function(elem) { + return elem.getAttribute("data-pluginname") + }) + } + } + + function setImageFetchersIntoOptions(parent, options) { + for (var sections = parent.querySelectorAll(".imageFetcher"), i = 0, length = sections.length; i < length; i++) { + var section = sections[i], + type = section.getAttribute("data-type"), + typeOptions = getTypeOptions(options, type); + typeOptions || (typeOptions = { + Type: type + }, options.TypeOptions.push(typeOptions)), typeOptions.ImageFetchers = Array.prototype.map.call(Array.prototype.filter.call(section.querySelectorAll(".chkImageFetcher"), function(elem) { + return elem.checked + }), function(elem) { + return elem.getAttribute("data-pluginname") + }), typeOptions.ImageFetcherOrder = Array.prototype.map.call(section.querySelectorAll(".imageFetcherItem"), function(elem) { + return elem.getAttribute("data-pluginname") + }) + } + } + + function setImageOptionsIntoOptions(parent, options) { + for (var originalTypeOptions = (currentLibraryOptions || {}).TypeOptions || [], i = 0, length = originalTypeOptions.length; i < length; i++) { + var originalTypeOption = originalTypeOptions[i], + typeOptions = getTypeOptions(options, originalTypeOption.Type); + typeOptions || (typeOptions = { + Type: type + }, options.TypeOptions.push(typeOptions)), originalTypeOption.ImageOptions && (typeOptions.ImageOptions = originalTypeOption.ImageOptions) + } + } + + function getLibraryOptions(parent) { + var options = { + EnableArchiveMediaFiles: !1, + EnablePhotos: parent.querySelector(".chkEnablePhotos").checked, + EnableRealtimeMonitor: parent.querySelector(".chkEnableRealtimeMonitor").checked, + ExtractChapterImagesDuringLibraryScan: parent.querySelector(".chkExtractChaptersDuringLibraryScan").checked, + EnableChapterImageExtraction: parent.querySelector(".chkExtractChapterImages").checked, + DownloadImagesInAdvance: parent.querySelector("#chkDownloadImagesInAdvance").checked, + EnableInternetProviders: !0, + ImportMissingEpisodes: parent.querySelector("#chkImportMissingEpisodes").checked, + SaveLocalMetadata: parent.querySelector("#chkSaveLocal").checked, + EnableAutomaticSeriesGrouping: parent.querySelector(".chkAutomaticallyGroupSeries").checked, + PreferredMetadataLanguage: parent.querySelector("#selectLanguage").value, + MetadataCountryCode: parent.querySelector("#selectCountry").value, + SeasonZeroDisplayName: parent.querySelector("#txtSeasonZeroName").value, + AutomaticRefreshIntervalDays: parseInt(parent.querySelector("#selectAutoRefreshInterval").value), + EnableEmbeddedTitles: parent.querySelector("#chkEnableEmbeddedTitles").checked, + SkipSubtitlesIfEmbeddedSubtitlesPresent: parent.querySelector("#chkSkipIfGraphicalSubsPresent").checked, + SkipSubtitlesIfAudioTrackMatches: parent.querySelector("#chkSkipIfAudioTrackPresent").checked, + SaveSubtitlesWithMedia: parent.querySelector("#chkSaveSubtitlesLocally").checked, + RequirePerfectSubtitleMatch: parent.querySelector("#chkRequirePerfectMatch").checked, + MetadataSavers: Array.prototype.map.call(Array.prototype.filter.call(parent.querySelectorAll(".chkMetadataSaver"), function(elem) { + return elem.checked + }), function(elem) { + return elem.getAttribute("data-pluginname") + }), + TypeOptions: [] + }; + return options.LocalMetadataReaderOrder = Array.prototype.map.call(parent.querySelectorAll(".localReaderOption"), function(elem) { + return elem.getAttribute("data-pluginname") + }), options.SubtitleDownloadLanguages = Array.prototype.map.call(Array.prototype.filter.call(parent.querySelectorAll(".chkSubtitleLanguage"), function(elem) { + return elem.checked + }), function(elem) { + return elem.getAttribute("data-lang") + }), setSubtitleFetchersIntoOptions(parent, options), setMetadataFetchersIntoOptions(parent, options), setImageFetchersIntoOptions(parent, options), setImageOptionsIntoOptions(parent, options), options + } + + function getOrderedPlugins(plugins, configuredOrder) { + return plugins = plugins.slice(0), plugins.sort(function(a, b) { + return a = configuredOrder.indexOf(a.Name), b = configuredOrder.indexOf(b.Name), a < b ? -1 : a > b ? 1 : 0 + }), plugins + } + + function setLibraryOptions(parent, options) { + currentLibraryOptions = options, currentAvailableOptions = parent.availableOptions, parent.querySelector("#selectLanguage").value = options.PreferredMetadataLanguage || "", parent.querySelector("#selectCountry").value = options.MetadataCountryCode || "", parent.querySelector("#selectAutoRefreshInterval").value = options.AutomaticRefreshIntervalDays || "0", parent.querySelector("#txtSeasonZeroName").value = options.SeasonZeroDisplayName || "Specials", parent.querySelector(".chkEnablePhotos").checked = options.EnablePhotos, parent.querySelector(".chkEnableRealtimeMonitor").checked = options.EnableRealtimeMonitor, parent.querySelector(".chkExtractChaptersDuringLibraryScan").checked = options.ExtractChapterImagesDuringLibraryScan, parent.querySelector(".chkExtractChapterImages").checked = options.EnableChapterImageExtraction, parent.querySelector("#chkDownloadImagesInAdvance").checked = options.DownloadImagesInAdvance, parent.querySelector("#chkSaveLocal").checked = options.SaveLocalMetadata, parent.querySelector("#chkImportMissingEpisodes").checked = options.ImportMissingEpisodes, parent.querySelector(".chkAutomaticallyGroupSeries").checked = options.EnableAutomaticSeriesGrouping, parent.querySelector("#chkEnableEmbeddedTitles").checked = options.EnableEmbeddedTitles, parent.querySelector("#chkSkipIfGraphicalSubsPresent").checked = options.SkipSubtitlesIfEmbeddedSubtitlesPresent, parent.querySelector("#chkSaveSubtitlesLocally").checked = options.SaveSubtitlesWithMedia, parent.querySelector("#chkSkipIfAudioTrackPresent").checked = options.SkipSubtitlesIfAudioTrackMatches, parent.querySelector("#chkRequirePerfectMatch").checked = options.RequirePerfectSubtitleMatch, Array.prototype.forEach.call(parent.querySelectorAll(".chkMetadataSaver"), function(elem) { + elem.checked = options.MetadataSavers ? -1 !== options.MetadataSavers.indexOf(elem.getAttribute("data-pluginname")) : "true" === elem.getAttribute("data-defaultenabled") + }), Array.prototype.forEach.call(parent.querySelectorAll(".chkSubtitleLanguage"), function(elem) { + elem.checked = !!options.SubtitleDownloadLanguages && -1 !== options.SubtitleDownloadLanguages.indexOf(elem.getAttribute("data-lang")) + }), renderMetadataReaders(parent, getOrderedPlugins(parent.availableOptions.MetadataReaders, options.LocalMetadataReaderOrder || [])), renderMetadataFetchers(parent, parent.availableOptions, options), renderImageFetchers(parent, parent.availableOptions, options), renderSubtitleFetchers(parent, parent.availableOptions, options) + } + var currentLibraryOptions, currentAvailableOptions; + return { + embed: embed, + setContentType: setContentType, + getLibraryOptions: getLibraryOptions, + setLibraryOptions: setLibraryOptions, + setAdvancedVisible: setAdvancedVisible + } +}); \ No newline at end of file diff --git a/dashboard-ui/components/medialibrarycreator/medialibrarycreator.js b/dashboard-ui/components/medialibrarycreator/medialibrarycreator.js index 9081df3968..e7f7abfdb2 100644 --- a/dashboard-ui/components/medialibrarycreator/medialibrarycreator.js +++ b/dashboard-ui/components/medialibrarycreator/medialibrarycreator.js @@ -1 +1,135 @@ -define(["loading","dialogHelper","dom","jQuery","components/libraryoptionseditor/libraryoptionseditor","emby-toggle","emby-input","emby-select","paper-icon-button-light","listViewStyle","formDialogStyle","emby-linkbutton","flexStyles"],function(loading,dialogHelper,dom,$,libraryoptionseditor){"use strict";function onSubmit(e){if(e.preventDefault(),e.stopPropagation(),0==pathInfos.length)return require(["alert"],function(alert){alert({text:Globalize.translate("PleaseAddAtLeastOneFolder"),type:"error"})}),!1;var form=this,dlg=$(form).parents(".dialog")[0],name=$("#txtValue",form).val(),type=$("#selectCollectionType",form).val();"mixed"==type&&(type=null);var libraryOptions=libraryoptionseditor.getLibraryOptions(dlg.querySelector(".libraryOptions"));return libraryOptions.PathInfos=pathInfos,ApiClient.addVirtualFolder(name,type,currentOptions.refresh,libraryOptions).then(function(){hasChanges=!0,dialogHelper.close(dlg)},function(){require(["toast"],function(toast){toast(Globalize.translate("ErrorAddingMediaPathToVirtualFolder"))})}),!1}function getCollectionTypeOptionsHtml(collectionTypeOptions){return collectionTypeOptions.filter(function(i){return!1!==i.isSelectable}).map(function(i){return'"}).join("")}function initEditor(page,collectionTypeOptions){$("#selectCollectionType",page).html(getCollectionTypeOptionsHtml(collectionTypeOptions)).val("").on("change",function(){var value=this.value,dlg=$(this).parents(".dialog")[0];if(libraryoptionseditor.setContentType(dlg.querySelector(".libraryOptions"),"mixed"==value?"":value),value?dlg.querySelector(".libraryOptions").classList.remove("hide"):dlg.querySelector(".libraryOptions").classList.add("hide"),"mixed"!=value){var index=this.selectedIndex;if(-1!=index){var name=this.options[index].innerHTML.replace("*","").replace("&","&");$("#txtValue",dlg).val(name);var folderOption=collectionTypeOptions.filter(function(i){return i.value==value})[0];$(".collectionTypeFieldDescription",dlg).html(folderOption.message||"")}}}),page.querySelector(".btnAddFolder").addEventListener("click",onAddButtonClick),page.querySelector("form").addEventListener("submit",onSubmit),page.querySelector(".folderList").addEventListener("click",onRemoveClick),page.querySelector(".chkAdvanced").addEventListener("change",onToggleAdvancedChange)}function onToggleAdvancedChange(){var dlg=dom.parentWithClass(this,"dlg-librarycreator");libraryoptionseditor.setAdvancedVisible(dlg.querySelector(".libraryOptions"),this.checked)}function onAddButtonClick(){var page=dom.parentWithClass(this,"dlg-librarycreator");require(["directorybrowser"],function(directoryBrowser){var picker=new directoryBrowser;picker.show({enableNetworkSharePath:!0,callback:function(path,networkSharePath){path&&addMediaLocation(page,path,networkSharePath),picker.close()}})})}function getFolderHtml(pathInfo,index){var html="";return html+='
    ',html+='
    ',html+='
    '+pathInfo.Path+"
    ",pathInfo.NetworkPath&&(html+='
    '+pathInfo.NetworkPath+"
    "),html+="
    ",html+='',html+="
    "}function renderPaths(page){var foldersHtml=pathInfos.map(getFolderHtml).join(""),folderList=page.querySelector(".folderList");folderList.innerHTML=foldersHtml,foldersHtml?folderList.classList.remove("hide"):folderList.classList.add("hide")}function addMediaLocation(page,path,networkSharePath){var pathLower=path.toLowerCase();if(0==pathInfos.filter(function(p){return p.Path.toLowerCase()==pathLower}).length){var pathInfo={Path:path};networkSharePath&&(pathInfo.NetworkPath=networkSharePath),pathInfos.push(pathInfo),renderPaths(page)}}function onRemoveClick(e){var button=dom.parentWithClass(e.target,"btnRemovePath"),index=parseInt(button.getAttribute("data-index")),location=pathInfos[index].Path,locationLower=location.toLowerCase();pathInfos=pathInfos.filter(function(p){return p.Path.toLowerCase()!=locationLower}),renderPaths(dom.parentWithClass(button,"dlg-librarycreator"))}function onDialogClosed(){loading.hide(),currentResolve(hasChanges)}function initLibraryOptions(dlg){libraryoptionseditor.embed(dlg.querySelector(".libraryOptions")).then(function(){$("#selectCollectionType",dlg).trigger("change"),onToggleAdvancedChange.call(dlg.querySelector(".chkAdvanced"))})}function editor(){this.show=function(options){return new Promise(function(resolve,reject){currentOptions=options,currentResolve=resolve,hasChanges=!1;var xhr=new XMLHttpRequest;xhr.open("GET","components/medialibrarycreator/medialibrarycreator.template.html",!0),xhr.onload=function(e){var template=this.response,dlg=dialogHelper.createDialog({size:"medium-tall",modal:!1,removeOnClose:!0,scrollY:!1});dlg.classList.add("ui-body-a"),dlg.classList.add("background-theme-a"),dlg.classList.add("dlg-librarycreator"),dlg.classList.add("formDialog"),dlg.innerHTML=Globalize.translateDocument(template),initEditor(dlg,options.collectionTypeOptions),dlg.addEventListener("close",onDialogClosed),dialogHelper.open(dlg),dlg.querySelector(".btnCancel").addEventListener("click",function(){dialogHelper.close(dlg)}),pathInfos=[],renderPaths(dlg),initLibraryOptions(dlg)},xhr.send()})}}var currentResolve,hasChanges,currentOptions,pathInfos=[];return editor}); \ No newline at end of file +define(["loading", "dialogHelper", "dom", "jQuery", "components/libraryoptionseditor/libraryoptionseditor", "emby-toggle", "emby-input", "emby-select", "paper-icon-button-light", "listViewStyle", "formDialogStyle", "emby-linkbutton", "flexStyles"], function(loading, dialogHelper, dom, $, libraryoptionseditor) { + "use strict"; + + function onSubmit(e) { + if (e.preventDefault(), e.stopPropagation(), 0 == pathInfos.length) return require(["alert"], function(alert) { + alert({ + text: Globalize.translate("PleaseAddAtLeastOneFolder"), + type: "error" + }) + }), !1; + var form = this, + dlg = $(form).parents(".dialog")[0], + name = $("#txtValue", form).val(), + type = $("#selectCollectionType", form).val(); + "mixed" == type && (type = null); + var libraryOptions = libraryoptionseditor.getLibraryOptions(dlg.querySelector(".libraryOptions")); + return libraryOptions.PathInfos = pathInfos, ApiClient.addVirtualFolder(name, type, currentOptions.refresh, libraryOptions).then(function() { + hasChanges = !0, dialogHelper.close(dlg) + }, function() { + require(["toast"], function(toast) { + toast(Globalize.translate("ErrorAddingMediaPathToVirtualFolder")) + }) + }), !1 + } + + function getCollectionTypeOptionsHtml(collectionTypeOptions) { + return collectionTypeOptions.filter(function(i) { + return !1 !== i.isSelectable + }).map(function(i) { + return '" + }).join("") + } + + function initEditor(page, collectionTypeOptions) { + $("#selectCollectionType", page).html(getCollectionTypeOptionsHtml(collectionTypeOptions)).val("").on("change", function() { + var value = this.value, + dlg = $(this).parents(".dialog")[0]; + if (libraryoptionseditor.setContentType(dlg.querySelector(".libraryOptions"), "mixed" == value ? "" : value), value ? dlg.querySelector(".libraryOptions").classList.remove("hide") : dlg.querySelector(".libraryOptions").classList.add("hide"), "mixed" != value) { + var index = this.selectedIndex; + if (-1 != index) { + var name = this.options[index].innerHTML.replace("*", "").replace("&", "&"); + $("#txtValue", dlg).val(name); + var folderOption = collectionTypeOptions.filter(function(i) { + return i.value == value + })[0]; + $(".collectionTypeFieldDescription", dlg).html(folderOption.message || "") + } + } + }), page.querySelector(".btnAddFolder").addEventListener("click", onAddButtonClick), page.querySelector("form").addEventListener("submit", onSubmit), page.querySelector(".folderList").addEventListener("click", onRemoveClick), page.querySelector(".chkAdvanced").addEventListener("change", onToggleAdvancedChange) + } + + function onToggleAdvancedChange() { + var dlg = dom.parentWithClass(this, "dlg-librarycreator"); + libraryoptionseditor.setAdvancedVisible(dlg.querySelector(".libraryOptions"), this.checked) + } + + function onAddButtonClick() { + var page = dom.parentWithClass(this, "dlg-librarycreator"); + require(["directorybrowser"], function(directoryBrowser) { + var picker = new directoryBrowser; + picker.show({ + enableNetworkSharePath: !0, + callback: function(path, networkSharePath) { + path && addMediaLocation(page, path, networkSharePath), picker.close() + } + }) + }) + } + + function getFolderHtml(pathInfo, index) { + var html = ""; + return html += '
    ', html += '
    ', html += '
    ' + pathInfo.Path + "
    ", pathInfo.NetworkPath && (html += '
    ' + pathInfo.NetworkPath + "
    "), html += "
    ", html += '', html += "
    " + } + + function renderPaths(page) { + var foldersHtml = pathInfos.map(getFolderHtml).join(""), + folderList = page.querySelector(".folderList"); + folderList.innerHTML = foldersHtml, foldersHtml ? folderList.classList.remove("hide") : folderList.classList.add("hide") + } + + function addMediaLocation(page, path, networkSharePath) { + var pathLower = path.toLowerCase(); + if (0 == pathInfos.filter(function(p) { + return p.Path.toLowerCase() == pathLower + }).length) { + var pathInfo = { + Path: path + }; + networkSharePath && (pathInfo.NetworkPath = networkSharePath), pathInfos.push(pathInfo), renderPaths(page) + } + } + + function onRemoveClick(e) { + var button = dom.parentWithClass(e.target, "btnRemovePath"), + index = parseInt(button.getAttribute("data-index")), + location = pathInfos[index].Path, + locationLower = location.toLowerCase(); + pathInfos = pathInfos.filter(function(p) { + return p.Path.toLowerCase() != locationLower + }), renderPaths(dom.parentWithClass(button, "dlg-librarycreator")) + } + + function onDialogClosed() { + loading.hide(), currentResolve(hasChanges) + } + + function initLibraryOptions(dlg) { + libraryoptionseditor.embed(dlg.querySelector(".libraryOptions")).then(function() { + $("#selectCollectionType", dlg).trigger("change"), onToggleAdvancedChange.call(dlg.querySelector(".chkAdvanced")) + }) + } + + function editor() { + this.show = function(options) { + return new Promise(function(resolve, reject) { + currentOptions = options, currentResolve = resolve, hasChanges = !1; + var xhr = new XMLHttpRequest; + xhr.open("GET", "components/medialibrarycreator/medialibrarycreator.template.html", !0), xhr.onload = function(e) { + var template = this.response, + dlg = dialogHelper.createDialog({ + size: "medium-tall", + modal: !1, + removeOnClose: !0, + scrollY: !1 + }); + dlg.classList.add("ui-body-a"), dlg.classList.add("background-theme-a"), dlg.classList.add("dlg-librarycreator"), dlg.classList.add("formDialog"), dlg.innerHTML = Globalize.translateDocument(template), initEditor(dlg, options.collectionTypeOptions), dlg.addEventListener("close", onDialogClosed), dialogHelper.open(dlg), dlg.querySelector(".btnCancel").addEventListener("click", function() { + dialogHelper.close(dlg) + }), pathInfos = [], renderPaths(dlg), initLibraryOptions(dlg) + }, xhr.send() + }) + } + } + var currentResolve, hasChanges, currentOptions, pathInfos = []; + return editor +}); \ No newline at end of file diff --git a/dashboard-ui/components/medialibraryeditor/medialibraryeditor.js b/dashboard-ui/components/medialibraryeditor/medialibraryeditor.js index 8257f5975c..ba9ca495a5 100644 --- a/dashboard-ui/components/medialibraryeditor/medialibraryeditor.js +++ b/dashboard-ui/components/medialibraryeditor/medialibraryeditor.js @@ -1 +1,149 @@ -define(["loading","dialogHelper","dom","components/libraryoptionseditor/libraryoptionseditor","emby-button","listViewStyle","paper-icon-button-light","formDialogStyle","emby-toggle","flexStyles"],function(loading,dialogHelper,dom,libraryoptionseditor){"use strict";function addMediaLocation(page,path,networkSharePath){var virtualFolder=currentOptions.library,refreshAfterChange=currentOptions.refresh;ApiClient.addMediaPath(virtualFolder.Name,path,networkSharePath,refreshAfterChange).then(function(){hasChanges=!0,refreshLibraryFromServer(page)},function(){require(["toast"],function(toast){toast(Globalize.translate("ErrorAddingMediaPathToVirtualFolder"))})})}function updateMediaLocation(page,path,networkSharePath){var virtualFolder=currentOptions.library;ApiClient.updateMediaPath(virtualFolder.Name,{Path:path,NetworkPath:networkSharePath}).then(function(){hasChanges=!0,refreshLibraryFromServer(page)},function(){require(["toast"],function(toast){toast(Globalize.translate("ErrorAddingMediaPathToVirtualFolder"))})})}function onRemoveClick(btnRemovePath,location){var button=btnRemovePath,virtualFolder=currentOptions.library;require(["confirm"],function(confirm){confirm({title:Globalize.translate("HeaderRemoveMediaLocation"),text:Globalize.translate("MessageConfirmRemoveMediaLocation"),confirmText:Globalize.translate("ButtonDelete"),primary:"cancel"}).then(function(){var refreshAfterChange=currentOptions.refresh;ApiClient.removeMediaPath(virtualFolder.Name,location,refreshAfterChange).then(function(){hasChanges=!0,refreshLibraryFromServer(dom.parentWithClass(button,"dlg-libraryeditor"))},function(){require(["toast"],function(toast){toast(Globalize.translate("DefaultErrorMessage"))})})})})}function onListItemClick(e){var listItem=dom.parentWithClass(e.target,"listItem");if(listItem){var index=parseInt(listItem.getAttribute("data-index")),pathInfos=(currentOptions.library.LibraryOptions||{}).PathInfos||[],pathInfo=null==index?{}:pathInfos[index]||{},originalPath=pathInfo.Path||(null==index?null:currentOptions.library.Locations[index]),btnRemovePath=dom.parentWithClass(e.target,"btnRemovePath");if(btnRemovePath)return void onRemoveClick(btnRemovePath,originalPath);showDirectoryBrowser(dom.parentWithClass(listItem,"dlg-libraryeditor"),originalPath,pathInfo.NetworkPath)}}function getFolderHtml(pathInfo,index){var html="";return html+='
    ',html+='
    ',html+='

    ',html+=pathInfo.Path,html+="

    ",pathInfo.NetworkPath&&(html+='
    '+pathInfo.NetworkPath+"
    "),html+="
    ",html+='',html+="
    "}function refreshLibraryFromServer(page){ApiClient.getVirtualFolders().then(function(result){var library=result.filter(function(f){return f.Name===currentOptions.library.Name})[0];library&&(currentOptions.library=library,renderLibrary(page,currentOptions))})}function renderLibrary(page,options){var pathInfos=(options.library.LibraryOptions||{}).PathInfos||[];pathInfos.length||(pathInfos=options.library.Locations.map(function(p){return{Path:p}})),"boxsets"===options.library.CollectionType?page.querySelector(".folders").classList.add("hide"):page.querySelector(".folders").classList.remove("hide"),page.querySelector(".folderList").innerHTML=pathInfos.map(getFolderHtml).join("")}function onAddButtonClick(){showDirectoryBrowser(dom.parentWithClass(this,"dlg-libraryeditor"))}function showDirectoryBrowser(context,originalPath,networkPath){require(["directorybrowser"],function(directoryBrowser){var picker=new directoryBrowser;picker.show({enableNetworkSharePath:!0,pathReadOnly:null!=originalPath,path:originalPath,networkSharePath:networkPath,callback:function(path,networkSharePath){path&&(originalPath?updateMediaLocation(context,originalPath,networkSharePath):addMediaLocation(context,path,networkSharePath)),picker.close()}})})}function onToggleAdvancedChange(){var dlg=dom.parentWithClass(this,"dlg-libraryeditor");libraryoptionseditor.setAdvancedVisible(dlg.querySelector(".libraryOptions"),this.checked)}function initEditor(dlg,options){renderLibrary(dlg,options),dlg.querySelector(".btnAddFolder").addEventListener("click",onAddButtonClick),dlg.querySelector(".folderList").addEventListener("click",onListItemClick),dlg.querySelector(".chkAdvanced").addEventListener("change",onToggleAdvancedChange),libraryoptionseditor.embed(dlg.querySelector(".libraryOptions"),options.library.CollectionType,options.library.LibraryOptions).then(function(){onToggleAdvancedChange.call(dlg.querySelector(".chkAdvanced"))})}function onDialogClosing(){var dlg=this,libraryOptions=libraryoptionseditor.getLibraryOptions(dlg.querySelector(".libraryOptions"));libraryOptions=Object.assign(currentOptions.library.LibraryOptions||{},libraryOptions),ApiClient.updateVirtualFolderOptions(currentOptions.library.ItemId,libraryOptions)}function onDialogClosed(){loading.hide(),hasChanges=!0,currentDeferred.resolveWith(null,[hasChanges])}function editor(){this.show=function(options){var deferred=jQuery.Deferred();currentOptions=options,currentDeferred=deferred,hasChanges=!1;var xhr=new XMLHttpRequest;return xhr.open("GET","components/medialibraryeditor/medialibraryeditor.template.html",!0),xhr.onload=function(e){var template=this.response,dlg=dialogHelper.createDialog({size:"medium-tall",modal:!1,removeOnClose:!0,scrollY:!1});dlg.classList.add("dlg-libraryeditor"),dlg.classList.add("ui-body-a"),dlg.classList.add("background-theme-a"),dlg.classList.add("formDialog"),dlg.innerHTML=Globalize.translateDocument(template),dlg.querySelector(".formDialogHeaderTitle").innerHTML=options.library.Name,initEditor(dlg,options),dlg.addEventListener("closing",onDialogClosing),dlg.addEventListener("close",onDialogClosed),dialogHelper.open(dlg),dlg.querySelector(".btnCancel").addEventListener("click",function(){dialogHelper.close(dlg)}),refreshLibraryFromServer(dlg)},xhr.send(),deferred.promise()}}var currentDeferred,hasChanges,currentOptions;return editor}); \ No newline at end of file +define(["loading", "dialogHelper", "dom", "components/libraryoptionseditor/libraryoptionseditor", "emby-button", "listViewStyle", "paper-icon-button-light", "formDialogStyle", "emby-toggle", "flexStyles"], function(loading, dialogHelper, dom, libraryoptionseditor) { + "use strict"; + + function addMediaLocation(page, path, networkSharePath) { + var virtualFolder = currentOptions.library, + refreshAfterChange = currentOptions.refresh; + ApiClient.addMediaPath(virtualFolder.Name, path, networkSharePath, refreshAfterChange).then(function() { + hasChanges = !0, refreshLibraryFromServer(page) + }, function() { + require(["toast"], function(toast) { + toast(Globalize.translate("ErrorAddingMediaPathToVirtualFolder")) + }) + }) + } + + function updateMediaLocation(page, path, networkSharePath) { + var virtualFolder = currentOptions.library; + ApiClient.updateMediaPath(virtualFolder.Name, { + Path: path, + NetworkPath: networkSharePath + }).then(function() { + hasChanges = !0, refreshLibraryFromServer(page) + }, function() { + require(["toast"], function(toast) { + toast(Globalize.translate("ErrorAddingMediaPathToVirtualFolder")) + }) + }) + } + + function onRemoveClick(btnRemovePath, location) { + var button = btnRemovePath, + virtualFolder = currentOptions.library; + require(["confirm"], function(confirm) { + confirm({ + title: Globalize.translate("HeaderRemoveMediaLocation"), + text: Globalize.translate("MessageConfirmRemoveMediaLocation"), + confirmText: Globalize.translate("ButtonDelete"), + primary: "cancel" + }).then(function() { + var refreshAfterChange = currentOptions.refresh; + ApiClient.removeMediaPath(virtualFolder.Name, location, refreshAfterChange).then(function() { + hasChanges = !0, refreshLibraryFromServer(dom.parentWithClass(button, "dlg-libraryeditor")) + }, function() { + require(["toast"], function(toast) { + toast(Globalize.translate("DefaultErrorMessage")) + }) + }) + }) + }) + } + + function onListItemClick(e) { + var listItem = dom.parentWithClass(e.target, "listItem"); + if (listItem) { + var index = parseInt(listItem.getAttribute("data-index")), + pathInfos = (currentOptions.library.LibraryOptions || {}).PathInfos || [], + pathInfo = null == index ? {} : pathInfos[index] || {}, + originalPath = pathInfo.Path || (null == index ? null : currentOptions.library.Locations[index]), + btnRemovePath = dom.parentWithClass(e.target, "btnRemovePath"); + if (btnRemovePath) return void onRemoveClick(btnRemovePath, originalPath); + showDirectoryBrowser(dom.parentWithClass(listItem, "dlg-libraryeditor"), originalPath, pathInfo.NetworkPath) + } + } + + function getFolderHtml(pathInfo, index) { + var html = ""; + return html += '
    ', html += '
    ', html += '

    ', html += pathInfo.Path, html += "

    ", pathInfo.NetworkPath && (html += '
    ' + pathInfo.NetworkPath + "
    "), html += "
    ", html += '', html += "
    " + } + + function refreshLibraryFromServer(page) { + ApiClient.getVirtualFolders().then(function(result) { + var library = result.filter(function(f) { + return f.Name === currentOptions.library.Name + })[0]; + library && (currentOptions.library = library, renderLibrary(page, currentOptions)) + }) + } + + function renderLibrary(page, options) { + var pathInfos = (options.library.LibraryOptions || {}).PathInfos || []; + pathInfos.length || (pathInfos = options.library.Locations.map(function(p) { + return { + Path: p + } + })), "boxsets" === options.library.CollectionType ? page.querySelector(".folders").classList.add("hide") : page.querySelector(".folders").classList.remove("hide"), page.querySelector(".folderList").innerHTML = pathInfos.map(getFolderHtml).join("") + } + + function onAddButtonClick() { + showDirectoryBrowser(dom.parentWithClass(this, "dlg-libraryeditor")) + } + + function showDirectoryBrowser(context, originalPath, networkPath) { + require(["directorybrowser"], function(directoryBrowser) { + var picker = new directoryBrowser; + picker.show({ + enableNetworkSharePath: !0, + pathReadOnly: null != originalPath, + path: originalPath, + networkSharePath: networkPath, + callback: function(path, networkSharePath) { + path && (originalPath ? updateMediaLocation(context, originalPath, networkSharePath) : addMediaLocation(context, path, networkSharePath)), picker.close() + } + }) + }) + } + + function onToggleAdvancedChange() { + var dlg = dom.parentWithClass(this, "dlg-libraryeditor"); + libraryoptionseditor.setAdvancedVisible(dlg.querySelector(".libraryOptions"), this.checked) + } + + function initEditor(dlg, options) { + renderLibrary(dlg, options), dlg.querySelector(".btnAddFolder").addEventListener("click", onAddButtonClick), dlg.querySelector(".folderList").addEventListener("click", onListItemClick), dlg.querySelector(".chkAdvanced").addEventListener("change", onToggleAdvancedChange), libraryoptionseditor.embed(dlg.querySelector(".libraryOptions"), options.library.CollectionType, options.library.LibraryOptions).then(function() { + onToggleAdvancedChange.call(dlg.querySelector(".chkAdvanced")) + }) + } + + function onDialogClosing() { + var dlg = this, + libraryOptions = libraryoptionseditor.getLibraryOptions(dlg.querySelector(".libraryOptions")); + libraryOptions = Object.assign(currentOptions.library.LibraryOptions || {}, libraryOptions), ApiClient.updateVirtualFolderOptions(currentOptions.library.ItemId, libraryOptions) + } + + function onDialogClosed() { + loading.hide(), hasChanges = !0, currentDeferred.resolveWith(null, [hasChanges]) + } + + function editor() { + this.show = function(options) { + var deferred = jQuery.Deferred(); + currentOptions = options, currentDeferred = deferred, hasChanges = !1; + var xhr = new XMLHttpRequest; + return xhr.open("GET", "components/medialibraryeditor/medialibraryeditor.template.html", !0), xhr.onload = function(e) { + var template = this.response, + dlg = dialogHelper.createDialog({ + size: "medium-tall", + modal: !1, + removeOnClose: !0, + scrollY: !1 + }); + dlg.classList.add("dlg-libraryeditor"), dlg.classList.add("ui-body-a"), dlg.classList.add("background-theme-a"), dlg.classList.add("formDialog"), dlg.innerHTML = Globalize.translateDocument(template), dlg.querySelector(".formDialogHeaderTitle").innerHTML = options.library.Name, initEditor(dlg, options), dlg.addEventListener("closing", onDialogClosing), dlg.addEventListener("close", onDialogClosed), dialogHelper.open(dlg), dlg.querySelector(".btnCancel").addEventListener("click", function() { + dialogHelper.close(dlg) + }), refreshLibraryFromServer(dlg) + }, xhr.send(), deferred.promise() + } + } + var currentDeferred, hasChanges, currentOptions; + return editor +}); \ No newline at end of file diff --git a/dashboard-ui/components/navdrawer/navdrawer.js b/dashboard-ui/components/navdrawer/navdrawer.js index 408945beae..3a1119e129 100644 --- a/dashboard-ui/components/navdrawer/navdrawer.js +++ b/dashboard-ui/components/navdrawer/navdrawer.js @@ -1 +1,179 @@ -define(["browser","dom","css!./navdrawer","scrollStyles"],function(browser,dom){"use strict";return function(options){function getTouches(e){return e.changedTouches||e.targetTouches||e.touches}function onMenuTouchStart(e){options.target.classList.remove("transition");var touches=getTouches(e),touch=touches[0]||{};menuTouchStartX=touch.clientX,menuTouchStartY=touch.clientY,menuTouchStartTime=(new Date).getTime()}function setVelocity(deltaX){var time=(new Date).getTime()-(menuTouchStartTime||0);velocity=Math.abs(deltaX)/time}function onMenuTouchMove(e){var isOpen=self.visible,touches=getTouches(e),touch=touches[0]||{},endX=touch.clientX||0,endY=touch.clientY||0,deltaX=endX-(menuTouchStartX||0),deltaY=endY-(menuTouchStartY||0);setVelocity(deltaX),isOpen&&1!==dragMode&&deltaX>0&&(dragMode=2),0===dragMode&&(!isOpen||Math.abs(deltaX)>=10)&&Math.abs(deltaY)<5?(dragMode=1,scrollContainer.addEventListener("scroll",disableEvent),self.showMask()):0===dragMode&&Math.abs(deltaY)>=5&&(dragMode=2),1===dragMode&&(newPos=currentPos+deltaX,self.changeMenuPos())}function onMenuTouchEnd(e){options.target.classList.add("transition"),scrollContainer.removeEventListener("scroll",disableEvent),dragMode=0;var touches=getTouches(e),touch=touches[0]||{},endX=touch.clientX||0,endY=touch.clientY||0,deltaX=endX-(menuTouchStartX||0),deltaY=endY-(menuTouchStartY||0);currentPos=deltaX,self.checkMenuState(deltaX,deltaY)}function onEdgeTouchStart(e){if(isPeeking)onMenuTouchMove(e);else{((getTouches(e)[0]||{}).clientX||0)<=options.handleSize&&(isPeeking=!0,"touchstart"===e.type&&(dom.removeEventListener(edgeContainer,"touchmove",onEdgeTouchMove,{}),dom.addEventListener(edgeContainer,"touchmove",onEdgeTouchMove,{})),onMenuTouchStart(e))}}function onEdgeTouchMove(e){onEdgeTouchStart(e),e.preventDefault(),e.stopPropagation()}function onEdgeTouchEnd(e){isPeeking&&(isPeeking=!1,dom.removeEventListener(edgeContainer,"touchmove",onEdgeTouchMove,{}),onMenuTouchEnd(e))}function disableEvent(e){e.preventDefault(),e.stopPropagation()}function onBackgroundTouchStart(e){var touches=getTouches(e),touch=touches[0]||{};backgroundTouchStartX=touch.clientX,backgroundTouchStartTime=(new Date).getTime()}function onBackgroundTouchMove(e){var touches=getTouches(e),touch=touches[0]||{},endX=touch.clientX||0;if(endX<=options.width&&self.isVisible){countStart++;var deltaX=endX-(backgroundTouchStartX||0);if(1===countStart&&(startPoint=deltaX),deltaX<0&&2!==dragMode){dragMode=1,newPos=deltaX-startPoint+options.width,self.changeMenuPos();var time=(new Date).getTime()-(backgroundTouchStartTime||0);velocity=Math.abs(deltaX)/time}}e.preventDefault(),e.stopPropagation()}function onBackgroundTouchEnd(e){var touches=getTouches(e),touch=touches[0]||{},endX=touch.clientX||0,deltaX=endX-(backgroundTouchStartX||0);self.checkMenuState(deltaX),countStart=0}function onMaskTransitionEnd(){var classList=mask.classList;classList.contains("backdrop")||classList.add("hide")}var self,defaults,mask,newPos=0,currentPos=0,startPoint=0,countStart=0,velocity=0;options.target.classList.add("transition");var dragMode=0,scrollContainer=options.target.querySelector(".mainDrawer-scrollContainer");scrollContainer.classList.add("scrollY");var TouchMenuLA=function(){self=this,defaults={width:260,handleSize:10,disableMask:!1,maxMaskOpacity:.5},this.isVisible=!1,this.initialize()};TouchMenuLA.prototype.initElements=function(){options.target.classList.add("touch-menu-la"),options.target.style.width=options.width+"px",options.target.style.left=-options.width+"px",options.disableMask||(mask=document.createElement("div"),mask.className="tmla-mask hide",document.body.appendChild(mask),dom.addEventListener(mask,dom.whichTransitionEvent(),onMaskTransitionEnd,{passive:!0}))};var menuTouchStartX,menuTouchStartY,menuTouchStartTime,edgeContainer=document.querySelector(".mainDrawerHandle"),isPeeking=!1;TouchMenuLA.prototype.animateToPosition=function(pos){requestAnimationFrame(function(){options.target.style.transform=pos?"translateX("+pos+"px)":"none"})},TouchMenuLA.prototype.changeMenuPos=function(){newPos<=options.width&&this.animateToPosition(newPos)},TouchMenuLA.prototype.clickMaskClose=function(){mask.addEventListener("click",function(){self.close()})},TouchMenuLA.prototype.checkMenuState=function(deltaX,deltaY){velocity>=.4?deltaX>=0||Math.abs(deltaY||0)>=70?self.open():self.close():newPos>=100?self.open():newPos&&self.close()},TouchMenuLA.prototype.open=function(){this.animateToPosition(options.width),currentPos=options.width,this.isVisible=!0,options.target.classList.add("drawer-open"),self.showMask(),self.invoke(options.onChange)},TouchMenuLA.prototype.close=function(){this.animateToPosition(0),currentPos=0,self.isVisible=!1,options.target.classList.remove("drawer-open"),self.hideMask(),self.invoke(options.onChange)},TouchMenuLA.prototype.toggle=function(){self.isVisible?self.close():self.open()};var backgroundTouchStartX,backgroundTouchStartTime;TouchMenuLA.prototype.showMask=function(){mask.classList.remove("hide"),mask.offsetWidth,mask.classList.add("backdrop")},TouchMenuLA.prototype.hideMask=function(){mask.classList.remove("backdrop")},TouchMenuLA.prototype.invoke=function(fn){fn&&fn.apply(self)};var _edgeSwipeEnabled;return TouchMenuLA.prototype.setEdgeSwipeEnabled=function(enabled){options.disableEdgeSwipe||browser.touch&&(enabled?_edgeSwipeEnabled||(_edgeSwipeEnabled=!0,dom.addEventListener(edgeContainer,"touchstart",onEdgeTouchStart,{passive:!0}),dom.addEventListener(edgeContainer,"touchend",onEdgeTouchEnd,{passive:!0}),dom.addEventListener(edgeContainer,"touchcancel",onEdgeTouchEnd,{passive:!0})):_edgeSwipeEnabled&&(_edgeSwipeEnabled=!1,dom.removeEventListener(edgeContainer,"touchstart",onEdgeTouchStart,{passive:!0}),dom.removeEventListener(edgeContainer,"touchend",onEdgeTouchEnd,{passive:!0}),dom.removeEventListener(edgeContainer,"touchcancel",onEdgeTouchEnd,{passive:!0})))},TouchMenuLA.prototype.initialize=function(){options=Object.assign(defaults,options||{}),browser.edge&&(options.disableEdgeSwipe=!0),self.initElements(),browser.touch&&(dom.addEventListener(options.target,"touchstart",onMenuTouchStart,{passive:!0}),dom.addEventListener(options.target,"touchmove",onMenuTouchMove,{passive:!0}),dom.addEventListener(options.target,"touchend",onMenuTouchEnd,{passive:!0}),dom.addEventListener(options.target,"touchcancel",onMenuTouchEnd,{passive:!0}),dom.addEventListener(mask,"touchstart",onBackgroundTouchStart,{passive:!0}),dom.addEventListener(mask,"touchmove",onBackgroundTouchMove,{}),dom.addEventListener(mask,"touchend",onBackgroundTouchEnd,{passive:!0}),dom.addEventListener(mask,"touchcancel",onBackgroundTouchEnd,{passive:!0})),self.clickMaskClose()},new TouchMenuLA}}); \ No newline at end of file +define(["browser", "dom", "css!./navdrawer", "scrollStyles"], function(browser, dom) { + "use strict"; + return function(options) { + function getTouches(e) { + return e.changedTouches || e.targetTouches || e.touches + } + + function onMenuTouchStart(e) { + options.target.classList.remove("transition"); + var touches = getTouches(e), + touch = touches[0] || {}; + menuTouchStartX = touch.clientX, menuTouchStartY = touch.clientY, menuTouchStartTime = (new Date).getTime() + } + + function setVelocity(deltaX) { + var time = (new Date).getTime() - (menuTouchStartTime || 0); + velocity = Math.abs(deltaX) / time + } + + function onMenuTouchMove(e) { + var isOpen = self.visible, + touches = getTouches(e), + touch = touches[0] || {}, + endX = touch.clientX || 0, + endY = touch.clientY || 0, + deltaX = endX - (menuTouchStartX || 0), + deltaY = endY - (menuTouchStartY || 0); + setVelocity(deltaX), isOpen && 1 !== dragMode && deltaX > 0 && (dragMode = 2), 0 === dragMode && (!isOpen || Math.abs(deltaX) >= 10) && Math.abs(deltaY) < 5 ? (dragMode = 1, scrollContainer.addEventListener("scroll", disableEvent), self.showMask()) : 0 === dragMode && Math.abs(deltaY) >= 5 && (dragMode = 2), 1 === dragMode && (newPos = currentPos + deltaX, self.changeMenuPos()) + } + + function onMenuTouchEnd(e) { + options.target.classList.add("transition"), scrollContainer.removeEventListener("scroll", disableEvent), dragMode = 0; + var touches = getTouches(e), + touch = touches[0] || {}, + endX = touch.clientX || 0, + endY = touch.clientY || 0, + deltaX = endX - (menuTouchStartX || 0), + deltaY = endY - (menuTouchStartY || 0); + currentPos = deltaX, self.checkMenuState(deltaX, deltaY) + } + + function onEdgeTouchStart(e) { + if (isPeeking) onMenuTouchMove(e); + else { + ((getTouches(e)[0] || {}).clientX || 0) <= options.handleSize && (isPeeking = !0, "touchstart" === e.type && (dom.removeEventListener(edgeContainer, "touchmove", onEdgeTouchMove, {}), dom.addEventListener(edgeContainer, "touchmove", onEdgeTouchMove, {})), onMenuTouchStart(e)) + } + } + + function onEdgeTouchMove(e) { + onEdgeTouchStart(e), e.preventDefault(), e.stopPropagation() + } + + function onEdgeTouchEnd(e) { + isPeeking && (isPeeking = !1, dom.removeEventListener(edgeContainer, "touchmove", onEdgeTouchMove, {}), onMenuTouchEnd(e)) + } + + function disableEvent(e) { + e.preventDefault(), e.stopPropagation() + } + + function onBackgroundTouchStart(e) { + var touches = getTouches(e), + touch = touches[0] || {}; + backgroundTouchStartX = touch.clientX, backgroundTouchStartTime = (new Date).getTime() + } + + function onBackgroundTouchMove(e) { + var touches = getTouches(e), + touch = touches[0] || {}, + endX = touch.clientX || 0; + if (endX <= options.width && self.isVisible) { + countStart++; + var deltaX = endX - (backgroundTouchStartX || 0); + if (1 === countStart && (startPoint = deltaX), deltaX < 0 && 2 !== dragMode) { + dragMode = 1, newPos = deltaX - startPoint + options.width, self.changeMenuPos(); + var time = (new Date).getTime() - (backgroundTouchStartTime || 0); + velocity = Math.abs(deltaX) / time + } + } + e.preventDefault(), e.stopPropagation() + } + + function onBackgroundTouchEnd(e) { + var touches = getTouches(e), + touch = touches[0] || {}, + endX = touch.clientX || 0, + deltaX = endX - (backgroundTouchStartX || 0); + self.checkMenuState(deltaX), countStart = 0 + } + + function onMaskTransitionEnd() { + var classList = mask.classList; + classList.contains("backdrop") || classList.add("hide") + } + var self, defaults, mask, newPos = 0, + currentPos = 0, + startPoint = 0, + countStart = 0, + velocity = 0; + options.target.classList.add("transition"); + var dragMode = 0, + scrollContainer = options.target.querySelector(".mainDrawer-scrollContainer"); + scrollContainer.classList.add("scrollY"); + var TouchMenuLA = function() { + self = this, defaults = { + width: 260, + handleSize: 10, + disableMask: !1, + maxMaskOpacity: .5 + }, this.isVisible = !1, this.initialize() + }; + TouchMenuLA.prototype.initElements = function() { + options.target.classList.add("touch-menu-la"), options.target.style.width = options.width + "px", options.target.style.left = -options.width + "px", options.disableMask || (mask = document.createElement("div"), mask.className = "tmla-mask hide", document.body.appendChild(mask), dom.addEventListener(mask, dom.whichTransitionEvent(), onMaskTransitionEnd, { + passive: !0 + })) + }; + var menuTouchStartX, menuTouchStartY, menuTouchStartTime, edgeContainer = document.querySelector(".mainDrawerHandle"), + isPeeking = !1; + TouchMenuLA.prototype.animateToPosition = function(pos) { + requestAnimationFrame(function() { + options.target.style.transform = pos ? "translateX(" + pos + "px)" : "none" + }) + }, TouchMenuLA.prototype.changeMenuPos = function() { + newPos <= options.width && this.animateToPosition(newPos) + }, TouchMenuLA.prototype.clickMaskClose = function() { + mask.addEventListener("click", function() { + self.close() + }) + }, TouchMenuLA.prototype.checkMenuState = function(deltaX, deltaY) { + velocity >= .4 ? deltaX >= 0 || Math.abs(deltaY || 0) >= 70 ? self.open() : self.close() : newPos >= 100 ? self.open() : newPos && self.close() + }, TouchMenuLA.prototype.open = function() { + this.animateToPosition(options.width), currentPos = options.width, this.isVisible = !0, options.target.classList.add("drawer-open"), self.showMask(), self.invoke(options.onChange) + }, TouchMenuLA.prototype.close = function() { + this.animateToPosition(0), currentPos = 0, self.isVisible = !1, options.target.classList.remove("drawer-open"), self.hideMask(), self.invoke(options.onChange) + }, TouchMenuLA.prototype.toggle = function() { + self.isVisible ? self.close() : self.open() + }; + var backgroundTouchStartX, backgroundTouchStartTime; + TouchMenuLA.prototype.showMask = function() { + mask.classList.remove("hide"), mask.offsetWidth, mask.classList.add("backdrop") + }, TouchMenuLA.prototype.hideMask = function() { + mask.classList.remove("backdrop") + }, TouchMenuLA.prototype.invoke = function(fn) { + fn && fn.apply(self) + }; + var _edgeSwipeEnabled; + return TouchMenuLA.prototype.setEdgeSwipeEnabled = function(enabled) { + options.disableEdgeSwipe || browser.touch && (enabled ? _edgeSwipeEnabled || (_edgeSwipeEnabled = !0, dom.addEventListener(edgeContainer, "touchstart", onEdgeTouchStart, { + passive: !0 + }), dom.addEventListener(edgeContainer, "touchend", onEdgeTouchEnd, { + passive: !0 + }), dom.addEventListener(edgeContainer, "touchcancel", onEdgeTouchEnd, { + passive: !0 + })) : _edgeSwipeEnabled && (_edgeSwipeEnabled = !1, dom.removeEventListener(edgeContainer, "touchstart", onEdgeTouchStart, { + passive: !0 + }), dom.removeEventListener(edgeContainer, "touchend", onEdgeTouchEnd, { + passive: !0 + }), dom.removeEventListener(edgeContainer, "touchcancel", onEdgeTouchEnd, { + passive: !0 + }))) + }, TouchMenuLA.prototype.initialize = function() { + options = Object.assign(defaults, options || {}), browser.edge && (options.disableEdgeSwipe = !0), self.initElements(), browser.touch && (dom.addEventListener(options.target, "touchstart", onMenuTouchStart, { + passive: !0 + }), dom.addEventListener(options.target, "touchmove", onMenuTouchMove, { + passive: !0 + }), dom.addEventListener(options.target, "touchend", onMenuTouchEnd, { + passive: !0 + }), dom.addEventListener(options.target, "touchcancel", onMenuTouchEnd, { + passive: !0 + }), dom.addEventListener(mask, "touchstart", onBackgroundTouchStart, { + passive: !0 + }), dom.addEventListener(mask, "touchmove", onBackgroundTouchMove, {}), dom.addEventListener(mask, "touchend", onBackgroundTouchEnd, { + passive: !0 + }), dom.addEventListener(mask, "touchcancel", onBackgroundTouchEnd, { + passive: !0 + })), self.clickMaskClose() + }, new TouchMenuLA + } +}); \ No newline at end of file diff --git a/dashboard-ui/components/remotecontrol.js b/dashboard-ui/components/remotecontrol.js index 451a4b3e21..4609629960 100644 --- a/dashboard-ui/components/remotecontrol.js +++ b/dashboard-ui/components/remotecontrol.js @@ -1 +1,410 @@ -define(["browser","datetime","backdrop","libraryBrowser","listView","imageLoader","playbackManager","nowPlayingHelper","events","connectionManager","apphost","globalize","cardStyle","emby-itemscontainer","css!css/nowplaying.css","emby-ratingbutton"],function(browser,datetime,backdrop,libraryBrowser,listView,imageLoader,playbackManager,nowPlayingHelper,events,connectionManager,appHost,globalize){"use strict";function showAudioMenu(context,player,button,item){var currentIndex=playbackManager.getAudioStreamIndex(player),streams=playbackManager.audioTracks(player),menuItems=streams.map(function(s){var menuItem={name:s.DisplayTitle,id:s.Index};return s.Index==currentIndex&&(menuItem.selected=!0),menuItem});require(["actionsheet"],function(actionsheet){actionsheet.show({items:menuItems,positionTo:button,callback:function(id){playbackManager.setAudioStreamIndex(parseInt(id),player)}})})}function showSubtitleMenu(context,player,button,item){var currentIndex=playbackManager.getSubtitleStreamIndex(player),streams=playbackManager.subtitleTracks(player),menuItems=streams.map(function(s){var menuItem={name:s.DisplayTitle,id:s.Index};return s.Index==currentIndex&&(menuItem.selected=!0),menuItem});menuItems.unshift({id:-1,name:globalize.translate("ButtonOff"),selected:null==currentIndex}),require(["actionsheet"],function(actionsheet){actionsheet.show({items:menuItems,positionTo:button,callback:function(id){playbackManager.setSubtitleStreamIndex(parseInt(id),player)}})})}function getNowPlayingNameHtml(nowPlayingItem,includeNonNameInfo){return nowPlayingHelper.getNowPlayingNames(nowPlayingItem,includeNonNameInfo).map(function(i){return i.text}).join("
    ")}function seriesImageUrl(item,options){if("Episode"!==item.Type)return null;if(options=options||{},options.type=options.type||"Primary","Primary"===options.type&&item.SeriesPrimaryImageTag)return options.tag=item.SeriesPrimaryImageTag,connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.SeriesId,options);if("Thumb"===options.type){if(item.SeriesThumbImageTag)return options.tag=item.SeriesThumbImageTag,connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.SeriesId,options);if(item.ParentThumbImageTag)return options.tag=item.ParentThumbImageTag,connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.ParentThumbItemId,options)}return null}function imageUrl(item,options){return options=options||{},options.type=options.type||"Primary",item.ImageTags&&item.ImageTags[options.type]?(options.tag=item.ImageTags[options.type],connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.PrimaryImageItemId||item.Id,options)):item.AlbumId&&item.AlbumPrimaryImageTag?(options.tag=item.AlbumPrimaryImageTag,connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.AlbumId,options)):null}function updateNowPlayingInfo(context,state){var item=state.NowPlayingItem,displayName=item?getNowPlayingNameHtml(item).replace("
    "," - "):"";context.querySelector(".nowPlayingPageTitle").innerHTML=displayName,displayName.length>0?context.querySelector(".nowPlayingPageTitle").classList.remove("hide"):context.querySelector(".nowPlayingPageTitle").classList.add("hide");var url=item?seriesImageUrl(item,{maxHeight:300})||imageUrl(item,{maxHeight:300}):null;if(console.log("updateNowPlayingInfo"),setImageUrl(context,url),item){backdrop.setBackdrops([item]);var apiClient=connectionManager.getApiClient(item.ServerId);apiClient.getItem(apiClient.getCurrentUserId(),item.Id).then(function(fullItem){var userData=fullItem.UserData||{},likes=null==userData.Likes?"":userData.Likes;context.querySelector(".nowPlayingPageUserDataButtons").innerHTML=''})}else backdrop.clear(),context.querySelector(".nowPlayingPageUserDataButtons").innerHTML=""}function setImageUrl(context,url){currentImgUrl=url;var imgContainer=context.querySelector(".nowPlayingPageImageContainer");url?(imgContainer.innerHTML='',imgContainer.classList.remove("hide")):(imgContainer.classList.add("hide"),imgContainer.innerHTML="")}function buttonEnabled(btn,enabled){btn.disabled=!enabled}function buttonVisible(btn,enabled){enabled?btn.classList.remove("hide"):btn.classList.add("hide")}function updateSupportedCommands(context,commands){for(var all=context.querySelectorAll(".btnCommand"),i=0,length=all.length;i1&&-1!=supportedCommands.indexOf("SetAudioStreamIndex"))}function updateSubtitleTracksDisplay(player,context){var supportedCommands=currentPlayerSupportedCommands;buttonVisible(context.querySelector(".btnSubtitles"),playbackManager.subtitleTracks(player).length&&-1!=supportedCommands.indexOf("SetSubtitleStreamIndex"))}function updateRepeatModeDisplay(repeatMode){var context=dlg,toggleRepeatButton=context.querySelector(".repeatToggleButton");"RepeatAll"==repeatMode?(toggleRepeatButton.innerHTML="repeat",toggleRepeatButton.classList.add("repeatButton-active")):"RepeatOne"==repeatMode?(toggleRepeatButton.innerHTML="repeat_one",toggleRepeatButton.classList.add("repeatButton-active")):(toggleRepeatButton.innerHTML="repeat",toggleRepeatButton.classList.remove("repeatButton-active"))}function updatePlayerVolumeState(context,isMuted,volumeLevel){var view=context,supportedCommands=currentPlayerSupportedCommands,showMuteButton=!0,showVolumeSlider=!0;-1===supportedCommands.indexOf("Mute")&&(showMuteButton=!1),-1===supportedCommands.indexOf("SetVolume")&&(showVolumeSlider=!1),currentPlayer.isLocalPlayer&&appHost.supports("physicalvolumecontrol")&&(showMuteButton=!1,showVolumeSlider=!1),isMuted?(view.querySelector(".buttonMute").setAttribute("title",globalize.translate("Unmute")),view.querySelector(".buttonMute i").innerHTML=""):(view.querySelector(".buttonMute").setAttribute("title",globalize.translate("Mute")),view.querySelector(".buttonMute i").innerHTML=""),showMuteButton?view.querySelector(".buttonMute").classList.remove("hide"):view.querySelector(".buttonMute").classList.add("hide");var nowPlayingVolumeSlider=context.querySelector(".nowPlayingVolumeSlider"),nowPlayingVolumeSliderContainer=context.querySelector(".nowPlayingVolumeSliderContainer");nowPlayingVolumeSlider&&(showVolumeSlider?nowPlayingVolumeSliderContainer.classList.remove("hide"):nowPlayingVolumeSliderContainer.classList.add("hide"),nowPlayingVolumeSlider.dragging||(nowPlayingVolumeSlider.value=volumeLevel||0))}function updatePlayPauseState(isPaused,isActive){var context=dlg,btnPlayPause=context.querySelector(".btnPlayPause");btnPlayPause.querySelector("i").innerHTML=isPaused?"play_arrow":"pause",buttonVisible(btnPlayPause,isActive)}function updateTimeDisplay(positionTicks,runtimeTicks){var context=dlg,positionSlider=context.querySelector(".nowPlayingPositionSlider");if(positionSlider&&!positionSlider.dragging)if(runtimeTicks){var pct=positionTicks/runtimeTicks;pct*=100,positionSlider.value=pct}else positionSlider.value=0;context.querySelector(".positionTime").innerHTML=null==positionTicks?"--:--":datetime.getDisplayRunningTime(positionTicks),context.querySelector(".runtime").innerHTML=null!=runtimeTicks?datetime.getDisplayRunningTime(runtimeTicks):"--:--"}function getPlaylistItems(player){return playbackManager.getPlaylist(player)}function loadPlaylist(context,player){getPlaylistItems(player).then(function(items){var html="";html+=listView.getListViewHtml({items:items,smallIcon:!0,action:"setplaylistindex",enableUserDataButtons:!1,rightButtons:[{icon:"",title:globalize.translate("ButtonRemove"),id:"remove"}],dragHandle:!0}),items.length?context.querySelector(".playlistSection").classList.remove("hide"):context.querySelector(".playlistSection").classList.add("hide");var itemsContainer=context.querySelector(".playlist");itemsContainer.innerHTML=html;var playlistItemId=playbackManager.getCurrentPlaylistItemId(player);if(playlistItemId){var img=itemsContainer.querySelector('.listItem[data-playlistItemId="'+playlistItemId+'"] .listItemImage');img&&(img.classList.remove("lazy"),img.classList.add("playlistIndexIndicatorImage"))}imageLoader.lazyChildren(itemsContainer)})}function onPlaybackStart(e,state){console.log("remotecontrol event: "+e.type);var player=this;onStateChanged.call(player,e,state)}function onRepeatModeChange(e){var player=this;updateRepeatModeDisplay(playbackManager.getRepeatMode(player))}function onPlaylistUpdate(e){loadPlaylist(dlg,this)}function onPlaylistItemRemoved(e,info){for(var context=dlg,playlistItemIds=info.playlistItemIds,i=0,length=playlistItemIds.length;i") + } + + function seriesImageUrl(item, options) { + if ("Episode" !== item.Type) return null; + if (options = options || {}, options.type = options.type || "Primary", "Primary" === options.type && item.SeriesPrimaryImageTag) return options.tag = item.SeriesPrimaryImageTag, connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.SeriesId, options); + if ("Thumb" === options.type) { + if (item.SeriesThumbImageTag) return options.tag = item.SeriesThumbImageTag, connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.SeriesId, options); + if (item.ParentThumbImageTag) return options.tag = item.ParentThumbImageTag, connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.ParentThumbItemId, options) + } + return null + } + + function imageUrl(item, options) { + return options = options || {}, options.type = options.type || "Primary", item.ImageTags && item.ImageTags[options.type] ? (options.tag = item.ImageTags[options.type], connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.PrimaryImageItemId || item.Id, options)) : item.AlbumId && item.AlbumPrimaryImageTag ? (options.tag = item.AlbumPrimaryImageTag, connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.AlbumId, options)) : null + } + + function updateNowPlayingInfo(context, state) { + var item = state.NowPlayingItem, + displayName = item ? getNowPlayingNameHtml(item).replace("
    ", " - ") : ""; + context.querySelector(".nowPlayingPageTitle").innerHTML = displayName, displayName.length > 0 ? context.querySelector(".nowPlayingPageTitle").classList.remove("hide") : context.querySelector(".nowPlayingPageTitle").classList.add("hide"); + var url = item ? seriesImageUrl(item, { + maxHeight: 300 + }) || imageUrl(item, { + maxHeight: 300 + }) : null; + if (console.log("updateNowPlayingInfo"), setImageUrl(context, url), item) { + backdrop.setBackdrops([item]); + var apiClient = connectionManager.getApiClient(item.ServerId); + apiClient.getItem(apiClient.getCurrentUserId(), item.Id).then(function(fullItem) { + var userData = fullItem.UserData || {}, + likes = null == userData.Likes ? "" : userData.Likes; + context.querySelector(".nowPlayingPageUserDataButtons").innerHTML = '' + }) + } else backdrop.clear(), context.querySelector(".nowPlayingPageUserDataButtons").innerHTML = "" + } + + function setImageUrl(context, url) { + currentImgUrl = url; + var imgContainer = context.querySelector(".nowPlayingPageImageContainer"); + url ? (imgContainer.innerHTML = '', imgContainer.classList.remove("hide")) : (imgContainer.classList.add("hide"), imgContainer.innerHTML = "") + } + + function buttonEnabled(btn, enabled) { + btn.disabled = !enabled + } + + function buttonVisible(btn, enabled) { + enabled ? btn.classList.remove("hide") : btn.classList.add("hide") + } + + function updateSupportedCommands(context, commands) { + for (var all = context.querySelectorAll(".btnCommand"), i = 0, length = all.length; i < length; i++) buttonEnabled(all[i], -1 != commands.indexOf(all[i].getAttribute("data-command"))) + } + var currentImgUrl; + return function() { + function toggleRepeat(player) { + if (player) switch (playbackManager.getRepeatMode(player)) { + case "RepeatNone": + playbackManager.setRepeatMode("RepeatAll", player); + break; + case "RepeatAll": + playbackManager.setRepeatMode("RepeatOne", player); + break; + case "RepeatOne": + playbackManager.setRepeatMode("RepeatNone", player) + } + } + + function updatePlayerState(player, context, state) { + lastPlayerState = state; + var item = state.NowPlayingItem, + playerInfo = playbackManager.getPlayerInfo(), + supportedCommands = playerInfo.supportedCommands; + currentPlayerSupportedCommands = supportedCommands; + var playState = state.PlayState || {}; + buttonVisible(context.querySelector(".btnToggleFullscreen"), item && "Video" == item.MediaType && -1 != supportedCommands.indexOf("ToggleFullscreen")), updateAudioTracksDisplay(player, context), updateSubtitleTracksDisplay(player, context), -1 != supportedCommands.indexOf("DisplayMessage") ? context.querySelector(".sendMessageSection").classList.remove("hide") : context.querySelector(".sendMessageSection").classList.add("hide"), -1 != supportedCommands.indexOf("SendString") ? context.querySelector(".sendTextSection").classList.remove("hide") : context.querySelector(".sendTextSection").classList.add("hide"), buttonVisible(context.querySelector(".btnStop"), null != item), buttonVisible(context.querySelector(".btnNextTrack"), null != item), buttonVisible(context.querySelector(".btnPreviousTrack"), null != item), buttonVisible(context.querySelector(".btnRewind"), null != item), buttonVisible(context.querySelector(".btnFastForward"), null != item); + var positionSlider = context.querySelector(".nowPlayingPositionSlider"); + if (positionSlider && !positionSlider.dragging) { + positionSlider.disabled = !playState.CanSeek; + var isProgressClear = state.MediaSource && null == state.MediaSource.RunTimeTicks; + positionSlider.setIsClear(isProgressClear) + } + updatePlayPauseState(playState.IsPaused, null != item), updateTimeDisplay(playState.PositionTicks, item ? item.RunTimeTicks : null), updatePlayerVolumeState(context, playState.IsMuted, playState.VolumeLevel), item && "Video" == item.MediaType ? context.classList.remove("hideVideoButtons") : context.classList.add("hideVideoButtons"), updateRepeatModeDisplay(playState.RepeatMode), updateNowPlayingInfo(context, state) + } + + function updateAudioTracksDisplay(player, context) { + var supportedCommands = currentPlayerSupportedCommands; + buttonVisible(context.querySelector(".btnAudioTracks"), playbackManager.audioTracks(player).length > 1 && -1 != supportedCommands.indexOf("SetAudioStreamIndex")) + } + + function updateSubtitleTracksDisplay(player, context) { + var supportedCommands = currentPlayerSupportedCommands; + buttonVisible(context.querySelector(".btnSubtitles"), playbackManager.subtitleTracks(player).length && -1 != supportedCommands.indexOf("SetSubtitleStreamIndex")) + } + + function updateRepeatModeDisplay(repeatMode) { + var context = dlg, + toggleRepeatButton = context.querySelector(".repeatToggleButton"); + "RepeatAll" == repeatMode ? (toggleRepeatButton.innerHTML = "repeat", toggleRepeatButton.classList.add("repeatButton-active")) : "RepeatOne" == repeatMode ? (toggleRepeatButton.innerHTML = "repeat_one", toggleRepeatButton.classList.add("repeatButton-active")) : (toggleRepeatButton.innerHTML = "repeat", toggleRepeatButton.classList.remove("repeatButton-active")) + } + + function updatePlayerVolumeState(context, isMuted, volumeLevel) { + var view = context, + supportedCommands = currentPlayerSupportedCommands, + showMuteButton = !0, + showVolumeSlider = !0; - 1 === supportedCommands.indexOf("Mute") && (showMuteButton = !1), -1 === supportedCommands.indexOf("SetVolume") && (showVolumeSlider = !1), currentPlayer.isLocalPlayer && appHost.supports("physicalvolumecontrol") && (showMuteButton = !1, showVolumeSlider = !1), isMuted ? (view.querySelector(".buttonMute").setAttribute("title", globalize.translate("Unmute")), view.querySelector(".buttonMute i").innerHTML = "") : (view.querySelector(".buttonMute").setAttribute("title", globalize.translate("Mute")), view.querySelector(".buttonMute i").innerHTML = ""), showMuteButton ? view.querySelector(".buttonMute").classList.remove("hide") : view.querySelector(".buttonMute").classList.add("hide"); + var nowPlayingVolumeSlider = context.querySelector(".nowPlayingVolumeSlider"), + nowPlayingVolumeSliderContainer = context.querySelector(".nowPlayingVolumeSliderContainer"); + nowPlayingVolumeSlider && (showVolumeSlider ? nowPlayingVolumeSliderContainer.classList.remove("hide") : nowPlayingVolumeSliderContainer.classList.add("hide"), nowPlayingVolumeSlider.dragging || (nowPlayingVolumeSlider.value = volumeLevel || 0)) + } + + function updatePlayPauseState(isPaused, isActive) { + var context = dlg, + btnPlayPause = context.querySelector(".btnPlayPause"); + btnPlayPause.querySelector("i").innerHTML = isPaused ? "play_arrow" : "pause", buttonVisible(btnPlayPause, isActive) + } + + function updateTimeDisplay(positionTicks, runtimeTicks) { + var context = dlg, + positionSlider = context.querySelector(".nowPlayingPositionSlider"); + if (positionSlider && !positionSlider.dragging) + if (runtimeTicks) { + var pct = positionTicks / runtimeTicks; + pct *= 100, positionSlider.value = pct + } else positionSlider.value = 0; + context.querySelector(".positionTime").innerHTML = null == positionTicks ? "--:--" : datetime.getDisplayRunningTime(positionTicks), context.querySelector(".runtime").innerHTML = null != runtimeTicks ? datetime.getDisplayRunningTime(runtimeTicks) : "--:--" + } + + function getPlaylistItems(player) { + return playbackManager.getPlaylist(player) + } + + function loadPlaylist(context, player) { + getPlaylistItems(player).then(function(items) { + var html = ""; + html += listView.getListViewHtml({ + items: items, + smallIcon: !0, + action: "setplaylistindex", + enableUserDataButtons: !1, + rightButtons: [{ + icon: "", + title: globalize.translate("ButtonRemove"), + id: "remove" + }], + dragHandle: !0 + }), items.length ? context.querySelector(".playlistSection").classList.remove("hide") : context.querySelector(".playlistSection").classList.add("hide"); + var itemsContainer = context.querySelector(".playlist"); + itemsContainer.innerHTML = html; + var playlistItemId = playbackManager.getCurrentPlaylistItemId(player); + if (playlistItemId) { + var img = itemsContainer.querySelector('.listItem[data-playlistItemId="' + playlistItemId + '"] .listItemImage'); + img && (img.classList.remove("lazy"), img.classList.add("playlistIndexIndicatorImage")) + } + imageLoader.lazyChildren(itemsContainer) + }) + } + + function onPlaybackStart(e, state) { + console.log("remotecontrol event: " + e.type); + var player = this; + onStateChanged.call(player, e, state) + } + + function onRepeatModeChange(e) { + var player = this; + updateRepeatModeDisplay(playbackManager.getRepeatMode(player)) + } + + function onPlaylistUpdate(e) { + loadPlaylist(dlg, this) + } + + function onPlaylistItemRemoved(e, info) { + for (var context = dlg, playlistItemIds = info.playlistItemIds, i = 0, length = playlistItemIds.length; i < length; i++) { + var listItem = context.querySelector('.listItem[data-playlistItemId="' + playlistItemIds[i] + '"]'); + listItem && listItem.parentNode.removeChild(listItem) + } + } + + function onPlaybackStopped(e, state) { + console.log("remotecontrol event: " + e.type); + var player = this; + state.NextMediaType || (updatePlayerState(player, dlg, {}), loadPlaylist(dlg)) + } + + function onPlayPauseStateChanged(e) { + updatePlayPauseState(this.paused(), !0) + } + + function onStateChanged(event, state) { + var player = this; + updatePlayerState(player, dlg, state), loadPlaylist(dlg, player) + } + + function onTimeUpdate(e) { + var now = (new Date).getTime(); + if (!(now - lastUpdateTime < 700)) { + lastUpdateTime = now; + var player = this; + currentRuntimeTicks = playbackManager.duration(player), updateTimeDisplay(playbackManager.currentTime(player), currentRuntimeTicks) + } + } + + function onVolumeChanged(e) { + var player = this; + updatePlayerVolumeState(dlg, player.isMuted(), player.getVolume()) + } + + function releaseCurrentPlayer() { + var player = currentPlayer; + player && (events.off(player, "playbackstart", onPlaybackStart), events.off(player, "statechange", onStateChanged), events.off(player, "repeatmodechange", onRepeatModeChange), events.off(player, "playlistitemremove", onPlaylistUpdate), events.off(player, "playlistitemmove", onPlaylistUpdate), events.off(player, "playbackstop", onPlaybackStopped), events.off(player, "volumechange", onVolumeChanged), events.off(player, "pause", onPlayPauseStateChanged), events.off(player, "unpause", onPlayPauseStateChanged), events.off(player, "timeupdate", onTimeUpdate), currentPlayer = null) + } + + function bindToPlayer(context, player) { + if (releaseCurrentPlayer(), currentPlayer = player, player) { + var state = playbackManager.getPlayerState(player); + onStateChanged.call(player, { + type: "init" + }, state), events.on(player, "playbackstart", onPlaybackStart), events.on(player, "statechange", onStateChanged), events.on(player, "repeatmodechange", onRepeatModeChange), events.on(player, "playlistitemremove", onPlaylistItemRemoved), events.on(player, "playlistitemmove", onPlaylistUpdate), events.on(player, "playbackstop", onPlaybackStopped), events.on(player, "volumechange", onVolumeChanged), events.on(player, "pause", onPlayPauseStateChanged), events.on(player, "unpause", onPlayPauseStateChanged), events.on(player, "timeupdate", onTimeUpdate); + var playerInfo = playbackManager.getPlayerInfo(), + supportedCommands = playerInfo.supportedCommands; + currentPlayerSupportedCommands = supportedCommands, updateSupportedCommands(context, supportedCommands) + } + } + + function onBtnCommandClick() { + currentPlayer && (this.classList.contains("repeatToggleButton") ? toggleRepeat(currentPlayer) : playbackManager.sendCommand({ + Name: this.getAttribute("data-command") + }, currentPlayer)) + } + + function getSaveablePlaylistItems() { + return getPlaylistItems(currentPlayer).then(function(items) { + return items.filter(function(i) { + return i.Id && i.ServerId + }) + }) + } + + function savePlaylist() { + require(["playlistEditor"], function(playlistEditor) { + getSaveablePlaylistItems().then(function(items) { + var serverId = items.length ? items[0].ServerId : ApiClient.serverId(); + (new playlistEditor).show({ + items: items.map(function(i) { + return i.Id + }), + serverId: serverId, + enableAddToPlayQueue: !1, + defaultValue: "new" + }) + }) + }) + } + + function bindEvents(context) { + for (var btnCommand = context.querySelectorAll(".btnCommand"), i = 0, length = btnCommand.length; i < length; i++) btnCommand[i].addEventListener("click", onBtnCommandClick); + context.querySelector(".btnToggleFullscreen").addEventListener("click", function(e) { + currentPlayer && playbackManager.sendCommand({ + Name: e.target.getAttribute("data-command") + }, currentPlayer) + }), context.querySelector(".btnAudioTracks").addEventListener("click", function(e) { + currentPlayer && lastPlayerState && lastPlayerState.NowPlayingItem && showAudioMenu(context, currentPlayer, e.target, lastPlayerState.NowPlayingItem) + }), context.querySelector(".btnSubtitles").addEventListener("click", function(e) { + currentPlayer && lastPlayerState && lastPlayerState.NowPlayingItem && showSubtitleMenu(context, currentPlayer, e.target, lastPlayerState.NowPlayingItem) + }), context.querySelector(".btnStop").addEventListener("click", function() { + currentPlayer && playbackManager.stop(currentPlayer) + }), context.querySelector(".btnPlayPause").addEventListener("click", function() { + currentPlayer && playbackManager.playPause(currentPlayer) + }), context.querySelector(".btnNextTrack").addEventListener("click", function() { + currentPlayer && playbackManager.nextTrack(currentPlayer) + }), context.querySelector(".btnRewind").addEventListener("click", function() { + currentPlayer && playbackManager.rewind(currentPlayer) + }), context.querySelector(".btnFastForward").addEventListener("click", function() { + currentPlayer && playbackManager.fastForward(currentPlayer) + }), context.querySelector(".btnPreviousTrack").addEventListener("click", function() { + currentPlayer && playbackManager.previousTrack(currentPlayer) + }), context.querySelector(".nowPlayingPositionSlider").addEventListener("change", function() { + var value = this.value; + if (currentPlayer) { + var newPercent = parseFloat(value); + playbackManager.seekPercent(newPercent, currentPlayer) + } + }), context.querySelector(".nowPlayingPositionSlider").getBubbleText = function(value) { + var state = lastPlayerState; + if (!state || !state.NowPlayingItem || !currentRuntimeTicks) return "--:--"; + var ticks = currentRuntimeTicks; + return ticks /= 100, ticks *= value, datetime.getDisplayRunningTime(ticks) + }, context.querySelector(".nowPlayingVolumeSlider").addEventListener("change", function() { + playbackManager.setVolume(this.value, currentPlayer) + }), context.querySelector(".buttonMute").addEventListener("click", function() { + playbackManager.toggleMute(currentPlayer) + }); + var playlistContainer = context.querySelector(".playlist"); + playlistContainer.addEventListener("action-remove", function(e) { + playbackManager.removeFromPlaylist([e.detail.playlistItemId], currentPlayer) + }), playlistContainer.addEventListener("itemdrop", function(e) { + var newIndex = e.detail.newIndex, + playlistItemId = e.detail.playlistItemId; + playbackManager.movePlaylistItem(playlistItemId, newIndex, currentPlayer) + }), context.querySelector(".btnSavePlaylist").addEventListener("click", savePlaylist) + } + + function onPlayerChange() { + bindToPlayer(dlg, playbackManager.getCurrentPlayer()) + } + + function onMessageSubmit(e) { + var form = e.target; + return playbackManager.sendCommand({ + Name: "DisplayMessage", + Arguments: { + Header: form.querySelector("#txtMessageTitle").value, + Text: form.querySelector("#txtMessageText", form).value + } + }, currentPlayer), form.querySelector("input").value = "", require(["toast"], function(toast) { + toast("Message sent.") + }), e.preventDefault(), e.stopPropagation(), !1 + } + + function onSendStringSubmit(e) { + var form = e.target; + return playbackManager.sendCommand({ + Name: "SendString", + Arguments: { + String: form.querySelector("#txtTypeText", form).value + } + }, currentPlayer), form.querySelector("input").value = "", require(["toast"], function(toast) { + toast("Text sent.") + }), e.preventDefault(), e.stopPropagation(), !1 + } + + function init(ownerView, context) { + bindEvents(context), context.querySelector(".sendMessageForm").addEventListener("submit", onMessageSubmit), context.querySelector(".typeTextForm").addEventListener("submit", onSendStringSubmit), events.on(playbackManager, "playerchange", onPlayerChange) + } + + function onDialogClosed(e) { + releaseCurrentPlayer(), events.off(playbackManager, "playerchange", onPlayerChange), lastPlayerState = null + } + + function onShow(context, tab) { + currentImgUrl = null, bindToPlayer(context, playbackManager.getCurrentPlayer()) + } + var dlg, currentPlayer, lastPlayerState, currentPlayerSupportedCommands = [], + lastUpdateTime = 0, + currentRuntimeTicks = 0, + self = this; + self.init = function(ownerView, context) { + dlg = context, init(ownerView, dlg) + }, self.onShow = function() { + onShow(dlg, window.location.hash) + }, self.destroy = function() { + onDialogClosed() + } + } +}); \ No newline at end of file diff --git a/dashboard-ui/components/tunerpicker.js b/dashboard-ui/components/tunerpicker.js index a9e4cc180c..784f677430 100644 --- a/dashboard-ui/components/tunerpicker.js +++ b/dashboard-ui/components/tunerpicker.js @@ -1 +1,78 @@ -define(["dialogHelper","dom","layoutManager","connectionManager","globalize","loading","material-icons","formDialogStyle","emby-button","emby-itemscontainer","cardStyle"],function(dialogHelper,dom,layoutManager,connectionManager,globalize,loading){"use strict";function getEditorHtml(){var html="";return html+='
    ',html+='
    ',html+='
    ',html+="

    "+globalize.translate("DetectingDevices")+"...

    ",html+="

    "+globalize.translate("MessagePleaseWait")+"

    ",html+="
    ",html+='

    '+globalize.translate("HeaderNewDevices")+"

    ",html+='
    ',html+="
    ",html+="
    ",html+="
    "}function getDeviceHtml(device){var padderClass,html="",cssClass="card scalableCard",cardBoxCssClass="cardBox visualCardBox";return cssClass+=" backdropCard backdropCard-scalable",padderClass="cardPadder-backdrop",layoutManager.tv&&(cssClass+=" card-focusscale",cardBoxCssClass+=" cardBox-focustransform"),cardBoxCssClass+=" card-focuscontent",html+='"}function getTunerName(providerId){switch(providerId=providerId.toLowerCase()){case"m3u":return"M3U";case"hdhomerun":return"HDHomerun";case"hauppauge":return"Hauppauge";case"satip":return"DVB";default:return"Unknown"}}function renderDevices(view,devices){var i,length,html="";for(i=0,length=devices.length;i
    "+globalize.translate("NoNewDevicesFound")+"

    ",view.querySelector(".devicesHeader").classList.add("hide"));var elem=view.querySelector(".results");elem.innerHTML=html,layoutManager.tv&&focusManager.autoFocus(elem)}function discoverDevices(view,apiClient){return loading.show(),view.querySelector(".loadingContent").classList.remove("hide"),ApiClient.getJSON(ApiClient.getUrl("LiveTv/Tuners/Discvover",{NewDevicesOnly:!0})).then(function(devices){currentDevices=devices,renderDevices(view,devices),view.querySelector(".loadingContent").classList.add("hide"),loading.hide()})}function tunerPicker(){this.show=function(options){var dialogOptions={removeOnClose:!0,scrollY:!1};layoutManager.tv?dialogOptions.size="fullscreen":dialogOptions.size="small";var dlg=dialogHelper.createDialog(dialogOptions);dlg.classList.add("formDialog");var html="";html+='
    ',html+='',html+='

    ',html+=globalize.translate("HeaderLiveTvTunerSetup"),html+="

    ",html+="
    ",html+=getEditorHtml(),dlg.innerHTML=html,dlg.querySelector(".btnCancel").addEventListener("click",function(){dialogHelper.close(dlg)});var deviceResult;dlg.querySelector(".results").addEventListener("click",function(e){var tunerCard=dom.parentWithClass(e.target,"card");if(tunerCard){var deviceId=tunerCard.getAttribute("data-id");deviceResult=currentDevices.filter(function(d){return d.DeviceId===deviceId})[0],dialogHelper.close(dlg)}}),layoutManager.tv&¢erFocus(dlg.querySelector(".formDialogContent"),!1,!0);var apiClient=connectionManager.getApiClient(options.serverId);return discoverDevices(dlg,apiClient),layoutManager.tv&¢erFocus(dlg.querySelector(".formDialogContent"),!1,!1),dialogHelper.open(dlg).then(function(){return deviceResult?Promise.resolve(deviceResult):Promise.reject()})}}var currentDevices=[];return tunerPicker}); \ No newline at end of file +define(["dialogHelper", "dom", "layoutManager", "connectionManager", "globalize", "loading", "material-icons", "formDialogStyle", "emby-button", "emby-itemscontainer", "cardStyle"], function(dialogHelper, dom, layoutManager, connectionManager, globalize, loading) { + "use strict"; + + function getEditorHtml() { + var html = ""; + return html += '
    ', html += '
    ', html += '
    ', html += "

    " + globalize.translate("DetectingDevices") + "...

    ", html += "

    " + globalize.translate("MessagePleaseWait") + "

    ", html += "
    ", html += '

    ' + globalize.translate("HeaderNewDevices") + "

    ", html += '
    ', html += "
    ", html += "
    ", html += "
    " + } + + function getDeviceHtml(device) { + var padderClass, html = "", + cssClass = "card scalableCard", + cardBoxCssClass = "cardBox visualCardBox"; + return cssClass += " backdropCard backdropCard-scalable", padderClass = "cardPadder-backdrop", layoutManager.tv && (cssClass += " card-focusscale", cardBoxCssClass += " cardBox-focustransform"), cardBoxCssClass += " card-focuscontent", html += '" + } + + function getTunerName(providerId) { + switch (providerId = providerId.toLowerCase()) { + case "m3u": + return "M3U"; + case "hdhomerun": + return "HDHomerun"; + case "hauppauge": + return "Hauppauge"; + case "satip": + return "DVB"; + default: + return "Unknown" + } + } + + function renderDevices(view, devices) { + var i, length, html = ""; + for (i = 0, length = devices.length; i < length; i++) html += getDeviceHtml(devices[i]); + devices.length ? view.querySelector(".devicesHeader").classList.remove("hide") : (html = "


    " + globalize.translate("NoNewDevicesFound") + "

    ", view.querySelector(".devicesHeader").classList.add("hide")); + var elem = view.querySelector(".results"); + elem.innerHTML = html, layoutManager.tv && focusManager.autoFocus(elem) + } + + function discoverDevices(view, apiClient) { + return loading.show(), view.querySelector(".loadingContent").classList.remove("hide"), ApiClient.getJSON(ApiClient.getUrl("LiveTv/Tuners/Discvover", { + NewDevicesOnly: !0 + })).then(function(devices) { + currentDevices = devices, renderDevices(view, devices), view.querySelector(".loadingContent").classList.add("hide"), loading.hide() + }) + } + + function tunerPicker() { + this.show = function(options) { + var dialogOptions = { + removeOnClose: !0, + scrollY: !1 + }; + layoutManager.tv ? dialogOptions.size = "fullscreen" : dialogOptions.size = "small"; + var dlg = dialogHelper.createDialog(dialogOptions); + dlg.classList.add("formDialog"); + var html = ""; + html += '
    ', html += '', html += '

    ', html += globalize.translate("HeaderLiveTvTunerSetup"), html += "

    ", html += "
    ", html += getEditorHtml(), dlg.innerHTML = html, dlg.querySelector(".btnCancel").addEventListener("click", function() { + dialogHelper.close(dlg) + }); + var deviceResult; + dlg.querySelector(".results").addEventListener("click", function(e) { + var tunerCard = dom.parentWithClass(e.target, "card"); + if (tunerCard) { + var deviceId = tunerCard.getAttribute("data-id"); + deviceResult = currentDevices.filter(function(d) { + return d.DeviceId === deviceId + })[0], dialogHelper.close(dlg) + } + }), layoutManager.tv && centerFocus(dlg.querySelector(".formDialogContent"), !1, !0); + var apiClient = connectionManager.getApiClient(options.serverId); + return discoverDevices(dlg, apiClient), layoutManager.tv && centerFocus(dlg.querySelector(".formDialogContent"), !1, !1), dialogHelper.open(dlg).then(function() { + return deviceResult ? Promise.resolve(deviceResult) : Promise.reject() + }) + } + } + var currentDevices = []; + return tunerPicker +}); \ No newline at end of file diff --git a/dashboard-ui/components/tvproviders/schedulesdirect.js b/dashboard-ui/components/tvproviders/schedulesdirect.js index aa16652d34..0eb54a472d 100644 --- a/dashboard-ui/components/tvproviders/schedulesdirect.js +++ b/dashboard-ui/components/tvproviders/schedulesdirect.js @@ -1 +1,174 @@ -define(["jQuery","loading","emby-checkbox","listViewStyle","emby-input","emby-select","emby-linkbutton","flexStyles"],function($,loading){"use strict";return function(page,providerId,options){function reload(){loading.show(),ApiClient.getNamedConfiguration("livetv").then(function(config){var info=config.ListingProviders.filter(function(i){return i.Id===providerId})[0]||{};listingsId=info.ListingsId,$("#selectListing",page).val(info.ListingsId||""),page.querySelector(".txtUser").value=info.Username||"",page.querySelector(".txtPass").value="",page.querySelector(".txtZipCode").value=info.ZipCode||"",info.Username&&info.Password?page.querySelector(".listingsSection").classList.remove("hide"):page.querySelector(".listingsSection").classList.add("hide"),page.querySelector(".chkAllTuners").checked=info.EnableAllTuners,page.querySelector(".chkAllTuners").checked?page.querySelector(".selectTunersSection").classList.add("hide"):page.querySelector(".selectTunersSection").classList.remove("hide"),setCountry(info),refreshTunerDevices(page,info,config.TunerHosts)})}function setCountry(info){ApiClient.getJSON(ApiClient.getUrl("LiveTv/ListingProviders/SchedulesDirect/Countries")).then(function(result){var i,length,countryList=[];for(var region in result){var countries=result[region];if(countries.length&&"ZZZ"!==region)for(i=0,length=countries.length;ib.name?1:a.name'+c.name+""}).join("")).val(info.Country||""),$(page.querySelector(".txtZipCode")).trigger("change")},function(){Dashboard.alert({message:Globalize.translate("ErrorGettingTvLineups")})}),loading.hide()}function sha256(str){if(!self.TextEncoder)return Promise.resolve("");var buffer=new TextEncoder("utf-8").encode(str);return crypto.subtle.digest("SHA-256",buffer).then(function(hash){return hex(hash)})}function hex(buffer){for(var hexCodes=[],view=new DataView(buffer),i=0;i'+o.Name+""})),listingsId&&$("#selectListing",page).val(listingsId),loading.hide()},function(result){Dashboard.alert({message:Globalize.translate("ErrorGettingTvLineups")}),refreshListings(""),loading.hide()})}function getTunerName(providerId){switch(providerId=providerId.toLowerCase()){case"m3u":return"M3U Playlist";case"hdhomerun":return"HDHomerun";case"satip":return"DVB";default:return"Unknown"}}function refreshTunerDevices(page,providerInfo,devices){for(var html="",i=0,length=devices.length;i';var enabledTuners=providerInfo.EnabledTuners||[],isChecked=providerInfo.EnableAllTuners||-1!==enabledTuners.indexOf(device.Id),checkedAttribute=isChecked?" checked":"";html+='",html+='
    ',html+='
    ',html+=device.FriendlyName||getTunerName(device.Type),html+="
    ",html+='
    ',html+=device.Url,html+="
    ",html+="
    ",html+=""}page.querySelector(".tunerList").innerHTML=html}var listingsId,self=this;self.submit=function(){page.querySelector(".btnSubmitListingsContainer").click()},self.init=function(){options=options||{},!1!==options.showCancelButton?page.querySelector(".btnCancel").classList.remove("hide"):page.querySelector(".btnCancel").classList.add("hide"),!1!==options.showSubmitButton?page.querySelector(".btnSubmitListings").classList.remove("hide"):page.querySelector(".btnSubmitListings").classList.add("hide"),$(".formLogin",page).on("submit",function(){return submitLoginForm(),!1}),$(".formListings",page).on("submit",function(){return submitListingsForm(),!1}),$(".txtZipCode",page).on("change",function(){refreshListings(this.value)}),page.querySelector(".chkAllTuners").addEventListener("change",function(e){e.target.checked?page.querySelector(".selectTunersSection").classList.add("hide"):page.querySelector(".selectTunersSection").classList.remove("hide")}),$(".createAccountHelp",page).html(Globalize.translate("MessageCreateAccountAt",'http://www.schedulesdirect.org')),reload()}}}); \ No newline at end of file +define(["jQuery", "loading", "emby-checkbox", "listViewStyle", "emby-input", "emby-select", "emby-linkbutton", "flexStyles"], function($, loading) { + "use strict"; + return function(page, providerId, options) { + function reload() { + loading.show(), ApiClient.getNamedConfiguration("livetv").then(function(config) { + var info = config.ListingProviders.filter(function(i) { + return i.Id === providerId + })[0] || {}; + listingsId = info.ListingsId, $("#selectListing", page).val(info.ListingsId || ""), page.querySelector(".txtUser").value = info.Username || "", page.querySelector(".txtPass").value = "", page.querySelector(".txtZipCode").value = info.ZipCode || "", info.Username && info.Password ? page.querySelector(".listingsSection").classList.remove("hide") : page.querySelector(".listingsSection").classList.add("hide"), page.querySelector(".chkAllTuners").checked = info.EnableAllTuners, page.querySelector(".chkAllTuners").checked ? page.querySelector(".selectTunersSection").classList.add("hide") : page.querySelector(".selectTunersSection").classList.remove("hide"), setCountry(info), refreshTunerDevices(page, info, config.TunerHosts) + }) + } + + function setCountry(info) { + ApiClient.getJSON(ApiClient.getUrl("LiveTv/ListingProviders/SchedulesDirect/Countries")).then(function(result) { + var i, length, countryList = []; + for (var region in result) { + var countries = result[region]; + if (countries.length && "ZZZ" !== region) + for (i = 0, length = countries.length; i < length; i++) countryList.push({ + name: countries[i].fullName, + value: countries[i].shortName + }) + } + countryList.sort(function(a, b) { + return a.name > b.name ? 1 : a.name < b.name ? -1 : 0 + }), $("#selectCountry", page).html(countryList.map(function(c) { + return '" + }).join("")).val(info.Country || ""), $(page.querySelector(".txtZipCode")).trigger("change") + }, function() { + Dashboard.alert({ + message: Globalize.translate("ErrorGettingTvLineups") + }) + }), loading.hide() + } + + function sha256(str) { + if (!self.TextEncoder) return Promise.resolve(""); + var buffer = new TextEncoder("utf-8").encode(str); + return crypto.subtle.digest("SHA-256", buffer).then(function(hash) { + return hex(hash) + }) + } + + function hex(buffer) { + for (var hexCodes = [], view = new DataView(buffer), i = 0; i < view.byteLength; i += 4) { + var value = view.getUint32(i), + stringValue = value.toString(16), + paddedValue = ("00000000" + stringValue).slice(-"00000000".length); + hexCodes.push(paddedValue) + } + return hexCodes.join("") + } + + function submitLoginForm() { + loading.show(), sha256(page.querySelector(".txtPass").value).then(function(passwordHash) { + var info = { + Type: "SchedulesDirect", + Username: page.querySelector(".txtUser").value, + EnableAllTuners: !0, + Password: passwordHash, + Pw: page.querySelector(".txtPass").value + }, + id = providerId; + id && (info.Id = id), ApiClient.ajax({ + type: "POST", + url: ApiClient.getUrl("LiveTv/ListingProviders", { + ValidateLogin: !0 + }), + data: JSON.stringify(info), + contentType: "application/json", + dataType: "json" + }).then(function(result) { + Dashboard.processServerConfigurationUpdateResult(), providerId = result.Id, reload() + }, function() { + Dashboard.alert({ + message: Globalize.translate("ErrorSavingTvProvider") + }) + }) + }) + } + + function submitListingsForm() { + var selectedListingsId = $("#selectListing", page).val(); + if (!selectedListingsId) return void Dashboard.alert({ + message: Globalize.translate("ErrorPleaseSelectLineup") + }); + loading.show(); + var id = providerId; + ApiClient.getNamedConfiguration("livetv").then(function(config) { + var info = config.ListingProviders.filter(function(i) { + return i.Id === id + })[0]; + info.ZipCode = page.querySelector(".txtZipCode").value, info.Country = $("#selectCountry", page).val(), info.ListingsId = selectedListingsId, info.EnableAllTuners = page.querySelector(".chkAllTuners").checked, info.EnabledTuners = info.EnableAllTuners ? [] : $(".chkTuner", page).get().filter(function(i) { + return i.checked + }).map(function(i) { + return i.getAttribute("data-id") + }), ApiClient.ajax({ + type: "POST", + url: ApiClient.getUrl("LiveTv/ListingProviders", { + ValidateListings: !0 + }), + data: JSON.stringify(info), + contentType: "application/json" + }).then(function(result) { + loading.hide(), !1 !== options.showConfirmation && Dashboard.processServerConfigurationUpdateResult(), Events.trigger(self, "submitted") + }, function() { + loading.hide(), Dashboard.alert({ + message: Globalize.translate("ErrorAddingListingsToSchedulesDirect") + }) + }) + }) + } + + function refreshListings(value) { + if (!value) return void $("#selectListing", page).html(""); + loading.show(), ApiClient.ajax({ + type: "GET", + url: ApiClient.getUrl("LiveTv/ListingProviders/Lineups", { + Id: providerId, + Location: value, + Country: $("#selectCountry", page).val() + }), + dataType: "json" + }).then(function(result) { + $("#selectListing", page).html(result.map(function(o) { + return '" + })), listingsId && $("#selectListing", page).val(listingsId), loading.hide() + }, function(result) { + Dashboard.alert({ + message: Globalize.translate("ErrorGettingTvLineups") + }), refreshListings(""), loading.hide() + }) + } + + function getTunerName(providerId) { + switch (providerId = providerId.toLowerCase()) { + case "m3u": + return "M3U Playlist"; + case "hdhomerun": + return "HDHomerun"; + case "satip": + return "DVB"; + default: + return "Unknown" + } + } + + function refreshTunerDevices(page, providerInfo, devices) { + for (var html = "", i = 0, length = devices.length; i < length; i++) { + var device = devices[i]; + html += '
    '; + var enabledTuners = providerInfo.EnabledTuners || [], + isChecked = providerInfo.EnableAllTuners || -1 !== enabledTuners.indexOf(device.Id), + checkedAttribute = isChecked ? " checked" : ""; + html += '", html += '
    ', html += '
    ', html += device.FriendlyName || getTunerName(device.Type), html += "
    ", html += '
    ', html += device.Url, html += "
    ", html += "
    ", html += "
    " + } + page.querySelector(".tunerList").innerHTML = html + } + var listingsId, self = this; + self.submit = function() { + page.querySelector(".btnSubmitListingsContainer").click() + }, self.init = function() { + options = options || {}, !1 !== options.showCancelButton ? page.querySelector(".btnCancel").classList.remove("hide") : page.querySelector(".btnCancel").classList.add("hide"), !1 !== options.showSubmitButton ? page.querySelector(".btnSubmitListings").classList.remove("hide") : page.querySelector(".btnSubmitListings").classList.add("hide"), $(".formLogin", page).on("submit", function() { + return submitLoginForm(), !1 + }), $(".formListings", page).on("submit", function() { + return submitListingsForm(), !1 + }), $(".txtZipCode", page).on("change", function() { + refreshListings(this.value) + }), page.querySelector(".chkAllTuners").addEventListener("change", function(e) { + e.target.checked ? page.querySelector(".selectTunersSection").classList.add("hide") : page.querySelector(".selectTunersSection").classList.remove("hide") + }), $(".createAccountHelp", page).html(Globalize.translate("MessageCreateAccountAt", 'http://www.schedulesdirect.org')), reload() + } + } +}); \ No newline at end of file diff --git a/dashboard-ui/components/tvproviders/xmltv.js b/dashboard-ui/components/tvproviders/xmltv.js index ddfdb9b9b1..48185d2878 100644 --- a/dashboard-ui/components/tvproviders/xmltv.js +++ b/dashboard-ui/components/tvproviders/xmltv.js @@ -1 +1,109 @@ -define(["jQuery","registrationServices","loading","emby-checkbox","emby-input","listViewStyle","paper-icon-button-light"],function($,registrationServices,loading){"use strict";return function(page,providerId,options){function getListingProvider(config,id){if(config&&id){var result=config.ListingProviders.filter(function(i){return i.Id===id})[0];return result?Promise.resolve(result):getListingProvider()}return ApiClient.getJSON(ApiClient.getUrl("LiveTv/ListingProviders/Default"))}function reload(){loading.show(),ApiClient.getNamedConfiguration("livetv").then(function(config){getListingProvider(config,providerId).then(function(info){page.querySelector(".txtPath").value=info.Path||"",page.querySelector(".txtKids").value=(info.KidsCategories||[]).join("|"),page.querySelector(".txtNews").value=(info.NewsCategories||[]).join("|"),page.querySelector(".txtSports").value=(info.SportsCategories||[]).join("|"),page.querySelector(".txtMovies").value=(info.MovieCategories||[]).join("|"),page.querySelector(".txtMoviePrefix").value=info.MoviePrefix||"",page.querySelector(".txtUserAgent").value=info.UserAgent||"",page.querySelector(".chkAllTuners").checked=info.EnableAllTuners,page.querySelector(".chkAllTuners").checked?page.querySelector(".selectTunersSection").classList.add("hide"):page.querySelector(".selectTunersSection").classList.remove("hide"),refreshTunerDevices(page,info,config.TunerHosts),loading.hide()})})}function getCategories(txtInput){var value=txtInput.value;return value?value.split("|"):[]}function submitListingsForm(){loading.show();var id=providerId;ApiClient.getNamedConfiguration("livetv").then(function(config){var info=config.ListingProviders.filter(function(i){return i.Id===id})[0]||{};info.Type="xmltv",info.Path=page.querySelector(".txtPath").value,info.MoviePrefix=page.querySelector(".txtMoviePrefix").value||null,info.UserAgent=page.querySelector(".txtUserAgent").value||null,info.MovieCategories=getCategories(page.querySelector(".txtMovies")),info.KidsCategories=getCategories(page.querySelector(".txtKids")),info.NewsCategories=getCategories(page.querySelector(".txtNews")),info.SportsCategories=getCategories(page.querySelector(".txtSports")),info.EnableAllTuners=page.querySelector(".chkAllTuners").checked,info.EnabledTuners=info.EnableAllTuners?[]:$(".chkTuner",page).get().filter(function(i){return i.checked}).map(function(i){return i.getAttribute("data-id")}),ApiClient.ajax({type:"POST",url:ApiClient.getUrl("LiveTv/ListingProviders",{ValidateListings:!0}),data:JSON.stringify(info),contentType:"application/json"}).then(function(result){loading.hide(),!1!==options.showConfirmation&&Dashboard.processServerConfigurationUpdateResult(),Events.trigger(self,"submitted")},function(){loading.hide(),Dashboard.alert({message:Globalize.translate("ErrorAddingXmlTvFile")})})})}function getTunerName(providerId){switch(providerId=providerId.toLowerCase()){case"m3u":return"M3U Playlist";case"hdhomerun":return"HDHomerun";case"satip":return"DVB";default:return"Unknown"}}function refreshTunerDevices(page,providerInfo,devices){for(var html="",i=0,length=devices.length;i';var enabledTuners=providerInfo.EnabledTuners||[],isChecked=providerInfo.EnableAllTuners||-1!==enabledTuners.indexOf(device.Id),checkedAttribute=isChecked?" checked":"";html+='",html+='
    ',html+='
    ',html+=device.FriendlyName||getTunerName(device.Type),html+="
    ",html+='
    ',html+=device.Url,html+="
    ",html+="
    ",html+=""}page.querySelector(".tunerList").innerHTML=html}function onSelectPathClick(e){var page=$(e.target).parents(".xmltvForm")[0];require(["directorybrowser"],function(directoryBrowser){var picker=new directoryBrowser;picker.show({includeFiles:!0,callback:function(path){if(path){var txtPath=page.querySelector(".txtPath");txtPath.value=path,txtPath.focus()}picker.close()}})})}var self=this;self.submit=function(){page.querySelector(".btnSubmitListings").click()},self.init=function(){options=options||{},!1!==options.showCancelButton?page.querySelector(".btnCancel").classList.remove("hide"):page.querySelector(".btnCancel").classList.add("hide"),!1!==options.showSubmitButton?page.querySelector(".btnSubmitListings").classList.remove("hide"):page.querySelector(".btnSubmitListings").classList.add("hide"),page.querySelector(".premiereHelp").innerHTML=Globalize.translate("XmlTvPremiere",24),$("form",page).on("submit",function(){return submitListingsForm(),!1}),page.querySelector("#btnSelectPath").addEventListener("click",onSelectPathClick),page.querySelector(".lnkPremiere").addEventListener("click",function(e){registrationServices.showPremiereInfo(),e.preventDefault()}),page.querySelector(".chkAllTuners").addEventListener("change",function(e){e.target.checked?page.querySelector(".selectTunersSection").classList.add("hide"):page.querySelector(".selectTunersSection").classList.remove("hide")}),reload()}}}); \ No newline at end of file +define(["jQuery", "registrationServices", "loading", "emby-checkbox", "emby-input", "listViewStyle", "paper-icon-button-light"], function($, registrationServices, loading) { + "use strict"; + return function(page, providerId, options) { + function getListingProvider(config, id) { + if (config && id) { + var result = config.ListingProviders.filter(function(i) { + return i.Id === id + })[0]; + return result ? Promise.resolve(result) : getListingProvider() + } + return ApiClient.getJSON(ApiClient.getUrl("LiveTv/ListingProviders/Default")) + } + + function reload() { + loading.show(), ApiClient.getNamedConfiguration("livetv").then(function(config) { + getListingProvider(config, providerId).then(function(info) { + page.querySelector(".txtPath").value = info.Path || "", page.querySelector(".txtKids").value = (info.KidsCategories || []).join("|"), page.querySelector(".txtNews").value = (info.NewsCategories || []).join("|"), page.querySelector(".txtSports").value = (info.SportsCategories || []).join("|"), page.querySelector(".txtMovies").value = (info.MovieCategories || []).join("|"), page.querySelector(".txtMoviePrefix").value = info.MoviePrefix || "", page.querySelector(".txtUserAgent").value = info.UserAgent || "", page.querySelector(".chkAllTuners").checked = info.EnableAllTuners, page.querySelector(".chkAllTuners").checked ? page.querySelector(".selectTunersSection").classList.add("hide") : page.querySelector(".selectTunersSection").classList.remove("hide"), refreshTunerDevices(page, info, config.TunerHosts), loading.hide() + }) + }) + } + + function getCategories(txtInput) { + var value = txtInput.value; + return value ? value.split("|") : [] + } + + function submitListingsForm() { + loading.show(); + var id = providerId; + ApiClient.getNamedConfiguration("livetv").then(function(config) { + var info = config.ListingProviders.filter(function(i) { + return i.Id === id + })[0] || {}; + info.Type = "xmltv", info.Path = page.querySelector(".txtPath").value, info.MoviePrefix = page.querySelector(".txtMoviePrefix").value || null, info.UserAgent = page.querySelector(".txtUserAgent").value || null, info.MovieCategories = getCategories(page.querySelector(".txtMovies")), info.KidsCategories = getCategories(page.querySelector(".txtKids")), info.NewsCategories = getCategories(page.querySelector(".txtNews")), info.SportsCategories = getCategories(page.querySelector(".txtSports")), info.EnableAllTuners = page.querySelector(".chkAllTuners").checked, info.EnabledTuners = info.EnableAllTuners ? [] : $(".chkTuner", page).get().filter(function(i) { + return i.checked + }).map(function(i) { + return i.getAttribute("data-id") + }), ApiClient.ajax({ + type: "POST", + url: ApiClient.getUrl("LiveTv/ListingProviders", { + ValidateListings: !0 + }), + data: JSON.stringify(info), + contentType: "application/json" + }).then(function(result) { + loading.hide(), !1 !== options.showConfirmation && Dashboard.processServerConfigurationUpdateResult(), Events.trigger(self, "submitted") + }, function() { + loading.hide(), Dashboard.alert({ + message: Globalize.translate("ErrorAddingXmlTvFile") + }) + }) + }) + } + + function getTunerName(providerId) { + switch (providerId = providerId.toLowerCase()) { + case "m3u": + return "M3U Playlist"; + case "hdhomerun": + return "HDHomerun"; + case "satip": + return "DVB"; + default: + return "Unknown" + } + } + + function refreshTunerDevices(page, providerInfo, devices) { + for (var html = "", i = 0, length = devices.length; i < length; i++) { + var device = devices[i]; + html += '
    '; + var enabledTuners = providerInfo.EnabledTuners || [], + isChecked = providerInfo.EnableAllTuners || -1 !== enabledTuners.indexOf(device.Id), + checkedAttribute = isChecked ? " checked" : ""; + html += '", html += '
    ', html += '
    ', html += device.FriendlyName || getTunerName(device.Type), html += "
    ", html += '
    ', html += device.Url, html += "
    ", html += "
    ", html += "
    " + } + page.querySelector(".tunerList").innerHTML = html + } + + function onSelectPathClick(e) { + var page = $(e.target).parents(".xmltvForm")[0]; + require(["directorybrowser"], function(directoryBrowser) { + var picker = new directoryBrowser; + picker.show({ + includeFiles: !0, + callback: function(path) { + if (path) { + var txtPath = page.querySelector(".txtPath"); + txtPath.value = path, txtPath.focus() + } + picker.close() + } + }) + }) + } + var self = this; + self.submit = function() { + page.querySelector(".btnSubmitListings").click() + }, self.init = function() { + options = options || {}, !1 !== options.showCancelButton ? page.querySelector(".btnCancel").classList.remove("hide") : page.querySelector(".btnCancel").classList.add("hide"), !1 !== options.showSubmitButton ? page.querySelector(".btnSubmitListings").classList.remove("hide") : page.querySelector(".btnSubmitListings").classList.add("hide"), page.querySelector(".premiereHelp").innerHTML = Globalize.translate("XmlTvPremiere", 24), $("form", page).on("submit", function() { + return submitListingsForm(), !1 + }), page.querySelector("#btnSelectPath").addEventListener("click", onSelectPathClick), page.querySelector(".lnkPremiere").addEventListener("click", function(e) { + registrationServices.showPremiereInfo(), e.preventDefault() + }), page.querySelector(".chkAllTuners").addEventListener("change", function(e) { + e.target.checked ? page.querySelector(".selectTunersSection").classList.add("hide") : page.querySelector(".selectTunersSection").classList.remove("hide") + }), reload() + } + } +}); \ No newline at end of file diff --git a/dashboard-ui/components/viewcontainer-lite.js b/dashboard-ui/components/viewcontainer-lite.js index 3f6da63b4b..d1729f1fab 100644 --- a/dashboard-ui/components/viewcontainer-lite.js +++ b/dashboard-ui/components/viewcontainer-lite.js @@ -1 +1,121 @@ -define(["browser","dom","layoutManager","css!bower_components/emby-webcomponents/viewmanager/viewcontainer-lite"],function(browser,dom,layoutManager){"use strict";function setControllerClass(view,options){if(options.controllerFactory)return Promise.resolve();var controllerUrl=view.getAttribute("data-controller");return controllerUrl?(0===controllerUrl.indexOf("__plugin/")&&(controllerUrl=controllerUrl.substring("__plugin/".length)),controllerUrl=Dashboard.getConfigurationResourceUrl(controllerUrl),getRequirePromise([controllerUrl]).then(function(ControllerFactory){options.controllerFactory=ControllerFactory})):Promise.resolve()}function getRequirePromise(deps){return new Promise(function(resolve,reject){require(deps,resolve)})}function loadView(options){if(!options.cancel){var selected=selectedPageIndex,previousAnimatable=-1===selected?null:allPages[selected],pageIndex=selected+1;pageIndex>=pageContainerCount&&(pageIndex=0);var isPluginpage=-1!==options.url.toLowerCase().indexOf("/configurationpage"),newViewInfo=normalizeNewView(options,isPluginpage),newView=newViewInfo.elem,dependencies="string"==typeof newView?null:newView.getAttribute("data-require");return dependencies=dependencies?dependencies.split(","):[],isPluginpage&&dependencies.push("legacy/dashboard"),newViewInfo.hasjQuerySelect&&dependencies.push("legacy/selectmenu"),newViewInfo.hasjQueryChecked&&dependencies.push("fnchecked"),newViewInfo.hasjQuery&&dependencies.push("jQuery"),(isPluginpage||newView.classList&&newView.classList.contains("type-interior"))&&dependencies.push("dashboardcss"),new Promise(function(resolve,reject){dependencies.join(",");require(dependencies,function(){var currentPage=allPages[pageIndex];currentPage&&triggerDestroy(currentPage);var view=newView;"string"==typeof view&&(view=document.createElement("div"),view.innerHTML=newView),view.classList.add("mainAnimatedPage"),currentPage?newViewInfo.hasScript&&window.$?(view=$(view).appendTo(mainAnimatedPages)[0],mainAnimatedPages.removeChild(currentPage)):mainAnimatedPages.replaceChild(view,currentPage):newViewInfo.hasScript&&window.$?view=$(view).appendTo(mainAnimatedPages)[0]:mainAnimatedPages.appendChild(view),options.type&&view.setAttribute("data-type",options.type);var properties=[];options.fullscreen&&properties.push("fullscreen"),properties.length&&view.setAttribute("data-properties",properties.join(","));allPages[pageIndex]=view,setControllerClass(view,options).then(function(){onBeforeChange&&onBeforeChange(view,!1,options),beforeAnimate(allPages,pageIndex,selected),selectedPageIndex=pageIndex,currentUrls[pageIndex]=options.url,!options.cancel&&previousAnimatable&&afterAnimate(allPages,pageIndex),window.$&&($.mobile=$.mobile||{},$.mobile.activePage=view),resolve(view)})})})}}function replaceAll(str,find,replace){return str.split(find).join(replace)}function parseHtml(html,hasScript){hasScript&&(html=replaceAll(html,"\x3c!----\x3e","<\/script>"));var wrapper=document.createElement("div");return wrapper.innerHTML=html,wrapper.querySelector('div[data-role="page"]')}function normalizeNewView(options,isPluginpage){var viewHtml=options.view;if(-1===viewHtml.indexOf('data-role="page"'))return viewHtml;var hasScript=-1!==viewHtml.indexOf("= pageContainerCount && (pageIndex = 0); + var isPluginpage = -1 !== options.url.toLowerCase().indexOf("/configurationpage"), + newViewInfo = normalizeNewView(options, isPluginpage), + newView = newViewInfo.elem, + dependencies = "string" == typeof newView ? null : newView.getAttribute("data-require"); + return dependencies = dependencies ? dependencies.split(",") : [], isPluginpage && dependencies.push("legacy/dashboard"), newViewInfo.hasjQuerySelect && dependencies.push("legacy/selectmenu"), newViewInfo.hasjQueryChecked && dependencies.push("fnchecked"), newViewInfo.hasjQuery && dependencies.push("jQuery"), (isPluginpage || newView.classList && newView.classList.contains("type-interior")) && dependencies.push("dashboardcss"), new Promise(function(resolve, reject) { + dependencies.join(","); + require(dependencies, function() { + var currentPage = allPages[pageIndex]; + currentPage && triggerDestroy(currentPage); + var view = newView; + "string" == typeof view && (view = document.createElement("div"), view.innerHTML = newView), view.classList.add("mainAnimatedPage"), currentPage ? newViewInfo.hasScript && window.$ ? (view = $(view).appendTo(mainAnimatedPages)[0], mainAnimatedPages.removeChild(currentPage)) : mainAnimatedPages.replaceChild(view, currentPage) : newViewInfo.hasScript && window.$ ? view = $(view).appendTo(mainAnimatedPages)[0] : mainAnimatedPages.appendChild(view), options.type && view.setAttribute("data-type", options.type); + var properties = []; + options.fullscreen && properties.push("fullscreen"), properties.length && view.setAttribute("data-properties", properties.join(",")); + allPages[pageIndex] = view, setControllerClass(view, options).then(function() { + onBeforeChange && onBeforeChange(view, !1, options), beforeAnimate(allPages, pageIndex, selected), selectedPageIndex = pageIndex, currentUrls[pageIndex] = options.url, !options.cancel && previousAnimatable && afterAnimate(allPages, pageIndex), window.$ && ($.mobile = $.mobile || {}, $.mobile.activePage = view), resolve(view) + }) + }) + }) + } + } + + function replaceAll(str, find, replace) { + return str.split(find).join(replace) + } + + function parseHtml(html, hasScript) { + hasScript && (html = replaceAll(html, "\x3c!----\x3e", "<\/script>")); + var wrapper = document.createElement("div"); + return wrapper.innerHTML = html, wrapper.querySelector('div[data-role="page"]') + } + + function normalizeNewView(options, isPluginpage) { + var viewHtml = options.view; + if (-1 === viewHtml.indexOf('data-role="page"')) return viewHtml; + var hasScript = -1 !== viewHtml.indexOf("'+l.Name+""})).val(config.UICulture),currentLanguage=config.UICulture,$("#chkUsageData",page).checked(config.EnableAnonymousUsageReporting),$("#chkRunAtStartup",page).checked(config.RunAtStartup),$("#chkRunWebAppAtStartup",page).checked(config.AutoRunWebApp||!1),systemInfo.CanSelfUpdate?page.querySelector(".fldAutomaticUpdates").classList.remove("hide"):page.querySelector(".fldAutomaticUpdates").classList.add("hide"),$("#chkEnableAutomaticServerUpdates",page).checked(config.EnableAutoUpdate),$("#chkEnableAutomaticRestart",page).checked(config.EnableAutomaticRestart),systemInfo.CanSelfRestart?page.querySelector("#fldEnableAutomaticRestart").classList.remove("hide"):page.querySelector("#fldEnableAutomaticRestart").classList.add("hide"),systemInfo.CanSelfRestart||systemInfo.CanSelfUpdate?$(".autoUpdatesContainer",page).removeClass("hide"):$(".autoUpdatesContainer",page).addClass("hide"),loading.hide()}function onSubmit(){loading.show();var form=this;$(form).parents(".page");return ApiClient.getServerConfiguration().then(function(config){config.UICulture=$("#selectLocalizationLanguage",form).val(),config.CachePath=form.querySelector("#txtCachePath").value;var requiresReload=!1;config.UICulture!==currentLanguage&&(requiresReload=!0),config.EnableAnonymousUsageReporting=$("#chkUsageData",form).checked(),config.RunAtStartup=$("#chkRunAtStartup",form).checked(),config.AutoRunWebApp=$("#chkRunWebAppAtStartup",form).checked(),config.EnableAutomaticRestart=$("#chkEnableAutomaticRestart",form).checked(),config.EnableAutoUpdate=$("#chkEnableAutomaticServerUpdates",form).checked(),ApiClient.updateServerConfiguration(config).then(function(){ApiClient.getNamedConfiguration(brandingConfigKey).then(function(brandingConfig){brandingConfig.LoginDisclaimer=form.querySelector("#txtLoginDisclaimer").value,brandingConfig.CustomCss=form.querySelector("#txtCustomCss").value,currentBrandingOptions&&brandingConfig.CustomCss!==currentBrandingOptions.CustomCss&&(requiresReload=!0),ApiClient.updateNamedConfiguration(brandingConfigKey,brandingConfig).then(function(){Dashboard.processServerConfigurationUpdateResult(),requiresReload&&!AppInfo.isNativeApp&&window.location.reload(!0)})})})}),!1}var currentBrandingOptions,currentLanguage,brandingConfigKey="branding";return function(view,params){$("#btnSelectCachePath",view).on("click.selectDirectory",function(){require(["directorybrowser"],function(directoryBrowser){var picker=new directoryBrowser;picker.show({callback:function(path){path&&(view.querySelector("#txtCachePath").value=path),picker.close()},validateWriteable:!0,header:Globalize.translate("HeaderSelectServerCachePath"),instruction:Globalize.translate("HeaderSelectServerCachePathHelp")})})}),$(".dashboardGeneralForm",view).off("submit",onSubmit).on("submit",onSubmit),view.addEventListener("viewshow",function(){var promise1=ApiClient.getServerConfiguration(),promise2=ApiClient.getJSON(ApiClient.getUrl("Localization/Options")),promise3=ApiClient.getSystemInfo();Promise.all([promise1,promise2,promise3]).then(function(responses){loadPage(view,responses[0],responses[1],responses[2])}),ApiClient.getNamedConfiguration(brandingConfigKey).then(function(config){currentBrandingOptions=config,view.querySelector("#txtLoginDisclaimer").value=config.LoginDisclaimer||"",view.querySelector("#txtCustomCss").value=config.CustomCss||""})})}}); \ No newline at end of file +define(["jQuery", "loading", "fnchecked", "emby-checkbox", "emby-textarea", "emby-input", "emby-select", "emby-linkbutton"], function($, loading) { + "use strict"; + + function loadPage(page, config, languageOptions, systemInfo) { + -1 !== systemInfo.OperatingSystem.toLowerCase().indexOf("windows") ? page.querySelector("#windowsStartupDescription").classList.remove("hide") : page.querySelector("#windowsStartupDescription").classList.add("hide"), systemInfo.SupportsAutoRunAtStartup ? page.querySelector("#fldRunAtStartup").classList.remove("hide") : page.querySelector("#fldRunAtStartup").classList.add("hide"), systemInfo.CanLaunchWebBrowser ? page.querySelector("#fldRunWebAppAtStartup").classList.remove("hide") : page.querySelector("#fldRunWebAppAtStartup").classList.add("hide"), page.querySelector("#txtCachePath").value = config.CachePath || "", $("#selectLocalizationLanguage", page).html(languageOptions.map(function(l) { + return '" + })).val(config.UICulture), currentLanguage = config.UICulture, $("#chkUsageData", page).checked(config.EnableAnonymousUsageReporting), $("#chkRunAtStartup", page).checked(config.RunAtStartup), $("#chkRunWebAppAtStartup", page).checked(config.AutoRunWebApp || !1), systemInfo.CanSelfUpdate ? page.querySelector(".fldAutomaticUpdates").classList.remove("hide") : page.querySelector(".fldAutomaticUpdates").classList.add("hide"), $("#chkEnableAutomaticServerUpdates", page).checked(config.EnableAutoUpdate), $("#chkEnableAutomaticRestart", page).checked(config.EnableAutomaticRestart), systemInfo.CanSelfRestart ? page.querySelector("#fldEnableAutomaticRestart").classList.remove("hide") : page.querySelector("#fldEnableAutomaticRestart").classList.add("hide"), systemInfo.CanSelfRestart || systemInfo.CanSelfUpdate ? $(".autoUpdatesContainer", page).removeClass("hide") : $(".autoUpdatesContainer", page).addClass("hide"), loading.hide() + } + + function onSubmit() { + loading.show(); + var form = this; + $(form).parents(".page"); + return ApiClient.getServerConfiguration().then(function(config) { + config.UICulture = $("#selectLocalizationLanguage", form).val(), config.CachePath = form.querySelector("#txtCachePath").value; + var requiresReload = !1; + config.UICulture !== currentLanguage && (requiresReload = !0), config.EnableAnonymousUsageReporting = $("#chkUsageData", form).checked(), config.RunAtStartup = $("#chkRunAtStartup", form).checked(), config.AutoRunWebApp = $("#chkRunWebAppAtStartup", form).checked(), config.EnableAutomaticRestart = $("#chkEnableAutomaticRestart", form).checked(), config.EnableAutoUpdate = $("#chkEnableAutomaticServerUpdates", form).checked(), ApiClient.updateServerConfiguration(config).then(function() { + ApiClient.getNamedConfiguration(brandingConfigKey).then(function(brandingConfig) { + brandingConfig.LoginDisclaimer = form.querySelector("#txtLoginDisclaimer").value, brandingConfig.CustomCss = form.querySelector("#txtCustomCss").value, currentBrandingOptions && brandingConfig.CustomCss !== currentBrandingOptions.CustomCss && (requiresReload = !0), ApiClient.updateNamedConfiguration(brandingConfigKey, brandingConfig).then(function() { + Dashboard.processServerConfigurationUpdateResult(), requiresReload && !AppInfo.isNativeApp && window.location.reload(!0) + }) + }) + }) + }), !1 + } + var currentBrandingOptions, currentLanguage, brandingConfigKey = "branding"; + return function(view, params) { + $("#btnSelectCachePath", view).on("click.selectDirectory", function() { + require(["directorybrowser"], function(directoryBrowser) { + var picker = new directoryBrowser; + picker.show({ + callback: function(path) { + path && (view.querySelector("#txtCachePath").value = path), picker.close() + }, + validateWriteable: !0, + header: Globalize.translate("HeaderSelectServerCachePath"), + instruction: Globalize.translate("HeaderSelectServerCachePathHelp") + }) + }) + }), $(".dashboardGeneralForm", view).off("submit", onSubmit).on("submit", onSubmit), view.addEventListener("viewshow", function() { + var promise1 = ApiClient.getServerConfiguration(), + promise2 = ApiClient.getJSON(ApiClient.getUrl("Localization/Options")), + promise3 = ApiClient.getSystemInfo(); + Promise.all([promise1, promise2, promise3]).then(function(responses) { + loadPage(view, responses[0], responses[1], responses[2]) + }), ApiClient.getNamedConfiguration(brandingConfigKey).then(function(config) { + currentBrandingOptions = config, view.querySelector("#txtLoginDisclaimer").value = config.LoginDisclaimer || "", view.querySelector("#txtCustomCss").value = config.CustomCss || "" + }) + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/dashboard/dashboardhosting.js b/dashboard-ui/dashboard/dashboardhosting.js index 0253853952..b08e8d7d7d 100644 --- a/dashboard-ui/dashboard/dashboardhosting.js +++ b/dashboard-ui/dashboard/dashboardhosting.js @@ -1 +1,105 @@ -define(["loading","libraryMenu","globalize","emby-checkbox","emby-select"],function(loading,libraryMenu,globalize){"use strict";function onSubmit(e){var form=this,localAddress=form.querySelector("#txtLocalAddress").value,enableUpnp=form.querySelector("#chkEnableUpnp").checked;confirmSelections(localAddress,enableUpnp,function(){var validationResult=getValidationAlert(form);if(validationResult)return void alertText(validationResult);validateHttps(form).then(function(){loading.show(),ApiClient.getServerConfiguration().then(function(config){config.LocalNetworkSubnets=form.querySelector("#txtLanNetworks").value.split(",").map(function(s){return s.trim()}).filter(function(s){return s.length>0}),config.RemoteIPFilter=form.querySelector("#txtExternalAddressFilter").value.split(",").map(function(s){return s.trim()}).filter(function(s){return s.length>0}),config.IsRemoteIPFilterBlacklist="blacklist"===form.querySelector("#selectExternalAddressFilterMode").value,config.PublicPort=form.querySelector("#txtPublicPort").value,config.PublicHttpsPort=form.querySelector("#txtPublicHttpsPort").value;var httpsMode=form.querySelector("#selectHttpsMode").value;"proxy"===httpsMode?(config.EnableHttps=!0,config.RequireHttps=!1,config.IsBehindProxy=!0):"required"===httpsMode?(config.EnableHttps=!0,config.RequireHttps=!0,config.IsBehindProxy=!1):"enabled"===httpsMode?(config.EnableHttps=!0,config.RequireHttps=!1,config.IsBehindProxy=!1):(config.EnableHttps=!1,config.RequireHttps=!1,config.IsBehindProxy=!1),config.HttpsPortNumber=form.querySelector("#txtHttpsPort").value,config.HttpServerPortNumber=form.querySelector("#txtPortNumber").value,config.EnableUPnP=enableUpnp,config.WanDdns=form.querySelector("#txtDdns").value,config.EnableRemoteAccess=form.querySelector("#chkRemoteAccess").checked,config.CertificatePath=form.querySelector("#txtCertificatePath").value||null,config.CertificatePassword=form.querySelector("#txtCertPassword").value||null,config.LocalNetworkAddresses=localAddress?[localAddress]:[],ApiClient.updateServerConfiguration(config).then(Dashboard.processServerConfigurationUpdateResult,Dashboard.processErrorResponse)})})}),e.preventDefault()}function triggerChange(select){var evt=document.createEvent("HTMLEvents");evt.initEvent("change",!1,!0),select.dispatchEvent(evt)}function getValidationAlert(form){return form.querySelector("#txtPublicPort").value===form.querySelector("#txtPublicHttpsPort").value?"The public http and https ports must be different.":form.querySelector("#txtPortNumber").value===form.querySelector("#txtHttpsPort").value?"The http and https ports must be different.":null}function validateHttps(form){var certPath=form.querySelector("#txtCertificatePath").value||null,httpsMode=form.querySelector("#selectHttpsMode").value;return"enabled"!==httpsMode&&"required"!==httpsMode||certPath?Promise.resolve():new Promise(function(resolve,reject){return alertText({title:globalize.translate("TitleHostingSettings"),text:globalize.translate("HttpsRequiresCert")}).then(reject,reject)})}function alertText(options){return new Promise(function(resolve,reject){require(["alert"],function(alert){alert(options).then(resolve,reject)})})}function confirmSelections(localAddress,enableUpnp,callback){localAddress||!enableUpnp?alertText({title:globalize.translate("TitleHostingSettings"),text:globalize.translate("SettingsWarning")}).then(callback):callback()}function getTabs(){return[{href:"dashboardhosting.html",name:globalize.translate("TabHosting")},{href:"serversecurity.html",name:globalize.translate("TabSecurity")}]}return function(view,params){function loadPage(page,config){page.querySelector("#txtPortNumber").value=config.HttpServerPortNumber,page.querySelector("#txtPublicPort").value=config.PublicPort,page.querySelector("#txtPublicHttpsPort").value=config.PublicHttpsPort,page.querySelector("#txtLocalAddress").value=config.LocalNetworkAddresses[0]||"",page.querySelector("#txtLanNetworks").value=(config.LocalNetworkSubnets||[]).join(", "),page.querySelector("#txtExternalAddressFilter").value=(config.RemoteIPFilter||[]).join(", "),page.querySelector("#selectExternalAddressFilterMode").value=config.IsRemoteIPFilterBlacklist?"blacklist":"whitelist",page.querySelector("#chkRemoteAccess").checked=null==config.EnableRemoteAccess||config.EnableRemoteAccess;var selectHttpsMode=page.querySelector("#selectHttpsMode");config.IsBehindProxy?selectHttpsMode.value="proxy":config.RequireHttps?selectHttpsMode.value="required":config.EnableHttps?selectHttpsMode.value="enabled":selectHttpsMode.value="disabled",page.querySelector("#txtHttpsPort").value=config.HttpsPortNumber,page.querySelector("#txtDdns").value=config.WanDdns||"";var txtCertificatePath=page.querySelector("#txtCertificatePath");txtCertificatePath.value=config.CertificatePath||"",page.querySelector("#txtCertPassword").value=config.CertificatePassword||"",page.querySelector("#chkEnableUpnp").checked=config.EnableUPnP,onCertPathChange.call(txtCertificatePath),triggerChange(page.querySelector("#chkRemoteAccess")),loading.hide()}function onCertPathChange(){this.value?view.querySelector("#txtDdns").setAttribute("required","required"):view.querySelector("#txtDdns").removeAttribute("required")}view.querySelector("#chkRemoteAccess").addEventListener("change",function(){this.checked?(view.querySelector(".fldExternalAddressFilter").classList.remove("hide"),view.querySelector(".fldExternalAddressFilterMode").classList.remove("hide"),view.querySelector(".fldPublicPort").classList.remove("hide"),view.querySelector(".fldPublicHttpsPort").classList.remove("hide"),view.querySelector(".fldDdns").classList.remove("hide"),view.querySelector(".fldCertificatePath").classList.remove("hide"),view.querySelector(".fldCertPassword").classList.remove("hide"),view.querySelector(".fldHttpsMode").classList.remove("hide"),view.querySelector(".fldEnableUpnp").classList.remove("hide")):(view.querySelector(".fldExternalAddressFilter").classList.add("hide"),view.querySelector(".fldExternalAddressFilterMode").classList.add("hide"),view.querySelector(".fldPublicPort").classList.add("hide"),view.querySelector(".fldPublicHttpsPort").classList.add("hide"),view.querySelector(".fldDdns").classList.add("hide"),view.querySelector(".fldCertificatePath").classList.add("hide"),view.querySelector(".fldCertPassword").classList.add("hide"),view.querySelector(".fldHttpsMode").classList.add("hide"),view.querySelector(".fldEnableUpnp").classList.add("hide"))}),view.querySelector("#btnSelectCertPath").addEventListener("click",function(){require(["directorybrowser"],function(directoryBrowser){var picker=new directoryBrowser;picker.show({includeFiles:!0,includeDirectories:!0,callback:function(path){path&&(view.querySelector("#txtCertificatePath").value=path),picker.close()},header:globalize.translate("HeaderSelectCertificatePath")})})}),view.querySelector(".dashboardHostingForm").addEventListener("submit",onSubmit),view.querySelector("#txtCertificatePath").addEventListener("change",onCertPathChange),view.addEventListener("viewshow",function(e){libraryMenu.setTabs("adminadvanced",0,getTabs),loading.show(),ApiClient.getServerConfiguration().then(function(config){loadPage(view,config)})})}}); \ No newline at end of file +define(["loading", "libraryMenu", "globalize", "emby-checkbox", "emby-select"], function(loading, libraryMenu, globalize) { + "use strict"; + + function onSubmit(e) { + var form = this, + localAddress = form.querySelector("#txtLocalAddress").value, + enableUpnp = form.querySelector("#chkEnableUpnp").checked; + confirmSelections(localAddress, enableUpnp, function() { + var validationResult = getValidationAlert(form); + if (validationResult) return void alertText(validationResult); + validateHttps(form).then(function() { + loading.show(), ApiClient.getServerConfiguration().then(function(config) { + config.LocalNetworkSubnets = form.querySelector("#txtLanNetworks").value.split(",").map(function(s) { + return s.trim() + }).filter(function(s) { + return s.length > 0 + }), config.RemoteIPFilter = form.querySelector("#txtExternalAddressFilter").value.split(",").map(function(s) { + return s.trim() + }).filter(function(s) { + return s.length > 0 + }), config.IsRemoteIPFilterBlacklist = "blacklist" === form.querySelector("#selectExternalAddressFilterMode").value, config.PublicPort = form.querySelector("#txtPublicPort").value, config.PublicHttpsPort = form.querySelector("#txtPublicHttpsPort").value; + var httpsMode = form.querySelector("#selectHttpsMode").value; + "proxy" === httpsMode ? (config.EnableHttps = !0, config.RequireHttps = !1, config.IsBehindProxy = !0) : "required" === httpsMode ? (config.EnableHttps = !0, config.RequireHttps = !0, config.IsBehindProxy = !1) : "enabled" === httpsMode ? (config.EnableHttps = !0, config.RequireHttps = !1, config.IsBehindProxy = !1) : (config.EnableHttps = !1, config.RequireHttps = !1, config.IsBehindProxy = !1), config.HttpsPortNumber = form.querySelector("#txtHttpsPort").value, config.HttpServerPortNumber = form.querySelector("#txtPortNumber").value, config.EnableUPnP = enableUpnp, config.WanDdns = form.querySelector("#txtDdns").value, config.EnableRemoteAccess = form.querySelector("#chkRemoteAccess").checked, config.CertificatePath = form.querySelector("#txtCertificatePath").value || null, config.CertificatePassword = form.querySelector("#txtCertPassword").value || null, config.LocalNetworkAddresses = localAddress ? [localAddress] : [], ApiClient.updateServerConfiguration(config).then(Dashboard.processServerConfigurationUpdateResult, Dashboard.processErrorResponse) + }) + }) + }), e.preventDefault() + } + + function triggerChange(select) { + var evt = document.createEvent("HTMLEvents"); + evt.initEvent("change", !1, !0), select.dispatchEvent(evt) + } + + function getValidationAlert(form) { + return form.querySelector("#txtPublicPort").value === form.querySelector("#txtPublicHttpsPort").value ? "The public http and https ports must be different." : form.querySelector("#txtPortNumber").value === form.querySelector("#txtHttpsPort").value ? "The http and https ports must be different." : null + } + + function validateHttps(form) { + var certPath = form.querySelector("#txtCertificatePath").value || null, + httpsMode = form.querySelector("#selectHttpsMode").value; + return "enabled" !== httpsMode && "required" !== httpsMode || certPath ? Promise.resolve() : new Promise(function(resolve, reject) { + return alertText({ + title: globalize.translate("TitleHostingSettings"), + text: globalize.translate("HttpsRequiresCert") + }).then(reject, reject) + }) + } + + function alertText(options) { + return new Promise(function(resolve, reject) { + require(["alert"], function(alert) { + alert(options).then(resolve, reject) + }) + }) + } + + function confirmSelections(localAddress, enableUpnp, callback) { + localAddress || !enableUpnp ? alertText({ + title: globalize.translate("TitleHostingSettings"), + text: globalize.translate("SettingsWarning") + }).then(callback) : callback() + } + + function getTabs() { + return [{ + href: "dashboardhosting.html", + name: globalize.translate("TabHosting") + }, { + href: "serversecurity.html", + name: globalize.translate("TabSecurity") + }] + } + return function(view, params) { + function loadPage(page, config) { + page.querySelector("#txtPortNumber").value = config.HttpServerPortNumber, page.querySelector("#txtPublicPort").value = config.PublicPort, page.querySelector("#txtPublicHttpsPort").value = config.PublicHttpsPort, page.querySelector("#txtLocalAddress").value = config.LocalNetworkAddresses[0] || "", page.querySelector("#txtLanNetworks").value = (config.LocalNetworkSubnets || []).join(", "), page.querySelector("#txtExternalAddressFilter").value = (config.RemoteIPFilter || []).join(", "), page.querySelector("#selectExternalAddressFilterMode").value = config.IsRemoteIPFilterBlacklist ? "blacklist" : "whitelist", page.querySelector("#chkRemoteAccess").checked = null == config.EnableRemoteAccess || config.EnableRemoteAccess; + var selectHttpsMode = page.querySelector("#selectHttpsMode"); + config.IsBehindProxy ? selectHttpsMode.value = "proxy" : config.RequireHttps ? selectHttpsMode.value = "required" : config.EnableHttps ? selectHttpsMode.value = "enabled" : selectHttpsMode.value = "disabled", page.querySelector("#txtHttpsPort").value = config.HttpsPortNumber, page.querySelector("#txtDdns").value = config.WanDdns || ""; + var txtCertificatePath = page.querySelector("#txtCertificatePath"); + txtCertificatePath.value = config.CertificatePath || "", page.querySelector("#txtCertPassword").value = config.CertificatePassword || "", page.querySelector("#chkEnableUpnp").checked = config.EnableUPnP, onCertPathChange.call(txtCertificatePath), triggerChange(page.querySelector("#chkRemoteAccess")), loading.hide() + } + + function onCertPathChange() { + this.value ? view.querySelector("#txtDdns").setAttribute("required", "required") : view.querySelector("#txtDdns").removeAttribute("required") + } + view.querySelector("#chkRemoteAccess").addEventListener("change", function() { + this.checked ? (view.querySelector(".fldExternalAddressFilter").classList.remove("hide"), view.querySelector(".fldExternalAddressFilterMode").classList.remove("hide"), view.querySelector(".fldPublicPort").classList.remove("hide"), view.querySelector(".fldPublicHttpsPort").classList.remove("hide"), view.querySelector(".fldDdns").classList.remove("hide"), view.querySelector(".fldCertificatePath").classList.remove("hide"), view.querySelector(".fldCertPassword").classList.remove("hide"), view.querySelector(".fldHttpsMode").classList.remove("hide"), view.querySelector(".fldEnableUpnp").classList.remove("hide")) : (view.querySelector(".fldExternalAddressFilter").classList.add("hide"), view.querySelector(".fldExternalAddressFilterMode").classList.add("hide"), view.querySelector(".fldPublicPort").classList.add("hide"), view.querySelector(".fldPublicHttpsPort").classList.add("hide"), view.querySelector(".fldDdns").classList.add("hide"), view.querySelector(".fldCertificatePath").classList.add("hide"), view.querySelector(".fldCertPassword").classList.add("hide"), view.querySelector(".fldHttpsMode").classList.add("hide"), view.querySelector(".fldEnableUpnp").classList.add("hide")) + }), view.querySelector("#btnSelectCertPath").addEventListener("click", function() { + require(["directorybrowser"], function(directoryBrowser) { + var picker = new directoryBrowser; + picker.show({ + includeFiles: !0, + includeDirectories: !0, + callback: function(path) { + path && (view.querySelector("#txtCertificatePath").value = path), picker.close() + }, + header: globalize.translate("HeaderSelectCertificatePath") + }) + }) + }), view.querySelector(".dashboardHostingForm").addEventListener("submit", onSubmit), view.querySelector("#txtCertificatePath").addEventListener("change", onCertPathChange), view.addEventListener("viewshow", function(e) { + libraryMenu.setTabs("adminadvanced", 0, getTabs), loading.show(), ApiClient.getServerConfiguration().then(function(config) { + loadPage(view, config) + }) + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/dashboard/devicesupload.js b/dashboard-ui/dashboard/devicesupload.js index c24e7923cb..572f5ac602 100644 --- a/dashboard-ui/dashboard/devicesupload.js +++ b/dashboard-ui/dashboard/devicesupload.js @@ -1 +1,40 @@ -define(["jQuery","loading","libraryMenu","fnchecked"],function($,loading,libraryMenu){"use strict";function load(page,config){$("#txtUploadPath",page).val(config.CameraUploadPath||""),$("#chkSubfolder",page).checked(config.EnableCameraUploadSubfolders)}function loadData(page){loading.show(),ApiClient.getNamedConfiguration("devices").then(function(config){load(page,config),loading.hide()})}function save(page){ApiClient.getNamedConfiguration("devices").then(function(config){config.CameraUploadPath=$("#txtUploadPath",page).val(),config.EnableCameraUploadSubfolders=$("#chkSubfolder",page).checked(),ApiClient.updateNamedConfiguration("devices",config).then(Dashboard.processServerConfigurationUpdateResult)})}function onSubmit(){return save($(this).parents(".page")),!1}$(document).on("pageinit","#devicesUploadPage",function(){var page=this;$("#btnSelectUploadPath",page).on("click.selectDirectory",function(){require(["directorybrowser"],function(directoryBrowser){var picker=new directoryBrowser;picker.show({callback:function(path){path&&$("#txtUploadPath",page).val(path),picker.close()},validateWriteable:!0,header:Globalize.translate("HeaderSelectUploadPath")})})}),$(".devicesUploadForm").off("submit",onSubmit).on("submit",onSubmit)}).on("pageshow","#devicesUploadPage",function(){loadData(this)})}); \ No newline at end of file +define(["jQuery", "loading", "libraryMenu", "fnchecked"], function($, loading, libraryMenu) { + "use strict"; + + function load(page, config) { + $("#txtUploadPath", page).val(config.CameraUploadPath || ""), $("#chkSubfolder", page).checked(config.EnableCameraUploadSubfolders) + } + + function loadData(page) { + loading.show(), ApiClient.getNamedConfiguration("devices").then(function(config) { + load(page, config), loading.hide() + }) + } + + function save(page) { + ApiClient.getNamedConfiguration("devices").then(function(config) { + config.CameraUploadPath = $("#txtUploadPath", page).val(), config.EnableCameraUploadSubfolders = $("#chkSubfolder", page).checked(), ApiClient.updateNamedConfiguration("devices", config).then(Dashboard.processServerConfigurationUpdateResult) + }) + } + + function onSubmit() { + return save($(this).parents(".page")), !1 + } + $(document).on("pageinit", "#devicesUploadPage", function() { + var page = this; + $("#btnSelectUploadPath", page).on("click.selectDirectory", function() { + require(["directorybrowser"], function(directoryBrowser) { + var picker = new directoryBrowser; + picker.show({ + callback: function(path) { + path && $("#txtUploadPath", page).val(path), picker.close() + }, + validateWriteable: !0, + header: Globalize.translate("HeaderSelectUploadPath") + }) + }) + }), $(".devicesUploadForm").off("submit", onSubmit).on("submit", onSubmit) + }).on("pageshow", "#devicesUploadPage", function() { + loadData(this) + }) +}); \ No newline at end of file diff --git a/dashboard-ui/dashboard/librarydisplay.js b/dashboard-ui/dashboard/librarydisplay.js index 5a06ab5adc..924641d743 100644 --- a/dashboard-ui/dashboard/librarydisplay.js +++ b/dashboard-ui/dashboard/librarydisplay.js @@ -1 +1,38 @@ -define(["globalize","loading","libraryMenu","emby-checkbox","emby-button","emby-linkbutton"],function(globalize,loading,libraryMenu){"use strict";function getTabs(){return[{href:"library.html",name:Globalize.translate("HeaderLibraries")},{href:"librarydisplay.html",name:Globalize.translate("TabDisplay")},{href:"metadataimages.html",name:Globalize.translate("TabMetadata")},{href:"metadatanfo.html",name:Globalize.translate("TabNfoSettings")},{href:"librarysettings.html",name:Globalize.translate("TabAdvanced")}]}return function(view,params){function loadData(){ApiClient.getServerConfiguration().then(function(config){view.querySelector(".chkFolderView").checked=config.EnableFolderView,view.querySelector(".chkGroupMoviesIntoCollections").checked=config.EnableGroupingIntoCollections,view.querySelector(".chkDisplaySpecialsWithinSeasons").checked=config.DisplaySpecialsWithinSeasons,view.querySelector(".chkExternalContentInSuggestions").checked=config.EnableExternalContentInSuggestions})}view.querySelector("form").addEventListener("submit",function(e){loading.show();var form=this;return ApiClient.getServerConfiguration().then(function(config){config.EnableFolderView=form.querySelector(".chkFolderView").checked,config.EnableGroupingIntoCollections=form.querySelector(".chkGroupMoviesIntoCollections").checked,config.DisplaySpecialsWithinSeasons=form.querySelector(".chkDisplaySpecialsWithinSeasons").checked,config.EnableExternalContentInSuggestions=form.querySelector(".chkExternalContentInSuggestions").checked,ApiClient.updateServerConfiguration(config).then(Dashboard.processServerConfigurationUpdateResult)}),e.preventDefault(),!1}),view.addEventListener("viewshow",function(){libraryMenu.setTabs("librarysetup",1,getTabs),loadData()})}}); \ No newline at end of file +define(["globalize", "loading", "libraryMenu", "emby-checkbox", "emby-button", "emby-linkbutton"], function(globalize, loading, libraryMenu) { + "use strict"; + + function getTabs() { + return [{ + href: "library.html", + name: Globalize.translate("HeaderLibraries") + }, { + href: "librarydisplay.html", + name: Globalize.translate("TabDisplay") + }, { + href: "metadataimages.html", + name: Globalize.translate("TabMetadata") + }, { + href: "metadatanfo.html", + name: Globalize.translate("TabNfoSettings") + }, { + href: "librarysettings.html", + name: Globalize.translate("TabAdvanced") + }] + } + return function(view, params) { + function loadData() { + ApiClient.getServerConfiguration().then(function(config) { + view.querySelector(".chkFolderView").checked = config.EnableFolderView, view.querySelector(".chkGroupMoviesIntoCollections").checked = config.EnableGroupingIntoCollections, view.querySelector(".chkDisplaySpecialsWithinSeasons").checked = config.DisplaySpecialsWithinSeasons, view.querySelector(".chkExternalContentInSuggestions").checked = config.EnableExternalContentInSuggestions + }) + } + view.querySelector("form").addEventListener("submit", function(e) { + loading.show(); + var form = this; + return ApiClient.getServerConfiguration().then(function(config) { + config.EnableFolderView = form.querySelector(".chkFolderView").checked, config.EnableGroupingIntoCollections = form.querySelector(".chkGroupMoviesIntoCollections").checked, config.DisplaySpecialsWithinSeasons = form.querySelector(".chkDisplaySpecialsWithinSeasons").checked, config.EnableExternalContentInSuggestions = form.querySelector(".chkExternalContentInSuggestions").checked, ApiClient.updateServerConfiguration(config).then(Dashboard.processServerConfigurationUpdateResult) + }), e.preventDefault(), !1 + }), view.addEventListener("viewshow", function() { + libraryMenu.setTabs("librarysetup", 1, getTabs), loadData() + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/dashboard/librarysettings.js b/dashboard-ui/dashboard/librarysettings.js index 3ae1f81e3d..1add2bb44b 100644 --- a/dashboard-ui/dashboard/librarysettings.js +++ b/dashboard-ui/dashboard/librarysettings.js @@ -1 +1,94 @@ -define(["jQuery","loading","libraryMenu","fnchecked","emby-checkbox","emby-linkbutton"],function($,loading,libraryMenu){"use strict";function loadPage(page,config){config.MergeMetadataAndImagesByName?$(".fldImagesByName",page).hide():$(".fldImagesByName",page).show(),$("#chkSaveMetadataHidden",page).checked(config.SaveMetadataHidden),$("#txtMetadataPath",page).val(config.MetadataPath||""),$("#txtMetadataNetworkPath",page).val(config.MetadataNetworkPath||""),loading.hide()}function loadMetadataConfig(page,config){$("#selectDateAdded",page).val(config.UseFileCreationTimeForDateAdded?"1":"0")}function loadFanartConfig(page,config){$("#txtFanartApiKey",page).val(config.UserApiKey||"")}function saveFanart(form){ApiClient.getNamedConfiguration("fanart").then(function(config){config.UserApiKey=$("#txtFanartApiKey",form).val(),ApiClient.updateNamedConfiguration("fanart",config)})}function saveMetadata(form){ApiClient.getNamedConfiguration("metadata").then(function(config){config.UseFileCreationTimeForDateAdded="1"===$("#selectDateAdded",form).val(),ApiClient.updateNamedConfiguration("metadata",config)})}function alertText(options){require(["alert"],function(alert){alert(options)})}function onSubmitFail(response){loading.hide(),response&&404===response.status?alertText("The metadata path entered could not be found. Please ensure the path is valid and try again."):response&&500===response.status&&alertText("The metadata path entered is not valid. Please ensure the path exists and that Emby server has write access to the folder.")}function onSubmit(){loading.show();var form=this;return ApiClient.getServerConfiguration().then(function(config){config.SaveMetadataHidden=$("#chkSaveMetadataHidden",form).checked(),config.EnableTvDbUpdates=$("#chkEnableTvdbUpdates",form).checked(),config.EnableTmdbUpdates=$("#chkEnableTmdbUpdates",form).checked(),config.EnableFanArtUpdates=$("#chkEnableFanartUpdates",form).checked(),config.MetadataPath=$("#txtMetadataPath",form).val(),config.MetadataNetworkPath=$("#txtMetadataNetworkPath",form).val(),config.FanartApiKey=$("#txtFanartApiKey",form).val(),ApiClient.updateServerConfiguration(config).then(Dashboard.processServerConfigurationUpdateResult,onSubmitFail)}),saveMetadata(form),saveFanart(form),!1}function getTabs(){return[{href:"library.html",name:Globalize.translate("HeaderLibraries")},{href:"librarydisplay.html",name:Globalize.translate("TabDisplay")},{href:"metadataimages.html",name:Globalize.translate("TabMetadata")},{href:"metadatanfo.html",name:Globalize.translate("TabNfoSettings")},{href:"librarysettings.html",name:Globalize.translate("TabAdvanced")}]}return function(view,params){$("#btnSelectMetadataPath",view).on("click.selectDirectory",function(){require(["directorybrowser"],function(directoryBrowser){var picker=new directoryBrowser;picker.show({path:$("#txtMetadataPath",view).val(),networkSharePath:$("#txtMetadataNetworkPath",view).val(),callback:function(path,networkPath){path&&($("#txtMetadataPath",view).val(path),$("#txtMetadataNetworkPath",view).val(networkPath)),picker.close()},validateWriteable:!0,header:Globalize.translate("HeaderSelectMetadataPath"),instruction:Globalize.translate("HeaderSelectMetadataPathHelp"),enableNetworkSharePath:!0})})}),$(".librarySettingsForm").off("submit",onSubmit).on("submit",onSubmit),view.addEventListener("viewshow",function(){libraryMenu.setTabs("librarysetup",4,getTabs),loading.show();var page=this;ApiClient.getServerConfiguration().then(function(config){loadPage(page,config)}),ApiClient.getNamedConfiguration("metadata").then(function(metadata){loadMetadataConfig(page,metadata)}),ApiClient.getNamedConfiguration("fanart").then(function(metadata){loadFanartConfig(page,metadata)}),ApiClient.getSystemInfo().then(function(info){"Windows"===info.OperatingSystem?page.querySelector(".fldSaveMetadataHidden").classList.remove("hide"):page.querySelector(".fldSaveMetadataHidden").classList.add("hide")})})}}); \ No newline at end of file +define(["jQuery", "loading", "libraryMenu", "fnchecked", "emby-checkbox", "emby-linkbutton"], function($, loading, libraryMenu) { + "use strict"; + + function loadPage(page, config) { + config.MergeMetadataAndImagesByName ? $(".fldImagesByName", page).hide() : $(".fldImagesByName", page).show(), $("#chkSaveMetadataHidden", page).checked(config.SaveMetadataHidden), $("#txtMetadataPath", page).val(config.MetadataPath || ""), $("#txtMetadataNetworkPath", page).val(config.MetadataNetworkPath || ""), loading.hide() + } + + function loadMetadataConfig(page, config) { + $("#selectDateAdded", page).val(config.UseFileCreationTimeForDateAdded ? "1" : "0") + } + + function loadFanartConfig(page, config) { + $("#txtFanartApiKey", page).val(config.UserApiKey || "") + } + + function saveFanart(form) { + ApiClient.getNamedConfiguration("fanart").then(function(config) { + config.UserApiKey = $("#txtFanartApiKey", form).val(), ApiClient.updateNamedConfiguration("fanart", config) + }) + } + + function saveMetadata(form) { + ApiClient.getNamedConfiguration("metadata").then(function(config) { + config.UseFileCreationTimeForDateAdded = "1" === $("#selectDateAdded", form).val(), ApiClient.updateNamedConfiguration("metadata", config) + }) + } + + function alertText(options) { + require(["alert"], function(alert) { + alert(options) + }) + } + + function onSubmitFail(response) { + loading.hide(), response && 404 === response.status ? alertText("The metadata path entered could not be found. Please ensure the path is valid and try again.") : response && 500 === response.status && alertText("The metadata path entered is not valid. Please ensure the path exists and that Emby server has write access to the folder.") + } + + function onSubmit() { + loading.show(); + var form = this; + return ApiClient.getServerConfiguration().then(function(config) { + config.SaveMetadataHidden = $("#chkSaveMetadataHidden", form).checked(), config.EnableTvDbUpdates = $("#chkEnableTvdbUpdates", form).checked(), config.EnableTmdbUpdates = $("#chkEnableTmdbUpdates", form).checked(), config.EnableFanArtUpdates = $("#chkEnableFanartUpdates", form).checked(), config.MetadataPath = $("#txtMetadataPath", form).val(), config.MetadataNetworkPath = $("#txtMetadataNetworkPath", form).val(), config.FanartApiKey = $("#txtFanartApiKey", form).val(), ApiClient.updateServerConfiguration(config).then(Dashboard.processServerConfigurationUpdateResult, onSubmitFail) + }), saveMetadata(form), saveFanart(form), !1 + } + + function getTabs() { + return [{ + href: "library.html", + name: Globalize.translate("HeaderLibraries") + }, { + href: "librarydisplay.html", + name: Globalize.translate("TabDisplay") + }, { + href: "metadataimages.html", + name: Globalize.translate("TabMetadata") + }, { + href: "metadatanfo.html", + name: Globalize.translate("TabNfoSettings") + }, { + href: "librarysettings.html", + name: Globalize.translate("TabAdvanced") + }] + } + return function(view, params) { + $("#btnSelectMetadataPath", view).on("click.selectDirectory", function() { + require(["directorybrowser"], function(directoryBrowser) { + var picker = new directoryBrowser; + picker.show({ + path: $("#txtMetadataPath", view).val(), + networkSharePath: $("#txtMetadataNetworkPath", view).val(), + callback: function(path, networkPath) { + path && ($("#txtMetadataPath", view).val(path), $("#txtMetadataNetworkPath", view).val(networkPath)), picker.close() + }, + validateWriteable: !0, + header: Globalize.translate("HeaderSelectMetadataPath"), + instruction: Globalize.translate("HeaderSelectMetadataPathHelp"), + enableNetworkSharePath: !0 + }) + }) + }), $(".librarySettingsForm").off("submit", onSubmit).on("submit", onSubmit), view.addEventListener("viewshow", function() { + libraryMenu.setTabs("librarysetup", 4, getTabs), loading.show(); + var page = this; + ApiClient.getServerConfiguration().then(function(config) { + loadPage(page, config) + }), ApiClient.getNamedConfiguration("metadata").then(function(metadata) { + loadMetadataConfig(page, metadata) + }), ApiClient.getNamedConfiguration("fanart").then(function(metadata) { + loadFanartConfig(page, metadata) + }), ApiClient.getSystemInfo().then(function(info) { + "Windows" === info.OperatingSystem ? page.querySelector(".fldSaveMetadataHidden").classList.remove("hide") : page.querySelector(".fldSaveMetadataHidden").classList.add("hide") + }) + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/dashboard/livetvtuner.js b/dashboard-ui/dashboard/livetvtuner.js index 7e2af5e569..b32e01b2d2 100644 --- a/dashboard-ui/dashboard/livetvtuner.js +++ b/dashboard-ui/dashboard/livetvtuner.js @@ -1 +1,128 @@ -define(["globalize","loading","libraryMenu","dom","emby-input","emby-button","emby-checkbox","emby-select"],function(globalize,loading,libraryMenu,dom){"use strict";function isM3uVariant(type){return-1!==["nextpvr"].indexOf(type||"")}function fillTypes(view,currentId){return ApiClient.getJSON(ApiClient.getUrl("LiveTv/TunerHosts/Types")).then(function(types){var selectType=view.querySelector(".selectType");selectType.innerHTML=types.map(function(t){return'"}).join("")+'",selectType.disabled=null!=currentId,selectType.value="",onTypeChange.call(selectType)})}function reload(view,providerId){view.querySelector(".txtDevicePath").value="",view.querySelector(".chkFavorite").checked=!1,view.querySelector(".txtDevicePath").value="",providerId&&ApiClient.getNamedConfiguration("livetv").then(function(config){var info=config.TunerHosts.filter(function(i){return i.Id===providerId})[0];fillTunerHostInfo(view,info)})}function fillTunerHostInfo(view,info){var selectType=view.querySelector(".selectType"),type=info.Type||"";info.Source&&isM3uVariant(info.Source)&&(type=info.Source),selectType.value=type,onTypeChange.call(selectType),view.querySelector(".txtDevicePath").value=info.Url||"",view.querySelector(".txtFriendlyName").value=info.FriendlyName||"",view.querySelector(".txtUserAgent").value=info.UserAgent||"",view.querySelector(".fldDeviceId").value=info.DeviceId||"",view.querySelector(".chkFavorite").checked=info.ImportFavoritesOnly,view.querySelector(".chkTranscode").checked=info.AllowHWTranscoding,view.querySelector(".chkStreamLoop").checked=info.EnableStreamLooping,view.querySelector(".txtTunerCount").value=info.TunerCount||"0"}function submitForm(page){loading.show();var info={Type:page.querySelector(".selectType").value,Url:page.querySelector(".txtDevicePath").value||null,UserAgent:page.querySelector(".txtUserAgent").value||null,FriendlyName:page.querySelector(".txtFriendlyName").value||null,DeviceId:page.querySelector(".fldDeviceId").value||null,TunerCount:page.querySelector(".txtTunerCount").value||0,ImportFavoritesOnly:page.querySelector(".chkFavorite").checked,AllowHWTranscoding:page.querySelector(".chkTranscode").checked,EnableStreamLooping:page.querySelector(".chkStreamLoop").checked};isM3uVariant(info.Type)&&(info.Source=info.Type,info.Type="m3u");var id=getParameterByName("id");id&&(info.Id=id);info.Id;ApiClient.ajax({type:"POST",url:ApiClient.getUrl("LiveTv/TunerHosts"),data:JSON.stringify(info),contentType:"application/json"}).then(function(result){Dashboard.processServerConfigurationUpdateResult(),Dashboard.navigate("livetvstatus.html")},function(){loading.hide(),Dashboard.alert({message:globalize.translate("ErrorSavingTvProvider")})})}function getRequirePromise(deps){return new Promise(function(resolve,reject){require(deps,resolve)})}function getDetectedDevice(){return getRequirePromise(["tunerPicker"]).then(function(tunerPicker){return(new tunerPicker).show({serverId:ApiClient.serverId()})})}function getTabs(){return[{href:"livetvstatus.html",name:globalize.translate("TabDevices")},{href:"appservices.html?context=livetv",name:globalize.translate("TabServices")}]}function onTypeChange(){var value=this.value,view=dom.parentWithClass(this,"page"),mayIncludeUnsupportedDrmChannels="hdhomerun"===value,supportsTranscoding="hdhomerun"===value,supportsFavorites="hdhomerun"===value,supportsTunerIpAddress="hdhomerun"===value,supportsTunerFileOrUrl="m3u"===value,supportsStreamLooping="m3u"===value,supportsTunerCount="m3u"===value,supportsUserAgent="m3u"===value,suppportsSubmit="other"!==value,supportsSelectablePath=supportsTunerFileOrUrl,txtDevicePath=view.querySelector(".txtDevicePath");supportsTunerIpAddress?(txtDevicePath.label(globalize.translate("LabelTunerIpAddress")),view.querySelector(".fldPath").classList.remove("hide")):supportsTunerFileOrUrl?(txtDevicePath.label(globalize.translate("LabelFileOrUrl")),view.querySelector(".fldPath").classList.remove("hide")):view.querySelector(".fldPath").classList.add("hide"),supportsSelectablePath?(view.querySelector(".btnSelectPath").classList.remove("hide"),view.querySelector(".txtDevicePath").setAttribute("required","required")):(view.querySelector(".btnSelectPath").classList.add("hide"),view.querySelector(".txtDevicePath").removeAttribute("required")),supportsUserAgent?view.querySelector(".fldUserAgent").classList.remove("hide"):view.querySelector(".fldUserAgent").classList.add("hide"),supportsFavorites?view.querySelector(".fldFavorites").classList.remove("hide"):view.querySelector(".fldFavorites").classList.add("hide"),supportsTranscoding?view.querySelector(".fldTranscode").classList.remove("hide"):view.querySelector(".fldTranscode").classList.add("hide"),supportsStreamLooping?view.querySelector(".fldStreamLoop").classList.remove("hide"):view.querySelector(".fldStreamLoop").classList.add("hide"),supportsTunerCount?(view.querySelector(".fldTunerCount").classList.remove("hide"),view.querySelector(".txtTunerCount").setAttribute("required","required")):(view.querySelector(".fldTunerCount").classList.add("hide"),view.querySelector(".txtTunerCount").removeAttribute("required")),mayIncludeUnsupportedDrmChannels?view.querySelector(".drmMessage").classList.remove("hide"):view.querySelector(".drmMessage").classList.add("hide"),suppportsSubmit?(view.querySelector(".button-submit").classList.remove("hide"),view.querySelector(".otherOptionsMessage").classList.add("hide")):(view.querySelector(".button-submit").classList.add("hide"),view.querySelector(".otherOptionsMessage").classList.remove("hide"))}return function(view,params){params.id||view.querySelector(".btnDetect").classList.remove("hide"),view.addEventListener("viewshow",function(){libraryMenu.setTabs("livetvadmin",0,getTabs);var currentId=params.id;fillTypes(view,currentId).then(function(){reload(view,currentId)})}),view.querySelector("form").addEventListener("submit",function(e){return submitForm(view),e.preventDefault(),e.stopPropagation(),!1}),view.querySelector(".selectType").addEventListener("change",onTypeChange),view.querySelector(".btnDetect").addEventListener("click",function(){getDetectedDevice().then(function(info){fillTunerHostInfo(view,info)})}),view.querySelector(".btnSelectPath").addEventListener("click",function(){require(["directorybrowser"],function(directoryBrowser){var picker=new directoryBrowser;picker.show({includeFiles:!0,callback:function(path){path&&(view.querySelector(".txtDevicePath").value=path),picker.close()}})})})}}); \ No newline at end of file +define(["globalize", "loading", "libraryMenu", "dom", "emby-input", "emby-button", "emby-checkbox", "emby-select"], function(globalize, loading, libraryMenu, dom) { + "use strict"; + + function isM3uVariant(type) { + return -1 !== ["nextpvr"].indexOf(type || "") + } + + function fillTypes(view, currentId) { + return ApiClient.getJSON(ApiClient.getUrl("LiveTv/TunerHosts/Types")).then(function(types) { + var selectType = view.querySelector(".selectType"); + selectType.innerHTML = types.map(function(t) { + return '" + }).join("") + '", selectType.disabled = null != currentId, selectType.value = "", onTypeChange.call(selectType) + }) + } + + function reload(view, providerId) { + view.querySelector(".txtDevicePath").value = "", view.querySelector(".chkFavorite").checked = !1, view.querySelector(".txtDevicePath").value = "", providerId && ApiClient.getNamedConfiguration("livetv").then(function(config) { + var info = config.TunerHosts.filter(function(i) { + return i.Id === providerId + })[0]; + fillTunerHostInfo(view, info) + }) + } + + function fillTunerHostInfo(view, info) { + var selectType = view.querySelector(".selectType"), + type = info.Type || ""; + info.Source && isM3uVariant(info.Source) && (type = info.Source), selectType.value = type, onTypeChange.call(selectType), view.querySelector(".txtDevicePath").value = info.Url || "", view.querySelector(".txtFriendlyName").value = info.FriendlyName || "", view.querySelector(".txtUserAgent").value = info.UserAgent || "", view.querySelector(".fldDeviceId").value = info.DeviceId || "", view.querySelector(".chkFavorite").checked = info.ImportFavoritesOnly, view.querySelector(".chkTranscode").checked = info.AllowHWTranscoding, view.querySelector(".chkStreamLoop").checked = info.EnableStreamLooping, view.querySelector(".txtTunerCount").value = info.TunerCount || "0" + } + + function submitForm(page) { + loading.show(); + var info = { + Type: page.querySelector(".selectType").value, + Url: page.querySelector(".txtDevicePath").value || null, + UserAgent: page.querySelector(".txtUserAgent").value || null, + FriendlyName: page.querySelector(".txtFriendlyName").value || null, + DeviceId: page.querySelector(".fldDeviceId").value || null, + TunerCount: page.querySelector(".txtTunerCount").value || 0, + ImportFavoritesOnly: page.querySelector(".chkFavorite").checked, + AllowHWTranscoding: page.querySelector(".chkTranscode").checked, + EnableStreamLooping: page.querySelector(".chkStreamLoop").checked + }; + isM3uVariant(info.Type) && (info.Source = info.Type, info.Type = "m3u"); + var id = getParameterByName("id"); + id && (info.Id = id); + info.Id; + ApiClient.ajax({ + type: "POST", + url: ApiClient.getUrl("LiveTv/TunerHosts"), + data: JSON.stringify(info), + contentType: "application/json" + }).then(function(result) { + Dashboard.processServerConfigurationUpdateResult(), Dashboard.navigate("livetvstatus.html") + }, function() { + loading.hide(), Dashboard.alert({ + message: globalize.translate("ErrorSavingTvProvider") + }) + }) + } + + function getRequirePromise(deps) { + return new Promise(function(resolve, reject) { + require(deps, resolve) + }) + } + + function getDetectedDevice() { + return getRequirePromise(["tunerPicker"]).then(function(tunerPicker) { + return (new tunerPicker).show({ + serverId: ApiClient.serverId() + }) + }) + } + + function getTabs() { + return [{ + href: "livetvstatus.html", + name: globalize.translate("TabDevices") + }, { + href: "appservices.html?context=livetv", + name: globalize.translate("TabServices") + }] + } + + function onTypeChange() { + var value = this.value, + view = dom.parentWithClass(this, "page"), + mayIncludeUnsupportedDrmChannels = "hdhomerun" === value, + supportsTranscoding = "hdhomerun" === value, + supportsFavorites = "hdhomerun" === value, + supportsTunerIpAddress = "hdhomerun" === value, + supportsTunerFileOrUrl = "m3u" === value, + supportsStreamLooping = "m3u" === value, + supportsTunerCount = "m3u" === value, + supportsUserAgent = "m3u" === value, + suppportsSubmit = "other" !== value, + supportsSelectablePath = supportsTunerFileOrUrl, + txtDevicePath = view.querySelector(".txtDevicePath"); + supportsTunerIpAddress ? (txtDevicePath.label(globalize.translate("LabelTunerIpAddress")), view.querySelector(".fldPath").classList.remove("hide")) : supportsTunerFileOrUrl ? (txtDevicePath.label(globalize.translate("LabelFileOrUrl")), view.querySelector(".fldPath").classList.remove("hide")) : view.querySelector(".fldPath").classList.add("hide"), supportsSelectablePath ? (view.querySelector(".btnSelectPath").classList.remove("hide"), view.querySelector(".txtDevicePath").setAttribute("required", "required")) : (view.querySelector(".btnSelectPath").classList.add("hide"), view.querySelector(".txtDevicePath").removeAttribute("required")), supportsUserAgent ? view.querySelector(".fldUserAgent").classList.remove("hide") : view.querySelector(".fldUserAgent").classList.add("hide"), supportsFavorites ? view.querySelector(".fldFavorites").classList.remove("hide") : view.querySelector(".fldFavorites").classList.add("hide"), supportsTranscoding ? view.querySelector(".fldTranscode").classList.remove("hide") : view.querySelector(".fldTranscode").classList.add("hide"), supportsStreamLooping ? view.querySelector(".fldStreamLoop").classList.remove("hide") : view.querySelector(".fldStreamLoop").classList.add("hide"), supportsTunerCount ? (view.querySelector(".fldTunerCount").classList.remove("hide"), view.querySelector(".txtTunerCount").setAttribute("required", "required")) : (view.querySelector(".fldTunerCount").classList.add("hide"), view.querySelector(".txtTunerCount").removeAttribute("required")), mayIncludeUnsupportedDrmChannels ? view.querySelector(".drmMessage").classList.remove("hide") : view.querySelector(".drmMessage").classList.add("hide"), suppportsSubmit ? (view.querySelector(".button-submit").classList.remove("hide"), view.querySelector(".otherOptionsMessage").classList.add("hide")) : (view.querySelector(".button-submit").classList.add("hide"), view.querySelector(".otherOptionsMessage").classList.remove("hide")) + } + return function(view, params) { + params.id || view.querySelector(".btnDetect").classList.remove("hide"), view.addEventListener("viewshow", function() { + libraryMenu.setTabs("livetvadmin", 0, getTabs); + var currentId = params.id; + fillTypes(view, currentId).then(function() { + reload(view, currentId) + }) + }), view.querySelector("form").addEventListener("submit", function(e) { + return submitForm(view), e.preventDefault(), e.stopPropagation(), !1 + }), view.querySelector(".selectType").addEventListener("change", onTypeChange), view.querySelector(".btnDetect").addEventListener("click", function() { + getDetectedDevice().then(function(info) { + fillTunerHostInfo(view, info) + }) + }), view.querySelector(".btnSelectPath").addEventListener("click", function() { + require(["directorybrowser"], function(directoryBrowser) { + var picker = new directoryBrowser; + picker.show({ + includeFiles: !0, + callback: function(path) { + path && (view.querySelector(".txtDevicePath").value = path), picker.close() + } + }) + }) + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/dashboard/logpage.js b/dashboard-ui/dashboard/logpage.js index 742d72c380..0c29389255 100644 --- a/dashboard-ui/dashboard/logpage.js +++ b/dashboard-ui/dashboard/logpage.js @@ -1 +1,29 @@ -define(["datetime","loading","apphost","listViewStyle","emby-linkbutton","flexStyles"],function(datetime,loading,appHost){"use strict";return function(view,params){view.querySelector("#chkDebugLog").addEventListener("change",function(){ApiClient.getServerConfiguration().then(function(config){config.EnableDebugLevelLogging=view.querySelector("#chkDebugLog").checked,ApiClient.updateServerConfiguration(config)})}),view.addEventListener("viewbeforeshow",function(){loading.show();var apiClient=ApiClient;apiClient.getJSON(apiClient.getUrl("System/Logs")).then(function(logs){var html="";html+='
    ',html+=logs.map(function(log){var logUrl=apiClient.getUrl("System/Logs/Log",{name:log.Name});logUrl+="&api_key="+apiClient.accessToken();var logHtml="";logHtml+='',logHtml+='
    ',logHtml+="

    "+log.Name+"

    ";var date=datetime.parseISO8601Date(log.DateModified,!0),text=datetime.toLocaleDateString(date);return text+=" "+datetime.getDisplayTime(date),logHtml+='
    '+text+"
    ",logHtml+="
    ",logHtml+="
    "}).join(""),html+="
    ",view.querySelector(".serverLogs").innerHTML=html,loading.hide()}),apiClient.getServerConfiguration().then(function(config){view.querySelector("#chkDebugLog").checked=config.EnableDebugLevelLogging})})}}); \ No newline at end of file +define(["datetime", "loading", "apphost", "listViewStyle", "emby-linkbutton", "flexStyles"], function(datetime, loading, appHost) { + "use strict"; + return function(view, params) { + view.querySelector("#chkDebugLog").addEventListener("change", function() { + ApiClient.getServerConfiguration().then(function(config) { + config.EnableDebugLevelLogging = view.querySelector("#chkDebugLog").checked, ApiClient.updateServerConfiguration(config) + }) + }), view.addEventListener("viewbeforeshow", function() { + loading.show(); + var apiClient = ApiClient; + apiClient.getJSON(apiClient.getUrl("System/Logs")).then(function(logs) { + var html = ""; + html += '
    ', html += logs.map(function(log) { + var logUrl = apiClient.getUrl("System/Logs/Log", { + name: log.Name + }); + logUrl += "&api_key=" + apiClient.accessToken(); + var logHtml = ""; + logHtml += '', logHtml += '
    ', logHtml += "

    " + log.Name + "

    "; + var date = datetime.parseISO8601Date(log.DateModified, !0), + text = datetime.toLocaleDateString(date); + return text += " " + datetime.getDisplayTime(date), logHtml += '
    ' + text + "
    ", logHtml += "
    ", logHtml += "
    " + }).join(""), html += "
    ", view.querySelector(".serverLogs").innerHTML = html, loading.hide() + }), apiClient.getServerConfiguration().then(function(config) { + view.querySelector("#chkDebugLog").checked = config.EnableDebugLevelLogging + }) + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/dashboard/serveractivity.js b/dashboard-ui/dashboard/serveractivity.js index 1fb15b271e..2b43215c93 100644 --- a/dashboard-ui/dashboard/serveractivity.js +++ b/dashboard-ui/dashboard/serveractivity.js @@ -1 +1,14 @@ -define(["components/activitylog","globalize"],function(ActivityLog,globalize){"use strict";return function(view,params){var activityLog;"false"!==params.useractivity?(view.querySelector(".activityItems").setAttribute("data-useractivity","true"),view.querySelector(".sectionTitle").innerHTML=globalize.translate("HeaderActivity")):(view.querySelector(".activityItems").setAttribute("data-useractivity","false"),view.querySelector(".sectionTitle").innerHTML=globalize.translate("Alerts")),view.addEventListener("viewshow",function(){activityLog||(activityLog=new ActivityLog({serverId:ApiClient.serverId(),element:view.querySelector(".activityItems")}))}),view.addEventListener("viewdestroy",function(){activityLog&&activityLog.destroy(),activityLog=null})}}); \ No newline at end of file +define(["components/activitylog", "globalize"], function(ActivityLog, globalize) { + "use strict"; + return function(view, params) { + var activityLog; + "false" !== params.useractivity ? (view.querySelector(".activityItems").setAttribute("data-useractivity", "true"), view.querySelector(".sectionTitle").innerHTML = globalize.translate("HeaderActivity")) : (view.querySelector(".activityItems").setAttribute("data-useractivity", "false"), view.querySelector(".sectionTitle").innerHTML = globalize.translate("Alerts")), view.addEventListener("viewshow", function() { + activityLog || (activityLog = new ActivityLog({ + serverId: ApiClient.serverId(), + element: view.querySelector(".activityItems") + })) + }), view.addEventListener("viewdestroy", function() { + activityLog && activityLog.destroy(), activityLog = null + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/dashboard/wizardfinishpage.js b/dashboard-ui/dashboard/wizardfinishpage.js index a4412df4dd..9d1ab5dada 100644 --- a/dashboard-ui/dashboard/wizardfinishpage.js +++ b/dashboard-ui/dashboard/wizardfinishpage.js @@ -1 +1,19 @@ -define(["loading"],function(loading){"use strict";function onFinish(){loading.show(),ApiClient.ajax({url:ApiClient.getUrl("Startup/Complete"),type:"POST"}).then(function(){Dashboard.navigate("dashboard.html"),loading.hide()})}return function(view,params){view.querySelector(".btnWizardNext").addEventListener("click",onFinish),view.addEventListener("viewshow",function(){document.querySelector(".skinHeader").classList.add("noHomeButtonHeader")}),view.addEventListener("viewhide",function(){document.querySelector(".skinHeader").classList.remove("noHomeButtonHeader")})}}); \ No newline at end of file +define(["loading"], function(loading) { + "use strict"; + + function onFinish() { + loading.show(), ApiClient.ajax({ + url: ApiClient.getUrl("Startup/Complete"), + type: "POST" + }).then(function() { + Dashboard.navigate("dashboard.html"), loading.hide() + }) + } + return function(view, params) { + view.querySelector(".btnWizardNext").addEventListener("click", onFinish), view.addEventListener("viewshow", function() { + document.querySelector(".skinHeader").classList.add("noHomeButtonHeader") + }), view.addEventListener("viewhide", function() { + document.querySelector(".skinHeader").classList.remove("noHomeButtonHeader") + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/dashboard/wizardremoteaccess.js b/dashboard-ui/dashboard/wizardremoteaccess.js index 3767b54d6e..8f68268cb5 100644 --- a/dashboard-ui/dashboard/wizardremoteaccess.js +++ b/dashboard-ui/dashboard/wizardremoteaccess.js @@ -1 +1,31 @@ -define(["loading","emby-checkbox","emby-button","emby-select"],function(loading){"use strict";function save(page){loading.show();var apiClient=ApiClient,config={};config.EnableRemoteAccess=page.querySelector("#chkRemoteAccess").checked,config.EnableAutomaticPortMapping=page.querySelector("#chkEnableUpnp").checked,apiClient.ajax({type:"POST",data:config,url:apiClient.getUrl("Startup/RemoteAccess")}).then(function(){loading.hide(),navigateToNextPage()})}function navigateToNextPage(){Dashboard.navigate("wizardagreement.html")}function onSubmit(e){return save(this),e.preventDefault(),!1}return function(view,params){view.querySelector(".wizardSettingsForm").addEventListener("submit",onSubmit),view.addEventListener("viewshow",function(){document.querySelector(".skinHeader").classList.add("noHomeButtonHeader")}),view.addEventListener("viewhide",function(){document.querySelector(".skinHeader").classList.remove("noHomeButtonHeader")})}}); \ No newline at end of file +define(["loading", "emby-checkbox", "emby-button", "emby-select"], function(loading) { + "use strict"; + + function save(page) { + loading.show(); + var apiClient = ApiClient, + config = {}; + config.EnableRemoteAccess = page.querySelector("#chkRemoteAccess").checked, config.EnableAutomaticPortMapping = page.querySelector("#chkEnableUpnp").checked, apiClient.ajax({ + type: "POST", + data: config, + url: apiClient.getUrl("Startup/RemoteAccess") + }).then(function() { + loading.hide(), navigateToNextPage() + }) + } + + function navigateToNextPage() { + Dashboard.navigate("wizardagreement.html") + } + + function onSubmit(e) { + return save(this), e.preventDefault(), !1 + } + return function(view, params) { + view.querySelector(".wizardSettingsForm").addEventListener("submit", onSubmit), view.addEventListener("viewshow", function() { + document.querySelector(".skinHeader").classList.add("noHomeButtonHeader") + }), view.addEventListener("viewhide", function() { + document.querySelector(".skinHeader").classList.remove("noHomeButtonHeader") + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/dashboard/wizardsettings.js b/dashboard-ui/dashboard/wizardsettings.js index 824d627539..6303d95efa 100644 --- a/dashboard-ui/dashboard/wizardsettings.js +++ b/dashboard-ui/dashboard/wizardsettings.js @@ -1 +1,67 @@ -define(["loading","emby-checkbox","emby-button","emby-select"],function(loading){"use strict";function save(page){loading.show();var apiClient=ApiClient;apiClient.getJSON(apiClient.getUrl("Startup/Configuration")).then(function(config){config.PreferredMetadataLanguage=page.querySelector("#selectLanguage").value,config.MetadataCountryCode=page.querySelector("#selectCountry").value,apiClient.ajax({type:"POST",data:config,url:apiClient.getUrl("Startup/Configuration")}).then(function(){loading.hide(),navigateToNextPage()})})}function populateLanguages(select,languages){var html="";html+="";for(var i=0,length=languages.length;i"+culture.DisplayName+""}select.innerHTML=html}function populateCountries(select,allCountries){var html="";html+="";for(var i=0,length=allCountries.length;i"+culture.DisplayName+""}select.innerHTML=html}function reloadData(page,config,cultures,countries){populateLanguages(page.querySelector("#selectLanguage"),cultures),populateCountries(page.querySelector("#selectCountry"),countries),page.querySelector("#selectLanguage").value=config.PreferredMetadataLanguage,page.querySelector("#selectCountry").value=config.MetadataCountryCode,loading.hide()}function reload(page){loading.show();var apiClient=ApiClient,promise1=apiClient.getJSON(apiClient.getUrl("Startup/Configuration")),promise2=apiClient.getCultures(),promise3=apiClient.getCountries();Promise.all([promise1,promise2,promise3]).then(function(responses){reloadData(page,responses[0],responses[1],responses[2])})}function navigateToNextPage(){Dashboard.navigate("wizardremoteaccess.html")}function onSubmit(e){return save(this),e.preventDefault(),!1}return function(view,params){view.querySelector(".wizardSettingsForm").addEventListener("submit",onSubmit),view.addEventListener("viewshow",function(){document.querySelector(".skinHeader").classList.add("noHomeButtonHeader"),reload(this)}),view.addEventListener("viewhide",function(){document.querySelector(".skinHeader").classList.remove("noHomeButtonHeader")})}}); \ No newline at end of file +define(["loading", "emby-checkbox", "emby-button", "emby-select"], function(loading) { + "use strict"; + + function save(page) { + loading.show(); + var apiClient = ApiClient; + apiClient.getJSON(apiClient.getUrl("Startup/Configuration")).then(function(config) { + config.PreferredMetadataLanguage = page.querySelector("#selectLanguage").value, config.MetadataCountryCode = page.querySelector("#selectCountry").value, apiClient.ajax({ + type: "POST", + data: config, + url: apiClient.getUrl("Startup/Configuration") + }).then(function() { + loading.hide(), navigateToNextPage() + }) + }) + } + + function populateLanguages(select, languages) { + var html = ""; + html += ""; + for (var i = 0, length = languages.length; i < length; i++) { + var culture = languages[i]; + html += "" + } + select.innerHTML = html + } + + function populateCountries(select, allCountries) { + var html = ""; + html += ""; + for (var i = 0, length = allCountries.length; i < length; i++) { + var culture = allCountries[i]; + html += "" + } + select.innerHTML = html + } + + function reloadData(page, config, cultures, countries) { + populateLanguages(page.querySelector("#selectLanguage"), cultures), populateCountries(page.querySelector("#selectCountry"), countries), page.querySelector("#selectLanguage").value = config.PreferredMetadataLanguage, page.querySelector("#selectCountry").value = config.MetadataCountryCode, loading.hide() + } + + function reload(page) { + loading.show(); + var apiClient = ApiClient, + promise1 = apiClient.getJSON(apiClient.getUrl("Startup/Configuration")), + promise2 = apiClient.getCultures(), + promise3 = apiClient.getCountries(); + Promise.all([promise1, promise2, promise3]).then(function(responses) { + reloadData(page, responses[0], responses[1], responses[2]) + }) + } + + function navigateToNextPage() { + Dashboard.navigate("wizardremoteaccess.html") + } + + function onSubmit(e) { + return save(this), e.preventDefault(), !1 + } + return function(view, params) { + view.querySelector(".wizardSettingsForm").addEventListener("submit", onSubmit), view.addEventListener("viewshow", function() { + document.querySelector(".skinHeader").classList.add("noHomeButtonHeader"), reload(this) + }), view.addEventListener("viewhide", function() { + document.querySelector(".skinHeader").classList.remove("noHomeButtonHeader") + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/dashboard/wizardstart.js b/dashboard-ui/dashboard/wizardstart.js index f566a1b8cb..568ef15b2b 100644 --- a/dashboard-ui/dashboard/wizardstart.js +++ b/dashboard-ui/dashboard/wizardstart.js @@ -1 +1,41 @@ -define(["jQuery","loading","emby-button","emby-select"],function($,loading){"use strict";function loadPage(page,config,languageOptions){$("#selectLocalizationLanguage",page).html(languageOptions.map(function(l){return'"})).val(config.UICulture),loading.hide()}function save(page){loading.show();var apiClient=ApiClient;apiClient.getJSON(apiClient.getUrl("Startup/Configuration")).then(function(config){config.UICulture=$("#selectLocalizationLanguage",page).val(),apiClient.ajax({type:"POST",data:config,url:apiClient.getUrl("Startup/Configuration")}).then(function(){Dashboard.navigate("wizarduser.html")})})}function onSubmit(){return save($(this).parents(".page")),!1}return function(view,params){$(".wizardStartForm",view).on("submit",onSubmit),view.addEventListener("viewshow",function(){document.querySelector(".skinHeader").classList.add("noHomeButtonHeader"),loading.show();var page=this,apiClient=ApiClient,promise1=apiClient.getJSON(apiClient.getUrl("Startup/Configuration")),promise2=apiClient.getJSON(apiClient.getUrl("Localization/Options"));Promise.all([promise1,promise2]).then(function(responses){loadPage(page,responses[0],responses[1])})}),view.addEventListener("viewhide",function(){document.querySelector(".skinHeader").classList.remove("noHomeButtonHeader")})}}); \ No newline at end of file +define(["jQuery", "loading", "emby-button", "emby-select"], function($, loading) { + "use strict"; + + function loadPage(page, config, languageOptions) { + $("#selectLocalizationLanguage", page).html(languageOptions.map(function(l) { + return '" + })).val(config.UICulture), loading.hide() + } + + function save(page) { + loading.show(); + var apiClient = ApiClient; + apiClient.getJSON(apiClient.getUrl("Startup/Configuration")).then(function(config) { + config.UICulture = $("#selectLocalizationLanguage", page).val(), apiClient.ajax({ + type: "POST", + data: config, + url: apiClient.getUrl("Startup/Configuration") + }).then(function() { + Dashboard.navigate("wizarduser.html") + }) + }) + } + + function onSubmit() { + return save($(this).parents(".page")), !1 + } + return function(view, params) { + $(".wizardStartForm", view).on("submit", onSubmit), view.addEventListener("viewshow", function() { + document.querySelector(".skinHeader").classList.add("noHomeButtonHeader"), loading.show(); + var page = this, + apiClient = ApiClient, + promise1 = apiClient.getJSON(apiClient.getUrl("Startup/Configuration")), + promise2 = apiClient.getJSON(apiClient.getUrl("Localization/Options")); + Promise.all([promise1, promise2]).then(function(responses) { + loadPage(page, responses[0], responses[1]) + }) + }), view.addEventListener("viewhide", function() { + document.querySelector(".skinHeader").classList.remove("noHomeButtonHeader") + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/devices/device.js b/dashboard-ui/devices/device.js index 8eea26b56d..e704b964aa 100644 --- a/dashboard-ui/devices/device.js +++ b/dashboard-ui/devices/device.js @@ -1 +1,44 @@ -define(["loading","libraryMenu","dom","emby-input","emby-button"],function(loading,libraryMenu,dom){"use strict";function load(page,device,deviceOptions){page.querySelector("#txtCustomName",page).value=deviceOptions.CustomName||"",page.querySelector(".reportedName",page).innerHTML=device.Name||""}function loadData(){var page=this;loading.show();var id=getParameterByName("id"),promise1=ApiClient.getJSON(ApiClient.getUrl("Devices/Info",{Id:id})),promise2=ApiClient.getJSON(ApiClient.getUrl("Devices/Options",{Id:id}));Promise.all([promise1,promise2]).then(function(responses){load(page,responses[0],responses[1]),loading.hide()})}function save(page){var id=getParameterByName("id");ApiClient.ajax({url:ApiClient.getUrl("Devices/Options",{Id:id}),type:"POST",data:JSON.stringify({CustomName:page.querySelector("#txtCustomName").value}),contentType:"application/json"}).then(Dashboard.processServerConfigurationUpdateResult)}function onSubmit(e){var form=this;return save(dom.parentWithClass(form,"page")),e.preventDefault(),!1}return function(view,params){view.querySelector("form").addEventListener("submit",onSubmit),view.addEventListener("viewshow",loadData)}}); \ No newline at end of file +define(["loading", "libraryMenu", "dom", "emby-input", "emby-button"], function(loading, libraryMenu, dom) { + "use strict"; + + function load(page, device, deviceOptions) { + page.querySelector("#txtCustomName", page).value = deviceOptions.CustomName || "", page.querySelector(".reportedName", page).innerHTML = device.Name || "" + } + + function loadData() { + var page = this; + loading.show(); + var id = getParameterByName("id"), + promise1 = ApiClient.getJSON(ApiClient.getUrl("Devices/Info", { + Id: id + })), + promise2 = ApiClient.getJSON(ApiClient.getUrl("Devices/Options", { + Id: id + })); + Promise.all([promise1, promise2]).then(function(responses) { + load(page, responses[0], responses[1]), loading.hide() + }) + } + + function save(page) { + var id = getParameterByName("id"); + ApiClient.ajax({ + url: ApiClient.getUrl("Devices/Options", { + Id: id + }), + type: "POST", + data: JSON.stringify({ + CustomName: page.querySelector("#txtCustomName").value + }), + contentType: "application/json" + }).then(Dashboard.processServerConfigurationUpdateResult) + } + + function onSubmit(e) { + var form = this; + return save(dom.parentWithClass(form, "page")), e.preventDefault(), !1 + } + return function(view, params) { + view.querySelector("form").addEventListener("submit", onSubmit), view.addEventListener("viewshow", loadData) + } +}); \ No newline at end of file diff --git a/dashboard-ui/devices/devices.js b/dashboard-ui/devices/devices.js index bd53b83a1e..ba658b7562 100644 --- a/dashboard-ui/devices/devices.js +++ b/dashboard-ui/devices/devices.js @@ -1 +1,80 @@ -define(["loading","dom","libraryMenu","globalize","humanedate","emby-linkbutton","emby-itemscontainer","cardStyle"],function(loading,dom,libraryMenu,globalize){"use strict";function canDelete(deviceId){return deviceId!==ApiClient.deviceId()}function deleteDevice(page,id){var msg=globalize.translate("DeleteDeviceConfirmation");require(["confirm"],function(confirm){confirm({text:msg,title:globalize.translate("HeaderDeleteDevice"),confirmText:globalize.translate("ButtonDelete"),primary:"cancel"}).then(function(){loading.show(),ApiClient.ajax({type:"DELETE",url:ApiClient.getUrl("Devices",{Id:id})}).then(function(){loadData(page)})})})}function showDeviceMenu(view,btn,deviceId){var menuItems=[];canEdit&&menuItems.push({name:globalize.translate("sharedcomponents#Edit"),id:"open",ironIcon:"mode-edit"}),canDelete(deviceId)&&menuItems.push({name:globalize.translate("sharedcomponents#Delete"),id:"delete",ironIcon:"delete"}),require(["actionsheet"],function(actionsheet){actionsheet.show({items:menuItems,positionTo:btn,callback:function(id){switch(id){case"open":Dashboard.navigate("devices/device.html?id="+deviceId);break;case"delete":deleteDevice(view,deviceId)}}})})}function load(page,devices){var html="";html+=devices.map(function(device){var deviceHtml="";deviceHtml+="
    ",deviceHtml+='
    ',deviceHtml+='",deviceHtml+='
    ',(canEdit||canDelete(device.Id))&&(deviceHtml+='
    ',deviceHtml+='',deviceHtml+="
    "),deviceHtml+="
    ",deviceHtml+=device.Name,deviceHtml+="
    ",deviceHtml+="
    ",deviceHtml+=device.AppName+" "+device.AppVersion,deviceHtml+="
    ",deviceHtml+="
    ",device.LastUserName&&(deviceHtml+=device.LastUserName,deviceHtml+=", "+humane_date(device.DateLastActivity)),deviceHtml+=" ",deviceHtml+="
    ",deviceHtml+="
    ",deviceHtml+="
    ",deviceHtml+="
    "}).join(""),page.querySelector(".devicesList").innerHTML=html}function loadData(page){loading.show(),ApiClient.getJSON(ApiClient.getUrl("Devices")).then(function(result){load(page,result.Items),loading.hide()})}var canEdit=ApiClient.isMinServerVersion("3.4.1.31");return function(view,params){view.querySelector(".devicesList").addEventListener("click",function(e){var btnDeviceMenu=dom.parentWithClass(e.target,"btnDeviceMenu");btnDeviceMenu&&showDeviceMenu(view,btnDeviceMenu,btnDeviceMenu.getAttribute("data-id"))}),view.addEventListener("viewshow",function(){loadData(this)})}}); \ No newline at end of file +define(["loading", "dom", "libraryMenu", "globalize", "humanedate", "emby-linkbutton", "emby-itemscontainer", "cardStyle"], function(loading, dom, libraryMenu, globalize) { + "use strict"; + + function canDelete(deviceId) { + return deviceId !== ApiClient.deviceId() + } + + function deleteDevice(page, id) { + var msg = globalize.translate("DeleteDeviceConfirmation"); + require(["confirm"], function(confirm) { + confirm({ + text: msg, + title: globalize.translate("HeaderDeleteDevice"), + confirmText: globalize.translate("ButtonDelete"), + primary: "cancel" + }).then(function() { + loading.show(), ApiClient.ajax({ + type: "DELETE", + url: ApiClient.getUrl("Devices", { + Id: id + }) + }).then(function() { + loadData(page) + }) + }) + }) + } + + function showDeviceMenu(view, btn, deviceId) { + var menuItems = []; + canEdit && menuItems.push({ + name: globalize.translate("sharedcomponents#Edit"), + id: "open", + ironIcon: "mode-edit" + }), canDelete(deviceId) && menuItems.push({ + name: globalize.translate("sharedcomponents#Delete"), + id: "delete", + ironIcon: "delete" + }), require(["actionsheet"], function(actionsheet) { + actionsheet.show({ + items: menuItems, + positionTo: btn, + callback: function(id) { + switch (id) { + case "open": + Dashboard.navigate("devices/device.html?id=" + deviceId); + break; + case "delete": + deleteDevice(view, deviceId) + } + } + }) + }) + } + + function load(page, devices) { + var html = ""; + html += devices.map(function(device) { + var deviceHtml = ""; + deviceHtml += "
    ", deviceHtml += '
    ', deviceHtml += '", deviceHtml += '
    ', (canEdit || canDelete(device.Id)) && (deviceHtml += '
    ', deviceHtml += '', deviceHtml += "
    "), deviceHtml += "
    ", deviceHtml += device.Name, deviceHtml += "
    ", deviceHtml += "
    ", deviceHtml += device.AppName + " " + device.AppVersion, deviceHtml += "
    ", deviceHtml += "
    ", device.LastUserName && (deviceHtml += device.LastUserName, deviceHtml += ", " + humane_date(device.DateLastActivity)), deviceHtml += " ", deviceHtml += "
    ", deviceHtml += "
    ", deviceHtml += "
    ", deviceHtml += "
    " + }).join(""), page.querySelector(".devicesList").innerHTML = html + } + + function loadData(page) { + loading.show(), ApiClient.getJSON(ApiClient.getUrl("Devices")).then(function(result) { + load(page, result.Items), loading.hide() + }) + } + var canEdit = ApiClient.isMinServerVersion("3.4.1.31"); + return function(view, params) { + view.querySelector(".devicesList").addEventListener("click", function(e) { + var btnDeviceMenu = dom.parentWithClass(e.target, "btnDeviceMenu"); + btnDeviceMenu && showDeviceMenu(view, btnDeviceMenu, btnDeviceMenu.getAttribute("data-id")) + }), view.addEventListener("viewshow", function() { + loadData(this) + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/home/favorites.js b/dashboard-ui/home/favorites.js index 004076c0b1..26366ed210 100644 --- a/dashboard-ui/home/favorites.js +++ b/dashboard-ui/home/favorites.js @@ -1 +1,214 @@ -define(["appRouter","cardBuilder","dom","globalize","connectionManager","apphost","layoutManager","focusManager","emby-itemscontainer","emby-scroller"],function(appRouter,cardBuilder,dom,globalize,connectionManager,appHost,layoutManager,focusManager){"use strict";function enableScrollX(){return!0}function getThumbShape(){return enableScrollX()?"overflowBackdrop":"backdrop"}function getPosterShape(){return enableScrollX()?"overflowPortrait":"portrait"}function getSquareShape(){return enableScrollX()?"overflowSquare":"square"}function getSections(){return[{name:"sharedcomponents#HeaderFavoriteMovies",types:"Movie",shape:getPosterShape(),showTitle:!0,showYear:!0,overlayPlayButton:!0,overlayText:!1,centerText:!0},{name:"sharedcomponents#HeaderFavoriteShows",types:"Series",shape:getPosterShape(),showTitle:!0,showYear:!0,overlayPlayButton:!0,overlayText:!1,centerText:!0},{name:"sharedcomponents#HeaderFavoriteEpisodes",types:"Episode",shape:getThumbShape(),preferThumb:!1,showTitle:!0,showParentTitle:!0,overlayPlayButton:!0,overlayText:!1,centerText:!0},{name:"sharedcomponents#HeaderFavoriteVideos",types:"Video",shape:getThumbShape(),preferThumb:!0,showTitle:!0,overlayPlayButton:!0,overlayText:!1,centerText:!0},{name:"sharedcomponents#HeaderFavoriteCollections",types:"BoxSet",shape:getPosterShape(),showTitle:!0,overlayPlayButton:!0,overlayText:!1,centerText:!0},{name:"sharedcomponents#HeaderFavoritePlaylists",types:"Playlist",shape:getSquareShape(),preferThumb:!1,showTitle:!0,overlayText:!1,showParentTitle:!1,centerText:!0,overlayPlayButton:!0,coverImage:!0},{name:"sharedcomponents#HeaderFavoriteArtists",types:"MusicArtist",shape:getSquareShape(),preferThumb:!1,showTitle:!0,overlayText:!1,showParentTitle:!1,centerText:!0,overlayPlayButton:!0,coverImage:!0},{name:"sharedcomponents#HeaderFavoriteAlbums",types:"MusicAlbum",shape:getSquareShape(),preferThumb:!1,showTitle:!0,overlayText:!1,showParentTitle:!0,centerText:!0,overlayPlayButton:!0,coverImage:!0},{name:"sharedcomponents#HeaderFavoriteSongs",types:"Audio",shape:getSquareShape(),preferThumb:!1,showTitle:!0,overlayText:!1,showParentTitle:!0,centerText:!0,overlayMoreButton:!0,action:"instantmix",coverImage:!0},{name:"sharedcomponents#HeaderFavoriteGames",types:"Game",shape:getSquareShape(),preferThumb:!1,showTitle:!0}]}function getFetchDataFn(section){return function(){var apiClient=this.apiClient,options={SortBy:(section.types,"SeriesName,SortName"),SortOrder:"Ascending",Filters:"IsFavorite",Recursive:!0,Fields:"PrimaryImageAspectRatio,BasicSyncInfo",CollapseBoxSetItems:!1,ExcludeLocationTypes:"Virtual",EnableTotalRecordCount:!1};options.Limit=20;var userId=apiClient.getCurrentUserId();return"MusicArtist"===section.types?apiClient.getArtists(userId,options):(options.IncludeItemTypes=section.types,apiClient.getItems(userId,options))}}function getRouteUrl(section,serverId){return appRouter.getRouteUrl("list",{serverId:serverId,itemTypes:section.types,isFavorite:!0})}function getItemsHtmlFn(section){return function(items){var supportsImageAnalysis=appHost.supports("imageanalysis"),cardLayout=(appHost.preferVisualCards||supportsImageAnalysis)&§ion.autoCardLayout&§ion.showTitle;cardLayout=!1;var serverId=this.apiClient.serverId(),leadingButtons=layoutManager.tv?[{name:globalize.translate("sharedcomponents#All"),id:"more",icon:"",routeUrl:getRouteUrl(section,serverId)}]:null,lines=0;return section.showTitle&&lines++,section.showYear&&lines++,section.showParentTitle&&lines++,cardBuilder.getCardsHtml({items:items,preferThumb:section.preferThumb,shape:section.shape,centerText:section.centerText&&!cardLayout,overlayText:!1!==section.overlayText,showTitle:section.showTitle,showYear:section.showYear,showParentTitle:section.showParentTitle,scalable:!0,coverImage:section.coverImage,overlayPlayButton:section.overlayPlayButton,overlayMoreButton:section.overlayMoreButton&&!cardLayout,action:section.action,allowBottomPadding:!enableScrollX(),cardLayout:cardLayout,vibrant:supportsImageAnalysis&&cardLayout,leadingButtons:leadingButtons,lines:lines})}}function FavoritesTab(view,params){this.view=view,this.params=params,this.apiClient=connectionManager.currentApiClient(),this.sectionsContainer=view.querySelector(".sections"),createSections(this,this.sectionsContainer,this.apiClient)}function createSections(instance,elem,apiClient){var i,length,sections=getSections(),html="";for(i=0,length=sections.length;i',html+='
    ',layoutManager.tv?html+='

    '+globalize.translate(section.name)+"

    ":(html+='',html+='

    ',html+=globalize.translate(section.name),html+="

    ",html+='',html+="
    "),html+="
    ",html+='
    ',html+=""}elem.innerHTML=html;var elems=elem.querySelectorAll(".itemsContainer");for(i=0,length=elems.length;i', html += '
    ', layoutManager.tv ? html += '

    ' + globalize.translate(section.name) + "

    " : (html += '', html += '

    ', html += globalize.translate(section.name), html += "

    ", html += '', html += "
    "), html += "
    ", html += '
    ', html += "" + } + elem.innerHTML = html; + var elems = elem.querySelectorAll(".itemsContainer"); + for (i = 0, length = elems.length; i < length; i++) { + var itemsContainer = elems[i]; + itemsContainer.fetchData = getFetchDataFn(sections[i]).bind(instance), itemsContainer.getItemsHtml = getItemsHtmlFn(sections[i]).bind(instance), itemsContainer.parentContainer = dom.parentWithClass(itemsContainer, "verticalSection") + } + } + return FavoritesTab.prototype.onResume = function(options) { + for (var promises = (this.apiClient, []), view = this.view, elems = this.sectionsContainer.querySelectorAll(".itemsContainer"), i = 0, length = elems.length; i < length; i++) promises.push(elems[i].resume(options)); + Promise.all(promises).then(function() { + options.autoFocus && focusManager.autoFocus(view) + }) + }, FavoritesTab.prototype.onPause = function() { + for (var elems = this.sectionsContainer.querySelectorAll(".itemsContainer"), i = 0, length = elems.length; i < length; i++) elems[i].pause() + }, FavoritesTab.prototype.destroy = function() { + this.view = null, this.params = null, this.apiClient = null; + for (var elems = this.sectionsContainer.querySelectorAll(".itemsContainer"), i = 0, length = elems.length; i < length; i++) elems[i].fetchData = null, elems[i].getItemsHtml = null, elems[i].parentContainer = null; + this.sectionsContainer = null + }, FavoritesTab +}); \ No newline at end of file diff --git a/dashboard-ui/home/home.js b/dashboard-ui/home/home.js index 6675114093..c6a60779c9 100644 --- a/dashboard-ui/home/home.js +++ b/dashboard-ui/home/home.js @@ -1 +1,52 @@ -define(["tabbedView","globalize","require","emby-tabs","emby-button","emby-scroller"],function(TabbedView,globalize,require){"use strict";function getTabs(){return[{name:globalize.translate("sharedcomponents#Home")},{name:globalize.translate("sharedcomponents#Favorites")}]}function getDefaultTabIndex(){return 0}function getRequirePromise(deps){return new Promise(function(resolve,reject){require(deps,resolve)})}function getTabController(index){if(null==index)throw new Error("index cannot be null");var depends=[];switch(index){case 0:depends.push("./hometab");break;case 1:depends.push("./favorites")}var instance=this;return getRequirePromise(depends).then(function(controllerFactory){var controller=instance.tabControllers[index];if(!controller){controller=new controllerFactory(instance.view.querySelector(".tabContent[data-index='"+index+"']"),instance.params),instance.tabControllers[index]=controller}return controller})}function HomeView(view,params){TabbedView.call(this,view,params)}return Object.assign(HomeView.prototype,TabbedView.prototype),HomeView.prototype.getTabs=getTabs,HomeView.prototype.getDefaultTabIndex=getDefaultTabIndex,HomeView.prototype.getTabController=getTabController,HomeView.prototype.setTitle=function(){Emby.Page.setTitle(null)},HomeView.prototype.onPause=function(){TabbedView.prototype.onPause.call(this),document.querySelector(".skinHeader").classList.remove("noHomeButtonHeader")},HomeView.prototype.onResume=function(options){TabbedView.prototype.onResume.call(this,options),document.querySelector(".skinHeader").classList.add("noHomeButtonHeader")},HomeView}); \ No newline at end of file +define(["tabbedView", "globalize", "require", "emby-tabs", "emby-button", "emby-scroller"], function(TabbedView, globalize, require) { + "use strict"; + + function getTabs() { + return [{ + name: globalize.translate("sharedcomponents#Home") + }, { + name: globalize.translate("sharedcomponents#Favorites") + }] + } + + function getDefaultTabIndex() { + return 0 + } + + function getRequirePromise(deps) { + return new Promise(function(resolve, reject) { + require(deps, resolve) + }) + } + + function getTabController(index) { + if (null == index) throw new Error("index cannot be null"); + var depends = []; + switch (index) { + case 0: + depends.push("./hometab"); + break; + case 1: + depends.push("./favorites") + } + var instance = this; + return getRequirePromise(depends).then(function(controllerFactory) { + var controller = instance.tabControllers[index]; + if (!controller) { + controller = new controllerFactory(instance.view.querySelector(".tabContent[data-index='" + index + "']"), instance.params), instance.tabControllers[index] = controller + } + return controller + }) + } + + function HomeView(view, params) { + TabbedView.call(this, view, params) + } + return Object.assign(HomeView.prototype, TabbedView.prototype), HomeView.prototype.getTabs = getTabs, HomeView.prototype.getDefaultTabIndex = getDefaultTabIndex, HomeView.prototype.getTabController = getTabController, HomeView.prototype.setTitle = function() { + Emby.Page.setTitle(null) + }, HomeView.prototype.onPause = function() { + TabbedView.prototype.onPause.call(this), document.querySelector(".skinHeader").classList.remove("noHomeButtonHeader") + }, HomeView.prototype.onResume = function(options) { + TabbedView.prototype.onResume.call(this, options), document.querySelector(".skinHeader").classList.add("noHomeButtonHeader") + }, HomeView +}); \ No newline at end of file diff --git a/dashboard-ui/home/hometab.js b/dashboard-ui/home/hometab.js index 58025718df..fed9b72146 100644 --- a/dashboard-ui/home/hometab.js +++ b/dashboard-ui/home/hometab.js @@ -1 +1,35 @@ -define(["userSettings","loading","connectionManager","apphost","layoutManager","focusManager","homeSections","emby-itemscontainer"],function(userSettings,loading,connectionManager,appHost,layoutManager,focusManager,homeSections){"use strict";function HomeTab(view,params){this.view=view,this.params=params,this.apiClient=connectionManager.currentApiClient(),this.sectionsContainer=view.querySelector(".sections"),view.querySelector(".sections").addEventListener("settingschange",onHomeScreenSettingsChanged.bind(this))}function onHomeScreenSettingsChanged(){this.sectionsRendered=!1,this.paused||this.onResume({refresh:!0})}return HomeTab.prototype.onResume=function(options){if(this.sectionsRendered){var sectionsContainer=this.sectionsContainer;return sectionsContainer?homeSections.resume(sectionsContainer,options):Promise.resolve()}loading.show();var view=this.view,apiClient=this.apiClient;return this.destroyHomeSections(),this.sectionsRendered=!0,apiClient.getCurrentUser().then(function(user){return homeSections.loadSections(view.querySelector(".sections"),apiClient,user,userSettings).then(function(){options.autoFocus&&focusManager.autoFocus(view),loading.hide()})})},HomeTab.prototype.onPause=function(){var sectionsContainer=this.sectionsContainer;sectionsContainer&&homeSections.pause(sectionsContainer)},HomeTab.prototype.destroy=function(){this.view=null,this.params=null,this.apiClient=null,this.destroyHomeSections(),this.sectionsContainer=null},HomeTab.prototype.destroyHomeSections=function(){var sectionsContainer=this.sectionsContainer;sectionsContainer&&homeSections.destroySections(sectionsContainer)},HomeTab}); \ No newline at end of file +define(["userSettings", "loading", "connectionManager", "apphost", "layoutManager", "focusManager", "homeSections", "emby-itemscontainer"], function(userSettings, loading, connectionManager, appHost, layoutManager, focusManager, homeSections) { + "use strict"; + + function HomeTab(view, params) { + this.view = view, this.params = params, this.apiClient = connectionManager.currentApiClient(), this.sectionsContainer = view.querySelector(".sections"), view.querySelector(".sections").addEventListener("settingschange", onHomeScreenSettingsChanged.bind(this)) + } + + function onHomeScreenSettingsChanged() { + this.sectionsRendered = !1, this.paused || this.onResume({ + refresh: !0 + }) + } + return HomeTab.prototype.onResume = function(options) { + if (this.sectionsRendered) { + var sectionsContainer = this.sectionsContainer; + return sectionsContainer ? homeSections.resume(sectionsContainer, options) : Promise.resolve() + } + loading.show(); + var view = this.view, + apiClient = this.apiClient; + return this.destroyHomeSections(), this.sectionsRendered = !0, apiClient.getCurrentUser().then(function(user) { + return homeSections.loadSections(view.querySelector(".sections"), apiClient, user, userSettings).then(function() { + options.autoFocus && focusManager.autoFocus(view), loading.hide() + }) + }) + }, HomeTab.prototype.onPause = function() { + var sectionsContainer = this.sectionsContainer; + sectionsContainer && homeSections.pause(sectionsContainer) + }, HomeTab.prototype.destroy = function() { + this.view = null, this.params = null, this.apiClient = null, this.destroyHomeSections(), this.sectionsContainer = null + }, HomeTab.prototype.destroyHomeSections = function() { + var sectionsContainer = this.sectionsContainer; + sectionsContainer && homeSections.destroySections(sectionsContainer) + }, HomeTab +}); \ No newline at end of file diff --git a/dashboard-ui/legacy/buttonenabled.js b/dashboard-ui/legacy/buttonenabled.js index aea7ab8ff8..6c2f3b1e94 100644 --- a/dashboard-ui/legacy/buttonenabled.js +++ b/dashboard-ui/legacy/buttonenabled.js @@ -1 +1,6 @@ -define(["jQuery"],function($){"use strict";$.fn.buttonEnabled=function(enabled){return enabled?this.attr("disabled","").removeAttr("disabled"):this.attr("disabled","disabled")}}); \ No newline at end of file +define(["jQuery"], function($) { + "use strict"; + $.fn.buttonEnabled = function(enabled) { + return enabled ? this.attr("disabled", "").removeAttr("disabled") : this.attr("disabled", "disabled") + } +}); \ No newline at end of file diff --git a/dashboard-ui/legacy/dashboard.js b/dashboard-ui/legacy/dashboard.js index 51f5820a7f..11ba3177b7 100644 --- a/dashboard-ui/legacy/dashboard.js +++ b/dashboard-ui/legacy/dashboard.js @@ -1 +1,20 @@ -Dashboard.confirm=function(message,title,callback){"use strict";require(["confirm"],function(confirm){confirm(message,title).then(function(){callback(!0)},function(){callback(!1)})})},Dashboard.showLoadingMsg=function(){"use strict";require(["loading"],function(loading){loading.show()})},Dashboard.hideLoadingMsg=function(){"use strict";require(["loading"],function(loading){loading.hide()})}; \ No newline at end of file +Dashboard.confirm = function(message, title, callback) { + "use strict"; + require(["confirm"], function(confirm) { + confirm(message, title).then(function() { + callback(!0) + }, function() { + callback(!1) + }) + }) +}, Dashboard.showLoadingMsg = function() { + "use strict"; + require(["loading"], function(loading) { + loading.show() + }) +}, Dashboard.hideLoadingMsg = function() { + "use strict"; + require(["loading"], function(loading) { + loading.hide() + }) +}; \ No newline at end of file diff --git a/dashboard-ui/legacy/fnchecked.js b/dashboard-ui/legacy/fnchecked.js index ed5a4c5bf6..120f6e148a 100644 --- a/dashboard-ui/legacy/fnchecked.js +++ b/dashboard-ui/legacy/fnchecked.js @@ -1 +1,10 @@ -define(["jQuery"],function($){"use strict";$.fn.checked=function(value){return!0===value||!1===value?$(this).each(function(){this.checked=value}):this.length&&this[0].checked},$.fn.checkboxradio=function(){return this}}); \ No newline at end of file +define(["jQuery"], function($) { + "use strict"; + $.fn.checked = function(value) { + return !0 === value || !1 === value ? $(this).each(function() { + this.checked = value + }) : this.length && this[0].checked + }, $.fn.checkboxradio = function() { + return this + } +}); \ No newline at end of file diff --git a/dashboard-ui/legacy/selectmenu.js b/dashboard-ui/legacy/selectmenu.js index 952941d9c7..bc211b9664 100644 --- a/dashboard-ui/legacy/selectmenu.js +++ b/dashboard-ui/legacy/selectmenu.js @@ -1 +1,6 @@ -define(["jQuery"],function($){"use strict";$.fn.selectmenu=function(){return this}}); \ No newline at end of file +define(["jQuery"], function($) { + "use strict"; + $.fn.selectmenu = function() { + return this + } +}); \ No newline at end of file diff --git a/dashboard-ui/list/list.js b/dashboard-ui/list/list.js index 6e38d1bfd3..7fdf8aa51e 100644 --- a/dashboard-ui/list/list.js +++ b/dashboard-ui/list/list.js @@ -1 +1,462 @@ -define(["globalize","listView","layoutManager","userSettings","focusManager","cardBuilder","loading","connectionManager","alphaNumericShortcuts","scroller","playbackManager","alphaPicker","emby-itemscontainer","emby-scroller"],function(globalize,listView,layoutManager,userSettings,focusManager,cardBuilder,loading,connectionManager,AlphaNumericShortcuts,scroller,playbackManager,alphaPicker){"use strict";function getInitialLiveTvQuery(instance,params){var query={UserId:connectionManager.getApiClient(params.serverId).getCurrentUserId(),StartIndex:0,Fields:"ChannelInfo,PrimaryImageAspectRatio",Limit:300};return"Recordings"===params.type?query.IsInProgress=!1:query.HasAired=!1,params.genreId&&(query.GenreIds=params.genreId),"true"===params.IsMovie?query.IsMovie=!0:"false"===params.IsMovie&&(query.IsMovie=!1),"true"===params.IsSeries?query.IsSeries=!0:"false"===params.IsSeries&&(query.IsSeries=!1),"true"===params.IsNews?query.IsNews=!0:"false"===params.IsNews&&(query.IsNews=!1),"true"===params.IsSports?query.IsSports=!0:"false"===params.IsSports&&(query.IsSports=!1),"true"===params.IsKids?query.IsKids=!0:"false"===params.IsKids&&(query.IsKids=!1),"true"===params.IsAiring?query.IsAiring=!0:"false"===params.IsAiring&&(query.IsAiring=!1),modifyQueryWithFilters(instance,query)}function modifyQueryWithFilters(instance,query){var sortValues=instance.getSortValues();query.SortBy||(query.SortBy=sortValues.sortBy,query.SortOrder=sortValues.sortOrder),query.Fields=query.Fields?query.Fields+",PrimaryImageAspectRatio":"PrimaryImageAspectRatio",query.ImageTypeLimit=1;var hasFilters,queryFilters=[],filters=instance.getFilters();return filters.IsPlayed&&(queryFilters.push("IsPlayed"),hasFilters=!0),filters.IsUnplayed&&(queryFilters.push("IsUnplayed"),hasFilters=!0),filters.IsFavorite&&(queryFilters.push("IsFavorite"),hasFilters=!0),filters.IsResumable&&(queryFilters.push("IsResumable"),hasFilters=!0),filters.VideoTypes&&(hasFilters=!0,query.VideoTypes=filters.VideoTypes),filters.GenreIds&&(hasFilters=!0,query.GenreIds=filters.GenreIds),filters.Is4K&&(query.Is4K=!0,hasFilters=!0),filters.IsHD&&(query.IsHD=!0,hasFilters=!0),filters.IsSD&&(query.IsHD=!1,hasFilters=!0),filters.Is3D&&(query.Is3D=!0,hasFilters=!0),filters.HasSubtitles&&(query.HasSubtitles=!0,hasFilters=!0),filters.HasTrailer&&(query.HasTrailer=!0,hasFilters=!0),filters.HasSpecialFeature&&(query.HasSpecialFeature=!0,hasFilters=!0),filters.HasThemeSong&&(query.HasThemeSong=!0,hasFilters=!0),filters.HasThemeVideo&&(query.HasThemeVideo=!0,hasFilters=!0),query.Filters=queryFilters.length?queryFilters.join(","):null,instance.setFilterStatus(hasFilters),instance.alphaPicker&&(query.NameStartsWithOrGreater=instance.alphaPicker.value()),query}function updateSortText(instance){var btnSortText=instance.btnSortText;if(btnSortText){for(var options=instance.getSortMenuOptions(),values=instance.getSortValues(),sortBy=values.sortBy,i=0,length=options.length;i40?(alphaPicker.classList.remove("hide"),layoutManager.tv?instance.itemsContainer.parentNode.classList.add("padded-left-withalphapicker"):instance.itemsContainer.parentNode.classList.add("padded-right-withalphapicker")):(alphaPicker.classList.add("hide"),instance.itemsContainer.parentNode.classList.remove("padded-left-withalphapicker"),instance.itemsContainer.parentNode.classList.remove("padded-right-withalphapicker"))}}}function getItems(instance,params,item,sortBy,startIndex,limit){var apiClient=connectionManager.getApiClient(params.serverId);if(instance.queryRecursive=!1,"Recordings"===params.type)return apiClient.getLiveTvRecordings(getInitialLiveTvQuery(instance,params));if("Programs"===params.type)return"true"===params.IsAiring?apiClient.getLiveTvRecommendedPrograms(getInitialLiveTvQuery(instance,params)):apiClient.getLiveTvPrograms(getInitialLiveTvQuery(instance,params));if("nextup"===params.type)return apiClient.getNextUpEpisodes(modifyQueryWithFilters(instance,{Limit:limit,Fields:"PrimaryImageAspectRatio,SeriesInfo,DateCreated,BasicSyncInfo",UserId:apiClient.getCurrentUserId(),ImageTypeLimit:1,EnableImageTypes:"Primary,Backdrop,Thumb",EnableTotalRecordCount:!1,SortBy:sortBy}));if(!item){instance.queryRecursive=!0;var method="getItems";return"MusicArtist"===params.type?method="getArtists":"Person"===params.type&&(method="getPeople"),apiClient[method](apiClient.getCurrentUserId(),modifyQueryWithFilters(instance,{StartIndex:startIndex,Limit:limit,Fields:"PrimaryImageAspectRatio,SortName",ImageTypeLimit:1,IncludeItemTypes:"MusicArtist"===params.type||"Person"===params.type?null:params.type,Recursive:!0,IsFavorite:"true"===params.IsFavorite||null,ArtistIds:params.artistId||null,SortBy:sortBy}))}if("Genre"===item.Type||"GameGenre"===item.Type||"MusicGenre"===item.Type||"Studio"===item.Type||"Person"===item.Type){instance.queryRecursive=!0;var query={StartIndex:startIndex,Limit:limit,Fields:"PrimaryImageAspectRatio,SortName",Recursive:!0,parentId:params.parentId,SortBy:sortBy};return"Studio"===item.Type?query.StudioIds=item.Id:"Genre"===item.Type||"GameGenre"===item.Type||"MusicGenre"===item.Type?query.GenreIds=item.Id:"Person"===item.Type&&(query.PersonIds=item.Id),"MusicGenre"===item.Type?query.IncludeItemTypes="MusicAlbum":"GameGenre"===item.Type?query.IncludeItemTypes="Game":"movies"===item.CollectionType?query.IncludeItemTypes="Movie":"tvshows"===item.CollectionType?query.IncludeItemTypes="Series":"Genre"===item.Type?query.IncludeItemTypes="Movie,Series,Video":"Person"===item.Type&&(query.IncludeItemTypes=params.type),apiClient.getItems(apiClient.getCurrentUserId(),modifyQueryWithFilters(instance,query))}return apiClient.getItems(apiClient.getCurrentUserId(),modifyQueryWithFilters(instance,{StartIndex:startIndex,Limit:limit,Fields:"PrimaryImageAspectRatio,SortName",ImageTypeLimit:1,ParentId:item.Id,SortBy:sortBy}))}function getItem(params){if("Recordings"===params.type)return Promise.resolve(null);if("Programs"===params.type)return Promise.resolve(null);if("nextup"===params.type)return Promise.resolve(null);var apiClient=connectionManager.getApiClient(params.serverId),itemId=params.genreId||params.gameGenreId||params.musicGenreId||params.studioId||params.personId||params.parentId;return itemId?apiClient.getItem(apiClient.getCurrentUserId(),itemId):Promise.resolve(null)}function showViewSettingsMenu(){var instance=this;require(["viewSettings"],function(ViewSettings){(new ViewSettings).show({settingsKey:instance.getSettingsKey(),settings:instance.getViewSettings(),visibleSettings:instance.getVisibleViewSettings()}).then(function(){updateItemsContainerForViewType(instance),instance.itemsContainer.refreshItems()})})}function showFilterMenu(){var instance=this;require(["filterMenu"],function(FilterMenu){(new FilterMenu).show({settingsKey:instance.getSettingsKey(),settings:instance.getFilters(),visibleSettings:instance.getVisibleFilters(),onChange:instance.itemsContainer.refreshItems.bind(instance.itemsContainer),parentId:instance.params.parentId,itemTypes:instance.getItemTypes(),serverId:instance.params.serverId,filterMenuOptions:instance.getFilterMenuOptions()}).then(function(){instance.itemsContainer.refreshItems()})})}function showSortMenu(){var instance=this;require(["sortMenu"],function(SortMenu){(new SortMenu).show({settingsKey:instance.getSettingsKey(),settings:instance.getSortValues(),onChange:instance.itemsContainer.refreshItems.bind(instance.itemsContainer),serverId:instance.params.serverId,sortOptions:instance.getSortMenuOptions()}).then(function(){updateSortText(instance),updateAlphaPickerState(instance),instance.itemsContainer.refreshItems()})})}function onNewItemClick(){var instance=this;require(["playlistEditor"],function(playlistEditor){(new playlistEditor).show({items:[],serverId:instance.params.serverId})})}function hideOrShowAll(elems,hide){for(var i=0,length=elems.length;i!'),btnFilter.classList.add("btnFilterWithBubble"),bubble=btnFilter.querySelector(".filterButtonBubble")}hasFilters?bubble.classList.remove("hide"):bubble.classList.add("hide")}},ItemsView.prototype.getFilterMenuOptions=function(){var params=this.params;return{IsAiring:params.IsAiring,IsMovie:params.IsMovie,IsSports:params.IsSports,IsKids:params.IsKids,IsNews:params.IsNews,IsSeries:params.IsSeries,Recursive:this.queryRecursive}},ItemsView.prototype.getVisibleViewSettings=function(){var item=(this.params,this.currentItem),fields=["showTitle"];return(!item||"PhotoAlbum"!==item.Type&&"ChannelFolderItem"!==item.Type)&&fields.push("imageType"),fields.push("viewType"),fields},ItemsView.prototype.getViewSettings=function(){var basekey=this.getSettingsKey(),params=this.params,item=this.currentItem,showTitle=userSettings.get(basekey+"-showTitle");"true"===showTitle?showTitle=!0:"false"===showTitle?showTitle=!1:"Programs"===params.type||"Recordings"===params.type||"Person"===params.type||"nextup"===params.type||"Audio"===params.type||"MusicAlbum"===params.type||"MusicArtist"===params.type?showTitle=!0:item&&"PhotoAlbum"!==item.Type&&(showTitle=!0);var imageType=userSettings.get(basekey+"-imageType");return imageType||"nextup"===params.type&&(imageType="thumb"),{showTitle:showTitle,showYear:"false"!==userSettings.get(basekey+"-showYear"),imageType:imageType||"primary",viewType:userSettings.get(basekey+"-viewType")||"images"}},ItemsView.prototype.getItemTypes=function(){var params=this.params;return"nextup"===params.type?["Episode"]:"Programs"===params.type?["Program"]:[]},ItemsView.prototype.getSettingsKey=function(){var values=[];values.push("items");var params=this.params;return params.type?values.push(params.type):params.parentId&&values.push(params.parentId),params.IsAiring&&values.push("IsAiring"),params.IsMovie&&values.push("IsMovie"),params.IsKids&&values.push("IsKids"),params.IsSports&&values.push("IsSports"),params.IsNews&&values.push("IsNews"),params.IsSeries&&values.push("IsSeries"),params.IsFavorite&&values.push("IsFavorite"),params.genreId&&values.push("Genre"),params.gameGenreId&&values.push("GameGenre"),params.musicGenreId&&values.push("MusicGenre"),params.studioId&&values.push("Studio"),params.personId&&values.push("Person"),params.parentId&&values.push("Folder"),values.join("-")},ItemsView}); \ No newline at end of file +define(["globalize", "listView", "layoutManager", "userSettings", "focusManager", "cardBuilder", "loading", "connectionManager", "alphaNumericShortcuts", "scroller", "playbackManager", "alphaPicker", "emby-itemscontainer", "emby-scroller"], function(globalize, listView, layoutManager, userSettings, focusManager, cardBuilder, loading, connectionManager, AlphaNumericShortcuts, scroller, playbackManager, alphaPicker) { + "use strict"; + + function getInitialLiveTvQuery(instance, params) { + var query = { + UserId: connectionManager.getApiClient(params.serverId).getCurrentUserId(), + StartIndex: 0, + Fields: "ChannelInfo,PrimaryImageAspectRatio", + Limit: 300 + }; + return "Recordings" === params.type ? query.IsInProgress = !1 : query.HasAired = !1, params.genreId && (query.GenreIds = params.genreId), "true" === params.IsMovie ? query.IsMovie = !0 : "false" === params.IsMovie && (query.IsMovie = !1), "true" === params.IsSeries ? query.IsSeries = !0 : "false" === params.IsSeries && (query.IsSeries = !1), "true" === params.IsNews ? query.IsNews = !0 : "false" === params.IsNews && (query.IsNews = !1), "true" === params.IsSports ? query.IsSports = !0 : "false" === params.IsSports && (query.IsSports = !1), "true" === params.IsKids ? query.IsKids = !0 : "false" === params.IsKids && (query.IsKids = !1), "true" === params.IsAiring ? query.IsAiring = !0 : "false" === params.IsAiring && (query.IsAiring = !1), modifyQueryWithFilters(instance, query) + } + + function modifyQueryWithFilters(instance, query) { + var sortValues = instance.getSortValues(); + query.SortBy || (query.SortBy = sortValues.sortBy, query.SortOrder = sortValues.sortOrder), query.Fields = query.Fields ? query.Fields + ",PrimaryImageAspectRatio" : "PrimaryImageAspectRatio", query.ImageTypeLimit = 1; + var hasFilters, queryFilters = [], + filters = instance.getFilters(); + return filters.IsPlayed && (queryFilters.push("IsPlayed"), hasFilters = !0), filters.IsUnplayed && (queryFilters.push("IsUnplayed"), hasFilters = !0), filters.IsFavorite && (queryFilters.push("IsFavorite"), hasFilters = !0), filters.IsResumable && (queryFilters.push("IsResumable"), hasFilters = !0), filters.VideoTypes && (hasFilters = !0, query.VideoTypes = filters.VideoTypes), filters.GenreIds && (hasFilters = !0, query.GenreIds = filters.GenreIds), filters.Is4K && (query.Is4K = !0, hasFilters = !0), filters.IsHD && (query.IsHD = !0, hasFilters = !0), filters.IsSD && (query.IsHD = !1, hasFilters = !0), filters.Is3D && (query.Is3D = !0, hasFilters = !0), filters.HasSubtitles && (query.HasSubtitles = !0, hasFilters = !0), filters.HasTrailer && (query.HasTrailer = !0, hasFilters = !0), filters.HasSpecialFeature && (query.HasSpecialFeature = !0, hasFilters = !0), filters.HasThemeSong && (query.HasThemeSong = !0, hasFilters = !0), filters.HasThemeVideo && (query.HasThemeVideo = !0, hasFilters = !0), query.Filters = queryFilters.length ? queryFilters.join(",") : null, instance.setFilterStatus(hasFilters), instance.alphaPicker && (query.NameStartsWithOrGreater = instance.alphaPicker.value()), query + } + + function updateSortText(instance) { + var btnSortText = instance.btnSortText; + if (btnSortText) { + for (var options = instance.getSortMenuOptions(), values = instance.getSortValues(), sortBy = values.sortBy, i = 0, length = options.length; i < length; i++) + if (sortBy === options[i].value) { + btnSortText.innerHTML = globalize.translate("sharedcomponents#SortByValue", options[i].name); + break + } var btnSortIcon = instance.btnSortIcon; + btnSortIcon && (btnSortIcon.innerHTML = "Descending" === values.sortOrder ? "" : "") + } + } + + function updateItemsContainerForViewType(instance) { + "list" === instance.getViewSettings().imageType ? (instance.itemsContainer.classList.remove("vertical-wrap"), instance.itemsContainer.classList.add("vertical-list")) : (instance.itemsContainer.classList.add("vertical-wrap"), instance.itemsContainer.classList.remove("vertical-list")) + } + + function updateAlphaPickerState(instance, numItems) { + if (instance.alphaPicker) { + var alphaPicker = instance.alphaPickerElement; + if (alphaPicker) { + var values = instance.getSortValues(); + null == numItems && (numItems = 100), "SortName" === values.sortBy && "Ascending" === values.sortOrder && numItems > 40 ? (alphaPicker.classList.remove("hide"), layoutManager.tv ? instance.itemsContainer.parentNode.classList.add("padded-left-withalphapicker") : instance.itemsContainer.parentNode.classList.add("padded-right-withalphapicker")) : (alphaPicker.classList.add("hide"), instance.itemsContainer.parentNode.classList.remove("padded-left-withalphapicker"), instance.itemsContainer.parentNode.classList.remove("padded-right-withalphapicker")) + } + } + } + + function getItems(instance, params, item, sortBy, startIndex, limit) { + var apiClient = connectionManager.getApiClient(params.serverId); + if (instance.queryRecursive = !1, "Recordings" === params.type) return apiClient.getLiveTvRecordings(getInitialLiveTvQuery(instance, params)); + if ("Programs" === params.type) return "true" === params.IsAiring ? apiClient.getLiveTvRecommendedPrograms(getInitialLiveTvQuery(instance, params)) : apiClient.getLiveTvPrograms(getInitialLiveTvQuery(instance, params)); + if ("nextup" === params.type) return apiClient.getNextUpEpisodes(modifyQueryWithFilters(instance, { + Limit: limit, + Fields: "PrimaryImageAspectRatio,SeriesInfo,DateCreated,BasicSyncInfo", + UserId: apiClient.getCurrentUserId(), + ImageTypeLimit: 1, + EnableImageTypes: "Primary,Backdrop,Thumb", + EnableTotalRecordCount: !1, + SortBy: sortBy + })); + if (!item) { + instance.queryRecursive = !0; + var method = "getItems"; + return "MusicArtist" === params.type ? method = "getArtists" : "Person" === params.type && (method = "getPeople"), apiClient[method](apiClient.getCurrentUserId(), modifyQueryWithFilters(instance, { + StartIndex: startIndex, + Limit: limit, + Fields: "PrimaryImageAspectRatio,SortName", + ImageTypeLimit: 1, + IncludeItemTypes: "MusicArtist" === params.type || "Person" === params.type ? null : params.type, + Recursive: !0, + IsFavorite: "true" === params.IsFavorite || null, + ArtistIds: params.artistId || null, + SortBy: sortBy + })) + } + if ("Genre" === item.Type || "GameGenre" === item.Type || "MusicGenre" === item.Type || "Studio" === item.Type || "Person" === item.Type) { + instance.queryRecursive = !0; + var query = { + StartIndex: startIndex, + Limit: limit, + Fields: "PrimaryImageAspectRatio,SortName", + Recursive: !0, + parentId: params.parentId, + SortBy: sortBy + }; + return "Studio" === item.Type ? query.StudioIds = item.Id : "Genre" === item.Type || "GameGenre" === item.Type || "MusicGenre" === item.Type ? query.GenreIds = item.Id : "Person" === item.Type && (query.PersonIds = item.Id), "MusicGenre" === item.Type ? query.IncludeItemTypes = "MusicAlbum" : "GameGenre" === item.Type ? query.IncludeItemTypes = "Game" : "movies" === item.CollectionType ? query.IncludeItemTypes = "Movie" : "tvshows" === item.CollectionType ? query.IncludeItemTypes = "Series" : "Genre" === item.Type ? query.IncludeItemTypes = "Movie,Series,Video" : "Person" === item.Type && (query.IncludeItemTypes = params.type), apiClient.getItems(apiClient.getCurrentUserId(), modifyQueryWithFilters(instance, query)) + } + return apiClient.getItems(apiClient.getCurrentUserId(), modifyQueryWithFilters(instance, { + StartIndex: startIndex, + Limit: limit, + Fields: "PrimaryImageAspectRatio,SortName", + ImageTypeLimit: 1, + ParentId: item.Id, + SortBy: sortBy + })) + } + + function getItem(params) { + if ("Recordings" === params.type) return Promise.resolve(null); + if ("Programs" === params.type) return Promise.resolve(null); + if ("nextup" === params.type) return Promise.resolve(null); + var apiClient = connectionManager.getApiClient(params.serverId), + itemId = params.genreId || params.gameGenreId || params.musicGenreId || params.studioId || params.personId || params.parentId; + return itemId ? apiClient.getItem(apiClient.getCurrentUserId(), itemId) : Promise.resolve(null) + } + + function showViewSettingsMenu() { + var instance = this; + require(["viewSettings"], function(ViewSettings) { + (new ViewSettings).show({ + settingsKey: instance.getSettingsKey(), + settings: instance.getViewSettings(), + visibleSettings: instance.getVisibleViewSettings() + }).then(function() { + updateItemsContainerForViewType(instance), instance.itemsContainer.refreshItems() + }) + }) + } + + function showFilterMenu() { + var instance = this; + require(["filterMenu"], function(FilterMenu) { + (new FilterMenu).show({ + settingsKey: instance.getSettingsKey(), + settings: instance.getFilters(), + visibleSettings: instance.getVisibleFilters(), + onChange: instance.itemsContainer.refreshItems.bind(instance.itemsContainer), + parentId: instance.params.parentId, + itemTypes: instance.getItemTypes(), + serverId: instance.params.serverId, + filterMenuOptions: instance.getFilterMenuOptions() + }).then(function() { + instance.itemsContainer.refreshItems() + }) + }) + } + + function showSortMenu() { + var instance = this; + require(["sortMenu"], function(SortMenu) { + (new SortMenu).show({ + settingsKey: instance.getSettingsKey(), + settings: instance.getSortValues(), + onChange: instance.itemsContainer.refreshItems.bind(instance.itemsContainer), + serverId: instance.params.serverId, + sortOptions: instance.getSortMenuOptions() + }).then(function() { + updateSortText(instance), updateAlphaPickerState(instance), instance.itemsContainer.refreshItems() + }) + }) + } + + function onNewItemClick() { + var instance = this; + require(["playlistEditor"], function(playlistEditor) { + (new playlistEditor).show({ + items: [], + serverId: instance.params.serverId + }) + }) + } + + function hideOrShowAll(elems, hide) { + for (var i = 0, length = elems.length; i < length; i++) hide ? elems[i].classList.add("hide") : elems[i].classList.remove("hide") + } + + function bindAll(elems, eventName, fn) { + for (var i = 0, length = elems.length; i < length; i++) elems[i].addEventListener(eventName, fn) + } + + function ItemsView(view, params) { + function fetchData() { + return getItems(self, params, self.currentItem).then(function(result) { + return null == self.totalItemCount && (self.totalItemCount = result.Items ? result.Items.length : result.length), updateAlphaPickerState(self, self.totalItemCount), result + }) + } + + function getItemsHtml(items) { + var settings = self.getViewSettings(); + if ("list" === settings.imageType) return listView.getListViewHtml({ + items: items + }); + var shape, preferThumb, preferDisc, preferLogo, defaultShape, item = self.currentItem, + lines = settings.showTitle ? 2 : 0; + "banner" === settings.imageType ? shape = "banner" : "disc" === settings.imageType ? (shape = "square", preferDisc = !0) : "logo" === settings.imageType ? (shape = "backdrop", preferLogo = !0) : "thumb" === settings.imageType ? (shape = "backdrop", preferThumb = !0) : "nextup" === params.type ? (shape = "backdrop", preferThumb = "thumb" === settings.imageType) : "Programs" === params.type || "Recordings" === params.type ? (shape = "true" === params.IsMovie ? "portrait" : "autoVertical", preferThumb = "true" !== params.IsMovie && "auto", defaultShape = "true" === params.IsMovie ? "portrait" : "backdrop") : shape = "autoVertical"; + var posterOptions = { + shape: shape, + showTitle: settings.showTitle, + showYear: settings.showTitle, + centerText: !0, + coverImage: !0, + preferThumb: preferThumb, + preferDisc: preferDisc, + preferLogo: preferLogo, + overlayPlayButton: !1, + overlayMoreButton: !0, + overlayText: !settings.showTitle, + defaultShape: defaultShape, + action: "Audio" === params.type ? "playallfromhere" : null + }; + if ("nextup" === params.type) posterOptions.showParentTitle = settings.showTitle; + else if ("Person" === params.type) posterOptions.showYear = !1, posterOptions.showParentTitle = !1, lines = 1; + else if ("Audio" === params.type) posterOptions.showParentTitle = settings.showTitle; + else if ("MusicAlbum" === params.type) posterOptions.showParentTitle = settings.showTitle; + else if ("Episode" === params.type) posterOptions.showParentTitle = settings.showTitle; + else if ("MusicArtist" === params.type) posterOptions.showYear = !1, lines = 1; + else if ("Programs" === params.type) { + lines = settings.showTitle ? 1 : 0; + var showParentTitle = settings.showTitle && "true" !== params.IsMovie; + showParentTitle && lines++; + var showAirTime = settings.showTitle && "Recordings" !== params.type; + showAirTime && lines++; + var showYear = settings.showTitle && "true" === params.IsMovie && "Recordings" === params.type; + showYear && lines++, posterOptions = Object.assign(posterOptions, { + inheritThumb: "Recordings" === params.type, + context: "livetv", + showParentTitle: showParentTitle, + showAirTime: showAirTime, + showAirDateTime: showAirTime, + overlayPlayButton: !1, + overlayMoreButton: !0, + showYear: showYear, + coverImage: !0 + }) + } else posterOptions.showParentTitle = settings.showTitle; + return posterOptions.lines = lines, posterOptions.items = items, item && "folders" === item.CollectionType && (posterOptions.context = "folders"), cardBuilder.getCardsHtml(posterOptions) + } + + function initAlphaPicker() { + self.scroller = view.querySelector(".scrollFrameY"); + var alphaPickerElement = self.alphaPickerElement; + layoutManager.tv ? (alphaPickerElement.classList.add("alphaPicker-fixed-left"), alphaPickerElement.classList.add("focuscontainer-left"), self.itemsContainer.parentNode.classList.add("padded-left-withalphapicker")) : (alphaPickerElement.classList.add("alphaPicker-fixed-right"), alphaPickerElement.classList.add("focuscontainer-right"), self.itemsContainer.parentNode.classList.add("padded-right-withalphapicker")), self.alphaPicker = new alphaPicker({ + element: alphaPickerElement, + itemsContainer: layoutManager.tv ? self.itemsContainer : null, + itemClass: "card", + valueChangeEvent: layoutManager.tv ? null : "click" + }), self.alphaPicker.on("alphavaluechanged", onAlphaPickerValueChanged) + } + + function onAlphaPickerValueChanged() { + self.alphaPicker.value(); + self.itemsContainer.refreshItems() + } + + function setTitle(item) { + Emby.Page.setTitle(getTitle(item) || ""), item && "playlists" === item.CollectionType ? hideOrShowAll(view.querySelectorAll(".btnNewItem"), !1) : hideOrShowAll(view.querySelectorAll(".btnNewItem"), !0) + } + + function getTitle(item) { + return "Recordings" === params.type ? globalize.translate("Recordings") : "Programs" === params.type ? "true" === params.IsMovie ? globalize.translate("Movies") : "true" === params.IsSports ? globalize.translate("Sports") : "true" === params.IsKids ? globalize.translate("HeaderForKids") : "true" === params.IsAiring ? globalize.translate("HeaderOnNow") : "true" === params.IsSeries ? globalize.translate("Shows") : "true" === params.IsNews ? globalize.translate("News") : globalize.translate("Programs") : "nextup" === params.type ? globalize.translate("NextUp") : "favoritemovies" === params.type ? globalize.translate("FavoriteMovies") : item ? item.Name : "Movie" === params.type ? globalize.translate("sharedcomponents#Movies") : "Series" === params.type ? globalize.translate("sharedcomponents#Shows") : "Season" === params.type ? globalize.translate("sharedcomponents#Seasons") : "Episode" === params.type ? globalize.translate("sharedcomponents#Episodes") : "MusicArtist" === params.type ? globalize.translate("sharedcomponents#Artists") : "MusicAlbum" === params.type ? globalize.translate("sharedcomponents#Albums") : "Audio" === params.type ? globalize.translate("sharedcomponents#Songs") : "Game" === params.type ? globalize.translate("sharedcomponents#Games") : "Video" === params.type ? globalize.translate("sharedcomponents#Videos") : void 0 + } + + function play() { + var currentItem = self.currentItem; + if (currentItem && !self.hasFilters) return void playbackManager.play({ + items: [currentItem] + }); + getItems(self, self.params, currentItem, null, null, 300).then(function(result) { + playbackManager.play({ + items: result.Items + }) + }) + } + + function queue() { + var currentItem = self.currentItem; + if (currentItem && !self.hasFilters) return void playbackManager.queue({ + items: [currentItem] + }); + getItems(self, self.params, currentItem, null, null, 300).then(function(result) { + playbackManager.queue({ + items: result.Items + }) + }) + } + + function shuffle() { + var currentItem = self.currentItem; + if (currentItem && !self.hasFilters) return void playbackManager.shuffle(currentItem); + getItems(self, self.params, currentItem, "Random", null, 300).then(function(result) { + playbackManager.play({ + items: result.Items + }) + }) + } + var self = this; + self.params = params, this.itemsContainer = view.querySelector(".itemsContainer"), params.parentId ? this.itemsContainer.setAttribute("data-parentid", params.parentId) : "nextup" === params.type ? this.itemsContainer.setAttribute("data-monitor", "videoplayback") : "favoritemovies" === params.type ? this.itemsContainer.setAttribute("data-monitor", "markfavorite") : "Programs" === params.type && this.itemsContainer.setAttribute("data-refreshinterval", "300000"); + var i, length, btnViewSettings = view.querySelectorAll(".btnViewSettings"); + for (i = 0, length = btnViewSettings.length; i < length; i++) btnViewSettings[i].addEventListener("click", showViewSettingsMenu.bind(this)); + var filterButtons = view.querySelectorAll(".btnFilter"); + this.filterButtons = filterButtons; + var hasVisibleFilters = this.getVisibleFilters().length; + for (i = 0, length = filterButtons.length; i < length; i++) { + var btnFilter = filterButtons[i]; + btnFilter.addEventListener("click", showFilterMenu.bind(this)), hasVisibleFilters ? btnFilter.classList.remove("hide") : btnFilter.classList.add("hide") + } + var sortButtons = view.querySelectorAll(".btnSort"); + for (this.sortButtons = sortButtons, i = 0, length = sortButtons.length; i < length; i++) { + var sortButton = sortButtons[i]; + sortButton.addEventListener("click", showSortMenu.bind(this)), "nextup" !== params.type && sortButton.classList.remove("hide") + } + this.btnSortText = view.querySelector(".btnSortText"), this.btnSortIcon = view.querySelector(".btnSortIcon"), bindAll(view.querySelectorAll(".btnNewItem"), "click", onNewItemClick.bind(this)), this.alphaPickerElement = view.querySelector(".alphaPicker"), self.itemsContainer.fetchData = fetchData, self.itemsContainer.getItemsHtml = getItemsHtml, view.addEventListener("viewshow", function(e) { + var isRestored = e.detail.isRestored; + isRestored || (loading.show(), updateSortText(self), updateItemsContainerForViewType(self)), setTitle(null), getItem(params).then(function(item) { + setTitle(item), self.currentItem = item; + var refresh = !isRestored; + self.itemsContainer.resume({ + refresh: refresh + }).then(function() { + loading.hide(), refresh && focusManager.autoFocus(self.itemsContainer) + }), isRestored || item && "PhotoAlbum" !== item.Type && initAlphaPicker(); + var itemType = item ? item.Type : null; + "MusicGenre" === itemType || "Programs" !== params.type && "Channel" !== itemType ? hideOrShowAll(view.querySelectorAll(".btnPlay"), !1) : hideOrShowAll(view.querySelectorAll(".btnPlay"), !0), "MusicGenre" === itemType || "Programs" !== params.type && "nextup" !== params.type && "Channel" !== itemType ? hideOrShowAll(view.querySelectorAll(".btnShuffle"), !1) : hideOrShowAll(view.querySelectorAll(".btnShuffle"), !0), item && playbackManager.canQueue(item) ? hideOrShowAll(view.querySelectorAll(".btnQueue"), !1) : hideOrShowAll(view.querySelectorAll(".btnQueue"), !0) + }), isRestored || (bindAll(view.querySelectorAll(".btnPlay"), "click", play), bindAll(view.querySelectorAll(".btnQueue"), "click", queue), bindAll(view.querySelectorAll(".btnShuffle"), "click", shuffle)), this.alphaNumericShortcuts = new AlphaNumericShortcuts({ + itemsContainer: self.itemsContainer + }) + }), view.addEventListener("viewhide", function(e) { + var itemsContainer = self.itemsContainer; + itemsContainer && itemsContainer.pause(); + var alphaNumericShortcuts = self.alphaNumericShortcuts; + alphaNumericShortcuts && (alphaNumericShortcuts.destroy(), self.alphaNumericShortcuts = null) + }), view.addEventListener("viewdestroy", function() { + self.listController && self.listController.destroy(), self.alphaPicker && (self.alphaPicker.off("alphavaluechanged", onAlphaPickerValueChanged), self.alphaPicker.destroy()), self.currentItem = null, self.scroller = null, self.itemsContainer = null, self.filterButtons = null, self.sortButtons = null, self.btnSortText = null, self.btnSortIcon = null, self.alphaPickerElement = null + }) + } + return ItemsView.prototype.getFilters = function() { + var basekey = this.getSettingsKey(); + return { + IsPlayed: "true" === userSettings.getFilter(basekey + "-filter-IsPlayed"), + IsUnplayed: "true" === userSettings.getFilter(basekey + "-filter-IsUnplayed"), + IsFavorite: "true" === userSettings.getFilter(basekey + "-filter-IsFavorite"), + IsResumable: "true" === userSettings.getFilter(basekey + "-filter-IsResumable"), + Is4K: "true" === userSettings.getFilter(basekey + "-filter-Is4K"), + IsHD: "true" === userSettings.getFilter(basekey + "-filter-IsHD"), + IsSD: "true" === userSettings.getFilter(basekey + "-filter-IsSD"), + Is3D: "true" === userSettings.getFilter(basekey + "-filter-Is3D"), + VideoTypes: userSettings.getFilter(basekey + "-filter-VideoTypes"), + SeriesStatus: userSettings.getFilter(basekey + "-filter-SeriesStatus"), + HasSubtitles: userSettings.getFilter(basekey + "-filter-HasSubtitles"), + HasTrailer: userSettings.getFilter(basekey + "-filter-HasTrailer"), + HasSpecialFeature: userSettings.getFilter(basekey + "-filter-HasSpecialFeature"), + HasThemeSong: userSettings.getFilter(basekey + "-filter-HasThemeSong"), + HasThemeVideo: userSettings.getFilter(basekey + "-filter-HasThemeVideo"), + GenreIds: userSettings.getFilter(basekey + "-filter-GenreIds") + } + }, ItemsView.prototype.getSortValues = function() { + var basekey = this.getSettingsKey(); + return { + sortBy: userSettings.getFilter(basekey + "-sortby") || this.getDefaultSortBy(), + sortOrder: "Descending" === userSettings.getFilter(basekey + "-sortorder") ? "Descending" : "Ascending" + } + }, ItemsView.prototype.getDefaultSortBy = function() { + var params = this.params, + sortNameOption = this.getNameSortOption(params); + return params.type ? sortNameOption.value : "IsFolder," + sortNameOption.value + }, ItemsView.prototype.getSortMenuOptions = function() { + var sortBy = [], + params = this.params; + "Programs" === params.type && sortBy.push({ + name: globalize.translate("sharedcomponents#AirDate"), + value: "StartDate,SortName" + }); + var option = this.getNameSortOption(params); + return option && sortBy.push(option), option = this.getCommunityRatingSortOption(), option && sortBy.push(option), option = this.getCriticRatingSortOption(), option && sortBy.push(option), "Programs" !== params.type && sortBy.push({ + name: globalize.translate("sharedcomponents#DateAdded"), + value: "DateCreated,SortName" + }), option = this.getDatePlayedSortOption(), option && sortBy.push(option), params.type || (option = this.getNameSortOption(params), sortBy.push({ + name: globalize.translate("sharedcomponents#Folders"), + value: "IsFolder," + option.value + })), sortBy.push({ + name: globalize.translate("sharedcomponents#ParentalRating"), + value: "OfficialRating,SortName" + }), option = this.getPlayCountSortOption(), option && sortBy.push(option), sortBy.push({ + name: globalize.translate("sharedcomponents#ReleaseDate"), + value: "ProductionYear,PremiereDate,SortName" + }), sortBy.push({ + name: globalize.translate("sharedcomponents#Runtime"), + value: "Runtime,SortName" + }), sortBy + }, ItemsView.prototype.getNameSortOption = function(params) { + return "Episode" === params.type ? { + name: globalize.translate("sharedcomponents#Name"), + value: "SeriesName,SortName" + } : { + name: globalize.translate("sharedcomponents#Name"), + value: "SortName" + } + }, ItemsView.prototype.getPlayCountSortOption = function() { + return "Programs" === this.params.type ? null : { + name: globalize.translate("sharedcomponents#PlayCount"), + value: "PlayCount,SortName" + } + }, ItemsView.prototype.getDatePlayedSortOption = function() { + return "Programs" === this.params.type ? null : { + name: globalize.translate("sharedcomponents#DatePlayed"), + value: "DatePlayed,SortName" + } + }, ItemsView.prototype.getCriticRatingSortOption = function() { + return "Programs" === this.params.type ? null : { + name: globalize.translate("sharedcomponents#CriticRating"), + value: "CriticRating,SortName" + } + }, ItemsView.prototype.getCommunityRatingSortOption = function() { + return { + name: globalize.translate("sharedcomponents#CommunityRating"), + value: "CommunityRating,SortName" + } + }, ItemsView.prototype.getVisibleFilters = function() { + var filters = [], + params = this.params; + return "nextup" === params.type || ("Programs" === params.type ? filters.push("Genres") : (params.type, filters.push("IsUnplayed"), filters.push("IsPlayed"), params.IsFavorite || filters.push("IsFavorite"), filters.push("IsResumable"), filters.push("VideoType"), filters.push("HasSubtitles"), filters.push("HasTrailer"), filters.push("HasSpecialFeature"), filters.push("HasThemeSong"), filters.push("HasThemeVideo"))), filters + }, ItemsView.prototype.setFilterStatus = function(hasFilters) { + this.hasFilters = hasFilters; + var filterButtons = this.filterButtons; + if (filterButtons.length) + for (var i = 0, length = filterButtons.length; i < length; i++) { + var btnFilter = filterButtons[i], + bubble = btnFilter.querySelector(".filterButtonBubble"); + if (!bubble) { + if (!hasFilters) continue; + btnFilter.insertAdjacentHTML("afterbegin", '
    !
    '), btnFilter.classList.add("btnFilterWithBubble"), bubble = btnFilter.querySelector(".filterButtonBubble") + } + hasFilters ? bubble.classList.remove("hide") : bubble.classList.add("hide") + } + }, ItemsView.prototype.getFilterMenuOptions = function() { + var params = this.params; + return { + IsAiring: params.IsAiring, + IsMovie: params.IsMovie, + IsSports: params.IsSports, + IsKids: params.IsKids, + IsNews: params.IsNews, + IsSeries: params.IsSeries, + Recursive: this.queryRecursive + } + }, ItemsView.prototype.getVisibleViewSettings = function() { + var item = (this.params, this.currentItem), + fields = ["showTitle"]; + return (!item || "PhotoAlbum" !== item.Type && "ChannelFolderItem" !== item.Type) && fields.push("imageType"), fields.push("viewType"), fields + }, ItemsView.prototype.getViewSettings = function() { + var basekey = this.getSettingsKey(), + params = this.params, + item = this.currentItem, + showTitle = userSettings.get(basekey + "-showTitle"); + "true" === showTitle ? showTitle = !0 : "false" === showTitle ? showTitle = !1 : "Programs" === params.type || "Recordings" === params.type || "Person" === params.type || "nextup" === params.type || "Audio" === params.type || "MusicAlbum" === params.type || "MusicArtist" === params.type ? showTitle = !0 : item && "PhotoAlbum" !== item.Type && (showTitle = !0); + var imageType = userSettings.get(basekey + "-imageType"); + return imageType || "nextup" === params.type && (imageType = "thumb"), { + showTitle: showTitle, + showYear: "false" !== userSettings.get(basekey + "-showYear"), + imageType: imageType || "primary", + viewType: userSettings.get(basekey + "-viewType") || "images" + } + }, ItemsView.prototype.getItemTypes = function() { + var params = this.params; + return "nextup" === params.type ? ["Episode"] : "Programs" === params.type ? ["Program"] : [] + }, ItemsView.prototype.getSettingsKey = function() { + var values = []; + values.push("items"); + var params = this.params; + return params.type ? values.push(params.type) : params.parentId && values.push(params.parentId), params.IsAiring && values.push("IsAiring"), params.IsMovie && values.push("IsMovie"), params.IsKids && values.push("IsKids"), params.IsSports && values.push("IsSports"), params.IsNews && values.push("IsNews"), params.IsSeries && values.push("IsSeries"), params.IsFavorite && values.push("IsFavorite"), params.genreId && values.push("Genre"), params.gameGenreId && values.push("GameGenre"), params.musicGenreId && values.push("MusicGenre"), params.studioId && values.push("Studio"), params.personId && values.push("Person"), params.parentId && values.push("Folder"), values.join("-") + }, ItemsView +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/apploader.js b/dashboard-ui/scripts/apploader.js index a9ce1ebfec..3eb53cfcd0 100644 --- a/dashboard-ui/scripts/apploader.js +++ b/dashboard-ui/scripts/apploader.js @@ -1 +1,12 @@ -!function(){"use strict";function loadApp(){var script=document.createElement("script"),src="./scripts/site.js";self.dashboardVersion&&(src+="?v="+self.dashboardVersion),script.src=src,document.head.appendChild(script)}!function(){var src,script=document.createElement("script");src=self.Promise?"./bower_components/alameda/alameda.js":"./bower_components/requirejs/require.js",self.dashboardVersion&&(src+="?v="+self.dashboardVersion),script.src=src,script.onload=loadApp,document.head.appendChild(script)}()}(); \ No newline at end of file +! function() { + "use strict"; + + function loadApp() { + var script = document.createElement("script"), + src = "./scripts/site.js"; + self.dashboardVersion && (src += "?v=" + self.dashboardVersion), script.src = src, document.head.appendChild(script) + }! function() { + var src, script = document.createElement("script"); + src = self.Promise ? "./bower_components/alameda/alameda.js" : "./bower_components/requirejs/require.js", self.dashboardVersion && (src += "?v=" + self.dashboardVersion), script.src = src, script.onload = loadApp, document.head.appendChild(script) + }() +}(); \ No newline at end of file diff --git a/dashboard-ui/scripts/appservices.js b/dashboard-ui/scripts/appservices.js index 7ad0830e98..e5f93f932d 100644 --- a/dashboard-ui/scripts/appservices.js +++ b/dashboard-ui/scripts/appservices.js @@ -1 +1,56 @@ -define(["loading","libraryMenu"],function(loading,libraryMenu){"use strict";function reloadList(page){loading.show();var promise1=ApiClient.getAvailablePlugins({TargetSystems:"Server"}),promise2=ApiClient.getInstalledPlugins();Promise.all([promise1,promise2]).then(function(responses){renderInstalled(page,responses[0],responses[1]),renderCatalog(page,responses[0],responses[1])})}function getCategories(){var context=getParameterByName("context"),categories=[];return"sync"==context?categories.push("Sync"):"livetv"==context?categories.push("Live TV"):"notifications"==context&&categories.push("Notifications"),categories}function renderInstalled(page,availablePlugins,installedPlugins){requirejs(["scripts/pluginspage"],function(){var category=getCategories()[0];installedPlugins=installedPlugins.filter(function(i){var catalogEntry=availablePlugins.filter(function(a){return(a.guid||"").toLowerCase()==(i.Id||"").toLowerCase()})[0];return!!catalogEntry&&catalogEntry.category==category}),PluginsPage.renderPlugins(page,installedPlugins)})}function renderCatalog(page,availablePlugins,installedPlugins){requirejs(["scripts/plugincatalogpage"],function(){var categories=getCategories();PluginCatalog.renderCatalog({catalogElement:page.querySelector(".catalog"),availablePlugins:availablePlugins,installedPlugins:installedPlugins,categories:categories,showCategory:!1,context:getParameterByName("context"),targetSystem:"Server"})})}function onPageShow(){var page=this,context=getParameterByName("context");"sync"==context?(libraryMenu.setTitle(Globalize.translate("TitleSync")),page.querySelector(".headerHelpButton").setAttribute("href","https://github.com/MediaBrowser/Wiki/wiki/Sync")):"livetv"==context?(libraryMenu.setTitle(Globalize.translate("TitleLiveTV")),page.querySelector(".headerHelpButton").setAttribute("href","https://github.com/MediaBrowser/Wiki/wiki/Live%20TV")):"notifications"==context&&(libraryMenu.setTitle(Globalize.translate("TitleNotifications")),page.querySelector(".headerHelpButton").setAttribute("href","https://github.com/MediaBrowser/Wiki/wiki/Notifications"))}pageIdOn("pagebeforeshow","appServicesPage",onPageShow),pageIdOn("pageshow","appServicesPage",onPageShow),pageIdOn("pageshow","appServicesPage",function(){reloadList(this)})}); \ No newline at end of file +define(["loading", "libraryMenu"], function(loading, libraryMenu) { + "use strict"; + + function reloadList(page) { + loading.show(); + var promise1 = ApiClient.getAvailablePlugins({ + TargetSystems: "Server" + }), + promise2 = ApiClient.getInstalledPlugins(); + Promise.all([promise1, promise2]).then(function(responses) { + renderInstalled(page, responses[0], responses[1]), renderCatalog(page, responses[0], responses[1]) + }) + } + + function getCategories() { + var context = getParameterByName("context"), + categories = []; + return "sync" == context ? categories.push("Sync") : "livetv" == context ? categories.push("Live TV") : "notifications" == context && categories.push("Notifications"), categories + } + + function renderInstalled(page, availablePlugins, installedPlugins) { + requirejs(["scripts/pluginspage"], function() { + var category = getCategories()[0]; + installedPlugins = installedPlugins.filter(function(i) { + var catalogEntry = availablePlugins.filter(function(a) { + return (a.guid || "").toLowerCase() == (i.Id || "").toLowerCase() + })[0]; + return !!catalogEntry && catalogEntry.category == category + }), PluginsPage.renderPlugins(page, installedPlugins) + }) + } + + function renderCatalog(page, availablePlugins, installedPlugins) { + requirejs(["scripts/plugincatalogpage"], function() { + var categories = getCategories(); + PluginCatalog.renderCatalog({ + catalogElement: page.querySelector(".catalog"), + availablePlugins: availablePlugins, + installedPlugins: installedPlugins, + categories: categories, + showCategory: !1, + context: getParameterByName("context"), + targetSystem: "Server" + }) + }) + } + + function onPageShow() { + var page = this, + context = getParameterByName("context"); + "sync" == context ? (libraryMenu.setTitle(Globalize.translate("TitleSync")), page.querySelector(".headerHelpButton").setAttribute("href", "https://github.com/MediaBrowser/Wiki/wiki/Sync")) : "livetv" == context ? (libraryMenu.setTitle(Globalize.translate("TitleLiveTV")), page.querySelector(".headerHelpButton").setAttribute("href", "https://github.com/MediaBrowser/Wiki/wiki/Live%20TV")) : "notifications" == context && (libraryMenu.setTitle(Globalize.translate("TitleNotifications")), page.querySelector(".headerHelpButton").setAttribute("href", "https://github.com/MediaBrowser/Wiki/wiki/Notifications")) + } + pageIdOn("pagebeforeshow", "appServicesPage", onPageShow), pageIdOn("pageshow", "appServicesPage", onPageShow), pageIdOn("pageshow", "appServicesPage", function() { + reloadList(this) + }) +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/autobackdrops.js b/dashboard-ui/scripts/autobackdrops.js index 909d4bd099..45f9ec044d 100644 --- a/dashboard-ui/scripts/autobackdrops.js +++ b/dashboard-ui/scripts/autobackdrops.js @@ -1 +1,53 @@ -define(["backdrop","userSettings","libraryMenu"],function(backdrop,userSettings,libraryMenu){"use strict";function enabled(){return userSettings.enableBackdrops()}function getBackdropItemIds(apiClient,userId,types,parentId){var key="backdrops2_"+userId+(types||"")+(parentId||""),data=cache[key];if(data)return console.log("Found backdrop id list in cache. Key: "+key),data=JSON.parse(data),Promise.resolve(data);var options={SortBy:"IsFavoriteOrLiked,Random",Limit:20,Recursive:!0,IncludeItemTypes:types,ImageTypes:"Backdrop",ParentId:parentId,EnableTotalRecordCount:!1};return apiClient.getItems(apiClient.getCurrentUserId(),options).then(function(result){var images=result.Items.map(function(i){return{Id:i.Id,tag:i.BackdropImageTags[0],ServerId:i.ServerId}});return cache[key]=JSON.stringify(images),images})}function showBackdrop(type,parentId){var apiClient=window.ApiClient;apiClient&&getBackdropItemIds(apiClient,apiClient.getCurrentUserId(),type,parentId).then(function(images){images.length?backdrop.setBackdrops(images.map(function(i){return i.BackdropImageTags=[i.tag],i})):backdrop.clear()})}var cache={};pageClassOn("pagebeforeshow","page",function(){var page=this;if(!page.classList.contains("selfBackdropPage"))if(page.classList.contains("backdropPage"))if(enabled()){var type=page.getAttribute("data-backdroptype"),parentId=page.classList.contains("globalBackdropPage")?"":libraryMenu.getTopParentId();showBackdrop(type,parentId)}else page.classList.remove("backdropPage"),backdrop.clear();else backdrop.clear()})}); \ No newline at end of file +define(["backdrop", "userSettings", "libraryMenu"], function(backdrop, userSettings, libraryMenu) { + "use strict"; + + function enabled() { + return userSettings.enableBackdrops() + } + + function getBackdropItemIds(apiClient, userId, types, parentId) { + var key = "backdrops2_" + userId + (types || "") + (parentId || ""), + data = cache[key]; + if (data) return console.log("Found backdrop id list in cache. Key: " + key), data = JSON.parse(data), Promise.resolve(data); + var options = { + SortBy: "IsFavoriteOrLiked,Random", + Limit: 20, + Recursive: !0, + IncludeItemTypes: types, + ImageTypes: "Backdrop", + ParentId: parentId, + EnableTotalRecordCount: !1 + }; + return apiClient.getItems(apiClient.getCurrentUserId(), options).then(function(result) { + var images = result.Items.map(function(i) { + return { + Id: i.Id, + tag: i.BackdropImageTags[0], + ServerId: i.ServerId + } + }); + return cache[key] = JSON.stringify(images), images + }) + } + + function showBackdrop(type, parentId) { + var apiClient = window.ApiClient; + apiClient && getBackdropItemIds(apiClient, apiClient.getCurrentUserId(), type, parentId).then(function(images) { + images.length ? backdrop.setBackdrops(images.map(function(i) { + return i.BackdropImageTags = [i.tag], i + })) : backdrop.clear() + }) + } + var cache = {}; + pageClassOn("pagebeforeshow", "page", function() { + var page = this; + if (!page.classList.contains("selfBackdropPage")) + if (page.classList.contains("backdropPage")) + if (enabled()) { + var type = page.getAttribute("data-backdroptype"), + parentId = page.classList.contains("globalBackdropPage") ? "" : libraryMenu.getTopParentId(); + showBackdrop(type, parentId) + } else page.classList.remove("backdropPage"), backdrop.clear(); + else backdrop.clear() + }) +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/camerauploadsettings.js b/dashboard-ui/scripts/camerauploadsettings.js index 3dc0b97322..cb05b9cdf1 100644 --- a/dashboard-ui/scripts/camerauploadsettings.js +++ b/dashboard-ui/scripts/camerauploadsettings.js @@ -1 +1,29 @@ -define(["appSettings","loading","emby-checkbox"],function(appSettings,loading){"use strict";function loadForm(page,user){var uploadServers=appSettings.cameraUploadServers();page.querySelector(".uploadServerList").innerHTML=ConnectionManager.getSavedServers().map(function(s){return'"}).join(""),loading.hide()}function saveUser(page){for(var chkUploadServer=page.querySelectorAll(".chkUploadServer"),cameraUploadServers=[],i=0,length=chkUploadServer.length;i' + s.Name + "" + }).join(""), loading.hide() + } + + function saveUser(page) { + for (var chkUploadServer = page.querySelectorAll(".chkUploadServer"), cameraUploadServers = [], i = 0, length = chkUploadServer.length; i < length; i++) chkUploadServer[i].checked && cameraUploadServers.push(chkUploadServer[i].getAttribute("data-id")); + appSettings.cameraUploadServers(cameraUploadServers), window.MainActivity && MainActivity.authorizeStorage(), loading.hide() + } + return function(view, params) { + view.querySelector("form").addEventListener("submit", function(e) { + return loading.show(), saveUser(view), e.preventDefault(), !1 + }), view.addEventListener("viewshow", function() { + var page = this; + loading.show(); + var userId = params.userId || Dashboard.getCurrentUserId(); + ApiClient.getUser(userId).then(function(user) { + loadForm(page, user) + }) + }), view.addEventListener("viewbeforehide", function() { + saveUser(this) + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/connectlogin.js b/dashboard-ui/scripts/connectlogin.js index 60fa2a1d35..77c74e2867 100644 --- a/dashboard-ui/scripts/connectlogin.js +++ b/dashboard-ui/scripts/connectlogin.js @@ -1 +1,167 @@ -define(["appSettings","loading","browser","emby-linkbutton"],function(appSettings,loading,browser){"use strict";function login(page,username,password){loading.show(),appSettings.enableAutoLogin(!0),ConnectionManager.loginToConnect(username,password).then(function(){loading.hide(),Dashboard.navigate("selectserver.html")},function(){loading.hide(),Dashboard.alert({message:Globalize.translate("MessageInvalidUser"),title:Globalize.translate("HeaderLoginFailure")}),page.querySelector("#txtManualPassword").value=""})}function handleConnectionResult(page,result){switch(loading.hide(),result.State){case"SignedIn":var apiClient=result.ApiClient;Dashboard.onServerChanged(apiClient.getCurrentUserId(),apiClient.accessToken(),apiClient),Dashboard.navigate("home.html");break;case"ServerSignIn":Dashboard.navigate("login.html?serverid="+result.Servers[0].Id,!1,"none");break;case"ServerSelection":Dashboard.navigate("selectserver.html",!1,"none");break;case"ConnectSignIn":loadMode(page,"welcome");break;case"ServerUpdateNeeded":Dashboard.alert({message:Globalize.translate("ServerUpdateNeeded",'https://emby.media')});break;case"Unavailable":Dashboard.alert({message:Globalize.translate("MessageUnableToConnectToServer"),title:Globalize.translate("HeaderConnectionFailure")})}}function loadAppConnection(page){loading.show(),ConnectionManager.connect({enableAutoLogin:appSettings.enableAutoLogin()}).then(function(result){handleConnectionResult(page,result)})}function loadPage(page,params){var mode=params.mode||"auto";if("auto"==mode){if(AppInfo.isNativeApp)return void loadAppConnection(page);mode="connect"}loadMode(page,mode)}function loadMode(page,mode){"welcome"==mode?(page.querySelector(".connectLoginForm").classList.add("hide"),page.querySelector(".welcomeContainer").classList.remove("hide"),page.querySelector(".manualServerForm").classList.add("hide"),page.querySelector(".signupForm").classList.add("hide")):"connect"==mode?(page.querySelector(".connectLoginForm").classList.remove("hide"),page.querySelector(".welcomeContainer").classList.add("hide"),page.querySelector(".manualServerForm").classList.add("hide"),page.querySelector(".signupForm").classList.add("hide")):"manualserver"==mode?(page.querySelector(".manualServerForm").classList.remove("hide"),page.querySelector(".connectLoginForm").classList.add("hide"),page.querySelector(".welcomeContainer").classList.add("hide"),page.querySelector(".signupForm").classList.add("hide")):"signup"==mode&&(page.querySelector(".manualServerForm").classList.add("hide"),page.querySelector(".connectLoginForm").classList.add("hide"),page.querySelector(".welcomeContainer").classList.add("hide"),page.querySelector(".signupForm").classList.remove("hide"),initSignup(page))}function skip(){Dashboard.navigate("selectserver.html")}function requireCaptcha(){return!AppInfo.isNativeApp&&0==window.location.href.toLowerCase().indexOf("https")}function supportInAppSignup(){return AppInfo.isNativeApp||0==window.location.href.toLowerCase().indexOf("https")}function initSignup(page){supportInAppSignup()&&requireCaptcha()&&require(["https://www.google.com/recaptcha/api.js?render=explicit"],function(){setTimeout(function(){var recaptchaContainer=page.querySelector(".recaptchaContainer");greWidgetId=grecaptcha.render(recaptchaContainer,{sitekey:"6Le2LAgTAAAAAK06Wvttt_yUnbISTy6q3Azqp9po",theme:"dark"})},100)})}function submitManualServer(page){var host=page.querySelector("#txtServerHost").value,port=page.querySelector("#txtServerPort").value;port&&(host+=":"+port),loading.show(),ConnectionManager.connectToAddress(host,{enableAutoLogin:appSettings.enableAutoLogin()}).then(function(result){handleConnectionResult(page,result)},function(){handleConnectionResult(page,{State:"Unavailable"})})}function submit(page){login(page,page.querySelector("#txtManualName").value,page.querySelector("#txtManualPassword").value)}var greWidgetId;return function(view,params){function onSubmit(e){return submit(view),e.preventDefault(),!1}function onManualServerSubmit(e){return submitManualServer(view),e.preventDefault(),!1}function onSignupFormSubmit(e){if(!supportInAppSignup())return e.preventDefault(),!1;var page=view,greResponse=greWidgetId?grecaptcha.getResponse(greWidgetId):null;return ConnectionManager.signupForConnect({email:page.querySelector("#txtSignupEmail",page).value,username:page.querySelector("#txtSignupUsername",page).value,password:page.querySelector("#txtSignupPassword",page).value,passwordConfirm:page.querySelector("#txtSignupPasswordConfirm",page).value,grecaptcha:greResponse}).then(function(result){var msg=result.Validated?Globalize.translate("MessageThankYouForConnectSignUpNoValidation"):Globalize.translate("MessageThankYouForConnectSignUp");Dashboard.alert({message:msg,callback:function(){Dashboard.navigate("connectlogin.html?mode=welcome")}})},function(result){"passwordmatch"==result.errorCode?Dashboard.alert({message:Globalize.translate("ErrorMessagePasswordNotMatchConfirm")}):"USERNAME_IN_USE"==result.errorCode?Dashboard.alert({message:Globalize.translate("ErrorMessageUsernameInUse")}):"EMAIL_IN_USE"==result.errorCode?Dashboard.alert({message:Globalize.translate("ErrorMessageEmailInUse")}):Dashboard.alert({message:Globalize.translate("DefaultErrorMessage")})}),e.preventDefault(),!1}function goBack(){require(["appRouter"],function(appRouter){appRouter.back()})}view.querySelector(".btnSkipConnect").addEventListener("click",skip),view.querySelector(".connectLoginForm").addEventListener("submit",onSubmit),view.querySelector(".manualServerForm").addEventListener("submit",onManualServerSubmit),view.querySelector(".signupForm").addEventListener("submit",onSignupFormSubmit),view.querySelector(".btnSignupForConnect").addEventListener("click",function(e){if(supportInAppSignup())return e.preventDefault(),e.stopPropagation(),Dashboard.navigate("connectlogin.html?mode=signup"),!1}),view.querySelector(".btnCancelSignup").addEventListener("click",goBack),view.querySelector(".btnCancelManualServer").addEventListener("click",goBack),view.querySelector(".btnWelcomeNext").addEventListener("click",function(){Dashboard.navigate("connectlogin.html?mode=connect")});var terms=view.querySelector(".terms");terms.innerHTML=Globalize.translate("LoginDisclaimer")+"",AppInfo.isNativeApp?(terms.classList.add("hide"),view.querySelector(".tvAppInfo").classList.add("hide")):(terms.classList.remove("hide"),view.querySelector(".tvAppInfo").classList.remove("hide")),view.addEventListener("viewbeforeshow",function(){var page=this;if(page.querySelector("#txtSignupEmail").value="",page.querySelector("#txtSignupUsername").value="",page.querySelector("#txtSignupPassword").value="",page.querySelector("#txtSignupPasswordConfirm").value="",browser.safari&&AppInfo.isNativeApp)page.querySelector(".embyIntroDownloadMessage").innerHTML=Globalize.translate("EmbyIntroDownloadMessageWithoutLink");else{page.querySelector(".embyIntroDownloadMessage").innerHTML=Globalize.translate("EmbyIntroDownloadMessage",'http://emby.media')}}),view.addEventListener("viewshow",function(){loadPage(view,params)})}}); \ No newline at end of file +define(["appSettings", "loading", "browser", "emby-linkbutton"], function(appSettings, loading, browser) { + "use strict"; + + function login(page, username, password) { + loading.show(), appSettings.enableAutoLogin(!0), ConnectionManager.loginToConnect(username, password).then(function() { + loading.hide(), Dashboard.navigate("selectserver.html") + }, function() { + loading.hide(), Dashboard.alert({ + message: Globalize.translate("MessageInvalidUser"), + title: Globalize.translate("HeaderLoginFailure") + }), page.querySelector("#txtManualPassword").value = "" + }) + } + + function handleConnectionResult(page, result) { + switch (loading.hide(), result.State) { + case "SignedIn": + var apiClient = result.ApiClient; + Dashboard.onServerChanged(apiClient.getCurrentUserId(), apiClient.accessToken(), apiClient), Dashboard.navigate("home.html"); + break; + case "ServerSignIn": + Dashboard.navigate("login.html?serverid=" + result.Servers[0].Id, !1, "none"); + break; + case "ServerSelection": + Dashboard.navigate("selectserver.html", !1, "none"); + break; + case "ConnectSignIn": + loadMode(page, "welcome"); + break; + case "ServerUpdateNeeded": + Dashboard.alert({ + message: Globalize.translate("ServerUpdateNeeded", 'https://emby.media') + }); + break; + case "Unavailable": + Dashboard.alert({ + message: Globalize.translate("MessageUnableToConnectToServer"), + title: Globalize.translate("HeaderConnectionFailure") + }) + } + } + + function loadAppConnection(page) { + loading.show(), ConnectionManager.connect({ + enableAutoLogin: appSettings.enableAutoLogin() + }).then(function(result) { + handleConnectionResult(page, result) + }) + } + + function loadPage(page, params) { + var mode = params.mode || "auto"; + if ("auto" == mode) { + if (AppInfo.isNativeApp) return void loadAppConnection(page); + mode = "connect" + } + loadMode(page, mode) + } + + function loadMode(page, mode) { + "welcome" == mode ? (page.querySelector(".connectLoginForm").classList.add("hide"), page.querySelector(".welcomeContainer").classList.remove("hide"), page.querySelector(".manualServerForm").classList.add("hide"), page.querySelector(".signupForm").classList.add("hide")) : "connect" == mode ? (page.querySelector(".connectLoginForm").classList.remove("hide"), page.querySelector(".welcomeContainer").classList.add("hide"), page.querySelector(".manualServerForm").classList.add("hide"), page.querySelector(".signupForm").classList.add("hide")) : "manualserver" == mode ? (page.querySelector(".manualServerForm").classList.remove("hide"), page.querySelector(".connectLoginForm").classList.add("hide"), page.querySelector(".welcomeContainer").classList.add("hide"), page.querySelector(".signupForm").classList.add("hide")) : "signup" == mode && (page.querySelector(".manualServerForm").classList.add("hide"), page.querySelector(".connectLoginForm").classList.add("hide"), page.querySelector(".welcomeContainer").classList.add("hide"), page.querySelector(".signupForm").classList.remove("hide"), initSignup(page)) + } + + function skip() { + Dashboard.navigate("selectserver.html") + } + + function requireCaptcha() { + return !AppInfo.isNativeApp && 0 == window.location.href.toLowerCase().indexOf("https") + } + + function supportInAppSignup() { + return AppInfo.isNativeApp || 0 == window.location.href.toLowerCase().indexOf("https") + } + + function initSignup(page) { + supportInAppSignup() && requireCaptcha() && require(["https://www.google.com/recaptcha/api.js?render=explicit"], function() { + setTimeout(function() { + var recaptchaContainer = page.querySelector(".recaptchaContainer"); + greWidgetId = grecaptcha.render(recaptchaContainer, { + sitekey: "6Le2LAgTAAAAAK06Wvttt_yUnbISTy6q3Azqp9po", + theme: "dark" + }) + }, 100) + }) + } + + function submitManualServer(page) { + var host = page.querySelector("#txtServerHost").value, + port = page.querySelector("#txtServerPort").value; + port && (host += ":" + port), loading.show(), ConnectionManager.connectToAddress(host, { + enableAutoLogin: appSettings.enableAutoLogin() + }).then(function(result) { + handleConnectionResult(page, result) + }, function() { + handleConnectionResult(page, { + State: "Unavailable" + }) + }) + } + + function submit(page) { + login(page, page.querySelector("#txtManualName").value, page.querySelector("#txtManualPassword").value) + } + var greWidgetId; + return function(view, params) { + function onSubmit(e) { + return submit(view), e.preventDefault(), !1 + } + + function onManualServerSubmit(e) { + return submitManualServer(view), e.preventDefault(), !1 + } + + function onSignupFormSubmit(e) { + if (!supportInAppSignup()) return e.preventDefault(), !1; + var page = view, + greResponse = greWidgetId ? grecaptcha.getResponse(greWidgetId) : null; + return ConnectionManager.signupForConnect({ + email: page.querySelector("#txtSignupEmail", page).value, + username: page.querySelector("#txtSignupUsername", page).value, + password: page.querySelector("#txtSignupPassword", page).value, + passwordConfirm: page.querySelector("#txtSignupPasswordConfirm", page).value, + grecaptcha: greResponse + }).then(function(result) { + var msg = result.Validated ? Globalize.translate("MessageThankYouForConnectSignUpNoValidation") : Globalize.translate("MessageThankYouForConnectSignUp"); + Dashboard.alert({ + message: msg, + callback: function() { + Dashboard.navigate("connectlogin.html?mode=welcome") + } + }) + }, function(result) { + "passwordmatch" == result.errorCode ? Dashboard.alert({ + message: Globalize.translate("ErrorMessagePasswordNotMatchConfirm") + }) : "USERNAME_IN_USE" == result.errorCode ? Dashboard.alert({ + message: Globalize.translate("ErrorMessageUsernameInUse") + }) : "EMAIL_IN_USE" == result.errorCode ? Dashboard.alert({ + message: Globalize.translate("ErrorMessageEmailInUse") + }) : Dashboard.alert({ + message: Globalize.translate("DefaultErrorMessage") + }) + }), e.preventDefault(), !1 + } + + function goBack() { + require(["appRouter"], function(appRouter) { + appRouter.back() + }) + } + view.querySelector(".btnSkipConnect").addEventListener("click", skip), view.querySelector(".connectLoginForm").addEventListener("submit", onSubmit), view.querySelector(".manualServerForm").addEventListener("submit", onManualServerSubmit), view.querySelector(".signupForm").addEventListener("submit", onSignupFormSubmit), view.querySelector(".btnSignupForConnect").addEventListener("click", function(e) { + if (supportInAppSignup()) return e.preventDefault(), e.stopPropagation(), Dashboard.navigate("connectlogin.html?mode=signup"), !1 + }), view.querySelector(".btnCancelSignup").addEventListener("click", goBack), view.querySelector(".btnCancelManualServer").addEventListener("click", goBack), view.querySelector(".btnWelcomeNext").addEventListener("click", function() { + Dashboard.navigate("connectlogin.html?mode=connect") + }); + var terms = view.querySelector(".terms"); + terms.innerHTML = Globalize.translate("LoginDisclaimer") + "", AppInfo.isNativeApp ? (terms.classList.add("hide"), view.querySelector(".tvAppInfo").classList.add("hide")) : (terms.classList.remove("hide"), view.querySelector(".tvAppInfo").classList.remove("hide")), view.addEventListener("viewbeforeshow", function() { + var page = this; + if (page.querySelector("#txtSignupEmail").value = "", page.querySelector("#txtSignupUsername").value = "", page.querySelector("#txtSignupPassword").value = "", page.querySelector("#txtSignupPasswordConfirm").value = "", browser.safari && AppInfo.isNativeApp) page.querySelector(".embyIntroDownloadMessage").innerHTML = Globalize.translate("EmbyIntroDownloadMessageWithoutLink"); + else { + page.querySelector(".embyIntroDownloadMessage").innerHTML = Globalize.translate("EmbyIntroDownloadMessage", 'http://emby.media') + } + }), view.addEventListener("viewshow", function() { + loadPage(view, params) + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/dashboardpage.js b/dashboard-ui/scripts/dashboardpage.js index 93a52e0199..49013978d4 100644 --- a/dashboard-ui/scripts/dashboardpage.js +++ b/dashboard-ui/scripts/dashboardpage.js @@ -1,2 +1,545 @@ -define(["datetime","events","itemHelper","serverNotifications","dom","globalize","loading","connectionManager","playMethodHelper","cardBuilder","imageLoader","components/activitylog","humanedate","listViewStyle","emby-linkbutton","flexStyles","emby-button","emby-itemscontainer"],function(datetime,events,itemHelper,serverNotifications,dom,globalize,loading,connectionManager,playMethodHelper,cardBuilder,imageLoader,ActivityLog){"use strict";function onConnectionHelpClick(e){return e.preventDefault(),!1}function buttonEnabled(elem,enabled){enabled?(elem.setAttribute("disabled",""),elem.removeAttribute("disabled")):elem.setAttribute("disabled","disabled")}function onEditServerNameClick(e){var page=dom.parentWithClass(this,"page");return require(["prompt"],function(prompt){prompt({label:globalize.translate("LabelFriendlyServerName"),description:globalize.translate("LabelFriendlyServerNameHelp"),value:page.querySelector(".serverNameHeader").innerHTML,confirmText:globalize.translate("ButtonSave")}).then(function(value){loading.show(),ApiClient.getServerConfiguration().then(function(config){config.ServerName=value,ApiClient.updateServerConfiguration(config).then(function(){page.querySelector(".serverNameHeader").innerHTML=value,loading.hide()})})})}),e.preventDefault(),!1}function showPlaybackInfo(btn,session){require(["alert"],function(alert){var showTranscodeReasons,title,text=[],displayPlayMethod=playMethodHelper.getDisplayPlayMethod(session),isDirectStream="DirectStream"===displayPlayMethod,isTranscode="Transcode"===displayPlayMethod;isDirectStream?(title=globalize.translate("sharedcomponents#DirectStreaming"),text.push(globalize.translate("sharedcomponents#DirectStreamHelp1")),text.push("
    "),text.push(globalize.translate("sharedcomponents#DirectStreamHelp2"))):isTranscode&&(title=globalize.translate("sharedcomponents#Transcoding"),text.push(globalize.translate("sharedcomponents#MediaIsBeingConverted")),session.TranscodingInfo&&session.TranscodingInfo.TranscodeReasons&&session.TranscodingInfo.TranscodeReasons.length&&(text.push("
    "),text.push(globalize.translate("sharedcomponents#LabelReasonForTranscoding")),showTranscodeReasons=!0)),showTranscodeReasons&&session.TranscodingInfo.TranscodeReasons.forEach(function(t){text.push(globalize.translate("sharedcomponents#"+t))}),alert({text:text.join("
    "),title:title})})}function showSendMessageForm(btn,session){require(["prompt"],function(prompt){prompt({title:globalize.translate("HeaderSendMessage"),label:globalize.translate("LabelMessageText"),confirmText:globalize.translate("ButtonSend")}).then(function(text){if(text){connectionManager.getApiClient(session.ServerId).sendMessageCommand(session.Id,{Text:text,TimeoutMs:5e3})}})})}function showOptionsMenu(btn,session){require(["actionsheet"],function(actionsheet){var menuItems=[];return session.ServerId&&session.DeviceId!==connectionManager.deviceId()&&menuItems.push({name:globalize.translate("SendMessage"),id:"sendmessage"}),session.TranscodingInfo&&session.TranscodingInfo.TranscodeReasons&&session.TranscodingInfo.TranscodeReasons.length&&menuItems.push({name:globalize.translate("ViewPlaybackInfo"),id:"transcodinginfo"}),actionsheet.show({items:menuItems,positionTo:btn}).then(function(id){switch(id){case"sendmessage":showSendMessageForm(btn,session);break;case"transcodinginfo":showPlaybackInfo(btn,session)}})})}function onActiveDevicesClick(e){var btn=dom.parentWithClass(e.target,"sessionCardButton");if(btn){var card=dom.parentWithClass(btn,"card");if(card){var sessionId=card.id,session=(DashboardPage.sessionsList||[]).filter(function(s){return"session"+s.Id===sessionId})[0];session&&(btn.classList.contains("btnCardOptions")?showOptionsMenu(btn,session):btn.classList.contains("btnSessionInfo")?showPlaybackInfo(btn,session):btn.classList.contains("btnSessionSendMessage")?showSendMessageForm(btn,session):btn.classList.contains("btnSessionStop")?connectionManager.getApiClient(session.ServerId).sendPlayStateCommand(session.Id,"Stop"):btn.classList.contains("btnSessionPlayPause")&&session.PlayState&&connectionManager.getApiClient(session.ServerId).sendPlayStateCommand(session.Id,"PlayPause"))}}}function filterSessions(sessions){for(var list=[],minActiveDate=(new Date).getTime()-9e5,i=0,length=sessions.length;i=minActiveDate&&list.push(session)}}return list}function getPluginSecurityInfo(){var apiClient=window.ApiClient;return apiClient?connectionManager.getRegistrationInfo("themes",apiClient,{viewOnly:!0}).then(function(result){return{IsMBSupporter:!0}},function(){return{IsMBSupporter:!1}}):Promise.reject()}function refreshActiveRecordings(view,apiClient){apiClient.getLiveTvRecordings({UserId:Dashboard.getCurrentUserId(),IsInProgress:!0,Fields:"CanDelete,PrimaryImageAspectRatio",EnableTotalRecordCount:!1,EnableImageTypes:"Primary,Thumb,Backdrop"}).then(function(result){var itemsContainer=view.querySelector(".activeRecordingItems");if(!result.Items.length)return view.querySelector(".activeRecordingsSection").classList.add("hide"),void(itemsContainer.innerHTML="");view.querySelector(".activeRecordingsSection").classList.remove("hide");itemsContainer.innerHTML=cardBuilder.getCardsHtml({items:result.Items,shape:"auto",defaultShape:"backdrop",showTitle:!0,showParentTitle:!0,coverImage:!0,cardLayout:!1,centerText:!0,preferThumb:"auto",overlayText:!1,overlayMoreButton:!0,action:"none",centerPlayButton:!0}),imageLoader.lazyChildren(itemsContainer)})}function renderHasPendingRestart(view,apiClient,hasPendingRestart){if(hasPendingRestart)view.querySelector("#pUpToDate").classList.add("hide"),view.querySelector("#pUpdateNow").classList.add("hide");else{if(DashboardPage.lastAppUpdateCheck&&(new Date).getTime()-DashboardPage.lastAppUpdateCheck<18e5)return;DashboardPage.lastAppUpdateCheck=(new Date).getTime(),apiClient.getAvailableApplicationUpdate().then(function(packageInfo){var version=packageInfo[0];version?(view.querySelector("#pUpToDate").classList.add("hide"),view.querySelector("#pUpdateNow").classList.remove("hide"),view.querySelector("#newVersionNumber").innerHTML=globalize.translate("VersionXIsAvailableForDownload").replace("{0}",version.versionStr)):(view.querySelector("#pUpToDate").classList.remove("hide"),view.querySelector("#pUpdateNow").classList.add("hide"))})}}function reloadSystemInfo(view,apiClient){apiClient.getSystemInfo().then(function(systemInfo){view.querySelector(".serverNameHeader").innerHTML=systemInfo.ServerName;var localizedVersion=globalize.translate("LabelVersionNumber",systemInfo.Version);systemInfo.SystemUpdateLevel&&"Release"!=systemInfo.SystemUpdateLevel&&(localizedVersion+=" "+globalize.translate("Option"+systemInfo.SystemUpdateLevel).toLowerCase()),systemInfo.CanSelfRestart?view.querySelector("#btnRestartServer").classList.remove("hide"):view.querySelector("#btnRestartServer").classList.add("hide"),view.querySelector("#appVersionNumber").innerHTML=localizedVersion,systemInfo.SupportsHttps?view.querySelector("#ports").innerHTML=globalize.translate("LabelRunningOnPorts",systemInfo.HttpServerPortNumber,systemInfo.HttpsPortNumber):view.querySelector("#ports").innerHTML=globalize.translate("LabelRunningOnPort",systemInfo.HttpServerPortNumber),DashboardPage.renderUrls(view,systemInfo),DashboardPage.renderPendingInstallations(view,systemInfo),systemInfo.CanSelfUpdate?(view.querySelector("#btnUpdateApplicationContainer").classList.remove("hide"),view.querySelector("#btnManualUpdateContainer").classList.add("hide")):(view.querySelector("#btnUpdateApplicationContainer").classList.add("hide"),view.querySelector("#btnManualUpdateContainer").classList.remove("hide")),"synology"==systemInfo.PackageName?view.querySelector("#btnManualUpdateContainer").innerHTML=globalize.translate("SynologyUpdateInstructions"):view.querySelector("#btnManualUpdateContainer").innerHTML=''+globalize.translate("PleaseUpdateManually")+"",DashboardPage.renderPaths(view,systemInfo),renderHasPendingRestart(view,apiClient,systemInfo.HasPendingRestart)})}function renderInfo(view,sessions,forceUpdate){sessions=filterSessions(sessions),renderActiveConnections(view,sessions),DashboardPage.renderPluginUpdateInfo(view,forceUpdate),loading.hide()}function pollForInfo(view,apiClient,forceUpdate){apiClient.getSessions({ActiveWithinSeconds:960}).then(function(sessions){renderInfo(view,sessions,forceUpdate)}),apiClient.getScheduledTasks().then(function(tasks){renderRunningTasks(view,tasks)})}function renderActiveConnections(view,sessions){var html="";DashboardPage.sessionsList=sessions;var parentElement=view.querySelector(".activeDevices"),cardElem=parentElement.querySelector(".card");cardElem&&cardElem.classList.add("deadSession");for(var i=0,length=sessions.length;i',html+='
    ',html+='
    ',html+='
    ',html+='
    ';var imgUrl=DashboardPage.getNowPlayingImageUrl(nowPlayingItem);imgUrl?(html+='
    ',html+='
    '+session.DeviceName+"
    ",html+='
    '+DashboardPage.getAppSecondaryText(session)+"
    ",html+="
    ",html+="
    ",html+='
    '+DashboardPage.getSessionNowPlayingTime(session)+"
    ",session.TranscodingInfo&&session.TranscodingInfo.Framerate?html+='
    '+session.TranscodingInfo.Framerate+" fps
    ":html+='
    ';var nowPlayingName=DashboardPage.getNowPlayingName(session);if(html+='
    ',html+=nowPlayingName.html,html+="
    ",nowPlayingItem&&nowPlayingItem.RunTimeTicks){html+=''}else html+='';session.TranscodingInfo&&session.TranscodingInfo.CompletionPercentage?html+='':html+='',html+="
    ",html+="
    ",html+="",html+='
    ',html+='
    ';var btnCssClass;btnCssClass=session.ServerId&&session.NowPlayingItem&&session.SupportsRemoteControl&&session.DeviceId!==connectionManager.deviceId()?"":" hide",html+='',html+='',btnCssClass=session.TranscodingInfo&&session.TranscodingInfo.TranscodeReasons&&session.TranscodingInfo&&session.TranscodingInfo.TranscodeReasons.length?"":" hide",html+='',btnCssClass=session.ServerId&&-1!==session.SupportedCommands.indexOf("DisplayMessage")&&session.DeviceId!==connectionManager.deviceId()?"":" hide",html+='',html+="
    ",html+='
    ',html+=DashboardPage.getSessionNowPlayingStreamInfo(session),html+="
    ",html+='
    ';var userImage=DashboardPage.getUserImage(session);html+=userImage?'':'
    ',html+='
    ',html+=DashboardPage.getUsersHtml(session)||" ",html+="
    ",html+="
    ",html+="
    ",html+="",html+=""}}parentElement.insertAdjacentHTML("beforeend",html);var deadSessionElem=parentElement.querySelector(".deadSession");deadSessionElem&&deadSessionElem.parentNode.removeChild(deadSessionElem)}function renderRunningTasks(view,tasks){var html="";tasks=tasks.filter(function(t){return"Idle"!=t.State&&!t.IsHidden}),tasks.length?view.querySelector(".runningTasksContainer").classList.remove("hide"):view.querySelector(".runningTasksContainer").classList.add("hide"),tasks.filter(function(t){return t.Key==DashboardPage.systemUpdateTaskKey}).length?buttonEnabled(view.querySelector("#btnUpdateApplication"),!1):buttonEnabled(view.querySelector("#btnUpdateApplication"),!0);for(var i=0,length=tasks.length;i",html+=task.Name+"
    ","Running"==task.State){var progress=(task.CurrentProgressPercentage||0).toFixed(1);html+='',html+=progress+"%",html+="",html+=""+progress+"%",html+=''}else"Cancelling"==task.State&&(html+=''+globalize.translate("LabelStopping")+"");html+="

    "}view.querySelector("#divRunningTasks").innerHTML=html}return window.DashboardPage={newsStartIndex:0,renderPaths:function(page,systemInfo){page.querySelector("#cachePath").innerHTML=systemInfo.CachePath,page.querySelector("#logPath").innerHTML=systemInfo.LogPath,page.querySelector("#transcodingTemporaryPath").innerHTML=systemInfo.TranscodingTempPath,page.querySelector("#metadataPath").innerHTML=systemInfo.InternalMetadataPath},reloadNews:function(page){var query={StartIndex:DashboardPage.newsStartIndex,Limit:4};ApiClient.getProductNews(query).then(function(result){var html=result.Items.map(function(item){var itemHtml="";itemHtml+='',itemHtml+='
    ',itemHtml+='dvr',itemHtml+='
    ',itemHtml+='
    ',itemHtml+=item.Title,itemHtml+="
    ",itemHtml+='
    ';var date=datetime.parseISO8601Date(item.Date,!0);return itemHtml+=datetime.toLocaleDateString(date),itemHtml+="
    ",itemHtml+="
    ",itemHtml+="
    ",itemHtml+="
    "});page.querySelector(".latestNewsItems").innerHTML=html.join("")})},startInterval:function(apiClient){apiClient.sendMessage("SessionsStart","0,1500"),apiClient.sendMessage("ScheduledTasksInfoStart","0,1000")},stopInterval:function(apiClient){apiClient.sendMessage("SessionsStop"),apiClient.sendMessage("ScheduledTasksInfoStop")},getSessionNowPlayingStreamInfo:function(session){var html="",showTranscodingInfo=!1,displayPlayMethod=playMethodHelper.getDisplayPlayMethod(session);if("DirectStream"===displayPlayMethod?(html+=globalize.translate("sharedcomponents#DirectStreaming"),!0):"Transcode"==displayPlayMethod?(html+=globalize.translate("sharedcomponents#Transcoding"),session.TranscodingInfo&&session.TranscodingInfo.Framerate&&(html+=" ("+session.TranscodingInfo.Framerate+" fps)"),showTranscodingInfo=!0,!0):"DirectPlay"==displayPlayMethod&&(html+=globalize.translate("sharedcomponents#DirectPlaying")),showTranscodingInfo){var line=[];session.TranscodingInfo&&(session.TranscodingInfo.Bitrate&&(session.TranscodingInfo.Bitrate>1e6?line.push((session.TranscodingInfo.Bitrate/1e6).toFixed(1)+" Mbps"):line.push(Math.floor(session.TranscodingInfo.Bitrate/1e3)+" kbps")),session.TranscodingInfo.Container&&line.push(session.TranscodingInfo.Container),session.TranscodingInfo.VideoCodec&&line.push(session.TranscodingInfo.VideoCodec),session.TranscodingInfo.AudioCodec&&session.TranscodingInfo.AudioCodec!=session.TranscodingInfo.Container&&line.push(session.TranscodingInfo.AudioCodec)),line.length&&(html+=" - "+line.join(" "))}return html||" "},getSessionNowPlayingTime:function(session){var nowPlayingItem=session.NowPlayingItem,html="";return nowPlayingItem?(session.PlayState.PositionTicks?html+=datetime.getDisplayRunningTime(session.PlayState.PositionTicks):html+="--:--:--",html+=" / ",nowPlayingItem&&nowPlayingItem.RunTimeTicks?html+=datetime.getDisplayRunningTime(nowPlayingItem.RunTimeTicks):html+="--:--:--",html):html},getAppSecondaryText:function(session){return session.Client+" "+session.ApplicationVersion},getNowPlayingName:function(session){var imgUrl="",nowPlayingItem=session.NowPlayingItem;if(!nowPlayingItem)return{html:"Last seen "+humane_date(session.LastActivityDate),image:imgUrl};var topText=itemHelper.getDisplayName(nowPlayingItem),bottomText="";return nowPlayingItem.Artists&&nowPlayingItem.Artists.length?(bottomText=topText,topText=nowPlayingItem.Artists[0]):nowPlayingItem.SeriesName||nowPlayingItem.Album?(bottomText=topText,topText=nowPlayingItem.SeriesName||nowPlayingItem.Album):nowPlayingItem.ProductionYear&&(bottomText=nowPlayingItem.ProductionYear),nowPlayingItem.ImageTags&&nowPlayingItem.ImageTags.Logo?imgUrl=ApiClient.getScaledImageUrl(nowPlayingItem.Id,{tag:nowPlayingItem.ImageTags.Logo,maxHeight:24,maxWidth:130,type:"Logo"}):nowPlayingItem.ParentLogoImageTag&&(imgUrl=ApiClient.getScaledImageUrl(nowPlayingItem.ParentLogoItemId,{tag:nowPlayingItem.ParentLogoImageTag,maxHeight:24,maxWidth:130,type:"Logo"})),imgUrl&&(topText=''),{html:bottomText?topText+"
    "+bottomText:topText,image:imgUrl}},getUsersHtml:function(session){var html=[];session.UserId&&html.push(session.UserName);for(var i=0,length=session.AdditionalUsers.length;i"):null},getNowPlayingImageUrl:function(item){if(item&&item.BackdropImageTags&&item.BackdropImageTags.length)return ApiClient.getScaledImageUrl(item.Id,{type:"Backdrop",width:275,tag:item.BackdropImageTags[0]});if(item&&item.ParentBackdropImageTags&&item.ParentBackdropImageTags.length)return ApiClient.getScaledImageUrl(item.ParentBackdropItemId,{type:"Backdrop",width:275,tag:item.ParentBackdropImageTags[0]});if(item&&item.BackdropImageTag)return ApiClient.getScaledImageUrl(item.BackdropItemId,{type:"Backdrop",width:275,tag:item.BackdropImageTag});var imageTags=(item||{}).ImageTags||{};return item&&imageTags.Thumb?ApiClient.getScaledImageUrl(item.Id,{type:"Thumb",width:275,tag:imageTags.Thumb}):item&&item.ParentThumbImageTag?ApiClient.getScaledImageUrl(item.ParentThumbItemId,{type:"Thumb",width:275,tag:item.ParentThumbImageTag}):item&&item.ThumbImageTag?ApiClient.getScaledImageUrl(item.ThumbItemId,{type:"Thumb",width:275,tag:item.ThumbImageTag}):item&&imageTags.Primary?ApiClient.getScaledImageUrl(item.Id,{type:"Primary",width:275,tag:imageTags.Primary}):item&&item.PrimaryImageTag?ApiClient.getScaledImageUrl(item.PrimaryImageItemId,{type:"Primary",width:275,tag:item.PrimaryImageTag}):null},systemUpdateTaskKey:"SystemUpdateTask",renderUrls:function(page,systemInfo){var helpButton=''+globalize.translate("ButtonHelp")+"",localUrlElem=page.querySelector(".localUrl"),externalUrlElem=page.querySelector(".externalUrl");if(systemInfo.LocalAddress){var localAccessHtml=globalize.translate("LabelLocalAccessUrl",''+systemInfo.LocalAddress+"");localUrlElem.innerHTML=localAccessHtml+helpButton,localUrlElem.classList.remove("hide")}else localUrlElem.classList.add("hide");if(systemInfo.WanAddress){var externalUrl=systemInfo.WanAddress,remoteAccessHtml=globalize.translate("LabelRemoteAccessUrl",''+externalUrl+"");externalUrlElem.innerHTML=remoteAccessHtml+helpButton,externalUrlElem.classList.remove("hide")}else externalUrlElem.classList.add("hide")},renderSupporterIcon:function(page,pluginSecurityInfo){var imgUrl,text,supporterIconContainer=page.querySelector(".supporterIconContainer");pluginSecurityInfo.IsMBSupporter?(supporterIconContainer.classList.remove("hide"),imgUrl="css/images/supporter/supporterbadge.png",text=globalize.translate("MessageThankYouForSupporting"),supporterIconContainer.innerHTML=''):supporterIconContainer.classList.add("hide")},renderPendingInstallations:function(page,systemInfo){if(!systemInfo.CompletedInstallations.length)return void page.querySelector("#collapsiblePendingInstallations").classList.add("hide");page.querySelector("#collapsiblePendingInstallations").classList.remove("hide");for(var html="",i=0,length=systemInfo.CompletedInstallations.length;i"+update.Name+" ("+update.Version+")"}page.querySelector("#pendingInstallations").innerHTML=html},renderPluginUpdateInfo:function(page,forceUpdate){!forceUpdate&&DashboardPage.lastPluginUpdateCheck&&(new Date).getTime()-DashboardPage.lastPluginUpdateCheck<18e5||(DashboardPage.lastPluginUpdateCheck=(new Date).getTime(),ApiClient.getAvailablePluginUpdates().then(function(updates){var elem=page.querySelector("#pPluginUpdates");if(!updates.length)return void elem.classList.add("hide");elem.classList.remove("hide");for(var html="",i=0,length=updates.length;i"+globalize.translate("NewVersionOfSomethingAvailable").replace("{0}",update.name)+"

    ",html+='"}elem.innerHTML=html}))},installPluginUpdate:function(button){buttonEnabled(button,!1);var name=button.getAttribute("data-name"),guid=button.getAttribute("data-guid"),version=button.getAttribute("data-version"),classification=button.getAttribute("data-classification");loading.show(),ApiClient.installPlugin(name,guid,classification,version).then(function(){loading.hide()})},updateApplication:function(btn){var page=dom.parentWithClass(btn,"page");buttonEnabled(page.querySelector("#btnUpdateApplication"),!1),loading.show(),ApiClient.getScheduledTasks().then(function(tasks){var task=tasks.filter(function(t){return t.Key==DashboardPage.systemUpdateTaskKey})[0];ApiClient.startScheduledTask(task.Id).then(function(){pollForInfo(page,ApiClient),loading.hide()})})},stopTask:function(btn,id){var page=dom.parentWithClass(btn,"page");ApiClient.stopScheduledTask(id).then(function(){pollForInfo(page,ApiClient)})},restart:function(btn){require(["confirm"],function(confirm){confirm({title:globalize.translate("HeaderRestart"),text:globalize.translate("MessageConfirmRestart"),confirmText:globalize.translate("ButtonRestart"),primary:"cancel"}).then(function(){var page=dom.parentWithClass(btn,"page");buttonEnabled(page.querySelector("#btnRestartServer"),!1),buttonEnabled(page.querySelector("#btnShutdown"),!1),Dashboard.restartServer()})})},shutdown:function(btn){require(["confirm"],function(confirm){confirm({title:globalize.translate("HeaderShutdown"),text:globalize.translate("MessageConfirmShutdown"),confirmText:globalize.translate("ButtonShutdown"),primary:"cancel"}).then(function(){var page=dom.parentWithClass(btn,"page");buttonEnabled(page.querySelector("#btnRestartServer"),!1),buttonEnabled(page.querySelector("#btnShutdown"),!1),ApiClient.shutdownServer()})})}},pageClassOn("pageshow","type-interior",function(){var page=this;page.querySelector(".customSupporterPromotion")||getPluginSecurityInfo().then(function(pluginSecurityInfo){var supporterPromotionElem=page.querySelector(".supporterPromotion");if(supporterPromotionElem&&supporterPromotionElem.parentNode.removeChild(supporterPromotionElem),!pluginSecurityInfo.IsMBSupporter){var html='",page.querySelector(".content-primary").insertAdjacentHTML("afterbegin",html)}})}),function(view,params){function onRestartRequired(e,apiClient){apiClient.serverId()===serverId&&renderHasPendingRestart(view,apiClient,!0)}function onServerShuttingDown(e,apiClient){apiClient.serverId()===serverId&&renderHasPendingRestart(view,apiClient,!0)}function onServerRestarting(e,apiClient){apiClient.serverId()===serverId&&renderHasPendingRestart(view,apiClient,!0)}function onPackageInstalling(e,apiClient){apiClient.serverId()===serverId&&(pollForInfo(view,apiClient,!0),reloadSystemInfo(view,apiClient))}function onPackageInstallationCompleted(e,apiClient){apiClient.serverId()===serverId&&(pollForInfo(view,apiClient,!0),reloadSystemInfo(view,apiClient))}function onSessionsUpdate(e,apiClient,info){apiClient.serverId()===serverId&&renderInfo(view,info)}function onScheduledTasksUpdate(e,apiClient,info){apiClient.serverId()===serverId&&renderRunningTasks(view,info)}var serverId=ApiClient.serverId();view.querySelector(".btnConnectionHelp").addEventListener("click",onConnectionHelpClick),view.querySelector(".btnEditServerName").addEventListener("click",onEditServerNameClick),view.querySelector(".activeDevices").addEventListener("click",onActiveDevicesClick),view.addEventListener("viewshow",function(){var page=this,apiClient=ApiClient;if(apiClient){DashboardPage.newsStartIndex=0,loading.show(),pollForInfo(page,apiClient),DashboardPage.startInterval(apiClient),events.on(serverNotifications,"RestartRequired",onRestartRequired),events.on(serverNotifications,"ServerShuttingDown",onServerShuttingDown),events.on(serverNotifications,"ServerRestarting",onServerRestarting),events.on(serverNotifications,"PackageInstalling",onPackageInstalling),events.on(serverNotifications,"PackageInstallationCompleted",onPackageInstallationCompleted),events.on(serverNotifications,"Sessions",onSessionsUpdate), -events.on(serverNotifications,"ScheduledTasksInfo",onScheduledTasksUpdate),DashboardPage.lastAppUpdateCheck=null,DashboardPage.lastPluginUpdateCheck=null,getPluginSecurityInfo().then(function(pluginSecurityInfo){DashboardPage.renderSupporterIcon(page,pluginSecurityInfo)}),reloadSystemInfo(page,ApiClient),DashboardPage.reloadNews(page),page.userActivityLog||(page.userActivityLog=new ActivityLog({serverId:ApiClient.serverId(),element:page.querySelector(".userActivityItems")})),ApiClient.isMinServerVersion("3.4.1.25")&&(page.serverActivityLog||(page.serverActivityLog=new ActivityLog({serverId:ApiClient.serverId(),element:page.querySelector(".serverActivityItems")})));var swaggerUrl="http://swagger.emby.media?url="+ApiClient.getUrl("openapi");swaggerUrl=swaggerUrl+"&api_key="+ApiClient.accessToken(),page.querySelector(".swaggerLink").setAttribute("href",swaggerUrl),refreshActiveRecordings(view,apiClient)}}),view.addEventListener("viewbeforehide",function(){var apiClient=ApiClient;events.off(serverNotifications,"RestartRequired",onRestartRequired),events.off(serverNotifications,"ServerShuttingDown",onServerShuttingDown),events.off(serverNotifications,"ServerRestarting",onServerRestarting),events.off(serverNotifications,"PackageInstalling",onPackageInstalling),events.off(serverNotifications,"PackageInstallationCompleted",onPackageInstallationCompleted),events.off(serverNotifications,"Sessions",onSessionsUpdate),events.off(serverNotifications,"ScheduledTasksInfo",onScheduledTasksUpdate),apiClient&&DashboardPage.stopInterval(apiClient)}),view.addEventListener("viewdestroy",function(){var page=this,userActivityLog=page.userActivityLog;userActivityLog&&userActivityLog.destroy();var serverActivityLog=page.serverActivityLog;serverActivityLog&&serverActivityLog.destroy()})}}); \ No newline at end of file +define(["datetime", "events", "itemHelper", "serverNotifications", "dom", "globalize", "loading", "connectionManager", "playMethodHelper", "cardBuilder", "imageLoader", "components/activitylog", "humanedate", "listViewStyle", "emby-linkbutton", "flexStyles", "emby-button", "emby-itemscontainer"], function(datetime, events, itemHelper, serverNotifications, dom, globalize, loading, connectionManager, playMethodHelper, cardBuilder, imageLoader, ActivityLog) { + "use strict"; + + function onConnectionHelpClick(e) { + return e.preventDefault(), !1 + } + + function buttonEnabled(elem, enabled) { + enabled ? (elem.setAttribute("disabled", ""), elem.removeAttribute("disabled")) : elem.setAttribute("disabled", "disabled") + } + + function onEditServerNameClick(e) { + var page = dom.parentWithClass(this, "page"); + return require(["prompt"], function(prompt) { + prompt({ + label: globalize.translate("LabelFriendlyServerName"), + description: globalize.translate("LabelFriendlyServerNameHelp"), + value: page.querySelector(".serverNameHeader").innerHTML, + confirmText: globalize.translate("ButtonSave") + }).then(function(value) { + loading.show(), ApiClient.getServerConfiguration().then(function(config) { + config.ServerName = value, ApiClient.updateServerConfiguration(config).then(function() { + page.querySelector(".serverNameHeader").innerHTML = value, loading.hide() + }) + }) + }) + }), e.preventDefault(), !1 + } + + function showPlaybackInfo(btn, session) { + require(["alert"], function(alert) { + var showTranscodeReasons, title, text = [], + displayPlayMethod = playMethodHelper.getDisplayPlayMethod(session), + isDirectStream = "DirectStream" === displayPlayMethod, + isTranscode = "Transcode" === displayPlayMethod; + isDirectStream ? (title = globalize.translate("sharedcomponents#DirectStreaming"), text.push(globalize.translate("sharedcomponents#DirectStreamHelp1")), text.push("
    "), text.push(globalize.translate("sharedcomponents#DirectStreamHelp2"))) : isTranscode && (title = globalize.translate("sharedcomponents#Transcoding"), text.push(globalize.translate("sharedcomponents#MediaIsBeingConverted")), session.TranscodingInfo && session.TranscodingInfo.TranscodeReasons && session.TranscodingInfo.TranscodeReasons.length && (text.push("
    "), text.push(globalize.translate("sharedcomponents#LabelReasonForTranscoding")), showTranscodeReasons = !0)), showTranscodeReasons && session.TranscodingInfo.TranscodeReasons.forEach(function(t) { + text.push(globalize.translate("sharedcomponents#" + t)) + }), alert({ + text: text.join("
    "), + title: title + }) + }) + } + + function showSendMessageForm(btn, session) { + require(["prompt"], function(prompt) { + prompt({ + title: globalize.translate("HeaderSendMessage"), + label: globalize.translate("LabelMessageText"), + confirmText: globalize.translate("ButtonSend") + }).then(function(text) { + if (text) { + connectionManager.getApiClient(session.ServerId).sendMessageCommand(session.Id, { + Text: text, + TimeoutMs: 5e3 + }) + } + }) + }) + } + + function showOptionsMenu(btn, session) { + require(["actionsheet"], function(actionsheet) { + var menuItems = []; + return session.ServerId && session.DeviceId !== connectionManager.deviceId() && menuItems.push({ + name: globalize.translate("SendMessage"), + id: "sendmessage" + }), session.TranscodingInfo && session.TranscodingInfo.TranscodeReasons && session.TranscodingInfo.TranscodeReasons.length && menuItems.push({ + name: globalize.translate("ViewPlaybackInfo"), + id: "transcodinginfo" + }), actionsheet.show({ + items: menuItems, + positionTo: btn + }).then(function(id) { + switch (id) { + case "sendmessage": + showSendMessageForm(btn, session); + break; + case "transcodinginfo": + showPlaybackInfo(btn, session) + } + }) + }) + } + + function onActiveDevicesClick(e) { + var btn = dom.parentWithClass(e.target, "sessionCardButton"); + if (btn) { + var card = dom.parentWithClass(btn, "card"); + if (card) { + var sessionId = card.id, + session = (DashboardPage.sessionsList || []).filter(function(s) { + return "session" + s.Id === sessionId + })[0]; + session && (btn.classList.contains("btnCardOptions") ? showOptionsMenu(btn, session) : btn.classList.contains("btnSessionInfo") ? showPlaybackInfo(btn, session) : btn.classList.contains("btnSessionSendMessage") ? showSendMessageForm(btn, session) : btn.classList.contains("btnSessionStop") ? connectionManager.getApiClient(session.ServerId).sendPlayStateCommand(session.Id, "Stop") : btn.classList.contains("btnSessionPlayPause") && session.PlayState && connectionManager.getApiClient(session.ServerId).sendPlayStateCommand(session.Id, "PlayPause")) + } + } + } + + function filterSessions(sessions) { + for (var list = [], minActiveDate = (new Date).getTime() - 9e5, i = 0, length = sessions.length; i < length; i++) { + var session = sessions[i]; + if (session.NowPlayingItem || session.UserId) { + datetime.parseISO8601Date(session.LastActivityDate, !0).getTime() >= minActiveDate && list.push(session) + } + } + return list + } + + function getPluginSecurityInfo() { + var apiClient = window.ApiClient; + return apiClient ? connectionManager.getRegistrationInfo("themes", apiClient, { + viewOnly: !0 + }).then(function(result) { + return { + IsMBSupporter: !0 + } + }, function() { + return { + IsMBSupporter: !1 + } + }) : Promise.reject() + } + + function refreshActiveRecordings(view, apiClient) { + apiClient.getLiveTvRecordings({ + UserId: Dashboard.getCurrentUserId(), + IsInProgress: !0, + Fields: "CanDelete,PrimaryImageAspectRatio", + EnableTotalRecordCount: !1, + EnableImageTypes: "Primary,Thumb,Backdrop" + }).then(function(result) { + var itemsContainer = view.querySelector(".activeRecordingItems"); + if (!result.Items.length) return view.querySelector(".activeRecordingsSection").classList.add("hide"), void(itemsContainer.innerHTML = ""); + view.querySelector(".activeRecordingsSection").classList.remove("hide"); + itemsContainer.innerHTML = cardBuilder.getCardsHtml({ + items: result.Items, + shape: "auto", + defaultShape: "backdrop", + showTitle: !0, + showParentTitle: !0, + coverImage: !0, + cardLayout: !1, + centerText: !0, + preferThumb: "auto", + overlayText: !1, + overlayMoreButton: !0, + action: "none", + centerPlayButton: !0 + }), imageLoader.lazyChildren(itemsContainer) + }) + } + + function renderHasPendingRestart(view, apiClient, hasPendingRestart) { + if (hasPendingRestart) view.querySelector("#pUpToDate").classList.add("hide"), view.querySelector("#pUpdateNow").classList.add("hide"); + else { + if (DashboardPage.lastAppUpdateCheck && (new Date).getTime() - DashboardPage.lastAppUpdateCheck < 18e5) return; + DashboardPage.lastAppUpdateCheck = (new Date).getTime(), apiClient.getAvailableApplicationUpdate().then(function(packageInfo) { + var version = packageInfo[0]; + version ? (view.querySelector("#pUpToDate").classList.add("hide"), view.querySelector("#pUpdateNow").classList.remove("hide"), view.querySelector("#newVersionNumber").innerHTML = globalize.translate("VersionXIsAvailableForDownload").replace("{0}", version.versionStr)) : (view.querySelector("#pUpToDate").classList.remove("hide"), view.querySelector("#pUpdateNow").classList.add("hide")) + }) + } + } + + function reloadSystemInfo(view, apiClient) { + apiClient.getSystemInfo().then(function(systemInfo) { + view.querySelector(".serverNameHeader").innerHTML = systemInfo.ServerName; + var localizedVersion = globalize.translate("LabelVersionNumber", systemInfo.Version); + systemInfo.SystemUpdateLevel && "Release" != systemInfo.SystemUpdateLevel && (localizedVersion += " " + globalize.translate("Option" + systemInfo.SystemUpdateLevel).toLowerCase()), systemInfo.CanSelfRestart ? view.querySelector("#btnRestartServer").classList.remove("hide") : view.querySelector("#btnRestartServer").classList.add("hide"), view.querySelector("#appVersionNumber").innerHTML = localizedVersion, systemInfo.SupportsHttps ? view.querySelector("#ports").innerHTML = globalize.translate("LabelRunningOnPorts", systemInfo.HttpServerPortNumber, systemInfo.HttpsPortNumber) : view.querySelector("#ports").innerHTML = globalize.translate("LabelRunningOnPort", systemInfo.HttpServerPortNumber), DashboardPage.renderUrls(view, systemInfo), DashboardPage.renderPendingInstallations(view, systemInfo), systemInfo.CanSelfUpdate ? (view.querySelector("#btnUpdateApplicationContainer").classList.remove("hide"), view.querySelector("#btnManualUpdateContainer").classList.add("hide")) : (view.querySelector("#btnUpdateApplicationContainer").classList.add("hide"), view.querySelector("#btnManualUpdateContainer").classList.remove("hide")), "synology" == systemInfo.PackageName ? view.querySelector("#btnManualUpdateContainer").innerHTML = globalize.translate("SynologyUpdateInstructions") : view.querySelector("#btnManualUpdateContainer").innerHTML = '' + globalize.translate("PleaseUpdateManually") + "", DashboardPage.renderPaths(view, systemInfo), renderHasPendingRestart(view, apiClient, systemInfo.HasPendingRestart) + }) + } + + function renderInfo(view, sessions, forceUpdate) { + sessions = filterSessions(sessions), renderActiveConnections(view, sessions), DashboardPage.renderPluginUpdateInfo(view, forceUpdate), loading.hide() + } + + function pollForInfo(view, apiClient, forceUpdate) { + apiClient.getSessions({ + ActiveWithinSeconds: 960 + }).then(function(sessions) { + renderInfo(view, sessions, forceUpdate) + }), apiClient.getScheduledTasks().then(function(tasks) { + renderRunningTasks(view, tasks) + }) + } + + function renderActiveConnections(view, sessions) { + var html = ""; + DashboardPage.sessionsList = sessions; + var parentElement = view.querySelector(".activeDevices"), + cardElem = parentElement.querySelector(".card"); + cardElem && cardElem.classList.add("deadSession"); + for (var i = 0, length = sessions.length; i < length; i++) { + var session = sessions[i], + rowId = "session" + session.Id, + elem = view.querySelector("#" + rowId); + if (elem) DashboardPage.updateSession(elem, session); + else { + var nowPlayingItem = session.NowPlayingItem, + className = "scalableCard card activeSession backdropCard backdropCard-scalable"; + session.TranscodingInfo && session.TranscodingInfo.CompletionPercentage && (className += " transcodingSession"), html += '
    ', html += '
    ', html += '
    ', html += '
    ', html += '
    '; + var imgUrl = DashboardPage.getNowPlayingImageUrl(nowPlayingItem); + imgUrl ? (html += '
    ", html += '
    ' + DashboardPage.getAppSecondaryText(session) + "
    ", html += "
    ", html += "
    ", html += '
    ' + DashboardPage.getSessionNowPlayingTime(session) + "
    ", session.TranscodingInfo && session.TranscodingInfo.Framerate ? html += '
    ' + session.TranscodingInfo.Framerate + " fps
    " : html += '
    '; + var nowPlayingName = DashboardPage.getNowPlayingName(session); + if (html += '
    ', html += nowPlayingName.html, html += "
    ", nowPlayingItem && nowPlayingItem.RunTimeTicks) { + html += '' + } else html += ''; + session.TranscodingInfo && session.TranscodingInfo.CompletionPercentage ? html += '' : html += '', html += "
    ", html += "
    ", html += "
    ", html += '
    ', html += '
    '; + var btnCssClass; + btnCssClass = session.ServerId && session.NowPlayingItem && session.SupportsRemoteControl && session.DeviceId !== connectionManager.deviceId() ? "" : " hide", html += '', html += '', btnCssClass = session.TranscodingInfo && session.TranscodingInfo.TranscodeReasons && session.TranscodingInfo && session.TranscodingInfo.TranscodeReasons.length ? "" : " hide", html += '', btnCssClass = session.ServerId && -1 !== session.SupportedCommands.indexOf("DisplayMessage") && session.DeviceId !== connectionManager.deviceId() ? "" : " hide", html += '', html += "
    ", html += '
    ', html += DashboardPage.getSessionNowPlayingStreamInfo(session), html += "
    ", html += '
    '; + var userImage = DashboardPage.getUserImage(session); + html += userImage ? '' : '
    ', html += '
    ', html += DashboardPage.getUsersHtml(session) || " ", html += "
    ", html += "
    ", html += "
    ", html += "", html += "" + } + } + parentElement.insertAdjacentHTML("beforeend", html); + var deadSessionElem = parentElement.querySelector(".deadSession"); + deadSessionElem && deadSessionElem.parentNode.removeChild(deadSessionElem) + } + + function renderRunningTasks(view, tasks) { + var html = ""; + tasks = tasks.filter(function(t) { + return "Idle" != t.State && !t.IsHidden + }), tasks.length ? view.querySelector(".runningTasksContainer").classList.remove("hide") : view.querySelector(".runningTasksContainer").classList.add("hide"), tasks.filter(function(t) { + return t.Key == DashboardPage.systemUpdateTaskKey + }).length ? buttonEnabled(view.querySelector("#btnUpdateApplication"), !1) : buttonEnabled(view.querySelector("#btnUpdateApplication"), !0); + for (var i = 0, length = tasks.length; i < length; i++) { + var task = tasks[i]; + if (html += "

    ", html += task.Name + "
    ", "Running" == task.State) { + var progress = (task.CurrentProgressPercentage || 0).toFixed(1); + html += '', html += progress + "%", html += "", html += "" + progress + "%", html += '' + } else "Cancelling" == task.State && (html += '' + globalize.translate("LabelStopping") + ""); + html += "

    " + } + view.querySelector("#divRunningTasks").innerHTML = html + } + return window.DashboardPage = { + newsStartIndex: 0, + renderPaths: function(page, systemInfo) { + page.querySelector("#cachePath").innerHTML = systemInfo.CachePath, page.querySelector("#logPath").innerHTML = systemInfo.LogPath, page.querySelector("#transcodingTemporaryPath").innerHTML = systemInfo.TranscodingTempPath, page.querySelector("#metadataPath").innerHTML = systemInfo.InternalMetadataPath + }, + reloadNews: function(page) { + var query = { + StartIndex: DashboardPage.newsStartIndex, + Limit: 4 + }; + ApiClient.getProductNews(query).then(function(result) { + var html = result.Items.map(function(item) { + var itemHtml = ""; + itemHtml += '', itemHtml += '
    ', itemHtml += 'dvr', itemHtml += '
    ', itemHtml += '
    ', itemHtml += item.Title, itemHtml += "
    ", itemHtml += '
    '; + var date = datetime.parseISO8601Date(item.Date, !0); + return itemHtml += datetime.toLocaleDateString(date), itemHtml += "
    ", itemHtml += "
    ", itemHtml += "
    ", itemHtml += "
    " + }); + page.querySelector(".latestNewsItems").innerHTML = html.join("") + }) + }, + startInterval: function(apiClient) { + apiClient.sendMessage("SessionsStart", "0,1500"), apiClient.sendMessage("ScheduledTasksInfoStart", "0,1000") + }, + stopInterval: function(apiClient) { + apiClient.sendMessage("SessionsStop"), apiClient.sendMessage("ScheduledTasksInfoStop") + }, + getSessionNowPlayingStreamInfo: function(session) { + var html = "", + showTranscodingInfo = !1, + displayPlayMethod = playMethodHelper.getDisplayPlayMethod(session); + if ("DirectStream" === displayPlayMethod ? (html += globalize.translate("sharedcomponents#DirectStreaming"), !0) : "Transcode" == displayPlayMethod ? (html += globalize.translate("sharedcomponents#Transcoding"), session.TranscodingInfo && session.TranscodingInfo.Framerate && (html += " (" + session.TranscodingInfo.Framerate + " fps)"), showTranscodingInfo = !0, !0) : "DirectPlay" == displayPlayMethod && (html += globalize.translate("sharedcomponents#DirectPlaying")), showTranscodingInfo) { + var line = []; + session.TranscodingInfo && (session.TranscodingInfo.Bitrate && (session.TranscodingInfo.Bitrate > 1e6 ? line.push((session.TranscodingInfo.Bitrate / 1e6).toFixed(1) + " Mbps") : line.push(Math.floor(session.TranscodingInfo.Bitrate / 1e3) + " kbps")), session.TranscodingInfo.Container && line.push(session.TranscodingInfo.Container), session.TranscodingInfo.VideoCodec && line.push(session.TranscodingInfo.VideoCodec), session.TranscodingInfo.AudioCodec && session.TranscodingInfo.AudioCodec != session.TranscodingInfo.Container && line.push(session.TranscodingInfo.AudioCodec)), line.length && (html += " - " + line.join(" ")) + } + return html || " " + }, + getSessionNowPlayingTime: function(session) { + var nowPlayingItem = session.NowPlayingItem, + html = ""; + return nowPlayingItem ? (session.PlayState.PositionTicks ? html += datetime.getDisplayRunningTime(session.PlayState.PositionTicks) : html += "--:--:--", html += " / ", nowPlayingItem && nowPlayingItem.RunTimeTicks ? html += datetime.getDisplayRunningTime(nowPlayingItem.RunTimeTicks) : html += "--:--:--", html) : html + }, + getAppSecondaryText: function(session) { + return session.Client + " " + session.ApplicationVersion + }, + getNowPlayingName: function(session) { + var imgUrl = "", + nowPlayingItem = session.NowPlayingItem; + if (!nowPlayingItem) return { + html: "Last seen " + humane_date(session.LastActivityDate), + image: imgUrl + }; + var topText = itemHelper.getDisplayName(nowPlayingItem), + bottomText = ""; + return nowPlayingItem.Artists && nowPlayingItem.Artists.length ? (bottomText = topText, topText = nowPlayingItem.Artists[0]) : nowPlayingItem.SeriesName || nowPlayingItem.Album ? (bottomText = topText, topText = nowPlayingItem.SeriesName || nowPlayingItem.Album) : nowPlayingItem.ProductionYear && (bottomText = nowPlayingItem.ProductionYear), nowPlayingItem.ImageTags && nowPlayingItem.ImageTags.Logo ? imgUrl = ApiClient.getScaledImageUrl(nowPlayingItem.Id, { + tag: nowPlayingItem.ImageTags.Logo, + maxHeight: 24, + maxWidth: 130, + type: "Logo" + }) : nowPlayingItem.ParentLogoImageTag && (imgUrl = ApiClient.getScaledImageUrl(nowPlayingItem.ParentLogoItemId, { + tag: nowPlayingItem.ParentLogoImageTag, + maxHeight: 24, + maxWidth: 130, + type: "Logo" + })), imgUrl && (topText = ''), { + html: bottomText ? topText + "
    " + bottomText : topText, + image: imgUrl + } + }, + getUsersHtml: function(session) { + var html = []; + session.UserId && html.push(session.UserName); + for (var i = 0, length = session.AdditionalUsers.length; i < length; i++) html.push(session.AdditionalUsers[i].UserName); + return html.join(", ") + }, + getUserImage: function(session) { + return session.UserId && session.UserPrimaryImageTag ? ApiClient.getUserImageUrl(session.UserId, { + tag: session.UserPrimaryImageTag, + height: 24, + type: "Primary" + }) : null + }, + updateSession: function(row, session) { + row.classList.remove("deadSession"); + var nowPlayingItem = session.NowPlayingItem; + nowPlayingItem ? row.classList.add("playingSession") : row.classList.remove("playingSession"), session.ServerId && -1 !== session.SupportedCommands.indexOf("DisplayMessage") && session.DeviceId !== connectionManager.deviceId() ? row.querySelector(".btnSessionSendMessage").classList.remove("hide") : row.querySelector(".btnSessionSendMessage").classList.add("hide"), session.TranscodingInfo && session.TranscodingInfo.TranscodeReasons && session.TranscodingInfo && session.TranscodingInfo.TranscodeReasons.length ? row.querySelector(".btnSessionInfo").classList.remove("hide") : row.querySelector(".btnSessionInfo").classList.add("hide"); + var btnSessionPlayPause = row.querySelector(".btnSessionPlayPause"); + session.ServerId && nowPlayingItem && session.SupportsRemoteControl && session.DeviceId !== connectionManager.deviceId() ? (btnSessionPlayPause.classList.remove("hide"), row.querySelector(".btnSessionStop").classList.remove("hide")) : (btnSessionPlayPause.classList.add("hide"), row.querySelector(".btnSessionStop").classList.add("hide")), session.PlayState && session.PlayState.IsPaused ? btnSessionPlayPause.querySelector("i").innerHTML = "" : btnSessionPlayPause.querySelector("i").innerHTML = "", row.querySelector(".sessionNowPlayingStreamInfo").innerHTML = DashboardPage.getSessionNowPlayingStreamInfo(session), row.querySelector(".sessionNowPlayingTime").innerHTML = DashboardPage.getSessionNowPlayingTime(session), row.querySelector(".sessionUserName").innerHTML = DashboardPage.getUsersHtml(session) || " ", row.querySelector(".sessionAppSecondaryText").innerHTML = DashboardPage.getAppSecondaryText(session), row.querySelector(".sessionTranscodingFramerate").innerHTML = session.TranscodingInfo && session.TranscodingInfo.Framerate ? session.TranscodingInfo.Framerate + " fps" : ""; + var nowPlayingName = DashboardPage.getNowPlayingName(session), + nowPlayingInfoElem = row.querySelector(".sessionNowPlayingInfo"); + nowPlayingName.image && nowPlayingName.image == nowPlayingInfoElem.getAttribute("data-imgsrc") || (nowPlayingInfoElem.innerHTML = nowPlayingName.html, nowPlayingInfoElem.setAttribute("data-imgsrc", nowPlayingName.image || "")); + var playbackProgressElem = row.querySelector(".playbackProgress"); + if (playbackProgressElem) + if (nowPlayingItem && nowPlayingItem.RunTimeTicks) { + var position = session.PlayState.PositionTicks || 0, + value = 100 * position / nowPlayingItem.RunTimeTicks; + playbackProgressElem.classList.remove("hide"), playbackProgressElem.value = value + } else playbackProgressElem.classList.add("hide"); + var transcodingProgress = row.querySelector(".transcodingProgress"); + session.TranscodingInfo && session.TranscodingInfo.CompletionPercentage ? (row.classList.add("transcodingSession"), transcodingProgress.value = session.TranscodingInfo.CompletionPercentage, transcodingProgress.classList.remove("hide")) : (transcodingProgress.classList.add("hide"), row.classList.remove("transcodingSession")); + var imgUrl = DashboardPage.getNowPlayingImageUrl(nowPlayingItem) || "", + imgElem = row.querySelector(".sessionNowPlayingContent"); + imgUrl != imgElem.getAttribute("data-src") && (imgElem.style.backgroundImage = imgUrl ? "url('" + imgUrl + "')" : "", imgElem.setAttribute("data-src", imgUrl), imgUrl ? imgElem.classList.add("sessionNowPlayingContent-withbackground") : imgElem.classList.remove("sessionNowPlayingContent-withbackground")) + }, + getClientImage: function(connection) { + var iconUrl = (connection.Client.toLowerCase(), connection.DeviceName.toLowerCase(), connection.AppIconUrl); + return iconUrl ? (-1 === iconUrl.indexOf("://") && (iconUrl = ApiClient.getUrl(iconUrl)), "") : null + }, + getNowPlayingImageUrl: function(item) { + if (item && item.BackdropImageTags && item.BackdropImageTags.length) return ApiClient.getScaledImageUrl(item.Id, { + type: "Backdrop", + width: 275, + tag: item.BackdropImageTags[0] + }); + if (item && item.ParentBackdropImageTags && item.ParentBackdropImageTags.length) return ApiClient.getScaledImageUrl(item.ParentBackdropItemId, { + type: "Backdrop", + width: 275, + tag: item.ParentBackdropImageTags[0] + }); + if (item && item.BackdropImageTag) return ApiClient.getScaledImageUrl(item.BackdropItemId, { + type: "Backdrop", + width: 275, + tag: item.BackdropImageTag + }); + var imageTags = (item || {}).ImageTags || {}; + return item && imageTags.Thumb ? ApiClient.getScaledImageUrl(item.Id, { + type: "Thumb", + width: 275, + tag: imageTags.Thumb + }) : item && item.ParentThumbImageTag ? ApiClient.getScaledImageUrl(item.ParentThumbItemId, { + type: "Thumb", + width: 275, + tag: item.ParentThumbImageTag + }) : item && item.ThumbImageTag ? ApiClient.getScaledImageUrl(item.ThumbItemId, { + type: "Thumb", + width: 275, + tag: item.ThumbImageTag + }) : item && imageTags.Primary ? ApiClient.getScaledImageUrl(item.Id, { + type: "Primary", + width: 275, + tag: imageTags.Primary + }) : item && item.PrimaryImageTag ? ApiClient.getScaledImageUrl(item.PrimaryImageItemId, { + type: "Primary", + width: 275, + tag: item.PrimaryImageTag + }) : null + }, + systemUpdateTaskKey: "SystemUpdateTask", + renderUrls: function(page, systemInfo) { + var helpButton = '' + globalize.translate("ButtonHelp") + "", + localUrlElem = page.querySelector(".localUrl"), + externalUrlElem = page.querySelector(".externalUrl"); + if (systemInfo.LocalAddress) { + var localAccessHtml = globalize.translate("LabelLocalAccessUrl", '' + systemInfo.LocalAddress + ""); + localUrlElem.innerHTML = localAccessHtml + helpButton, localUrlElem.classList.remove("hide") + } else localUrlElem.classList.add("hide"); + if (systemInfo.WanAddress) { + var externalUrl = systemInfo.WanAddress, + remoteAccessHtml = globalize.translate("LabelRemoteAccessUrl", '' + externalUrl + ""); + externalUrlElem.innerHTML = remoteAccessHtml + helpButton, externalUrlElem.classList.remove("hide") + } else externalUrlElem.classList.add("hide") + }, + renderSupporterIcon: function(page, pluginSecurityInfo) { + var imgUrl, text, supporterIconContainer = page.querySelector(".supporterIconContainer"); + pluginSecurityInfo.IsMBSupporter ? (supporterIconContainer.classList.remove("hide"), imgUrl = "css/images/supporter/supporterbadge.png", text = globalize.translate("MessageThankYouForSupporting"), supporterIconContainer.innerHTML = '') : supporterIconContainer.classList.add("hide") + }, + renderPendingInstallations: function(page, systemInfo) { + if (!systemInfo.CompletedInstallations.length) return void page.querySelector("#collapsiblePendingInstallations").classList.add("hide"); + page.querySelector("#collapsiblePendingInstallations").classList.remove("hide"); + for (var html = "", i = 0, length = systemInfo.CompletedInstallations.length; i < length; i++) { + var update = systemInfo.CompletedInstallations[i]; + html += "
    " + update.Name + " (" + update.Version + ")
    " + } + page.querySelector("#pendingInstallations").innerHTML = html + }, + renderPluginUpdateInfo: function(page, forceUpdate) { + !forceUpdate && DashboardPage.lastPluginUpdateCheck && (new Date).getTime() - DashboardPage.lastPluginUpdateCheck < 18e5 || (DashboardPage.lastPluginUpdateCheck = (new Date).getTime(), ApiClient.getAvailablePluginUpdates().then(function(updates) { + var elem = page.querySelector("#pPluginUpdates"); + if (!updates.length) return void elem.classList.add("hide"); + elem.classList.remove("hide"); + for (var html = "", i = 0, length = updates.length; i < length; i++) { + var update = updates[i]; + html += "

    " + globalize.translate("NewVersionOfSomethingAvailable").replace("{0}", update.name) + "

    ", html += '" + } + elem.innerHTML = html + })) + }, + installPluginUpdate: function(button) { + buttonEnabled(button, !1); + var name = button.getAttribute("data-name"), + guid = button.getAttribute("data-guid"), + version = button.getAttribute("data-version"), + classification = button.getAttribute("data-classification"); + loading.show(), ApiClient.installPlugin(name, guid, classification, version).then(function() { + loading.hide() + }) + }, + updateApplication: function(btn) { + var page = dom.parentWithClass(btn, "page"); + buttonEnabled(page.querySelector("#btnUpdateApplication"), !1), loading.show(), ApiClient.getScheduledTasks().then(function(tasks) { + var task = tasks.filter(function(t) { + return t.Key == DashboardPage.systemUpdateTaskKey + })[0]; + ApiClient.startScheduledTask(task.Id).then(function() { + pollForInfo(page, ApiClient), loading.hide() + }) + }) + }, + stopTask: function(btn, id) { + var page = dom.parentWithClass(btn, "page"); + ApiClient.stopScheduledTask(id).then(function() { + pollForInfo(page, ApiClient) + }) + }, + restart: function(btn) { + require(["confirm"], function(confirm) { + confirm({ + title: globalize.translate("HeaderRestart"), + text: globalize.translate("MessageConfirmRestart"), + confirmText: globalize.translate("ButtonRestart"), + primary: "cancel" + }).then(function() { + var page = dom.parentWithClass(btn, "page"); + buttonEnabled(page.querySelector("#btnRestartServer"), !1), buttonEnabled(page.querySelector("#btnShutdown"), !1), Dashboard.restartServer() + }) + }) + }, + shutdown: function(btn) { + require(["confirm"], function(confirm) { + confirm({ + title: globalize.translate("HeaderShutdown"), + text: globalize.translate("MessageConfirmShutdown"), + confirmText: globalize.translate("ButtonShutdown"), + primary: "cancel" + }).then(function() { + var page = dom.parentWithClass(btn, "page"); + buttonEnabled(page.querySelector("#btnRestartServer"), !1), buttonEnabled(page.querySelector("#btnShutdown"), !1), ApiClient.shutdownServer() + }) + }) + } + }, pageClassOn("pageshow", "type-interior", function() { + var page = this; + page.querySelector(".customSupporterPromotion") || getPluginSecurityInfo().then(function(pluginSecurityInfo) { + var supporterPromotionElem = page.querySelector(".supporterPromotion"); + if (supporterPromotionElem && supporterPromotionElem.parentNode.removeChild(supporterPromotionElem), !pluginSecurityInfo.IsMBSupporter) { + var html = '", page.querySelector(".content-primary").insertAdjacentHTML("afterbegin", html) + } + }) + }), + function(view, params) { + function onRestartRequired(e, apiClient) { + apiClient.serverId() === serverId && renderHasPendingRestart(view, apiClient, !0) + } + + function onServerShuttingDown(e, apiClient) { + apiClient.serverId() === serverId && renderHasPendingRestart(view, apiClient, !0) + } + + function onServerRestarting(e, apiClient) { + apiClient.serverId() === serverId && renderHasPendingRestart(view, apiClient, !0) + } + + function onPackageInstalling(e, apiClient) { + apiClient.serverId() === serverId && (pollForInfo(view, apiClient, !0), reloadSystemInfo(view, apiClient)) + } + + function onPackageInstallationCompleted(e, apiClient) { + apiClient.serverId() === serverId && (pollForInfo(view, apiClient, !0), reloadSystemInfo(view, apiClient)) + } + + function onSessionsUpdate(e, apiClient, info) { + apiClient.serverId() === serverId && renderInfo(view, info) + } + + function onScheduledTasksUpdate(e, apiClient, info) { + apiClient.serverId() === serverId && renderRunningTasks(view, info) + } + var serverId = ApiClient.serverId(); + view.querySelector(".btnConnectionHelp").addEventListener("click", onConnectionHelpClick), view.querySelector(".btnEditServerName").addEventListener("click", onEditServerNameClick), view.querySelector(".activeDevices").addEventListener("click", onActiveDevicesClick), view.addEventListener("viewshow", function() { + var page = this, + apiClient = ApiClient; + if (apiClient) { + DashboardPage.newsStartIndex = 0, loading.show(), pollForInfo(page, apiClient), DashboardPage.startInterval(apiClient), events.on(serverNotifications, "RestartRequired", onRestartRequired), events.on(serverNotifications, "ServerShuttingDown", onServerShuttingDown), events.on(serverNotifications, "ServerRestarting", onServerRestarting), events.on(serverNotifications, "PackageInstalling", onPackageInstalling), events.on(serverNotifications, "PackageInstallationCompleted", onPackageInstallationCompleted), events.on(serverNotifications, "Sessions", onSessionsUpdate), + events.on(serverNotifications, "ScheduledTasksInfo", onScheduledTasksUpdate), DashboardPage.lastAppUpdateCheck = null, DashboardPage.lastPluginUpdateCheck = null, getPluginSecurityInfo().then(function(pluginSecurityInfo) { + DashboardPage.renderSupporterIcon(page, pluginSecurityInfo) + }), reloadSystemInfo(page, ApiClient), DashboardPage.reloadNews(page), page.userActivityLog || (page.userActivityLog = new ActivityLog({ + serverId: ApiClient.serverId(), + element: page.querySelector(".userActivityItems") + })), ApiClient.isMinServerVersion("3.4.1.25") && (page.serverActivityLog || (page.serverActivityLog = new ActivityLog({ + serverId: ApiClient.serverId(), + element: page.querySelector(".serverActivityItems") + }))); + var swaggerUrl = "http://swagger.emby.media?url=" + ApiClient.getUrl("openapi"); + swaggerUrl = swaggerUrl + "&api_key=" + ApiClient.accessToken(), page.querySelector(".swaggerLink").setAttribute("href", swaggerUrl), refreshActiveRecordings(view, apiClient) + } + }), view.addEventListener("viewbeforehide", function() { + var apiClient = ApiClient; + events.off(serverNotifications, "RestartRequired", onRestartRequired), events.off(serverNotifications, "ServerShuttingDown", onServerShuttingDown), events.off(serverNotifications, "ServerRestarting", onServerRestarting), events.off(serverNotifications, "PackageInstalling", onPackageInstalling), events.off(serverNotifications, "PackageInstallationCompleted", onPackageInstallationCompleted), events.off(serverNotifications, "Sessions", onSessionsUpdate), events.off(serverNotifications, "ScheduledTasksInfo", onScheduledTasksUpdate), apiClient && DashboardPage.stopInterval(apiClient) + }), view.addEventListener("viewdestroy", function() { + var page = this, + userActivityLog = page.userActivityLog; + userActivityLog && userActivityLog.destroy(); + var serverActivityLog = page.serverActivityLog; + serverActivityLog && serverActivityLog.destroy() + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/dlnaprofile.js b/dashboard-ui/scripts/dlnaprofile.js index ebed2be541..f9d72a3540 100644 --- a/dashboard-ui/scripts/dlnaprofile.js +++ b/dashboard-ui/scripts/dlnaprofile.js @@ -1 +1,371 @@ -define(["jQuery","loading","fnchecked","emby-select","emby-button","emby-input","emby-checkbox","listViewStyle","emby-linkbutton"],function($,loading){"use strict";function loadProfile(page){loading.show();var promise1=getProfile(),promise2=ApiClient.getUsers();Promise.all([promise1,promise2]).then(function(responses){currentProfile=responses[0],renderProfile(page,currentProfile,responses[1]),loading.hide()})}function getProfile(){var id=getParameterByName("id"),url=id?"Dlna/Profiles/"+id:"Dlna/Profiles/Default";return ApiClient.getJSON(ApiClient.getUrl(url))}function renderProfile(page,profile,users){$("#txtName",page).val(profile.Name),$(".chkMediaType",page).each(function(){this.checked=-1!=(profile.SupportedMediaTypes||"").split(",").indexOf(this.getAttribute("data-value"))}),$("#chkEnableAlbumArtInDidl",page).checked(profile.EnableAlbumArtInDidl),$("#chkEnableSingleImageLimit",page).checked(profile.EnableSingleAlbumArtLimit),renderXmlDocumentAttributes(page,profile.XmlRootAttributes||[]);var idInfo=profile.Identification||{};renderIdentificationHeaders(page,idInfo.Headers||[]),renderSubtitleProfiles(page,profile.SubtitleProfiles||[]),$("#txtInfoFriendlyName",page).val(profile.FriendlyName||""),$("#txtInfoModelName",page).val(profile.ModelName||""),$("#txtInfoModelNumber",page).val(profile.ModelNumber||""),$("#txtInfoModelDescription",page).val(profile.ModelDescription||""),$("#txtInfoModelUrl",page).val(profile.ModelUrl||""),$("#txtInfoManufacturer",page).val(profile.Manufacturer||""),$("#txtInfoManufacturerUrl",page).val(profile.ManufacturerUrl||""),$("#txtInfoSerialNumber",page).val(profile.SerialNumber||""),$("#txtIdFriendlyName",page).val(idInfo.FriendlyName||""),$("#txtIdModelName",page).val(idInfo.ModelName||""),$("#txtIdModelNumber",page).val(idInfo.ModelNumber||""),$("#txtIdModelDescription",page).val(idInfo.ModelDescription||""),$("#txtIdModelUrl",page).val(idInfo.ModelUrl||""),$("#txtIdManufacturer",page).val(idInfo.Manufacturer||""),$("#txtIdManufacturerUrl",page).val(idInfo.ManufacturerUrl||""),$("#txtIdSerialNumber",page).val(idInfo.SerialNumber||""),$("#txtIdDeviceDescription",page).val(idInfo.DeviceDescription||""),$("#txtAlbumArtPn",page).val(profile.AlbumArtPn||""),$("#txtAlbumArtMaxWidth",page).val(profile.MaxAlbumArtWidth||""),$("#txtAlbumArtMaxHeight",page).val(profile.MaxAlbumArtHeight||""),$("#txtIconMaxWidth",page).val(profile.MaxIconWidth||""),$("#txtIconMaxHeight",page).val(profile.MaxIconHeight||""),$("#chkIgnoreTranscodeByteRangeRequests",page).checked(profile.IgnoreTranscodeByteRangeRequests),$("#txtMaxAllowedBitrate",page).val(profile.MaxStreamingBitrate||""),$("#txtMusicStreamingTranscodingBitrate",page).val(profile.MusicStreamingTranscodingBitrate||""),$("#chkRequiresPlainFolders",page).checked(profile.RequiresPlainFolders),$("#chkRequiresPlainVideoItems",page).checked(profile.RequiresPlainVideoItems),$("#txtProtocolInfo",page).val(profile.ProtocolInfo||""),$("#txtXDlnaCap",page).val(profile.XDlnaCap||""),$("#txtXDlnaDoc",page).val(profile.XDlnaDoc||""),$("#txtSonyAggregationFlags",page).val(profile.SonyAggregationFlags||""),profile.DirectPlayProfiles=profile.DirectPlayProfiles||[],profile.TranscodingProfiles=profile.TranscodingProfiles||[],profile.ContainerProfiles=profile.ContainerProfiles||[],profile.CodecProfiles=profile.CodecProfiles||[],profile.ResponseProfiles=profile.ResponseProfiles||[];var usersHtml=""+users.map(function(u){return'"}).join("");$("#selectUser",page).html(usersHtml).val(profile.UserId||""),renderSubProfiles(page,profile)}function renderIdentificationHeaders(page,headers){var index=0,html='
    '+headers.map(function(h){var li='
    ';return li+='info',li+='
    ',li+='

    '+h.Name+": "+(h.Value||"")+"

    ",li+='
    '+(h.Match||"")+"
    ",li+="
    ",li+='',li+="
    ",index++,li}).join("")+"
    ",elem=$(".httpHeaderIdentificationList",page).html(html).trigger("create");$(".btnDeleteIdentificationHeader",elem).on("click",function(){var itemIndex=parseInt(this.getAttribute("data-index"));currentProfile.Identification.Headers.splice(itemIndex,1),renderIdentificationHeaders(page,currentProfile.Identification.Headers)})}function openPopup(elem){elem.classList.remove("hide")}function closePopup(elem){elem.classList.add("hide")}function editIdentificationHeader(page,header){isSubProfileNew=null==header,header=header||{},currentSubProfile=header;var popup=$("#identificationHeaderPopup",page);$("#txtIdentificationHeaderName",popup).val(header.Name||""),$("#txtIdentificationHeaderValue",popup).val(header.Value||""),$("#selectMatchType",popup).val(header.Match||"Equals"),openPopup(popup[0])}function saveIdentificationHeader(page){currentSubProfile.Name=$("#txtIdentificationHeaderName",page).val(),currentSubProfile.Value=$("#txtIdentificationHeaderValue",page).val(),currentSubProfile.Match=$("#selectMatchType",page).val(),isSubProfileNew&&(currentProfile.Identification=currentProfile.Identification||{},currentProfile.Identification.Headers=currentProfile.Identification.Headers||[],currentProfile.Identification.Headers.push(currentSubProfile)),renderIdentificationHeaders(page,currentProfile.Identification.Headers),currentSubProfile=null,closePopup($("#identificationHeaderPopup",page)[0])}function renderXmlDocumentAttributes(page,attribute){var html='
    '+attribute.map(function(h){var li='
    ';return li+='info',li+='
    ',li+='

    '+h.Name+" = "+(h.Value||"")+"

    ",li+="
    ",li+='',li+="
    "}).join("")+"
    ",elem=$(".xmlDocumentAttributeList",page).html(html).trigger("create");$(".btnDeleteXmlAttribute",elem).on("click",function(){var itemIndex=parseInt(this.getAttribute("data-index"));currentProfile.XmlRootAttributes.splice(itemIndex,1),renderXmlDocumentAttributes(page,currentProfile.XmlRootAttributes)})}function editXmlDocumentAttribute(page,attribute){isSubProfileNew=null==attribute,attribute=attribute||{},currentSubProfile=attribute;var popup=$("#xmlAttributePopup",page);$("#txtXmlAttributeName",popup).val(attribute.Name||""),$("#txtXmlAttributeValue",popup).val(attribute.Value||""),openPopup(popup[0])}function saveXmlDocumentAttribute(page){currentSubProfile.Name=$("#txtXmlAttributeName",page).val(),currentSubProfile.Value=$("#txtXmlAttributeValue",page).val(),isSubProfileNew&¤tProfile.XmlRootAttributes.push(currentSubProfile),renderXmlDocumentAttributes(page,currentProfile.XmlRootAttributes),currentSubProfile=null,closePopup($("#xmlAttributePopup",page)[0])}function renderSubtitleProfiles(page,profiles){var index=0,html='
    '+profiles.map(function(h){var li='
    ';return li+='info',li+='
    ',li+='

    '+(h.Format||"")+"

    ",li+="
    ",li+='',li+="
    ",index++,li}).join("")+"
    ",elem=$(".subtitleProfileList",page).html(html).trigger("create");$(".btnDeleteProfile",elem).on("click",function(){var itemIndex=parseInt(this.getAttribute("data-index"));currentProfile.SubtitleProfiles.splice(itemIndex,1),renderSubtitleProfiles(page,currentProfile.SubtitleProfiles)}),$(".lnkEditSubProfile",elem).on("click",function(){var itemIndex=parseInt(this.getAttribute("data-index"));editSubtitleProfile(page,currentProfile.SubtitleProfiles[itemIndex])})}function editSubtitleProfile(page,profile){isSubProfileNew=null==profile,profile=profile||{},currentSubProfile=profile;var popup=$("#subtitleProfilePopup",page);$("#txtSubtitleProfileFormat",popup).val(profile.Format||""),$("#selectSubtitleProfileMethod",popup).val(profile.Method||""),$("#selectSubtitleProfileDidlMode",popup).val(profile.DidlMode||""),openPopup(popup[0])}function saveSubtitleProfile(page){currentSubProfile.Format=$("#txtSubtitleProfileFormat",page).val(),currentSubProfile.Method=$("#selectSubtitleProfileMethod",page).val(),currentSubProfile.DidlMode=$("#selectSubtitleProfileDidlMode",page).val(),isSubProfileNew&¤tProfile.SubtitleProfiles.push(currentSubProfile),renderSubtitleProfiles(page,currentProfile.SubtitleProfiles),currentSubProfile=null,closePopup($("#subtitleProfilePopup",page)[0])}function renderSubProfiles(page,profile){renderDirectPlayProfiles(page,profile.DirectPlayProfiles),renderTranscodingProfiles(page,profile.TranscodingProfiles),renderContainerProfiles(page,profile.ContainerProfiles),renderCodecProfiles(page,profile.CodecProfiles),renderResponseProfiles(page,profile.ResponseProfiles)}function saveDirectPlayProfile(page){currentSubProfile.Type=$("#selectDirectPlayProfileType",page).val(),currentSubProfile.Container=$("#txtDirectPlayContainer",page).val(),currentSubProfile.AudioCodec=$("#txtDirectPlayAudioCodec",page).val(),currentSubProfile.VideoCodec=$("#txtDirectPlayVideoCodec",page).val(),isSubProfileNew&¤tProfile.DirectPlayProfiles.push(currentSubProfile),renderSubProfiles(page,currentProfile),currentSubProfile=null,closePopup($("#popupEditDirectPlayProfile",page)[0])}function renderDirectPlayProfiles(page,profiles){var html="";html+='";var elem=$(".directPlayProfiles",page).html(html).trigger("create");$(".btnDeleteProfile",elem).on("click",function(){var index=this.getAttribute("data-profileindex");deleteDirectPlayProfile(page,index)}),$(".lnkEditSubProfile",elem).on("click",function(){var index=parseInt(this.getAttribute("data-profileindex"));editDirectPlayProfile(page,currentProfile.DirectPlayProfiles[index])})}function deleteDirectPlayProfile(page,index){currentProfile.DirectPlayProfiles.splice(index,1),renderDirectPlayProfiles(page,currentProfile.DirectPlayProfiles)}function editDirectPlayProfile(page,directPlayProfile){isSubProfileNew=null==directPlayProfile,directPlayProfile=directPlayProfile||{},currentSubProfile=directPlayProfile;var popup=$("#popupEditDirectPlayProfile",page);$("#selectDirectPlayProfileType",popup).val(directPlayProfile.Type||"Video").trigger("change"),$("#txtDirectPlayContainer",popup).val(directPlayProfile.Container||""),$("#txtDirectPlayAudioCodec",popup).val(directPlayProfile.AudioCodec||""),$("#txtDirectPlayVideoCodec",popup).val(directPlayProfile.VideoCodec||""),openPopup(popup[0])}function renderTranscodingProfiles(page,profiles){var html="";html+='";var elem=$(".transcodingProfiles",page).html(html).trigger("create");$(".btnDeleteProfile",elem).on("click",function(){var index=this.getAttribute("data-profileindex");deleteTranscodingProfile(page,index)}),$(".lnkEditSubProfile",elem).on("click",function(){var index=parseInt(this.getAttribute("data-profileindex"));editTranscodingProfile(page,currentProfile.TranscodingProfiles[index])})}function editTranscodingProfile(page,transcodingProfile){isSubProfileNew=null==transcodingProfile,transcodingProfile=transcodingProfile||{},currentSubProfile=transcodingProfile;var popup=$("#transcodingProfilePopup",page);$("#selectTranscodingProfileType",popup).val(transcodingProfile.Type||"Video").trigger("change"),$("#txtTranscodingContainer",popup).val(transcodingProfile.Container||""),$("#txtTranscodingAudioCodec",popup).val(transcodingProfile.AudioCodec||""),$("#txtTranscodingVideoCodec",popup).val(transcodingProfile.VideoCodec||""),$("#selectTranscodingProtocol",popup).val(transcodingProfile.Protocol||"Http"),$("#chkEnableMpegtsM2TsMode",popup).checked(transcodingProfile.EnableMpegtsM2TsMode||!1),$("#chkEstimateContentLength",popup).checked(transcodingProfile.EstimateContentLength||!1),$("#chkReportByteRangeRequests",popup).checked("Bytes"==transcodingProfile.TranscodeSeekInfo),$(".radioTabButton:first",popup).trigger("click"),openPopup(popup[0])}function deleteTranscodingProfile(page,index){currentProfile.TranscodingProfiles.splice(index,1),renderTranscodingProfiles(page,currentProfile.TranscodingProfiles)}function saveTranscodingProfile(page){currentSubProfile.Type=$("#selectTranscodingProfileType",page).val(),currentSubProfile.Container=$("#txtTranscodingContainer",page).val(),currentSubProfile.AudioCodec=$("#txtTranscodingAudioCodec",page).val(),currentSubProfile.VideoCodec=$("#txtTranscodingVideoCodec",page).val(),currentSubProfile.Protocol=$("#selectTranscodingProtocol",page).val(),currentSubProfile.Context="Streaming",currentSubProfile.EnableMpegtsM2TsMode=$("#chkEnableMpegtsM2TsMode",page).checked(),currentSubProfile.EstimateContentLength=$("#chkEstimateContentLength",page).checked(),currentSubProfile.TranscodeSeekInfo=$("#chkReportByteRangeRequests",page).checked()?"Bytes":"Auto",isSubProfileNew&¤tProfile.TranscodingProfiles.push(currentSubProfile),renderSubProfiles(page,currentProfile),currentSubProfile=null,closePopup($("#transcodingProfilePopup",page)[0])}function renderContainerProfiles(page,profiles){var html="";html+='";var elem=$(".containerProfiles",page).html(html).trigger("create");$(".btnDeleteProfile",elem).on("click",function(){var index=this.getAttribute("data-profileindex");deleteContainerProfile(page,index)}),$(".lnkEditSubProfile",elem).on("click",function(){var index=parseInt(this.getAttribute("data-profileindex"));editContainerProfile(page,currentProfile.ContainerProfiles[index])})}function deleteContainerProfile(page,index){currentProfile.ContainerProfiles.splice(index,1),renderContainerProfiles(page,currentProfile.ContainerProfiles)}function editContainerProfile(page,containerProfile){isSubProfileNew=null==containerProfile,containerProfile=containerProfile||{},currentSubProfile=containerProfile;var popup=$("#containerProfilePopup",page);$("#selectContainerProfileType",popup).val(containerProfile.Type||"Video").trigger("change"),$("#txtContainerProfileContainer",popup).val(containerProfile.Container||""),$(".radioTabButton:first",popup).trigger("click"),openPopup(popup[0])}function saveContainerProfile(page){currentSubProfile.Type=$("#selectContainerProfileType",page).val(),currentSubProfile.Container=$("#txtContainerProfileContainer",page).val(),isSubProfileNew&¤tProfile.ContainerProfiles.push(currentSubProfile),renderSubProfiles(page,currentProfile),currentSubProfile=null,closePopup($("#containerProfilePopup",page)[0])}function renderCodecProfiles(page,profiles){var html="";html+='";var elem=$(".codecProfiles",page).html(html).trigger("create");$(".btnDeleteProfile",elem).on("click",function(){var index=this.getAttribute("data-profileindex");deleteCodecProfile(page,index)}),$(".lnkEditSubProfile",elem).on("click",function(){var index=parseInt(this.getAttribute("data-profileindex"));editCodecProfile(page,currentProfile.CodecProfiles[index])})}function deleteCodecProfile(page,index){currentProfile.CodecProfiles.splice(index,1),renderCodecProfiles(page,currentProfile.CodecProfiles)}function editCodecProfile(page,codecProfile){isSubProfileNew=null==codecProfile,codecProfile=codecProfile||{},currentSubProfile=codecProfile;var popup=$("#codecProfilePopup",page);$("#selectCodecProfileType",popup).val(codecProfile.Type||"Video").trigger("change"),$("#txtCodecProfileCodec",popup).val(codecProfile.Codec||""),$(".radioTabButton:first",popup).trigger("click"),openPopup(popup[0])}function saveCodecProfile(page){currentSubProfile.Type=$("#selectCodecProfileType",page).val(),currentSubProfile.Codec=$("#txtCodecProfileCodec",page).val(),isSubProfileNew&¤tProfile.CodecProfiles.push(currentSubProfile),renderSubProfiles(page,currentProfile),currentSubProfile=null,closePopup($("#codecProfilePopup",page)[0])}function renderResponseProfiles(page,profiles){var html="";html+='";var elem=$(".mediaProfiles",page).html(html).trigger("create");$(".btnDeleteProfile",elem).on("click",function(){var index=this.getAttribute("data-profileindex");deleteResponseProfile(page,index)}),$(".lnkEditSubProfile",elem).on("click",function(){var index=parseInt(this.getAttribute("data-profileindex"));editResponseProfile(page,currentProfile.ResponseProfiles[index])})}function deleteResponseProfile(page,index){currentProfile.ResponseProfiles.splice(index,1),renderResponseProfiles(page,currentProfile.ResponseProfiles)}function editResponseProfile(page,responseProfile){isSubProfileNew=null==responseProfile,responseProfile=responseProfile||{},currentSubProfile=responseProfile;var popup=$("#responseProfilePopup",page);$("#selectResponseProfileType",popup).val(responseProfile.Type||"Video").trigger("change"),$("#txtResponseProfileContainer",popup).val(responseProfile.Container||""),$("#txtResponseProfileAudioCodec",popup).val(responseProfile.AudioCodec||""),$("#txtResponseProfileVideoCodec",popup).val(responseProfile.VideoCodec||""),$(".radioTabButton:first",popup).trigger("click"),openPopup(popup[0])}function saveResponseProfile(page){currentSubProfile.Type=$("#selectResponseProfileType",page).val(),currentSubProfile.Container=$("#txtResponseProfileContainer",page).val(),currentSubProfile.AudioCodec=$("#txtResponseProfileAudioCodec",page).val(),currentSubProfile.VideoCodec=$("#txtResponseProfileVideoCodec",page).val(),isSubProfileNew&¤tProfile.ResponseProfiles.push(currentSubProfile),renderSubProfiles(page,currentProfile),currentSubProfile=null,closePopup($("#responseProfilePopup",page)[0])}function saveProfile(page,profile){updateProfile(page,profile);var id=getParameterByName("id");id?ApiClient.ajax({type:"POST",url:ApiClient.getUrl("Dlna/Profiles/"+id),data:JSON.stringify(profile),contentType:"application/json"}).then(function(){require(["toast"],function(toast){toast("Settings saved.")})},Dashboard.processErrorResponse):ApiClient.ajax({type:"POST",url:ApiClient.getUrl("Dlna/Profiles"),data:JSON.stringify(profile),contentType:"application/json"}).then(function(){Dashboard.navigate("dlnaprofiles.html")},Dashboard.processErrorResponse),loading.hide()}function updateProfile(page,profile){profile.Name=$("#txtName",page).val(),profile.EnableAlbumArtInDidl=$("#chkEnableAlbumArtInDidl",page).checked(),profile.EnableSingleAlbumArtLimit=$("#chkEnableSingleImageLimit",page).checked(),profile.SupportedMediaTypes=$(".chkMediaType:checked",page).get().map(function(c){return c.getAttribute("data-value")}).join(","),profile.Identification=profile.Identification||{},profile.FriendlyName=$("#txtInfoFriendlyName",page).val(),profile.ModelName=$("#txtInfoModelName",page).val(),profile.ModelNumber=$("#txtInfoModelNumber",page).val(),profile.ModelDescription=$("#txtInfoModelDescription",page).val(),profile.ModelUrl=$("#txtInfoModelUrl",page).val(),profile.Manufacturer=$("#txtInfoManufacturer",page).val(),profile.ManufacturerUrl=$("#txtInfoManufacturerUrl",page).val(),profile.SerialNumber=$("#txtInfoSerialNumber",page).val(),profile.Identification.FriendlyName=$("#txtIdFriendlyName",page).val(),profile.Identification.ModelName=$("#txtIdModelName",page).val(),profile.Identification.ModelNumber=$("#txtIdModelNumber",page).val(),profile.Identification.ModelDescription=$("#txtIdModelDescription",page).val(),profile.Identification.ModelUrl=$("#txtIdModelUrl",page).val(),profile.Identification.Manufacturer=$("#txtIdManufacturer",page).val(),profile.Identification.ManufacturerUrl=$("#txtIdManufacturerUrl",page).val(),profile.Identification.SerialNumber=$("#txtIdSerialNumber",page).val(),profile.Identification.DeviceDescription=$("#txtIdDeviceDescription",page).val(),profile.AlbumArtPn=$("#txtAlbumArtPn",page).val(),profile.MaxAlbumArtWidth=$("#txtAlbumArtMaxWidth",page).val(),profile.MaxAlbumArtHeight=$("#txtAlbumArtMaxHeight",page).val(),profile.MaxIconWidth=$("#txtIconMaxWidth",page).val(),profile.MaxIconHeight=$("#txtIconMaxHeight",page).val(),profile.RequiresPlainFolders=$("#chkRequiresPlainFolders",page).checked(),profile.RequiresPlainVideoItems=$("#chkRequiresPlainVideoItems",page).checked(),profile.IgnoreTranscodeByteRangeRequests=$("#chkIgnoreTranscodeByteRangeRequests",page).checked(),profile.MaxStreamingBitrate=$("#txtMaxAllowedBitrate",page).val(),profile.MusicStreamingTranscodingBitrate=$("#txtMusicStreamingTranscodingBitrate",page).val(),profile.ProtocolInfo=$("#txtProtocolInfo",page).val(),profile.XDlnaCap=$("#txtXDlnaCap",page).val(),profile.XDlnaDoc=$("#txtXDlnaDoc",page).val(),profile.SonyAggregationFlags=$("#txtSonyAggregationFlags",page).val(),profile.UserId=$("#selectUser",page).val()}var currentProfile,currentSubProfile,isSubProfileNew,allText=Globalize.translate("LabelAll");$(document).on("pageinit","#dlnaProfilePage",function(){var page=this;$(".radioTabButton",page).on("click",function(){$(this).siblings().removeClass("ui-btn-active"),$(this).addClass("ui-btn-active");var value="A"==this.tagName?this.getAttribute("data-value"):this.value,elem=$("."+value,page);elem.siblings(".tabContent").hide(),elem.show()}),$("#selectDirectPlayProfileType",page).on("change",function(){"Video"==this.value?$("#fldDirectPlayVideoCodec",page).show():$("#fldDirectPlayVideoCodec",page).hide(),"Photo"==this.value?$("#fldDirectPlayAudioCodec",page).hide():$("#fldDirectPlayAudioCodec",page).show()}),$("#selectTranscodingProfileType",page).on("change",function(){"Video"==this.value?($("#fldTranscodingVideoCodec",page).show(),$("#fldTranscodingProtocol",page).show(),$("#fldEnableMpegtsM2TsMode",page).show()):($("#fldTranscodingVideoCodec",page).hide(),$("#fldTranscodingProtocol",page).hide(),$("#fldEnableMpegtsM2TsMode",page).hide()),"Photo"==this.value?($("#fldTranscodingAudioCodec",page).hide(),$("#fldEstimateContentLength",page).hide(),$("#fldReportByteRangeRequests",page).hide()):($("#fldTranscodingAudioCodec",page).show(),$("#fldEstimateContentLength",page).show(),$("#fldReportByteRangeRequests",page).show())}),$("#selectResponseProfileType",page).on("change",function(){"Video"==this.value?$("#fldResponseProfileVideoCodec",page).show():$("#fldResponseProfileVideoCodec",page).hide(),"Photo"==this.value?$("#fldResponseProfileAudioCodec",page).hide():$("#fldResponseProfileAudioCodec",page).show()}),$(".btnAddDirectPlayProfile",page).on("click",function(){editDirectPlayProfile(page)}),$(".btnAddTranscodingProfile",page).on("click",function(){editTranscodingProfile(page)}),$(".btnAddContainerProfile",page).on("click",function(){editContainerProfile(page)}),$(".btnAddCodecProfile",page).on("click",function(){editCodecProfile(page)}),$(".btnAddResponseProfile",page).on("click",function(){editResponseProfile(page)}),$(".btnAddIdentificationHttpHeader",page).on("click",function(){editIdentificationHeader(page)}),$(".btnAddXmlDocumentAttribute",page).on("click",function(){editXmlDocumentAttribute(page)}),$(".btnAddSubtitleProfile",page).on("click",function(){editSubtitleProfile(page)}),$(".dlnaProfileForm").off("submit",DlnaProfilePage.onSubmit).on("submit",DlnaProfilePage.onSubmit),$(".editDirectPlayProfileForm").off("submit",DlnaProfilePage.onDirectPlayFormSubmit).on("submit",DlnaProfilePage.onDirectPlayFormSubmit),$(".transcodingProfileForm").off("submit",DlnaProfilePage.onTranscodingProfileFormSubmit).on("submit",DlnaProfilePage.onTranscodingProfileFormSubmit),$(".containerProfileForm").off("submit",DlnaProfilePage.onContainerProfileFormSubmit).on("submit",DlnaProfilePage.onContainerProfileFormSubmit),$(".codecProfileForm").off("submit",DlnaProfilePage.onCodecProfileFormSubmit).on("submit",DlnaProfilePage.onCodecProfileFormSubmit),$(".editResponseProfileForm").off("submit",DlnaProfilePage.onResponseProfileFormSubmit).on("submit",DlnaProfilePage.onResponseProfileFormSubmit),$(".identificationHeaderForm").off("submit",DlnaProfilePage.onIdentificationHeaderFormSubmit).on("submit",DlnaProfilePage.onIdentificationHeaderFormSubmit),$(".xmlAttributeForm").off("submit",DlnaProfilePage.onXmlAttributeFormSubmit).on("submit",DlnaProfilePage.onXmlAttributeFormSubmit),$(".subtitleProfileForm").off("submit",DlnaProfilePage.onSubtitleProfileFormSubmit).on("submit",DlnaProfilePage.onSubtitleProfileFormSubmit)}).on("pageshow","#dlnaProfilePage",function(){var page=this;$("#radioInfo",page).trigger("click"),loadProfile(page)}),window.DlnaProfilePage={onSubmit:function(){return loading.show(),saveProfile($(this).parents(".page"),currentProfile),!1},onDirectPlayFormSubmit:function(){return saveDirectPlayProfile($(this).parents(".page")),!1},onTranscodingProfileFormSubmit:function(){return saveTranscodingProfile($(this).parents(".page")),!1},onContainerProfileFormSubmit:function(){return saveContainerProfile($(this).parents(".page")),!1},onCodecProfileFormSubmit:function(){return saveCodecProfile($(this).parents(".page")),!1},onResponseProfileFormSubmit:function(){return saveResponseProfile($(this).parents(".page")),!1},onIdentificationHeaderFormSubmit:function(){return saveIdentificationHeader($(this).parents(".page")),!1},onXmlAttributeFormSubmit:function(){return saveXmlDocumentAttribute($(this).parents(".page")),!1},onSubtitleProfileFormSubmit:function(){return saveSubtitleProfile($(this).parents(".page")),!1}}}); \ No newline at end of file +define(["jQuery", "loading", "fnchecked", "emby-select", "emby-button", "emby-input", "emby-checkbox", "listViewStyle", "emby-linkbutton"], function($, loading) { + "use strict"; + + function loadProfile(page) { + loading.show(); + var promise1 = getProfile(), + promise2 = ApiClient.getUsers(); + Promise.all([promise1, promise2]).then(function(responses) { + currentProfile = responses[0], renderProfile(page, currentProfile, responses[1]), loading.hide() + }) + } + + function getProfile() { + var id = getParameterByName("id"), + url = id ? "Dlna/Profiles/" + id : "Dlna/Profiles/Default"; + return ApiClient.getJSON(ApiClient.getUrl(url)) + } + + function renderProfile(page, profile, users) { + $("#txtName", page).val(profile.Name), $(".chkMediaType", page).each(function() { + this.checked = -1 != (profile.SupportedMediaTypes || "").split(",").indexOf(this.getAttribute("data-value")) + }), $("#chkEnableAlbumArtInDidl", page).checked(profile.EnableAlbumArtInDidl), $("#chkEnableSingleImageLimit", page).checked(profile.EnableSingleAlbumArtLimit), renderXmlDocumentAttributes(page, profile.XmlRootAttributes || []); + var idInfo = profile.Identification || {}; + renderIdentificationHeaders(page, idInfo.Headers || []), renderSubtitleProfiles(page, profile.SubtitleProfiles || []), $("#txtInfoFriendlyName", page).val(profile.FriendlyName || ""), $("#txtInfoModelName", page).val(profile.ModelName || ""), $("#txtInfoModelNumber", page).val(profile.ModelNumber || ""), $("#txtInfoModelDescription", page).val(profile.ModelDescription || ""), $("#txtInfoModelUrl", page).val(profile.ModelUrl || ""), $("#txtInfoManufacturer", page).val(profile.Manufacturer || ""), $("#txtInfoManufacturerUrl", page).val(profile.ManufacturerUrl || ""), $("#txtInfoSerialNumber", page).val(profile.SerialNumber || ""), $("#txtIdFriendlyName", page).val(idInfo.FriendlyName || ""), $("#txtIdModelName", page).val(idInfo.ModelName || ""), $("#txtIdModelNumber", page).val(idInfo.ModelNumber || ""), $("#txtIdModelDescription", page).val(idInfo.ModelDescription || ""), $("#txtIdModelUrl", page).val(idInfo.ModelUrl || ""), $("#txtIdManufacturer", page).val(idInfo.Manufacturer || ""), $("#txtIdManufacturerUrl", page).val(idInfo.ManufacturerUrl || ""), $("#txtIdSerialNumber", page).val(idInfo.SerialNumber || ""), $("#txtIdDeviceDescription", page).val(idInfo.DeviceDescription || ""), $("#txtAlbumArtPn", page).val(profile.AlbumArtPn || ""), $("#txtAlbumArtMaxWidth", page).val(profile.MaxAlbumArtWidth || ""), $("#txtAlbumArtMaxHeight", page).val(profile.MaxAlbumArtHeight || ""), $("#txtIconMaxWidth", page).val(profile.MaxIconWidth || ""), $("#txtIconMaxHeight", page).val(profile.MaxIconHeight || ""), $("#chkIgnoreTranscodeByteRangeRequests", page).checked(profile.IgnoreTranscodeByteRangeRequests), $("#txtMaxAllowedBitrate", page).val(profile.MaxStreamingBitrate || ""), $("#txtMusicStreamingTranscodingBitrate", page).val(profile.MusicStreamingTranscodingBitrate || ""), $("#chkRequiresPlainFolders", page).checked(profile.RequiresPlainFolders), $("#chkRequiresPlainVideoItems", page).checked(profile.RequiresPlainVideoItems), $("#txtProtocolInfo", page).val(profile.ProtocolInfo || ""), $("#txtXDlnaCap", page).val(profile.XDlnaCap || ""), $("#txtXDlnaDoc", page).val(profile.XDlnaDoc || ""), $("#txtSonyAggregationFlags", page).val(profile.SonyAggregationFlags || ""), profile.DirectPlayProfiles = profile.DirectPlayProfiles || [], profile.TranscodingProfiles = profile.TranscodingProfiles || [], profile.ContainerProfiles = profile.ContainerProfiles || [], profile.CodecProfiles = profile.CodecProfiles || [], profile.ResponseProfiles = profile.ResponseProfiles || []; + var usersHtml = "" + users.map(function(u) { + return '" + }).join(""); + $("#selectUser", page).html(usersHtml).val(profile.UserId || ""), renderSubProfiles(page, profile) + } + + function renderIdentificationHeaders(page, headers) { + var index = 0, + html = '
    ' + headers.map(function(h) { + var li = '
    '; + return li += 'info', li += '
    ', li += '

    ' + h.Name + ": " + (h.Value || "") + "

    ", li += '
    ' + (h.Match || "") + "
    ", li += "
    ", li += '', li += "
    ", index++, li + }).join("") + "
    ", + elem = $(".httpHeaderIdentificationList", page).html(html).trigger("create"); + $(".btnDeleteIdentificationHeader", elem).on("click", function() { + var itemIndex = parseInt(this.getAttribute("data-index")); + currentProfile.Identification.Headers.splice(itemIndex, 1), renderIdentificationHeaders(page, currentProfile.Identification.Headers) + }) + } + + function openPopup(elem) { + elem.classList.remove("hide") + } + + function closePopup(elem) { + elem.classList.add("hide") + } + + function editIdentificationHeader(page, header) { + isSubProfileNew = null == header, header = header || {}, currentSubProfile = header; + var popup = $("#identificationHeaderPopup", page); + $("#txtIdentificationHeaderName", popup).val(header.Name || ""), $("#txtIdentificationHeaderValue", popup).val(header.Value || ""), $("#selectMatchType", popup).val(header.Match || "Equals"), openPopup(popup[0]) + } + + function saveIdentificationHeader(page) { + currentSubProfile.Name = $("#txtIdentificationHeaderName", page).val(), currentSubProfile.Value = $("#txtIdentificationHeaderValue", page).val(), currentSubProfile.Match = $("#selectMatchType", page).val(), isSubProfileNew && (currentProfile.Identification = currentProfile.Identification || {}, currentProfile.Identification.Headers = currentProfile.Identification.Headers || [], currentProfile.Identification.Headers.push(currentSubProfile)), renderIdentificationHeaders(page, currentProfile.Identification.Headers), currentSubProfile = null, closePopup($("#identificationHeaderPopup", page)[0]) + } + + function renderXmlDocumentAttributes(page, attribute) { + var html = '
    ' + attribute.map(function(h) { + var li = '
    '; + return li += 'info', li += '
    ', li += '

    ' + h.Name + " = " + (h.Value || "") + "

    ", li += "
    ", li += '', li += "
    " + }).join("") + "
    ", + elem = $(".xmlDocumentAttributeList", page).html(html).trigger("create"); + $(".btnDeleteXmlAttribute", elem).on("click", function() { + var itemIndex = parseInt(this.getAttribute("data-index")); + currentProfile.XmlRootAttributes.splice(itemIndex, 1), renderXmlDocumentAttributes(page, currentProfile.XmlRootAttributes) + }) + } + + function editXmlDocumentAttribute(page, attribute) { + isSubProfileNew = null == attribute, attribute = attribute || {}, currentSubProfile = attribute; + var popup = $("#xmlAttributePopup", page); + $("#txtXmlAttributeName", popup).val(attribute.Name || ""), $("#txtXmlAttributeValue", popup).val(attribute.Value || ""), openPopup(popup[0]) + } + + function saveXmlDocumentAttribute(page) { + currentSubProfile.Name = $("#txtXmlAttributeName", page).val(), currentSubProfile.Value = $("#txtXmlAttributeValue", page).val(), isSubProfileNew && currentProfile.XmlRootAttributes.push(currentSubProfile), renderXmlDocumentAttributes(page, currentProfile.XmlRootAttributes), currentSubProfile = null, closePopup($("#xmlAttributePopup", page)[0]) + } + + function renderSubtitleProfiles(page, profiles) { + var index = 0, + html = '
    ' + profiles.map(function(h) { + var li = '
    '; + return li += 'info', li += '
    ', li += '

    ' + (h.Format || "") + "

    ", li += "
    ", li += '', li += "
    ", index++, li + }).join("") + "
    ", + elem = $(".subtitleProfileList", page).html(html).trigger("create"); + $(".btnDeleteProfile", elem).on("click", function() { + var itemIndex = parseInt(this.getAttribute("data-index")); + currentProfile.SubtitleProfiles.splice(itemIndex, 1), renderSubtitleProfiles(page, currentProfile.SubtitleProfiles) + }), $(".lnkEditSubProfile", elem).on("click", function() { + var itemIndex = parseInt(this.getAttribute("data-index")); + editSubtitleProfile(page, currentProfile.SubtitleProfiles[itemIndex]) + }) + } + + function editSubtitleProfile(page, profile) { + isSubProfileNew = null == profile, profile = profile || {}, currentSubProfile = profile; + var popup = $("#subtitleProfilePopup", page); + $("#txtSubtitleProfileFormat", popup).val(profile.Format || ""), $("#selectSubtitleProfileMethod", popup).val(profile.Method || ""), $("#selectSubtitleProfileDidlMode", popup).val(profile.DidlMode || ""), openPopup(popup[0]) + } + + function saveSubtitleProfile(page) { + currentSubProfile.Format = $("#txtSubtitleProfileFormat", page).val(), currentSubProfile.Method = $("#selectSubtitleProfileMethod", page).val(), currentSubProfile.DidlMode = $("#selectSubtitleProfileDidlMode", page).val(), isSubProfileNew && currentProfile.SubtitleProfiles.push(currentSubProfile), renderSubtitleProfiles(page, currentProfile.SubtitleProfiles), currentSubProfile = null, closePopup($("#subtitleProfilePopup", page)[0]) + } + + function renderSubProfiles(page, profile) { + renderDirectPlayProfiles(page, profile.DirectPlayProfiles), renderTranscodingProfiles(page, profile.TranscodingProfiles), renderContainerProfiles(page, profile.ContainerProfiles), renderCodecProfiles(page, profile.CodecProfiles), renderResponseProfiles(page, profile.ResponseProfiles) + } + + function saveDirectPlayProfile(page) { + currentSubProfile.Type = $("#selectDirectPlayProfileType", page).val(), currentSubProfile.Container = $("#txtDirectPlayContainer", page).val(), currentSubProfile.AudioCodec = $("#txtDirectPlayAudioCodec", page).val(), currentSubProfile.VideoCodec = $("#txtDirectPlayVideoCodec", page).val(), isSubProfileNew && currentProfile.DirectPlayProfiles.push(currentSubProfile), renderSubProfiles(page, currentProfile), currentSubProfile = null, closePopup($("#popupEditDirectPlayProfile", page)[0]) + } + + function renderDirectPlayProfiles(page, profiles) { + var html = ""; + html += '"; + var elem = $(".directPlayProfiles", page).html(html).trigger("create"); + $(".btnDeleteProfile", elem).on("click", function() { + var index = this.getAttribute("data-profileindex"); + deleteDirectPlayProfile(page, index) + }), $(".lnkEditSubProfile", elem).on("click", function() { + var index = parseInt(this.getAttribute("data-profileindex")); + editDirectPlayProfile(page, currentProfile.DirectPlayProfiles[index]) + }) + } + + function deleteDirectPlayProfile(page, index) { + currentProfile.DirectPlayProfiles.splice(index, 1), renderDirectPlayProfiles(page, currentProfile.DirectPlayProfiles) + } + + function editDirectPlayProfile(page, directPlayProfile) { + isSubProfileNew = null == directPlayProfile, directPlayProfile = directPlayProfile || {}, currentSubProfile = directPlayProfile; + var popup = $("#popupEditDirectPlayProfile", page); + $("#selectDirectPlayProfileType", popup).val(directPlayProfile.Type || "Video").trigger("change"), $("#txtDirectPlayContainer", popup).val(directPlayProfile.Container || ""), $("#txtDirectPlayAudioCodec", popup).val(directPlayProfile.AudioCodec || ""), $("#txtDirectPlayVideoCodec", popup).val(directPlayProfile.VideoCodec || ""), openPopup(popup[0]) + } + + function renderTranscodingProfiles(page, profiles) { + var html = ""; + html += '"; + var elem = $(".transcodingProfiles", page).html(html).trigger("create"); + $(".btnDeleteProfile", elem).on("click", function() { + var index = this.getAttribute("data-profileindex"); + deleteTranscodingProfile(page, index) + }), $(".lnkEditSubProfile", elem).on("click", function() { + var index = parseInt(this.getAttribute("data-profileindex")); + editTranscodingProfile(page, currentProfile.TranscodingProfiles[index]) + }) + } + + function editTranscodingProfile(page, transcodingProfile) { + isSubProfileNew = null == transcodingProfile, transcodingProfile = transcodingProfile || {}, currentSubProfile = transcodingProfile; + var popup = $("#transcodingProfilePopup", page); + $("#selectTranscodingProfileType", popup).val(transcodingProfile.Type || "Video").trigger("change"), $("#txtTranscodingContainer", popup).val(transcodingProfile.Container || ""), $("#txtTranscodingAudioCodec", popup).val(transcodingProfile.AudioCodec || ""), $("#txtTranscodingVideoCodec", popup).val(transcodingProfile.VideoCodec || ""), $("#selectTranscodingProtocol", popup).val(transcodingProfile.Protocol || "Http"), $("#chkEnableMpegtsM2TsMode", popup).checked(transcodingProfile.EnableMpegtsM2TsMode || !1), $("#chkEstimateContentLength", popup).checked(transcodingProfile.EstimateContentLength || !1), $("#chkReportByteRangeRequests", popup).checked("Bytes" == transcodingProfile.TranscodeSeekInfo), $(".radioTabButton:first", popup).trigger("click"), openPopup(popup[0]) + } + + function deleteTranscodingProfile(page, index) { + currentProfile.TranscodingProfiles.splice(index, 1), renderTranscodingProfiles(page, currentProfile.TranscodingProfiles) + } + + function saveTranscodingProfile(page) { + currentSubProfile.Type = $("#selectTranscodingProfileType", page).val(), currentSubProfile.Container = $("#txtTranscodingContainer", page).val(), currentSubProfile.AudioCodec = $("#txtTranscodingAudioCodec", page).val(), currentSubProfile.VideoCodec = $("#txtTranscodingVideoCodec", page).val(), currentSubProfile.Protocol = $("#selectTranscodingProtocol", page).val(), currentSubProfile.Context = "Streaming", currentSubProfile.EnableMpegtsM2TsMode = $("#chkEnableMpegtsM2TsMode", page).checked(), currentSubProfile.EstimateContentLength = $("#chkEstimateContentLength", page).checked(), currentSubProfile.TranscodeSeekInfo = $("#chkReportByteRangeRequests", page).checked() ? "Bytes" : "Auto", isSubProfileNew && currentProfile.TranscodingProfiles.push(currentSubProfile), renderSubProfiles(page, currentProfile), currentSubProfile = null, closePopup($("#transcodingProfilePopup", page)[0]) + } + + function renderContainerProfiles(page, profiles) { + var html = ""; + html += '"; + var elem = $(".containerProfiles", page).html(html).trigger("create"); + $(".btnDeleteProfile", elem).on("click", function() { + var index = this.getAttribute("data-profileindex"); + deleteContainerProfile(page, index) + }), $(".lnkEditSubProfile", elem).on("click", function() { + var index = parseInt(this.getAttribute("data-profileindex")); + editContainerProfile(page, currentProfile.ContainerProfiles[index]) + }) + } + + function deleteContainerProfile(page, index) { + currentProfile.ContainerProfiles.splice(index, 1), renderContainerProfiles(page, currentProfile.ContainerProfiles) + } + + function editContainerProfile(page, containerProfile) { + isSubProfileNew = null == containerProfile, containerProfile = containerProfile || {}, currentSubProfile = containerProfile; + var popup = $("#containerProfilePopup", page); + $("#selectContainerProfileType", popup).val(containerProfile.Type || "Video").trigger("change"), $("#txtContainerProfileContainer", popup).val(containerProfile.Container || ""), $(".radioTabButton:first", popup).trigger("click"), openPopup(popup[0]) + } + + function saveContainerProfile(page) { + currentSubProfile.Type = $("#selectContainerProfileType", page).val(), currentSubProfile.Container = $("#txtContainerProfileContainer", page).val(), isSubProfileNew && currentProfile.ContainerProfiles.push(currentSubProfile), renderSubProfiles(page, currentProfile), currentSubProfile = null, closePopup($("#containerProfilePopup", page)[0]) + } + + function renderCodecProfiles(page, profiles) { + var html = ""; + html += '"; + var elem = $(".codecProfiles", page).html(html).trigger("create"); + $(".btnDeleteProfile", elem).on("click", function() { + var index = this.getAttribute("data-profileindex"); + deleteCodecProfile(page, index) + }), $(".lnkEditSubProfile", elem).on("click", function() { + var index = parseInt(this.getAttribute("data-profileindex")); + editCodecProfile(page, currentProfile.CodecProfiles[index]) + }) + } + + function deleteCodecProfile(page, index) { + currentProfile.CodecProfiles.splice(index, 1), renderCodecProfiles(page, currentProfile.CodecProfiles) + } + + function editCodecProfile(page, codecProfile) { + isSubProfileNew = null == codecProfile, codecProfile = codecProfile || {}, currentSubProfile = codecProfile; + var popup = $("#codecProfilePopup", page); + $("#selectCodecProfileType", popup).val(codecProfile.Type || "Video").trigger("change"), $("#txtCodecProfileCodec", popup).val(codecProfile.Codec || ""), $(".radioTabButton:first", popup).trigger("click"), openPopup(popup[0]) + } + + function saveCodecProfile(page) { + currentSubProfile.Type = $("#selectCodecProfileType", page).val(), currentSubProfile.Codec = $("#txtCodecProfileCodec", page).val(), isSubProfileNew && currentProfile.CodecProfiles.push(currentSubProfile), renderSubProfiles(page, currentProfile), currentSubProfile = null, closePopup($("#codecProfilePopup", page)[0]) + } + + function renderResponseProfiles(page, profiles) { + var html = ""; + html += '"; + var elem = $(".mediaProfiles", page).html(html).trigger("create"); + $(".btnDeleteProfile", elem).on("click", function() { + var index = this.getAttribute("data-profileindex"); + deleteResponseProfile(page, index) + }), $(".lnkEditSubProfile", elem).on("click", function() { + var index = parseInt(this.getAttribute("data-profileindex")); + editResponseProfile(page, currentProfile.ResponseProfiles[index]) + }) + } + + function deleteResponseProfile(page, index) { + currentProfile.ResponseProfiles.splice(index, 1), renderResponseProfiles(page, currentProfile.ResponseProfiles) + } + + function editResponseProfile(page, responseProfile) { + isSubProfileNew = null == responseProfile, responseProfile = responseProfile || {}, currentSubProfile = responseProfile; + var popup = $("#responseProfilePopup", page); + $("#selectResponseProfileType", popup).val(responseProfile.Type || "Video").trigger("change"), $("#txtResponseProfileContainer", popup).val(responseProfile.Container || ""), $("#txtResponseProfileAudioCodec", popup).val(responseProfile.AudioCodec || ""), $("#txtResponseProfileVideoCodec", popup).val(responseProfile.VideoCodec || ""), $(".radioTabButton:first", popup).trigger("click"), openPopup(popup[0]) + } + + function saveResponseProfile(page) { + currentSubProfile.Type = $("#selectResponseProfileType", page).val(), currentSubProfile.Container = $("#txtResponseProfileContainer", page).val(), currentSubProfile.AudioCodec = $("#txtResponseProfileAudioCodec", page).val(), currentSubProfile.VideoCodec = $("#txtResponseProfileVideoCodec", page).val(), isSubProfileNew && currentProfile.ResponseProfiles.push(currentSubProfile), renderSubProfiles(page, currentProfile), currentSubProfile = null, closePopup($("#responseProfilePopup", page)[0]) + } + + function saveProfile(page, profile) { + updateProfile(page, profile); + var id = getParameterByName("id"); + id ? ApiClient.ajax({ + type: "POST", + url: ApiClient.getUrl("Dlna/Profiles/" + id), + data: JSON.stringify(profile), + contentType: "application/json" + }).then(function() { + require(["toast"], function(toast) { + toast("Settings saved.") + }) + }, Dashboard.processErrorResponse) : ApiClient.ajax({ + type: "POST", + url: ApiClient.getUrl("Dlna/Profiles"), + data: JSON.stringify(profile), + contentType: "application/json" + }).then(function() { + Dashboard.navigate("dlnaprofiles.html") + }, Dashboard.processErrorResponse), loading.hide() + } + + function updateProfile(page, profile) { + profile.Name = $("#txtName", page).val(), profile.EnableAlbumArtInDidl = $("#chkEnableAlbumArtInDidl", page).checked(), profile.EnableSingleAlbumArtLimit = $("#chkEnableSingleImageLimit", page).checked(), profile.SupportedMediaTypes = $(".chkMediaType:checked", page).get().map(function(c) { + return c.getAttribute("data-value") + }).join(","), profile.Identification = profile.Identification || {}, profile.FriendlyName = $("#txtInfoFriendlyName", page).val(), profile.ModelName = $("#txtInfoModelName", page).val(), profile.ModelNumber = $("#txtInfoModelNumber", page).val(), profile.ModelDescription = $("#txtInfoModelDescription", page).val(), profile.ModelUrl = $("#txtInfoModelUrl", page).val(), profile.Manufacturer = $("#txtInfoManufacturer", page).val(), profile.ManufacturerUrl = $("#txtInfoManufacturerUrl", page).val(), profile.SerialNumber = $("#txtInfoSerialNumber", page).val(), profile.Identification.FriendlyName = $("#txtIdFriendlyName", page).val(), profile.Identification.ModelName = $("#txtIdModelName", page).val(), profile.Identification.ModelNumber = $("#txtIdModelNumber", page).val(), profile.Identification.ModelDescription = $("#txtIdModelDescription", page).val(), profile.Identification.ModelUrl = $("#txtIdModelUrl", page).val(), profile.Identification.Manufacturer = $("#txtIdManufacturer", page).val(), profile.Identification.ManufacturerUrl = $("#txtIdManufacturerUrl", page).val(), profile.Identification.SerialNumber = $("#txtIdSerialNumber", page).val(), profile.Identification.DeviceDescription = $("#txtIdDeviceDescription", page).val(), profile.AlbumArtPn = $("#txtAlbumArtPn", page).val(), profile.MaxAlbumArtWidth = $("#txtAlbumArtMaxWidth", page).val(), profile.MaxAlbumArtHeight = $("#txtAlbumArtMaxHeight", page).val(), profile.MaxIconWidth = $("#txtIconMaxWidth", page).val(), profile.MaxIconHeight = $("#txtIconMaxHeight", page).val(), profile.RequiresPlainFolders = $("#chkRequiresPlainFolders", page).checked(), profile.RequiresPlainVideoItems = $("#chkRequiresPlainVideoItems", page).checked(), profile.IgnoreTranscodeByteRangeRequests = $("#chkIgnoreTranscodeByteRangeRequests", page).checked(), profile.MaxStreamingBitrate = $("#txtMaxAllowedBitrate", page).val(), profile.MusicStreamingTranscodingBitrate = $("#txtMusicStreamingTranscodingBitrate", page).val(), profile.ProtocolInfo = $("#txtProtocolInfo", page).val(), profile.XDlnaCap = $("#txtXDlnaCap", page).val(), profile.XDlnaDoc = $("#txtXDlnaDoc", page).val(), profile.SonyAggregationFlags = $("#txtSonyAggregationFlags", page).val(), profile.UserId = $("#selectUser", page).val() + } + var currentProfile, currentSubProfile, isSubProfileNew, allText = Globalize.translate("LabelAll"); + $(document).on("pageinit", "#dlnaProfilePage", function() { + var page = this; + $(".radioTabButton", page).on("click", function() { + $(this).siblings().removeClass("ui-btn-active"), $(this).addClass("ui-btn-active"); + var value = "A" == this.tagName ? this.getAttribute("data-value") : this.value, + elem = $("." + value, page); + elem.siblings(".tabContent").hide(), elem.show() + }), $("#selectDirectPlayProfileType", page).on("change", function() { + "Video" == this.value ? $("#fldDirectPlayVideoCodec", page).show() : $("#fldDirectPlayVideoCodec", page).hide(), "Photo" == this.value ? $("#fldDirectPlayAudioCodec", page).hide() : $("#fldDirectPlayAudioCodec", page).show() + }), $("#selectTranscodingProfileType", page).on("change", function() { + "Video" == this.value ? ($("#fldTranscodingVideoCodec", page).show(), $("#fldTranscodingProtocol", page).show(), $("#fldEnableMpegtsM2TsMode", page).show()) : ($("#fldTranscodingVideoCodec", page).hide(), $("#fldTranscodingProtocol", page).hide(), $("#fldEnableMpegtsM2TsMode", page).hide()), "Photo" == this.value ? ($("#fldTranscodingAudioCodec", page).hide(), $("#fldEstimateContentLength", page).hide(), $("#fldReportByteRangeRequests", page).hide()) : ($("#fldTranscodingAudioCodec", page).show(), $("#fldEstimateContentLength", page).show(), $("#fldReportByteRangeRequests", page).show()) + }), $("#selectResponseProfileType", page).on("change", function() { + "Video" == this.value ? $("#fldResponseProfileVideoCodec", page).show() : $("#fldResponseProfileVideoCodec", page).hide(), "Photo" == this.value ? $("#fldResponseProfileAudioCodec", page).hide() : $("#fldResponseProfileAudioCodec", page).show() + }), $(".btnAddDirectPlayProfile", page).on("click", function() { + editDirectPlayProfile(page) + }), $(".btnAddTranscodingProfile", page).on("click", function() { + editTranscodingProfile(page) + }), $(".btnAddContainerProfile", page).on("click", function() { + editContainerProfile(page) + }), $(".btnAddCodecProfile", page).on("click", function() { + editCodecProfile(page) + }), $(".btnAddResponseProfile", page).on("click", function() { + editResponseProfile(page) + }), $(".btnAddIdentificationHttpHeader", page).on("click", function() { + editIdentificationHeader(page) + }), $(".btnAddXmlDocumentAttribute", page).on("click", function() { + editXmlDocumentAttribute(page) + }), $(".btnAddSubtitleProfile", page).on("click", function() { + editSubtitleProfile(page) + }), $(".dlnaProfileForm").off("submit", DlnaProfilePage.onSubmit).on("submit", DlnaProfilePage.onSubmit), $(".editDirectPlayProfileForm").off("submit", DlnaProfilePage.onDirectPlayFormSubmit).on("submit", DlnaProfilePage.onDirectPlayFormSubmit), $(".transcodingProfileForm").off("submit", DlnaProfilePage.onTranscodingProfileFormSubmit).on("submit", DlnaProfilePage.onTranscodingProfileFormSubmit), $(".containerProfileForm").off("submit", DlnaProfilePage.onContainerProfileFormSubmit).on("submit", DlnaProfilePage.onContainerProfileFormSubmit), $(".codecProfileForm").off("submit", DlnaProfilePage.onCodecProfileFormSubmit).on("submit", DlnaProfilePage.onCodecProfileFormSubmit), $(".editResponseProfileForm").off("submit", DlnaProfilePage.onResponseProfileFormSubmit).on("submit", DlnaProfilePage.onResponseProfileFormSubmit), $(".identificationHeaderForm").off("submit", DlnaProfilePage.onIdentificationHeaderFormSubmit).on("submit", DlnaProfilePage.onIdentificationHeaderFormSubmit), $(".xmlAttributeForm").off("submit", DlnaProfilePage.onXmlAttributeFormSubmit).on("submit", DlnaProfilePage.onXmlAttributeFormSubmit), $(".subtitleProfileForm").off("submit", DlnaProfilePage.onSubtitleProfileFormSubmit).on("submit", DlnaProfilePage.onSubtitleProfileFormSubmit) + }).on("pageshow", "#dlnaProfilePage", function() { + var page = this; + $("#radioInfo", page).trigger("click"), loadProfile(page) + }), window.DlnaProfilePage = { + onSubmit: function() { + return loading.show(), saveProfile($(this).parents(".page"), currentProfile), !1 + }, + onDirectPlayFormSubmit: function() { + return saveDirectPlayProfile($(this).parents(".page")), !1 + }, + onTranscodingProfileFormSubmit: function() { + return saveTranscodingProfile($(this).parents(".page")), !1 + }, + onContainerProfileFormSubmit: function() { + return saveContainerProfile($(this).parents(".page")), !1 + }, + onCodecProfileFormSubmit: function() { + return saveCodecProfile($(this).parents(".page")), !1 + }, + onResponseProfileFormSubmit: function() { + return saveResponseProfile($(this).parents(".page")), !1 + }, + onIdentificationHeaderFormSubmit: function() { + return saveIdentificationHeader($(this).parents(".page")), !1 + }, + onXmlAttributeFormSubmit: function() { + return saveXmlDocumentAttribute($(this).parents(".page")), !1 + }, + onSubtitleProfileFormSubmit: function() { + return saveSubtitleProfile($(this).parents(".page")), !1 + } + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/dlnaprofiles.js b/dashboard-ui/scripts/dlnaprofiles.js index 439b61f073..1f0fd1e791 100644 --- a/dashboard-ui/scripts/dlnaprofiles.js +++ b/dashboard-ui/scripts/dlnaprofiles.js @@ -1 +1,60 @@ -define(["jQuery","globalize","loading","libraryMenu","listViewStyle","emby-linkbutton"],function($,globalize,loading,libraryMenu){"use strict";function loadProfiles(page){loading.show(),ApiClient.getJSON(ApiClient.getUrl("Dlna/ProfileInfos")).then(function(result){renderUserProfiles(page,result),renderSystemProfiles(page,result),loading.hide()})}function renderUserProfiles(page,profiles){renderProfiles(page,page.querySelector(".customProfiles"),profiles.filter(function(p){return"User"==p.Type}))}function renderSystemProfiles(page,profiles){renderProfiles(page,page.querySelector(".systemProfiles"),profiles.filter(function(p){return"System"==p.Type}))}function renderProfiles(page,element,profiles){var html="";profiles.length&&(html+='
    ');for(var i=0,length=profiles.length;i',html+='live_tv',html+='","User"==profile.Type&&(html+=''),html+="
    "}profiles.length&&(html+=""),element.innerHTML=html,$(".btnDeleteProfile",element).on("click",function(){var id=this.getAttribute("data-profileid");deleteProfile(page,id)})}function deleteProfile(page,id){require(["confirm"],function(confirm){confirm(globalize.translate("MessageConfirmProfileDeletion"),globalize.translate("HeaderConfirmProfileDeletion")).then(function(){loading.show(),ApiClient.ajax({type:"DELETE",url:ApiClient.getUrl("Dlna/Profiles/"+id)}).then(function(){loading.hide(),loadProfiles(page)})})})}function getTabs(){return[{href:"dlnasettings.html",name:globalize.translate("TabSettings")},{href:"dlnaprofiles.html",name:globalize.translate("TabProfiles")}]}$(document).on("pageshow","#dlnaProfilesPage",function(){libraryMenu.setTabs("dlna",1,getTabs),loadProfiles(this)})}); \ No newline at end of file +define(["jQuery", "globalize", "loading", "libraryMenu", "listViewStyle", "emby-linkbutton"], function($, globalize, loading, libraryMenu) { + "use strict"; + + function loadProfiles(page) { + loading.show(), ApiClient.getJSON(ApiClient.getUrl("Dlna/ProfileInfos")).then(function(result) { + renderUserProfiles(page, result), renderSystemProfiles(page, result), loading.hide() + }) + } + + function renderUserProfiles(page, profiles) { + renderProfiles(page, page.querySelector(".customProfiles"), profiles.filter(function(p) { + return "User" == p.Type + })) + } + + function renderSystemProfiles(page, profiles) { + renderProfiles(page, page.querySelector(".systemProfiles"), profiles.filter(function(p) { + return "System" == p.Type + })) + } + + function renderProfiles(page, element, profiles) { + var html = ""; + profiles.length && (html += '
    '); + for (var i = 0, length = profiles.length; i < length; i++) { + var profile = profiles[i]; + html += '
    ', html += 'live_tv', html += '", "User" == profile.Type && (html += ''), html += "
    " + } + profiles.length && (html += "
    "), element.innerHTML = html, $(".btnDeleteProfile", element).on("click", function() { + var id = this.getAttribute("data-profileid"); + deleteProfile(page, id) + }) + } + + function deleteProfile(page, id) { + require(["confirm"], function(confirm) { + confirm(globalize.translate("MessageConfirmProfileDeletion"), globalize.translate("HeaderConfirmProfileDeletion")).then(function() { + loading.show(), ApiClient.ajax({ + type: "DELETE", + url: ApiClient.getUrl("Dlna/Profiles/" + id) + }).then(function() { + loading.hide(), loadProfiles(page) + }) + }) + }) + } + + function getTabs() { + return [{ + href: "dlnasettings.html", + name: globalize.translate("TabSettings") + }, { + href: "dlnaprofiles.html", + name: globalize.translate("TabProfiles") + }] + } + $(document).on("pageshow", "#dlnaProfilesPage", function() { + libraryMenu.setTabs("dlna", 1, getTabs), loadProfiles(this) + }) +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/dlnasettings.js b/dashboard-ui/scripts/dlnasettings.js index d4159f76b8..cc4693096a 100644 --- a/dashboard-ui/scripts/dlnasettings.js +++ b/dashboard-ui/scripts/dlnasettings.js @@ -1 +1,40 @@ -define(["jQuery","loading","libraryMenu","fnchecked"],function($,loading,libraryMenu){"use strict";function loadPage(page,config,users){page.querySelector("#chkEnablePlayTo").checked=config.EnablePlayTo,page.querySelector("#chkEnableDlnaDebugLogging").checked=config.EnableDebugLog,$("#txtClientDiscoveryInterval",page).val(config.ClientDiscoveryIntervalSeconds),$("#chkEnableServer",page).checked(config.EnableServer),$("#chkBlastAliveMessages",page).checked(config.BlastAliveMessages),$("#txtBlastInterval",page).val(config.BlastAliveMessageIntervalSeconds);var usersHtml=users.map(function(u){return'"}).join("");$("#selectUser",page).html(usersHtml).val(config.DefaultUserId||""),loading.hide()}function onSubmit(){loading.show();var form=this;return ApiClient.getNamedConfiguration("dlna").then(function(config){config.EnablePlayTo=form.querySelector("#chkEnablePlayTo").checked,config.EnableDebugLog=form.querySelector("#chkEnableDlnaDebugLogging").checked,config.ClientDiscoveryIntervalSeconds=$("#txtClientDiscoveryInterval",form).val(),config.EnableServer=$("#chkEnableServer",form).checked(),config.BlastAliveMessages=$("#chkBlastAliveMessages",form).checked(),config.BlastAliveMessageIntervalSeconds=$("#txtBlastInterval",form).val(),config.DefaultUserId=$("#selectUser",form).val(),ApiClient.updateNamedConfiguration("dlna",config).then(Dashboard.processServerConfigurationUpdateResult)}),!1}function getTabs(){return[{href:"dlnasettings.html",name:Globalize.translate("TabSettings")},{href:"dlnaprofiles.html",name:Globalize.translate("TabProfiles")}]}$(document).on("pageinit","#dlnaSettingsPage",function(){$(".dlnaSettingsForm").off("submit",onSubmit).on("submit",onSubmit)}).on("pageshow","#dlnaSettingsPage",function(){libraryMenu.setTabs("dlna",0,getTabs),loading.show();var page=this,promise1=ApiClient.getNamedConfiguration("dlna"),promise2=ApiClient.getUsers();Promise.all([promise1,promise2]).then(function(responses){loadPage(page,responses[0],responses[1])})})}); \ No newline at end of file +define(["jQuery", "loading", "libraryMenu", "fnchecked"], function($, loading, libraryMenu) { + "use strict"; + + function loadPage(page, config, users) { + page.querySelector("#chkEnablePlayTo").checked = config.EnablePlayTo, page.querySelector("#chkEnableDlnaDebugLogging").checked = config.EnableDebugLog, $("#txtClientDiscoveryInterval", page).val(config.ClientDiscoveryIntervalSeconds), $("#chkEnableServer", page).checked(config.EnableServer), $("#chkBlastAliveMessages", page).checked(config.BlastAliveMessages), $("#txtBlastInterval", page).val(config.BlastAliveMessageIntervalSeconds); + var usersHtml = users.map(function(u) { + return '" + }).join(""); + $("#selectUser", page).html(usersHtml).val(config.DefaultUserId || ""), loading.hide() + } + + function onSubmit() { + loading.show(); + var form = this; + return ApiClient.getNamedConfiguration("dlna").then(function(config) { + config.EnablePlayTo = form.querySelector("#chkEnablePlayTo").checked, config.EnableDebugLog = form.querySelector("#chkEnableDlnaDebugLogging").checked, config.ClientDiscoveryIntervalSeconds = $("#txtClientDiscoveryInterval", form).val(), config.EnableServer = $("#chkEnableServer", form).checked(), config.BlastAliveMessages = $("#chkBlastAliveMessages", form).checked(), config.BlastAliveMessageIntervalSeconds = $("#txtBlastInterval", form).val(), config.DefaultUserId = $("#selectUser", form).val(), ApiClient.updateNamedConfiguration("dlna", config).then(Dashboard.processServerConfigurationUpdateResult) + }), !1 + } + + function getTabs() { + return [{ + href: "dlnasettings.html", + name: Globalize.translate("TabSettings") + }, { + href: "dlnaprofiles.html", + name: Globalize.translate("TabProfiles") + }] + } + $(document).on("pageinit", "#dlnaSettingsPage", function() { + $(".dlnaSettingsForm").off("submit", onSubmit).on("submit", onSubmit) + }).on("pageshow", "#dlnaSettingsPage", function() { + libraryMenu.setTabs("dlna", 0, getTabs), loading.show(); + var page = this, + promise1 = ApiClient.getNamedConfiguration("dlna"), + promise2 = ApiClient.getUsers(); + Promise.all([promise1, promise2]).then(function(responses) { + loadPage(page, responses[0], responses[1]) + }) + }) +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/edititemmetadata.js b/dashboard-ui/scripts/edititemmetadata.js index 11b1edb0ee..c77c947dae 100644 --- a/dashboard-ui/scripts/edititemmetadata.js +++ b/dashboard-ui/scripts/edititemmetadata.js @@ -1 +1,17 @@ -define(["loading"],function(loading){"use strict";function reload(context,itemId){loading.show(),itemId?require(["metadataEditor"],function(metadataEditor){metadataEditor.embed(context.querySelector(".editPageInnerContent"),itemId,ApiClient.serverInfo().Id)}):(context.querySelector(".editPageInnerContent").innerHTML="",loading.hide())}return function(view,params){view.addEventListener("viewshow",function(){reload(this,MetadataEditor.getCurrentItemId())}),MetadataEditor.setCurrentItemId(null),view.querySelector(".libraryTree").addEventListener("itemclicked",function(event){var data=event.detail;data.id!=MetadataEditor.getCurrentItemId()&&(MetadataEditor.setCurrentItemId(data.id),reload(view,data.id))})}}); \ No newline at end of file +define(["loading"], function(loading) { + "use strict"; + + function reload(context, itemId) { + loading.show(), itemId ? require(["metadataEditor"], function(metadataEditor) { + metadataEditor.embed(context.querySelector(".editPageInnerContent"), itemId, ApiClient.serverInfo().Id) + }) : (context.querySelector(".editPageInnerContent").innerHTML = "", loading.hide()) + } + return function(view, params) { + view.addEventListener("viewshow", function() { + reload(this, MetadataEditor.getCurrentItemId()) + }), MetadataEditor.setCurrentItemId(null), view.querySelector(".libraryTree").addEventListener("itemclicked", function(event) { + var data = event.detail; + data.id != MetadataEditor.getCurrentItemId() && (MetadataEditor.setCurrentItemId(data.id), reload(view, data.id)) + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/editorsidebar.js b/dashboard-ui/scripts/editorsidebar.js index 81e81130ec..672d2e0213 100644 --- a/dashboard-ui/scripts/editorsidebar.js +++ b/dashboard-ui/scripts/editorsidebar.js @@ -1 +1,223 @@ -define(["datetime","jQuery","material-icons"],function(datetime,$){"use strict";function getNode(item,folderState,selected){var htmlName=getNodeInnerHtml(item),node={id:item.Id,text:htmlName,state:{opened:item.IsFolder&&"open"==folderState,selected:selected},li_attr:{serveritemtype:item.Type,collectiontype:item.CollectionType}};return item.IsFolder?(node.children=[{text:"Loading...",icon:!1}],node.icon=!1):node.icon=!1,node.state.opened&&(node.li_attr.loadedFromServer=!0),selected&&(selectedNodeId=item.Id),node}function getNodeInnerHtml(item){var name=item.Name;item.Number&&(name=item.Number+" - "+name),null!=item.IndexNumber&&"Season"!=item.Type&&(name=item.IndexNumber+" - "+name);var htmlName="
    ";return item.LockData&&(htmlName+='lock'),htmlName+=name,htmlName+="
    "}function loadChildrenOfRootNode(page,scope,callback){ApiClient.getLiveTvChannels({limit:0}).then(function(result){var nodes=[];nodes.push({id:"MediaFolders",text:Globalize.translate("HeaderMediaFolders"),state:{opened:!0},li_attr:{itemtype:"mediafolders",loadedFromServer:!0},icon:!1}),result.TotalRecordCount&&nodes.push({id:"livetv",text:Globalize.translate("HeaderLiveTV"),state:{opened:!1},li_attr:{itemtype:"livetv"},children:[{text:"Loading...",icon:!1}],icon:!1}),callback.call(scope,nodes),nodesToLoad.push("MediaFolders")})}function loadLiveTvChannels(openItems,callback){ApiClient.getLiveTvChannels({AddCurrentProgram:!1}).then(function(result){var nodes=result.Items.map(function(i){return getNode(i,-1==openItems.indexOf(i.Id)?"closed":"open",!1)});callback(nodes)})}function loadMediaFolders(page,scope,openItems,callback){ApiClient.getJSON(ApiClient.getUrl("Library/MediaFolders")).then(function(result){var nodes=result.Items.map(function(n){return getNode(n,-1==openItems.indexOf(n.Id)?"closed":"open",!1)});callback.call(scope,nodes);for(var i=0,length=nodes.length;ia",page)[0];if(null!=elem&&($(".editorNode",elem).remove(),$(elem).append(getNodeInnerHtml(item)),item.IsFolder)){var tree=jQuery.jstree._reference(".libraryTree"),currentNode=tree._get_node(null,!1);tree.refresh(currentNode)}}function setCurrentItemId(id){itemId=id}function getCurrentItemId(){if(itemId)return itemId;var url=window.location.hash||window.location.href;return getParameterByName("id",url)}var selectedNodeId,nodesToLoad=[];$(document).on("itemsaved",".metadataEditorPage",function(e,item){updateEditorNode(this,item)}).on("pagebeforeshow",".metadataEditorPage",function(){require(["css!css/metadataeditor.css"])}).on("pagebeforeshow",".metadataEditorPage",function(){var page=this;Dashboard.getCurrentUser().then(function(user){var id=getCurrentItemId();id?ApiClient.getAncestorItems(id,user.Id).then(function(ancestors){var ids=ancestors.map(function(i){return i.Id});initializeTree(page,user,ids,id)}):initializeTree(page,user,[])})}).on("pagebeforehide",".metadataEditorPage",function(){$(".libraryTree",this).off("select_node.jstree",onNodeSelect).off("open_node.jstree",onNodeOpen).off("load_node.jstree",onNodeLoad)});var itemId;window.MetadataEditor={getItemPromise:function(){var currentItemId=getCurrentItemId();return currentItemId?ApiClient.getItem(Dashboard.getCurrentUserId(),currentItemId):ApiClient.getRootFolder(Dashboard.getCurrentUserId())},getCurrentItemId:getCurrentItemId,setCurrentItemId:setCurrentItemId}}); \ No newline at end of file +define(["datetime", "jQuery", "material-icons"], function(datetime, $) { + "use strict"; + + function getNode(item, folderState, selected) { + var htmlName = getNodeInnerHtml(item), + node = { + id: item.Id, + text: htmlName, + state: { + opened: item.IsFolder && "open" == folderState, + selected: selected + }, + li_attr: { + serveritemtype: item.Type, + collectiontype: item.CollectionType + } + }; + return item.IsFolder ? (node.children = [{ + text: "Loading...", + icon: !1 + }], node.icon = !1) : node.icon = !1, node.state.opened && (node.li_attr.loadedFromServer = !0), selected && (selectedNodeId = item.Id), node + } + + function getNodeInnerHtml(item) { + var name = item.Name; + item.Number && (name = item.Number + " - " + name), null != item.IndexNumber && "Season" != item.Type && (name = item.IndexNumber + " - " + name); + var htmlName = "
    "; + return item.LockData && (htmlName += 'lock'), htmlName += name, htmlName += "
    " + } + + function loadChildrenOfRootNode(page, scope, callback) { + ApiClient.getLiveTvChannels({ + limit: 0 + }).then(function(result) { + var nodes = []; + nodes.push({ + id: "MediaFolders", + text: Globalize.translate("HeaderMediaFolders"), + state: { + opened: !0 + }, + li_attr: { + itemtype: "mediafolders", + loadedFromServer: !0 + }, + icon: !1 + }), result.TotalRecordCount && nodes.push({ + id: "livetv", + text: Globalize.translate("HeaderLiveTV"), + state: { + opened: !1 + }, + li_attr: { + itemtype: "livetv" + }, + children: [{ + text: "Loading...", + icon: !1 + }], + icon: !1 + }), callback.call(scope, nodes), nodesToLoad.push("MediaFolders") + }) + } + + function loadLiveTvChannels(openItems, callback) { + ApiClient.getLiveTvChannels({ + AddCurrentProgram: !1 + }).then(function(result) { + var nodes = result.Items.map(function(i) { + return getNode(i, -1 == openItems.indexOf(i.Id) ? "closed" : "open", !1) + }); + callback(nodes) + }) + } + + function loadMediaFolders(page, scope, openItems, callback) { + ApiClient.getJSON(ApiClient.getUrl("Library/MediaFolders")).then(function(result) { + var nodes = result.Items.map(function(n) { + return getNode(n, -1 == openItems.indexOf(n.Id) ? "closed" : "open", !1) + }); + callback.call(scope, nodes); + for (var i = 0, length = nodes.length; i < length; i++) nodes[i].state.opened && nodesToLoad.push(nodes[i].id) + }) + } + + function loadNode(page, scope, node, openItems, selectedId, currentUser, callback) { + var id = node.id; + if ("#" == id) return void loadChildrenOfRootNode(page, scope, callback); + if ("livetv" == id) return void loadLiveTvChannels(openItems, callback); + if ("MediaFolders" == id) return void loadMediaFolders(page, scope, openItems, callback); + var query = { + ParentId: id, + Fields: "Settings", + IsVirtualUnaired: !1, + IsMissing: !1, + EnableTotalRecordCount: !1, + EnableImages: !1, + EnableUserData: !1 + }, + itemtype = node.li_attr.itemtype; + "Season" != itemtype && "Series" != itemtype && (query.SortBy = "SortName"), ApiClient.getItems(Dashboard.getCurrentUserId(), query).then(function(result) { + var nodes = result.Items.map(function(n) { + return getNode(n, -1 == openItems.indexOf(n.Id) ? "closed" : "open", n.Id == selectedId) + }); + callback.call(scope, nodes); + for (var i = 0, length = nodes.length; i < length; i++) nodes[i].state.opened && nodesToLoad.push(nodes[i].id) + }) + } + + function scrollToNode(id) { + var elem = $("#" + id)[0]; + elem && elem.scrollIntoView() + } + + function initializeTree(page, currentUser, openItems, selectedId) { + require(["jstree"], function() { + initializeTreeInternal(page, currentUser, openItems, selectedId) + }) + } + + function onNodeSelect(event, data) { + var node = data.node, + eventData = { + id: node.id, + itemType: node.li_attr.itemtype, + serverItemType: node.li_attr.serveritemtype, + collectionType: node.li_attr.collectiontype + }; + "livetv" != eventData.itemType && "mediafolders" != eventData.itemType ? (this.dispatchEvent(new CustomEvent("itemclicked", { + detail: eventData, + bubbles: !0, + cancelable: !1 + })), document.querySelector(".editPageSidebar").classList.add("editPageSidebar-withcontent")) : document.querySelector(".editPageSidebar").classList.remove("editPageSidebar-withcontent") + } + + function onNodeOpen(event, data) { + var page = $(this).parents(".page")[0], + node = data.node; + node.children && node.children && loadNodesToLoad(page, node), node.li_attr && "#" != node.id && !node.li_attr.loadedFromServer && (node.li_attr.loadedFromServer = !0, $.jstree.reference(".libraryTree", page).load_node(node.id, loadNodeCallback)) + } + + function onNodeLoad(event, data) { + var page = $(this).parents(".page")[0], + node = data.node; + node.children && node.children && loadNodesToLoad(page, node), node.li_attr && "#" != node.id && !node.li_attr.loadedFromServer && (node.li_attr.loadedFromServer = !0, $.jstree.reference(".libraryTree", page).load_node(node.id, loadNodeCallback)) + } + + function initializeTreeInternal(page, currentUser, openItems, selectedId) { + nodesToLoad = [], selectedNodeId = null, $.jstree.destroy(), $(".libraryTree", page).jstree({ + plugins: ["wholerow"], + core: { + check_callback: !0, + data: function(node, callback) { + loadNode(page, this, node, openItems, selectedId, currentUser, callback) + }, + themes: { + variant: "large" + } + } + }).off("select_node.jstree", onNodeSelect).on("select_node.jstree", onNodeSelect).off("open_node.jstree", onNodeOpen).on("open_node.jstree", onNodeOpen).off("load_node.jstree", onNodeLoad).on("load_node.jstree", onNodeLoad) + } + + function loadNodesToLoad(page, node) { + for (var children = node.children, i = 0, length = children.length; i < length; i++) { + var child = children[i]; - 1 != nodesToLoad.indexOf(child) && (nodesToLoad = nodesToLoad.filter(function(n) { + return n != child + }), $.jstree.reference(".libraryTree", page).load_node(child, loadNodeCallback)) + } + } + + function loadNodeCallback(node) { + selectedNodeId && node.children && -1 != node.children.indexOf(selectedNodeId) && setTimeout(function() { + scrollToNode(selectedNodeId) + }, 500) + } + + function updateEditorNode(page, item) { + var elem = $("#" + item.Id + ">a", page)[0]; + if (null != elem && ($(".editorNode", elem).remove(), $(elem).append(getNodeInnerHtml(item)), item.IsFolder)) { + var tree = jQuery.jstree._reference(".libraryTree"), + currentNode = tree._get_node(null, !1); + tree.refresh(currentNode) + } + } + + function setCurrentItemId(id) { + itemId = id + } + + function getCurrentItemId() { + if (itemId) return itemId; + var url = window.location.hash || window.location.href; + return getParameterByName("id", url) + } + var selectedNodeId, nodesToLoad = []; + $(document).on("itemsaved", ".metadataEditorPage", function(e, item) { + updateEditorNode(this, item) + }).on("pagebeforeshow", ".metadataEditorPage", function() { + require(["css!css/metadataeditor.css"]) + }).on("pagebeforeshow", ".metadataEditorPage", function() { + var page = this; + Dashboard.getCurrentUser().then(function(user) { + var id = getCurrentItemId(); + id ? ApiClient.getAncestorItems(id, user.Id).then(function(ancestors) { + var ids = ancestors.map(function(i) { + return i.Id + }); + initializeTree(page, user, ids, id) + }) : initializeTree(page, user, []) + }) + }).on("pagebeforehide", ".metadataEditorPage", function() { + $(".libraryTree", this).off("select_node.jstree", onNodeSelect).off("open_node.jstree", onNodeOpen).off("load_node.jstree", onNodeLoad) + }); + var itemId; + window.MetadataEditor = { + getItemPromise: function() { + var currentItemId = getCurrentItemId(); + return currentItemId ? ApiClient.getItem(Dashboard.getCurrentUserId(), currentItemId) : ApiClient.getRootFolder(Dashboard.getCurrentUserId()) + }, + getCurrentItemId: getCurrentItemId, + setCurrentItemId: setCurrentItemId + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/encodingsettings.js b/dashboard-ui/scripts/encodingsettings.js index b341cba2d1..7a2461a6bb 100644 --- a/dashboard-ui/scripts/encodingsettings.js +++ b/dashboard-ui/scripts/encodingsettings.js @@ -1 +1,97 @@ -define(["jQuery","loading","globalize","dom"],function($,loading,globalize,dom){"use strict";function loadPage(page,config,systemInfo){Array.prototype.forEach.call(page.querySelectorAll(".chkDecodeCodec"),function(c){c.checked=-1!==(config.HardwareDecodingCodecs||[]).indexOf(c.getAttribute("data-codec"))}),page.querySelector("#chkHardwareEncoding").checked=config.EnableHardwareEncoding,$("#selectVideoDecoder",page).val(config.HardwareAccelerationType),$("#selectThreadCount",page).val(config.EncodingThreadCount),$("#txtDownMixAudioBoost",page).val(config.DownMixAudioBoost),page.querySelector(".txtEncoderPath").value=config.EncoderAppPath||"",$("#txtTranscodingTempPath",page).val(config.TranscodingTempPath||""),$("#txtVaapiDevice",page).val(config.VaapiDevice||""),page.querySelector("#selectH264Preset").value=config.H264Preset||"",page.querySelector("#txtH264Crf").value=config.H264Crf||"",page.querySelector("#chkEnableSubtitleExtraction").checked=config.EnableSubtitleExtraction||!1,page.querySelector("#selectVideoDecoder").dispatchEvent(new CustomEvent("change",{bubbles:!0})),loading.hide()}function onSaveEncodingPathFailure(response){loading.hide();var msg="";msg=globalize.translate("FFmpegSavePathNotFound"),require(["alert"],function(alert){alert(msg)})}function updateEncoder(form){return ApiClient.getSystemInfo().then(function(systemInfo){return ApiClient.ajax({url:ApiClient.getUrl("System/MediaEncoder/Path"),type:"POST",data:{Path:form.querySelector(".txtEncoderPath").value,PathType:"Custom"}}).then(Dashboard.processServerConfigurationUpdateResult,onSaveEncodingPathFailure)})}function onSubmit(){var form=this,onDecoderConfirmed=function(){loading.show(),ApiClient.getNamedConfiguration("encoding").then(function(config){config.DownMixAudioBoost=$("#txtDownMixAudioBoost",form).val(),config.TranscodingTempPath=$("#txtTranscodingTempPath",form).val(),config.EncodingThreadCount=$("#selectThreadCount",form).val(),config.HardwareAccelerationType=$("#selectVideoDecoder",form).val(),config.VaapiDevice=$("#txtVaapiDevice",form).val(),config.H264Preset=form.querySelector("#selectH264Preset").value,config.H264Crf=parseInt(form.querySelector("#txtH264Crf").value||"0"),config.EnableSubtitleExtraction=form.querySelector("#chkEnableSubtitleExtraction").checked,config.HardwareDecodingCodecs=Array.prototype.map.call(Array.prototype.filter.call(form.querySelectorAll(".chkDecodeCodec"),function(c){return c.checked}),function(c){return c.getAttribute("data-codec")}),config.EnableHardwareEncoding=form.querySelector("#chkHardwareEncoding").checked,ApiClient.updateNamedConfiguration("encoding",config).then(function(){updateEncoder(form)})})};return $("#selectVideoDecoder",form).val()?require(["alert"],function(alert){alert({title:globalize.translate("TitleHardwareAcceleration"),text:globalize.translate("HardwareAccelerationWarning")}).then(onDecoderConfirmed)}):onDecoderConfirmed(),!1}function setDecodingCodecsVisible(context,value){value=value||"";var any;Array.prototype.forEach.call(context.querySelectorAll(".chkDecodeCodec"),function(c){-1===c.getAttribute("data-types").split(",").indexOf(value)?dom.parentWithTag(c,"LABEL").classList.add("hide"):(dom.parentWithTag(c,"LABEL").classList.remove("hide"),any=!0)}),any?context.querySelector(".decodingCodecsList").classList.remove("hide"):context.querySelector(".decodingCodecsList").classList.add("hide")}$(document).on("pageinit","#encodingSettingsPage",function(){var page=this;page.querySelector("#selectVideoDecoder").addEventListener("change",function(){"vaapi"==this.value?(page.querySelector(".fldVaapiDevice").classList.remove("hide"),page.querySelector("#txtVaapiDevice").setAttribute("required","required")):(page.querySelector(".fldVaapiDevice").classList.add("hide"),page.querySelector("#txtVaapiDevice").removeAttribute("required")),this.value?page.querySelector(".hardwareAccelerationOptions").classList.remove("hide"):page.querySelector(".hardwareAccelerationOptions").classList.add("hide"),setDecodingCodecsVisible(page,this.value)}),$("#btnSelectEncoderPath",page).on("click.selectDirectory",function(){require(["directorybrowser"],function(directoryBrowser){var picker=new directoryBrowser;picker.show({includeFiles:!0,callback:function(path){path&&$(".txtEncoderPath",page).val(path),picker.close()}})})}),$("#btnSelectTranscodingTempPath",page).on("click.selectDirectory",function(){require(["directorybrowser"],function(directoryBrowser){var picker=new directoryBrowser;picker.show({callback:function(path){path&&$("#txtTranscodingTempPath",page).val(path),picker.close()},validateWriteable:!0,header:globalize.translate("HeaderSelectTranscodingPath"),instruction:globalize.translate("HeaderSelectTranscodingPathHelp")})})}),$(".encodingSettingsForm").off("submit",onSubmit).on("submit",onSubmit)}).on("pageshow","#encodingSettingsPage",function(){loading.show();var page=this;ApiClient.getNamedConfiguration("encoding").then(function(config){ApiClient.getSystemInfo().then(function(systemInfo){"External"==systemInfo.EncoderLocationType?(page.querySelector(".fldEncoderPath").classList.add("hide"),page.querySelector(".txtEncoderPath").removeAttribute("required")):(page.querySelector(".fldEncoderPath").classList.remove("hide"),page.querySelector(".txtEncoderPath").setAttribute("required","required")),loadPage(page,config,systemInfo)})})})}); \ No newline at end of file +define(["jQuery", "loading", "globalize", "dom"], function($, loading, globalize, dom) { + "use strict"; + + function loadPage(page, config, systemInfo) { + Array.prototype.forEach.call(page.querySelectorAll(".chkDecodeCodec"), function(c) { + c.checked = -1 !== (config.HardwareDecodingCodecs || []).indexOf(c.getAttribute("data-codec")) + }), page.querySelector("#chkHardwareEncoding").checked = config.EnableHardwareEncoding, $("#selectVideoDecoder", page).val(config.HardwareAccelerationType), $("#selectThreadCount", page).val(config.EncodingThreadCount), $("#txtDownMixAudioBoost", page).val(config.DownMixAudioBoost), page.querySelector(".txtEncoderPath").value = config.EncoderAppPath || "", $("#txtTranscodingTempPath", page).val(config.TranscodingTempPath || ""), $("#txtVaapiDevice", page).val(config.VaapiDevice || ""), page.querySelector("#selectH264Preset").value = config.H264Preset || "", page.querySelector("#txtH264Crf").value = config.H264Crf || "", page.querySelector("#chkEnableSubtitleExtraction").checked = config.EnableSubtitleExtraction || !1, page.querySelector("#selectVideoDecoder").dispatchEvent(new CustomEvent("change", { + bubbles: !0 + })), loading.hide() + } + + function onSaveEncodingPathFailure(response) { + loading.hide(); + var msg = ""; + msg = globalize.translate("FFmpegSavePathNotFound"), require(["alert"], function(alert) { + alert(msg) + }) + } + + function updateEncoder(form) { + return ApiClient.getSystemInfo().then(function(systemInfo) { + return ApiClient.ajax({ + url: ApiClient.getUrl("System/MediaEncoder/Path"), + type: "POST", + data: { + Path: form.querySelector(".txtEncoderPath").value, + PathType: "Custom" + } + }).then(Dashboard.processServerConfigurationUpdateResult, onSaveEncodingPathFailure) + }) + } + + function onSubmit() { + var form = this, + onDecoderConfirmed = function() { + loading.show(), ApiClient.getNamedConfiguration("encoding").then(function(config) { + config.DownMixAudioBoost = $("#txtDownMixAudioBoost", form).val(), config.TranscodingTempPath = $("#txtTranscodingTempPath", form).val(), config.EncodingThreadCount = $("#selectThreadCount", form).val(), config.HardwareAccelerationType = $("#selectVideoDecoder", form).val(), config.VaapiDevice = $("#txtVaapiDevice", form).val(), config.H264Preset = form.querySelector("#selectH264Preset").value, config.H264Crf = parseInt(form.querySelector("#txtH264Crf").value || "0"), config.EnableSubtitleExtraction = form.querySelector("#chkEnableSubtitleExtraction").checked, config.HardwareDecodingCodecs = Array.prototype.map.call(Array.prototype.filter.call(form.querySelectorAll(".chkDecodeCodec"), function(c) { + return c.checked + }), function(c) { + return c.getAttribute("data-codec") + }), config.EnableHardwareEncoding = form.querySelector("#chkHardwareEncoding").checked, ApiClient.updateNamedConfiguration("encoding", config).then(function() { + updateEncoder(form) + }) + }) + }; + return $("#selectVideoDecoder", form).val() ? require(["alert"], function(alert) { + alert({ + title: globalize.translate("TitleHardwareAcceleration"), + text: globalize.translate("HardwareAccelerationWarning") + }).then(onDecoderConfirmed) + }) : onDecoderConfirmed(), !1 + } + + function setDecodingCodecsVisible(context, value) { + value = value || ""; + var any; + Array.prototype.forEach.call(context.querySelectorAll(".chkDecodeCodec"), function(c) { + -1 === c.getAttribute("data-types").split(",").indexOf(value) ? dom.parentWithTag(c, "LABEL").classList.add("hide") : (dom.parentWithTag(c, "LABEL").classList.remove("hide"), any = !0) + }), any ? context.querySelector(".decodingCodecsList").classList.remove("hide") : context.querySelector(".decodingCodecsList").classList.add("hide") + } + $(document).on("pageinit", "#encodingSettingsPage", function() { + var page = this; + page.querySelector("#selectVideoDecoder").addEventListener("change", function() { + "vaapi" == this.value ? (page.querySelector(".fldVaapiDevice").classList.remove("hide"), page.querySelector("#txtVaapiDevice").setAttribute("required", "required")) : (page.querySelector(".fldVaapiDevice").classList.add("hide"), page.querySelector("#txtVaapiDevice").removeAttribute("required")), this.value ? page.querySelector(".hardwareAccelerationOptions").classList.remove("hide") : page.querySelector(".hardwareAccelerationOptions").classList.add("hide"), setDecodingCodecsVisible(page, this.value) + }), $("#btnSelectEncoderPath", page).on("click.selectDirectory", function() { + require(["directorybrowser"], function(directoryBrowser) { + var picker = new directoryBrowser; + picker.show({ + includeFiles: !0, + callback: function(path) { + path && $(".txtEncoderPath", page).val(path), picker.close() + } + }) + }) + }), $("#btnSelectTranscodingTempPath", page).on("click.selectDirectory", function() { + require(["directorybrowser"], function(directoryBrowser) { + var picker = new directoryBrowser; + picker.show({ + callback: function(path) { + path && $("#txtTranscodingTempPath", page).val(path), picker.close() + }, + validateWriteable: !0, + header: globalize.translate("HeaderSelectTranscodingPath"), + instruction: globalize.translate("HeaderSelectTranscodingPathHelp") + }) + }) + }), $(".encodingSettingsForm").off("submit", onSubmit).on("submit", onSubmit) + }).on("pageshow", "#encodingSettingsPage", function() { + loading.show(); + var page = this; + ApiClient.getNamedConfiguration("encoding").then(function(config) { + ApiClient.getSystemInfo().then(function(systemInfo) { + "External" == systemInfo.EncoderLocationType ? (page.querySelector(".fldEncoderPath").classList.add("hide"), page.querySelector(".txtEncoderPath").removeAttribute("required")) : (page.querySelector(".fldEncoderPath").classList.remove("hide"), page.querySelector(".txtEncoderPath").setAttribute("required", "required")), loadPage(page, config, systemInfo) + }) + }) + }) +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/episodes.js b/dashboard-ui/scripts/episodes.js index 428107cd26..5885d96c33 100644 --- a/dashboard-ui/scripts/episodes.js +++ b/dashboard-ui/scripts/episodes.js @@ -1 +1,155 @@ -define(["loading","events","libraryBrowser","imageLoader","listView","cardBuilder","emby-itemscontainer"],function(loading,events,libraryBrowser,imageLoader,listView,cardBuilder){"use strict";return function(view,params,tabContent){function getPageData(context){var key=getSavedQueryKey(context),pageData=data[key];return pageData||(pageData=data[key]={query:{SortBy:"SeriesSortName,SortName",SortOrder:"Ascending",IncludeItemTypes:"Episode",Recursive:!0,Fields:"PrimaryImageAspectRatio,MediaSourceCount,UserData",IsMissing:!1,ImageTypeLimit:1,EnableImageTypes:"Primary,Backdrop,Thumb",StartIndex:0,Limit:pageSize},view:libraryBrowser.getSavedView(key)||"Poster"},pageData.query.ParentId=params.topParentId,libraryBrowser.loadSavedQueryValues(key,pageData.query)),pageData}function getQuery(context){return getPageData(context).query}function getSavedQueryKey(context){return context.savedQueryKey||(context.savedQueryKey=libraryBrowser.getSavedQueryKey("episodes")),context.savedQueryKey}function onViewStyleChange(){var viewStyle=self.getCurrentViewStyle(),itemsContainer=tabContent.querySelector(".itemsContainer");"List"==viewStyle?(itemsContainer.classList.add("vertical-list"),itemsContainer.classList.remove("vertical-wrap")):(itemsContainer.classList.remove("vertical-list"),itemsContainer.classList.add("vertical-wrap")),itemsContainer.innerHTML=""}function reloadItems(page){loading.show();var query=getQuery(page);ApiClient.getItems(Dashboard.getCurrentUserId(),query).then(function(result){function onNextPageClick(){query.StartIndex+=query.Limit,reloadItems(tabContent)}function onPreviousPageClick(){query.StartIndex-=query.Limit,reloadItems(tabContent)}window.scrollTo(0,0);var html,pagingHtml=libraryBrowser.getQueryPagingHtml({startIndex:query.StartIndex,limit:query.Limit,totalRecordCount:result.TotalRecordCount,showLimit:!1,updatePageSizeSetting:!1,addLayoutButton:!1,sortButton:!1,filterButton:!1}),viewStyle=self.getCurrentViewStyle(),itemsContainer=tabContent.querySelector(".itemsContainer");html="List"==viewStyle?listView.getListViewHtml({items:result.Items,sortBy:query.SortBy,showParentTitle:!0}):"PosterCard"==viewStyle?cardBuilder.getCardsHtml({items:result.Items,shape:"backdrop",showTitle:!0,showParentTitle:!0,scalable:!0,cardLayout:!0}):cardBuilder.getCardsHtml({items:result.Items,shape:"backdrop",showTitle:!0,showParentTitle:!0,overlayText:!1,centerText:!0,scalable:!0,overlayPlayButton:!0});var i,length,elems=tabContent.querySelectorAll(".paging");for(i=0,length=elems.length;i",void Dashboard.alert({message:msg,title:Globalize.translate("HeaderForgotPassword")})}}return function(view,params){function onSubmit(e){return ApiClient.ajax({type:"POST",url:ApiClient.getUrl("Users/ForgotPassword"),dataType:"json",data:{EnteredUsername:view.querySelector("#txtName").value}}).then(processForgotPasswordResult),e.preventDefault(),!1}view.querySelector("form").addEventListener("submit",onSubmit)}}); \ No newline at end of file +define([], function() { + "use strict"; + + function processForgotPasswordResult(result) { + if ("ContactAdmin" == result.Action) return void Dashboard.alert({ + message: Globalize.translate("MessageContactAdminToResetPassword"), + title: Globalize.translate("HeaderForgotPassword") + }); + if ("InNetworkRequired" == result.Action) return void Dashboard.alert({ + message: Globalize.translate("MessageForgotPasswordInNetworkRequired"), + title: Globalize.translate("HeaderForgotPassword") + }); + if ("PinCode" == result.Action) { + var msg = Globalize.translate("MessageForgotPasswordFileCreated"); + return msg += "
    ", msg += "
    ", msg += result.PinFile, msg += "
    ", void Dashboard.alert({ + message: msg, + title: Globalize.translate("HeaderForgotPassword") + }) + } + } + return function(view, params) { + function onSubmit(e) { + return ApiClient.ajax({ + type: "POST", + url: ApiClient.getUrl("Users/ForgotPassword"), + dataType: "json", + data: { + EnteredUsername: view.querySelector("#txtName").value + } + }).then(processForgotPasswordResult), e.preventDefault(), !1 + } + view.querySelector("form").addEventListener("submit", onSubmit) + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/forgotpasswordpin.js b/dashboard-ui/scripts/forgotpasswordpin.js index e23314ea11..29f8a8369a 100644 --- a/dashboard-ui/scripts/forgotpasswordpin.js +++ b/dashboard-ui/scripts/forgotpasswordpin.js @@ -1 +1,33 @@ -define([],function(){"use strict";function processForgotPasswordResult(result){if(result.Success){var msg=Globalize.translate("MessagePasswordResetForUsers");return msg+="
    ",msg+="
    ",msg+=result.UsersReset.join("
    "),void Dashboard.alert({message:msg,title:Globalize.translate("HeaderPasswordReset"),callback:function(){window.location.href="login.html"}})}Dashboard.alert({message:Globalize.translate("MessageInvalidForgotPasswordPin"),title:Globalize.translate("HeaderPasswordReset")})}return function(view,params){function onSubmit(e){return ApiClient.ajax({type:"POST",url:ApiClient.getUrl("Users/ForgotPassword/Pin"),dataType:"json",data:{Pin:view.querySelector("#txtPin").value}}).then(processForgotPasswordResult),e.preventDefault(),!1}view.querySelector("form").addEventListener("submit",onSubmit)}}); \ No newline at end of file +define([], function() { + "use strict"; + + function processForgotPasswordResult(result) { + if (result.Success) { + var msg = Globalize.translate("MessagePasswordResetForUsers"); + return msg += "
    ", msg += "
    ", msg += result.UsersReset.join("
    "), void Dashboard.alert({ + message: msg, + title: Globalize.translate("HeaderPasswordReset"), + callback: function() { + window.location.href = "login.html" + } + }) + } + Dashboard.alert({ + message: Globalize.translate("MessageInvalidForgotPasswordPin"), + title: Globalize.translate("HeaderPasswordReset") + }) + } + return function(view, params) { + function onSubmit(e) { + return ApiClient.ajax({ + type: "POST", + url: ApiClient.getUrl("Users/ForgotPassword/Pin"), + dataType: "json", + data: { + Pin: view.querySelector("#txtPin").value + } + }).then(processForgotPasswordResult), e.preventDefault(), !1 + } + view.querySelector("form").addEventListener("submit", onSubmit) + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/itembynamedetailpage.js b/dashboard-ui/scripts/itembynamedetailpage.js index 6975c1112d..789fd0491e 100644 --- a/dashboard-ui/scripts/itembynamedetailpage.js +++ b/dashboard-ui/scripts/itembynamedetailpage.js @@ -1 +1,263 @@ -define(["connectionManager","listView","cardBuilder","imageLoader","libraryBrowser","emby-itemscontainer","emby-linkbutton"],function(connectionManager,listView,cardBuilder,imageLoader,libraryBrowser){"use strict";function renderItems(page,item){var sections=[];item.ArtistCount&§ions.push({name:Globalize.translate("TabArtists"),type:"MusicArtist"}),item.ProgramCount&&"Person"==item.Type&§ions.push({name:Globalize.translate("HeaderUpcomingOnTV"),type:"Program"}),item.MovieCount&§ions.push({name:Globalize.translate("TabMovies"),type:"Movie"}),item.SeriesCount&§ions.push({name:Globalize.translate("TabShows"),type:"Series"}),item.EpisodeCount&§ions.push({name:Globalize.translate("TabEpisodes"),type:"Episode"}),item.TrailerCount&§ions.push({name:Globalize.translate("TabTrailers"),type:"Trailer"}),item.GameCount&§ions.push({name:Globalize.translate("TabGames"),type:"Game"}),item.AlbumCount&§ions.push({name:Globalize.translate("TabAlbums"),type:"MusicAlbum"}),item.MusicVideoCount&§ions.push({name:Globalize.translate("TabMusicVideos"),type:"MusicVideo"});var elem=page.querySelector("#childrenContent");elem.innerHTML=sections.map(function(section){var html="",sectionClass="verticalSection";return"Audio"===section.type&&(sectionClass+=" verticalSection-extrabottompadding"),html+='
    ',html+='
    ',html+='

    ',html+=section.name,html+="

    ",html+='",html+="
    ",html+='
    ',html+="
    ",html+="
    "}).join("");for(var sectionElems=elem.querySelectorAll(".verticalSection"),i=0,length=sectionElems.length;iquery.Limit){var link=element.querySelector("a");link.classList.remove("hide"),link.setAttribute("href",getMoreItemsHref(item,type))}else element.querySelector("a").classList.add("hide");listOptions.items=result.Items;var itemsContainer=element.querySelector(".itemsContainer");"Audio"==type?(html=listView.getListViewHtml(listOptions),itemsContainer.classList.remove("vertical-wrap"),itemsContainer.classList.add("vertical-list")):(html=cardBuilder.getCardsHtml(listOptions),itemsContainer.classList.add("vertical-wrap"),itemsContainer.classList.remove("vertical-list")),itemsContainer.innerHTML=html,imageLoader.lazyChildren(itemsContainer)})}function getMoreItemsHref(item,type){return"Genre"==item.Type?"list/list.html?type="+type+"&genreId="+item.Id+"&serverId="+item.ServerId:"MusicGenre"==item.Type?"list/list.html?type="+type+"&musicGenreId="+item.Id+"&serverId="+item.ServerId:"GameGenre"==item.Type?"list/list.html?type="+type+"&gameGenreId="+item.Id+"&serverId="+item.ServerId:"Studio"==item.Type?"list/list.html?type="+type+"&studioId="+item.Id+"&serverId="+item.ServerId:"MusicArtist"==item.Type?"list/list.html?type="+type+"&artistId="+item.Id+"&serverId="+item.ServerId:"Person"==item.Type?"list/list.html?type="+type+"&personId="+item.Id+"&serverId="+item.ServerId:"list/list.html?type="+type+"&parentId="+item.Id+"&serverId="+item.ServerId}function addCurrentItemToQuery(query,item){"Person"==item.Type?query.PersonIds=item.Id:"Genre"==item.Type?query.GenreIds=item.Id:"MusicGenre"==item.Type?query.GenreIds=item.Id:"GameGenre"==item.Type?query.GenreIds=item.Id:"Studio"==item.Type?query.StudioIds=item.Id:"MusicArtist"==item.Type&&(connectionManager.getApiClient(item.ServerId).isMinServerVersion("3.4.1.18")?query.AlbumArtistIds=item.Id:query.ArtistIds=item.Id)}function getQuery(options,item){var query={SortOrder:"Ascending",IncludeItemTypes:"",Recursive:!0,Fields:"AudioInfo,SeriesInfo,ParentId,PrimaryImageAspectRatio,BasicSyncInfo",Limit:100,StartIndex:0,CollapseBoxSetItems:!1};return query=Object.assign(query,options||{}),addCurrentItemToQuery(query,item),query}function getItemsFunction(options,item){var query=getQuery(options,item);return function(index,limit,fields){query.StartIndex=index,query.Limit=limit,fields&&(query.Fields+=","+fields);var apiClient=connectionManager.getApiClient(item.ServerId);return"MusicArtist"===query.IncludeItemTypes?(query.IncludeItemTypes=null,apiClient.getAlbumArtists(apiClient.getCurrentUserId(),query)):apiClient.getItems(apiClient.getCurrentUserId(),query)}}window.ItemsByName={renderItems:renderItems}}); \ No newline at end of file +define(["connectionManager", "listView", "cardBuilder", "imageLoader", "libraryBrowser", "emby-itemscontainer", "emby-linkbutton"], function(connectionManager, listView, cardBuilder, imageLoader, libraryBrowser) { + "use strict"; + + function renderItems(page, item) { + var sections = []; + item.ArtistCount && sections.push({ + name: Globalize.translate("TabArtists"), + type: "MusicArtist" + }), item.ProgramCount && "Person" == item.Type && sections.push({ + name: Globalize.translate("HeaderUpcomingOnTV"), + type: "Program" + }), item.MovieCount && sections.push({ + name: Globalize.translate("TabMovies"), + type: "Movie" + }), item.SeriesCount && sections.push({ + name: Globalize.translate("TabShows"), + type: "Series" + }), item.EpisodeCount && sections.push({ + name: Globalize.translate("TabEpisodes"), + type: "Episode" + }), item.TrailerCount && sections.push({ + name: Globalize.translate("TabTrailers"), + type: "Trailer" + }), item.GameCount && sections.push({ + name: Globalize.translate("TabGames"), + type: "Game" + }), item.AlbumCount && sections.push({ + name: Globalize.translate("TabAlbums"), + type: "MusicAlbum" + }), item.MusicVideoCount && sections.push({ + name: Globalize.translate("TabMusicVideos"), + type: "MusicVideo" + }); + var elem = page.querySelector("#childrenContent"); + elem.innerHTML = sections.map(function(section) { + var html = "", + sectionClass = "verticalSection"; + return "Audio" === section.type && (sectionClass += " verticalSection-extrabottompadding"), html += '
    ', html += '
    ', html += '

    ', html += section.name, html += "

    ", html += '", html += "
    ", html += '
    ', html += "
    ", html += "
    " + }).join(""); + for (var sectionElems = elem.querySelectorAll(".verticalSection"), i = 0, length = sectionElems.length; i < length; i++) renderSection(page, item, sectionElems[i], sectionElems[i].getAttribute("data-type")) + } + + function renderSection(page, item, element, type) { + switch (type) { + case "Program": + loadItems(element, item, type, { + MediaTypes: "", + IncludeItemTypes: "Program", + PersonTypes: "", + ArtistIds: "", + AlbumArtistIds: "", + Limit: 10, + SortBy: "StartDate" + }, { + shape: "backdrop", + showTitle: !0, + centerText: !0, + overlayMoreButton: !0, + preferThumb: !0, + overlayText: !1, + showAirTime: !0, + showAirDateTime: !0, + showChannelName: !0 + }); + break; + case "Movie": + loadItems(element, item, type, { + MediaTypes: "", + IncludeItemTypes: "Movie", + PersonTypes: "", + ArtistIds: "", + AlbumArtistIds: "", + Limit: 10, + SortBy: "SortName" + }, { + shape: "portrait", + showTitle: !0, + centerText: !0, + overlayMoreButton: !0, + overlayText: !1, + showYear: !0 + }); + break; + case "MusicVideo": + loadItems(element, item, type, { + MediaTypes: "", + IncludeItemTypes: "MusicVideo", + PersonTypes: "", + ArtistIds: "", + AlbumArtistIds: "", + Limit: 10, + SortBy: "SortName" + }, { + shape: "portrait", + showTitle: !0, + centerText: !0, + overlayPlayButton: !0 + }); + break; + case "Game": + loadItems(element, item, type, { + MediaTypes: "", + IncludeItemTypes: "Game", + PersonTypes: "", + ArtistIds: "", + AlbumArtistIds: "", + Limit: 10, + SortBy: "SortName" + }, { + shape: "portrait", + showTitle: !0, + centerText: !0, + overlayMoreButton: !0 + }); + break; + case "Trailer": + loadItems(element, item, type, { + MediaTypes: "", + IncludeItemTypes: "Trailer", + PersonTypes: "", + ArtistIds: "", + AlbumArtistIds: "", + Limit: 10, + SortBy: "SortName" + }, { + shape: "portrait", + showTitle: !0, + centerText: !0, + overlayPlayButton: !0 + }); + break; + case "Series": + loadItems(element, item, type, { + MediaTypes: "", + IncludeItemTypes: "Series", + PersonTypes: "", + ArtistIds: "", + AlbumArtistIds: "", + Limit: 10, + SortBy: "SortName" + }, { + shape: "portrait", + showTitle: !0, + centerText: !0, + overlayMoreButton: !0 + }); + break; + case "MusicAlbum": + loadItems(element, item, type, { + MediaTypes: "", + IncludeItemTypes: "MusicAlbum", + PersonTypes: "", + ArtistIds: "", + AlbumArtistIds: "" + }, { + shape: "square", + playFromHere: !0, + showTitle: !0, + showYear: !0, + coverImage: !0, + centerText: !0, + overlayPlayButton: !0 + }); + break; + case "MusicArtist": + loadItems(element, item, type, { + MediaTypes: "", + IncludeItemTypes: "MusicArtist", + PersonTypes: "", + ArtistIds: "", + AlbumArtistIds: "", + Limit: 8, + SortBy: "SortName" + }, { + shape: "square", + playFromHere: !0, + showTitle: !0, + showParentTitle: !0, + coverImage: !0, + centerText: !0, + overlayPlayButton: !0 + }); + break; + case "Episode": + loadItems(element, item, type, { + MediaTypes: "", + IncludeItemTypes: "Episode", + PersonTypes: "", + ArtistIds: "", + AlbumArtistIds: "", + Limit: 6, + SortBy: "SortName" + }, { + shape: "backdrop", + showTitle: !0, + showParentTitle: !0, + centerText: !0, + overlayPlayButton: !0 + }); + break; + case "Audio": + loadItems(element, item, type, { + MediaTypes: "", + IncludeItemTypes: "Audio", + PersonTypes: "", + ArtistIds: "", + AlbumArtistIds: "", + SortBy: "AlbumArtist,Album,SortName" + }, { + playFromHere: !0, + action: "playallfromhere", + smallIcon: !0, + artist: !0 + }) + } + } + + function loadItems(element, item, type, query, listOptions) { + query = getQuery(query, item), getItemsFunction(query, item)(query.StartIndex, query.Limit, query.Fields).then(function(result) { + var html = ""; + if (query.Limit && result.TotalRecordCount > query.Limit) { + var link = element.querySelector("a"); + link.classList.remove("hide"), link.setAttribute("href", getMoreItemsHref(item, type)) + } else element.querySelector("a").classList.add("hide"); + listOptions.items = result.Items; + var itemsContainer = element.querySelector(".itemsContainer"); + "Audio" == type ? (html = listView.getListViewHtml(listOptions), itemsContainer.classList.remove("vertical-wrap"), itemsContainer.classList.add("vertical-list")) : (html = cardBuilder.getCardsHtml(listOptions), itemsContainer.classList.add("vertical-wrap"), itemsContainer.classList.remove("vertical-list")), itemsContainer.innerHTML = html, imageLoader.lazyChildren(itemsContainer) + }) + } + + function getMoreItemsHref(item, type) { + return "Genre" == item.Type ? "list/list.html?type=" + type + "&genreId=" + item.Id + "&serverId=" + item.ServerId : "MusicGenre" == item.Type ? "list/list.html?type=" + type + "&musicGenreId=" + item.Id + "&serverId=" + item.ServerId : "GameGenre" == item.Type ? "list/list.html?type=" + type + "&gameGenreId=" + item.Id + "&serverId=" + item.ServerId : "Studio" == item.Type ? "list/list.html?type=" + type + "&studioId=" + item.Id + "&serverId=" + item.ServerId : "MusicArtist" == item.Type ? "list/list.html?type=" + type + "&artistId=" + item.Id + "&serverId=" + item.ServerId : "Person" == item.Type ? "list/list.html?type=" + type + "&personId=" + item.Id + "&serverId=" + item.ServerId : "list/list.html?type=" + type + "&parentId=" + item.Id + "&serverId=" + item.ServerId + } + + function addCurrentItemToQuery(query, item) { + "Person" == item.Type ? query.PersonIds = item.Id : "Genre" == item.Type ? query.GenreIds = item.Id : "MusicGenre" == item.Type ? query.GenreIds = item.Id : "GameGenre" == item.Type ? query.GenreIds = item.Id : "Studio" == item.Type ? query.StudioIds = item.Id : "MusicArtist" == item.Type && (connectionManager.getApiClient(item.ServerId).isMinServerVersion("3.4.1.18") ? query.AlbumArtistIds = item.Id : query.ArtistIds = item.Id) + } + + function getQuery(options, item) { + var query = { + SortOrder: "Ascending", + IncludeItemTypes: "", + Recursive: !0, + Fields: "AudioInfo,SeriesInfo,ParentId,PrimaryImageAspectRatio,BasicSyncInfo", + Limit: 100, + StartIndex: 0, + CollapseBoxSetItems: !1 + }; + return query = Object.assign(query, options || {}), addCurrentItemToQuery(query, item), query + } + + function getItemsFunction(options, item) { + var query = getQuery(options, item); + return function(index, limit, fields) { + query.StartIndex = index, query.Limit = limit, fields && (query.Fields += "," + fields); + var apiClient = connectionManager.getApiClient(item.ServerId); + return "MusicArtist" === query.IncludeItemTypes ? (query.IncludeItemTypes = null, apiClient.getAlbumArtists(apiClient.getCurrentUserId(), query)) : apiClient.getItems(apiClient.getCurrentUserId(), query) + } + } + window.ItemsByName = { + renderItems: renderItems + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/itemdetailpage.js b/dashboard-ui/scripts/itemdetailpage.js index 8018cf712d..dbff04c2e5 100644 --- a/dashboard-ui/scripts/itemdetailpage.js +++ b/dashboard-ui/scripts/itemdetailpage.js @@ -1,2 +1,1209 @@ -define(["loading","appRouter","layoutManager","connectionManager","cardBuilder","datetime","mediaInfo","backdrop","listView","itemContextMenu","itemHelper","dom","indicators","apphost","imageLoader","libraryMenu","globalize","browser","events","scrollHelper","playbackManager","libraryBrowser","scrollStyles","emby-itemscontainer","emby-checkbox","emby-linkbutton","emby-playstatebutton","emby-ratingbutton","emby-downloadbutton","emby-scroller","emby-select"],function(loading,appRouter,layoutManager,connectionManager,cardBuilder,datetime,mediaInfo,backdrop,listView,itemContextMenu,itemHelper,dom,indicators,appHost,imageLoader,libraryMenu,globalize,browser,events,scrollHelper,playbackManager,libraryBrowser){"use strict";function getPromise(apiClient,params){var id=params.id;if(id)return apiClient.getItem(apiClient.getCurrentUserId(),id);if(params.seriesTimerId)return apiClient.getLiveTvSeriesTimer(params.seriesTimerId);var name=params.genre;if(name)return apiClient.getGenre(name,apiClient.getCurrentUserId());if(name=params.musicgenre)return apiClient.getMusicGenre(name,apiClient.getCurrentUserId());if(name=params.gamegenre)return apiClient.getGameGenre(name,apiClient.getCurrentUserId());if(name=params.musicartist)return apiClient.getArtist(name,apiClient.getCurrentUserId());throw new Error("Invalid request")}function hideAll(page,className,show){var i,length,elems=page.querySelectorAll("."+className);for(i=0,length=elems.length;i"}function renderSeriesTimerSchedule(page,apiClient,seriesTimerId){apiClient.getLiveTvTimers({UserId:apiClient.getCurrentUserId(),ImageTypeLimit:1,EnableImageTypes:"Primary,Backdrop,Thumb",SortBy:"StartDate",EnableTotalRecordCount:!1,EnableUserData:!1,SeriesTimerId:seriesTimerId,Fields:"ChannelInfo,ChannelImage"}).then(function(result){result.Items.length&&result.Items[0].SeriesTimerId!=seriesTimerId&&(result.Items=[]);var html=getProgramScheduleHtml(result.Items),scheduleTab=page.querySelector(".seriesTimerSchedule");scheduleTab.innerHTML=html,imageLoader.lazyChildren(scheduleTab)})}function renderTimerEditor(page,item,apiClient,user){if("Recording"!==item.Type||!user.Policy.EnableLiveTvManagement||!item.TimerId||"InProgress"!==item.Status)return void hideAll(page,"btnCancelTimer");hideAll(page,"btnCancelTimer",!0)}function renderSeriesTimerEditor(page,item,apiClient,user){return"SeriesTimer"!==item.Type?void hideAll(page,"btnCancelSeriesTimer"):user.Policy.EnableLiveTvManagement?(require(["seriesRecordingEditor"],function(seriesRecordingEditor){seriesRecordingEditor.embed(item,apiClient.serverId(),{context:page.querySelector(".seriesRecordingEditor")})}),page.querySelector(".seriesTimerScheduleSection").classList.remove("hide"),hideAll(page,"btnCancelSeriesTimer",!0),void renderSeriesTimerSchedule(page,apiClient,item.Id)):(page.querySelector(".seriesTimerScheduleSection").classList.add("hide"),void hideAll(page,"btnCancelSeriesTimer"))}function renderTrackSelections(page,instance,item,forceReload){var select=page.querySelector(".selectSource");if(!item.MediaSources||!itemHelper.supportsMediaSourceSelection(item)||-1===playbackManager.getSupportedCommands().indexOf("PlayMediaSource")||!playbackManager.canPlay(item))return page.querySelector(".trackSelections").classList.add("hide"),select.innerHTML="",page.querySelector(".selectVideo").innerHTML="",page.querySelector(".selectAudio").innerHTML="",void(page.querySelector(".selectSubtitles").innerHTML="");playbackManager.getPlaybackMediaSources(item).then(function(mediaSources){instance._currentPlaybackMediaSources=mediaSources,page.querySelector(".trackSelections").classList.remove("hide"),select.setLabel(globalize.translate("sharedcomponents#LabelVersion"));var currentValue=select.value,selectedId=mediaSources[0].Id;select.innerHTML=mediaSources.map(function(v){var selected=v.Id===selectedId?" selected":"";return'"}).join(""),mediaSources.length>1?page.querySelector(".selectSourceContainer").classList.remove("hide"):page.querySelector(".selectSourceContainer").classList.add("hide"),(select.value!==currentValue||forceReload)&&(renderVideoSelections(page,mediaSources),renderAudioSelections(page,mediaSources),renderSubtitleSelections(page,mediaSources))})}function renderVideoSelections(page,mediaSources){var mediaSourceId=page.querySelector(".selectSource").value,mediaSource=mediaSources.filter(function(m){return m.Id===mediaSourceId})[0],tracks=mediaSource.MediaStreams.filter(function(m){return"Video"===m.Type}),select=page.querySelector(".selectVideo");select.setLabel(globalize.translate("sharedcomponents#LabelVideo"));var selectedId=tracks.length?tracks[0].Index:-1;select.innerHTML=tracks.map(function(v){var selected=v.Index===selectedId?" selected":"",titleParts=[],resolutionText=mediaInfo.getResolutionText(v);return resolutionText&&titleParts.push(resolutionText),v.Codec&&titleParts.push(v.Codec.toUpperCase()),'"}).join(""),select.setAttribute("disabled","disabled"),tracks.length?page.querySelector(".selectVideoContainer").classList.remove("hide"):page.querySelector(".selectVideoContainer").classList.add("hide")}function renderAudioSelections(page,mediaSources){var mediaSourceId=page.querySelector(".selectSource").value,mediaSource=mediaSources.filter(function(m){return m.Id===mediaSourceId})[0],tracks=mediaSource.MediaStreams.filter(function(m){return"Audio"===m.Type}),select=page.querySelector(".selectAudio");select.setLabel(globalize.translate("sharedcomponents#LabelAudio"));var selectedId=mediaSource.DefaultAudioStreamIndex;select.innerHTML=tracks.map(function(v){var selected=v.Index===selectedId?" selected":"";return'"}).join(""),tracks.length>1?select.removeAttribute("disabled"):select.setAttribute("disabled","disabled"),tracks.length?page.querySelector(".selectAudioContainer").classList.remove("hide"):page.querySelector(".selectAudioContainer").classList.add("hide")}function renderSubtitleSelections(page,mediaSources){var mediaSourceId=page.querySelector(".selectSource").value,mediaSource=mediaSources.filter(function(m){return m.Id===mediaSourceId})[0],tracks=mediaSource.MediaStreams.filter(function(m){return"Subtitle"===m.Type}),select=page.querySelector(".selectSubtitles");select.setLabel(globalize.translate("sharedcomponents#LabelSubtitles"));var selectedId=null==mediaSource.DefaultSubtitleStreamIndex?-1:mediaSource.DefaultSubtitleStreamIndex;if(tracks.length){var selected=-1===selectedId?" selected":"";select.innerHTML='"+tracks.map(function(v){return selected=v.Index===selectedId?" selected":"",'"}).join(""),page.querySelector(".selectSubtitlesContainer").classList.remove("hide")}else select.innerHTML="",page.querySelector(".selectSubtitlesContainer").classList.add("hide")}function reloadPlayButtons(page,item){var canPlay=!1;if("Program"==item.Type){var now=new Date;now>=datetime.parseISO8601Date(item.StartDate,!0)&&now0)}else hideAll(page,"btnPlay"),hideAll(page,"btnResume"),hideAll(page,"btnInstantMix"),hideAll(page,"btnShuffle");return canPlay}function reloadUserDataButtons(page,item){var i,length,btnPlaystates=page.querySelectorAll(".btnPlaystate");for(i=0,length=btnPlaystates.length;i'+artist.Name+"")}return html=html.join(" / ")}function renderName(item,container,isStatic,context){var parentRoute,parentNameHtml=[],parentNameLast=!1;item.AlbumArtists?(parentNameHtml.push(getArtistLinksHtml(item.AlbumArtists,item.ServerId,context)),parentNameLast=!0):item.ArtistItems&&item.ArtistItems.length&&"MusicVideo"===item.Type?(parentNameHtml.push(getArtistLinksHtml(item.ArtistItems,item.ServerId,context)),parentNameLast=!0):item.SeriesName&&"Episode"===item.Type?(parentRoute=appRouter.getRouteUrl({Id:item.SeriesId,Name:item.SeriesName,Type:"Series",IsFolder:!0,ServerId:item.ServerId},{context:context}),parentNameHtml.push(''+item.SeriesName+"")):(item.IsSeries||item.EpisodeTitle)&&parentNameHtml.push(item.Name),item.SeriesName&&"Season"===item.Type?(parentRoute=appRouter.getRouteUrl({Id:item.SeriesId,Name:item.SeriesName,Type:"Series",IsFolder:!0,ServerId:item.ServerId},{context:context}),parentNameHtml.push(''+item.SeriesName+"")):null!=item.ParentIndexNumber&&"Episode"===item.Type?(parentRoute=appRouter.getRouteUrl({Id:item.SeasonId,Name:item.SeasonName,Type:"Season",IsFolder:!0,ServerId:item.ServerId},{context:context}),parentNameHtml.push(''+item.SeasonName+"")):null!=item.ParentIndexNumber&&item.IsSeries?parentNameHtml.push(item.SeasonName||"S"+item.ParentIndexNumber):item.Album&&item.AlbumId&&("MusicVideo"===item.Type||"Audio"===item.Type)?(parentRoute=appRouter.getRouteUrl({Id:item.AlbumId,Name:item.Album,Type:"MusicAlbum",IsFolder:!0,ServerId:item.ServerId},{context:context}),parentNameHtml.push(''+item.Album+"")):item.Album&&parentNameHtml.push(item.Album);var html="";parentNameHtml.length&&(html=parentNameLast?'

    '+parentNameHtml.join(" - ")+"

    ":'

    '+parentNameHtml.join(" - ")+"

    ");var name=itemHelper.getDisplayName(item,{includeParentInfo:!1});html&&!parentNameLast?html+='

    '+name+"

    ":html=parentNameLast?'

    '+name+"

    "+html:'

    '+name+"

    "+html,container.innerHTML=html,html.length?container.classList.remove("hide"):container.classList.add("hide")}function setTrailerButtonVisibility(page,item){(item.LocalTrailerCount||item.RemoteTrailers&&item.RemoteTrailers.length)&&-1!==playbackManager.getSupportedCommands().indexOf("PlayTrailers")?hideAll(page,"btnPlayTrailer",!0):hideAll(page,"btnPlayTrailer")}function renderDetailPageBackdrop(page,item,apiClient){var imgUrl,screenWidth=screen.availWidth,hasbackdrop=!1,itemBackdropElement=page.querySelector("#itemBackdrop"),usePrimaryImage="Video"===item.MediaType&&"Movie"!==item.Type&&"Trailer"!==item.Type||item.MediaType&&"Video"!==item.MediaType;return"Program"===item.Type&&item.ImageTags&&item.ImageTags.Thumb?(imgUrl=apiClient.getScaledImageUrl(item.Id,{type:"Thumb",index:0,maxWidth:screenWidth,tag:item.ImageTags.Thumb}),itemBackdropElement.classList.remove("noBackdrop"),imageLoader.lazyImage(itemBackdropElement,imgUrl,!1),hasbackdrop=!0):usePrimaryImage&&item.ImageTags&&item.ImageTags.Primary?(imgUrl=apiClient.getScaledImageUrl(item.Id,{type:"Primary",index:0,maxWidth:screenWidth,tag:item.ImageTags.Primary}),itemBackdropElement.classList.remove("noBackdrop"),imageLoader.lazyImage(itemBackdropElement,imgUrl,!1),hasbackdrop=!0):item.BackdropImageTags&&item.BackdropImageTags.length?(imgUrl=apiClient.getScaledImageUrl(item.Id,{type:"Backdrop",index:0,maxWidth:screenWidth,tag:item.BackdropImageTags[0]}),itemBackdropElement.classList.remove("noBackdrop"),imageLoader.lazyImage(itemBackdropElement,imgUrl,!1),hasbackdrop=!0):item.ParentBackdropItemId&&item.ParentBackdropImageTags&&item.ParentBackdropImageTags.length?(imgUrl=apiClient.getScaledImageUrl(item.ParentBackdropItemId,{type:"Backdrop",index:0,tag:item.ParentBackdropImageTags[0],maxWidth:screenWidth}),itemBackdropElement.classList.remove("noBackdrop"),imageLoader.lazyImage(itemBackdropElement,imgUrl,!1),hasbackdrop=!0):item.ImageTags&&item.ImageTags.Thumb?(imgUrl=apiClient.getScaledImageUrl(item.Id,{type:"Thumb",index:0,maxWidth:screenWidth,tag:item.ImageTags.Thumb}),itemBackdropElement.classList.remove("noBackdrop"),imageLoader.lazyImage(itemBackdropElement,imgUrl,!1),hasbackdrop=!0):(itemBackdropElement.classList.add("noBackdrop"),itemBackdropElement.style.backgroundImage=""),hasbackdrop}function reloadFromItem(instance,page,params,item,user){var context=params.context;renderName(item,page.querySelector(".nameContainer"),!1,context);var apiClient=connectionManager.getApiClient(item.ServerId);renderSeriesTimerEditor(page,item,apiClient,user),renderTimerEditor(page,item,apiClient,user),renderImage(page,item,apiClient,user),renderLogo(page,item,apiClient),setTitle(item,apiClient),setInitialCollapsibleState(page,item,apiClient,context,user),renderDetails(page,item,apiClient,context),renderTrackSelections(page,instance,item),dom.getWindowSize().innerWidth>=1e3?backdrop.setBackdrops([item]):backdrop.clear(),renderDetailPageBackdrop(page,item,apiClient);var canPlay=reloadPlayButtons(page,item);(item.LocalTrailerCount||item.RemoteTrailers&&item.RemoteTrailers.length)&&-1!==playbackManager.getSupportedCommands().indexOf("PlayTrailers")?hideAll(page,"btnPlayTrailer",!0):hideAll(page,"btnPlayTrailer"),setTrailerButtonVisibility(page,item),item.CanDelete&&!item.IsFolder?hideAll(page,"btnDeleteItem",!0):hideAll(page,"btnDeleteItem"),renderSyncLocalContainer(page,params,user,item),"Program"!==item.Type||canPlay?hideAll(page,"mainDetailButtons",!0):hideAll(page,"mainDetailButtons"),showRecordingFields(instance,page,item,user);var groupedVersions=(item.MediaSources||[]).filter(function(g){return"Grouping"==g.Type});user.Policy.IsAdministrator&&groupedVersions.length?page.querySelector(".splitVersionContainer").classList.remove("hide"):page.querySelector(".splitVersionContainer").classList.add("hide"),itemContextMenu.getCommands(getContextMenuOptions(item,user)).length?hideAll(page,"btnMoreCommands",!0):hideAll(page,"btnMoreCommands");var itemBirthday=page.querySelector("#itemBirthday");if("Person"==item.Type&&item.PremiereDate)try{var birthday=datetime.parseISO8601Date(item.PremiereDate,!0).toDateString();itemBirthday.classList.remove("hide"),itemBirthday.innerHTML=globalize.translate("BirthDateValue").replace("{0}",birthday)}catch(err){itemBirthday.classList.add("hide")}else itemBirthday.classList.add("hide");var itemDeathDate=page.querySelector("#itemDeathDate");if("Person"==item.Type&&item.EndDate)try{var deathday=datetime.parseISO8601Date(item.EndDate,!0).toDateString();itemDeathDate.classList.remove("hide"),itemDeathDate.innerHTML=globalize.translate("DeathDateValue").replace("{0}",deathday)}catch(err){itemDeathDate.classList.add("hide")}var itemBirthLocation=page.querySelector("#itemBirthLocation");if("Person"==item.Type&&item.ProductionLocations&&item.ProductionLocations.length){var gmap=''+item.ProductionLocations[0]+"";itemBirthLocation.classList.remove("hide"),itemBirthLocation.innerHTML=globalize.translate("BirthPlaceValue").replace("{0}",gmap)}else itemBirthLocation.classList.add("hide");setPeopleHeader(page,item),loading.hide()}function logoImageUrl(item,apiClient,options){return options=options||{},options.type="Logo",item.ImageTags&&item.ImageTags.Logo?(options.tag=item.ImageTags.Logo,apiClient.getScaledImageUrl(item.Id,options)):item.ParentLogoImageTag?(options.tag=item.ParentLogoImageTag,apiClient.getScaledImageUrl(item.ParentLogoItemId,options)):null}function setTitle(item,apiClient){var url=logoImageUrl(item,apiClient,{});if(url=null){var pageTitle=document.querySelector(".pageTitle");pageTitle.style.backgroundImage="url('"+url+"')",pageTitle.classList.add("pageTitleWithLogo"),pageTitle.innerHTML=""}else Emby.Page.setTitle("")}function renderLogo(page,item,apiClient){var url=logoImageUrl(item,apiClient,{maxWidth:300}),detailLogo=page.querySelector(".detailLogo");url?(detailLogo.classList.remove("hide"),detailLogo.classList.add("lazy"),detailLogo.setAttribute("data-src",url),imageLoader.lazyImage(detailLogo)):detailLogo.classList.add("hide")}function showRecordingFields(instance,page,item,user){if(!instance.currentRecordingFields){var recordingFieldsElement=page.querySelector(".recordingFields");"Program"==item.Type&&user.Policy.EnableLiveTvManagement?require(["recordingFields"],function(recordingFields){instance.currentRecordingFields=new recordingFields({parent:recordingFieldsElement,programId:item.Id,serverId:item.ServerId}),recordingFieldsElement.classList.remove("hide")}):(recordingFieldsElement.classList.add("hide"),recordingFieldsElement.innerHTML="")}}function renderLinks(linksElem,item){var html=[];if(item.DateCreated&&itemHelper.enableDateAddedDisplay(item)){var dateCreated=datetime.parseISO8601Date(item.DateCreated);html.push(globalize.translate("sharedcomponents#AddedOnValue",datetime.toLocaleDateString(dateCreated)+" "+datetime.getDisplayTime(dateCreated)))}var links=[];if(!layoutManager.tv&&(item.HomePageUrl&&links.push(''+globalize.translate("ButtonWebsite")+""),item.ExternalUrls))for(var i=0,length=item.ExternalUrls.length;i'+url.Name+"")}links.length&&html.push(globalize.translate("sharedcomponents#LinksValue",links.join(", "))),linksElem.innerHTML=html.join(", "),html.length?linksElem.classList.remove("hide"):linksElem.classList.add("hide")}function renderDetailImage(page,elem,item,apiClient,editable,imageLoader,indicators){"SeriesTimer"!==item.Type&&"Program"!==item.Type||(editable=!1),"Person"!==item.Type?(elem.classList.add("detailimg-hidemobile"),page.querySelector(".detailPageContent").classList.add("detailPageContent-nodetailimg")):page.querySelector(".detailPageContent").classList.remove("detailPageContent-nodetailimg");var imageTags=item.ImageTags||{};item.PrimaryImageTag&&(imageTags.Primary=item.PrimaryImageTag);var url,html="",shape="portrait",detectRatio=!1;imageTags.Primary?(url=apiClient.getScaledImageUrl(item.Id,{type:"Primary",maxHeight:360,tag:item.ImageTags.Primary}),detectRatio=!0):item.BackdropImageTags&&item.BackdropImageTags.length?(url=apiClient.getScaledImageUrl(item.Id,{type:"Backdrop",maxHeight:360,tag:item.BackdropImageTags[0]}),shape="thumb"):imageTags.Thumb?(url=apiClient.getScaledImageUrl(item.Id,{type:"Thumb",maxHeight:360,tag:item.ImageTags.Thumb}),shape="thumb"):imageTags.Disc?(url=apiClient.getScaledImageUrl(item.Id,{type:"Disc",maxHeight:360,tag:item.ImageTags.Disc}),shape="square"):item.AlbumId&&item.AlbumPrimaryImageTag?(url=apiClient.getScaledImageUrl(item.AlbumId,{type:"Primary",maxHeight:360,tag:item.AlbumPrimaryImageTag}),shape="square"):item.SeriesId&&item.SeriesPrimaryImageTag?url=apiClient.getScaledImageUrl(item.SeriesId,{type:"Primary",maxHeight:360,tag:item.SeriesPrimaryImageTag}):item.ParentPrimaryImageItemId&&item.ParentPrimaryImageTag&&(url=apiClient.getScaledImageUrl(item.ParentPrimaryImageItemId,{type:"Primary",maxHeight:360,tag:item.ParentPrimaryImageTag})),html+='
    ',editable&&(html+=""),detectRatio&&item.PrimaryImageAspectRatio&&(item.PrimaryImageAspectRatio>=1.48?shape="thumb":item.PrimaryImageAspectRatio>=.85&&item.PrimaryImageAspectRatio<=1.34&&(shape="square")),html+="",editable&&(html+="");var progressHtml=item.IsFolder||!item.UserData?"":indicators.getProgressBarHtml(item);html+='
    ',progressHtml&&(html+=progressHtml),html+="
    ",html+="
    ",elem.innerHTML=html,"thumb"==shape?(elem.classList.add("thumbDetailImageContainer"),elem.classList.remove("portraitDetailImageContainer"),elem.classList.remove("squareDetailImageContainer")):"square"==shape?(elem.classList.remove("thumbDetailImageContainer"),elem.classList.remove("portraitDetailImageContainer"),elem.classList.add("squareDetailImageContainer")):(elem.classList.remove("thumbDetailImageContainer"),elem.classList.add("portraitDetailImageContainer"),elem.classList.remove("squareDetailImageContainer")),url&&imageLoader.lazyImage(elem.querySelector("img"),url)}function renderImage(page,item,apiClient,user){renderDetailImage(page,page.querySelector(".detailImageContainer"),item,apiClient,user.Policy.IsAdministrator&&"Photo"!=item.MediaType,imageLoader,indicators)}function refreshDetailImageUserData(elem,item){elem.querySelector(".detailImageProgressContainer").innerHTML=indicators.getProgressBarHtml(item)}function refreshImage(page,item,user){refreshDetailImageUserData(page.querySelector(".detailImageContainer"),item)}function setPeopleHeader(page,item){"Audio"==item.MediaType||"MusicAlbum"==item.Type||"Book"==item.MediaType||"Photo"==item.MediaType?page.querySelector("#peopleHeader").innerHTML=globalize.translate("HeaderPeople"):page.querySelector("#peopleHeader").innerHTML=globalize.translate("HeaderCastAndCrew")}function renderNextUp(page,item,user){var section=page.querySelector(".nextUpSection");if("Series"!=item.Type)return void section.classList.add("hide");connectionManager.getApiClient(item.ServerId).getNextUpEpisodes({SeriesId:item.Id,UserId:user.Id}).then(function(result){result.Items.length?section.classList.remove("hide"):section.classList.add("hide");var html=cardBuilder.getCardsHtml({items:result.Items,shape:getThumbShape(!1),showTitle:!0,displayAsSpecial:"Season"==item.Type&&item.IndexNumber,overlayText:!1,centerText:!0,overlayPlayButton:!0}),itemsContainer=section.querySelector(".nextUpItems");itemsContainer.innerHTML=html,imageLoader.lazyChildren(itemsContainer)})}function setInitialCollapsibleState(page,item,apiClient,context,user){page.querySelector(".collectionItems").innerHTML="","Playlist"==item.Type?(page.querySelector("#childrenCollapsible").classList.remove("hide"),renderPlaylistItems(page,item,user)):"Studio"==item.Type||"Person"==item.Type||"Genre"==item.Type||"MusicGenre"==item.Type||"GameGenre"==item.Type||"MusicArtist"==item.Type?(page.querySelector("#childrenCollapsible").classList.remove("hide"),renderItemsByName(page,item,user)):item.IsFolder?("BoxSet"==item.Type&&page.querySelector("#childrenCollapsible").classList.add("hide"),renderChildren(page,item)):page.querySelector("#childrenCollapsible").classList.add("hide"),"Series"==item.Type&&renderSeriesSchedule(page,item,user),"Series"==item.Type?renderNextUp(page,item,user):page.querySelector(".nextUpSection").classList.add("hide"),item.MediaSources&&item.MediaSources.length&&(null==item.EnableMediaSourceDisplay?"Channel"!==item.SourceType:item.EnableMediaSourceDisplay)?renderMediaSources(page,user,item):page.querySelector(".audioVideoMediaInfo").classList.add("hide"),renderScenes(page,item),item.SpecialFeatureCount&&0!=item.SpecialFeatureCount&&"Series"!=item.Type?(page.querySelector("#specialsCollapsible").classList.remove("hide"),renderSpecials(page,item,user,6)):page.querySelector("#specialsCollapsible").classList.add("hide"),renderCast(page,item,context,enableScrollX()?null:12),item.PartCount&&item.PartCount>1?(page.querySelector("#additionalPartsCollapsible").classList.remove("hide"),renderAdditionalParts(page,item,user)):page.querySelector("#additionalPartsCollapsible").classList.add("hide"),"MusicAlbum"==item.Type?renderMusicVideos(page,item,user):page.querySelector("#musicVideosCollapsible").classList.add("hide")}function renderOverview(elems,item){for(var i=0,length=elems.length;i'+p.Name+""}).join(", "),elem=page.querySelector(".genres");elem.innerHTML=genres.length>1?globalize.translate("sharedcomponents#GenresValue",html):globalize.translate("sharedcomponents#GenreValue",html),genres.length?elem.classList.remove("hide"):elem.classList.add("hide")}function renderDirector(page,item,apiClient,context,isStatic){var directors=(item.People||[]).filter(function(p){return"Director"===p.Type}),html=directors.map(function(p){return''+p.Name+""}).join(", "),elem=page.querySelector(".directors");elem.innerHTML=directors.length>1?globalize.translate("sharedcomponents#DirectorsValue",html):globalize.translate("sharedcomponents#DirectorValue",html),directors.length?elem.classList.remove("hide"):elem.classList.add("hide")}function renderDetails(page,item,apiClient,context,isStatic){renderSimilarItems(page,item,context),renderMoreFromSeason(page,item,apiClient),renderMoreFromArtist(page,item,apiClient),renderDirector(page,item,apiClient,context,isStatic),renderGenres(page,item,apiClient,context,isStatic),renderChannelGuide(page,apiClient,item);var taglineElement=page.querySelector(".tagline");item.Taglines&&item.Taglines.length?(taglineElement.classList.remove("hide"),taglineElement.innerHTML=item.Taglines[0]):taglineElement.classList.add("hide");var overview=page.querySelector(".overview"),externalLinksElem=page.querySelector(".itemExternalLinks");"Season"!==item.Type&&"MusicAlbum"!==item.Type&&"MusicArtist"!==item.Type||(overview.classList.add("detailsHiddenOnMobile"),externalLinksElem.classList.add("detailsHiddenOnMobile")),renderOverview([overview],item);var i,length,itemMiscInfo=page.querySelectorAll(".itemMiscInfo-primary");for(i=0,length=itemMiscInfo.length;i'+item.Studios[0].Name+""}html?(html=("Ended"==item.Status?"Aired ":"Airs ")+html,seriesAirTime.innerHTML=html,seriesAirTime.classList.remove("hide")):seriesAirTime.classList.add("hide")}function renderTags(page,item){var itemTags=page.querySelector(".itemTags"),tagElements=[],tags=item.Tags||[];"Program"===item.Type&&(tags=[]);for(var i=0,length=tags.length;i',html+='

    '+datetime.toLocaleDateString(currentStartDate,{weekday:"long",month:"long",day:"numeric"})+"

    ",html+='
    '+listView.getListViewHtml({items:currentItems,enableUserDataButtons:!1,showParentTitle:!0,image:!1,showProgramTime:!0,mediaInfo:!1,parentTitleWithTitle:!0})+"
    "),currentStartDate=itemStartDate,currentItems=[]),currentItems.push(item)}currentItems.length&&(html+='
    ',html+='

    '+datetime.toLocaleDateString(currentStartDate,{weekday:"long",month:"long",day:"numeric"})+"

    ",html+='
    '+listView.getListViewHtml({items:currentItems,enableUserDataButtons:!1,showParentTitle:!0,image:!1,showProgramTime:!0,mediaInfo:!1,parentTitleWithTitle:!0})+"
    "),page.querySelector(".programGuide").innerHTML=html}function renderChannelGuide(page,apiClient,item){"TvChannel"===item.Type&&(page.querySelector(".programGuideSection").classList.remove("hide"),apiClient.getLiveTvPrograms({ChannelIds:item.Id,UserId:apiClient.getCurrentUserId(),HasAired:!1,SortBy:"StartDate",EnableTotalRecordCount:!1,EnableImages:!1,ImageTypeLimit:0,EnableUserData:!1}).then(function(result){renderProgramsForChannel(page,result)}))}function renderSeriesSchedule(page,item,user){var apiClient=connectionManager.getApiClient(item.ServerId);apiClient.getLiveTvPrograms({UserId:apiClient.getCurrentUserId(),HasAired:!1,SortBy:"StartDate",EnableTotalRecordCount:!1,EnableImages:!1,ImageTypeLimit:0,Limit:50,EnableUserData:!1,LibrarySeriesId:item.Id}).then(function(result){result.Items.length?page.querySelector("#seriesScheduleSection").classList.remove("hide"):page.querySelector("#seriesScheduleSection").classList.add("hide"),page.querySelector("#seriesScheduleList").innerHTML=listView.getListViewHtml({items:result.Items,enableUserDataButtons:!1,showParentTitle:!1,image:!1,showProgramDateTime:!0,mediaInfo:!1,showTitle:!0,moreButton:!1,action:"programdialog"}),loading.hide()})}function inferContext(item){return"Movie"===item.Type||"BoxSet"===item.Type?"movies":"Series"===item.Type||"Season"===item.Type||"Episode"===item.Type?"tvshows":"Game"===item.Type||"GameSystem"===item.Type?"games":"Game"===item.Type||"GameSystem"===item.Type?"games":"MusicArtist"===item.Type||"MusicAlbum"===item.Type||"Audio"===item.Type||"AudioBook"===item.Type?"music":"Program"===item.Type?"livetv":null}function filterItemsByCollectionItemType(items,typeInfo){return items.filter(function(item){return typeInfo.mediaType?item.MediaType==typeInfo.mediaType:item.Type==typeInfo.type})}function renderCollectionItems(page,parentItem,types,items){page.querySelector(".collectionItems").innerHTML="";var i,length;for(i=0,length=types.length;i0}).length});otherTypeItems.length&&renderCollectionItemType(page,parentItem,otherType,otherTypeItems),items.length||renderCollectionItemType(page,parentItem,{name:globalize.translate("HeaderItems")},items);var containers=page.querySelectorAll(".collectionItemsContainer"),notifyRefreshNeeded=function(){renderChildren(page,parentItem)};for(i=0,length=containers.length;i",html+="",html+='',html+="",html+='
    ';var shape="MusicAlbum"==type.type?getSquareShape(!1):getPortraitShape(!1);html+=cardBuilder.getCardsHtml({items:items,shape:shape,showTitle:!0,centerText:!0,lazy:!0,showDetailsMenu:!0,overlayMoreButton:!0,showAddToCollection:!1,showRemoveFromCollection:!0,collectionId:parentItem.Id}),html+="
    ",html+="";var collectionItems=page.querySelector(".collectionItems");collectionItems.insertAdjacentHTML("beforeend",html),imageLoader.lazyChildren(collectionItems),collectionItems.querySelector(".btnAddToCollection").addEventListener("click",function(){require(["alert"],function(alert){alert({text:globalize.translate("AddItemToCollectionHelp"),html:globalize.translate("AddItemToCollectionHelp")+'

    '+globalize.translate("ButtonLearnMore")+""})})})}function renderMusicVideos(page,item,user){connectionManager.getApiClient(item.ServerId).getItems(user.Id,{SortBy:"SortName",SortOrder:"Ascending",IncludeItemTypes:"MusicVideo",Recursive:!0,Fields:"PrimaryImageAspectRatio,BasicSyncInfo,CanDelete,MediaSourceCount",AlbumIds:item.Id}).then(function(result){if(result.Items.length){page.querySelector("#musicVideosCollapsible").classList.remove("hide");var musicVideosContent=page.querySelector(".musicVideosContent");musicVideosContent.innerHTML=getVideosHtml(result.Items,user),imageLoader.lazyChildren(musicVideosContent)}else page.querySelector("#musicVideosCollapsible").classList.add("hide")})}function renderAdditionalParts(page,item,user){connectionManager.getApiClient(item.ServerId).getAdditionalVideoParts(user.Id,item.Id).then(function(result){if(result.Items.length){page.querySelector("#additionalPartsCollapsible").classList.remove("hide");var additionalPartsContent=page.querySelector("#additionalPartsContent");additionalPartsContent.innerHTML=getVideosHtml(result.Items,user),imageLoader.lazyChildren(additionalPartsContent)}else page.querySelector("#additionalPartsCollapsible").classList.add("hide")})}function renderScenes(page,item){var chapters=item.Chapters||[];if(chapters.length&&!chapters[0].ImageTag&&(chapters=[]),chapters.length){page.querySelector("#scenesCollapsible").classList.remove("hide");var scenesContent=page.querySelector("#scenesContent");require(["chaptercardbuilder"],function(chaptercardbuilder){chaptercardbuilder.buildChapterCards(item,chapters,{itemsContainer:scenesContent,width:400,backdropShape:"overflowBackdrop",squareShape:"overflowSquare"})})}else page.querySelector("#scenesCollapsible").classList.add("hide")}function renderMediaSources(page,user,item){var html=item.MediaSources.map(function(v){return getMediaSourceHtml(user,item,v)}).join('
    ');item.MediaSources.length>1&&(html="
    "+html),page.querySelector("#mediaInfoContent").innerHTML=html,html?page.querySelector(".audioVideoMediaInfo").classList.remove("hide"):page.querySelector(".audioVideoMediaInfo").classList.add("hide")}function getMediaSourceHtml(user,item,version){var html="";version.Name&&item.MediaSources.length>1&&(html+='
    '+version.Name+"

    ");for(var i=0,length=version.MediaStreams.length;i';html+='

    '+globalize.translate("MediaInfoStreamType"+stream.Type)+"

    ";var attributes=[];stream.DisplayTitle&&attributes.push(createAttribute("Title",stream.DisplayTitle)),stream.Language&&"Video"!=stream.Type&&attributes.push(createAttribute(globalize.translate("MediaInfoLanguage"),stream.Language)),stream.Codec&&attributes.push(createAttribute(globalize.translate("MediaInfoCodec"),stream.Codec.toUpperCase())),stream.CodecTag&&attributes.push(createAttribute(globalize.translate("MediaInfoCodecTag"),stream.CodecTag)),null!=stream.IsAVC&&attributes.push(createAttribute("AVC",stream.IsAVC?"Yes":"No")),stream.Profile&&attributes.push(createAttribute(globalize.translate("MediaInfoProfile"),stream.Profile)),stream.Level&&attributes.push(createAttribute(globalize.translate("MediaInfoLevel"),stream.Level)),(stream.Width||stream.Height)&&attributes.push(createAttribute(globalize.translate("MediaInfoResolution"),stream.Width+"x"+stream.Height)),stream.AspectRatio&&"mjpeg"!=stream.Codec&&attributes.push(createAttribute(globalize.translate("MediaInfoAspectRatio"),stream.AspectRatio)),"Video"==stream.Type&&(null!=stream.IsAnamorphic&&attributes.push(createAttribute(globalize.translate("MediaInfoAnamorphic"),stream.IsAnamorphic?"Yes":"No")),attributes.push(createAttribute(globalize.translate("MediaInfoInterlaced"),stream.IsInterlaced?"Yes":"No"))),(stream.AverageFrameRate||stream.RealFrameRate)&&attributes.push(createAttribute(globalize.translate("MediaInfoFramerate"),stream.AverageFrameRate||stream.RealFrameRate)),stream.ChannelLayout&&attributes.push(createAttribute(globalize.translate("MediaInfoLayout"),stream.ChannelLayout)),stream.Channels&&attributes.push(createAttribute(globalize.translate("MediaInfoChannels"),stream.Channels+" ch")),stream.BitRate&&"mjpeg"!=stream.Codec&&attributes.push(createAttribute(globalize.translate("MediaInfoBitrate"),parseInt(stream.BitRate/1e3)+" kbps")),stream.SampleRate&&attributes.push(createAttribute(globalize.translate("MediaInfoSampleRate"),stream.SampleRate+" Hz")),stream.VideoRange&&"SDR"!==stream.VideoRange&&attributes.push(createAttribute(globalize.translate("sharedcomponents#VideoRange"),stream.VideoRange)),stream.ColorPrimaries&&attributes.push(createAttribute(globalize.translate("sharedcomponents#ColorPrimaries"),stream.ColorPrimaries)),stream.ColorSpace&&attributes.push(createAttribute(globalize.translate("sharedcomponents#ColorSpace"),stream.ColorSpace)),stream.ColorTransfer&&attributes.push(createAttribute(globalize.translate("sharedcomponents#ColorTransfer"),stream.ColorTransfer)),stream.BitDepth&&attributes.push(createAttribute(globalize.translate("MediaInfoBitDepth"),stream.BitDepth+" bit")),stream.PixelFormat&&attributes.push(createAttribute(globalize.translate("MediaInfoPixelFormat"),stream.PixelFormat)),stream.RefFrames&&attributes.push(createAttribute(globalize.translate("MediaInfoRefFrames"),stream.RefFrames)),stream.NalLengthSize&&attributes.push(createAttribute("NAL",stream.NalLengthSize)),"Video"!=stream.Type&&attributes.push(createAttribute(globalize.translate("MediaInfoDefault"),stream.IsDefault?"Yes":"No")),"Subtitle"==stream.Type&&(attributes.push(createAttribute(globalize.translate("MediaInfoForced"),stream.IsForced?"Yes":"No")),attributes.push(createAttribute(globalize.translate("MediaInfoExternal"),stream.IsExternal?"Yes":"No"))),"Video"==stream.Type&&version.Timestamp&&attributes.push(createAttribute(globalize.translate("MediaInfoTimestamp"),version.Timestamp)),html+=attributes.join("
    "),html+=""}}if(version.Container&&(html+='
    '+globalize.translate("MediaInfoContainer")+''+version.Container+"
    "),version.Formats&&version.Formats.length,version.Path&&"Http"!=version.Protocol&&user&&user.Policy.IsAdministrator&&(html+='
    '+globalize.translate("MediaInfoPath")+''+version.Path+"
    "),version.Size){var size=(version.Size/1048576).toFixed(0);html+='
    '+globalize.translate("MediaInfoSize")+''+size+" MB
    "}return html}function createAttribute(label,value){return''+label+''+value+""}function getVideosHtml(items,user,limit,moreButtonClass){var html=cardBuilder.getCardsHtml({items:items,shape:"auto",showTitle:!0,action:"play",overlayText:!1,centerText:!0,showRuntime:!0});return limit&&items.length>limit&&(html+='

    "),html}function renderSpecials(page,item,user,limit){connectionManager.getApiClient(item.ServerId).getSpecialFeatures(user.Id,item.Id).then(function(specials){var specialsContent=page.querySelector("#specialsContent");specialsContent.innerHTML=getVideosHtml(specials,user,limit,"moreSpecials"),imageLoader.lazyChildren(specialsContent)})}function renderCast(page,item,context,limit,isStatic){var people=(item.People||[]).filter(function(p){return"Director"!==p.Type});if(!people.length)return void page.querySelector("#castCollapsible").classList.add("hide");page.querySelector("#castCollapsible").classList.remove("hide");var castContent=page.querySelector("#castContent");enableScrollX()?(castContent.classList.add("scrollX"),limit=32):castContent.classList.add("vertical-wrap");var limitExceeded=limit&&people.length>limit;limitExceeded&&(people=people.slice(0),people.length=Math.min(limit,people.length)),require(["peoplecardbuilder"],function(peoplecardbuilder){peoplecardbuilder.buildPeopleCards(people,{itemsContainer:castContent,coverImage:!0,serverId:item.ServerId,width:160,shape:getPortraitShape()})});var morePeopleButton=page.querySelector(".morePeople");morePeopleButton&&(limitExceeded&&!enableScrollX()?morePeopleButton.classList.remove("hide"):morePeopleButton.classList.add("hide"))}function itemDetailPage(){var self=this;self.setInitialCollapsibleState=setInitialCollapsibleState,self.renderDetails=renderDetails,self.renderCast=renderCast,self.renderMediaSources=renderMediaSources}function bindAll(view,selector,eventName,fn){var i,length,elems=view.querySelectorAll(selector);for(i=0,length=elems.length;i" + v.Name + "" + }).join(""), mediaSources.length > 1 ? page.querySelector(".selectSourceContainer").classList.remove("hide") : page.querySelector(".selectSourceContainer").classList.add("hide"), (select.value !== currentValue || forceReload) && (renderVideoSelections(page, mediaSources), renderAudioSelections(page, mediaSources), renderSubtitleSelections(page, mediaSources)) + }) + } + + function renderVideoSelections(page, mediaSources) { + var mediaSourceId = page.querySelector(".selectSource").value, + mediaSource = mediaSources.filter(function(m) { + return m.Id === mediaSourceId + })[0], + tracks = mediaSource.MediaStreams.filter(function(m) { + return "Video" === m.Type + }), + select = page.querySelector(".selectVideo"); + select.setLabel(globalize.translate("sharedcomponents#LabelVideo")); + var selectedId = tracks.length ? tracks[0].Index : -1; + select.innerHTML = tracks.map(function(v) { + var selected = v.Index === selectedId ? " selected" : "", + titleParts = [], + resolutionText = mediaInfo.getResolutionText(v); + return resolutionText && titleParts.push(resolutionText), v.Codec && titleParts.push(v.Codec.toUpperCase()), '" + }).join(""), select.setAttribute("disabled", "disabled"), tracks.length ? page.querySelector(".selectVideoContainer").classList.remove("hide") : page.querySelector(".selectVideoContainer").classList.add("hide") + } + + function renderAudioSelections(page, mediaSources) { + var mediaSourceId = page.querySelector(".selectSource").value, + mediaSource = mediaSources.filter(function(m) { + return m.Id === mediaSourceId + })[0], + tracks = mediaSource.MediaStreams.filter(function(m) { + return "Audio" === m.Type + }), + select = page.querySelector(".selectAudio"); + select.setLabel(globalize.translate("sharedcomponents#LabelAudio")); + var selectedId = mediaSource.DefaultAudioStreamIndex; + select.innerHTML = tracks.map(function(v) { + var selected = v.Index === selectedId ? " selected" : ""; + return '" + }).join(""), tracks.length > 1 ? select.removeAttribute("disabled") : select.setAttribute("disabled", "disabled"), tracks.length ? page.querySelector(".selectAudioContainer").classList.remove("hide") : page.querySelector(".selectAudioContainer").classList.add("hide") + } + + function renderSubtitleSelections(page, mediaSources) { + var mediaSourceId = page.querySelector(".selectSource").value, + mediaSource = mediaSources.filter(function(m) { + return m.Id === mediaSourceId + })[0], + tracks = mediaSource.MediaStreams.filter(function(m) { + return "Subtitle" === m.Type + }), + select = page.querySelector(".selectSubtitles"); + select.setLabel(globalize.translate("sharedcomponents#LabelSubtitles")); + var selectedId = null == mediaSource.DefaultSubtitleStreamIndex ? -1 : mediaSource.DefaultSubtitleStreamIndex; + if (tracks.length) { + var selected = -1 === selectedId ? " selected" : ""; + select.innerHTML = '" + tracks.map(function(v) { + return selected = v.Index === selectedId ? " selected" : "", '" + }).join(""), page.querySelector(".selectSubtitlesContainer").classList.remove("hide") + } else select.innerHTML = "", page.querySelector(".selectSubtitlesContainer").classList.add("hide") + } + + function reloadPlayButtons(page, item) { + var canPlay = !1; + if ("Program" == item.Type) { + var now = new Date; + now >= datetime.parseISO8601Date(item.StartDate, !0) && now < datetime.parseISO8601Date(item.EndDate, !0) ? (hideAll(page, "btnPlay", !0), canPlay = !0) : hideAll(page, "btnPlay"), hideAll(page, "btnResume"), hideAll(page, "btnInstantMix"), hideAll(page, "btnShuffle") + } else if (playbackManager.canPlay(item)) { + hideAll(page, "btnPlay", !0); + var enableInstantMix = -1 !== ["Audio", "MusicAlbum", "MusicGenre", "MusicArtist"].indexOf(item.Type); + hideAll(page, "btnInstantMix", enableInstantMix); + var enableShuffle = item.IsFolder || -1 !== ["MusicAlbum", "MusicGenre", "MusicArtist"].indexOf(item.Type); + hideAll(page, "btnShuffle", enableShuffle), canPlay = !0, hideAll(page, "btnResume", item.UserData && item.UserData.PlaybackPositionTicks > 0) + } else hideAll(page, "btnPlay"), hideAll(page, "btnResume"), hideAll(page, "btnInstantMix"), hideAll(page, "btnShuffle"); + return canPlay + } + + function reloadUserDataButtons(page, item) { + var i, length, btnPlaystates = page.querySelectorAll(".btnPlaystate"); + for (i = 0, length = btnPlaystates.length; i < length; i++) { + var btnPlaystate = btnPlaystates[i]; + itemHelper.canMarkPlayed(item) ? (btnPlaystate.classList.remove("hide"), btnPlaystate.setItem(item)) : (btnPlaystate.classList.add("hide"), btnPlaystate.setItem(null)) + } + var btnUserRatings = page.querySelectorAll(".btnUserRating"); + for (i = 0, length = btnUserRatings.length; i < length; i++) { + var btnUserRating = btnUserRatings[i]; + itemHelper.canRate(item) ? (btnUserRating.classList.remove("hide"), btnUserRating.setItem(item)) : (btnUserRating.classList.add("hide"), btnUserRating.setItem(null)) + } + } + + function getArtistLinksHtml(artists, serverId, context) { + for (var html = [], i = 0, length = artists.length; i < length; i++) { + var artist = artists[i], + href = appRouter.getRouteUrl(artist, { + context: context, + itemType: "MusicArtist", + serverId: serverId + }); + html.push('' + artist.Name + "") + } + return html = html.join(" / ") + } + + function renderName(item, container, isStatic, context) { + var parentRoute, parentNameHtml = [], + parentNameLast = !1; + item.AlbumArtists ? (parentNameHtml.push(getArtistLinksHtml(item.AlbumArtists, item.ServerId, context)), parentNameLast = !0) : item.ArtistItems && item.ArtistItems.length && "MusicVideo" === item.Type ? (parentNameHtml.push(getArtistLinksHtml(item.ArtistItems, item.ServerId, context)), parentNameLast = !0) : item.SeriesName && "Episode" === item.Type ? (parentRoute = appRouter.getRouteUrl({ + Id: item.SeriesId, + Name: item.SeriesName, + Type: "Series", + IsFolder: !0, + ServerId: item.ServerId + }, { + context: context + }), parentNameHtml.push('' + item.SeriesName + "")) : (item.IsSeries || item.EpisodeTitle) && parentNameHtml.push(item.Name), item.SeriesName && "Season" === item.Type ? (parentRoute = appRouter.getRouteUrl({ + Id: item.SeriesId, + Name: item.SeriesName, + Type: "Series", + IsFolder: !0, + ServerId: item.ServerId + }, { + context: context + }), parentNameHtml.push('' + item.SeriesName + "")) : null != item.ParentIndexNumber && "Episode" === item.Type ? (parentRoute = appRouter.getRouteUrl({ + Id: item.SeasonId, + Name: item.SeasonName, + Type: "Season", + IsFolder: !0, + ServerId: item.ServerId + }, { + context: context + }), parentNameHtml.push('' + item.SeasonName + "")) : null != item.ParentIndexNumber && item.IsSeries ? parentNameHtml.push(item.SeasonName || "S" + item.ParentIndexNumber) : item.Album && item.AlbumId && ("MusicVideo" === item.Type || "Audio" === item.Type) ? (parentRoute = appRouter.getRouteUrl({ + Id: item.AlbumId, + Name: item.Album, + Type: "MusicAlbum", + IsFolder: !0, + ServerId: item.ServerId + }, { + context: context + }), parentNameHtml.push('' + item.Album + "")) : item.Album && parentNameHtml.push(item.Album); + var html = ""; + parentNameHtml.length && (html = parentNameLast ? '

    ' + parentNameHtml.join(" - ") + "

    " : '

    ' + parentNameHtml.join(" - ") + "

    "); + var name = itemHelper.getDisplayName(item, { + includeParentInfo: !1 + }); + html && !parentNameLast ? html += '

    ' + name + "

    " : html = parentNameLast ? '

    ' + name + "

    " + html : '

    ' + name + "

    " + html, container.innerHTML = html, html.length ? container.classList.remove("hide") : container.classList.add("hide") + } + + function setTrailerButtonVisibility(page, item) { + (item.LocalTrailerCount || item.RemoteTrailers && item.RemoteTrailers.length) && -1 !== playbackManager.getSupportedCommands().indexOf("PlayTrailers") ? hideAll(page, "btnPlayTrailer", !0) : hideAll(page, "btnPlayTrailer") + } + + function renderDetailPageBackdrop(page, item, apiClient) { + var imgUrl, screenWidth = screen.availWidth, + hasbackdrop = !1, + itemBackdropElement = page.querySelector("#itemBackdrop"), + usePrimaryImage = "Video" === item.MediaType && "Movie" !== item.Type && "Trailer" !== item.Type || item.MediaType && "Video" !== item.MediaType; + return "Program" === item.Type && item.ImageTags && item.ImageTags.Thumb ? (imgUrl = apiClient.getScaledImageUrl(item.Id, { + type: "Thumb", + index: 0, + maxWidth: screenWidth, + tag: item.ImageTags.Thumb + }), itemBackdropElement.classList.remove("noBackdrop"), imageLoader.lazyImage(itemBackdropElement, imgUrl, !1), hasbackdrop = !0) : usePrimaryImage && item.ImageTags && item.ImageTags.Primary ? (imgUrl = apiClient.getScaledImageUrl(item.Id, { + type: "Primary", + index: 0, + maxWidth: screenWidth, + tag: item.ImageTags.Primary + }), itemBackdropElement.classList.remove("noBackdrop"), imageLoader.lazyImage(itemBackdropElement, imgUrl, !1), hasbackdrop = !0) : item.BackdropImageTags && item.BackdropImageTags.length ? (imgUrl = apiClient.getScaledImageUrl(item.Id, { + type: "Backdrop", + index: 0, + maxWidth: screenWidth, + tag: item.BackdropImageTags[0] + }), itemBackdropElement.classList.remove("noBackdrop"), imageLoader.lazyImage(itemBackdropElement, imgUrl, !1), hasbackdrop = !0) : item.ParentBackdropItemId && item.ParentBackdropImageTags && item.ParentBackdropImageTags.length ? (imgUrl = apiClient.getScaledImageUrl(item.ParentBackdropItemId, { + type: "Backdrop", + index: 0, + tag: item.ParentBackdropImageTags[0], + maxWidth: screenWidth + }), itemBackdropElement.classList.remove("noBackdrop"), imageLoader.lazyImage(itemBackdropElement, imgUrl, !1), hasbackdrop = !0) : item.ImageTags && item.ImageTags.Thumb ? (imgUrl = apiClient.getScaledImageUrl(item.Id, { + type: "Thumb", + index: 0, + maxWidth: screenWidth, + tag: item.ImageTags.Thumb + }), itemBackdropElement.classList.remove("noBackdrop"), imageLoader.lazyImage(itemBackdropElement, imgUrl, !1), hasbackdrop = !0) : (itemBackdropElement.classList.add("noBackdrop"), itemBackdropElement.style.backgroundImage = ""), hasbackdrop + } + + function reloadFromItem(instance, page, params, item, user) { + var context = params.context; + renderName(item, page.querySelector(".nameContainer"), !1, context); + var apiClient = connectionManager.getApiClient(item.ServerId); + renderSeriesTimerEditor(page, item, apiClient, user), renderTimerEditor(page, item, apiClient, user), renderImage(page, item, apiClient, user), renderLogo(page, item, apiClient), setTitle(item, apiClient), setInitialCollapsibleState(page, item, apiClient, context, user), renderDetails(page, item, apiClient, context), renderTrackSelections(page, instance, item), dom.getWindowSize().innerWidth >= 1e3 ? backdrop.setBackdrops([item]) : backdrop.clear(), renderDetailPageBackdrop(page, item, apiClient); + var canPlay = reloadPlayButtons(page, item); + (item.LocalTrailerCount || item.RemoteTrailers && item.RemoteTrailers.length) && -1 !== playbackManager.getSupportedCommands().indexOf("PlayTrailers") ? hideAll(page, "btnPlayTrailer", !0) : hideAll(page, "btnPlayTrailer"), setTrailerButtonVisibility(page, item), item.CanDelete && !item.IsFolder ? hideAll(page, "btnDeleteItem", !0) : hideAll(page, "btnDeleteItem"), renderSyncLocalContainer(page, params, user, item), "Program" !== item.Type || canPlay ? hideAll(page, "mainDetailButtons", !0) : hideAll(page, "mainDetailButtons"), showRecordingFields(instance, page, item, user); + var groupedVersions = (item.MediaSources || []).filter(function(g) { + return "Grouping" == g.Type + }); + user.Policy.IsAdministrator && groupedVersions.length ? page.querySelector(".splitVersionContainer").classList.remove("hide") : page.querySelector(".splitVersionContainer").classList.add("hide"), itemContextMenu.getCommands(getContextMenuOptions(item, user)).length ? hideAll(page, "btnMoreCommands", !0) : hideAll(page, "btnMoreCommands"); + var itemBirthday = page.querySelector("#itemBirthday"); + if ("Person" == item.Type && item.PremiereDate) try { + var birthday = datetime.parseISO8601Date(item.PremiereDate, !0).toDateString(); + itemBirthday.classList.remove("hide"), itemBirthday.innerHTML = globalize.translate("BirthDateValue").replace("{0}", birthday) + } catch (err) { + itemBirthday.classList.add("hide") + } else itemBirthday.classList.add("hide"); + var itemDeathDate = page.querySelector("#itemDeathDate"); + if ("Person" == item.Type && item.EndDate) try { + var deathday = datetime.parseISO8601Date(item.EndDate, !0).toDateString(); + itemDeathDate.classList.remove("hide"), itemDeathDate.innerHTML = globalize.translate("DeathDateValue").replace("{0}", deathday) + } catch (err) { + itemDeathDate.classList.add("hide") + } + var itemBirthLocation = page.querySelector("#itemBirthLocation"); + if ("Person" == item.Type && item.ProductionLocations && item.ProductionLocations.length) { + var gmap = '' + item.ProductionLocations[0] + ""; + itemBirthLocation.classList.remove("hide"), itemBirthLocation.innerHTML = globalize.translate("BirthPlaceValue").replace("{0}", gmap) + } else itemBirthLocation.classList.add("hide"); + setPeopleHeader(page, item), loading.hide() + } + + function logoImageUrl(item, apiClient, options) { + return options = options || {}, options.type = "Logo", item.ImageTags && item.ImageTags.Logo ? (options.tag = item.ImageTags.Logo, apiClient.getScaledImageUrl(item.Id, options)) : item.ParentLogoImageTag ? (options.tag = item.ParentLogoImageTag, apiClient.getScaledImageUrl(item.ParentLogoItemId, options)) : null + } + + function setTitle(item, apiClient) { + var url = logoImageUrl(item, apiClient, {}); + if (url = null) { + var pageTitle = document.querySelector(".pageTitle"); + pageTitle.style.backgroundImage = "url('" + url + "')", pageTitle.classList.add("pageTitleWithLogo"), pageTitle.innerHTML = "" + } else Emby.Page.setTitle("") + } + + function renderLogo(page, item, apiClient) { + var url = logoImageUrl(item, apiClient, { + maxWidth: 300 + }), + detailLogo = page.querySelector(".detailLogo"); + url ? (detailLogo.classList.remove("hide"), detailLogo.classList.add("lazy"), detailLogo.setAttribute("data-src", url), imageLoader.lazyImage(detailLogo)) : detailLogo.classList.add("hide") + } + + function showRecordingFields(instance, page, item, user) { + if (!instance.currentRecordingFields) { + var recordingFieldsElement = page.querySelector(".recordingFields"); + "Program" == item.Type && user.Policy.EnableLiveTvManagement ? require(["recordingFields"], function(recordingFields) { + instance.currentRecordingFields = new recordingFields({ + parent: recordingFieldsElement, + programId: item.Id, + serverId: item.ServerId + }), recordingFieldsElement.classList.remove("hide") + }) : (recordingFieldsElement.classList.add("hide"), recordingFieldsElement.innerHTML = "") + } + } + + function renderLinks(linksElem, item) { + var html = []; + if (item.DateCreated && itemHelper.enableDateAddedDisplay(item)) { + var dateCreated = datetime.parseISO8601Date(item.DateCreated); + html.push(globalize.translate("sharedcomponents#AddedOnValue", datetime.toLocaleDateString(dateCreated) + " " + datetime.getDisplayTime(dateCreated))) + } + var links = []; + if (!layoutManager.tv && (item.HomePageUrl && links.push('' + globalize.translate("ButtonWebsite") + ""), item.ExternalUrls)) + for (var i = 0, length = item.ExternalUrls.length; i < length; i++) { + var url = item.ExternalUrls[i]; + links.push('' + url.Name + "") + } + links.length && html.push(globalize.translate("sharedcomponents#LinksValue", links.join(", "))), linksElem.innerHTML = html.join(", "), html.length ? linksElem.classList.remove("hide") : linksElem.classList.add("hide") + } + + function renderDetailImage(page, elem, item, apiClient, editable, imageLoader, indicators) { + "SeriesTimer" !== item.Type && "Program" !== item.Type || (editable = !1), "Person" !== item.Type ? (elem.classList.add("detailimg-hidemobile"), page.querySelector(".detailPageContent").classList.add("detailPageContent-nodetailimg")) : page.querySelector(".detailPageContent").classList.remove("detailPageContent-nodetailimg"); + var imageTags = item.ImageTags || {}; + item.PrimaryImageTag && (imageTags.Primary = item.PrimaryImageTag); + var url, html = "", + shape = "portrait", + detectRatio = !1; + imageTags.Primary ? (url = apiClient.getScaledImageUrl(item.Id, { + type: "Primary", + maxHeight: 360, + tag: item.ImageTags.Primary + }), detectRatio = !0) : item.BackdropImageTags && item.BackdropImageTags.length ? (url = apiClient.getScaledImageUrl(item.Id, { + type: "Backdrop", + maxHeight: 360, + tag: item.BackdropImageTags[0] + }), shape = "thumb") : imageTags.Thumb ? (url = apiClient.getScaledImageUrl(item.Id, { + type: "Thumb", + maxHeight: 360, + tag: item.ImageTags.Thumb + }), shape = "thumb") : imageTags.Disc ? (url = apiClient.getScaledImageUrl(item.Id, { + type: "Disc", + maxHeight: 360, + tag: item.ImageTags.Disc + }), shape = "square") : item.AlbumId && item.AlbumPrimaryImageTag ? (url = apiClient.getScaledImageUrl(item.AlbumId, { + type: "Primary", + maxHeight: 360, + tag: item.AlbumPrimaryImageTag + }), shape = "square") : item.SeriesId && item.SeriesPrimaryImageTag ? url = apiClient.getScaledImageUrl(item.SeriesId, { + type: "Primary", + maxHeight: 360, + tag: item.SeriesPrimaryImageTag + }) : item.ParentPrimaryImageItemId && item.ParentPrimaryImageTag && (url = apiClient.getScaledImageUrl(item.ParentPrimaryImageItemId, { + type: "Primary", + maxHeight: 360, + tag: item.ParentPrimaryImageTag + })), html += '
    ', editable && (html += ""), detectRatio && item.PrimaryImageAspectRatio && (item.PrimaryImageAspectRatio >= 1.48 ? shape = "thumb" : item.PrimaryImageAspectRatio >= .85 && item.PrimaryImageAspectRatio <= 1.34 && (shape = "square")), html += "", editable && (html += ""); + var progressHtml = item.IsFolder || !item.UserData ? "" : indicators.getProgressBarHtml(item); + html += '
    ', progressHtml && (html += progressHtml), html += "
    ", html += "
    ", elem.innerHTML = html, "thumb" == shape ? (elem.classList.add("thumbDetailImageContainer"), elem.classList.remove("portraitDetailImageContainer"), elem.classList.remove("squareDetailImageContainer")) : "square" == shape ? (elem.classList.remove("thumbDetailImageContainer"), elem.classList.remove("portraitDetailImageContainer"), elem.classList.add("squareDetailImageContainer")) : (elem.classList.remove("thumbDetailImageContainer"), elem.classList.add("portraitDetailImageContainer"), elem.classList.remove("squareDetailImageContainer")), url && imageLoader.lazyImage(elem.querySelector("img"), url) + } + + function renderImage(page, item, apiClient, user) { + renderDetailImage(page, page.querySelector(".detailImageContainer"), item, apiClient, user.Policy.IsAdministrator && "Photo" != item.MediaType, imageLoader, indicators) + } + + function refreshDetailImageUserData(elem, item) { + elem.querySelector(".detailImageProgressContainer").innerHTML = indicators.getProgressBarHtml(item) + } + + function refreshImage(page, item, user) { + refreshDetailImageUserData(page.querySelector(".detailImageContainer"), item) + } + + function setPeopleHeader(page, item) { + "Audio" == item.MediaType || "MusicAlbum" == item.Type || "Book" == item.MediaType || "Photo" == item.MediaType ? page.querySelector("#peopleHeader").innerHTML = globalize.translate("HeaderPeople") : page.querySelector("#peopleHeader").innerHTML = globalize.translate("HeaderCastAndCrew") + } + + function renderNextUp(page, item, user) { + var section = page.querySelector(".nextUpSection"); + if ("Series" != item.Type) return void section.classList.add("hide"); + connectionManager.getApiClient(item.ServerId).getNextUpEpisodes({ + SeriesId: item.Id, + UserId: user.Id + }).then(function(result) { + result.Items.length ? section.classList.remove("hide") : section.classList.add("hide"); + var html = cardBuilder.getCardsHtml({ + items: result.Items, + shape: getThumbShape(!1), + showTitle: !0, + displayAsSpecial: "Season" == item.Type && item.IndexNumber, + overlayText: !1, + centerText: !0, + overlayPlayButton: !0 + }), + itemsContainer = section.querySelector(".nextUpItems"); + itemsContainer.innerHTML = html, imageLoader.lazyChildren(itemsContainer) + }) + } + + function setInitialCollapsibleState(page, item, apiClient, context, user) { + page.querySelector(".collectionItems").innerHTML = "", "Playlist" == item.Type ? (page.querySelector("#childrenCollapsible").classList.remove("hide"), renderPlaylistItems(page, item, user)) : "Studio" == item.Type || "Person" == item.Type || "Genre" == item.Type || "MusicGenre" == item.Type || "GameGenre" == item.Type || "MusicArtist" == item.Type ? (page.querySelector("#childrenCollapsible").classList.remove("hide"), renderItemsByName(page, item, user)) : item.IsFolder ? ("BoxSet" == item.Type && page.querySelector("#childrenCollapsible").classList.add("hide"), renderChildren(page, item)) : page.querySelector("#childrenCollapsible").classList.add("hide"), "Series" == item.Type && renderSeriesSchedule(page, item, user), "Series" == item.Type ? renderNextUp(page, item, user) : page.querySelector(".nextUpSection").classList.add("hide"), item.MediaSources && item.MediaSources.length && (null == item.EnableMediaSourceDisplay ? "Channel" !== item.SourceType : item.EnableMediaSourceDisplay) ? renderMediaSources(page, user, item) : page.querySelector(".audioVideoMediaInfo").classList.add("hide"), renderScenes(page, item), item.SpecialFeatureCount && 0 != item.SpecialFeatureCount && "Series" != item.Type ? (page.querySelector("#specialsCollapsible").classList.remove("hide"), renderSpecials(page, item, user, 6)) : page.querySelector("#specialsCollapsible").classList.add("hide"), renderCast(page, item, context, enableScrollX() ? null : 12), item.PartCount && item.PartCount > 1 ? (page.querySelector("#additionalPartsCollapsible").classList.remove("hide"), renderAdditionalParts(page, item, user)) : page.querySelector("#additionalPartsCollapsible").classList.add("hide"), "MusicAlbum" == item.Type ? renderMusicVideos(page, item, user) : page.querySelector("#musicVideosCollapsible").classList.add("hide") + } + + function renderOverview(elems, item) { + for (var i = 0, length = elems.length; i < length; i++) { + var elem = elems[i], + overview = item.Overview || ""; + if (overview) { + elem.innerHTML = overview, elem.classList.remove("hide"); + for (var anchors = elem.querySelectorAll("a"), j = 0, length2 = anchors.length; j < length2; j++) anchors[j].setAttribute("target", "_blank") + } else elem.innerHTML = "", elem.classList.add("hide") + } + } + + function renderGenres(page, item, apiClient, context, isStatic) { + context = context || inferContext(item); + var type, genres = item.GenreItems || []; + switch (context) { + case "games": + type = "GameGenre"; + break; + case "music": + type = "MusicGenre"; + break; + default: + type = "Genre" + } + var html = genres.map(function(p) { + return '' + p.Name + "" + }).join(", "), + elem = page.querySelector(".genres"); + elem.innerHTML = genres.length > 1 ? globalize.translate("sharedcomponents#GenresValue", html) : globalize.translate("sharedcomponents#GenreValue", html), genres.length ? elem.classList.remove("hide") : elem.classList.add("hide") + } + + function renderDirector(page, item, apiClient, context, isStatic) { + var directors = (item.People || []).filter(function(p) { + return "Director" === p.Type + }), + html = directors.map(function(p) { + return '' + p.Name + "" + }).join(", "), + elem = page.querySelector(".directors"); + elem.innerHTML = directors.length > 1 ? globalize.translate("sharedcomponents#DirectorsValue", html) : globalize.translate("sharedcomponents#DirectorValue", html), directors.length ? elem.classList.remove("hide") : elem.classList.add("hide") + } + + function renderDetails(page, item, apiClient, context, isStatic) { + renderSimilarItems(page, item, context), renderMoreFromSeason(page, item, apiClient), renderMoreFromArtist(page, item, apiClient), renderDirector(page, item, apiClient, context, isStatic), renderGenres(page, item, apiClient, context, isStatic), renderChannelGuide(page, apiClient, item); + var taglineElement = page.querySelector(".tagline"); + item.Taglines && item.Taglines.length ? (taglineElement.classList.remove("hide"), taglineElement.innerHTML = item.Taglines[0]) : taglineElement.classList.add("hide"); + var overview = page.querySelector(".overview"), + externalLinksElem = page.querySelector(".itemExternalLinks"); + "Season" !== item.Type && "MusicAlbum" !== item.Type && "MusicArtist" !== item.Type || (overview.classList.add("detailsHiddenOnMobile"), externalLinksElem.classList.add("detailsHiddenOnMobile")), renderOverview([overview], item); + var i, length, itemMiscInfo = page.querySelectorAll(".itemMiscInfo-primary"); + for (i = 0, length = itemMiscInfo.length; i < length; i++) mediaInfo.fillPrimaryMediaInfo(itemMiscInfo[i], item, { + interactive: !0, + episodeTitle: !1, + subtitles: !1 + }), itemMiscInfo[i].innerHTML && "SeriesTimer" !== item.Type ? itemMiscInfo[i].classList.remove("hide") : itemMiscInfo[i].classList.add("hide"); + for (itemMiscInfo = page.querySelectorAll(".itemMiscInfo-secondary"), i = 0, length = itemMiscInfo.length; i < length; i++) mediaInfo.fillSecondaryMediaInfo(itemMiscInfo[i], item, { + interactive: !0 + }), itemMiscInfo[i].innerHTML ? itemMiscInfo[i].classList.remove("hide") : itemMiscInfo[i].classList.add("hide"); + reloadUserDataButtons(page, item), renderLinks(externalLinksElem, item), renderTags(page, item), renderSeriesAirTime(page, item, isStatic) + } + + function enableScrollX() { + return browser.mobile && screen.availWidth <= 1e3 + } + + function getPortraitShape(scrollX) { + return null == scrollX && (scrollX = enableScrollX()), scrollX ? "overflowPortrait" : "portrait" + } + + function getSquareShape(scrollX) { + return null == scrollX && (scrollX = enableScrollX()), scrollX ? "overflowSquare" : "square" + } + + function getThumbShape(scrollX) { + return null == scrollX && (scrollX = enableScrollX()), scrollX ? "overflowBackdrop" : "backdrop" + } + + function renderMoreFromSeason(view, item, apiClient) { + var section = view.querySelector(".moreFromSeasonSection"); + if (section) { + if ("Episode" !== item.Type || !item.SeasonId || !item.SeriesId) return void section.classList.add("hide"); + var userId = apiClient.getCurrentUserId(); + apiClient.getEpisodes(item.SeriesId, { + SeasonId: item.SeasonId, + UserId: userId, + Fields: "ItemCounts,PrimaryImageAspectRatio,BasicSyncInfo,CanDelete,MediaSourceCount" + }).then(function(result) { + if (result.Items.length < 2) return void section.classList.add("hide"); + section.classList.remove("hide"), section.querySelector("h2").innerHTML = globalize.translate("MoreFromValue", item.SeasonName); + var itemsContainer = section.querySelector(".itemsContainer"); + cardBuilder.buildCards(result.Items, { + parentContainer: section, + itemsContainer: itemsContainer, + shape: "autooverflow", + sectionTitleTagName: "h2", + scalable: !0, + showTitle: !0, + overlayText: !1, + centerText: !0, + includeParentInfoInTitle: !1, + allowBottomPadding: !1 + }); + var card = itemsContainer.querySelector('.card[data-id="' + item.Id + '"]'); + card && setTimeout(function() { + section.querySelector(".emby-scroller").toStart(card.previousSibling || card, !0) + }, 100) + }) + } + } + + function renderMoreFromArtist(view, item, apiClient) { + var section = view.querySelector(".moreFromArtistSection"); + if (section) { + if ("MusicArtist" === item.Type) { + if (!apiClient.isMinServerVersion("3.4.1.19")) return void section.classList.add("hide") + } else if ("MusicAlbum" !== item.Type || !item.AlbumArtists || !item.AlbumArtists.length) return void section.classList.add("hide"); + var query = { + IncludeItemTypes: "MusicAlbum", + Recursive: !0, + ExcludeItemIds: item.Id, + SortBy: "ProductionYear,SortName", + SortOrder: "Descending" + }; + "MusicArtist" === item.Type ? query.ContributingArtistIds = item.Id : apiClient.isMinServerVersion("3.4.1.18") ? query.AlbumArtistIds = item.AlbumArtists[0].Id : query.ArtistIds = item.AlbumArtists[0].Id, apiClient.getItems(apiClient.getCurrentUserId(), query).then(function(result) { + if (!result.Items.length) return void section.classList.add("hide"); + section.classList.remove("hide"), "MusicArtist" === item.Type ? section.querySelector("h2").innerHTML = globalize.translate("sharedcomponents#HeaderAppearsOn") : section.querySelector("h2").innerHTML = globalize.translate("MoreFromValue", item.AlbumArtists[0].Name), cardBuilder.buildCards(result.Items, { + parentContainer: section, + itemsContainer: section.querySelector(".itemsContainer"), + shape: "autooverflow", + sectionTitleTagName: "h2", + scalable: !0, + coverImage: "MusicArtist" === item.Type || "MusicAlbum" === item.Type, + showTitle: !0, + showParentTitle: !1, + centerText: !0, + overlayText: !1, + overlayPlayButton: !0, + showYear: !0 + }) + }) + } + } + + function renderSimilarItems(page, item, context) { + var similarCollapsible = page.querySelector("#similarCollapsible"); + if (similarCollapsible) { + if ("Movie" != item.Type && "Trailer" != item.Type && "Series" != item.Type && "Program" != item.Type && "Recording" != item.Type && "Game" != item.Type && "MusicAlbum" != item.Type && "MusicArtist" != item.Type && "Playlist" != item.Type) return void similarCollapsible.classList.add("hide"); + similarCollapsible.classList.remove("hide"); + var apiClient = connectionManager.getApiClient(item.ServerId), + options = { + userId: apiClient.getCurrentUserId(), + limit: 12, + fields: "PrimaryImageAspectRatio,UserData,CanDelete" + }; + "MusicAlbum" == item.Type && item.AlbumArtists && item.AlbumArtists.length && (options.ExcludeArtistIds = item.AlbumArtists[0].Id), apiClient.getSimilarItems(item.Id, options).then(function(result) { + if (!result.Items.length) return void similarCollapsible.classList.add("hide"); + similarCollapsible.classList.remove("hide"); + var html = ""; + html += cardBuilder.getCardsHtml({ + items: result.Items, + shape: "autooverflow", + showParentTitle: "MusicAlbum" == item.Type, + centerText: !0, + showTitle: !0, + context: context, + lazy: !0, + showDetailsMenu: !0, + coverImage: "MusicAlbum" == item.Type || "MusicArtist" == item.Type, + overlayPlayButton: !0, + overlayText: !1, + showYear: "Movie" === item.Type || "Trailer" === item.Type + }); + var similarContent = similarCollapsible.querySelector(".similarContent"); + similarContent.innerHTML = html, imageLoader.lazyChildren(similarContent) + }) + } + } + + function renderSeriesAirTime(page, item, isStatic) { + var seriesAirTime = page.querySelector("#seriesAirTime"); + if ("Series" != item.Type) return void seriesAirTime.classList.add("hide"); + var html = ""; + if (item.AirDays && item.AirDays.length && (html += 7 == item.AirDays.length ? "daily" : item.AirDays.map(function(a) { + return a + "s" + }).join(",")), item.AirTime && (html += " at " + item.AirTime), item.Studios.length) + if (isStatic) html += " on " + item.Studios[0].Name; + else { + var context = inferContext(item), + href = appRouter.getRouteUrl(item.Studios[0], { + context: context, + itemType: "Studio", + serverId: item.ServerId + }); + html += ' on ' + item.Studios[0].Name + "" + } html ? (html = ("Ended" == item.Status ? "Aired " : "Airs ") + html, seriesAirTime.innerHTML = html, seriesAirTime.classList.remove("hide")) : seriesAirTime.classList.add("hide") + } + + function renderTags(page, item) { + var itemTags = page.querySelector(".itemTags"), + tagElements = [], + tags = item.Tags || []; + "Program" === item.Type && (tags = []); + for (var i = 0, length = tags.length; i < length; i++) tagElements.push(tags[i]); + tagElements.length ? (itemTags.innerHTML = globalize.translate("sharedcomponents#TagsValue", tagElements.join(", ")), itemTags.classList.remove("hide")) : (itemTags.innerHTML = "", itemTags.classList.add("hide")) + } + + function renderChildren(page, item) { + var fields = "ItemCounts,PrimaryImageAspectRatio,BasicSyncInfo,CanDelete,MediaSourceCount", + query = { + ParentId: item.Id, + Fields: fields + }; + "BoxSet" !== item.Type && (query.SortBy = "SortName"); + var promise, apiClient = connectionManager.getApiClient(item.ServerId), + userId = apiClient.getCurrentUserId(); + "Series" == item.Type ? promise = apiClient.getSeasons(item.Id, { + userId: userId, + Fields: fields + }) : "Season" == item.Type ? (fields += ",Overview", promise = apiClient.getEpisodes(item.SeriesId, { + seasonId: item.Id, + userId: userId, + Fields: fields + })) : "MusicAlbum" == item.Type || "MusicArtist" == item.Type && (query.SortBy = "ProductionYear,SortName"), promise = promise || apiClient.getItems(apiClient.getCurrentUserId(), query), promise.then(function(result) { + var html = "", + scrollX = !1, + isList = !1, + childrenItemsContainer = page.querySelector(".childrenItemsContainer"); + if ("MusicAlbum" == item.Type) html = listView.getListViewHtml({ + items: result.Items, + smallIcon: !0, + showIndex: !0, + index: "disc", + showIndexNumberLeft: !0, + playFromHere: !0, + action: "playallfromhere", + image: !1, + artist: "auto", + containerAlbumArtists: item.AlbumArtists, + addToListButton: !0 + }), isList = !0; + else if ("Series" == item.Type) scrollX = enableScrollX(), html = cardBuilder.getCardsHtml({ + items: result.Items, + shape: getPortraitShape(), + showTitle: !0, + centerText: !0, + lazy: !0, + overlayPlayButton: !0, + allowBottomPadding: !scrollX + }); + else if ("Season" == item.Type || "Episode" == item.Type) { + if ("Episode" === item.Type || (isList = !0), scrollX = "Episode" == item.Type, result.Items.length < 2 && "Episode" === item.Type) return; + "Episode" === item.Type ? html = cardBuilder.getCardsHtml({ + items: result.Items, + shape: getThumbShape(scrollX), + showTitle: !0, + displayAsSpecial: "Season" == item.Type && item.IndexNumber, + playFromHere: !0, + overlayText: !0, + lazy: !0, + showDetailsMenu: !0, + overlayPlayButton: !0, + allowBottomPadding: !scrollX, + includeParentInfoInTitle: !1 + }) : "Season" === item.Type && (html = listView.getListViewHtml({ + items: result.Items, + showIndexNumber: !1, + enableOverview: !0, + imageSize: "large", + enableSideMediaInfo: !1, + highlight: !1, + action: "none", + infoButton: !0, + imagePlayButton: !0, + includeParentInfoInTitle: !1 + })) + } else "GameSystem" == item.Type && (html = cardBuilder.getCardsHtml({ + items: result.Items, + shape: "auto", + showTitle: !0, + centerText: !0, + lazy: !0, + showDetailsMenu: !0 + })); + if ("BoxSet" !== item.Type && page.querySelector("#childrenCollapsible").classList.remove("hide"), scrollX ? (childrenItemsContainer.classList.add("scrollX"), childrenItemsContainer.classList.add("hiddenScrollX"), childrenItemsContainer.classList.remove("vertical-wrap"), childrenItemsContainer.classList.remove("vertical-list")) : (childrenItemsContainer.classList.remove("scrollX"), childrenItemsContainer.classList.remove("hiddenScrollX"), childrenItemsContainer.classList.remove("smoothScrollX"), isList ? (childrenItemsContainer.classList.add("vertical-list"), childrenItemsContainer.classList.remove("vertical-wrap")) : (childrenItemsContainer.classList.add("vertical-wrap"), childrenItemsContainer.classList.remove("vertical-list"))), childrenItemsContainer.innerHTML = html, imageLoader.lazyChildren(childrenItemsContainer), "BoxSet" == item.Type) { + var collectionItemTypes = [{ + name: globalize.translate("HeaderVideos"), + mediaType: "Video" + }, { + name: globalize.translate("HeaderSeries"), + type: "Series" + }, { + name: globalize.translate("HeaderAlbums"), + type: "MusicAlbum" + }, { + name: globalize.translate("HeaderGames"), + type: "Game" + }, { + name: globalize.translate("HeaderBooks"), + type: "Book" + }]; + renderCollectionItems(page, item, collectionItemTypes, result.Items) + } + }), "Season" == item.Type ? page.querySelector("#childrenTitle").innerHTML = globalize.translate("HeaderEpisodes") : "Series" == item.Type ? page.querySelector("#childrenTitle").innerHTML = globalize.translate("HeaderSeasons") : "MusicAlbum" == item.Type ? page.querySelector("#childrenTitle").innerHTML = globalize.translate("HeaderTracks") : "GameSystem" == item.Type ? page.querySelector("#childrenTitle").innerHTML = globalize.translate("HeaderGames") : page.querySelector("#childrenTitle").innerHTML = globalize.translate("HeaderItems"), "MusicAlbum" == item.Type || "Season" == item.Type ? (page.querySelector(".childrenSectionHeader").classList.add("hide"), page.querySelector("#childrenCollapsible").classList.add("verticalSection-extrabottompadding")) : page.querySelector(".childrenSectionHeader").classList.remove("hide") + } + + function renderItemsByName(page, item, user) { + require("scripts/itembynamedetailpage".split(","), function() { + window.ItemsByName.renderItems(page, item) + }) + } + + function renderPlaylistItems(page, item, user) { + require("scripts/playlistedit".split(","), function() { + PlaylistViewer.render(page, item) + }) + } + + function renderProgramsForChannel(page, result) { + for (var html = "", currentItems = [], currentStartDate = null, i = 0, length = result.Items.length; i < length; i++) { + var item = result.Items[i], + itemStartDate = datetime.parseISO8601Date(item.StartDate); + currentStartDate && currentStartDate.toDateString() === itemStartDate.toDateString() || (currentItems.length && (html += '
    ', html += '

    ' + datetime.toLocaleDateString(currentStartDate, { + weekday: "long", + month: "long", + day: "numeric" + }) + "

    ", html += '
    ' + listView.getListViewHtml({ + items: currentItems, + enableUserDataButtons: !1, + showParentTitle: !0, + image: !1, + showProgramTime: !0, + mediaInfo: !1, + parentTitleWithTitle: !0 + }) + "
    "), currentStartDate = itemStartDate, currentItems = []), currentItems.push(item) + } + currentItems.length && (html += '
    ', html += '

    ' + datetime.toLocaleDateString(currentStartDate, { + weekday: "long", + month: "long", + day: "numeric" + }) + "

    ", html += '
    ' + listView.getListViewHtml({ + items: currentItems, + enableUserDataButtons: !1, + showParentTitle: !0, + image: !1, + showProgramTime: !0, + mediaInfo: !1, + parentTitleWithTitle: !0 + }) + "
    "), page.querySelector(".programGuide").innerHTML = html + } + + function renderChannelGuide(page, apiClient, item) { + "TvChannel" === item.Type && (page.querySelector(".programGuideSection").classList.remove("hide"), apiClient.getLiveTvPrograms({ + ChannelIds: item.Id, + UserId: apiClient.getCurrentUserId(), + HasAired: !1, + SortBy: "StartDate", + EnableTotalRecordCount: !1, + EnableImages: !1, + ImageTypeLimit: 0, + EnableUserData: !1 + }).then(function(result) { + renderProgramsForChannel(page, result) + })) + } + + function renderSeriesSchedule(page, item, user) { + var apiClient = connectionManager.getApiClient(item.ServerId); + apiClient.getLiveTvPrograms({ + UserId: apiClient.getCurrentUserId(), + HasAired: !1, + SortBy: "StartDate", + EnableTotalRecordCount: !1, + EnableImages: !1, + ImageTypeLimit: 0, + Limit: 50, + EnableUserData: !1, + LibrarySeriesId: item.Id + }).then(function(result) { + result.Items.length ? page.querySelector("#seriesScheduleSection").classList.remove("hide") : page.querySelector("#seriesScheduleSection").classList.add("hide"), page.querySelector("#seriesScheduleList").innerHTML = listView.getListViewHtml({ + items: result.Items, + enableUserDataButtons: !1, + showParentTitle: !1, + image: !1, + showProgramDateTime: !0, + mediaInfo: !1, + showTitle: !0, + moreButton: !1, + action: "programdialog" + }), loading.hide() + }) + } + + function inferContext(item) { + return "Movie" === item.Type || "BoxSet" === item.Type ? "movies" : "Series" === item.Type || "Season" === item.Type || "Episode" === item.Type ? "tvshows" : "Game" === item.Type || "GameSystem" === item.Type ? "games" : "Game" === item.Type || "GameSystem" === item.Type ? "games" : "MusicArtist" === item.Type || "MusicAlbum" === item.Type || "Audio" === item.Type || "AudioBook" === item.Type ? "music" : "Program" === item.Type ? "livetv" : null + } + + function filterItemsByCollectionItemType(items, typeInfo) { + return items.filter(function(item) { + return typeInfo.mediaType ? item.MediaType == typeInfo.mediaType : item.Type == typeInfo.type + }) + } + + function renderCollectionItems(page, parentItem, types, items) { + page.querySelector(".collectionItems").innerHTML = ""; + var i, length; + for (i = 0, length = types.length; i < length; i++) { + var type = types[i], + typeItems = filterItemsByCollectionItemType(items, type); + typeItems.length && renderCollectionItemType(page, parentItem, type, typeItems) + } + var otherType = { + name: globalize.translate("HeaderOtherItems") + }, + otherTypeItems = items.filter(function(curr) { + return !types.filter(function(t) { + return filterItemsByCollectionItemType([curr], t).length > 0 + }).length + }); + otherTypeItems.length && renderCollectionItemType(page, parentItem, otherType, otherTypeItems), items.length || renderCollectionItemType(page, parentItem, { + name: globalize.translate("HeaderItems") + }, items); + var containers = page.querySelectorAll(".collectionItemsContainer"), + notifyRefreshNeeded = function() { + renderChildren(page, parentItem) + }; + for (i = 0, length = containers.length; i < length; i++) containers[i].notifyRefreshNeeded = notifyRefreshNeeded + } + + function renderCollectionItemType(page, parentItem, type, items) { + var html = ""; + html += '
    ', html += '
    ', html += '

    ', html += "" + type.name + "", html += "

    ", html += '', html += "
    ", html += '
    '; + var shape = "MusicAlbum" == type.type ? getSquareShape(!1) : getPortraitShape(!1); + html += cardBuilder.getCardsHtml({ + items: items, + shape: shape, + showTitle: !0, + centerText: !0, + lazy: !0, + showDetailsMenu: !0, + overlayMoreButton: !0, + showAddToCollection: !1, + showRemoveFromCollection: !0, + collectionId: parentItem.Id + }), html += "
    ", html += "
    "; + var collectionItems = page.querySelector(".collectionItems"); + collectionItems.insertAdjacentHTML("beforeend", html), imageLoader.lazyChildren(collectionItems), collectionItems.querySelector(".btnAddToCollection").addEventListener("click", function() { + require(["alert"], function(alert) { + alert({ + text: globalize.translate("AddItemToCollectionHelp"), + html: globalize.translate("AddItemToCollectionHelp") + '

    ' + globalize.translate("ButtonLearnMore") + "" + }) + }) + }) + } + + function renderMusicVideos(page, item, user) { + connectionManager.getApiClient(item.ServerId).getItems(user.Id, { + SortBy: "SortName", + SortOrder: "Ascending", + IncludeItemTypes: "MusicVideo", + Recursive: !0, + Fields: "PrimaryImageAspectRatio,BasicSyncInfo,CanDelete,MediaSourceCount", + AlbumIds: item.Id + }).then(function(result) { + if (result.Items.length) { + page.querySelector("#musicVideosCollapsible").classList.remove("hide"); + var musicVideosContent = page.querySelector(".musicVideosContent"); + musicVideosContent.innerHTML = getVideosHtml(result.Items, user), imageLoader.lazyChildren(musicVideosContent) + } else page.querySelector("#musicVideosCollapsible").classList.add("hide") + }) + } + + function renderAdditionalParts(page, item, user) { + connectionManager.getApiClient(item.ServerId).getAdditionalVideoParts(user.Id, item.Id).then(function(result) { + if (result.Items.length) { + page.querySelector("#additionalPartsCollapsible").classList.remove("hide"); + var additionalPartsContent = page.querySelector("#additionalPartsContent"); + additionalPartsContent.innerHTML = getVideosHtml(result.Items, user), imageLoader.lazyChildren(additionalPartsContent) + } else page.querySelector("#additionalPartsCollapsible").classList.add("hide") + }) + } + + function renderScenes(page, item) { + var chapters = item.Chapters || []; + if (chapters.length && !chapters[0].ImageTag && (chapters = []), chapters.length) { + page.querySelector("#scenesCollapsible").classList.remove("hide"); + var scenesContent = page.querySelector("#scenesContent"); + require(["chaptercardbuilder"], function(chaptercardbuilder) { + chaptercardbuilder.buildChapterCards(item, chapters, { + itemsContainer: scenesContent, + width: 400, + backdropShape: "overflowBackdrop", + squareShape: "overflowSquare" + }) + }) + } else page.querySelector("#scenesCollapsible").classList.add("hide") + } + + function renderMediaSources(page, user, item) { + var html = item.MediaSources.map(function(v) { + return getMediaSourceHtml(user, item, v) + }).join('
    '); + item.MediaSources.length > 1 && (html = "
    " + html), page.querySelector("#mediaInfoContent").innerHTML = html, html ? page.querySelector(".audioVideoMediaInfo").classList.remove("hide") : page.querySelector(".audioVideoMediaInfo").classList.add("hide") + } + + function getMediaSourceHtml(user, item, version) { + var html = ""; + version.Name && item.MediaSources.length > 1 && (html += '
    ' + version.Name + "

    "); + for (var i = 0, length = version.MediaStreams.length; i < length; i++) { + var stream = version.MediaStreams[i]; + if ("Data" != stream.Type) { + html += '
    '; + html += '

    ' + globalize.translate("MediaInfoStreamType" + stream.Type) + "

    "; + var attributes = []; + stream.DisplayTitle && attributes.push(createAttribute("Title", stream.DisplayTitle)), stream.Language && "Video" != stream.Type && attributes.push(createAttribute(globalize.translate("MediaInfoLanguage"), stream.Language)), stream.Codec && attributes.push(createAttribute(globalize.translate("MediaInfoCodec"), stream.Codec.toUpperCase())), stream.CodecTag && attributes.push(createAttribute(globalize.translate("MediaInfoCodecTag"), stream.CodecTag)), null != stream.IsAVC && attributes.push(createAttribute("AVC", stream.IsAVC ? "Yes" : "No")), stream.Profile && attributes.push(createAttribute(globalize.translate("MediaInfoProfile"), stream.Profile)), stream.Level && attributes.push(createAttribute(globalize.translate("MediaInfoLevel"), stream.Level)), (stream.Width || stream.Height) && attributes.push(createAttribute(globalize.translate("MediaInfoResolution"), stream.Width + "x" + stream.Height)), stream.AspectRatio && "mjpeg" != stream.Codec && attributes.push(createAttribute(globalize.translate("MediaInfoAspectRatio"), stream.AspectRatio)), "Video" == stream.Type && (null != stream.IsAnamorphic && attributes.push(createAttribute(globalize.translate("MediaInfoAnamorphic"), stream.IsAnamorphic ? "Yes" : "No")), attributes.push(createAttribute(globalize.translate("MediaInfoInterlaced"), stream.IsInterlaced ? "Yes" : "No"))), (stream.AverageFrameRate || stream.RealFrameRate) && attributes.push(createAttribute(globalize.translate("MediaInfoFramerate"), stream.AverageFrameRate || stream.RealFrameRate)), stream.ChannelLayout && attributes.push(createAttribute(globalize.translate("MediaInfoLayout"), stream.ChannelLayout)), stream.Channels && attributes.push(createAttribute(globalize.translate("MediaInfoChannels"), stream.Channels + " ch")), stream.BitRate && "mjpeg" != stream.Codec && attributes.push(createAttribute(globalize.translate("MediaInfoBitrate"), parseInt(stream.BitRate / 1e3) + " kbps")), stream.SampleRate && attributes.push(createAttribute(globalize.translate("MediaInfoSampleRate"), stream.SampleRate + " Hz")), stream.VideoRange && "SDR" !== stream.VideoRange && attributes.push(createAttribute(globalize.translate("sharedcomponents#VideoRange"), stream.VideoRange)), stream.ColorPrimaries && attributes.push(createAttribute(globalize.translate("sharedcomponents#ColorPrimaries"), stream.ColorPrimaries)), stream.ColorSpace && attributes.push(createAttribute(globalize.translate("sharedcomponents#ColorSpace"), stream.ColorSpace)), stream.ColorTransfer && attributes.push(createAttribute(globalize.translate("sharedcomponents#ColorTransfer"), stream.ColorTransfer)), stream.BitDepth && attributes.push(createAttribute(globalize.translate("MediaInfoBitDepth"), stream.BitDepth + " bit")), stream.PixelFormat && attributes.push(createAttribute(globalize.translate("MediaInfoPixelFormat"), stream.PixelFormat)), stream.RefFrames && attributes.push(createAttribute(globalize.translate("MediaInfoRefFrames"), stream.RefFrames)), stream.NalLengthSize && attributes.push(createAttribute("NAL", stream.NalLengthSize)), "Video" != stream.Type && attributes.push(createAttribute(globalize.translate("MediaInfoDefault"), stream.IsDefault ? "Yes" : "No")), "Subtitle" == stream.Type && (attributes.push(createAttribute(globalize.translate("MediaInfoForced"), stream.IsForced ? "Yes" : "No")), attributes.push(createAttribute(globalize.translate("MediaInfoExternal"), stream.IsExternal ? "Yes" : "No"))), "Video" == stream.Type && version.Timestamp && attributes.push(createAttribute(globalize.translate("MediaInfoTimestamp"), version.Timestamp)), html += attributes.join("
    "), html += "
    " + } + } + if (version.Container && (html += '
    ' + globalize.translate("MediaInfoContainer") + '' + version.Container + "
    "), version.Formats && version.Formats.length, version.Path && "Http" != version.Protocol && user && user.Policy.IsAdministrator && (html += '
    ' + globalize.translate("MediaInfoPath") + '' + version.Path + "
    "), version.Size) { + var size = (version.Size / 1048576).toFixed(0); + html += '
    ' + globalize.translate("MediaInfoSize") + '' + size + " MB
    " + } + return html + } + + function createAttribute(label, value) { + return '' + label + '' + value + "" + } + + function getVideosHtml(items, user, limit, moreButtonClass) { + var html = cardBuilder.getCardsHtml({ + items: items, + shape: "auto", + showTitle: !0, + action: "play", + overlayText: !1, + centerText: !0, + showRuntime: !0 + }); + return limit && items.length > limit && (html += '

    "), html + } + + function renderSpecials(page, item, user, limit) { + connectionManager.getApiClient(item.ServerId).getSpecialFeatures(user.Id, item.Id).then(function(specials) { + var specialsContent = page.querySelector("#specialsContent"); + specialsContent.innerHTML = getVideosHtml(specials, user, limit, "moreSpecials"), imageLoader.lazyChildren(specialsContent) + }) + } + + function renderCast(page, item, context, limit, isStatic) { + var people = (item.People || []).filter(function(p) { + return "Director" !== p.Type + }); + if (!people.length) return void page.querySelector("#castCollapsible").classList.add("hide"); + page.querySelector("#castCollapsible").classList.remove("hide"); + var castContent = page.querySelector("#castContent"); + enableScrollX() ? (castContent.classList.add("scrollX"), limit = 32) : castContent.classList.add("vertical-wrap"); + var limitExceeded = limit && people.length > limit; + limitExceeded && (people = people.slice(0), people.length = Math.min(limit, people.length)), require(["peoplecardbuilder"], function(peoplecardbuilder) { + peoplecardbuilder.buildPeopleCards(people, { + itemsContainer: castContent, + coverImage: !0, + serverId: item.ServerId, + width: 160, + shape: getPortraitShape() + }) + }); + var morePeopleButton = page.querySelector(".morePeople"); + morePeopleButton && (limitExceeded && !enableScrollX() ? morePeopleButton.classList.remove("hide") : morePeopleButton.classList.add("hide")) + } + + function itemDetailPage() { + var self = this; + self.setInitialCollapsibleState = setInitialCollapsibleState, self.renderDetails = renderDetails, self.renderCast = renderCast, self.renderMediaSources = renderMediaSources + } + + function bindAll(view, selector, eventName, fn) { + var i, length, elems = view.querySelectorAll(selector); + for (i = 0, length = elems.length; i < length; i++) elems[i].addEventListener(eventName, fn) + } + + function onTrackSelectionsSubmit(e) { + return e.preventDefault(), !1 + } + return window.ItemDetailPage = new itemDetailPage, + function(view, params) { + function reload(instance, page, params) { + loading.show(); + var apiClient = params.serverId ? connectionManager.getApiClient(params.serverId) : ApiClient, + promises = [getPromise(apiClient, params), apiClient.getCurrentUser()]; + Promise.all(promises).then(function(responses) { + var item = responses[0], + user = responses[1]; + currentItem = item, reloadFromItem(instance, page, params, item, user) + }) + } + + function splitVersions(instance, page, apiClient, params) { + require(["confirm"], function(confirm) { + confirm("Are you sure you wish to split the media sources into separate items?", "Split Media Apart").then(function() { + loading.show(), apiClient.ajax({ + type: "DELETE", + url: apiClient.getUrl("Videos/" + params.id + "/AlternateSources") + }).then(function() { + loading.hide(), reload(instance, page, params) + }) + }) + }) + } + + function getPlayOptions(startPosition) { + var audioStreamIndex = view.querySelector(".selectAudio").value || null; + return { + startPositionTicks: startPosition, + mediaSourceId: view.querySelector(".selectSource").value, + audioStreamIndex: audioStreamIndex, + subtitleStreamIndex: view.querySelector(".selectSubtitles").value + } + } + + function playItem(item, startPosition) { + var playOptions = getPlayOptions(startPosition); + playOptions.items = [item], playbackManager.play(playOptions) + } + + function playTrailer(page) { + playbackManager.playTrailers(currentItem) + } + + function playCurrentItem(button, mode) { + var item = currentItem; + if ("Program" === item.Type) { + var apiClient = connectionManager.getApiClient(item.ServerId); + return void apiClient.getLiveTvChannel(item.ChannelId, apiClient.getCurrentUserId()).then(function(channel) { + playbackManager.play({ + items: [channel] + }) + }) + } + playItem(item, item.UserData && "resume" === mode ? item.UserData.PlaybackPositionTicks : 0) + } + + function onPlayClick() { + playCurrentItem(this, this.getAttribute("data-mode")) + } + + function onInstantMixClick() { + playbackManager.instantMix(currentItem) + } + + function onShuffleClick() { + playbackManager.shuffle(currentItem) + } + + function onDeleteClick() { + require(["deleteHelper"], function(deleteHelper) { + deleteHelper.deleteItem({ + item: currentItem, + navigate: !0 + }) + }) + } + + function onCancelSeriesTimerClick() { + require(["recordingHelper"], function(recordingHelper) { + recordingHelper.cancelSeriesTimerWithConfirmation(currentItem.Id, currentItem.ServerId).then(function() { + Dashboard.navigate("livetv.html") + }) + }) + } + + function onCancelTimerClick() { + require(["recordingHelper"], function(recordingHelper) { + recordingHelper.cancelTimer(connectionManager.getApiClient(currentItem.ServerId), currentItem.TimerId).then(function() { + reload(self, view, params) + }) + }) + } + + function onPlayTrailerClick() { + playTrailer(view) + } + + function onDownloadChange() { + reload(self, view, params) + } + + function onMoreCommandsClick() { + var button = this; + apiClient.getCurrentUser().then(function(user) { + itemContextMenu.show(getContextMenuOptions(currentItem, user, button)).then(function(result) { + result.deleted ? appRouter.goHome() : result.updated && reload(self, view, params) + }) + }) + } + + function onPlayerChange() { + renderTrackSelections(view, self, currentItem), setTrailerButtonVisibility(view, currentItem) + } + + function editImages() { + return new Promise(function(resolve, reject) { + require(["imageEditor"], function(imageEditor) { + imageEditor.show({ + itemId: currentItem.Id, + serverId: currentItem.ServerId + }).then(resolve, reject) + }) + }) + } + + function onWebSocketMessage(e, data) { + var msg = data; + if ("UserDataChanged" === msg.MessageType && currentItem && msg.Data.UserId == apiClient.getCurrentUserId()) { + var key = currentItem.UserData.Key, + userData = msg.Data.UserDataList.filter(function(u) { + return u.Key == key + })[0]; + userData && (currentItem.UserData = userData, reloadPlayButtons(view, currentItem), apiClient.getCurrentUser().then(function(user) { + refreshImage(view, currentItem, user) + })) + } + } + var currentItem, self = this, + apiClient = params.serverId ? connectionManager.getApiClient(params.serverId) : ApiClient; + view.querySelectorAll(".btnPlay"); + bindAll(view, ".btnPlay", "click", onPlayClick), bindAll(view, ".btnResume", "click", onPlayClick), bindAll(view, ".btnInstantMix", "click", onInstantMixClick), bindAll(view, ".btnShuffle", "click", onShuffleClick), bindAll(view, ".btnPlayTrailer", "click", onPlayTrailerClick), bindAll(view, ".btnCancelSeriesTimer", "click", onCancelSeriesTimerClick), bindAll(view, ".btnCancelTimer", "click", onCancelTimerClick), bindAll(view, ".btnDeleteItem", "click", onDeleteClick), bindAll(view, ".btnSyncDownload", "download", onDownloadChange), bindAll(view, ".btnSyncDownload", "download-cancel", onDownloadChange), view.querySelector(".btnMoreCommands i").innerHTML = "", view.querySelector(".trackSelections").addEventListener("submit", onTrackSelectionsSubmit), view.querySelector(".btnSplitVersions").addEventListener("click", function() { + splitVersions(self, view, apiClient, params) + }), bindAll(view, ".btnMoreCommands", "click", onMoreCommandsClick), view.querySelector(".selectSource").addEventListener("change", function() { + renderVideoSelections(view, self._currentPlaybackMediaSources), renderAudioSelections(view, self._currentPlaybackMediaSources), renderSubtitleSelections(view, self._currentPlaybackMediaSources) + }), view.addEventListener("click", function(e) { + dom.parentWithClass(e.target, "moreScenes") ? apiClient.getCurrentUser().then(function(user) { + renderScenes(view, currentItem) + }) : dom.parentWithClass(e.target, "morePeople") ? renderCast(view, currentItem, params.context) : dom.parentWithClass(e.target, "moreSpecials") && apiClient.getCurrentUser().then(function(user) { + renderSpecials(view, currentItem, user) + }) + }), view.querySelector(".detailImageContainer").addEventListener("click", function(e) { + dom.parentWithClass(e.target, "itemDetailGalleryLink") && editImages().then(function() { + reload(self, view, params) + }) + }), view.addEventListener("viewshow", function(e) { + var page = this; + libraryMenu.setTransparentMenu(!0), e.detail.isRestored ? currentItem && (setTitle(currentItem, connectionManager.getApiClient(currentItem.ServerId)), renderTrackSelections(page, self, currentItem, !0)) : reload(self, page, params), events.on(apiClient, "message", onWebSocketMessage), events.on(playbackManager, "playerchange", onPlayerChange) + }), view.addEventListener("viewbeforehide", function() { + events.off(apiClient, "message", onWebSocketMessage), events.off(playbackManager, "playerchange", onPlayerChange), libraryMenu.setTransparentMenu(!1) + }), view.addEventListener("viewdestroy", function() { + currentItem = null, self._currentPlaybackMediaSources = null, self.currentRecordingFields = null + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/librarybrowser.js b/dashboard-ui/scripts/librarybrowser.js index 0fce9c63ac..5278842d7f 100644 --- a/dashboard-ui/scripts/librarybrowser.js +++ b/dashboard-ui/scripts/librarybrowser.js @@ -1 +1,101 @@ -define(["userSettings"],function(userSettings){"use strict";var libraryBrowser={getSavedQueryKey:function(modifier){return window.location.href.split("#")[0]+(modifier||"")},loadSavedQueryValues:function(key,query){var values=userSettings.get(key);return values?(values=JSON.parse(values),Object.assign(query,values)):query},saveQueryValues:function(key,query){var values={};query.SortBy&&(values.SortBy=query.SortBy),query.SortOrder&&(values.SortOrder=query.SortOrder),userSettings.set(key,JSON.stringify(values))},saveViewSetting:function(key,value){userSettings.set(key+"-_view",value)},getSavedView:function(key){return userSettings.get(key+"-_view")},showLayoutMenu:function(button,currentLayout,views){var dispatchEvent=!0;views||(dispatchEvent=!1,views=button.getAttribute("data-layouts"),views=views?views.split(","):["List","Poster","PosterCard","Thumb","ThumbCard"]);var menuItems=views.map(function(v){return{name:Globalize.translate("Option"+v),id:v,selected:currentLayout==v}});require(["actionsheet"],function(actionsheet){actionsheet.show({items:menuItems,positionTo:button,callback:function(id){button.dispatchEvent(new CustomEvent("layoutchange",{detail:{viewStyle:id},bubbles:!0,cancelable:!1})),dispatchEvent||window.$&&$(button).trigger("layoutchange",[id])}})})},getQueryPagingHtml:function(options){var startIndex=options.startIndex,limit=options.limit,totalRecordCount=options.totalRecordCount,html="",recordsEnd=Math.min(startIndex+limit,totalRecordCount),showControls=limit',showControls){html+='';html+=(totalRecordCount?startIndex+1:0)+"-"+recordsEnd+" of "+totalRecordCount,html+=""}return(showControls||options.viewButton||options.filterButton||options.sortButton||options.addLayoutButton)&&(html+='
    ',showControls&&(html+='',html+=''),options.addLayoutButton&&(html+=''),options.sortButton&&(html+=''),options.filterButton&&(html+=''),html+="
    "),html+=""},showSortMenu:function(options){require(["dialogHelper","emby-radio"],function(dialogHelper){function onSortByChange(){var newValue=this.value;if(this.checked){var changed=options.query.SortBy!=newValue;options.query.SortBy=newValue.replace("_",","),options.query.StartIndex=0,options.callback&&changed&&options.callback()}}function onSortOrderChange(){var newValue=this.value;if(this.checked){var changed=options.query.SortOrder!=newValue;options.query.SortOrder=newValue,options.query.StartIndex=0,options.callback&&changed&&options.callback()}}var dlg=dialogHelper.createDialog({removeOnClose:!0,modal:!1,entryAnimationDuration:160,exitAnimationDuration:200});dlg.classList.add("ui-body-a"),dlg.classList.add("background-theme-a"),dlg.classList.add("formDialog");var html="";html+='
    ',html+='

    ',html+=Globalize.translate("HeaderSortBy"),html+="

    ";var i,length,isChecked;for(html+="
    ",i=0,length=options.items.length;i"+option.name+""}html+="
    ",html+='

    ',html+=Globalize.translate("HeaderSortOrder"),html+="

    ",html+="
    ",isChecked="Ascending"==options.query.SortOrder?" checked":"",html+='",isChecked="Descending"==options.query.SortOrder?" checked":"",html+='",html+="
    ",html+="
    ",dlg.innerHTML=html,dialogHelper.open(dlg);var sortBys=dlg.querySelectorAll(".menuSortBy");for(i=0,length=sortBys.length;i', html += ''), options.addLayoutButton && (html += ''), options.sortButton && (html += ''), options.filterButton && (html += ''), html += ""), html += "" + }, + showSortMenu: function(options) { + require(["dialogHelper", "emby-radio"], function(dialogHelper) { + function onSortByChange() { + var newValue = this.value; + if (this.checked) { + var changed = options.query.SortBy != newValue; + options.query.SortBy = newValue.replace("_", ","), options.query.StartIndex = 0, options.callback && changed && options.callback() + } + } + + function onSortOrderChange() { + var newValue = this.value; + if (this.checked) { + var changed = options.query.SortOrder != newValue; + options.query.SortOrder = newValue, options.query.StartIndex = 0, options.callback && changed && options.callback() + } + } + var dlg = dialogHelper.createDialog({ + removeOnClose: !0, + modal: !1, + entryAnimationDuration: 160, + exitAnimationDuration: 200 + }); + dlg.classList.add("ui-body-a"), dlg.classList.add("background-theme-a"), dlg.classList.add("formDialog"); + var html = ""; + html += '
    ', html += '

    ', html += Globalize.translate("HeaderSortBy"), html += "

    "; + var i, length, isChecked; + for (html += "
    ", i = 0, length = options.items.length; i < length; i++) { + var option = options.items[i], + radioValue = option.id.replace(",", "_"); + isChecked = (options.query.SortBy || "").replace(",", "_") == radioValue ? " checked" : "", html += '" + } + html += "
    ", html += '

    ', html += Globalize.translate("HeaderSortOrder"), html += "

    ", html += "
    ", isChecked = "Ascending" == options.query.SortOrder ? " checked" : "", html += '", isChecked = "Descending" == options.query.SortOrder ? " checked" : "", html += '", html += "
    ", html += "
    ", dlg.innerHTML = html, dialogHelper.open(dlg); + var sortBys = dlg.querySelectorAll(".menuSortBy"); + for (i = 0, length = sortBys.length; i < length; i++) sortBys[i].addEventListener("change", onSortByChange); + var sortOrders = dlg.querySelectorAll(".menuSortOrder"); + for (i = 0, length = sortOrders.length; i < length; i++) sortOrders[i].addEventListener("change", onSortOrderChange) + }) + } + }; + return window.LibraryBrowser = libraryBrowser, libraryBrowser +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/librarymenu.js b/dashboard-ui/scripts/librarymenu.js index 1ab4bcd2f0..327661742a 100644 --- a/dashboard-ui/scripts/librarymenu.js +++ b/dashboard-ui/scripts/librarymenu.js @@ -1 +1,456 @@ -define(["dom","layoutManager","inputManager","connectionManager","events","viewManager","libraryBrowser","appRouter","apphost","playbackManager","browser","globalize","paper-icon-button-light","material-icons","scrollStyles","flexStyles"],function(dom,layoutManager,inputManager,connectionManager,events,viewManager,libraryBrowser,appRouter,appHost,playbackManager,browser,globalize){"use strict";function getCurrentApiClient(){return currentUser&¤tUser.localUser?connectionManager.getApiClient(currentUser.localUser.ServerId):connectionManager.currentApiClient()}function lazyLoadViewMenuBarImages(){require(["imageLoader"],function(imageLoader){imageLoader.lazyChildren(skinHeader)})}function onBackClick(){appRouter.back()}function updateUserInHeader(user){var hasImage;if(user&&user.name){if(user.imageUrl){var url=user.imageUrl;user.supportsImageParams&&(url+="&height="+Math.round(26*Math.max(window.devicePixelRatio||1,2))),updateHeaderUserButton(url),hasImage=!0}headerUserButton.classList.remove("hide")}else headerUserButton.classList.add("hide");hasImage||updateHeaderUserButton(null),user&&user.localUser?(headerHomeButton&&headerHomeButton.classList.remove("hide"),headerSearchButton&&headerSearchButton.classList.remove("hide"),headerSettingsButton&&(user.localUser.Policy.IsAdministrator?headerSettingsButton.classList.remove("hide"):headerSettingsButton.classList.add("hide")),headerCastButton.classList.remove("hide")):(headerHomeButton.classList.add("hide"),headerCastButton.classList.add("hide"),headerSearchButton&&headerSearchButton.classList.add("hide"),headerSettingsButton&&headerSettingsButton.classList.add("hide")),requiresUserRefresh=!1}function updateHeaderUserButton(src){src?(headerUserButton.classList.add("headerUserButtonRound"),headerUserButton.innerHTML=''):(headerUserButton.classList.remove("headerUserButtonRound"),headerUserButton.innerHTML='')}function showSearch(){inputManager.trigger("search")}function onHeaderUserButtonClick(e){Dashboard.navigate("mypreferencesmenu.html")}function onSettingsClick(e){Dashboard.navigate("dashboard.html")}function onHeaderHomeButtonClick(){Dashboard.navigate("home.html")}function bindMenuEvents(){(mainDrawerButton=document.querySelector(".mainDrawerButton"))&&mainDrawerButton.addEventListener("click",toggleMainDrawer);var headerBackButton=skinHeader.querySelector(".headerBackButton");headerBackButton&&headerBackButton.addEventListener("click",onBackClick),headerSearchButton&&headerSearchButton.addEventListener("click",showSearch),headerUserButton.addEventListener("click",onHeaderUserButtonClick),headerHomeButton.addEventListener("click",onHeaderHomeButtonClick),initHeadRoom(skinHeader),headerCastButton.addEventListener("click",onCastButtonClicked),headerSettingsButton&&headerSettingsButton.addEventListener("click",onSettingsClick)}function onCastButtonClicked(){var btn=this;require(["playerSelectionMenu"],function(playerSelectionMenu){playerSelectionMenu.show(btn)})}function getItemHref(item,context){return appRouter.getRouteUrl(item,{context:context})}function toggleMainDrawer(){navDrawerInstance.isVisible?closeMainDrawer():openMainDrawer()}function openMainDrawer(){navDrawerInstance.open(),lastOpenTime=(new Date).getTime()}function onMainDrawerOpened(){layoutManager.mobile&&document.body.classList.add("bodyWithPopupOpen")}function closeMainDrawer(){navDrawerInstance.close()}function onMainDrawerSelect(e){navDrawerInstance.isVisible?onMainDrawerOpened():document.body.classList.remove("bodyWithPopupOpen")}function refreshLibraryInfoInDrawer(user,drawer){var html="";html+='
    ',html+=''+globalize.translate("ButtonHome")+"",html+='
    ',html+='

    ',html+=globalize.translate("sharedcomponents#HeaderMyDownloads"),html+="

    ",html+=''+globalize.translate("sharedcomponents#Browse")+"",html+=''+globalize.translate("sharedcomponents#Manage")+"",html+="
    ",html+='
    ',html+="
    ";var localUser=user.localUser;localUser&&localUser.Policy.IsAdministrator&&(html+='
    ',html+='

    ',html+=globalize.translate("HeaderAdmin"),html+="

    ",html+=''+globalize.translate("ButtonManageServer")+"",html+=''+globalize.translate("MetadataManager")+"",html+="
    "),html+='
    ',user.localUser&&(html+=''+globalize.translate("ButtonSettings")+""),html+=''+globalize.translate("sharedcomponents#Sync")+"",Dashboard.isConnectMode()&&(html+=''+globalize.translate("ButtonSelectServer")+""),!user.localUser||user.localUser.EnableAutoLogin&&!user.connectUser||(html+=''+globalize.translate("ButtonSignOut")+""),html+="
    ",navDrawerScrollContainer.innerHTML=html;var btnLogout=navDrawerScrollContainer.querySelector(".btnLogout");btnLogout&&btnLogout.addEventListener("click",onLogoutClick)}function refreshDashboardInfoInDrawer(apiClient){currentDrawerType="admin",loadNavDrawer(),navDrawerScrollContainer.querySelector(".adminDrawerLogo")?updateDashboardMenuSelectedItem():createDashboardMenu(apiClient)}function isUrlInCurrentView(url){return-1!==window.location.href.toString().toLowerCase().indexOf(url.toLowerCase())}function updateDashboardMenuSelectedItem(){for(var links=navDrawerScrollContainer.querySelectorAll(".navMenuOption"),currentViewId=viewManager.currentView().id,i=0,length=links.length;i0),selected){link.classList.add("navMenuOption-selected");var title="";link=link.querySelector("span")||link;title+=(link.innerText||link.textContent).trim(),LibraryMenu.setTitle(title)}else link.classList.remove("navMenuOption-selected")}}function createToolsMenuList(pluginItems){var links=[{name:globalize.translate("TabServer")},{name:globalize.translate("TabDashboard"),href:"dashboard.html",pageIds:["dashboardPage","serverActivityPage"],icon:"dashboard"},{name:globalize.translate("TabSettings"),href:"dashboardgeneral.html",pageIds:["dashboardGeneralPage"],icon:"settings"},{name:globalize.translate("TabUsers"),href:"userprofiles.html",pageIds:["userProfilesPage","newUserPage","editUserPage","userLibraryAccessPage","userParentalControlPage","userPasswordPage"],icon:"people"},{name:"Emby Premiere",href:"supporterkey.html",pageIds:["supporterKeyPage"],icon:"star"},{name:globalize.translate("TabLibrary"),href:"library.html",pageIds:["mediaLibraryPage","librarySettingsPage","libraryDisplayPage","metadataImagesConfigurationPage","metadataNfoPage"],icon:"folder",color:"#38c"},{name:globalize.translate("TabPlayback"),icon:"play_circle_filled",color:"#E5342E",href:"playbackconfiguration.html",pageIds:["playbackConfigurationPage","streamingSettingsPage"]},{name:globalize.translate("TabTranscoding"),icon:"transform",href:"encodingsettings.html",pageIds:["encodingSettingsPage"]}];return addPluginPagesToMainMenu(links,pluginItems,"server"),links.push({divider:!0,name:globalize.translate("TabDevices")}),links.push({name:globalize.translate("TabDevices"),href:"devices/devices.html",pageIds:["devicesPage","devicePage"],icon:"tablet"}),links.push({name:globalize.translate("HeaderDownloadSync"),icon:"file_download",href:"syncactivity.html",pageIds:["syncActivityPage","syncJobPage","syncSettingsPage"],color:"#009688"}),links.push({name:globalize.translate("TabCameraUpload"),href:"devicesupload.html",pageIds:["devicesUploadPage"],icon:"photo_camera"}),links.push({name:globalize.translate("DLNA"),href:"dlnasettings.html",pageIds:["dlnaSettingsPage","dlnaProfilesPage","dlnaProfilePage"],icon:""}),links.push({divider:!0,name:globalize.translate("TabLiveTV")}),links.push({name:globalize.translate("TabLiveTV"),href:"livetvstatus.html",pageIds:["liveTvStatusPage","liveTvTunerPage"],icon:""}),links.push({name:globalize.translate("DVR"),href:"livetvsettings.html",pageIds:["liveTvSettingsPage"],icon:"dvr"}),links.push({divider:!0,name:globalize.translate("TabExpert")}),links.push({name:globalize.translate("TabAdvanced"),icon:"settings",href:"dashboardhosting.html",color:"#F16834",pageIds:["dashboardHostingPage","serverSecurityPage"]}),links.push({name:globalize.translate("TabLogs"),href:"log.html",pageIds:["logPage"],icon:"folder_open"}),links.push({name:globalize.translate("TabNotifications"),icon:"notifications",color:"brown",href:"notificationsettings.html",pageIds:["notificationSettingsPage","notificationSettingPage"]}),links.push({name:globalize.translate("TabPlugins"),icon:"add_shopping_cart",color:"#9D22B1",href:"plugins.html",pageIds:["pluginsPage","pluginCatalogPage"]}),links.push({name:globalize.translate("TabScheduledTasks"),href:"scheduledtasks.html",pageIds:["scheduledTasksPage","scheduledTaskPage"],icon:"schedule"}),links.push({name:globalize.translate("MetadataManager"),href:"edititemmetadata.html",pageIds:[],icon:"mode_edit"}),addPluginPagesToMainMenu(links,pluginItems),links}function addPluginPagesToMainMenu(links,pluginItems,section){for(var i=0,length=pluginItems.length;i",item.icon&&(menuHtml+=''+item.icon+""),menuHtml+='',menuHtml+=item.name,menuHtml+="",menuHtml+=""}function getToolsMenuHtml(apiClient){return getToolsMenuLinks(apiClient).then(function(items){var i,length,item,menuHtml="";for(menuHtml+='
    ',i=0,length=items.length;i',menuHtml+=item.name,menuHtml+="");return menuHtml+="
    "})}function createDashboardMenu(apiClient){return getToolsMenuHtml(apiClient).then(function(toolsMenuHtml){var html="";html+='",html+=toolsMenuHtml,navDrawerScrollContainer.innerHTML=html,updateDashboardMenuSelectedItem()})}function onSidebarLinkClick(){var section=this.getElementsByClassName("sectionName")[0],text=section?section.innerHTML:this.innerHTML;LibraryMenu.setTitle(text)}function getUserViews(apiClient,userId){return apiClient.getUserViews({},userId).then(function(result){for(var items=result.Items,list=[],i=0,length=items.length;i',html+=globalize.translate("HeaderMedia"),html+="",html+=items.map(function(i){var icon="folder",itemId=i.Id;"channels"==i.CollectionType?itemId="channels":"livetv"==i.CollectionType&&(itemId="livetv"),"photos"==i.CollectionType?icon="photo_library":"music"==i.CollectionType||"musicvideos"==i.CollectionType?icon="library_music":"books"==i.CollectionType?icon="library_books":"playlists"==i.CollectionType?icon="view_list":"games"==i.CollectionType?icon="games":"movies"==i.CollectionType?icon="video_library":"channels"==i.CollectionType||"Channel"==i.Type?icon="videocam":"tvshows"==i.CollectionType?icon="tv":"livetv"==i.CollectionType&&(icon="live_tv"),icon=i.icon||icon;i.onclick&&i.onclick;return''+icon+''+i.Name+""}).join(""),libraryMenuOptions.innerHTML=html;for(var elem=libraryMenuOptions,sidebarLinks=elem.querySelectorAll(".navMenuOption"),i=0,length=sidebarLinks.length;i",html+='',html+='',html+='

    ',html+="",html+='
    ',html+='',html+='',html+='',html+='',layoutManager.mobile||(html+=''),html+="
    ",html+="",html+='
    ',html+="
    ",skinHeader.classList.add("skinHeader-withBackground"),skinHeader.innerHTML=html,headerHomeButton=skinHeader.querySelector(".headerHomeButton"),headerUserButton=skinHeader.querySelector(".headerUserButton"),headerSettingsButton=skinHeader.querySelector(".headerSettingsButton"),headerCastButton=skinHeader.querySelector(".headerCastButton"),headerSearchButton=skinHeader.querySelector(".headerSearchButton"),browser.chrome||skinHeader.classList.add("skinHeader-blurred"),lazyLoadViewMenuBarImages(),bindMenuEvents()}(),events.on(connectionManager,"localusersignedin",function(e,user){currentDrawerType=null,currentUser={localUser:user},loadNavDrawer(),connectionManager.user(connectionManager.getApiClient(user.ServerId)).then(function(user){currentUser=user,updateUserInHeader(user)})}),events.on(connectionManager,"localusersignedout",function(){currentUser={},updateUserInHeader()}),events.on(playbackManager,"playerchange",updateCastIcon),loadNavDrawer(),LibraryMenu}); \ No newline at end of file +define(["dom", "layoutManager", "inputManager", "connectionManager", "events", "viewManager", "libraryBrowser", "appRouter", "apphost", "playbackManager", "browser", "globalize", "paper-icon-button-light", "material-icons", "scrollStyles", "flexStyles"], function(dom, layoutManager, inputManager, connectionManager, events, viewManager, libraryBrowser, appRouter, appHost, playbackManager, browser, globalize) { + "use strict"; + + function getCurrentApiClient() { + return currentUser && currentUser.localUser ? connectionManager.getApiClient(currentUser.localUser.ServerId) : connectionManager.currentApiClient() + } + + function lazyLoadViewMenuBarImages() { + require(["imageLoader"], function(imageLoader) { + imageLoader.lazyChildren(skinHeader) + }) + } + + function onBackClick() { + appRouter.back() + } + + function updateUserInHeader(user) { + var hasImage; + if (user && user.name) { + if (user.imageUrl) { + var url = user.imageUrl; + user.supportsImageParams && (url += "&height=" + Math.round(26 * Math.max(window.devicePixelRatio || 1, 2))), updateHeaderUserButton(url), hasImage = !0 + } + headerUserButton.classList.remove("hide") + } else headerUserButton.classList.add("hide"); + hasImage || updateHeaderUserButton(null), user && user.localUser ? (headerHomeButton && headerHomeButton.classList.remove("hide"), headerSearchButton && headerSearchButton.classList.remove("hide"), headerSettingsButton && (user.localUser.Policy.IsAdministrator ? headerSettingsButton.classList.remove("hide") : headerSettingsButton.classList.add("hide")), headerCastButton.classList.remove("hide")) : (headerHomeButton.classList.add("hide"), headerCastButton.classList.add("hide"), headerSearchButton && headerSearchButton.classList.add("hide"), headerSettingsButton && headerSettingsButton.classList.add("hide")), requiresUserRefresh = !1 + } + + function updateHeaderUserButton(src) { + src ? (headerUserButton.classList.add("headerUserButtonRound"), headerUserButton.innerHTML = '') : (headerUserButton.classList.remove("headerUserButtonRound"), headerUserButton.innerHTML = '') + } + + function showSearch() { + inputManager.trigger("search") + } + + function onHeaderUserButtonClick(e) { + Dashboard.navigate("mypreferencesmenu.html") + } + + function onSettingsClick(e) { + Dashboard.navigate("dashboard.html") + } + + function onHeaderHomeButtonClick() { + Dashboard.navigate("home.html") + } + + function bindMenuEvents() { + (mainDrawerButton = document.querySelector(".mainDrawerButton")) && mainDrawerButton.addEventListener("click", toggleMainDrawer); + var headerBackButton = skinHeader.querySelector(".headerBackButton"); + headerBackButton && headerBackButton.addEventListener("click", onBackClick), headerSearchButton && headerSearchButton.addEventListener("click", showSearch), headerUserButton.addEventListener("click", onHeaderUserButtonClick), headerHomeButton.addEventListener("click", onHeaderHomeButtonClick), initHeadRoom(skinHeader), headerCastButton.addEventListener("click", onCastButtonClicked), headerSettingsButton && headerSettingsButton.addEventListener("click", onSettingsClick) + } + + function onCastButtonClicked() { + var btn = this; + require(["playerSelectionMenu"], function(playerSelectionMenu) { + playerSelectionMenu.show(btn) + }) + } + + function getItemHref(item, context) { + return appRouter.getRouteUrl(item, { + context: context + }) + } + + function toggleMainDrawer() { + navDrawerInstance.isVisible ? closeMainDrawer() : openMainDrawer() + } + + function openMainDrawer() { + navDrawerInstance.open(), lastOpenTime = (new Date).getTime() + } + + function onMainDrawerOpened() { + layoutManager.mobile && document.body.classList.add("bodyWithPopupOpen") + } + + function closeMainDrawer() { + navDrawerInstance.close() + } + + function onMainDrawerSelect(e) { + navDrawerInstance.isVisible ? onMainDrawerOpened() : document.body.classList.remove("bodyWithPopupOpen") + } + + function refreshLibraryInfoInDrawer(user, drawer) { + var html = ""; + html += '
    ', html += '' + globalize.translate("ButtonHome") + "", html += '
    ', html += '

    ', html += globalize.translate("sharedcomponents#HeaderMyDownloads"), html += "

    ", html += '' + globalize.translate("sharedcomponents#Browse") + "", html += '' + globalize.translate("sharedcomponents#Manage") + "", html += "
    ", html += '
    ', html += "
    "; + var localUser = user.localUser; + localUser && localUser.Policy.IsAdministrator && (html += '
    ', html += '

    ', html += globalize.translate("HeaderAdmin"), html += "

    ", html += '' + globalize.translate("ButtonManageServer") + "", html += '' + globalize.translate("MetadataManager") + "", html += "
    "), html += '
    ', user.localUser && (html += '' + globalize.translate("ButtonSettings") + ""), html += '' + globalize.translate("sharedcomponents#Sync") + "", Dashboard.isConnectMode() && (html += '' + globalize.translate("ButtonSelectServer") + ""), !user.localUser || user.localUser.EnableAutoLogin && !user.connectUser || (html += '' + globalize.translate("ButtonSignOut") + ""), html += "
    ", navDrawerScrollContainer.innerHTML = html; + var btnLogout = navDrawerScrollContainer.querySelector(".btnLogout"); + btnLogout && btnLogout.addEventListener("click", onLogoutClick) + } + + function refreshDashboardInfoInDrawer(apiClient) { + currentDrawerType = "admin", loadNavDrawer(), navDrawerScrollContainer.querySelector(".adminDrawerLogo") ? updateDashboardMenuSelectedItem() : createDashboardMenu(apiClient) + } + + function isUrlInCurrentView(url) { + return -1 !== window.location.href.toString().toLowerCase().indexOf(url.toLowerCase()) + } + + function updateDashboardMenuSelectedItem() { + for (var links = navDrawerScrollContainer.querySelectorAll(".navMenuOption"), currentViewId = viewManager.currentView().id, i = 0, length = links.length; i < length; i++) { + var link = links[i], + selected = !1, + pageIds = link.getAttribute("data-pageids"); + pageIds && (pageIds = pageIds.split("|"), selected = -1 != pageIds.indexOf(currentViewId)); + var pageUrls = link.getAttribute("data-pageurls"); + if (pageUrls && (pageUrls = pageUrls.split("|"), selected = pageUrls.filter(isUrlInCurrentView).length > 0), selected) { + link.classList.add("navMenuOption-selected"); + var title = ""; + link = link.querySelector("span") || link; + title += (link.innerText || link.textContent).trim(), LibraryMenu.setTitle(title) + } else link.classList.remove("navMenuOption-selected") + } + } + + function createToolsMenuList(pluginItems) { + var links = [{ + name: globalize.translate("TabServer") + }, { + name: globalize.translate("TabDashboard"), + href: "dashboard.html", + pageIds: ["dashboardPage", "serverActivityPage"], + icon: "dashboard" + }, { + name: globalize.translate("TabSettings"), + href: "dashboardgeneral.html", + pageIds: ["dashboardGeneralPage"], + icon: "settings" + }, { + name: globalize.translate("TabUsers"), + href: "userprofiles.html", + pageIds: ["userProfilesPage", "newUserPage", "editUserPage", "userLibraryAccessPage", "userParentalControlPage", "userPasswordPage"], + icon: "people" + }, { + name: "Emby Premiere", + href: "supporterkey.html", + pageIds: ["supporterKeyPage"], + icon: "star" + }, { + name: globalize.translate("TabLibrary"), + href: "library.html", + pageIds: ["mediaLibraryPage", "librarySettingsPage", "libraryDisplayPage", "metadataImagesConfigurationPage", "metadataNfoPage"], + icon: "folder", + color: "#38c" + }, { + name: globalize.translate("TabPlayback"), + icon: "play_circle_filled", + color: "#E5342E", + href: "playbackconfiguration.html", + pageIds: ["playbackConfigurationPage", "streamingSettingsPage"] + }, { + name: globalize.translate("TabTranscoding"), + icon: "transform", + href: "encodingsettings.html", + pageIds: ["encodingSettingsPage"] + }]; + return addPluginPagesToMainMenu(links, pluginItems, "server"), links.push({ + divider: !0, + name: globalize.translate("TabDevices") + }), links.push({ + name: globalize.translate("TabDevices"), + href: "devices/devices.html", + pageIds: ["devicesPage", "devicePage"], + icon: "tablet" + }), links.push({ + name: globalize.translate("HeaderDownloadSync"), + icon: "file_download", + href: "syncactivity.html", + pageIds: ["syncActivityPage", "syncJobPage", "syncSettingsPage"], + color: "#009688" + }), links.push({ + name: globalize.translate("TabCameraUpload"), + href: "devicesupload.html", + pageIds: ["devicesUploadPage"], + icon: "photo_camera" + }), links.push({ + name: globalize.translate("DLNA"), + href: "dlnasettings.html", + pageIds: ["dlnaSettingsPage", "dlnaProfilesPage", "dlnaProfilePage"], + icon: "" + }), links.push({ + divider: !0, + name: globalize.translate("TabLiveTV") + }), links.push({ + name: globalize.translate("TabLiveTV"), + href: "livetvstatus.html", + pageIds: ["liveTvStatusPage", "liveTvTunerPage"], + icon: "" + }), links.push({ + name: globalize.translate("DVR"), + href: "livetvsettings.html", + pageIds: ["liveTvSettingsPage"], + icon: "dvr" + }), links.push({ + divider: !0, + name: globalize.translate("TabExpert") + }), links.push({ + name: globalize.translate("TabAdvanced"), + icon: "settings", + href: "dashboardhosting.html", + color: "#F16834", + pageIds: ["dashboardHostingPage", "serverSecurityPage"] + }), links.push({ + name: globalize.translate("TabLogs"), + href: "log.html", + pageIds: ["logPage"], + icon: "folder_open" + }), links.push({ + name: globalize.translate("TabNotifications"), + icon: "notifications", + color: "brown", + href: "notificationsettings.html", + pageIds: ["notificationSettingsPage", "notificationSettingPage"] + }), links.push({ + name: globalize.translate("TabPlugins"), + icon: "add_shopping_cart", + color: "#9D22B1", + href: "plugins.html", + pageIds: ["pluginsPage", "pluginCatalogPage"] + }), links.push({ + name: globalize.translate("TabScheduledTasks"), + href: "scheduledtasks.html", + pageIds: ["scheduledTasksPage", "scheduledTaskPage"], + icon: "schedule" + }), links.push({ + name: globalize.translate("MetadataManager"), + href: "edititemmetadata.html", + pageIds: [], + icon: "mode_edit" + }), addPluginPagesToMainMenu(links, pluginItems), links + } + + function addPluginPagesToMainMenu(links, pluginItems, section) { + for (var i = 0, length = pluginItems.length; i < length; i++) { + var pluginItem = pluginItems[i]; + Dashboard.allowPluginPages(pluginItem.PluginId) && (pluginItem.EnableInMainMenu && pluginItem.MenuSection === section && links.push({ + name: pluginItem.DisplayName, + icon: pluginItem.MenuIcon || "folder", + href: Dashboard.getConfigurationPageUrl(pluginItem.Name), + pageUrls: [Dashboard.getConfigurationPageUrl(pluginItem.Name)] + })) + } + } + + function getToolsMenuLinks(apiClient) { + return apiClient.getJSON(apiClient.getUrl("web/configurationpages") + "?pageType=PluginConfiguration&EnableInMainMenu=true").then(createToolsMenuList, function(err) { + return createToolsMenuList([]) + }) + } + + function getToolsLinkHtml(item) { + var menuHtml = "", + pageIds = item.pageIds ? item.pageIds.join("|") : ""; + pageIds = pageIds ? ' data-pageids="' + pageIds + '"' : ""; + var pageUrls = item.pageUrls ? item.pageUrls.join("|") : ""; + return pageUrls = pageUrls ? ' data-pageurls="' + pageUrls + '"' : "", menuHtml += '", item.icon && (menuHtml += '' + item.icon + ""), menuHtml += '', menuHtml += item.name, menuHtml += "", menuHtml += "" + } + + function getToolsMenuHtml(apiClient) { + return getToolsMenuLinks(apiClient).then(function(items) { + var i, length, item, menuHtml = ""; + for (menuHtml += '
    ', i = 0, length = items.length; i < length; i++) item = items[i], item.href ? menuHtml += getToolsLinkHtml(item) : item.name && (menuHtml += '

    ', menuHtml += item.name, menuHtml += "

    "); + return menuHtml += "
    " + }) + } + + function createDashboardMenu(apiClient) { + return getToolsMenuHtml(apiClient).then(function(toolsMenuHtml) { + var html = ""; + html += '", html += toolsMenuHtml, navDrawerScrollContainer.innerHTML = html, updateDashboardMenuSelectedItem() + }) + } + + function onSidebarLinkClick() { + var section = this.getElementsByClassName("sectionName")[0], + text = section ? section.innerHTML : this.innerHTML; + LibraryMenu.setTitle(text) + } + + function getUserViews(apiClient, userId) { + return apiClient.getUserViews({}, userId).then(function(result) { + for (var items = result.Items, list = [], i = 0, length = items.length; i < length; i++) { + var view = items[i]; + if (list.push(view), "livetv" == view.CollectionType) { + view.ImageTags = {}, view.icon = "live_tv"; + var guideView = Object.assign({}, view); + guideView.Name = globalize.translate("ButtonGuide"), guideView.ImageTags = {}, guideView.icon = "dvr", guideView.url = "livetv.html?tab=1", list.push(guideView) + } + } + return list + }) + } + + function showBySelector(selector, show) { + var elem = document.querySelector(selector); + elem && (show ? elem.classList.remove("hide") : elem.classList.add("hide")) + } + + function updateLibraryMenu(user) { + if (!user) return showBySelector(".libraryMenuDownloads", !1), showBySelector(".lnkSyncToOtherDevices", !1), void showBySelector(".userMenuOptions", !1); + user.Policy.EnableContentDownloading ? showBySelector(".lnkSyncToOtherDevices", !0) : showBySelector(".lnkSyncToOtherDevices", !1), user.Policy.EnableContentDownloading && appHost.supports("sync") ? showBySelector(".libraryMenuDownloads", !0) : showBySelector(".libraryMenuDownloads", !1); + var userId = Dashboard.getCurrentUserId(), + apiClient = getCurrentApiClient(), + libraryMenuOptions = document.querySelector(".libraryMenuOptions"); + libraryMenuOptions && getUserViews(apiClient, userId).then(function(result) { + var items = result, + html = ""; + html += '

    ', html += globalize.translate("HeaderMedia"), html += "

    ", html += items.map(function(i) { + var icon = "folder", + itemId = i.Id; + "channels" == i.CollectionType ? itemId = "channels" : "livetv" == i.CollectionType && (itemId = "livetv"), "photos" == i.CollectionType ? icon = "photo_library" : "music" == i.CollectionType || "musicvideos" == i.CollectionType ? icon = "library_music" : "books" == i.CollectionType ? icon = "library_books" : "playlists" == i.CollectionType ? icon = "view_list" : "games" == i.CollectionType ? icon = "games" : "movies" == i.CollectionType ? icon = "video_library" : "channels" == i.CollectionType || "Channel" == i.Type ? icon = "videocam" : "tvshows" == i.CollectionType ? icon = "tv" : "livetv" == i.CollectionType && (icon = "live_tv"), icon = i.icon || icon; + i.onclick && i.onclick; + return '' + icon + '' + i.Name + "" + }).join(""), libraryMenuOptions.innerHTML = html; + for (var elem = libraryMenuOptions, sidebarLinks = elem.querySelectorAll(".navMenuOption"), i = 0, length = sidebarLinks.length; i < length; i++) sidebarLinks[i].removeEventListener("click", onSidebarLinkClick), sidebarLinks[i].addEventListener("click", onSidebarLinkClick) + }) + } + + function getTopParentId() { + return getParameterByName("topParentId") || null + } + + function onMainDrawerClick(e) { + dom.parentWithTag(e.target, "A") && setTimeout(closeMainDrawer, 30) + } + + function onLogoutClick() { + Dashboard.logout() + } + + function updateCastIcon() { + var context = document, + info = playbackManager.getPlayerInfo(), + icon = headerCastButton.querySelector("i"); + info && !info.isLocalPlayer ? (icon.innerHTML = "", headerCastButton.classList.add("castButton-active"), context.querySelector(".headerSelectedPlayer").innerHTML = info.deviceName || info.name) : (icon.innerHTML = "", headerCastButton.classList.remove("castButton-active"), context.querySelector(".headerSelectedPlayer").innerHTML = "") + } + + function updateLibraryNavLinks(page) { + var i, length, isLiveTvPage = page.classList.contains("liveTvPage"), + isChannelsPage = page.classList.contains("channelsPage"), + isEditorPage = page.classList.contains("metadataEditorPage"), + isMySyncPage = page.classList.contains("mySyncPage"), + id = isLiveTvPage || isChannelsPage || isEditorPage || isMySyncPage || page.classList.contains("allLibraryPage") ? "" : getTopParentId() || "", + elems = document.getElementsByClassName("lnkMediaFolder"); + for (i = 0, length = elems.length; i < length; i++) { + var lnkMediaFolder = elems[i], + itemId = lnkMediaFolder.getAttribute("data-itemid"); + isChannelsPage && "channels" == itemId ? lnkMediaFolder.classList.add("navMenuOption-selected") : isLiveTvPage && "livetv" == itemId ? lnkMediaFolder.classList.add("navMenuOption-selected") : isEditorPage && "editor" == itemId ? lnkMediaFolder.classList.add("navMenuOption-selected") : isMySyncPage && "manageoffline" == itemId && -1 != window.location.href.toString().indexOf("mode=download") ? lnkMediaFolder.classList.add("navMenuOption-selected") : isMySyncPage && "syncotherdevices" == itemId && -1 == window.location.href.toString().indexOf("mode=download") ? lnkMediaFolder.classList.add("navMenuOption-selected") : id && itemId == id ? lnkMediaFolder.classList.add("navMenuOption-selected") : lnkMediaFolder.classList.remove("navMenuOption-selected") + } + } + + function updateMenuForPageType(isDashboardPage, isLibraryPage) { + var newPageType = isDashboardPage ? 2 : isLibraryPage ? 1 : 3; + if (currentPageType !== newPageType) { + currentPageType = newPageType, isDashboardPage && !layoutManager.mobile ? skinHeader.classList.add("headroomDisabled") : skinHeader.classList.remove("headroomDisabled"); + var bodyClassList = document.body.classList; + isLibraryPage ? (bodyClassList.add("libraryDocument"), bodyClassList.remove("dashboardDocument"), bodyClassList.remove("hideMainDrawer"), navDrawerInstance && navDrawerInstance.setEdgeSwipeEnabled(!0)) : isDashboardPage ? (bodyClassList.remove("libraryDocument"), bodyClassList.add("dashboardDocument"), bodyClassList.remove("hideMainDrawer"), navDrawerInstance && navDrawerInstance.setEdgeSwipeEnabled(!0)) : (bodyClassList.remove("libraryDocument"), bodyClassList.remove("dashboardDocument"), bodyClassList.add("hideMainDrawer"), navDrawerInstance && navDrawerInstance.setEdgeSwipeEnabled(!1)) + } + requiresUserRefresh && connectionManager.user(getCurrentApiClient()).then(updateUserInHeader) + } + + function updateTitle(page) { + var title = page.getAttribute("data-title"); + title ? LibraryMenu.setTitle(title) : page.classList.contains("standalonePage") && LibraryMenu.setDefaultTitle() + } + + function updateBackButton(page) { + headerBackButton || (headerBackButton = document.querySelector(".headerBackButton")), headerBackButton && ("false" !== page.getAttribute("data-backbutton") && appRouter.canGoBack() ? headerBackButton.classList.remove("hide") : headerBackButton.classList.add("hide")) + } + + function initHeadRoom(elem) { + require(["headroom-window"], function(headroom) { + headroom.add(elem) + }) + } + + function refreshLibraryDrawer(user) { + loadNavDrawer(), currentDrawerType = "library", (user ? Promise.resolve(user) : connectionManager.user(getCurrentApiClient())).then(function(user) { + refreshLibraryInfoInDrawer(user), updateLibraryMenu(user.localUser) + }) + } + + function getNavDrawerOptions() { + var drawerWidth = screen.availWidth - 50; + return drawerWidth = Math.max(drawerWidth, 240), drawerWidth = Math.min(drawerWidth, 320), { + target: navDrawerElement, + onChange: onMainDrawerSelect, + width: drawerWidth + } + } + + function loadNavDrawer() { + return navDrawerInstance ? Promise.resolve(navDrawerInstance) : (navDrawerElement = document.querySelector(".mainDrawer"), navDrawerScrollContainer = navDrawerElement.querySelector(".scrollContainer"), navDrawerScrollContainer.addEventListener("click", onMainDrawerClick), new Promise(function(resolve, reject) { + require(["navdrawer"], function(navdrawer) { + navDrawerInstance = new navdrawer(getNavDrawerOptions()), navDrawerElement.classList.remove("hide"), resolve(navDrawerInstance) + }) + })) + } + var navDrawerElement, navDrawerScrollContainer, navDrawerInstance, mainDrawerButton, headerHomeButton, currentDrawerType, pageTitleElement, headerBackButton, headerUserButton, currentUser, headerSettingsButton, headerCastButton, headerSearchButton, enableLibraryNavDrawer = !layoutManager.tv, + skinHeader = document.querySelector(".skinHeader"), + requiresUserRefresh = !0, + lastOpenTime = (new Date).getTime(); + window.LibraryMenu = { + getTopParentId: getTopParentId, + onHardwareMenuButtonClick: function() { + toggleMainDrawer() + }, + setTabs: function(type, selectedIndex, builder) { + require(["mainTabsManager"], function(mainTabsManager) { + type ? mainTabsManager.setTabs(viewManager.currentView(), selectedIndex, builder, function() { + return [] + }) : mainTabsManager.setTabs(null) + }) + }, + setDefaultTitle: function() { + pageTitleElement || (pageTitleElement = document.querySelector(".pageTitle")), pageTitleElement && (pageTitleElement.classList.add("pageTitleWithLogo"), pageTitleElement.classList.add("pageTitleWithDefaultLogo"), pageTitleElement.style.backgroundImage = null, pageTitleElement.innerHTML = ""), document.title = "Emby" + }, + setTitle: function(title) { + if (null == title) return void LibraryMenu.setDefaultTitle(); + "-" === title && (title = ""); + var html = title; + pageTitleElement || (pageTitleElement = document.querySelector(".pageTitle")), pageTitleElement && (pageTitleElement.classList.remove("pageTitleWithLogo"), pageTitleElement.classList.remove("pageTitleWithDefaultLogo"), pageTitleElement.style.backgroundImage = null, pageTitleElement.innerHTML = html || ""), document.title = title || "Emby" + }, + setTransparentMenu: function(transparent) { + transparent ? skinHeader.classList.add("semiTransparent") : skinHeader.classList.remove("semiTransparent") + } + }; + var currentPageType; + return pageClassOn("pagebeforeshow", "page", function(e) { + this.classList.contains("withTabs") || LibraryMenu.setTabs(null) + }), pageClassOn("pageshow", "page", function(e) { + var page = this, + isDashboardPage = page.classList.contains("type-interior"), + isLibraryPage = !isDashboardPage && page.classList.contains("libraryPage"), + apiClient = getCurrentApiClient(); + isDashboardPage ? (mainDrawerButton && mainDrawerButton.classList.remove("hide"), refreshDashboardInfoInDrawer(apiClient)) : (mainDrawerButton && (enableLibraryNavDrawer ? mainDrawerButton.classList.remove("hide") : mainDrawerButton.classList.add("hide")), "library" !== currentDrawerType && refreshLibraryDrawer()), updateMenuForPageType(isDashboardPage, isLibraryPage), e.detail.isRestored || window.scrollTo(0, 0), updateTitle(page), updateBackButton(page), updateLibraryNavLinks(page) + }), + function() { + var html = ""; + html += '
    ', html += '
    ', html += '", html += '', html += '', html += '

    ', html += "
    ", html += '
    ', html += '', html += '', html += '', html += '', layoutManager.mobile || (html += ''), html += "
    ", html += "
    ", html += '
    ', html += "
    ", skinHeader.classList.add("skinHeader-withBackground"), skinHeader.innerHTML = html, headerHomeButton = skinHeader.querySelector(".headerHomeButton"), headerUserButton = skinHeader.querySelector(".headerUserButton"), headerSettingsButton = skinHeader.querySelector(".headerSettingsButton"), headerCastButton = skinHeader.querySelector(".headerCastButton"), headerSearchButton = skinHeader.querySelector(".headerSearchButton"), browser.chrome || skinHeader.classList.add("skinHeader-blurred"), lazyLoadViewMenuBarImages(), bindMenuEvents() + }(), events.on(connectionManager, "localusersignedin", function(e, user) { + currentDrawerType = null, currentUser = { + localUser: user + }, loadNavDrawer(), connectionManager.user(connectionManager.getApiClient(user.ServerId)).then(function(user) { + currentUser = user, updateUserInHeader(user) + }) + }), events.on(connectionManager, "localusersignedout", function() { + currentUser = {}, updateUserInHeader() + }), events.on(playbackManager, "playerchange", updateCastIcon), loadNavDrawer(), LibraryMenu +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/livetvchannels.js b/dashboard-ui/scripts/livetvchannels.js index 345492dacc..beba62ecfb 100644 --- a/dashboard-ui/scripts/livetvchannels.js +++ b/dashboard-ui/scripts/livetvchannels.js @@ -1 +1,84 @@ -define(["cardBuilder","imageLoader","libraryBrowser","loading","events","emby-itemscontainer"],function(cardBuilder,imageLoader,libraryBrowser,loading,events){"use strict";return function(view,params,tabContent){function getPageData(){return pageData||(pageData={query:{StartIndex:0,Limit:100,Fields:"PrimaryImageAspectRatio"}}),pageData}function getQuery(){return getPageData().query}function getChannelsHtml(channels){return cardBuilder.getCardsHtml({items:channels,shape:"square",showTitle:!0,lazy:!0,cardLayout:!0,showDetailsMenu:!0,showCurrentProgram:!0,showCurrentProgramTime:!0})}function renderChannels(context,result){function onNextPageClick(){query.StartIndex+=query.Limit,reloadItems(context)}function onPreviousPageClick(){query.StartIndex-=query.Limit,reloadItems(context)}var query=getQuery();context.querySelector(".paging").innerHTML=libraryBrowser.getQueryPagingHtml({startIndex:query.StartIndex,limit:query.Limit,totalRecordCount:result.TotalRecordCount,showLimit:!1,updatePageSizeSetting:!1,filterButton:!1});var html=getChannelsHtml(result.Items),elem=context.querySelector("#items");elem.innerHTML=html,imageLoader.lazyChildren(elem);var i,length,elems;for(elems=context.querySelectorAll(".btnNextPage"),i=0,length=elems.length;i',html+='

    '+group.name+"

    "),enableScrollX()){var scrollXClass="scrollX hiddenScrollX";layoutManager.tv&&(scrollXClass+=" smoothScrollX"),html+='
    '}else html+='
    ';html+=cardBuilder.getCardsHtml({items:group.items,shape:cardLayout?getBackdropShape():enableScrollX()?"autoOverflow":"autoVertical",showParentTitleOrTitle:!0,showAirTime:!0,showAirEndTime:!0,showChannelName:!cardLayout,cardLayout:cardLayout,centerText:!cardLayout,action:"edit",cardFooterAside:"none",preferThumb:!!cardLayout||"auto",defaultShape:cardLayout?null:"portrait",coverImage:!0,allowBottomPadding:!1,overlayText:!1,showChannelLogo:cardLayout}),html+="
    ",group.name&&(html+="
    ")}return Promise.resolve(html)}window.LiveTvHelpers={getTimersHtml:getTimersHtml}}); \ No newline at end of file +define(["layoutManager", "datetime", "cardBuilder", "apphost"], function(layoutManager, datetime, cardBuilder, appHost) { + "use strict"; + + function enableScrollX() { + return !layoutManager.desktop + } + + function getBackdropShape() { + return enableScrollX() ? "overflowBackdrop" : "backdrop" + } + + function getTimersHtml(timers, options) { + options = options || {}; + var i, length, items = timers.map(function(t) { + return t.Type = "Timer", t + }), + groups = [], + currentGroupName = "", + currentGroup = []; + for (i = 0, length = items.length; i < length; i++) { + var item = items[i], + dateText = ""; + if (!1 !== options.indexByDate && item.StartDate) try { + var premiereDate = datetime.parseISO8601Date(item.StartDate, !0); + dateText = datetime.toLocaleDateString(premiereDate, { + weekday: "long", + month: "short", + day: "numeric" + }) + } catch (err) {} + dateText != currentGroupName ? (currentGroup.length && groups.push({ + name: currentGroupName, + items: currentGroup + }), currentGroupName = dateText, currentGroup = [item]) : currentGroup.push(item) + } + currentGroup.length && groups.push({ + name: currentGroupName, + items: currentGroup + }); + var html = ""; + for (i = 0, length = groups.length; i < length; i++) { + var group = groups[i], + supportsImageAnalysis = appHost.supports("imageanalysis"), + cardLayout = appHost.preferVisualCards || supportsImageAnalysis; + if (cardLayout = !0, group.name && (html += '
    ', html += '

    ' + group.name + "

    "), enableScrollX()) { + var scrollXClass = "scrollX hiddenScrollX"; + layoutManager.tv && (scrollXClass += " smoothScrollX"), html += '
    ' + } else html += '
    '; + html += cardBuilder.getCardsHtml({ + items: group.items, + shape: cardLayout ? getBackdropShape() : enableScrollX() ? "autoOverflow" : "autoVertical", + showParentTitleOrTitle: !0, + showAirTime: !0, + showAirEndTime: !0, + showChannelName: !cardLayout, + cardLayout: cardLayout, + centerText: !cardLayout, + action: "edit", + cardFooterAside: "none", + preferThumb: !!cardLayout || "auto", + defaultShape: cardLayout ? null : "portrait", + coverImage: !0, + allowBottomPadding: !1, + overlayText: !1, + showChannelLogo: cardLayout + }), html += "
    ", group.name && (html += "
    ") + } + return Promise.resolve(html) + } + window.LiveTvHelpers = { + getTimersHtml: getTimersHtml + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/livetvguide.js b/dashboard-ui/scripts/livetvguide.js index c301d84305..3c8b3f4109 100644 --- a/dashboard-ui/scripts/livetvguide.js +++ b/dashboard-ui/scripts/livetvguide.js @@ -1 +1,16 @@ -define(["tvguide"],function(tvguide){"use strict";return function(view,params,tabContent){var guideInstance,self=this;self.renderTab=function(){guideInstance||(guideInstance=new tvguide({element:tabContent,serverId:ApiClient.serverId()}))},self.onShow=function(){guideInstance&&guideInstance.resume()},self.onHide=function(){guideInstance&&guideInstance.pause()}}}); \ No newline at end of file +define(["tvguide"], function(tvguide) { + "use strict"; + return function(view, params, tabContent) { + var guideInstance, self = this; + self.renderTab = function() { + guideInstance || (guideInstance = new tvguide({ + element: tabContent, + serverId: ApiClient.serverId() + })) + }, self.onShow = function() { + guideInstance && guideInstance.resume() + }, self.onHide = function() { + guideInstance && guideInstance.pause() + } + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/livetvguideprovider.js b/dashboard-ui/scripts/livetvguideprovider.js index 7b5952a7fc..40617cdb90 100644 --- a/dashboard-ui/scripts/livetvguideprovider.js +++ b/dashboard-ui/scripts/livetvguideprovider.js @@ -1 +1,26 @@ -define(["events","loading"],function(events,loading){"use strict";function onListingsSubmitted(){Dashboard.navigate("livetvstatus.html")}function init(page,type,providerId){var url="components/tvproviders/"+type+".js";require([url],function(factory){var instance=new factory(page,providerId,{});events.on(instance,"submitted",onListingsSubmitted),instance.init()})}function loadTemplate(page,type,providerId){require(["text!./components/tvproviders/"+type+".template.html"],function(html){page.querySelector(".providerTemplate").innerHTML=Globalize.translateDocument(html),init(page,type,providerId)})}pageIdOn("pageshow","liveTvGuideProviderPage",function(){loading.show();var providerId=getParameterByName("id");loadTemplate(this,getParameterByName("type"),providerId)})}); \ No newline at end of file +define(["events", "loading"], function(events, loading) { + "use strict"; + + function onListingsSubmitted() { + Dashboard.navigate("livetvstatus.html") + } + + function init(page, type, providerId) { + var url = "components/tvproviders/" + type + ".js"; + require([url], function(factory) { + var instance = new factory(page, providerId, {}); + events.on(instance, "submitted", onListingsSubmitted), instance.init() + }) + } + + function loadTemplate(page, type, providerId) { + require(["text!./components/tvproviders/" + type + ".template.html"], function(html) { + page.querySelector(".providerTemplate").innerHTML = Globalize.translateDocument(html), init(page, type, providerId) + }) + } + pageIdOn("pageshow", "liveTvGuideProviderPage", function() { + loading.show(); + var providerId = getParameterByName("id"); + loadTemplate(this, getParameterByName("type"), providerId) + }) +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/livetvrecordings.js b/dashboard-ui/scripts/livetvrecordings.js index 1aee6e6021..6c0ee4e515 100644 --- a/dashboard-ui/scripts/livetvrecordings.js +++ b/dashboard-ui/scripts/livetvrecordings.js @@ -1 +1,71 @@ -define(["layoutManager","loading","components/categorysyncbuttons","cardBuilder","apphost","imageLoader","scripts/livetvcomponents","listViewStyle","emby-itemscontainer"],function(layoutManager,loading,categorysyncbuttons,cardBuilder,appHost,imageLoader){"use strict";function renderRecordings(elem,recordings,cardOptions,scrollX){recordings.length?elem.classList.remove("hide"):elem.classList.add("hide");var recordingItems=elem.querySelector(".recordingItems");scrollX?(recordingItems.classList.add("scrollX"),recordingItems.classList.add("hiddenScrollX"),recordingItems.classList.remove("vertical-wrap")):(recordingItems.classList.remove("scrollX"),recordingItems.classList.remove("hiddenScrollX"),recordingItems.classList.add("vertical-wrap"));appHost.supports("imageanalysis");recordingItems.innerHTML=cardBuilder.getCardsHtml(Object.assign({items:recordings,shape:scrollX?"autooverflow":"auto",defaultShape:scrollX?"overflowBackdrop":"backdrop",showTitle:!0,showParentTitle:!0,coverImage:!0,cardLayout:!1,centerText:!0,vibrant:!1,allowBottomPadding:!scrollX,preferThumb:"auto",overlayText:!1},cardOptions||{})),imageLoader.lazyChildren(recordingItems)}function renderLatestRecordings(context,promise){promise.then(function(result){renderRecordings(context.querySelector("#latestRecordings"),result.Items,{showYear:!0,lines:2},!1),loading.hide()})}function renderRecordingFolders(context,promise){promise.then(function(result){renderRecordings(context.querySelector("#recordingFolders"),result.Items,{showYear:!1,showParentTitle:!1},!1)})}function onMoreClick(e){var type=this.getAttribute("data-type"),serverId=ApiClient.serverId();switch(type){case"latest":Dashboard.navigate("list/list.html?type=Recordings&serverId="+serverId)}}return function(view,params,tabContent){function enableFullRender(){return(new Date).getTime()-lastFullRender>3e5}var foldersPromise,latestPromise,self=this,lastFullRender=0;categorysyncbuttons.init(tabContent);for(var moreButtons=tabContent.querySelectorAll(".more"),i=0,length=moreButtons.length;i 3e5 + } + var foldersPromise, latestPromise, self = this, + lastFullRender = 0; + categorysyncbuttons.init(tabContent); + for (var moreButtons = tabContent.querySelectorAll(".more"), i = 0, length = moreButtons.length; i < length; i++) moreButtons[i].addEventListener("click", onMoreClick); + self.preRender = function() { + enableFullRender() && (latestPromise = ApiClient.getLiveTvRecordings({ + UserId: Dashboard.getCurrentUserId(), + Limit: 12, + Fields: "CanDelete,PrimaryImageAspectRatio,BasicSyncInfo", + EnableTotalRecordCount: !1, + EnableImageTypes: "Primary,Thumb,Backdrop" + }), foldersPromise = ApiClient.getRecordingFolders(Dashboard.getCurrentUserId())) + }, self.renderTab = function() { + enableFullRender() && (loading.show(), renderLatestRecordings(tabContent, latestPromise), renderRecordingFolders(tabContent, foldersPromise), lastFullRender = (new Date).getTime()) + } + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/livetvschedule.js b/dashboard-ui/scripts/livetvschedule.js index 366c7040eb..8b31d4907b 100644 --- a/dashboard-ui/scripts/livetvschedule.js +++ b/dashboard-ui/scripts/livetvschedule.js @@ -1 +1,81 @@ -define(["layoutManager","cardBuilder","apphost","imageLoader","loading","scripts/livetvcomponents","emby-button","emby-itemscontainer"],function(layoutManager,cardBuilder,appHost,imageLoader,loading){"use strict";function enableScrollX(){return!layoutManager.desktop}function renderRecordings(elem,recordings,cardOptions){recordings.length?elem.classList.remove("hide"):elem.classList.add("hide");var recordingItems=elem.querySelector(".recordingItems");enableScrollX()?(recordingItems.classList.add("scrollX"),layoutManager.tv&&recordingItems.classList.add("smoothScrollX"),recordingItems.classList.add("hiddenScrollX"),recordingItems.classList.remove("vertical-wrap")):(recordingItems.classList.remove("scrollX"),recordingItems.classList.remove("smoothScrollX"),recordingItems.classList.remove("hiddenScrollX"),recordingItems.classList.add("vertical-wrap"));var supportsImageAnalysis=appHost.supports("imageanalysis"),cardLayout=appHost.preferVisualCards||supportsImageAnalysis;cardLayout=!1,recordingItems.innerHTML=cardBuilder.getCardsHtml(Object.assign({items:recordings,shape:enableScrollX()?"autooverflow":"auto",showTitle:!0,showParentTitle:!0,coverImage:!0,cardLayout:cardLayout,centerText:!cardLayout,vibrant:cardLayout&&supportsImageAnalysis,allowBottomPadding:!enableScrollX(),preferThumb:"auto"},cardOptions||{})),imageLoader.lazyChildren(recordingItems)}function getBackdropShape(){return enableScrollX()?"overflowBackdrop":"backdrop"}function renderActiveRecordings(context,promise){promise.then(function(result){renderRecordings(context.querySelector("#activeRecordings"),result.Items,{shape:enableScrollX()?"autooverflow":"auto",defaultShape:getBackdropShape(),showParentTitle:!1,showParentTitleOrTitle:!0,showTitle:!1,showAirTime:!0,showAirEndTime:!0,showChannelName:!0,coverImage:!0,overlayText:!1,overlayMoreButton:!0})})}function renderTimers(context,timers,options){LiveTvHelpers.getTimersHtml(timers,options).then(function(html){var elem=context;html?elem.classList.remove("hide"):elem.classList.add("hide"),elem.querySelector(".recordingItems").innerHTML=html,imageLoader.lazyChildren(elem)})}function renderUpcomingRecordings(context,promise){promise.then(function(result){renderTimers(context.querySelector("#upcomingRecordings"),result.Items),loading.hide()})}return function(view,params,tabContent){var activeRecordingsPromise,upcomingRecordingsPromise,self=this;tabContent.querySelector("#upcomingRecordings .recordingItems").addEventListener("timercancelled",function(){self.preRender(),self.renderTab()}),self.preRender=function(){activeRecordingsPromise=ApiClient.getLiveTvRecordings({UserId:Dashboard.getCurrentUserId(),IsInProgress:!0,Fields:"CanDelete,PrimaryImageAspectRatio,BasicSyncInfo",EnableTotalRecordCount:!1,EnableImageTypes:"Primary,Thumb,Backdrop"}),upcomingRecordingsPromise=ApiClient.getLiveTvTimers({IsActive:!1,IsScheduled:!0})},self.renderTab=function(){loading.show(),renderActiveRecordings(tabContent,activeRecordingsPromise),renderUpcomingRecordings(tabContent,upcomingRecordingsPromise)}}}); \ No newline at end of file +define(["layoutManager", "cardBuilder", "apphost", "imageLoader", "loading", "scripts/livetvcomponents", "emby-button", "emby-itemscontainer"], function(layoutManager, cardBuilder, appHost, imageLoader, loading) { + "use strict"; + + function enableScrollX() { + return !layoutManager.desktop + } + + function renderRecordings(elem, recordings, cardOptions) { + recordings.length ? elem.classList.remove("hide") : elem.classList.add("hide"); + var recordingItems = elem.querySelector(".recordingItems"); + enableScrollX() ? (recordingItems.classList.add("scrollX"), layoutManager.tv && recordingItems.classList.add("smoothScrollX"), recordingItems.classList.add("hiddenScrollX"), recordingItems.classList.remove("vertical-wrap")) : (recordingItems.classList.remove("scrollX"), recordingItems.classList.remove("smoothScrollX"), recordingItems.classList.remove("hiddenScrollX"), recordingItems.classList.add("vertical-wrap")); + var supportsImageAnalysis = appHost.supports("imageanalysis"), + cardLayout = appHost.preferVisualCards || supportsImageAnalysis; + cardLayout = !1, recordingItems.innerHTML = cardBuilder.getCardsHtml(Object.assign({ + items: recordings, + shape: enableScrollX() ? "autooverflow" : "auto", + showTitle: !0, + showParentTitle: !0, + coverImage: !0, + cardLayout: cardLayout, + centerText: !cardLayout, + vibrant: cardLayout && supportsImageAnalysis, + allowBottomPadding: !enableScrollX(), + preferThumb: "auto" + }, cardOptions || {})), imageLoader.lazyChildren(recordingItems) + } + + function getBackdropShape() { + return enableScrollX() ? "overflowBackdrop" : "backdrop" + } + + function renderActiveRecordings(context, promise) { + promise.then(function(result) { + renderRecordings(context.querySelector("#activeRecordings"), result.Items, { + shape: enableScrollX() ? "autooverflow" : "auto", + defaultShape: getBackdropShape(), + showParentTitle: !1, + showParentTitleOrTitle: !0, + showTitle: !1, + showAirTime: !0, + showAirEndTime: !0, + showChannelName: !0, + coverImage: !0, + overlayText: !1, + overlayMoreButton: !0 + }) + }) + } + + function renderTimers(context, timers, options) { + LiveTvHelpers.getTimersHtml(timers, options).then(function(html) { + var elem = context; + html ? elem.classList.remove("hide") : elem.classList.add("hide"), elem.querySelector(".recordingItems").innerHTML = html, imageLoader.lazyChildren(elem) + }) + } + + function renderUpcomingRecordings(context, promise) { + promise.then(function(result) { + renderTimers(context.querySelector("#upcomingRecordings"), result.Items), loading.hide() + }) + } + return function(view, params, tabContent) { + var activeRecordingsPromise, upcomingRecordingsPromise, self = this; + tabContent.querySelector("#upcomingRecordings .recordingItems").addEventListener("timercancelled", function() { + self.preRender(), self.renderTab() + }), self.preRender = function() { + activeRecordingsPromise = ApiClient.getLiveTvRecordings({ + UserId: Dashboard.getCurrentUserId(), + IsInProgress: !0, + Fields: "CanDelete,PrimaryImageAspectRatio,BasicSyncInfo", + EnableTotalRecordCount: !1, + EnableImageTypes: "Primary,Thumb,Backdrop" + }), upcomingRecordingsPromise = ApiClient.getLiveTvTimers({ + IsActive: !1, + IsScheduled: !0 + }) + }, self.renderTab = function() { + loading.show(), renderActiveRecordings(tabContent, activeRecordingsPromise), renderUpcomingRecordings(tabContent, upcomingRecordingsPromise) + } + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/livetvseriestimers.js b/dashboard-ui/scripts/livetvseriestimers.js index 3be4a94eb9..5acd9f326c 100644 --- a/dashboard-ui/scripts/livetvseriestimers.js +++ b/dashboard-ui/scripts/livetvseriestimers.js @@ -1 +1,43 @@ -define(["datetime","cardBuilder","imageLoader","apphost","loading","paper-icon-button-light","emby-button"],function(datetime,cardBuilder,imageLoader,appHost,loading){"use strict";function renderTimers(context,timers){var html="";appHost.supports("imageanalysis");html+=cardBuilder.getCardsHtml({items:timers,shape:"auto",defaultShape:"portrait",showTitle:!0,cardLayout:!1,preferThumb:"auto",coverImage:!0,overlayText:!1,showSeriesTimerTime:!0,showSeriesTimerChannel:!0,centerText:!0,overlayMoreButton:!0,lines:3});var elem=context.querySelector("#items");elem.innerHTML=html,imageLoader.lazyChildren(elem),loading.hide()}function reload(context,promise){loading.show(),promise.then(function(result){renderTimers(context,result.Items)})}var query={SortBy:"SortName",SortOrder:"Ascending"};return function(view,params,tabContent){var timersPromise,self=this;self.preRender=function(){timersPromise=ApiClient.getLiveTvSeriesTimers(query)},self.renderTab=function(){reload(tabContent,timersPromise)}}}); \ No newline at end of file +define(["datetime", "cardBuilder", "imageLoader", "apphost", "loading", "paper-icon-button-light", "emby-button"], function(datetime, cardBuilder, imageLoader, appHost, loading) { + "use strict"; + + function renderTimers(context, timers) { + var html = ""; + appHost.supports("imageanalysis"); + html += cardBuilder.getCardsHtml({ + items: timers, + shape: "auto", + defaultShape: "portrait", + showTitle: !0, + cardLayout: !1, + preferThumb: "auto", + coverImage: !0, + overlayText: !1, + showSeriesTimerTime: !0, + showSeriesTimerChannel: !0, + centerText: !0, + overlayMoreButton: !0, + lines: 3 + }); + var elem = context.querySelector("#items"); + elem.innerHTML = html, imageLoader.lazyChildren(elem), loading.hide() + } + + function reload(context, promise) { + loading.show(), promise.then(function(result) { + renderTimers(context, result.Items) + }) + } + var query = { + SortBy: "SortName", + SortOrder: "Ascending" + }; + return function(view, params, tabContent) { + var timersPromise, self = this; + self.preRender = function() { + timersPromise = ApiClient.getLiveTvSeriesTimers(query) + }, self.renderTab = function() { + reload(tabContent, timersPromise) + } + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/livetvsettings.js b/dashboard-ui/scripts/livetvsettings.js index 632739dae0..4d659ad6b4 100644 --- a/dashboard-ui/scripts/livetvsettings.js +++ b/dashboard-ui/scripts/livetvsettings.js @@ -1 +1,79 @@ -define(["jQuery","loading","fnchecked","emby-linkbutton"],function($,loading){"use strict";function loadPage(page,config){$(".liveTvSettingsForm",page).show(),$(".noLiveTvServices",page).hide(),$("#selectGuideDays",page).val(config.GuideDays||""),$("#txtPrePaddingMinutes",page).val(config.PrePaddingSeconds/60),$("#txtPostPaddingMinutes",page).val(config.PostPaddingSeconds/60),page.querySelector("#txtRecordingPath").value=config.RecordingPath||"",page.querySelector("#txtMovieRecordingPath").value=config.MovieRecordingPath||"",page.querySelector("#txtSeriesRecordingPath").value=config.SeriesRecordingPath||"",page.querySelector("#txtPostProcessor").value=config.RecordingPostProcessor||"",page.querySelector("#txtPostProcessorArguments").value=config.RecordingPostProcessorArguments||"",loading.hide()}function onSubmit(){loading.show();var form=this;return ApiClient.getNamedConfiguration("livetv").then(function(config){config.GuideDays=$("#selectGuideDays",form).val()||null;var recordingPath=form.querySelector("#txtRecordingPath").value||null,movieRecordingPath=form.querySelector("#txtMovieRecordingPath").value||null,seriesRecordingPath=form.querySelector("#txtSeriesRecordingPath").value||null,recordingPathChanged=recordingPath!=config.RecordingPath||movieRecordingPath!=config.MovieRecordingPath||seriesRecordingPath!=config.SeriesRecordingPath;config.RecordingPath=recordingPath,config.MovieRecordingPath=movieRecordingPath,config.SeriesRecordingPath=seriesRecordingPath,config.RecordingEncodingFormat="mkv",config.PrePaddingSeconds=60*$("#txtPrePaddingMinutes",form).val(),config.PostPaddingSeconds=60*$("#txtPostPaddingMinutes",form).val(),config.RecordingPostProcessor=$("#txtPostProcessor",form).val(),config.RecordingPostProcessorArguments=$("#txtPostProcessorArguments",form).val(),ApiClient.updateNamedConfiguration("livetv",config).then(function(){Dashboard.processServerConfigurationUpdateResult(),showSaveMessage(recordingPathChanged)})}),!1}function showSaveMessage(recordingPathChanged){var msg="";recordingPathChanged&&(msg+=Globalize.translate("RecordingPathChangeMessage")),msg&&require(["alert"],function(alert){alert(msg)})}$(document).on("pageinit","#liveTvSettingsPage",function(){var page=this;$(".liveTvSettingsForm").off("submit",onSubmit).on("submit",onSubmit),$("#btnSelectRecordingPath",page).on("click.selectDirectory",function(){require(["directorybrowser"],function(directoryBrowser){var picker=new directoryBrowser;picker.show({callback:function(path){path&&$("#txtRecordingPath",page).val(path),picker.close()},validateWriteable:!0})})}),$("#btnSelectMovieRecordingPath",page).on("click.selectDirectory",function(){require(["directorybrowser"],function(directoryBrowser){var picker=new directoryBrowser;picker.show({callback:function(path){path&&$("#txtMovieRecordingPath",page).val(path),picker.close()},validateWriteable:!0})})}),$("#btnSelectSeriesRecordingPath",page).on("click.selectDirectory",function(){require(["directorybrowser"],function(directoryBrowser){var picker=new directoryBrowser;picker.show({callback:function(path){path&&$("#txtSeriesRecordingPath",page).val(path),picker.close()},validateWriteable:!0})})}),$("#btnSelectPostProcessorPath",page).on("click.selectDirectory",function(){require(["directorybrowser"],function(directoryBrowser){var picker=new directoryBrowser;picker.show({includeFiles:!0,callback:function(path){path&&$("#txtPostProcessor",page).val(path),picker.close()}})})})}).on("pageshow","#liveTvSettingsPage",function(){loading.show();var page=this;ApiClient.getNamedConfiguration("livetv").then(function(config){loadPage(page,config)})})}); \ No newline at end of file +define(["jQuery", "loading", "fnchecked", "emby-linkbutton"], function($, loading) { + "use strict"; + + function loadPage(page, config) { + $(".liveTvSettingsForm", page).show(), $(".noLiveTvServices", page).hide(), $("#selectGuideDays", page).val(config.GuideDays || ""), $("#txtPrePaddingMinutes", page).val(config.PrePaddingSeconds / 60), $("#txtPostPaddingMinutes", page).val(config.PostPaddingSeconds / 60), page.querySelector("#txtRecordingPath").value = config.RecordingPath || "", page.querySelector("#txtMovieRecordingPath").value = config.MovieRecordingPath || "", page.querySelector("#txtSeriesRecordingPath").value = config.SeriesRecordingPath || "", page.querySelector("#txtPostProcessor").value = config.RecordingPostProcessor || "", page.querySelector("#txtPostProcessorArguments").value = config.RecordingPostProcessorArguments || "", loading.hide() + } + + function onSubmit() { + loading.show(); + var form = this; + return ApiClient.getNamedConfiguration("livetv").then(function(config) { + config.GuideDays = $("#selectGuideDays", form).val() || null; + var recordingPath = form.querySelector("#txtRecordingPath").value || null, + movieRecordingPath = form.querySelector("#txtMovieRecordingPath").value || null, + seriesRecordingPath = form.querySelector("#txtSeriesRecordingPath").value || null, + recordingPathChanged = recordingPath != config.RecordingPath || movieRecordingPath != config.MovieRecordingPath || seriesRecordingPath != config.SeriesRecordingPath; + config.RecordingPath = recordingPath, config.MovieRecordingPath = movieRecordingPath, config.SeriesRecordingPath = seriesRecordingPath, config.RecordingEncodingFormat = "mkv", config.PrePaddingSeconds = 60 * $("#txtPrePaddingMinutes", form).val(), config.PostPaddingSeconds = 60 * $("#txtPostPaddingMinutes", form).val(), config.RecordingPostProcessor = $("#txtPostProcessor", form).val(), config.RecordingPostProcessorArguments = $("#txtPostProcessorArguments", form).val(), ApiClient.updateNamedConfiguration("livetv", config).then(function() { + Dashboard.processServerConfigurationUpdateResult(), showSaveMessage(recordingPathChanged) + }) + }), !1 + } + + function showSaveMessage(recordingPathChanged) { + var msg = ""; + recordingPathChanged && (msg += Globalize.translate("RecordingPathChangeMessage")), msg && require(["alert"], function(alert) { + alert(msg) + }) + } + $(document).on("pageinit", "#liveTvSettingsPage", function() { + var page = this; + $(".liveTvSettingsForm").off("submit", onSubmit).on("submit", onSubmit), $("#btnSelectRecordingPath", page).on("click.selectDirectory", function() { + require(["directorybrowser"], function(directoryBrowser) { + var picker = new directoryBrowser; + picker.show({ + callback: function(path) { + path && $("#txtRecordingPath", page).val(path), picker.close() + }, + validateWriteable: !0 + }) + }) + }), $("#btnSelectMovieRecordingPath", page).on("click.selectDirectory", function() { + require(["directorybrowser"], function(directoryBrowser) { + var picker = new directoryBrowser; + picker.show({ + callback: function(path) { + path && $("#txtMovieRecordingPath", page).val(path), picker.close() + }, + validateWriteable: !0 + }) + }) + }), $("#btnSelectSeriesRecordingPath", page).on("click.selectDirectory", function() { + require(["directorybrowser"], function(directoryBrowser) { + var picker = new directoryBrowser; + picker.show({ + callback: function(path) { + path && $("#txtSeriesRecordingPath", page).val(path), picker.close() + }, + validateWriteable: !0 + }) + }) + }), $("#btnSelectPostProcessorPath", page).on("click.selectDirectory", function() { + require(["directorybrowser"], function(directoryBrowser) { + var picker = new directoryBrowser; + picker.show({ + includeFiles: !0, + callback: function(path) { + path && $("#txtPostProcessor", page).val(path), picker.close() + } + }) + }) + }) + }).on("pageshow", "#liveTvSettingsPage", function() { + loading.show(); + var page = this; + ApiClient.getNamedConfiguration("livetv").then(function(config) { + loadPage(page, config) + }) + }) +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/livetvstatus.js b/dashboard-ui/scripts/livetvstatus.js index 1f96ec7403..96f7b3dd91 100644 --- a/dashboard-ui/scripts/livetvstatus.js +++ b/dashboard-ui/scripts/livetvstatus.js @@ -1 +1,260 @@ -define(["jQuery","globalize","scripts/taskbutton","dom","libraryMenu","layoutManager","loading","listViewStyle","flexStyles","emby-itemscontainer","cardStyle","material-icons","emby-linkbutton"],function($,globalize,taskButton,dom,libraryMenu,layoutManager,loading){"use strict";function getDeviceHtml(device){var padderClass,html="",cssClass="card scalableCard",cardBoxCssClass="cardBox visualCardBox";return cssClass+=" backdropCard backdropCard-scalable",padderClass="cardPadder-backdrop",layoutManager.tv&&(cssClass+=" card-focusscale",cardBoxCssClass+=" cardBox-focustransform"),cardBoxCssClass+=" card-focuscontent",html+='
    ',html+='
    ',html+='
    ',html+='
    ',html+='
    ',html+='
    dvr
    ',html+="
    ",html+="
    ",html+='
    ',html+='',html+='
    '+(device.FriendlyName||getTunerName(device.Type))+"
    ",html+='
    ',html+=device.Url||" ",html+="
    ",html+="
    ",html+="
    ",html+="
    "}function renderDevices(page,devices){var html=devices.map(getDeviceHtml).join("");page.querySelector(".devicesList").innerHTML=html}function deleteDevice(page,id){var message=globalize.translate("MessageConfirmDeleteTunerDevice");require(["confirm"],function(confirm){confirm(message,globalize.translate("HeaderDeleteDevice")).then(function(){loading.show(),ApiClient.ajax({type:"DELETE",url:ApiClient.getUrl("LiveTv/TunerHosts",{Id:id})}).then(function(){reload(page)})})})}function reload(page){loading.show(),ApiClient.getNamedConfiguration("livetv").then(function(config){renderDevices(page,config.TunerHosts),renderProviders(page,config.ListingProviders)}),loading.hide()}function submitAddDeviceForm(page){page.querySelector(".dlgAddDevice").close(),loading.show(),ApiClient.ajax({type:"POST",url:ApiClient.getUrl("LiveTv/TunerHosts"),data:JSON.stringify({Type:$("#selectTunerDeviceType",page).val(),Url:$("#txtDevicePath",page).val()}),contentType:"application/json"}).then(function(){reload(page)},function(){Dashboard.alert({message:globalize.translate("ErrorAddingTunerDevice")})})}function renderProviders(page,providers){var html="";if(providers.length){html+='
    ';for(var i=0,length=providers.length;i',html+='dvr',html+='",html+='',html+="
    "}html+="
    "}var elem=$(".providerList",page).html(html);$(".btnOptions",elem).on("click",function(){var id=this.getAttribute("data-id");showProviderOptions(page,id,this)})}function showProviderOptions(page,providerId,button){var items=[];items.push({name:globalize.translate("ButtonDelete"),id:"delete"}),items.push({name:globalize.translate("MapChannels"),id:"map"}),require(["actionsheet"],function(actionsheet){actionsheet.show({items:items,positionTo:button}).then(function(id){switch(id){case"delete":deleteProvider(page,providerId);break;case"map":mapChannels(page,providerId)}})})}function mapChannels(page,providerId){require(["components/channelmapper/channelmapper"],function(channelmapper){new channelmapper({serverId:ApiClient.serverInfo().Id,providerId:providerId}).show()})}function deleteProvider(page,id){var message=globalize.translate("MessageConfirmDeleteGuideProvider");require(["confirm"],function(confirm){confirm(message,globalize.translate("HeaderDeleteProvider")).then(function(){loading.show(),ApiClient.ajax({type:"DELETE",url:ApiClient.getUrl("LiveTv/ListingProviders",{Id:id})}).then(function(){reload(page)},function(){reload(page)})})})}function getTunerName(providerId){switch(providerId=providerId.toLowerCase()){case"m3u":return"M3U";case"hdhomerun":return"HDHomerun";case"hauppauge":return"Hauppauge";case"satip":return"DVB";default:return"Unknown"}}function getProviderName(providerId){switch(providerId=providerId.toLowerCase()){case"schedulesdirect":return"Schedules Direct";case"xmltv":return"Xml TV";case"emby":return"Emby Guide";default:return"Unknown"}}function getProviderConfigurationUrl(providerId){switch(providerId=providerId.toLowerCase()){case"xmltv":return"livetvguideprovider.html?type=xmltv";case"schedulesdirect":return"livetvguideprovider.html?type=schedulesdirect";case"emby":return"livetvguideprovider.html?type=emby"}}function addProvider(button){var menuItems=[];menuItems.push({name:"Schedules Direct",id:"SchedulesDirect"}),menuItems.push({name:"Xml TV",id:"xmltv"}),menuItems.push({name:globalize.translate("ButtonOther"),id:"other"}),require(["actionsheet"],function(actionsheet){actionsheet.show({items:menuItems,positionTo:button,callback:function(id){"other"==id?Dashboard.alert({message:globalize.translate("ForAdditionalLiveTvOptions")}):Dashboard.navigate(getProviderConfigurationUrl(id))}})})}function addDevice(button){Dashboard.navigate("livetvtuner.html")}function getTabs(){return[{href:"livetvstatus.html",name:globalize.translate("TabDevices")},{href:"appservices.html?context=livetv",name:globalize.translate("TabServices")}]}function showDeviceMenu(button,tunerDeviceId){var items=[];items.push({name:globalize.translate("ButtonDelete"),id:"delete"}),items.push({name:globalize.translate("ButtonEdit"),id:"edit"}),require(["actionsheet"],function(actionsheet){actionsheet.show({items:items,positionTo:button}).then(function(id){switch(id){case"delete":deleteDevice(dom.parentWithClass(button,"page"),tunerDeviceId);break;case"edit":Dashboard.navigate("livetvtuner.html?id="+tunerDeviceId)}})})}function onDevicesListClick(e){var card=dom.parentWithClass(e.target,"card");if(card){var id=card.getAttribute("data-id"),btnCardOptions=dom.parentWithClass(e.target,"btnCardOptions");btnCardOptions?showDeviceMenu(btnCardOptions,id):Dashboard.navigate("livetvtuner.html?id="+id)}}$(document).on("pageinit","#liveTvStatusPage",function(){var page=this;$(".btnAddDevice",page).on("click",function(){addDevice(this)}),$(".formAddDevice",page).on("submit",function(){return submitAddDeviceForm(page),!1}),$(".btnAddProvider",page).on("click",function(){addProvider(this)}),page.querySelector(".devicesList").addEventListener("click",onDevicesListClick)}).on("pageshow","#liveTvStatusPage",function(){libraryMenu.setTabs("livetvadmin",0,getTabs);var page=this;reload(page),taskButton({mode:"on",progressElem:page.querySelector(".refreshGuideProgress"),taskKey:"RefreshGuide",button:page.querySelector(".btnRefresh")})}).on("pagehide","#liveTvStatusPage",function(){var page=this;taskButton({mode:"off",progressElem:page.querySelector(".refreshGuideProgress"),taskKey:"RefreshGuide",button:page.querySelector(".btnRefresh")})})}); \ No newline at end of file +define(["jQuery", "globalize", "scripts/taskbutton", "dom", "libraryMenu", "layoutManager", "loading", "listViewStyle", "flexStyles", "emby-itemscontainer", "cardStyle", "material-icons", "emby-linkbutton"], function($, globalize, taskButton, dom, libraryMenu, layoutManager, loading) { + "use strict"; + + function getDeviceHtml(device) { + var padderClass, html = "", + cssClass = "card scalableCard", + cardBoxCssClass = "cardBox visualCardBox"; + return cssClass += " backdropCard backdropCard-scalable", padderClass = "cardPadder-backdrop", layoutManager.tv && (cssClass += " card-focusscale", cardBoxCssClass += " cardBox-focustransform"), cardBoxCssClass += " card-focuscontent", html += '
    ', html += '
    ', html += '
    ', html += '
    ', html += '
    ', html += '
    dvr
    ', html += "
    ", html += "
    ", html += '
    ', html += '', html += '
    ' + (device.FriendlyName || getTunerName(device.Type)) + "
    ", html += '
    ', html += device.Url || " ", html += "
    ", html += "
    ", html += "
    ", html += "
    " + } + + function renderDevices(page, devices) { + var html = devices.map(getDeviceHtml).join(""); + page.querySelector(".devicesList").innerHTML = html + } + + function deleteDevice(page, id) { + var message = globalize.translate("MessageConfirmDeleteTunerDevice"); + require(["confirm"], function(confirm) { + confirm(message, globalize.translate("HeaderDeleteDevice")).then(function() { + loading.show(), ApiClient.ajax({ + type: "DELETE", + url: ApiClient.getUrl("LiveTv/TunerHosts", { + Id: id + }) + }).then(function() { + reload(page) + }) + }) + }) + } + + function reload(page) { + loading.show(), ApiClient.getNamedConfiguration("livetv").then(function(config) { + renderDevices(page, config.TunerHosts), renderProviders(page, config.ListingProviders) + }), loading.hide() + } + + function submitAddDeviceForm(page) { + page.querySelector(".dlgAddDevice").close(), loading.show(), ApiClient.ajax({ + type: "POST", + url: ApiClient.getUrl("LiveTv/TunerHosts"), + data: JSON.stringify({ + Type: $("#selectTunerDeviceType", page).val(), + Url: $("#txtDevicePath", page).val() + }), + contentType: "application/json" + }).then(function() { + reload(page) + }, function() { + Dashboard.alert({ + message: globalize.translate("ErrorAddingTunerDevice") + }) + }) + } + + function renderProviders(page, providers) { + var html = ""; + if (providers.length) { + html += '
    '; + for (var i = 0, length = providers.length; i < length; i++) { + var provider = providers[i]; + html += '" + } + html += "
    " + } + var elem = $(".providerList", page).html(html); + $(".btnOptions", elem).on("click", function() { + var id = this.getAttribute("data-id"); + showProviderOptions(page, id, this) + }) + } + + function showProviderOptions(page, providerId, button) { + var items = []; + items.push({ + name: globalize.translate("ButtonDelete"), + id: "delete" + }), items.push({ + name: globalize.translate("MapChannels"), + id: "map" + }), require(["actionsheet"], function(actionsheet) { + actionsheet.show({ + items: items, + positionTo: button + }).then(function(id) { + switch (id) { + case "delete": + deleteProvider(page, providerId); + break; + case "map": + mapChannels(page, providerId) + } + }) + }) + } + + function mapChannels(page, providerId) { + require(["components/channelmapper/channelmapper"], function(channelmapper) { + new channelmapper({ + serverId: ApiClient.serverInfo().Id, + providerId: providerId + }).show() + }) + } + + function deleteProvider(page, id) { + var message = globalize.translate("MessageConfirmDeleteGuideProvider"); + require(["confirm"], function(confirm) { + confirm(message, globalize.translate("HeaderDeleteProvider")).then(function() { + loading.show(), ApiClient.ajax({ + type: "DELETE", + url: ApiClient.getUrl("LiveTv/ListingProviders", { + Id: id + }) + }).then(function() { + reload(page) + }, function() { + reload(page) + }) + }) + }) + } + + function getTunerName(providerId) { + switch (providerId = providerId.toLowerCase()) { + case "m3u": + return "M3U"; + case "hdhomerun": + return "HDHomerun"; + case "hauppauge": + return "Hauppauge"; + case "satip": + return "DVB"; + default: + return "Unknown" + } + } + + function getProviderName(providerId) { + switch (providerId = providerId.toLowerCase()) { + case "schedulesdirect": + return "Schedules Direct"; + case "xmltv": + return "Xml TV"; + case "emby": + return "Emby Guide"; + default: + return "Unknown" + } + } + + function getProviderConfigurationUrl(providerId) { + switch (providerId = providerId.toLowerCase()) { + case "xmltv": + return "livetvguideprovider.html?type=xmltv"; + case "schedulesdirect": + return "livetvguideprovider.html?type=schedulesdirect"; + case "emby": + return "livetvguideprovider.html?type=emby" + } + } + + function addProvider(button) { + var menuItems = []; + menuItems.push({ + name: "Schedules Direct", + id: "SchedulesDirect" + }), menuItems.push({ + name: "Xml TV", + id: "xmltv" + }), menuItems.push({ + name: globalize.translate("ButtonOther"), + id: "other" + }), require(["actionsheet"], function(actionsheet) { + actionsheet.show({ + items: menuItems, + positionTo: button, + callback: function(id) { + "other" == id ? Dashboard.alert({ + message: globalize.translate("ForAdditionalLiveTvOptions") + }) : Dashboard.navigate(getProviderConfigurationUrl(id)) + } + }) + }) + } + + function addDevice(button) { + Dashboard.navigate("livetvtuner.html") + } + + function getTabs() { + return [{ + href: "livetvstatus.html", + name: globalize.translate("TabDevices") + }, { + href: "appservices.html?context=livetv", + name: globalize.translate("TabServices") + }] + } + + function showDeviceMenu(button, tunerDeviceId) { + var items = []; + items.push({ + name: globalize.translate("ButtonDelete"), + id: "delete" + }), items.push({ + name: globalize.translate("ButtonEdit"), + id: "edit" + }), require(["actionsheet"], function(actionsheet) { + actionsheet.show({ + items: items, + positionTo: button + }).then(function(id) { + switch (id) { + case "delete": + deleteDevice(dom.parentWithClass(button, "page"), tunerDeviceId); + break; + case "edit": + Dashboard.navigate("livetvtuner.html?id=" + tunerDeviceId) + } + }) + }) + } + + function onDevicesListClick(e) { + var card = dom.parentWithClass(e.target, "card"); + if (card) { + var id = card.getAttribute("data-id"), + btnCardOptions = dom.parentWithClass(e.target, "btnCardOptions"); + btnCardOptions ? showDeviceMenu(btnCardOptions, id) : Dashboard.navigate("livetvtuner.html?id=" + id) + } + } + $(document).on("pageinit", "#liveTvStatusPage", function() { + var page = this; + $(".btnAddDevice", page).on("click", function() { + addDevice(this) + }), $(".formAddDevice", page).on("submit", function() { + return submitAddDeviceForm(page), !1 + }), $(".btnAddProvider", page).on("click", function() { + addProvider(this) + }), page.querySelector(".devicesList").addEventListener("click", onDevicesListClick) + }).on("pageshow", "#liveTvStatusPage", function() { + libraryMenu.setTabs("livetvadmin", 0, getTabs); + var page = this; + reload(page), taskButton({ + mode: "on", + progressElem: page.querySelector(".refreshGuideProgress"), + taskKey: "RefreshGuide", + button: page.querySelector(".btnRefresh") + }) + }).on("pagehide", "#liveTvStatusPage", function() { + var page = this; + taskButton({ + mode: "off", + progressElem: page.querySelector(".refreshGuideProgress"), + taskKey: "RefreshGuide", + button: page.querySelector(".btnRefresh") + }) + }) +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/livetvsuggested.js b/dashboard-ui/scripts/livetvsuggested.js index ed6cb8519e..4377195338 100644 --- a/dashboard-ui/scripts/livetvsuggested.js +++ b/dashboard-ui/scripts/livetvsuggested.js @@ -1 +1,273 @@ -define(["layoutManager","userSettings","inputManager","loading","registrationServices","globalize","libraryBrowser","mainTabsManager","cardBuilder","apphost","imageLoader","scrollStyles","emby-itemscontainer","emby-tabs","emby-button"],function(layoutManager,userSettings,inputManager,loading,registrationServices,globalize,libraryBrowser,mainTabsManager,cardBuilder,appHost,imageLoader){"use strict";function enableScrollX(){return!layoutManager.desktop}function getBackdropShape(){return enableScrollX()?"overflowBackdrop":"backdrop"}function getPortraitShape(){return enableScrollX()?"overflowPortrait":"portrait"}function getLimit(){return enableScrollX()?12:9}function loadRecommendedPrograms(page){loading.show();var limit=getLimit();enableScrollX()&&(limit*=2),ApiClient.getLiveTvRecommendedPrograms({userId:Dashboard.getCurrentUserId(),IsAiring:!0,limit:limit,ImageTypeLimit:1,EnableImageTypes:"Primary,Thumb,Backdrop",EnableTotalRecordCount:!1,Fields:"ChannelInfo,PrimaryImageAspectRatio"}).then(function(result){renderItems(page,result.Items,"activeProgramItems","play",{showAirDateTime:!1,showAirEndTime:!0}),loading.hide()})}function reload(page,enableFullRender){enableFullRender&&(loadRecommendedPrograms(page),ApiClient.getLiveTvPrograms({userId:Dashboard.getCurrentUserId(),HasAired:!1,limit:getLimit(),IsMovie:!1,IsSports:!1,IsKids:!1,IsNews:!1,IsSeries:!0,EnableTotalRecordCount:!1,Fields:"ChannelInfo,PrimaryImageAspectRatio",EnableImageTypes:"Primary,Thumb"}).then(function(result){renderItems(page,result.Items,"upcomingEpisodeItems")}),ApiClient.getLiveTvPrograms({userId:Dashboard.getCurrentUserId(),HasAired:!1,limit:getLimit(),IsMovie:!0,EnableTotalRecordCount:!1,Fields:"ChannelInfo",EnableImageTypes:"Primary,Thumb"}).then(function(result){renderItems(page,result.Items,"upcomingTvMovieItems",null,{shape:getPortraitShape(),preferThumb:null,showParentTitle:!1})}),ApiClient.getLiveTvPrograms({userId:Dashboard.getCurrentUserId(),HasAired:!1,limit:getLimit(),IsSports:!0,EnableTotalRecordCount:!1,Fields:"ChannelInfo,PrimaryImageAspectRatio",EnableImageTypes:"Primary,Thumb"}).then(function(result){renderItems(page,result.Items,"upcomingSportsItems")}),ApiClient.getLiveTvPrograms({userId:Dashboard.getCurrentUserId(),HasAired:!1,limit:getLimit(),IsKids:!0,EnableTotalRecordCount:!1,Fields:"ChannelInfo,PrimaryImageAspectRatio",EnableImageTypes:"Primary,Thumb"}).then(function(result){renderItems(page,result.Items,"upcomingKidsItems")}),ApiClient.getLiveTvPrograms({userId:Dashboard.getCurrentUserId(),HasAired:!1,limit:getLimit(),IsNews:!0,EnableTotalRecordCount:!1,Fields:"ChannelInfo,PrimaryImageAspectRatio",EnableImageTypes:"Primary,Thumb"}).then(function(result){renderItems(page,result.Items,"upcomingNewsItems",null,{showParentTitleOrTitle:!0,showTitle:!1,showParentTitle:!1})}))}function renderItems(page,items,sectionClass,overlayButton,cardOptions){var html=cardBuilder.getCardsHtml(Object.assign({items:items,preferThumb:"auto",inheritThumb:!1,shape:enableScrollX()?"autooverflow":"auto",defaultShape:getBackdropShape(),showParentTitle:!0,showTitle:!0,centerText:!0,coverImage:!0,overlayText:!1,lazy:!0,overlayPlayButton:"play"===overlayButton,overlayMoreButton:"more"===overlayButton,overlayInfoButton:"info"===overlayButton,allowBottomPadding:!enableScrollX(),showAirTime:!0,showAirDateTime:!0},cardOptions||{})),elem=page.querySelector("."+sectionClass);elem.innerHTML=html,imageLoader.lazyChildren(elem)}function getTabs(){return[{name:globalize.translate("Programs")},{name:globalize.translate("TabGuide")},{name:globalize.translate("TabChannels")},{name:globalize.translate("TabRecordings")},{name:globalize.translate("HeaderSchedule")},{name:globalize.translate("TabSeries")},{name:globalize.translate("ButtonSearch"),cssClass:"searchTabButton"}]}function validateUnlock(view,showDialog){registrationServices.validateFeature("livetv",{showDialog:showDialog,viewOnly:!0}).then(function(){view.querySelector(".liveTvContainer").classList.remove("hide"),view.querySelector(".unlockContainer").classList.add("hide")},function(){view.querySelector(".liveTvContainer").classList.add("hide"),view.querySelector(".unlockContainer").classList.remove("hide")})}function setScrollClasses(elem,scrollX){scrollX?(elem.classList.add("hiddenScrollX"),layoutManager.tv&&elem.classList.add("smoothScrollX"),elem.classList.add("scrollX"),elem.classList.remove("vertical-wrap")):(elem.classList.remove("hiddenScrollX"),elem.classList.remove("smoothScrollX"),elem.classList.remove("scrollX"),elem.classList.add("vertical-wrap"))}function getDefaultTabIndex(folderId){switch(userSettings.get("landing-"+folderId)){case"guide":return 1;default:return 0}}return function(view,params){function enableFullRender(){return(new Date).getTime()-lastFullRender>3e5}function onBeforeTabChange(e){preLoadTab(view,parseInt(e.detail.selectedTabIndex))}function onTabChange(e){var previousTabController=tabControllers[parseInt(e.detail.previousIndex)];previousTabController&&previousTabController.onHide&&previousTabController.onHide(),loadTab(view,parseInt(e.detail.selectedTabIndex))}function getTabContainers(){return view.querySelectorAll(".pageTabContent")}function initTabs(){mainTabsManager.setTabs(view,currentTabIndex,getTabs,getTabContainers,onBeforeTabChange,onTabChange)}function getTabController(page,index,callback){var depends=[];switch(index){case 0:break;case 1:depends.push("scripts/livetvguide");break;case 2:depends.push("scripts/livetvchannels");break;case 3:depends.push("scripts/livetvrecordings");break;case 4:depends.push("scripts/livetvschedule");break;case 5:depends.push("scripts/livetvseriestimers");break;case 6:depends.push("scripts/searchtab")}require(depends,function(controllerFactory){var tabContent;0==index&&(tabContent=view.querySelector(".pageTabContent[data-index='"+index+"']"),self.tabContent=tabContent);var controller=tabControllers[index];controller||(tabContent=view.querySelector(".pageTabContent[data-index='"+index+"']"),controller=0===index?self:6===index?new controllerFactory(view,tabContent,{collectionType:"livetv"}):new controllerFactory(view,params,tabContent),tabControllers[index]=controller,controller.initTab&&controller.initTab()),callback(controller)})}function preLoadTab(page,index){getTabController(page,index,function(controller){-1==renderedTabs.indexOf(index)&&controller.preRender&&controller.preRender()})}function loadTab(page,index){currentTabIndex=index,getTabController(page,index,function(controller){initialTabIndex=null,1===index?document.body.classList.add("autoScrollY"):document.body.classList.remove("autoScrollY"),-1==renderedTabs.indexOf(index)?(1===index&&renderedTabs.push(index),controller.renderTab()):controller.onShow&&controller.onShow(),currentTabController=controller})}function onInputCommand(e){switch(e.detail.command){case"search":e.preventDefault(),Dashboard.navigate("search.html?collectionType=livetv")}}var isViewRestored,self=this,currentTabIndex=parseInt(params.tab||getDefaultTabIndex("livetv")),initialTabIndex=currentTabIndex,lastFullRender=0;[].forEach.call(view.querySelectorAll(".sectionTitleTextButton-programs"),function(link){var href=link.href;href&&(link.href=href+"&serverId="+ApiClient.serverId())}),view.querySelector(".unlockText").innerHTML=globalize.translate("sharedcomponents#LiveTvRequiresUnlock"),validateUnlock(view,!1),self.initTab=function(){for(var tabContent=view.querySelector(".pageTabContent[data-index='0']"),containers=tabContent.querySelectorAll(".itemsContainer"),i=0,length=containers.length;i 3e5 + } + + function onBeforeTabChange(e) { + preLoadTab(view, parseInt(e.detail.selectedTabIndex)) + } + + function onTabChange(e) { + var previousTabController = tabControllers[parseInt(e.detail.previousIndex)]; + previousTabController && previousTabController.onHide && previousTabController.onHide(), loadTab(view, parseInt(e.detail.selectedTabIndex)) + } + + function getTabContainers() { + return view.querySelectorAll(".pageTabContent") + } + + function initTabs() { + mainTabsManager.setTabs(view, currentTabIndex, getTabs, getTabContainers, onBeforeTabChange, onTabChange) + } + + function getTabController(page, index, callback) { + var depends = []; + switch (index) { + case 0: + break; + case 1: + depends.push("scripts/livetvguide"); + break; + case 2: + depends.push("scripts/livetvchannels"); + break; + case 3: + depends.push("scripts/livetvrecordings"); + break; + case 4: + depends.push("scripts/livetvschedule"); + break; + case 5: + depends.push("scripts/livetvseriestimers"); + break; + case 6: + depends.push("scripts/searchtab") + } + require(depends, function(controllerFactory) { + var tabContent; + 0 == index && (tabContent = view.querySelector(".pageTabContent[data-index='" + index + "']"), self.tabContent = tabContent); + var controller = tabControllers[index]; + controller || (tabContent = view.querySelector(".pageTabContent[data-index='" + index + "']"), controller = 0 === index ? self : 6 === index ? new controllerFactory(view, tabContent, { + collectionType: "livetv" + }) : new controllerFactory(view, params, tabContent), tabControllers[index] = controller, controller.initTab && controller.initTab()), callback(controller) + }) + } + + function preLoadTab(page, index) { + getTabController(page, index, function(controller) { + -1 == renderedTabs.indexOf(index) && controller.preRender && controller.preRender() + }) + } + + function loadTab(page, index) { + currentTabIndex = index, getTabController(page, index, function(controller) { + initialTabIndex = null, 1 === index ? document.body.classList.add("autoScrollY") : document.body.classList.remove("autoScrollY"), -1 == renderedTabs.indexOf(index) ? (1 === index && renderedTabs.push(index), controller.renderTab()) : controller.onShow && controller.onShow(), currentTabController = controller + }) + } + + function onInputCommand(e) { + switch (e.detail.command) { + case "search": + e.preventDefault(), Dashboard.navigate("search.html?collectionType=livetv") + } + } + var isViewRestored, self = this, + currentTabIndex = parseInt(params.tab || getDefaultTabIndex("livetv")), + initialTabIndex = currentTabIndex, + lastFullRender = 0; + [].forEach.call(view.querySelectorAll(".sectionTitleTextButton-programs"), function(link) { + var href = link.href; + href && (link.href = href + "&serverId=" + ApiClient.serverId()) + }), view.querySelector(".unlockText").innerHTML = globalize.translate("sharedcomponents#LiveTvRequiresUnlock"), validateUnlock(view, !1), self.initTab = function() { + for (var tabContent = view.querySelector(".pageTabContent[data-index='0']"), containers = tabContent.querySelectorAll(".itemsContainer"), i = 0, length = containers.length; i < length; i++) setScrollClasses(containers[i], enableScrollX()) + }, self.renderTab = function() { + var tabContent = view.querySelector(".pageTabContent[data-index='0']"); + enableFullRender() ? (reload(tabContent, !0), lastFullRender = (new Date).getTime()) : reload(tabContent) + }; + var currentTabController, tabControllers = [], + renderedTabs = []; + view.querySelector(".btnUnlock").addEventListener("click", function() { + validateUnlock(view, !0) + }), view.addEventListener("viewbeforeshow", function(e) { + isViewRestored = e.detail.isRestored, initTabs() + }), view.addEventListener("viewshow", function(e) { + isViewRestored = e.detail.isRestored, isViewRestored || mainTabsManager.selectedTabIndex(initialTabIndex), inputManager.on(window, onInputCommand) + }), view.addEventListener("viewbeforehide", function(e) { + currentTabController && currentTabController.onHide && currentTabController.onHide(), document.body.classList.remove("autoScrollY"), inputManager.off(window, onInputCommand) + }), view.addEventListener("viewdestroy", function(e) { + tabControllers.forEach(function(t) { + t.destroy && t.destroy() + }) + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/loginpage.js b/dashboard-ui/scripts/loginpage.js index 8afdbee359..f9baf346b6 100644 --- a/dashboard-ui/scripts/loginpage.js +++ b/dashboard-ui/scripts/loginpage.js @@ -1 +1,97 @@ -define(["appSettings","dom","connectionManager","loading","cardStyle","emby-checkbox"],function(appSettings,dom,connectionManager,loading){"use strict";function authenticateUserByName(page,apiClient,username,password){loading.show(),apiClient.authenticateUserByName(username,password).then(function(result){var newUrl,user=result.User,serverId=getParameterByName("serverid");newUrl=user.Policy.IsAdministrator&&!serverId?"dashboard.html":"home.html",loading.hide(),Dashboard.onServerChanged(user.Id,result.AccessToken,apiClient),Dashboard.navigate(newUrl)},function(response){page.querySelector("#txtManualName").value="",page.querySelector("#txtManualPassword").value="",loading.hide(),401==response.status?require(["toast"],function(toast){toast(Globalize.translate("MessageInvalidUser"))}):showServerConnectionFailure()})}function showServerConnectionFailure(){Dashboard.alert({message:Globalize.translate("MessageUnableToConnectToServer"),title:Globalize.translate("HeaderConnectionFailure")})}function showManualForm(context,showCancel,focusPassword){context.querySelector(".chkRememberLogin").checked=appSettings.enableAutoLogin(),context.querySelector(".manualLoginForm").classList.remove("hide"),context.querySelector(".visualLoginForm").classList.add("hide"),focusPassword?context.querySelector("#txtManualPassword").focus():context.querySelector("#txtManualName").focus(),showCancel?context.querySelector(".btnCancel").classList.remove("hide"):context.querySelector(".btnCancel").classList.add("hide")}function getRandomMetroColor(){var index=Math.floor(Math.random()*(metroColors.length-1));return metroColors[index]}function getMetroColor(str){if(str){for(var character=String(str.substr(0,1).charCodeAt()),sum=0,i=0;i
    ',html+='
    ',html+='
    ',html+='
    ';var imgUrl;if(user.PrimaryImageTag)imgUrl=apiClient.getUserImageUrl(user.Id,{width:300,tag:user.PrimaryImageTag,type:"Primary"}),html+='
    ";else{var background=getMetroColor(user.Id);imgUrl="css/images/logindefault.png",html+='
    '}html+="
    ",html+="
    ",html+='
    ',html+='
    '+user.Name+"
    ",html+="
    ",html+="
    ",html+=""}context.querySelector("#divUsers").innerHTML=html}var metroColors=["#6FBD45","#4BB3DD","#4164A5","#E12026","#800080","#E1B222","#008040","#0094FF","#FF00C7","#FF870F","#7F0037"];return function(view,params){function getApiClient(){var serverId=params.serverid;return serverId?connectionManager.getOrCreateApiClient(serverId):ApiClient}function showVisualForm(){view.querySelector(".visualLoginForm").classList.remove("hide"),view.querySelector(".manualLoginForm").classList.add("hide")}view.querySelector("#divUsers").addEventListener("click",function(e){var card=dom.parentWithClass(e.target,"card"),cardContent=card?card.querySelector(".cardContent"):null;if(cardContent){var context=view,id=cardContent.getAttribute("data-userid"),name=cardContent.getAttribute("data-username"),haspw=cardContent.getAttribute("data-haspw");"manual"==id?(context.querySelector("#txtManualName").value="",showManualForm(context,!0)):"false"==haspw?authenticateUserByName(context,getApiClient(),name,""):(context.querySelector("#txtManualName").value=name,context.querySelector("#txtManualPassword").value="",showManualForm(context,!0,!0))}}),view.querySelector(".manualLoginForm").addEventListener("submit",function(e){appSettings.enableAutoLogin(view.querySelector(".chkRememberLogin").checked);var apiClient=getApiClient();return authenticateUserByName(view,apiClient,view.querySelector("#txtManualName").value,view.querySelector("#txtManualPassword").value),e.preventDefault(),!1}),view.querySelector(".btnForgotPassword").addEventListener("click",function(){Dashboard.navigate("forgotpassword.html")}),view.querySelector(".btnCancel").addEventListener("click",showVisualForm),view.querySelector(".btnManual").addEventListener("click",function(){view.querySelector("#txtManualName").value="",showManualForm(view,!0)}),view.addEventListener("viewshow",function(e){loading.show();var apiClient=getApiClient();apiClient.getPublicUsers().then(function(users){users.length?users.length&&users[0].EnableAutoLogin?authenticateUserByName(view,apiClient,users[0].Name,""):(showVisualForm(),loadUserList(view,apiClient,users)):(view.querySelector("#txtManualName").value="",showManualForm(view,!1,!1)),loading.hide()}),apiClient.getJSON(apiClient.getUrl("Branding/Configuration")).then(function(options){view.querySelector(".disclaimer").textContent=options.LoginDisclaimer||""}),Dashboard.isConnectMode()?view.querySelector(".connectButtons").classList.remove("hide"):view.querySelector(".connectButtons").classList.add("hide")})}}); \ No newline at end of file +define(["appSettings", "dom", "connectionManager", "loading", "cardStyle", "emby-checkbox"], function(appSettings, dom, connectionManager, loading) { + "use strict"; + + function authenticateUserByName(page, apiClient, username, password) { + loading.show(), apiClient.authenticateUserByName(username, password).then(function(result) { + var newUrl, user = result.User, + serverId = getParameterByName("serverid"); + newUrl = user.Policy.IsAdministrator && !serverId ? "dashboard.html" : "home.html", loading.hide(), Dashboard.onServerChanged(user.Id, result.AccessToken, apiClient), Dashboard.navigate(newUrl) + }, function(response) { + page.querySelector("#txtManualName").value = "", page.querySelector("#txtManualPassword").value = "", loading.hide(), 401 == response.status ? require(["toast"], function(toast) { + toast(Globalize.translate("MessageInvalidUser")) + }) : showServerConnectionFailure() + }) + } + + function showServerConnectionFailure() { + Dashboard.alert({ + message: Globalize.translate("MessageUnableToConnectToServer"), + title: Globalize.translate("HeaderConnectionFailure") + }) + } + + function showManualForm(context, showCancel, focusPassword) { + context.querySelector(".chkRememberLogin").checked = appSettings.enableAutoLogin(), context.querySelector(".manualLoginForm").classList.remove("hide"), context.querySelector(".visualLoginForm").classList.add("hide"), focusPassword ? context.querySelector("#txtManualPassword").focus() : context.querySelector("#txtManualName").focus(), showCancel ? context.querySelector(".btnCancel").classList.remove("hide") : context.querySelector(".btnCancel").classList.add("hide") + } + + function getRandomMetroColor() { + var index = Math.floor(Math.random() * (metroColors.length - 1)); + return metroColors[index] + } + + function getMetroColor(str) { + if (str) { + for (var character = String(str.substr(0, 1).charCodeAt()), sum = 0, i = 0; i < character.length; i++) sum += parseInt(character.charAt(i)); + var index = String(sum).substr(-1); + return metroColors[index] + } + return getRandomMetroColor() + } + + function loadUserList(context, apiClient, users) { + for (var html = "", i = 0, length = users.length; i < length; i++) { + var user = users[i]; + html += '" + } + context.querySelector("#divUsers").innerHTML = html + } + var metroColors = ["#6FBD45", "#4BB3DD", "#4164A5", "#E12026", "#800080", "#E1B222", "#008040", "#0094FF", "#FF00C7", "#FF870F", "#7F0037"]; + return function(view, params) { + function getApiClient() { + var serverId = params.serverid; + return serverId ? connectionManager.getOrCreateApiClient(serverId) : ApiClient + } + + function showVisualForm() { + view.querySelector(".visualLoginForm").classList.remove("hide"), view.querySelector(".manualLoginForm").classList.add("hide") + } + view.querySelector("#divUsers").addEventListener("click", function(e) { + var card = dom.parentWithClass(e.target, "card"), + cardContent = card ? card.querySelector(".cardContent") : null; + if (cardContent) { + var context = view, + id = cardContent.getAttribute("data-userid"), + name = cardContent.getAttribute("data-username"), + haspw = cardContent.getAttribute("data-haspw"); + "manual" == id ? (context.querySelector("#txtManualName").value = "", showManualForm(context, !0)) : "false" == haspw ? authenticateUserByName(context, getApiClient(), name, "") : (context.querySelector("#txtManualName").value = name, context.querySelector("#txtManualPassword").value = "", showManualForm(context, !0, !0)) + } + }), view.querySelector(".manualLoginForm").addEventListener("submit", function(e) { + appSettings.enableAutoLogin(view.querySelector(".chkRememberLogin").checked); + var apiClient = getApiClient(); + return authenticateUserByName(view, apiClient, view.querySelector("#txtManualName").value, view.querySelector("#txtManualPassword").value), e.preventDefault(), !1 + }), view.querySelector(".btnForgotPassword").addEventListener("click", function() { + Dashboard.navigate("forgotpassword.html") + }), view.querySelector(".btnCancel").addEventListener("click", showVisualForm), view.querySelector(".btnManual").addEventListener("click", function() { + view.querySelector("#txtManualName").value = "", showManualForm(view, !0) + }), view.addEventListener("viewshow", function(e) { + loading.show(); + var apiClient = getApiClient(); + apiClient.getPublicUsers().then(function(users) { + users.length ? users.length && users[0].EnableAutoLogin ? authenticateUserByName(view, apiClient, users[0].Name, "") : (showVisualForm(), loadUserList(view, apiClient, users)) : (view.querySelector("#txtManualName").value = "", showManualForm(view, !1, !1)), loading.hide() + }), apiClient.getJSON(apiClient.getUrl("Branding/Configuration")).then(function(options) { + view.querySelector(".disclaimer").textContent = options.LoginDisclaimer || "" + }), Dashboard.isConnectMode() ? view.querySelector(".connectButtons").classList.remove("hide") : view.querySelector(".connectButtons").classList.add("hide") + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/managedownloads.js b/dashboard-ui/scripts/managedownloads.js index 6e791d80b4..1072d56f4d 100644 --- a/dashboard-ui/scripts/managedownloads.js +++ b/dashboard-ui/scripts/managedownloads.js @@ -1 +1,15 @@ -define(["syncJobList"],function(syncJobList){"use strict";return function(view,params){var apiClient=ApiClient,mySyncJobList=new syncJobList({serverId:apiClient.serverId(),userId:null,element:view.querySelector(".syncActivity"),mode:"download"});view.addEventListener("viewdestroy",function(){mySyncJobList&&(mySyncJobList.destroy(),mySyncJobList=null)})}}); \ No newline at end of file +define(["syncJobList"], function(syncJobList) { + "use strict"; + return function(view, params) { + var apiClient = ApiClient, + mySyncJobList = new syncJobList({ + serverId: apiClient.serverId(), + userId: null, + element: view.querySelector(".syncActivity"), + mode: "download" + }); + view.addEventListener("viewdestroy", function() { + mySyncJobList && (mySyncJobList.destroy(), mySyncJobList = null) + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/medialibrarypage.js b/dashboard-ui/scripts/medialibrarypage.js index 9803fc47a7..a45a9ae21b 100644 --- a/dashboard-ui/scripts/medialibrarypage.js +++ b/dashboard-ui/scripts/medialibrarypage.js @@ -1 +1,313 @@ -define(["jQuery","apphost","scripts/taskbutton","loading","libraryMenu","globalize","dom","indicators","cardStyle","emby-itemrefreshindicator"],function($,appHost,taskButton,loading,libraryMenu,globalize,dom,indicators){"use strict";function changeCollectionType(page,virtualFolder){require(["alert"],function(alert){alert({title:globalize.translate("HeaderChangeFolderType"),text:globalize.translate("HeaderChangeFolderTypeHelp")})})}function addVirtualFolder(page){require(["medialibrarycreator"],function(medialibrarycreator){(new medialibrarycreator).show({collectionTypeOptions:getCollectionTypeOptions().filter(function(f){return!f.hidden}),refresh:shouldRefreshLibraryAfterChanges(page)}).then(function(hasChanges){hasChanges&&reloadLibrary(page)})})}function editVirtualFolder(page,virtualFolder){require(["medialibraryeditor"],function(medialibraryeditor){(new medialibraryeditor).show({refresh:shouldRefreshLibraryAfterChanges(page),library:virtualFolder}).then(function(hasChanges){hasChanges&&reloadLibrary(page)})})}function deleteVirtualFolder(page,virtualFolder){var msg=globalize.translate("MessageAreYouSureYouWishToRemoveMediaFolder");virtualFolder.Locations.length&&(msg+="

    "+globalize.translate("MessageTheFollowingLocationWillBeRemovedFromLibrary")+"

    ",msg+=virtualFolder.Locations.join("
    ")),require(["confirm"],function(confirm){confirm(msg,globalize.translate("HeaderRemoveMediaFolder")).then(function(){var refreshAfterChange=shouldRefreshLibraryAfterChanges(page);ApiClient.removeVirtualFolder(virtualFolder.Name,refreshAfterChange).then(function(){reloadLibrary(page)})})})}function refreshVirtualFolder(page,virtualFolder){require(["refreshDialog"],function(refreshDialog){new refreshDialog({itemIds:[virtualFolder.ItemId],serverId:ApiClient.serverId(),mode:"scan"}).show()})}function renameVirtualFolder(page,virtualFolder){require(["prompt"],function(prompt){prompt({label:globalize.translate("LabelNewName"),confirmText:globalize.translate("ButtonRename")}).then(function(newName){if(newName&&newName!=virtualFolder.Name){var refreshAfterChange=shouldRefreshLibraryAfterChanges(page);ApiClient.renameVirtualFolder(virtualFolder.Name,newName,refreshAfterChange).then(function(){reloadLibrary(page)})}})})}function showCardMenu(page,elem,virtualFolders){var card=dom.parentWithClass(elem,"card"),index=parseInt(card.getAttribute("data-index")),virtualFolder=virtualFolders[index],menuItems=[];menuItems.push({name:globalize.translate("ButtonChangeContentType"),id:"changetype",ironIcon:"videocam"}),menuItems.push({name:globalize.translate("ButtonEditImages"),id:"editimages",ironIcon:"photo"}),menuItems.push({name:globalize.translate("ManageLibrary"),id:"edit",ironIcon:"folder_open"}),menuItems.push({name:globalize.translate("ButtonRemove"),id:"delete",ironIcon:"remove"}),menuItems.push({name:globalize.translate("ButtonRename"),id:"rename",ironIcon:"mode_edit"}),menuItems.push({name:globalize.translate("ScanLibrary"),id:"refresh",ironIcon:"refresh"}),require(["actionsheet"],function(actionsheet){actionsheet.show({items:menuItems,positionTo:elem,callback:function(resultId){switch(resultId){case"changetype":changeCollectionType(page,virtualFolder);break;case"edit":editVirtualFolder(page,virtualFolder);break;case"editimages":editImages(page,virtualFolder);break;case"rename":renameVirtualFolder(page,virtualFolder);break;case"delete":deleteVirtualFolder(page,virtualFolder);break;case"refresh":refreshVirtualFolder(page,virtualFolder)}}})})}function reloadLibrary(page){loading.show(),ApiClient.getVirtualFolders().then(function(result){reloadVirtualFolders(page,result)})}function shouldRefreshLibraryAfterChanges(page){return"mediaLibraryPage"===page.id}function reloadVirtualFolders(page,virtualFolders){var html="";virtualFolders.push({Name:globalize.translate("ButtonAddMediaLibrary"),icon:"add_circle",Locations:[],showType:!1,showLocations:!1,showMenu:!1,showNameWithIcon:!0});for(var i=0,length=virtualFolders.length;i',"")}function getCollectionTypeOptions(){return[{name:"",value:""},{name:globalize.translate("FolderTypeMovies"),value:"movies",message:getLink("MovieLibraryHelp","https://github.com/MediaBrowser/Wiki/wiki/Movie%20naming")},{name:globalize.translate("FolderTypeMusic"),value:"music"},{name:globalize.translate("FolderTypeTvShows"),value:"tvshows",message:getLink("TvLibraryHelp","https://github.com/MediaBrowser/Wiki/wiki/TV%20naming")},{name:globalize.translate("FolderTypeBooks"),value:"books",message:getLink("BookLibraryHelp","https://github.com/MediaBrowser/Wiki/wiki/Book%20naming")},{name:globalize.translate("FolderTypeGames"),value:"games",message:globalize.translate("MessageGamePluginRequired")},{name:globalize.translate("OptionHomeVideos"),value:"homevideos"},{name:globalize.translate("FolderTypeMusicVideos"),value:"musicvideos"},{name:globalize.translate("FolderTypeUnset"),value:"mixed",message:globalize.translate("MessageUnsetContentHelp")}]}function getIcon(type){switch(type){case"movies":return"local_movies";case"music":return"library_music";case"photos":return"photo";case"livetv":case"tvshows":return"live_tv";case"games":return"folder";case"trailers":return"local_movies";case"homevideos":case"musicvideos":return"video_library";case"books":case"channels":case"playlists":default:return"folder"}}function getVirtualFolderHtml(page,virtualFolder,index){var html="",style="";page.classList.contains("wizardPage")&&(style+="min-width:33.3%;"),html+='
    ',html+='
    ',html+='
    ',html+='
    ',html+='
    ';var imgUrl="";virtualFolder.PrimaryImageItemId&&(imgUrl=ApiClient.getScaledImageUrl(virtualFolder.PrimaryImageItemId,{type:"Primary"}));var hasCardImageContainer;if(imgUrl?(html+='
    ",hasCardImageContainer=!0):virtualFolder.showNameWithIcon||(html+='
    ',html+=''+(virtualFolder.icon||getIcon(virtualFolder.CollectionType))+"",hasCardImageContainer=!0),hasCardImageContainer){html+='
    ';html+='
    ',html+="
    ",html+="
    "}if(!imgUrl&&virtualFolder.showNameWithIcon&&(html+='

    ',html+=''+(virtualFolder.icon||getIcon(virtualFolder.CollectionType))+"",virtualFolder.showNameWithIcon&&(html+='
    ',html+=virtualFolder.Name,html+="
    "),html+="

    "),html+="
    ",html+="
    ",html+='
    ',!1!==virtualFolder.showMenu){html+='
    ',html+='',html+="
    "}html+="
    ",virtualFolder.showNameWithIcon?html+=" ":html+=virtualFolder.Name,html+="
    ";var typeName=getCollectionTypeOptions().filter(function(t){return t.value==virtualFolder.CollectionType})[0];return typeName=typeName?typeName.name:globalize.translate("FolderTypeUnset"),html+="
    ",!1===virtualFolder.showType?html+=" ":html+=typeName,html+="
    ",!1===virtualFolder.showLocations?(html+="
    ",html+=" ",html+="
    "):virtualFolder.Locations.length&&1==virtualFolder.Locations.length?(html+="
    ",html+=virtualFolder.Locations[0],html+="
    "):(html+="
    ",html+=globalize.translate("NumLocationsValue",virtualFolder.Locations.length),html+="
    "),html+="
    ",html+="
    ",html+="
    "}function getTabs(){return[{href:"library.html",name:globalize.translate("HeaderLibraries")},{href:"librarydisplay.html",name:globalize.translate("TabDisplay")},{href:"metadataimages.html",name:globalize.translate("TabMetadata")},{href:"metadatanfo.html",name:globalize.translate("TabNfoSettings")},{href:"librarysettings.html",name:globalize.translate("TabAdvanced")}]}window.WizardLibraryPage={next:function(){Dashboard.navigate("wizardsettings.html")}},pageClassOn("pageshow","mediaLibraryPage",function(){reloadLibrary(this)}),pageIdOn("pageshow","mediaLibraryPage",function(){libraryMenu.setTabs("librarysetup",0,getTabs);var page=this;taskButton({mode:"on",progressElem:page.querySelector(".refreshProgress"),taskKey:"RefreshLibrary",button:page.querySelector(".btnRefresh")})}),pageIdOn("pagebeforehide","mediaLibraryPage",function(){var page=this;taskButton({mode:"off",progressElem:page.querySelector(".refreshProgress"),taskKey:"RefreshLibrary",button:page.querySelector(".btnRefresh")})})}); \ No newline at end of file +define(["jQuery", "apphost", "scripts/taskbutton", "loading", "libraryMenu", "globalize", "dom", "indicators", "cardStyle", "emby-itemrefreshindicator"], function($, appHost, taskButton, loading, libraryMenu, globalize, dom, indicators) { + "use strict"; + + function changeCollectionType(page, virtualFolder) { + require(["alert"], function(alert) { + alert({ + title: globalize.translate("HeaderChangeFolderType"), + text: globalize.translate("HeaderChangeFolderTypeHelp") + }) + }) + } + + function addVirtualFolder(page) { + require(["medialibrarycreator"], function(medialibrarycreator) { + (new medialibrarycreator).show({ + collectionTypeOptions: getCollectionTypeOptions().filter(function(f) { + return !f.hidden + }), + refresh: shouldRefreshLibraryAfterChanges(page) + }).then(function(hasChanges) { + hasChanges && reloadLibrary(page) + }) + }) + } + + function editVirtualFolder(page, virtualFolder) { + require(["medialibraryeditor"], function(medialibraryeditor) { + (new medialibraryeditor).show({ + refresh: shouldRefreshLibraryAfterChanges(page), + library: virtualFolder + }).then(function(hasChanges) { + hasChanges && reloadLibrary(page) + }) + }) + } + + function deleteVirtualFolder(page, virtualFolder) { + var msg = globalize.translate("MessageAreYouSureYouWishToRemoveMediaFolder"); + virtualFolder.Locations.length && (msg += "

    " + globalize.translate("MessageTheFollowingLocationWillBeRemovedFromLibrary") + "

    ", msg += virtualFolder.Locations.join("
    ")), require(["confirm"], function(confirm) { + confirm(msg, globalize.translate("HeaderRemoveMediaFolder")).then(function() { + var refreshAfterChange = shouldRefreshLibraryAfterChanges(page); + ApiClient.removeVirtualFolder(virtualFolder.Name, refreshAfterChange).then(function() { + reloadLibrary(page) + }) + }) + }) + } + + function refreshVirtualFolder(page, virtualFolder) { + require(["refreshDialog"], function(refreshDialog) { + new refreshDialog({ + itemIds: [virtualFolder.ItemId], + serverId: ApiClient.serverId(), + mode: "scan" + }).show() + }) + } + + function renameVirtualFolder(page, virtualFolder) { + require(["prompt"], function(prompt) { + prompt({ + label: globalize.translate("LabelNewName"), + confirmText: globalize.translate("ButtonRename") + }).then(function(newName) { + if (newName && newName != virtualFolder.Name) { + var refreshAfterChange = shouldRefreshLibraryAfterChanges(page); + ApiClient.renameVirtualFolder(virtualFolder.Name, newName, refreshAfterChange).then(function() { + reloadLibrary(page) + }) + } + }) + }) + } + + function showCardMenu(page, elem, virtualFolders) { + var card = dom.parentWithClass(elem, "card"), + index = parseInt(card.getAttribute("data-index")), + virtualFolder = virtualFolders[index], + menuItems = []; + menuItems.push({ + name: globalize.translate("ButtonChangeContentType"), + id: "changetype", + ironIcon: "videocam" + }), menuItems.push({ + name: globalize.translate("ButtonEditImages"), + id: "editimages", + ironIcon: "photo" + }), menuItems.push({ + name: globalize.translate("ManageLibrary"), + id: "edit", + ironIcon: "folder_open" + }), menuItems.push({ + name: globalize.translate("ButtonRemove"), + id: "delete", + ironIcon: "remove" + }), menuItems.push({ + name: globalize.translate("ButtonRename"), + id: "rename", + ironIcon: "mode_edit" + }), menuItems.push({ + name: globalize.translate("ScanLibrary"), + id: "refresh", + ironIcon: "refresh" + }), require(["actionsheet"], function(actionsheet) { + actionsheet.show({ + items: menuItems, + positionTo: elem, + callback: function(resultId) { + switch (resultId) { + case "changetype": + changeCollectionType(page, virtualFolder); + break; + case "edit": + editVirtualFolder(page, virtualFolder); + break; + case "editimages": + editImages(page, virtualFolder); + break; + case "rename": + renameVirtualFolder(page, virtualFolder); + break; + case "delete": + deleteVirtualFolder(page, virtualFolder); + break; + case "refresh": + refreshVirtualFolder(page, virtualFolder) + } + } + }) + }) + } + + function reloadLibrary(page) { + loading.show(), ApiClient.getVirtualFolders().then(function(result) { + reloadVirtualFolders(page, result) + }) + } + + function shouldRefreshLibraryAfterChanges(page) { + return "mediaLibraryPage" === page.id + } + + function reloadVirtualFolders(page, virtualFolders) { + var html = ""; + virtualFolders.push({ + Name: globalize.translate("ButtonAddMediaLibrary"), + icon: "add_circle", + Locations: [], + showType: !1, + showLocations: !1, + showMenu: !1, + showNameWithIcon: !0 + }); + for (var i = 0, length = virtualFolders.length; i < length; i++) { + var virtualFolder = virtualFolders[i]; + html += getVirtualFolderHtml(page, virtualFolder, i) + } + var divVirtualFolders = page.querySelector("#divVirtualFolders"); + divVirtualFolders.innerHTML = html, divVirtualFolders.classList.add("itemsContainer"), divVirtualFolders.classList.add("vertical-wrap"), $(".btnCardMenu", divVirtualFolders).on("click", function() { + showCardMenu(page, this, virtualFolders) + }), divVirtualFolders.querySelector(".addLibrary").addEventListener("click", function() { + addVirtualFolder(page) + }), $(".editLibrary", divVirtualFolders).on("click", function() { + var card = $(this).parents(".card")[0], + index = parseInt(card.getAttribute("data-index")), + virtualFolder = virtualFolders[index]; + virtualFolder.ItemId && editVirtualFolder(page, virtualFolder) + }), loading.hide() + } + + function editImages(page, virtualFolder) { + require(["imageEditor"], function(imageEditor) { + imageEditor.show({ + itemId: virtualFolder.ItemId, + serverId: ApiClient.serverId() + }).then(function() { + reloadLibrary(page) + }) + }) + } + + function getLink(text, url) { + return globalize.translate(text, '', "") + } + + function getCollectionTypeOptions() { + return [{ + name: "", + value: "" + }, { + name: globalize.translate("FolderTypeMovies"), + value: "movies", + message: getLink("MovieLibraryHelp", "https://github.com/MediaBrowser/Wiki/wiki/Movie%20naming") + }, { + name: globalize.translate("FolderTypeMusic"), + value: "music" + }, { + name: globalize.translate("FolderTypeTvShows"), + value: "tvshows", + message: getLink("TvLibraryHelp", "https://github.com/MediaBrowser/Wiki/wiki/TV%20naming") + }, { + name: globalize.translate("FolderTypeBooks"), + value: "books", + message: getLink("BookLibraryHelp", "https://github.com/MediaBrowser/Wiki/wiki/Book%20naming") + }, { + name: globalize.translate("FolderTypeGames"), + value: "games", + message: globalize.translate("MessageGamePluginRequired") + }, { + name: globalize.translate("OptionHomeVideos"), + value: "homevideos" + }, { + name: globalize.translate("FolderTypeMusicVideos"), + value: "musicvideos" + }, { + name: globalize.translate("FolderTypeUnset"), + value: "mixed", + message: globalize.translate("MessageUnsetContentHelp") + }] + } + + function getIcon(type) { + switch (type) { + case "movies": + return "local_movies"; + case "music": + return "library_music"; + case "photos": + return "photo"; + case "livetv": + case "tvshows": + return "live_tv"; + case "games": + return "folder"; + case "trailers": + return "local_movies"; + case "homevideos": + case "musicvideos": + return "video_library"; + case "books": + case "channels": + case "playlists": + default: + return "folder" + } + } + + function getVirtualFolderHtml(page, virtualFolder, index) { + var html = "", + style = ""; + page.classList.contains("wizardPage") && (style += "min-width:33.3%;"), html += '
    ', html += '
    ', html += '
    ', html += '
    ', html += '
    '; + var imgUrl = ""; + virtualFolder.PrimaryImageItemId && (imgUrl = ApiClient.getScaledImageUrl(virtualFolder.PrimaryImageItemId, { + type: "Primary" + })); + var hasCardImageContainer; + if (imgUrl ? (html += '
    ", hasCardImageContainer = !0) : virtualFolder.showNameWithIcon || (html += '
    ', html += '' + (virtualFolder.icon || getIcon(virtualFolder.CollectionType)) + "", hasCardImageContainer = !0), hasCardImageContainer) { + html += '
    '; + html += '
    ', html += "
    ", html += "
    " + } + if (!imgUrl && virtualFolder.showNameWithIcon && (html += '

    ', html += '' + (virtualFolder.icon || getIcon(virtualFolder.CollectionType)) + "", virtualFolder.showNameWithIcon && (html += '
    ', html += virtualFolder.Name, html += "
    "), html += "

    "), html += "
    ", html += "
    ", html += '
    ', !1 !== virtualFolder.showMenu) { + html += '
    ', html += '', html += "
    " + } + html += "
    ", virtualFolder.showNameWithIcon ? html += " " : html += virtualFolder.Name, html += "
    "; + var typeName = getCollectionTypeOptions().filter(function(t) { + return t.value == virtualFolder.CollectionType + })[0]; + return typeName = typeName ? typeName.name : globalize.translate("FolderTypeUnset"), html += "
    ", !1 === virtualFolder.showType ? html += " " : html += typeName, html += "
    ", !1 === virtualFolder.showLocations ? (html += "
    ", html += " ", html += "
    ") : virtualFolder.Locations.length && 1 == virtualFolder.Locations.length ? (html += "
    ", html += virtualFolder.Locations[0], html += "
    ") : (html += "
    ", html += globalize.translate("NumLocationsValue", virtualFolder.Locations.length), html += "
    "), html += "
    ", html += "
    ", html += "
    " + } + + function getTabs() { + return [{ + href: "library.html", + name: globalize.translate("HeaderLibraries") + }, { + href: "librarydisplay.html", + name: globalize.translate("TabDisplay") + }, { + href: "metadataimages.html", + name: globalize.translate("TabMetadata") + }, { + href: "metadatanfo.html", + name: globalize.translate("TabNfoSettings") + }, { + href: "librarysettings.html", + name: globalize.translate("TabAdvanced") + }] + } + window.WizardLibraryPage = { + next: function() { + Dashboard.navigate("wizardsettings.html") + } + }, pageClassOn("pageshow", "mediaLibraryPage", function() { + reloadLibrary(this) + }), pageIdOn("pageshow", "mediaLibraryPage", function() { + libraryMenu.setTabs("librarysetup", 0, getTabs); + var page = this; + taskButton({ + mode: "on", + progressElem: page.querySelector(".refreshProgress"), + taskKey: "RefreshLibrary", + button: page.querySelector(".btnRefresh") + }) + }), pageIdOn("pagebeforehide", "mediaLibraryPage", function() { + var page = this; + taskButton({ + mode: "off", + progressElem: page.querySelector(".refreshProgress"), + taskKey: "RefreshLibrary", + button: page.querySelector(".btnRefresh") + }) + }) +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/metadataimagespage.js b/dashboard-ui/scripts/metadataimagespage.js index 8d8d0b3fa2..58eae09dd1 100644 --- a/dashboard-ui/scripts/metadataimagespage.js +++ b/dashboard-ui/scripts/metadataimagespage.js @@ -1 +1,66 @@ -define(["jQuery","dom","loading","libraryMenu","listViewStyle"],function($,dom,loading,libraryMenu){"use strict";function populateLanguages(select){return ApiClient.getCultures().then(function(languages){var html="";html+="";for(var i=0,length=languages.length;i"+culture.DisplayName+""}select.innerHTML=html})}function populateCountries(select){return ApiClient.getCountries().then(function(allCountries){var html="";html+="";for(var i=0,length=allCountries.length;i"+culture.DisplayName+""}select.innerHTML=html})}function loadPage(page){var promises=[ApiClient.getServerConfiguration(),populateLanguages(page.querySelector("#selectLanguage")),populateCountries(page.querySelector("#selectCountry"))];Promise.all(promises).then(function(responses){var config=responses[0];page.querySelector("#selectLanguage").value=config.PreferredMetadataLanguage||"",page.querySelector("#selectCountry").value=config.MetadataCountryCode||"",loading.hide()})}function onSubmit(){var form=this;return loading.show(),ApiClient.getServerConfiguration().then(function(config){config.PreferredMetadataLanguage=form.querySelector("#selectLanguage").value,config.MetadataCountryCode=form.querySelector("#selectCountry").value,ApiClient.updateServerConfiguration(config).then(Dashboard.processServerConfigurationUpdateResult)}),!1}function getTabs(){return[{href:"library.html",name:Globalize.translate("HeaderLibraries")},{href:"librarydisplay.html",name:Globalize.translate("TabDisplay")},{href:"metadataimages.html",name:Globalize.translate("TabMetadata")},{href:"metadatanfo.html",name:Globalize.translate("TabNfoSettings")},{href:"librarysettings.html",name:Globalize.translate("TabAdvanced")}]}$(document).on("pageinit","#metadataImagesConfigurationPage",function(){$(".metadataImagesConfigurationForm").off("submit",onSubmit).on("submit",onSubmit)}).on("pageshow","#metadataImagesConfigurationPage",function(){libraryMenu.setTabs("metadata",2,getTabs),loading.show(),loadPage(this)})}); \ No newline at end of file +define(["jQuery", "dom", "loading", "libraryMenu", "listViewStyle"], function($, dom, loading, libraryMenu) { + "use strict"; + + function populateLanguages(select) { + return ApiClient.getCultures().then(function(languages) { + var html = ""; + html += ""; + for (var i = 0, length = languages.length; i < length; i++) { + var culture = languages[i]; + html += "" + } + select.innerHTML = html + }) + } + + function populateCountries(select) { + return ApiClient.getCountries().then(function(allCountries) { + var html = ""; + html += ""; + for (var i = 0, length = allCountries.length; i < length; i++) { + var culture = allCountries[i]; + html += "" + } + select.innerHTML = html + }) + } + + function loadPage(page) { + var promises = [ApiClient.getServerConfiguration(), populateLanguages(page.querySelector("#selectLanguage")), populateCountries(page.querySelector("#selectCountry"))]; + Promise.all(promises).then(function(responses) { + var config = responses[0]; + page.querySelector("#selectLanguage").value = config.PreferredMetadataLanguage || "", page.querySelector("#selectCountry").value = config.MetadataCountryCode || "", loading.hide() + }) + } + + function onSubmit() { + var form = this; + return loading.show(), ApiClient.getServerConfiguration().then(function(config) { + config.PreferredMetadataLanguage = form.querySelector("#selectLanguage").value, config.MetadataCountryCode = form.querySelector("#selectCountry").value, ApiClient.updateServerConfiguration(config).then(Dashboard.processServerConfigurationUpdateResult) + }), !1 + } + + function getTabs() { + return [{ + href: "library.html", + name: Globalize.translate("HeaderLibraries") + }, { + href: "librarydisplay.html", + name: Globalize.translate("TabDisplay") + }, { + href: "metadataimages.html", + name: Globalize.translate("TabMetadata") + }, { + href: "metadatanfo.html", + name: Globalize.translate("TabNfoSettings") + }, { + href: "librarysettings.html", + name: Globalize.translate("TabAdvanced") + }] + } + $(document).on("pageinit", "#metadataImagesConfigurationPage", function() { + $(".metadataImagesConfigurationForm").off("submit", onSubmit).on("submit", onSubmit) + }).on("pageshow", "#metadataImagesConfigurationPage", function() { + libraryMenu.setTabs("metadata", 2, getTabs), loading.show(), loadPage(this) + }) +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/metadatanfo.js b/dashboard-ui/scripts/metadatanfo.js index cfabe3da67..d7ed677304 100644 --- a/dashboard-ui/scripts/metadatanfo.js +++ b/dashboard-ui/scripts/metadatanfo.js @@ -1 +1,60 @@ -define(["jQuery","loading","libraryMenu"],function($,loading,libraryMenu){"use strict";function loadPage(page,config,users){var html='";html+=users.map(function(user){return'"}).join(""),$("#selectUser",page).html(html).val(config.UserId||""),$("#selectReleaseDateFormat",page).val(config.ReleaseDateFormat),page.querySelector("#chkSaveImagePaths").checked=config.SaveImagePathsInNfo,page.querySelector("#chkEnablePathSubstitution").checked=config.EnablePathSubstitution,page.querySelector("#chkEnableExtraThumbs").checked=config.EnableExtraThumbsDuplication,loading.hide()}function onSubmit(){loading.show();var form=this;return ApiClient.getNamedConfiguration(metadataKey).then(function(config){config.UserId=$("#selectUser",form).val()||null,config.ReleaseDateFormat=$("#selectReleaseDateFormat",form).val(),config.SaveImagePathsInNfo=form.querySelector("#chkSaveImagePaths").checked,config.EnablePathSubstitution=form.querySelector("#chkEnablePathSubstitution").checked,config.EnableExtraThumbsDuplication=form.querySelector("#chkEnableExtraThumbs").checked,ApiClient.updateNamedConfiguration(metadataKey,config).then(function(){Dashboard.processServerConfigurationUpdateResult(),showConfirmMessage(config)})}),!1}function showConfirmMessage(config){var msg=[];msg.push(Globalize.translate("MetadataSettingChangeHelp")),require(["alert"],function(alert){alert({text:msg.join("

    ")})})}function getTabs(){return[{href:"library.html",name:Globalize.translate("HeaderLibraries")},{href:"librarydisplay.html",name:Globalize.translate("TabDisplay")},{href:"metadataimages.html",name:Globalize.translate("TabMetadata")},{href:"metadatanfo.html",name:Globalize.translate("TabNfoSettings")},{href:"librarysettings.html",name:Globalize.translate("TabAdvanced")}]}var metadataKey="xbmcmetadata";$(document).on("pageinit","#metadataNfoPage",function(){$(".metadataNfoForm").off("submit",onSubmit).on("submit",onSubmit)}).on("pageshow","#metadataNfoPage",function(){libraryMenu.setTabs("metadata",3,getTabs),loading.show();var page=this,promise1=ApiClient.getUsers(),promise2=ApiClient.getNamedConfiguration(metadataKey);Promise.all([promise1,promise2]).then(function(responses){loadPage(page,responses[1],responses[0])})})}); \ No newline at end of file +define(["jQuery", "loading", "libraryMenu"], function($, loading, libraryMenu) { + "use strict"; + + function loadPage(page, config, users) { + var html = '"; + html += users.map(function(user) { + return '" + }).join(""), $("#selectUser", page).html(html).val(config.UserId || ""), $("#selectReleaseDateFormat", page).val(config.ReleaseDateFormat), page.querySelector("#chkSaveImagePaths").checked = config.SaveImagePathsInNfo, page.querySelector("#chkEnablePathSubstitution").checked = config.EnablePathSubstitution, page.querySelector("#chkEnableExtraThumbs").checked = config.EnableExtraThumbsDuplication, loading.hide() + } + + function onSubmit() { + loading.show(); + var form = this; + return ApiClient.getNamedConfiguration(metadataKey).then(function(config) { + config.UserId = $("#selectUser", form).val() || null, config.ReleaseDateFormat = $("#selectReleaseDateFormat", form).val(), config.SaveImagePathsInNfo = form.querySelector("#chkSaveImagePaths").checked, config.EnablePathSubstitution = form.querySelector("#chkEnablePathSubstitution").checked, config.EnableExtraThumbsDuplication = form.querySelector("#chkEnableExtraThumbs").checked, ApiClient.updateNamedConfiguration(metadataKey, config).then(function() { + Dashboard.processServerConfigurationUpdateResult(), showConfirmMessage(config) + }) + }), !1 + } + + function showConfirmMessage(config) { + var msg = []; + msg.push(Globalize.translate("MetadataSettingChangeHelp")), require(["alert"], function(alert) { + alert({ + text: msg.join("

    ") + }) + }) + } + + function getTabs() { + return [{ + href: "library.html", + name: Globalize.translate("HeaderLibraries") + }, { + href: "librarydisplay.html", + name: Globalize.translate("TabDisplay") + }, { + href: "metadataimages.html", + name: Globalize.translate("TabMetadata") + }, { + href: "metadatanfo.html", + name: Globalize.translate("TabNfoSettings") + }, { + href: "librarysettings.html", + name: Globalize.translate("TabAdvanced") + }] + } + var metadataKey = "xbmcmetadata"; + $(document).on("pageinit", "#metadataNfoPage", function() { + $(".metadataNfoForm").off("submit", onSubmit).on("submit", onSubmit) + }).on("pageshow", "#metadataNfoPage", function() { + libraryMenu.setTabs("metadata", 3, getTabs), loading.show(); + var page = this, + promise1 = ApiClient.getUsers(), + promise2 = ApiClient.getNamedConfiguration(metadataKey); + Promise.all([promise1, promise2]).then(function(responses) { + loadPage(page, responses[1], responses[0]) + }) + }) +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/moviecollections.js b/dashboard-ui/scripts/moviecollections.js index a380277a03..bf908fc887 100644 --- a/dashboard-ui/scripts/moviecollections.js +++ b/dashboard-ui/scripts/moviecollections.js @@ -1 +1,163 @@ -define(["loading","events","libraryBrowser","imageLoader","listView","cardBuilder","apphost","emby-itemscontainer"],function(loading,events,libraryBrowser,imageLoader,listView,cardBuilder,appHost){"use strict";return function(view,params,tabContent){function getPageData(context){var key=getSavedQueryKey(context),pageData=data[key];return pageData||(pageData=data[key]={query:{SortBy:"SortName",SortOrder:"Ascending",IncludeItemTypes:"BoxSet",Recursive:!0,Fields:"PrimaryImageAspectRatio,SortName",ImageTypeLimit:1,EnableImageTypes:"Primary,Backdrop,Banner,Thumb",StartIndex:0,Limit:pageSize},view:libraryBrowser.getSavedView(key)||"Poster"},pageData.query.ParentId=params.topParentId,libraryBrowser.loadSavedQueryValues(key,pageData.query)),pageData}function getQuery(context){return getPageData(context).query}function getSavedQueryKey(context){return context.savedQueryKey||(context.savedQueryKey=libraryBrowser.getSavedQueryKey("moviecollections")),context.savedQueryKey}function onViewStyleChange(){var viewStyle=self.getCurrentViewStyle(),itemsContainer=tabContent.querySelector(".itemsContainer");"List"==viewStyle?(itemsContainer.classList.add("vertical-list"),itemsContainer.classList.remove("vertical-wrap")):(itemsContainer.classList.remove("vertical-list"),itemsContainer.classList.add("vertical-wrap")),itemsContainer.innerHTML=""}function reloadItems(page){loading.show();var query=getQuery(page);ApiClient.getItems(ApiClient.getCurrentUserId(),query).then(function(result){function onNextPageClick(){query.StartIndex+=query.Limit,reloadItems(tabContent)}function onPreviousPageClick(){query.StartIndex-=query.Limit,reloadItems(tabContent)}window.scrollTo(0,0);var html,pagingHtml=libraryBrowser.getQueryPagingHtml({startIndex:query.StartIndex,limit:query.Limit,totalRecordCount:result.TotalRecordCount,showLimit:!1,updatePageSizeSetting:!1,addLayoutButton:!1,sortButton:!1,filterButton:!1}),viewStyle=self.getCurrentViewStyle();html="Thumb"==viewStyle?cardBuilder.getCardsHtml({items:result.Items,shape:"backdrop",preferThumb:!0,context:"movies",overlayPlayButton:!0,centerText:!0,showTitle:!0}):"ThumbCard"==viewStyle?cardBuilder.getCardsHtml({items:result.Items,shape:"backdrop",preferThumb:!0,context:"movies",lazy:!0,cardLayout:!0,showTitle:!0,vibrant:!0}):"Banner"==viewStyle?cardBuilder.getCardsHtml({items:result.Items,shape:"banner",preferBanner:!0,context:"movies",lazy:!0}):"List"==viewStyle?listView.getListViewHtml({items:result.Items,context:"movies",sortBy:query.SortBy}):"PosterCard"==viewStyle?cardBuilder.getCardsHtml({items:result.Items,shape:"auto",context:"movies",showTitle:!0,centerText:!1,cardLayout:!0,vibrant:!0}):cardBuilder.getCardsHtml({items:result.Items,shape:"auto",context:"movies",centerText:!0,overlayPlayButton:!0,showTitle:!0});var i,length,elems=tabContent.querySelectorAll(".paging");for(i=0,length=elems.length;i'+Globalize.translate("MessageNoCollectionsAvailable")+"

    ");var itemsContainer=tabContent.querySelector(".itemsContainer");itemsContainer.innerHTML=html,imageLoader.lazyChildren(itemsContainer),libraryBrowser.saveQueryValues(getSavedQueryKey(page),query),loading.hide()})}var self=this,pageSize=100,data={};self.getCurrentViewStyle=function(){return getPageData(tabContent).view},function(tabContent){tabContent.querySelector(".btnSort").addEventListener("click",function(e){libraryBrowser.showSortMenu({items:[{name:Globalize.translate("OptionNameSort"),id:"SortName"},{name:Globalize.translate("OptionImdbRating"),id:"CommunityRating,SortName"},{name:Globalize.translate("OptionDateAdded"),id:"DateCreated,SortName"},{name:Globalize.translate("OptionParentalRating"),id:"OfficialRating,SortName"},{name:Globalize.translate("OptionReleaseDate"),id:"PremiereDate,SortName"}],callback:function(){getQuery(tabContent).StartIndex=0,reloadItems(tabContent)},query:getQuery(tabContent),button:e.target})});var btnSelectView=tabContent.querySelector(".btnSelectView");btnSelectView.addEventListener("click",function(e){libraryBrowser.showLayoutMenu(e.target,self.getCurrentViewStyle(),"List,Poster,PosterCard,Thumb,ThumbCard".split(","))}),btnSelectView.addEventListener("layoutchange",function(e){var viewStyle=e.detail.viewStyle;getPageData(tabContent).view=viewStyle,libraryBrowser.saveViewSetting(getSavedQueryKey(tabContent),viewStyle),getQuery(tabContent).StartIndex=0,onViewStyleChange(),reloadItems(tabContent)}),tabContent.querySelector(".btnNewCollection").addEventListener("click",function(){require(["collectionEditor"],function(collectionEditor){var serverId=ApiClient.serverInfo().Id;(new collectionEditor).show({items:[],serverId:serverId})})})}(tabContent),onViewStyleChange(),self.renderTab=function(){reloadItems(tabContent)},self.destroy=function(){}}}); \ No newline at end of file +define(["loading", "events", "libraryBrowser", "imageLoader", "listView", "cardBuilder", "apphost", "emby-itemscontainer"], function(loading, events, libraryBrowser, imageLoader, listView, cardBuilder, appHost) { + "use strict"; + return function(view, params, tabContent) { + function getPageData(context) { + var key = getSavedQueryKey(context), + pageData = data[key]; + return pageData || (pageData = data[key] = { + query: { + SortBy: "SortName", + SortOrder: "Ascending", + IncludeItemTypes: "BoxSet", + Recursive: !0, + Fields: "PrimaryImageAspectRatio,SortName", + ImageTypeLimit: 1, + EnableImageTypes: "Primary,Backdrop,Banner,Thumb", + StartIndex: 0, + Limit: pageSize + }, + view: libraryBrowser.getSavedView(key) || "Poster" + }, pageData.query.ParentId = params.topParentId, libraryBrowser.loadSavedQueryValues(key, pageData.query)), pageData + } + + function getQuery(context) { + return getPageData(context).query + } + + function getSavedQueryKey(context) { + return context.savedQueryKey || (context.savedQueryKey = libraryBrowser.getSavedQueryKey("moviecollections")), context.savedQueryKey + } + + function onViewStyleChange() { + var viewStyle = self.getCurrentViewStyle(), + itemsContainer = tabContent.querySelector(".itemsContainer"); + "List" == viewStyle ? (itemsContainer.classList.add("vertical-list"), itemsContainer.classList.remove("vertical-wrap")) : (itemsContainer.classList.remove("vertical-list"), itemsContainer.classList.add("vertical-wrap")), itemsContainer.innerHTML = "" + } + + function reloadItems(page) { + loading.show(); + var query = getQuery(page); + ApiClient.getItems(ApiClient.getCurrentUserId(), query).then(function(result) { + function onNextPageClick() { + query.StartIndex += query.Limit, reloadItems(tabContent) + } + + function onPreviousPageClick() { + query.StartIndex -= query.Limit, reloadItems(tabContent) + } + window.scrollTo(0, 0); + var html, pagingHtml = libraryBrowser.getQueryPagingHtml({ + startIndex: query.StartIndex, + limit: query.Limit, + totalRecordCount: result.TotalRecordCount, + showLimit: !1, + updatePageSizeSetting: !1, + addLayoutButton: !1, + sortButton: !1, + filterButton: !1 + }), + viewStyle = self.getCurrentViewStyle(); + html = "Thumb" == viewStyle ? cardBuilder.getCardsHtml({ + items: result.Items, + shape: "backdrop", + preferThumb: !0, + context: "movies", + overlayPlayButton: !0, + centerText: !0, + showTitle: !0 + }) : "ThumbCard" == viewStyle ? cardBuilder.getCardsHtml({ + items: result.Items, + shape: "backdrop", + preferThumb: !0, + context: "movies", + lazy: !0, + cardLayout: !0, + showTitle: !0, + vibrant: !0 + }) : "Banner" == viewStyle ? cardBuilder.getCardsHtml({ + items: result.Items, + shape: "banner", + preferBanner: !0, + context: "movies", + lazy: !0 + }) : "List" == viewStyle ? listView.getListViewHtml({ + items: result.Items, + context: "movies", + sortBy: query.SortBy + }) : "PosterCard" == viewStyle ? cardBuilder.getCardsHtml({ + items: result.Items, + shape: "auto", + context: "movies", + showTitle: !0, + centerText: !1, + cardLayout: !0, + vibrant: !0 + }) : cardBuilder.getCardsHtml({ + items: result.Items, + shape: "auto", + context: "movies", + centerText: !0, + overlayPlayButton: !0, + showTitle: !0 + }); + var i, length, elems = tabContent.querySelectorAll(".paging"); + for (i = 0, length = elems.length; i < length; i++) elems[i].innerHTML = pagingHtml; + for (elems = tabContent.querySelectorAll(".btnNextPage"), i = 0, length = elems.length; i < length; i++) elems[i].addEventListener("click", onNextPageClick); + for (elems = tabContent.querySelectorAll(".btnPreviousPage"), i = 0, length = elems.length; i < length; i++) elems[i].addEventListener("click", onPreviousPageClick); + result.Items.length || (html = '

    ' + Globalize.translate("MessageNoCollectionsAvailable") + "

    "); + var itemsContainer = tabContent.querySelector(".itemsContainer"); + itemsContainer.innerHTML = html, imageLoader.lazyChildren(itemsContainer), libraryBrowser.saveQueryValues(getSavedQueryKey(page), query), loading.hide() + }) + } + var self = this, + pageSize = 100, + data = {}; + self.getCurrentViewStyle = function() { + return getPageData(tabContent).view + }, + function(tabContent) { + tabContent.querySelector(".btnSort").addEventListener("click", function(e) { + libraryBrowser.showSortMenu({ + items: [{ + name: Globalize.translate("OptionNameSort"), + id: "SortName" + }, { + name: Globalize.translate("OptionImdbRating"), + id: "CommunityRating,SortName" + }, { + name: Globalize.translate("OptionDateAdded"), + id: "DateCreated,SortName" + }, { + name: Globalize.translate("OptionParentalRating"), + id: "OfficialRating,SortName" + }, { + name: Globalize.translate("OptionReleaseDate"), + id: "PremiereDate,SortName" + }], + callback: function() { + getQuery(tabContent).StartIndex = 0, reloadItems(tabContent) + }, + query: getQuery(tabContent), + button: e.target + }) + }); + var btnSelectView = tabContent.querySelector(".btnSelectView"); + btnSelectView.addEventListener("click", function(e) { + libraryBrowser.showLayoutMenu(e.target, self.getCurrentViewStyle(), "List,Poster,PosterCard,Thumb,ThumbCard".split(",")) + }), btnSelectView.addEventListener("layoutchange", function(e) { + var viewStyle = e.detail.viewStyle; + getPageData(tabContent).view = viewStyle, libraryBrowser.saveViewSetting(getSavedQueryKey(tabContent), viewStyle), getQuery(tabContent).StartIndex = 0, onViewStyleChange(), reloadItems(tabContent) + }), tabContent.querySelector(".btnNewCollection").addEventListener("click", function() { + require(["collectionEditor"], function(collectionEditor) { + var serverId = ApiClient.serverInfo().Id; + (new collectionEditor).show({ + items: [], + serverId: serverId + }) + }) + }) + }(tabContent), onViewStyleChange(), self.renderTab = function() { + reloadItems(tabContent) + }, self.destroy = function() {} + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/moviegenres.js b/dashboard-ui/scripts/moviegenres.js index 94076cebca..baac9fbc8c 100644 --- a/dashboard-ui/scripts/moviegenres.js +++ b/dashboard-ui/scripts/moviegenres.js @@ -1 +1,141 @@ -define(["layoutManager","loading","libraryBrowser","cardBuilder","lazyLoader","apphost","globalize","appRouter","dom","emby-linkbutton"],function(layoutManager,loading,libraryBrowser,cardBuilder,lazyLoader,appHost,globalize,appRouter,dom){"use strict";return function(view,params,tabContent){function getPageData(){var key=getSavedQueryKey(),pageData=data[key];return pageData||(pageData=data[key]={query:{SortBy:"SortName",SortOrder:"Ascending",IncludeItemTypes:"Movie",Recursive:!0,EnableTotalRecordCount:!1},view:"Poster"},pageData.query.ParentId=params.topParentId,libraryBrowser.loadSavedQueryValues(key,pageData.query)),pageData}function getQuery(){return getPageData().query}function getSavedQueryKey(){return libraryBrowser.getSavedQueryKey("moviegenres")}function getPromise(){loading.show();var query=getQuery();return ApiClient.getGenres(ApiClient.getCurrentUserId(),query)}function enableScrollX(){return!layoutManager.desktop}function getThumbShape(){return enableScrollX()?"overflowBackdrop":"backdrop"}function getPortraitShape(){return enableScrollX()?"overflowPortrait":"portrait"}function fillItemsContainer(elem){var id=elem.getAttribute("data-id"),viewStyle=self.getCurrentViewStyle(),limit="Thumb"==viewStyle||"ThumbCard"==viewStyle?5:9;enableScrollX()&&(limit=10);var enableImageTypes="Thumb"==viewStyle||"ThumbCard"==viewStyle?"Primary,Backdrop,Thumb":"Primary",query={SortBy:"SortName",SortOrder:"Ascending",IncludeItemTypes:"Movie",Recursive:!0,Fields:"PrimaryImageAspectRatio,MediaSourceCount,BasicSyncInfo",ImageTypeLimit:1,EnableImageTypes:enableImageTypes,Limit:limit,GenreIds:id,EnableTotalRecordCount:!1,ParentId:params.topParentId};ApiClient.getItems(ApiClient.getCurrentUserId(),query).then(function(result){var supportsImageAnalysis=appHost.supports("imageanalysis");"Thumb"==viewStyle?cardBuilder.buildCards(result.Items,{itemsContainer:elem,shape:getThumbShape(),preferThumb:!0,showTitle:!0,scalable:!0,centerText:!0,overlayMoreButton:!0,allowBottomPadding:!1}):"ThumbCard"==viewStyle?cardBuilder.buildCards(result.Items,{itemsContainer:elem,shape:getThumbShape(),preferThumb:!0,showTitle:!0,scalable:!0,centerText:!1,cardLayout:!0,vibrant:supportsImageAnalysis,showYear:!0}):"PosterCard"==viewStyle?cardBuilder.buildCards(result.Items,{itemsContainer:elem,shape:getPortraitShape(),showTitle:!0,scalable:!0,centerText:!1,cardLayout:!0,vibrant:supportsImageAnalysis,showYear:!0}):"Poster"==viewStyle&&cardBuilder.buildCards(result.Items,{itemsContainer:elem,shape:getPortraitShape(),scalable:!0,overlayMoreButton:!0,allowBottomPadding:!1}),result.Items.length>=query.Limit&&tabContent.querySelector(".btnMoreFromGenre"+id+" i").classList.remove("hide")})}function reloadItems(context,promise){var query=getQuery();promise.then(function(result){for(var elem=context.querySelector("#items"),html="",items=result.Items,i=0,length=items.length;i',html+='",enableScrollX()){var scrollXClass="scrollX hiddenScrollX";layoutManager.tv&&(scrollXClass+=" smoothScrollX"),html+='
    '}else html+='
    ';html+="
    ",html+="
    "}elem.innerHTML=html,lazyLoader.lazyChildren(elem,fillItemsContainer),libraryBrowser.saveQueryValues(getSavedQueryKey(),query),loading.hide()})}function fullyReload(){self.preRender(),self.renderTab()}var self=this,data={};self.getViewStyles=function(){return"Poster,PosterCard,Thumb,ThumbCard".split(",")},self.getCurrentViewStyle=function(){return getPageData(tabContent).view},self.setCurrentViewStyle=function(viewStyle){getPageData(tabContent).view=viewStyle,libraryBrowser.saveViewSetting(getSavedQueryKey(tabContent),viewStyle),fullyReload()},self.enableViewSelection=!0;var promise;self.preRender=function(){promise=getPromise()},self.renderTab=function(){reloadItems(tabContent,promise)}}}); \ No newline at end of file +define(["layoutManager", "loading", "libraryBrowser", "cardBuilder", "lazyLoader", "apphost", "globalize", "appRouter", "dom", "emby-linkbutton"], function(layoutManager, loading, libraryBrowser, cardBuilder, lazyLoader, appHost, globalize, appRouter, dom) { + "use strict"; + return function(view, params, tabContent) { + function getPageData() { + var key = getSavedQueryKey(), + pageData = data[key]; + return pageData || (pageData = data[key] = { + query: { + SortBy: "SortName", + SortOrder: "Ascending", + IncludeItemTypes: "Movie", + Recursive: !0, + EnableTotalRecordCount: !1 + }, + view: "Poster" + }, pageData.query.ParentId = params.topParentId, libraryBrowser.loadSavedQueryValues(key, pageData.query)), pageData + } + + function getQuery() { + return getPageData().query + } + + function getSavedQueryKey() { + return libraryBrowser.getSavedQueryKey("moviegenres") + } + + function getPromise() { + loading.show(); + var query = getQuery(); + return ApiClient.getGenres(ApiClient.getCurrentUserId(), query) + } + + function enableScrollX() { + return !layoutManager.desktop + } + + function getThumbShape() { + return enableScrollX() ? "overflowBackdrop" : "backdrop" + } + + function getPortraitShape() { + return enableScrollX() ? "overflowPortrait" : "portrait" + } + + function fillItemsContainer(elem) { + var id = elem.getAttribute("data-id"), + viewStyle = self.getCurrentViewStyle(), + limit = "Thumb" == viewStyle || "ThumbCard" == viewStyle ? 5 : 9; + enableScrollX() && (limit = 10); + var enableImageTypes = "Thumb" == viewStyle || "ThumbCard" == viewStyle ? "Primary,Backdrop,Thumb" : "Primary", + query = { + SortBy: "SortName", + SortOrder: "Ascending", + IncludeItemTypes: "Movie", + Recursive: !0, + Fields: "PrimaryImageAspectRatio,MediaSourceCount,BasicSyncInfo", + ImageTypeLimit: 1, + EnableImageTypes: enableImageTypes, + Limit: limit, + GenreIds: id, + EnableTotalRecordCount: !1, + ParentId: params.topParentId + }; + ApiClient.getItems(ApiClient.getCurrentUserId(), query).then(function(result) { + var supportsImageAnalysis = appHost.supports("imageanalysis"); + "Thumb" == viewStyle ? cardBuilder.buildCards(result.Items, { + itemsContainer: elem, + shape: getThumbShape(), + preferThumb: !0, + showTitle: !0, + scalable: !0, + centerText: !0, + overlayMoreButton: !0, + allowBottomPadding: !1 + }) : "ThumbCard" == viewStyle ? cardBuilder.buildCards(result.Items, { + itemsContainer: elem, + shape: getThumbShape(), + preferThumb: !0, + showTitle: !0, + scalable: !0, + centerText: !1, + cardLayout: !0, + vibrant: supportsImageAnalysis, + showYear: !0 + }) : "PosterCard" == viewStyle ? cardBuilder.buildCards(result.Items, { + itemsContainer: elem, + shape: getPortraitShape(), + showTitle: !0, + scalable: !0, + centerText: !1, + cardLayout: !0, + vibrant: supportsImageAnalysis, + showYear: !0 + }) : "Poster" == viewStyle && cardBuilder.buildCards(result.Items, { + itemsContainer: elem, + shape: getPortraitShape(), + scalable: !0, + overlayMoreButton: !0, + allowBottomPadding: !1 + }), result.Items.length >= query.Limit && tabContent.querySelector(".btnMoreFromGenre" + id + " i").classList.remove("hide") + }) + } + + function reloadItems(context, promise) { + var query = getQuery(); + promise.then(function(result) { + for (var elem = context.querySelector("#items"), html = "", items = result.Items, i = 0, length = items.length; i < length; i++) { + var item = items[i]; + if (html += '
    ', html += '", enableScrollX()) { + var scrollXClass = "scrollX hiddenScrollX"; + layoutManager.tv && (scrollXClass += " smoothScrollX"), html += '
    ' + } else html += '
    '; + html += "
    ", html += "
    " + } + elem.innerHTML = html, lazyLoader.lazyChildren(elem, fillItemsContainer), libraryBrowser.saveQueryValues(getSavedQueryKey(), query), loading.hide() + }) + } + + function fullyReload() { + self.preRender(), self.renderTab() + } + var self = this, + data = {}; + self.getViewStyles = function() { + return "Poster,PosterCard,Thumb,ThumbCard".split(",") + }, self.getCurrentViewStyle = function() { + return getPageData(tabContent).view + }, self.setCurrentViewStyle = function(viewStyle) { + getPageData(tabContent).view = viewStyle, libraryBrowser.saveViewSetting(getSavedQueryKey(tabContent), viewStyle), fullyReload() + }, self.enableViewSelection = !0; + var promise; + self.preRender = function() { + promise = getPromise() + }, self.renderTab = function() { + reloadItems(tabContent, promise) + } + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/movies.js b/dashboard-ui/scripts/movies.js index f1af581c28..36c04a7c6a 100644 --- a/dashboard-ui/scripts/movies.js +++ b/dashboard-ui/scripts/movies.js @@ -1 +1,188 @@ -define(["layoutManager","userSettings","events","libraryBrowser","alphaPicker","listView","cardBuilder","emby-itemscontainer"],function(layoutManager,userSettings,events,libraryBrowser,alphaPicker,listView,cardBuilder){"use strict";return function(view,params,tabContent,options){function onViewStyleChange(){"List"==self.getCurrentViewStyle()?(itemsContainer.classList.add("vertical-list"),itemsContainer.classList.remove("vertical-wrap")):(itemsContainer.classList.remove("vertical-list"),itemsContainer.classList.add("vertical-wrap")),itemsContainer.innerHTML=""}function updateFilterControls(){self.alphaPicker&&self.alphaPicker.value(query.NameStartsWithOrGreater)}function fetchData(){return ApiClient.getItems(ApiClient.getCurrentUserId(),query)}function afterRefresh(result){function onNextPageClick(){query.StartIndex+=query.Limit,itemsContainer.refreshItems()}function onPreviousPageClick(){query.StartIndex-=query.Limit,itemsContainer.refreshItems()}window.scrollTo(0,0),updateFilterControls();var i,length,pagingHtml=libraryBrowser.getQueryPagingHtml({startIndex:query.StartIndex,limit:query.Limit,totalRecordCount:result.TotalRecordCount,showLimit:!1,updatePageSizeSetting:!1,addLayoutButton:!1,sortButton:!1,filterButton:!1}),elems=tabContent.querySelectorAll(".paging");for(i=0,length=elems.length;i=1920?5:screenWidth>=1600?5:3,Recursive:!0,Fields:"PrimaryImageAspectRatio,MediaSourceCount,BasicSyncInfo",CollapseBoxSetItems:!1,ParentId:parentId,ImageTypeLimit:1,EnableImageTypes:"Primary,Backdrop,Banner,Thumb",EnableTotalRecordCount:!1};ApiClient.getItems(userId,options).then(function(result){result.Items.length?page.querySelector("#resumableSection").classList.remove("hide"):page.querySelector("#resumableSection").classList.add("hide");var allowBottomPadding=!enableScrollX(),container=page.querySelector("#resumableItems");cardBuilder.buildCards(result.Items,{itemsContainer:container,preferThumb:!0,shape:getThumbShape(),scalable:!0,overlayPlayButton:!0,allowBottomPadding:allowBottomPadding,cardLayout:!1,showTitle:!0,showYear:!0,centerText:!0})})}function getRecommendationHtml(recommendation){var html="",title="";switch(recommendation.RecommendationType){case"SimilarToRecentlyPlayed":title=Globalize.translate("RecommendationBecauseYouWatched").replace("{0}",recommendation.BaselineItemName);break;case"SimilarToLikedItem":title=Globalize.translate("RecommendationBecauseYouLike").replace("{0}",recommendation.BaselineItemName);break;case"HasDirectorFromRecentlyPlayed":case"HasLikedDirector":title=Globalize.translate("RecommendationDirectedBy").replace("{0}",recommendation.BaselineItemName);break;case"HasActorFromRecentlyPlayed":case"HasLikedActor":title=Globalize.translate("RecommendationStarring").replace("{0}",recommendation.BaselineItemName)}html+='
    ',html+='

    '+title+"

    ";var allowBottomPadding=!0;return enableScrollX()?(allowBottomPadding=!1,html+='
    '):html+='
    ',html+=cardBuilder.getCardsHtml(recommendation.Items,{shape:getPortraitShape(),scalable:!0,overlayPlayButton:!0,allowBottomPadding:allowBottomPadding}),html+="
    ",html+="
    "}function loadSuggestions(page,userId,parentId){var screenWidth=dom.getWindowSize().innerWidth,url=ApiClient.getUrl("Movies/Recommendations",{userId:userId,categoryLimit:6,ItemLimit:screenWidth>=1920?8:screenWidth>=1600?8:screenWidth>=1200?6:5,Fields:"PrimaryImageAspectRatio,MediaSourceCount,BasicSyncInfo",ImageTypeLimit:1,EnableImageTypes:"Primary,Backdrop,Banner,Thumb"});ApiClient.getJSON(url).then(function(recommendations){if(!recommendations.length)return page.querySelector(".noItemsMessage").classList.remove("hide"),void(page.querySelector(".recommendations").innerHTML="");var html=recommendations.map(getRecommendationHtml).join("");page.querySelector(".noItemsMessage").classList.add("hide");var recs=page.querySelector(".recommendations");recs.innerHTML=html,imageLoader.lazyChildren(recs)})}function setScrollClasses(elem,scrollX){scrollX?(elem.classList.add("hiddenScrollX"),layoutManager.tv&&elem.classList.add("smoothScrollX"),elem.classList.add("scrollX"),elem.classList.remove("vertical-wrap")):(elem.classList.remove("hiddenScrollX"),elem.classList.remove("smoothScrollX"),elem.classList.remove("scrollX"),elem.classList.add("vertical-wrap"))}function initSuggestedTab(page,tabContent){for(var containers=tabContent.querySelectorAll(".itemsContainer"),i=0,length=containers.length;i= 1920 ? 5 : screenWidth >= 1600 ? 5 : 3, + Recursive: !0, + Fields: "PrimaryImageAspectRatio,MediaSourceCount,BasicSyncInfo", + CollapseBoxSetItems: !1, + ParentId: parentId, + ImageTypeLimit: 1, + EnableImageTypes: "Primary,Backdrop,Banner,Thumb", + EnableTotalRecordCount: !1 + }; + ApiClient.getItems(userId, options).then(function(result) { + result.Items.length ? page.querySelector("#resumableSection").classList.remove("hide") : page.querySelector("#resumableSection").classList.add("hide"); + var allowBottomPadding = !enableScrollX(), + container = page.querySelector("#resumableItems"); + cardBuilder.buildCards(result.Items, { + itemsContainer: container, + preferThumb: !0, + shape: getThumbShape(), + scalable: !0, + overlayPlayButton: !0, + allowBottomPadding: allowBottomPadding, + cardLayout: !1, + showTitle: !0, + showYear: !0, + centerText: !0 + }) + }) + } + + function getRecommendationHtml(recommendation) { + var html = "", + title = ""; + switch (recommendation.RecommendationType) { + case "SimilarToRecentlyPlayed": + title = Globalize.translate("RecommendationBecauseYouWatched").replace("{0}", recommendation.BaselineItemName); + break; + case "SimilarToLikedItem": + title = Globalize.translate("RecommendationBecauseYouLike").replace("{0}", recommendation.BaselineItemName); + break; + case "HasDirectorFromRecentlyPlayed": + case "HasLikedDirector": + title = Globalize.translate("RecommendationDirectedBy").replace("{0}", recommendation.BaselineItemName); + break; + case "HasActorFromRecentlyPlayed": + case "HasLikedActor": + title = Globalize.translate("RecommendationStarring").replace("{0}", recommendation.BaselineItemName) + } + html += '
    ', html += '

    ' + title + "

    "; + var allowBottomPadding = !0; + return enableScrollX() ? (allowBottomPadding = !1, html += '
    ') : html += '
    ', html += cardBuilder.getCardsHtml(recommendation.Items, { + shape: getPortraitShape(), + scalable: !0, + overlayPlayButton: !0, + allowBottomPadding: allowBottomPadding + }), html += "
    ", html += "
    " + } + + function loadSuggestions(page, userId, parentId) { + var screenWidth = dom.getWindowSize().innerWidth, + url = ApiClient.getUrl("Movies/Recommendations", { + userId: userId, + categoryLimit: 6, + ItemLimit: screenWidth >= 1920 ? 8 : screenWidth >= 1600 ? 8 : screenWidth >= 1200 ? 6 : 5, + Fields: "PrimaryImageAspectRatio,MediaSourceCount,BasicSyncInfo", + ImageTypeLimit: 1, + EnableImageTypes: "Primary,Backdrop,Banner,Thumb" + }); + ApiClient.getJSON(url).then(function(recommendations) { + if (!recommendations.length) return page.querySelector(".noItemsMessage").classList.remove("hide"), void(page.querySelector(".recommendations").innerHTML = ""); + var html = recommendations.map(getRecommendationHtml).join(""); + page.querySelector(".noItemsMessage").classList.add("hide"); + var recs = page.querySelector(".recommendations"); + recs.innerHTML = html, imageLoader.lazyChildren(recs) + }) + } + + function setScrollClasses(elem, scrollX) { + scrollX ? (elem.classList.add("hiddenScrollX"), layoutManager.tv && elem.classList.add("smoothScrollX"), elem.classList.add("scrollX"), elem.classList.remove("vertical-wrap")) : (elem.classList.remove("hiddenScrollX"), elem.classList.remove("smoothScrollX"), elem.classList.remove("scrollX"), elem.classList.add("vertical-wrap")) + } + + function initSuggestedTab(page, tabContent) { + for (var containers = tabContent.querySelectorAll(".itemsContainer"), i = 0, length = containers.length; i < length; i++) setScrollClasses(containers[i], enableScrollX()) + } + + function loadSuggestionsTab(view, params, tabContent) { + var parentId = params.topParentId, + userId = ApiClient.getCurrentUserId(); + console.log("loadSuggestionsTab"), loadResume(tabContent, userId, parentId), loadLatest(tabContent, userId, parentId), loadSuggestions(tabContent, userId, parentId) + } + + function getTabs() { + return [{ + name: Globalize.translate("sharedcomponents#Movies") + }, { + name: Globalize.translate("TabSuggestions") + }, { + name: Globalize.translate("TabTrailers") + }, { + name: Globalize.translate("TabFavorites") + }, { + name: Globalize.translate("TabCollections") + }, { + name: Globalize.translate("TabGenres") + }, { + name: Globalize.translate("ButtonSearch"), + cssClass: "searchTabButton" + }] + } + + function getDefaultTabIndex(folderId) { + switch (userSettings.get("landing-" + folderId)) { + case "suggestions": + return 1; + case "favorites": + return 3; + case "collections": + return 4; + case "genres": + return 5; + default: + return 0 + } + } + return function(view, params) { + function onBeforeTabChange(e) { + preLoadTab(view, parseInt(e.detail.selectedTabIndex)) + } + + function onTabChange(e) { + var newIndex = parseInt(e.detail.selectedTabIndex); + loadTab(view, newIndex) + } + + function getTabContainers() { + return view.querySelectorAll(".pageTabContent") + } + + function initTabs() { + mainTabsManager.setTabs(view, currentTabIndex, getTabs, getTabContainers, onBeforeTabChange, onTabChange) + } + + function getTabController(page, index, callback) { + var depends = []; + switch (index) { + case 0: + depends.push("scripts/movies"); + break; + case 1: + break; + case 2: + depends.push("scripts/movietrailers"); + break; + case 3: + depends.push("scripts/movies"); + break; + case 4: + depends.push("scripts/moviecollections"); + break; + case 5: + depends.push("scripts/moviegenres"); + break; + case 6: + depends.push("scripts/searchtab") + } + require(depends, function(controllerFactory) { + var tabContent; + index === suggestionsTabIndex && (tabContent = view.querySelector(".pageTabContent[data-index='" + index + "']"), self.tabContent = tabContent); + var controller = tabControllers[index]; + controller || (tabContent = view.querySelector(".pageTabContent[data-index='" + index + "']"), controller = index === suggestionsTabIndex ? self : 6 === index ? new controllerFactory(view, tabContent, { + collectionType: "movies", + parentId: params.topParentId + }) : 0 === index || 3 === index ? new controllerFactory(view, params, tabContent, { + mode: index ? "favorites" : "movies" + }) : new controllerFactory(view, params, tabContent), tabControllers[index] = controller, controller.initTab && controller.initTab()), callback(controller) + }) + } + + function preLoadTab(page, index) { + getTabController(page, index, function(controller) { + -1 == renderedTabs.indexOf(index) && controller.preRender && controller.preRender() + }) + } + + function loadTab(page, index) { + currentTabIndex = index, getTabController(page, index, function(controller) { + initialTabIndex = null, -1 == renderedTabs.indexOf(index) && (renderedTabs.push(index), controller.renderTab()) + }) + } + + function onPlaybackStop(e, state) { + state.NowPlayingItem && "Video" == state.NowPlayingItem.MediaType && (renderedTabs = [], mainTabsManager.getTabsElement().triggerTabChange()) + } + + function onInputCommand(e) { + switch (e.detail.command) { + case "search": + e.preventDefault(), Dashboard.navigate("search.html?collectionType=movies&parentId=" + params.topParentId) + } + } + var isViewRestored, self = this, + currentTabIndex = parseInt(params.tab || getDefaultTabIndex(params.topParentId)), + initialTabIndex = currentTabIndex, + suggestionsTabIndex = 1; + self.initTab = function() { + var tabContent = view.querySelector(".pageTabContent[data-index='" + suggestionsTabIndex + "']"); + categorysyncbuttons.init(tabContent), initSuggestedTab(view, tabContent) + }, self.renderTab = function() { + var tabContent = view.querySelector(".pageTabContent[data-index='" + suggestionsTabIndex + "']"); + loadSuggestionsTab(view, params, tabContent) + }; + var tabControllers = [], + renderedTabs = []; + view.addEventListener("viewshow", function(e) { + if (isViewRestored = e.detail.isRestored, initTabs(), !view.getAttribute("data-title")) { + var parentId = params.topParentId; + parentId ? ApiClient.getItem(ApiClient.getCurrentUserId(), parentId).then(function(item) { + view.setAttribute("data-title", item.Name), libraryMenu.setTitle(item.Name) + }) : (view.setAttribute("data-title", Globalize.translate("TabMovies")), libraryMenu.setTitle(Globalize.translate("TabMovies"))) + } + events.on(playbackManager, "playbackstop", onPlaybackStop), inputManager.on(window, onInputCommand) + }), view.addEventListener("viewbeforehide", function(e) { + inputManager.off(window, onInputCommand) + }), view.addEventListener("viewdestroy", function(e) { + tabControllers.forEach(function(t) { + t.destroy && t.destroy() + }) + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/movietrailers.js b/dashboard-ui/scripts/movietrailers.js index ed3177a5b9..9761733db4 100644 --- a/dashboard-ui/scripts/movietrailers.js +++ b/dashboard-ui/scripts/movietrailers.js @@ -1 +1,177 @@ -define(["layoutManager","loading","events","libraryBrowser","imageLoader","alphaPicker","listView","cardBuilder","apphost","emby-itemscontainer"],function(layoutManager,loading,events,libraryBrowser,imageLoader,alphaPicker,listView,cardBuilder,appHost){"use strict";return function(view,params,tabContent){function getPageData(context){var key=getSavedQueryKey(context),pageData=data[key];return pageData||(pageData=data[key]={query:{SortBy:"SortName",SortOrder:"Ascending",IncludeItemTypes:"Trailer",Recursive:!0,Fields:"PrimaryImageAspectRatio,SortName,BasicSyncInfo",ImageTypeLimit:1,EnableImageTypes:"Primary,Backdrop,Banner,Thumb",StartIndex:0,Limit:pageSize},view:libraryBrowser.getSavedView(key)||"Poster"},libraryBrowser.loadSavedQueryValues(key,pageData.query)),pageData}function getQuery(context){return getPageData(context).query}function getSavedQueryKey(context){return context.savedQueryKey||(context.savedQueryKey=libraryBrowser.getSavedQueryKey("trailers")),context.savedQueryKey}function reloadItems(){loading.show();var query=getQuery(tabContent);ApiClient.getItems(ApiClient.getCurrentUserId(),query).then(function(result){function onNextPageClick(){query.StartIndex+=query.Limit,reloadItems()}function onPreviousPageClick(){query.StartIndex-=query.Limit,reloadItems()}window.scrollTo(0,0),updateFilterControls(tabContent);var html,pagingHtml=libraryBrowser.getQueryPagingHtml({startIndex:query.StartIndex,limit:query.Limit,totalRecordCount:result.TotalRecordCount,showLimit:!1,updatePageSizeSetting:!1,addLayoutButton:!1,sortButton:!1,filterButton:!1}),viewStyle=self.getCurrentViewStyle();html="Thumb"==viewStyle?cardBuilder.getCardsHtml({items:result.Items,shape:"backdrop",preferThumb:!0,context:"movies",overlayPlayButton:!0}):"ThumbCard"==viewStyle?cardBuilder.getCardsHtml({items:result.Items,shape:"backdrop",preferThumb:!0,context:"movies",cardLayout:!0,showTitle:!0,showYear:!0,vibrant:!0}):"Banner"==viewStyle?cardBuilder.getCardsHtml({items:result.Items,shape:"banner",preferBanner:!0,context:"movies"}):"List"==viewStyle?listView.getListViewHtml({items:result.Items,context:"movies",sortBy:query.SortBy}):"PosterCard"==viewStyle?cardBuilder.getCardsHtml({items:result.Items,shape:"portrait",context:"movies",showTitle:!0,showYear:!0,cardLayout:!0,vibrant:!0}):cardBuilder.getCardsHtml({items:result.Items,shape:"portrait",context:"movies",centerText:!0,overlayPlayButton:!0,showTitle:!0,showYear:!0});var i,length,elems=tabContent.querySelectorAll(".paging");for(i=0,length=elems.length;i'+Globalize.translate("MessageNoTrailersFound")+"

    ");var itemsContainer=tabContent.querySelector(".itemsContainer");itemsContainer.innerHTML=html,imageLoader.lazyChildren(itemsContainer),libraryBrowser.saveQueryValues(getSavedQueryKey(tabContent),query),loading.hide()})}function updateFilterControls(tabContent){var query=getQuery(tabContent);self.alphaPicker.value(query.NameStartsWithOrGreater)}var self=this,pageSize=100,data={};self.showFilterMenu=function(){require(["components/filterdialog/filterdialog"],function(filterDialogFactory){var filterDialog=new filterDialogFactory({query:getQuery(tabContent),mode:"movies",serverId:ApiClient.serverId()});events.on(filterDialog,"filterchange",function(){getQuery(tabContent).StartIndex=0,reloadItems()}),filterDialog.show()})},self.getCurrentViewStyle=function(){return getPageData(tabContent).view},function(tabContent){var alphaPickerElement=tabContent.querySelector(".alphaPicker");if(alphaPickerElement.addEventListener("alphavaluechanged",function(e){var newValue=e.detail.value,query=getQuery(tabContent);query.NameStartsWithOrGreater=newValue,query.StartIndex=0,reloadItems()}),self.alphaPicker=new alphaPicker({element:alphaPickerElement,valueChangeEvent:"click"}),layoutManager.desktop||layoutManager.mobile){tabContent.querySelector(".alphaPicker").classList.add("alphabetPicker-right");var itemsContainer=tabContent.querySelector(".itemsContainer");itemsContainer.classList.remove("padded-left-withalphapicker"),itemsContainer.classList.add("padded-right-withalphapicker")}tabContent.querySelector(".btnFilter").addEventListener("click",function(){self.showFilterMenu()}),tabContent.querySelector(".btnSort").addEventListener("click",function(e){libraryBrowser.showSortMenu({items:[{name:Globalize.translate("OptionNameSort"),id:"SortName"},{name:Globalize.translate("OptionImdbRating"),id:"CommunityRating,SortName"},{name:Globalize.translate("OptionDateAdded"),id:"DateCreated,SortName"},{name:Globalize.translate("OptionDatePlayed"),id:"DatePlayed,SortName"},{name:Globalize.translate("OptionParentalRating"),id:"OfficialRating,SortName"},{name:Globalize.translate("OptionPlayCount"),id:"PlayCount,SortName"},{name:Globalize.translate("OptionReleaseDate"),id:"PremiereDate,SortName"}],callback:function(){getQuery(tabContent).StartIndex=0,reloadItems()},query:getQuery(tabContent),button:e.target})})}(tabContent),self.renderTab=function(){reloadItems(),updateFilterControls(tabContent)},self.destroy=function(){}}}); \ No newline at end of file +define(["layoutManager", "loading", "events", "libraryBrowser", "imageLoader", "alphaPicker", "listView", "cardBuilder", "apphost", "emby-itemscontainer"], function(layoutManager, loading, events, libraryBrowser, imageLoader, alphaPicker, listView, cardBuilder, appHost) { + "use strict"; + return function(view, params, tabContent) { + function getPageData(context) { + var key = getSavedQueryKey(context), + pageData = data[key]; + return pageData || (pageData = data[key] = { + query: { + SortBy: "SortName", + SortOrder: "Ascending", + IncludeItemTypes: "Trailer", + Recursive: !0, + Fields: "PrimaryImageAspectRatio,SortName,BasicSyncInfo", + ImageTypeLimit: 1, + EnableImageTypes: "Primary,Backdrop,Banner,Thumb", + StartIndex: 0, + Limit: pageSize + }, + view: libraryBrowser.getSavedView(key) || "Poster" + }, libraryBrowser.loadSavedQueryValues(key, pageData.query)), pageData + } + + function getQuery(context) { + return getPageData(context).query + } + + function getSavedQueryKey(context) { + return context.savedQueryKey || (context.savedQueryKey = libraryBrowser.getSavedQueryKey("trailers")), context.savedQueryKey + } + + function reloadItems() { + loading.show(); + var query = getQuery(tabContent); + ApiClient.getItems(ApiClient.getCurrentUserId(), query).then(function(result) { + function onNextPageClick() { + query.StartIndex += query.Limit, reloadItems() + } + + function onPreviousPageClick() { + query.StartIndex -= query.Limit, reloadItems() + } + window.scrollTo(0, 0), updateFilterControls(tabContent); + var html, pagingHtml = libraryBrowser.getQueryPagingHtml({ + startIndex: query.StartIndex, + limit: query.Limit, + totalRecordCount: result.TotalRecordCount, + showLimit: !1, + updatePageSizeSetting: !1, + addLayoutButton: !1, + sortButton: !1, + filterButton: !1 + }), + viewStyle = self.getCurrentViewStyle(); + html = "Thumb" == viewStyle ? cardBuilder.getCardsHtml({ + items: result.Items, + shape: "backdrop", + preferThumb: !0, + context: "movies", + overlayPlayButton: !0 + }) : "ThumbCard" == viewStyle ? cardBuilder.getCardsHtml({ + items: result.Items, + shape: "backdrop", + preferThumb: !0, + context: "movies", + cardLayout: !0, + showTitle: !0, + showYear: !0, + vibrant: !0 + }) : "Banner" == viewStyle ? cardBuilder.getCardsHtml({ + items: result.Items, + shape: "banner", + preferBanner: !0, + context: "movies" + }) : "List" == viewStyle ? listView.getListViewHtml({ + items: result.Items, + context: "movies", + sortBy: query.SortBy + }) : "PosterCard" == viewStyle ? cardBuilder.getCardsHtml({ + items: result.Items, + shape: "portrait", + context: "movies", + showTitle: !0, + showYear: !0, + cardLayout: !0, + vibrant: !0 + }) : cardBuilder.getCardsHtml({ + items: result.Items, + shape: "portrait", + context: "movies", + centerText: !0, + overlayPlayButton: !0, + showTitle: !0, + showYear: !0 + }); + var i, length, elems = tabContent.querySelectorAll(".paging"); + for (i = 0, length = elems.length; i < length; i++) elems[i].innerHTML = pagingHtml; + for (elems = tabContent.querySelectorAll(".btnNextPage"), i = 0, length = elems.length; i < length; i++) elems[i].addEventListener("click", onNextPageClick); + for (elems = tabContent.querySelectorAll(".btnPreviousPage"), i = 0, length = elems.length; i < length; i++) elems[i].addEventListener("click", onPreviousPageClick); + result.Items.length || (html = '

    ' + Globalize.translate("MessageNoTrailersFound") + "

    "); + var itemsContainer = tabContent.querySelector(".itemsContainer"); + itemsContainer.innerHTML = html, imageLoader.lazyChildren(itemsContainer), libraryBrowser.saveQueryValues(getSavedQueryKey(tabContent), query), loading.hide() + }) + } + + function updateFilterControls(tabContent) { + var query = getQuery(tabContent); + self.alphaPicker.value(query.NameStartsWithOrGreater) + } + var self = this, + pageSize = 100, + data = {}; + self.showFilterMenu = function() { + require(["components/filterdialog/filterdialog"], function(filterDialogFactory) { + var filterDialog = new filterDialogFactory({ + query: getQuery(tabContent), + mode: "movies", + serverId: ApiClient.serverId() + }); + events.on(filterDialog, "filterchange", function() { + getQuery(tabContent).StartIndex = 0, reloadItems() + }), filterDialog.show() + }) + }, self.getCurrentViewStyle = function() { + return getPageData(tabContent).view + }, + function(tabContent) { + var alphaPickerElement = tabContent.querySelector(".alphaPicker"); + if (alphaPickerElement.addEventListener("alphavaluechanged", function(e) { + var newValue = e.detail.value, + query = getQuery(tabContent); + query.NameStartsWithOrGreater = newValue, query.StartIndex = 0, reloadItems() + }), self.alphaPicker = new alphaPicker({ + element: alphaPickerElement, + valueChangeEvent: "click" + }), layoutManager.desktop || layoutManager.mobile) { + tabContent.querySelector(".alphaPicker").classList.add("alphabetPicker-right"); + var itemsContainer = tabContent.querySelector(".itemsContainer"); + itemsContainer.classList.remove("padded-left-withalphapicker"), itemsContainer.classList.add("padded-right-withalphapicker") + } + tabContent.querySelector(".btnFilter").addEventListener("click", function() { + self.showFilterMenu() + }), tabContent.querySelector(".btnSort").addEventListener("click", function(e) { + libraryBrowser.showSortMenu({ + items: [{ + name: Globalize.translate("OptionNameSort"), + id: "SortName" + }, { + name: Globalize.translate("OptionImdbRating"), + id: "CommunityRating,SortName" + }, { + name: Globalize.translate("OptionDateAdded"), + id: "DateCreated,SortName" + }, { + name: Globalize.translate("OptionDatePlayed"), + id: "DatePlayed,SortName" + }, { + name: Globalize.translate("OptionParentalRating"), + id: "OfficialRating,SortName" + }, { + name: Globalize.translate("OptionPlayCount"), + id: "PlayCount,SortName" + }, { + name: Globalize.translate("OptionReleaseDate"), + id: "PremiereDate,SortName" + }], + callback: function() { + getQuery(tabContent).StartIndex = 0, reloadItems() + }, + query: getQuery(tabContent), + button: e.target + }) + }) + }(tabContent), self.renderTab = function() { + reloadItems(), updateFilterControls(tabContent) + }, self.destroy = function() {} + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/musicalbums.js b/dashboard-ui/scripts/musicalbums.js index d190a1e041..b1b09be4a8 100644 --- a/dashboard-ui/scripts/musicalbums.js +++ b/dashboard-ui/scripts/musicalbums.js @@ -1 +1,182 @@ -define(["layoutManager","playbackManager","loading","events","libraryBrowser","imageLoader","alphaPicker","listView","cardBuilder","apphost","emby-itemscontainer"],function(layoutManager,playbackManager,loading,events,libraryBrowser,imageLoader,alphaPicker,listView,cardBuilder,appHost){"use strict";return function(view,params,tabContent){function playAll(){ApiClient.getItem(ApiClient.getCurrentUserId(),params.topParentId).then(function(item){playbackManager.play({items:[item]})})}function shuffle(){ApiClient.getItem(ApiClient.getCurrentUserId(),params.topParentId).then(function(item){getQuery();playbackManager.shuffle(item,null)})}function getPageData(){var key=getSavedQueryKey();return pageData||(pageData={query:{SortBy:"SortName",SortOrder:"Ascending",IncludeItemTypes:"MusicAlbum",Recursive:!0,Fields:"PrimaryImageAspectRatio,SortName,BasicSyncInfo",ImageTypeLimit:1,EnableImageTypes:"Primary,Backdrop,Banner,Thumb",StartIndex:0,Limit:pageSize},view:libraryBrowser.getSavedView(key)||"Poster"},pageData.query.ParentId=params.topParentId,libraryBrowser.loadSavedQueryValues(key,pageData.query)),pageData}function getQuery(){return getPageData().query}function getSavedQueryKey(){return savedQueryKey||(savedQueryKey=libraryBrowser.getSavedQueryKey("musicalbums")),savedQueryKey}function onViewStyleChange(){var viewStyle=self.getCurrentViewStyle(),itemsContainer=tabContent.querySelector(".itemsContainer");"List"==viewStyle?(itemsContainer.classList.add("vertical-list"),itemsContainer.classList.remove("vertical-wrap")):(itemsContainer.classList.remove("vertical-list"),itemsContainer.classList.add("vertical-wrap")),itemsContainer.innerHTML=""}function reloadItems(page){loading.show();var query=getQuery();ApiClient.getItems(ApiClient.getCurrentUserId(),query).then(function(result){function onNextPageClick(){query.StartIndex+=query.Limit,reloadItems(tabContent)}function onPreviousPageClick(){query.StartIndex-=query.Limit,reloadItems(tabContent)}window.scrollTo(0,0),updateFilterControls(page);var html,pagingHtml=libraryBrowser.getQueryPagingHtml({startIndex:query.StartIndex,limit:query.Limit,totalRecordCount:result.TotalRecordCount,showLimit:!1,updatePageSizeSetting:!1,addLayoutButton:!1,sortButton:!1,filterButton:!1}),viewStyle=self.getCurrentViewStyle();html="List"==viewStyle?listView.getListViewHtml({items:result.Items,context:"music",sortBy:query.SortBy,addToListButton:!0}):"PosterCard"==viewStyle?cardBuilder.getCardsHtml({items:result.Items,shape:"square",context:"music",showTitle:!0,coverImage:!0,showParentTitle:!0,lazy:!0,cardLayout:!0}):cardBuilder.getCardsHtml({items:result.Items,shape:"square",context:"music",showTitle:!0,showParentTitle:!0,lazy:!0,centerText:!0,overlayPlayButton:!0});var i,length,elems=tabContent.querySelectorAll(".paging");for(i=0,length=elems.length;i=1920?9:screenWidth>=1200?12:screenWidth>=1e3?10:8}function enableScrollX(){return!layoutManager.desktop}function getSquareShape(){return enableScrollX()?"overflowSquare":"square"}function loadLatest(page,parentId){loading.show();var userId=ApiClient.getCurrentUserId(),options={IncludeItemTypes:"Audio",Limit:enableScrollX()?3*itemsPerRow():2*itemsPerRow(),Fields:"PrimaryImageAspectRatio,BasicSyncInfo",ParentId:parentId,ImageTypeLimit:1,EnableImageTypes:"Primary,Backdrop,Banner,Thumb",EnableTotalRecordCount:!1};ApiClient.getJSON(ApiClient.getUrl("Users/"+userId+"/Items/Latest",options)).then(function(items){var elem=page.querySelector("#recentlyAddedSongs"),supportsImageAnalysis=appHost.supports("imageanalysis");supportsImageAnalysis=!1,elem.innerHTML=cardBuilder.getCardsHtml({items:items,showUnplayedIndicator:!1,showLatestItemsPopup:!1,shape:getSquareShape(),showTitle:!0,showParentTitle:!0,lazy:!0,centerText:!supportsImageAnalysis,overlayPlayButton:!supportsImageAnalysis,allowBottomPadding:!enableScrollX(),cardLayout:supportsImageAnalysis,vibrant:supportsImageAnalysis,coverImage:!0}),imageLoader.lazyChildren(elem),loading.hide()})}function loadRecentlyPlayed(page,parentId){var options={SortBy:"DatePlayed",SortOrder:"Descending",IncludeItemTypes:"Audio",Limit:itemsPerRow(),Recursive:!0,Fields:"PrimaryImageAspectRatio,AudioInfo",Filters:"IsPlayed",ParentId:parentId,ImageTypeLimit:1,EnableImageTypes:"Primary,Backdrop,Banner,Thumb",EnableTotalRecordCount:!1};ApiClient.getItems(ApiClient.getCurrentUserId(),options).then(function(result){var elem=page.querySelector("#recentlyPlayed");result.Items.length?elem.classList.remove("hide"):elem.classList.add("hide");var itemsContainer=elem.querySelector(".itemsContainer"),supportsImageAnalysis=appHost.supports("imageanalysis");supportsImageAnalysis=!1,itemsContainer.innerHTML=cardBuilder.getCardsHtml({items:result.Items,showUnplayedIndicator:!1,shape:getSquareShape(),showTitle:!0,showParentTitle:!0,action:"instantmix",lazy:!0,centerText:!supportsImageAnalysis,overlayMoreButton:!supportsImageAnalysis,allowBottomPadding:!enableScrollX(),cardLayout:supportsImageAnalysis,vibrant:supportsImageAnalysis,coverImage:!0}),imageLoader.lazyChildren(itemsContainer)})}function loadFrequentlyPlayed(page,parentId){var options={SortBy:"PlayCount",SortOrder:"Descending",IncludeItemTypes:"Audio",Limit:itemsPerRow(),Recursive:!0,Fields:"PrimaryImageAspectRatio,AudioInfo",Filters:"IsPlayed",ParentId:parentId,ImageTypeLimit:1,EnableImageTypes:"Primary,Backdrop,Banner,Thumb",EnableTotalRecordCount:!1};ApiClient.getItems(ApiClient.getCurrentUserId(),options).then(function(result){var elem=page.querySelector("#topPlayed");result.Items.length?elem.classList.remove("hide"):elem.classList.add("hide");var itemsContainer=elem.querySelector(".itemsContainer"),supportsImageAnalysis=appHost.supports("imageanalysis");supportsImageAnalysis=!1,itemsContainer.innerHTML=cardBuilder.getCardsHtml({items:result.Items,showUnplayedIndicator:!1,shape:getSquareShape(),showTitle:!0,showParentTitle:!0,action:"instantmix",lazy:!0,centerText:!supportsImageAnalysis,overlayMoreButton:!supportsImageAnalysis,allowBottomPadding:!enableScrollX(),cardLayout:supportsImageAnalysis,vibrant:supportsImageAnalysis,coverImage:!0}),imageLoader.lazyChildren(itemsContainer)})}function loadSuggestionsTab(page,tabContent,parentId){console.log("loadSuggestionsTab"),loadLatest(tabContent,parentId),loadRecentlyPlayed(tabContent,parentId),loadFrequentlyPlayed(tabContent,parentId),require(["components/favoriteitems"],function(favoriteItems){favoriteItems.render(tabContent,ApiClient.getCurrentUserId(),parentId,["favoriteArtists","favoriteAlbums","favoriteSongs"])})}function getTabs(){return[{name:Globalize.translate("TabSuggestions")},{name:Globalize.translate("TabAlbums")},{name:Globalize.translate("TabAlbumArtists")},{name:Globalize.translate("TabArtists")},{name:Globalize.translate("TabPlaylists")},{name:Globalize.translate("TabSongs")},{name:Globalize.translate("TabGenres")},{name:Globalize.translate("ButtonSearch"),cssClass:"searchTabButton"}]}function getDefaultTabIndex(folderId){switch(userSettings.get("landing-"+folderId)){case"albums":return 1;case"albumartists":return 2;case"artists":return 3;case"playlists":return 4;case"songs":return 5;case"genres":return 6;default:return 0}}return function(view,params){function reload(){loading.show();var tabContent=view.querySelector(".pageTabContent[data-index='0']");loadSuggestionsTab(view,tabContent,params.topParentId)}function enableScrollX(){return browser.mobile}function setScrollClasses(elem,scrollX){scrollX?(elem.classList.add("hiddenScrollX"),layoutManager.tv&&elem.classList.add("smoothScrollX"),elem.classList.add("scrollX"),elem.classList.remove("vertical-wrap")):(elem.classList.remove("hiddenScrollX"),elem.classList.remove("smoothScrollX"),elem.classList.remove("scrollX"),elem.classList.add("vertical-wrap"))}function onBeforeTabChange(e){preLoadTab(view,parseInt(e.detail.selectedTabIndex))}function onTabChange(e){loadTab(view,parseInt(e.detail.selectedTabIndex))}function getTabContainers(){return view.querySelectorAll(".pageTabContent")}function initTabs(){mainTabsManager.setTabs(view,currentTabIndex,getTabs,getTabContainers,onBeforeTabChange,onTabChange)}function getTabController(page,index,callback){var depends=[];switch(index){case 0:break;case 1:depends.push("scripts/musicalbums");break;case 2:case 3:depends.push("scripts/musicartists");break;case 4:depends.push("scripts/musicplaylists");break;case 5:depends.push("scripts/songs");break;case 6:depends.push("scripts/musicgenres");break;case 7:depends.push("scripts/searchtab")}require(depends,function(controllerFactory){var tabContent;0==index&&(tabContent=view.querySelector(".pageTabContent[data-index='"+index+"']"),self.tabContent=tabContent);var controller=tabControllers[index];controller||(tabContent=view.querySelector(".pageTabContent[data-index='"+index+"']"),controller=0===index?self:7===index?new controllerFactory(view,tabContent,{collectionType:"music",parentId:params.topParentId}):new controllerFactory(view,params,tabContent),2==index?controller.mode="albumartists":3==index&&(controller.mode="artists"),tabControllers[index]=controller,controller.initTab&&controller.initTab()),callback(controller)})}function preLoadTab(page,index){getTabController(page,index,function(controller){-1==renderedTabs.indexOf(index)&&controller.preRender&&controller.preRender()})}function loadTab(page,index){currentTabIndex=index,getTabController(page,index,function(controller){initialTabIndex=null,-1==renderedTabs.indexOf(index)&&(renderedTabs.push(index),controller.renderTab())})}function onInputCommand(e){switch(e.detail.command){case"search":e.preventDefault(),Dashboard.navigate("search.html?collectionType=music&parentId="+params.topParentId)}}var isViewRestored,self=this,currentTabIndex=parseInt(params.tab||getDefaultTabIndex(params.topParentId)),initialTabIndex=currentTabIndex;self.initTab=function(){for(var tabContent=view.querySelector(".pageTabContent[data-index='0']"),containers=tabContent.querySelectorAll(".itemsContainer"),i=0,length=containers.length;i= 1920 ? 9 : screenWidth >= 1200 ? 12 : screenWidth >= 1e3 ? 10 : 8 + } + + function enableScrollX() { + return !layoutManager.desktop + } + + function getSquareShape() { + return enableScrollX() ? "overflowSquare" : "square" + } + + function loadLatest(page, parentId) { + loading.show(); + var userId = ApiClient.getCurrentUserId(), + options = { + IncludeItemTypes: "Audio", + Limit: enableScrollX() ? 3 * itemsPerRow() : 2 * itemsPerRow(), + Fields: "PrimaryImageAspectRatio,BasicSyncInfo", + ParentId: parentId, + ImageTypeLimit: 1, + EnableImageTypes: "Primary,Backdrop,Banner,Thumb", + EnableTotalRecordCount: !1 + }; + ApiClient.getJSON(ApiClient.getUrl("Users/" + userId + "/Items/Latest", options)).then(function(items) { + var elem = page.querySelector("#recentlyAddedSongs"), + supportsImageAnalysis = appHost.supports("imageanalysis"); + supportsImageAnalysis = !1, elem.innerHTML = cardBuilder.getCardsHtml({ + items: items, + showUnplayedIndicator: !1, + showLatestItemsPopup: !1, + shape: getSquareShape(), + showTitle: !0, + showParentTitle: !0, + lazy: !0, + centerText: !supportsImageAnalysis, + overlayPlayButton: !supportsImageAnalysis, + allowBottomPadding: !enableScrollX(), + cardLayout: supportsImageAnalysis, + vibrant: supportsImageAnalysis, + coverImage: !0 + }), imageLoader.lazyChildren(elem), loading.hide() + }) + } + + function loadRecentlyPlayed(page, parentId) { + var options = { + SortBy: "DatePlayed", + SortOrder: "Descending", + IncludeItemTypes: "Audio", + Limit: itemsPerRow(), + Recursive: !0, + Fields: "PrimaryImageAspectRatio,AudioInfo", + Filters: "IsPlayed", + ParentId: parentId, + ImageTypeLimit: 1, + EnableImageTypes: "Primary,Backdrop,Banner,Thumb", + EnableTotalRecordCount: !1 + }; + ApiClient.getItems(ApiClient.getCurrentUserId(), options).then(function(result) { + var elem = page.querySelector("#recentlyPlayed"); + result.Items.length ? elem.classList.remove("hide") : elem.classList.add("hide"); + var itemsContainer = elem.querySelector(".itemsContainer"), + supportsImageAnalysis = appHost.supports("imageanalysis"); + supportsImageAnalysis = !1, itemsContainer.innerHTML = cardBuilder.getCardsHtml({ + items: result.Items, + showUnplayedIndicator: !1, + shape: getSquareShape(), + showTitle: !0, + showParentTitle: !0, + action: "instantmix", + lazy: !0, + centerText: !supportsImageAnalysis, + overlayMoreButton: !supportsImageAnalysis, + allowBottomPadding: !enableScrollX(), + cardLayout: supportsImageAnalysis, + vibrant: supportsImageAnalysis, + coverImage: !0 + }), imageLoader.lazyChildren(itemsContainer) + }) + } + + function loadFrequentlyPlayed(page, parentId) { + var options = { + SortBy: "PlayCount", + SortOrder: "Descending", + IncludeItemTypes: "Audio", + Limit: itemsPerRow(), + Recursive: !0, + Fields: "PrimaryImageAspectRatio,AudioInfo", + Filters: "IsPlayed", + ParentId: parentId, + ImageTypeLimit: 1, + EnableImageTypes: "Primary,Backdrop,Banner,Thumb", + EnableTotalRecordCount: !1 + }; + ApiClient.getItems(ApiClient.getCurrentUserId(), options).then(function(result) { + var elem = page.querySelector("#topPlayed"); + result.Items.length ? elem.classList.remove("hide") : elem.classList.add("hide"); + var itemsContainer = elem.querySelector(".itemsContainer"), + supportsImageAnalysis = appHost.supports("imageanalysis"); + supportsImageAnalysis = !1, itemsContainer.innerHTML = cardBuilder.getCardsHtml({ + items: result.Items, + showUnplayedIndicator: !1, + shape: getSquareShape(), + showTitle: !0, + showParentTitle: !0, + action: "instantmix", + lazy: !0, + centerText: !supportsImageAnalysis, + overlayMoreButton: !supportsImageAnalysis, + allowBottomPadding: !enableScrollX(), + cardLayout: supportsImageAnalysis, + vibrant: supportsImageAnalysis, + coverImage: !0 + }), imageLoader.lazyChildren(itemsContainer) + }) + } + + function loadSuggestionsTab(page, tabContent, parentId) { + console.log("loadSuggestionsTab"), loadLatest(tabContent, parentId), loadRecentlyPlayed(tabContent, parentId), loadFrequentlyPlayed(tabContent, parentId), require(["components/favoriteitems"], function(favoriteItems) { + favoriteItems.render(tabContent, ApiClient.getCurrentUserId(), parentId, ["favoriteArtists", "favoriteAlbums", "favoriteSongs"]) + }) + } + + function getTabs() { + return [{ + name: Globalize.translate("TabSuggestions") + }, { + name: Globalize.translate("TabAlbums") + }, { + name: Globalize.translate("TabAlbumArtists") + }, { + name: Globalize.translate("TabArtists") + }, { + name: Globalize.translate("TabPlaylists") + }, { + name: Globalize.translate("TabSongs") + }, { + name: Globalize.translate("TabGenres") + }, { + name: Globalize.translate("ButtonSearch"), + cssClass: "searchTabButton" + }] + } + + function getDefaultTabIndex(folderId) { + switch (userSettings.get("landing-" + folderId)) { + case "albums": + return 1; + case "albumartists": + return 2; + case "artists": + return 3; + case "playlists": + return 4; + case "songs": + return 5; + case "genres": + return 6; + default: + return 0 + } + } + return function(view, params) { + function reload() { + loading.show(); + var tabContent = view.querySelector(".pageTabContent[data-index='0']"); + loadSuggestionsTab(view, tabContent, params.topParentId) + } + + function enableScrollX() { + return browser.mobile + } + + function setScrollClasses(elem, scrollX) { + scrollX ? (elem.classList.add("hiddenScrollX"), layoutManager.tv && elem.classList.add("smoothScrollX"), elem.classList.add("scrollX"), elem.classList.remove("vertical-wrap")) : (elem.classList.remove("hiddenScrollX"), elem.classList.remove("smoothScrollX"), elem.classList.remove("scrollX"), elem.classList.add("vertical-wrap")) + } + + function onBeforeTabChange(e) { + preLoadTab(view, parseInt(e.detail.selectedTabIndex)) + } + + function onTabChange(e) { + loadTab(view, parseInt(e.detail.selectedTabIndex)) + } + + function getTabContainers() { + return view.querySelectorAll(".pageTabContent") + } + + function initTabs() { + mainTabsManager.setTabs(view, currentTabIndex, getTabs, getTabContainers, onBeforeTabChange, onTabChange) + } + + function getTabController(page, index, callback) { + var depends = []; + switch (index) { + case 0: + break; + case 1: + depends.push("scripts/musicalbums"); + break; + case 2: + case 3: + depends.push("scripts/musicartists"); + break; + case 4: + depends.push("scripts/musicplaylists"); + break; + case 5: + depends.push("scripts/songs"); + break; + case 6: + depends.push("scripts/musicgenres"); + break; + case 7: + depends.push("scripts/searchtab") + } + require(depends, function(controllerFactory) { + var tabContent; + 0 == index && (tabContent = view.querySelector(".pageTabContent[data-index='" + index + "']"), self.tabContent = tabContent); + var controller = tabControllers[index]; + controller || (tabContent = view.querySelector(".pageTabContent[data-index='" + index + "']"), controller = 0 === index ? self : 7 === index ? new controllerFactory(view, tabContent, { + collectionType: "music", + parentId: params.topParentId + }) : new controllerFactory(view, params, tabContent), 2 == index ? controller.mode = "albumartists" : 3 == index && (controller.mode = "artists"), tabControllers[index] = controller, controller.initTab && controller.initTab()), callback(controller) + }) + } + + function preLoadTab(page, index) { + getTabController(page, index, function(controller) { + -1 == renderedTabs.indexOf(index) && controller.preRender && controller.preRender() + }) + } + + function loadTab(page, index) { + currentTabIndex = index, getTabController(page, index, function(controller) { + initialTabIndex = null, -1 == renderedTabs.indexOf(index) && (renderedTabs.push(index), controller.renderTab()) + }) + } + + function onInputCommand(e) { + switch (e.detail.command) { + case "search": + e.preventDefault(), Dashboard.navigate("search.html?collectionType=music&parentId=" + params.topParentId) + } + } + var isViewRestored, self = this, + currentTabIndex = parseInt(params.tab || getDefaultTabIndex(params.topParentId)), + initialTabIndex = currentTabIndex; + self.initTab = function() { + for (var tabContent = view.querySelector(".pageTabContent[data-index='0']"), containers = tabContent.querySelectorAll(".itemsContainer"), i = 0, length = containers.length; i < length; i++) setScrollClasses(containers[i], enableScrollX()) + }, self.renderTab = function() { + reload() + }; + var tabControllers = [], + renderedTabs = []; + view.addEventListener("viewshow", function(e) { + if (isViewRestored = e.detail.isRestored, initTabs(), !view.getAttribute("data-title")) { + var parentId = params.topParentId; + parentId ? ApiClient.getItem(ApiClient.getCurrentUserId(), parentId).then(function(item) { + view.setAttribute("data-title", item.Name), libraryMenu.setTitle(item.Name) + }) : (view.setAttribute("data-title", Globalize.translate("TabMusic")), libraryMenu.setTitle(Globalize.translate("TabMusic"))) + } + inputManager.on(window, onInputCommand) + }), view.addEventListener("viewbeforehide", function(e) { + inputManager.off(window, onInputCommand) + }), view.addEventListener("viewdestroy", function(e) { + tabControllers.forEach(function(t) { + t.destroy && t.destroy() + }) + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/mypreferencescommon.js b/dashboard-ui/scripts/mypreferencescommon.js index d84e11fbd9..c530787aa8 100644 --- a/dashboard-ui/scripts/mypreferencescommon.js +++ b/dashboard-ui/scripts/mypreferencescommon.js @@ -1 +1,16 @@ -define(["apphost","connectionManager","listViewStyle","emby-linkbutton"],function(appHost,connectionManager){"use strict";return function(view,params){view.querySelector(".btnLogout").addEventListener("click",function(){Dashboard.logout()}),view.addEventListener("viewshow",function(){var page=this,userId=params.userId||Dashboard.getCurrentUserId();page.querySelector(".lnkDisplayPreferences").setAttribute("href","mypreferencesdisplay.html?userId="+userId),page.querySelector(".lnkLanguagePreferences").setAttribute("href","mypreferenceslanguages.html?userId="+userId),page.querySelector(".lnkSubtitleSettings").setAttribute("href","mypreferencessubtitles.html?userId="+userId),page.querySelector(".lnkHomeScreenPreferences").setAttribute("href","mypreferenceshome.html?userId="+userId),page.querySelector(".lnkMyProfile").setAttribute("href","myprofile.html?userId="+userId),page.querySelector(".lnkSync").setAttribute("href","mysyncsettings.html?userId="+userId),page.querySelector(".lnkCameraUpload").setAttribute("href","camerauploadsettings.html?userId="+userId),appHost.supports("cameraupload")?page.querySelector(".lnkCameraUpload").classList.remove("hide"):page.querySelector(".lnkCameraUpload").classList.add("hide"),appHost.supports("sync")?page.querySelector(".lnkSync").classList.remove("hide"):page.querySelector(".lnkSync").classList.add("hide"),connectionManager.user(ApiClient).then(function(user){!user.localUser||user.localUser.EnableAutoLogin&&!user.connectUser?view.querySelector(".btnLogout").classList.add("hide"):view.querySelector(".btnLogout").classList.remove("hide")}),Dashboard.getCurrentUser().then(function(user){page.querySelector(".headerUser").innerHTML=user.Name,user.Policy.IsAdministrator?page.querySelector(".adminSection").classList.remove("hide"):page.querySelector(".adminSection").classList.add("hide")}),appHost.supports("multiserver")?page.querySelector(".selectServer").classList.remove("hide"):page.querySelector(".selectServer").classList.add("hide")})}}); \ No newline at end of file +define(["apphost", "connectionManager", "listViewStyle", "emby-linkbutton"], function(appHost, connectionManager) { + "use strict"; + return function(view, params) { + view.querySelector(".btnLogout").addEventListener("click", function() { + Dashboard.logout() + }), view.addEventListener("viewshow", function() { + var page = this, + userId = params.userId || Dashboard.getCurrentUserId(); + page.querySelector(".lnkDisplayPreferences").setAttribute("href", "mypreferencesdisplay.html?userId=" + userId), page.querySelector(".lnkLanguagePreferences").setAttribute("href", "mypreferenceslanguages.html?userId=" + userId), page.querySelector(".lnkSubtitleSettings").setAttribute("href", "mypreferencessubtitles.html?userId=" + userId), page.querySelector(".lnkHomeScreenPreferences").setAttribute("href", "mypreferenceshome.html?userId=" + userId), page.querySelector(".lnkMyProfile").setAttribute("href", "myprofile.html?userId=" + userId), page.querySelector(".lnkSync").setAttribute("href", "mysyncsettings.html?userId=" + userId), page.querySelector(".lnkCameraUpload").setAttribute("href", "camerauploadsettings.html?userId=" + userId), appHost.supports("cameraupload") ? page.querySelector(".lnkCameraUpload").classList.remove("hide") : page.querySelector(".lnkCameraUpload").classList.add("hide"), appHost.supports("sync") ? page.querySelector(".lnkSync").classList.remove("hide") : page.querySelector(".lnkSync").classList.add("hide"), connectionManager.user(ApiClient).then(function(user) { + !user.localUser || user.localUser.EnableAutoLogin && !user.connectUser ? view.querySelector(".btnLogout").classList.add("hide") : view.querySelector(".btnLogout").classList.remove("hide") + }), Dashboard.getCurrentUser().then(function(user) { + page.querySelector(".headerUser").innerHTML = user.Name, user.Policy.IsAdministrator ? page.querySelector(".adminSection").classList.remove("hide") : page.querySelector(".adminSection").classList.add("hide") + }), appHost.supports("multiserver") ? page.querySelector(".selectServer").classList.remove("hide") : page.querySelector(".selectServer").classList.add("hide") + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/mypreferencesdisplay.js b/dashboard-ui/scripts/mypreferencesdisplay.js index 299fc2d8ec..4b4440f96a 100644 --- a/dashboard-ui/scripts/mypreferencesdisplay.js +++ b/dashboard-ui/scripts/mypreferencesdisplay.js @@ -1 +1,28 @@ -define(["displaySettings","userSettingsBuilder","userSettings"],function(DisplaySettings,userSettingsBuilder,currentUserSettings){"use strict";return function(view,params){function onBeforeUnload(e){hasChanges&&(e.returnValue="You currently have unsaved changes. Are you sure you wish to leave?")}var settingsInstance,hasChanges,userId=params.userId||ApiClient.getCurrentUserId(),userSettings=userId===ApiClient.getCurrentUserId()?currentUserSettings:new userSettingsBuilder;view.addEventListener("viewshow",function(){window.addEventListener("beforeunload",onBeforeUnload),settingsInstance?settingsInstance.loadData():settingsInstance=new DisplaySettings({serverId:ApiClient.serverId(),userId:userId,element:view.querySelector(".settingsContainer"),userSettings:userSettings,enableSaveButton:!1,enableSaveConfirmation:!1})}),view.addEventListener("change",function(){hasChanges=!0}),view.addEventListener("viewbeforehide",function(){window.removeEventListener("beforeunload",onBeforeUnload),hasChanges=!1,settingsInstance&&settingsInstance.submit()}),view.addEventListener("viewdestroy",function(){settingsInstance&&(settingsInstance.destroy(),settingsInstance=null)}),view.addEventListener("viewdestroy",function(){settingsInstance&&(settingsInstance.destroy(),settingsInstance=null)})}}); \ No newline at end of file +define(["displaySettings", "userSettingsBuilder", "userSettings"], function(DisplaySettings, userSettingsBuilder, currentUserSettings) { + "use strict"; + return function(view, params) { + function onBeforeUnload(e) { + hasChanges && (e.returnValue = "You currently have unsaved changes. Are you sure you wish to leave?") + } + var settingsInstance, hasChanges, userId = params.userId || ApiClient.getCurrentUserId(), + userSettings = userId === ApiClient.getCurrentUserId() ? currentUserSettings : new userSettingsBuilder; + view.addEventListener("viewshow", function() { + window.addEventListener("beforeunload", onBeforeUnload), settingsInstance ? settingsInstance.loadData() : settingsInstance = new DisplaySettings({ + serverId: ApiClient.serverId(), + userId: userId, + element: view.querySelector(".settingsContainer"), + userSettings: userSettings, + enableSaveButton: !1, + enableSaveConfirmation: !1 + }) + }), view.addEventListener("change", function() { + hasChanges = !0 + }), view.addEventListener("viewbeforehide", function() { + window.removeEventListener("beforeunload", onBeforeUnload), hasChanges = !1, settingsInstance && settingsInstance.submit() + }), view.addEventListener("viewdestroy", function() { + settingsInstance && (settingsInstance.destroy(), settingsInstance = null) + }), view.addEventListener("viewdestroy", function() { + settingsInstance && (settingsInstance.destroy(), settingsInstance = null) + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/mypreferenceshome.js b/dashboard-ui/scripts/mypreferenceshome.js index bf53cf1633..a7147ddda3 100644 --- a/dashboard-ui/scripts/mypreferenceshome.js +++ b/dashboard-ui/scripts/mypreferenceshome.js @@ -1 +1,26 @@ -define(["homescreenSettings","userSettingsBuilder","dom","globalize","loading","userSettings","listViewStyle"],function(HomescreenSettings,userSettingsBuilder,dom,globalize,loading,currentUserSettings){"use strict";return function(view,params){function onBeforeUnload(e){hasChanges&&(e.returnValue="You currently have unsaved changes. Are you sure you wish to leave?")}var homescreenSettingsInstance,hasChanges,userId=params.userId||ApiClient.getCurrentUserId(),userSettings=userId===ApiClient.getCurrentUserId()?currentUserSettings:new userSettingsBuilder;view.addEventListener("viewshow",function(){window.addEventListener("beforeunload",onBeforeUnload),homescreenSettingsInstance?homescreenSettingsInstance.loadData():homescreenSettingsInstance=new HomescreenSettings({serverId:ApiClient.serverId(),userId:userId,element:view.querySelector(".homeScreenSettingsContainer"),userSettings:userSettings,enableSaveButton:!1,enableSaveConfirmation:!1})}),view.addEventListener("change",function(){hasChanges=!0}),view.addEventListener("viewbeforehide",function(){hasChanges=!1,homescreenSettingsInstance&&homescreenSettingsInstance.submit()}),view.addEventListener("viewdestroy",function(){homescreenSettingsInstance&&(homescreenSettingsInstance.destroy(),homescreenSettingsInstance=null)})}}); \ No newline at end of file +define(["homescreenSettings", "userSettingsBuilder", "dom", "globalize", "loading", "userSettings", "listViewStyle"], function(HomescreenSettings, userSettingsBuilder, dom, globalize, loading, currentUserSettings) { + "use strict"; + return function(view, params) { + function onBeforeUnload(e) { + hasChanges && (e.returnValue = "You currently have unsaved changes. Are you sure you wish to leave?") + } + var homescreenSettingsInstance, hasChanges, userId = params.userId || ApiClient.getCurrentUserId(), + userSettings = userId === ApiClient.getCurrentUserId() ? currentUserSettings : new userSettingsBuilder; + view.addEventListener("viewshow", function() { + window.addEventListener("beforeunload", onBeforeUnload), homescreenSettingsInstance ? homescreenSettingsInstance.loadData() : homescreenSettingsInstance = new HomescreenSettings({ + serverId: ApiClient.serverId(), + userId: userId, + element: view.querySelector(".homeScreenSettingsContainer"), + userSettings: userSettings, + enableSaveButton: !1, + enableSaveConfirmation: !1 + }) + }), view.addEventListener("change", function() { + hasChanges = !0 + }), view.addEventListener("viewbeforehide", function() { + hasChanges = !1, homescreenSettingsInstance && homescreenSettingsInstance.submit() + }), view.addEventListener("viewdestroy", function() { + homescreenSettingsInstance && (homescreenSettingsInstance.destroy(), homescreenSettingsInstance = null) + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/mypreferenceslanguages.js b/dashboard-ui/scripts/mypreferenceslanguages.js index 285185e013..856470948a 100644 --- a/dashboard-ui/scripts/mypreferenceslanguages.js +++ b/dashboard-ui/scripts/mypreferenceslanguages.js @@ -1 +1,26 @@ -define(["playbackSettings","userSettingsBuilder","dom","globalize","loading","userSettings","listViewStyle"],function(PlaybackSettings,userSettingsBuilder,dom,globalize,loading,currentUserSettings){"use strict";return function(view,params){function onBeforeUnload(e){hasChanges&&(e.returnValue="You currently have unsaved changes. Are you sure you wish to leave?")}var settingsInstance,hasChanges,userId=params.userId||ApiClient.getCurrentUserId(),userSettings=userId===ApiClient.getCurrentUserId()?currentUserSettings:new userSettingsBuilder;view.addEventListener("viewshow",function(){window.addEventListener("beforeunload",onBeforeUnload),settingsInstance?settingsInstance.loadData():settingsInstance=new PlaybackSettings({serverId:ApiClient.serverId(),userId:userId,element:view.querySelector(".settingsContainer"),userSettings:userSettings,enableSaveButton:!1,enableSaveConfirmation:!1})}),view.addEventListener("change",function(){hasChanges=!0}),view.addEventListener("viewbeforehide",function(){hasChanges=!1,settingsInstance&&settingsInstance.submit()}),view.addEventListener("viewdestroy",function(){settingsInstance&&(settingsInstance.destroy(),settingsInstance=null)})}}); \ No newline at end of file +define(["playbackSettings", "userSettingsBuilder", "dom", "globalize", "loading", "userSettings", "listViewStyle"], function(PlaybackSettings, userSettingsBuilder, dom, globalize, loading, currentUserSettings) { + "use strict"; + return function(view, params) { + function onBeforeUnload(e) { + hasChanges && (e.returnValue = "You currently have unsaved changes. Are you sure you wish to leave?") + } + var settingsInstance, hasChanges, userId = params.userId || ApiClient.getCurrentUserId(), + userSettings = userId === ApiClient.getCurrentUserId() ? currentUserSettings : new userSettingsBuilder; + view.addEventListener("viewshow", function() { + window.addEventListener("beforeunload", onBeforeUnload), settingsInstance ? settingsInstance.loadData() : settingsInstance = new PlaybackSettings({ + serverId: ApiClient.serverId(), + userId: userId, + element: view.querySelector(".settingsContainer"), + userSettings: userSettings, + enableSaveButton: !1, + enableSaveConfirmation: !1 + }) + }), view.addEventListener("change", function() { + hasChanges = !0 + }), view.addEventListener("viewbeforehide", function() { + hasChanges = !1, settingsInstance && settingsInstance.submit() + }), view.addEventListener("viewdestroy", function() { + settingsInstance && (settingsInstance.destroy(), settingsInstance = null) + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/mypreferencessubtitles.js b/dashboard-ui/scripts/mypreferencessubtitles.js index 686faca1c3..81d949e1a9 100644 --- a/dashboard-ui/scripts/mypreferencessubtitles.js +++ b/dashboard-ui/scripts/mypreferencessubtitles.js @@ -1 +1,26 @@ -define(["subtitleSettings","userSettingsBuilder","userSettings"],function(SubtitleSettings,userSettingsBuilder,currentUserSettings){"use strict";return function(view,params){function onBeforeUnload(e){hasChanges&&(e.returnValue="You currently have unsaved changes. Are you sure you wish to leave?")}var subtitleSettingsInstance,hasChanges,userId=params.userId||ApiClient.getCurrentUserId(),userSettings=userId===ApiClient.getCurrentUserId()?currentUserSettings:new userSettingsBuilder;view.addEventListener("viewshow",function(){window.addEventListener("beforeunload",onBeforeUnload),subtitleSettingsInstance?subtitleSettingsInstance.loadData():subtitleSettingsInstance=new SubtitleSettings({serverId:ApiClient.serverId(),userId:userId,element:view.querySelector(".settingsContainer"),userSettings:userSettings,enableSaveButton:!1,enableSaveConfirmation:!1})}),view.addEventListener("change",function(){hasChanges=!0}),view.addEventListener("viewbeforehide",function(){hasChanges=!1,subtitleSettingsInstance&&subtitleSettingsInstance.submit()}),view.addEventListener("viewdestroy",function(){subtitleSettingsInstance&&(subtitleSettingsInstance.destroy(),subtitleSettingsInstance=null)})}}); \ No newline at end of file +define(["subtitleSettings", "userSettingsBuilder", "userSettings"], function(SubtitleSettings, userSettingsBuilder, currentUserSettings) { + "use strict"; + return function(view, params) { + function onBeforeUnload(e) { + hasChanges && (e.returnValue = "You currently have unsaved changes. Are you sure you wish to leave?") + } + var subtitleSettingsInstance, hasChanges, userId = params.userId || ApiClient.getCurrentUserId(), + userSettings = userId === ApiClient.getCurrentUserId() ? currentUserSettings : new userSettingsBuilder; + view.addEventListener("viewshow", function() { + window.addEventListener("beforeunload", onBeforeUnload), subtitleSettingsInstance ? subtitleSettingsInstance.loadData() : subtitleSettingsInstance = new SubtitleSettings({ + serverId: ApiClient.serverId(), + userId: userId, + element: view.querySelector(".settingsContainer"), + userSettings: userSettings, + enableSaveButton: !1, + enableSaveConfirmation: !1 + }) + }), view.addEventListener("change", function() { + hasChanges = !0 + }), view.addEventListener("viewbeforehide", function() { + hasChanges = !1, subtitleSettingsInstance && subtitleSettingsInstance.submit() + }), view.addEventListener("viewdestroy", function() { + subtitleSettingsInstance && (subtitleSettingsInstance.destroy(), subtitleSettingsInstance = null) + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/myprofile.js b/dashboard-ui/scripts/myprofile.js index 2ef9c49ac4..f6c0760c53 100644 --- a/dashboard-ui/scripts/myprofile.js +++ b/dashboard-ui/scripts/myprofile.js @@ -1 +1,95 @@ -define(["scripts/userpasswordpage","loading","libraryMenu","apphost","emby-linkbutton"],function(Userpasswordpage,loading,libraryMenu,appHost){"use strict";function reloadUser(page){var userId=getParameterByName("userId");loading.show(),ApiClient.getUser(userId).then(function(user){page.querySelector(".username").innerHTML=user.Name;var uploadUserImage=page.querySelector("#uploadUserImage");uploadUserImage.value="",uploadUserImage.dispatchEvent(new CustomEvent("change",{})),libraryMenu.setTitle(user.Name);var imageUrl,fldImage=page.querySelector("#fldImage");imageUrl=user.PrimaryImageTag?ApiClient.getUserImageUrl(user.Id,{height:200,tag:user.PrimaryImageTag,type:"Primary"}):"css/images/logindefault.png",fldImage.classList.remove("hide"),fldImage.innerHTML="";var showImageEditing=!1;"Guest"==user.ConnectLinkType?page.querySelector(".connectMessage").classList.remove("hide"):(user.PrimaryImageTag,showImageEditing=!0,page.querySelector(".connectMessage").classList.add("hide")),Dashboard.getCurrentUser().then(function(loggedInUser){showImageEditing&&appHost.supports("fileinput")&&(loggedInUser.Policy.IsAdministrator||user.Policy.EnableUserPreferenceAccess)?(page.querySelector(".newImageForm").classList.remove("hide"),user.PrimaryImageTag?page.querySelector("#btnDeleteImage").classList.remove("hide"):page.querySelector("#btnDeleteImage").classList.add("hide")):(page.querySelector(".newImageForm").classList.add("hide"),page.querySelector("#btnDeleteImage").classList.add("hide"))}),loading.hide()})}function onFileReaderError(evt){switch(loading.hide(),evt.target.error.code){case evt.target.error.NOT_FOUND_ERR:require(["toast"],function(toast){toast(Globalize.translate("FileNotFound"))});break;case evt.target.error.NOT_READABLE_ERR:require(["toast"],function(toast){toast(Globalize.translate("FileReadError"))});break;case evt.target.error.ABORT_ERR:break;default:require(["toast"],function(toast){toast(Globalize.translate("FileReadError"))})}}function onFileReaderAbort(evt){loading.hide(),require(["toast"],function(toast){toast(Globalize.translate("FileReadCancelled"))})}function setFiles(page,files){var file=files[0];if(!file||!file.type.match("image.*"))return page.querySelector("#userImageOutput").innerHTML="",page.querySelector("#fldUpload").classList.add("hide"),void(currentFile=null);currentFile=file;var reader=new FileReader;reader.onerror=onFileReaderError,reader.onloadstart=function(){page.querySelector("#fldUpload").classList.add("hide")},reader.onabort=onFileReaderAbort,reader.onload=function(e){var html=[''].join("");page.querySelector("#userImageOutput").innerHTML=html,page.querySelector("#fldUpload").classList.remove("hide")},reader.readAsDataURL(file)}function onImageDragOver(e){return e.preventDefault(),e.originalEvent.dataTransfer.dropEffect="Copy",!1}var currentFile;return function(view,params){reloadUser(view);new Userpasswordpage(view,params);view.querySelector("#userImageDropZone").addEventListener("dragOver",onImageDragOver),view.querySelector("#btnDeleteImage").addEventListener("click",function(){require(["confirm"],function(confirm){confirm(Globalize.translate("DeleteImageConfirmation"),Globalize.translate("DeleteImage")).then(function(){loading.show();var userId=getParameterByName("userId");ApiClient.deleteUserImage(userId,"primary").then(function(){loading.hide(),reloadUser(view)})})})}),view.querySelector(".btnBrowse").addEventListener("click",function(){view.querySelector("#uploadUserImage").click()}),view.querySelector(".newImageForm").addEventListener("submit",function(e){var file=currentFile;if(!file)return!1;if("image/png"!=file.type&&"image/jpeg"!=file.type&&"image/jpeg"!=file.type)return!1;loading.show();var userId=getParameterByName("userId");return ApiClient.uploadUserImage(userId,"Primary",file).then(function(){loading.hide(),reloadUser(view)}),e.preventDefault(),!1}),view.querySelector("#uploadUserImage").addEventListener("change",function(e){setFiles(view,e.target.files)})}}); \ No newline at end of file +define(["scripts/userpasswordpage", "loading", "libraryMenu", "apphost", "emby-linkbutton"], function(Userpasswordpage, loading, libraryMenu, appHost) { + "use strict"; + + function reloadUser(page) { + var userId = getParameterByName("userId"); + loading.show(), ApiClient.getUser(userId).then(function(user) { + page.querySelector(".username").innerHTML = user.Name; + var uploadUserImage = page.querySelector("#uploadUserImage"); + uploadUserImage.value = "", uploadUserImage.dispatchEvent(new CustomEvent("change", {})), libraryMenu.setTitle(user.Name); + var imageUrl, fldImage = page.querySelector("#fldImage"); + imageUrl = user.PrimaryImageTag ? ApiClient.getUserImageUrl(user.Id, { + height: 200, + tag: user.PrimaryImageTag, + type: "Primary" + }) : "css/images/logindefault.png", fldImage.classList.remove("hide"), fldImage.innerHTML = ""; + var showImageEditing = !1; + "Guest" == user.ConnectLinkType ? page.querySelector(".connectMessage").classList.remove("hide") : (user.PrimaryImageTag, showImageEditing = !0, page.querySelector(".connectMessage").classList.add("hide")), Dashboard.getCurrentUser().then(function(loggedInUser) { + showImageEditing && appHost.supports("fileinput") && (loggedInUser.Policy.IsAdministrator || user.Policy.EnableUserPreferenceAccess) ? (page.querySelector(".newImageForm").classList.remove("hide"), user.PrimaryImageTag ? page.querySelector("#btnDeleteImage").classList.remove("hide") : page.querySelector("#btnDeleteImage").classList.add("hide")) : (page.querySelector(".newImageForm").classList.add("hide"), page.querySelector("#btnDeleteImage").classList.add("hide")) + }), loading.hide() + }) + } + + function onFileReaderError(evt) { + switch (loading.hide(), evt.target.error.code) { + case evt.target.error.NOT_FOUND_ERR: + require(["toast"], function(toast) { + toast(Globalize.translate("FileNotFound")) + }); + break; + case evt.target.error.NOT_READABLE_ERR: + require(["toast"], function(toast) { + toast(Globalize.translate("FileReadError")) + }); + break; + case evt.target.error.ABORT_ERR: + break; + default: + require(["toast"], function(toast) { + toast(Globalize.translate("FileReadError")) + }) + } + } + + function onFileReaderAbort(evt) { + loading.hide(), require(["toast"], function(toast) { + toast(Globalize.translate("FileReadCancelled")) + }) + } + + function setFiles(page, files) { + var file = files[0]; + if (!file || !file.type.match("image.*")) return page.querySelector("#userImageOutput").innerHTML = "", page.querySelector("#fldUpload").classList.add("hide"), void(currentFile = null); + currentFile = file; + var reader = new FileReader; + reader.onerror = onFileReaderError, reader.onloadstart = function() { + page.querySelector("#fldUpload").classList.add("hide") + }, reader.onabort = onFileReaderAbort, reader.onload = function(e) { + var html = [''].join(""); + page.querySelector("#userImageOutput").innerHTML = html, page.querySelector("#fldUpload").classList.remove("hide") + }, reader.readAsDataURL(file) + } + + function onImageDragOver(e) { + return e.preventDefault(), e.originalEvent.dataTransfer.dropEffect = "Copy", !1 + } + var currentFile; + return function(view, params) { + reloadUser(view); + new Userpasswordpage(view, params); + view.querySelector("#userImageDropZone").addEventListener("dragOver", onImageDragOver), view.querySelector("#btnDeleteImage").addEventListener("click", function() { + require(["confirm"], function(confirm) { + confirm(Globalize.translate("DeleteImageConfirmation"), Globalize.translate("DeleteImage")).then(function() { + loading.show(); + var userId = getParameterByName("userId"); + ApiClient.deleteUserImage(userId, "primary").then(function() { + loading.hide(), reloadUser(view) + }) + }) + }) + }), view.querySelector(".btnBrowse").addEventListener("click", function() { + view.querySelector("#uploadUserImage").click() + }), view.querySelector(".newImageForm").addEventListener("submit", function(e) { + var file = currentFile; + if (!file) return !1; + if ("image/png" != file.type && "image/jpeg" != file.type && "image/jpeg" != file.type) return !1; + loading.show(); + var userId = getParameterByName("userId"); + return ApiClient.uploadUserImage(userId, "Primary", file).then(function() { + loading.hide(), reloadUser(view) + }), e.preventDefault(), !1 + }), view.querySelector("#uploadUserImage").addEventListener("change", function(e) { + setFiles(view, e.target.files) + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/mysync.js b/dashboard-ui/scripts/mysync.js index 5f0b1ceaa7..d971a870b4 100644 --- a/dashboard-ui/scripts/mysync.js +++ b/dashboard-ui/scripts/mysync.js @@ -1 +1,18 @@ -define(["apphost","globalize","syncJobList","events","localsync","emby-button","paper-icon-button-light"],function(appHost,globalize,syncJobList,events,localSync){"use strict";return function(view,params){var interval,mySyncJobList=new syncJobList({mode:params.mode,enableRemoteSyncManagement:!1,serverId:ApiClient.serverId(),userId:"offline"===params.mode?null:ApiClient.getCurrentUserId(),element:view.querySelector(".syncActivity"),mode:params.mode});view.addEventListener("viewbeforehide",function(){interval&&(clearInterval(interval),interval=null)}),view.addEventListener("viewdestroy",function(){mySyncJobList.destroy()})}}); \ No newline at end of file +define(["apphost", "globalize", "syncJobList", "events", "localsync", "emby-button", "paper-icon-button-light"], function(appHost, globalize, syncJobList, events, localSync) { + "use strict"; + return function(view, params) { + var interval, mySyncJobList = new syncJobList({ + mode: params.mode, + enableRemoteSyncManagement: !1, + serverId: ApiClient.serverId(), + userId: "offline" === params.mode ? null : ApiClient.getCurrentUserId(), + element: view.querySelector(".syncActivity"), + mode: params.mode + }); + view.addEventListener("viewbeforehide", function() { + interval && (clearInterval(interval), interval = null) + }), view.addEventListener("viewdestroy", function() { + mySyncJobList.destroy() + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/mysyncsettings.js b/dashboard-ui/scripts/mysyncsettings.js index 0a1f640d0c..c968acb2a1 100644 --- a/dashboard-ui/scripts/mysyncsettings.js +++ b/dashboard-ui/scripts/mysyncsettings.js @@ -1 +1,33 @@ -define(["appSettings","apphost","emby-checkbox","emby-select","emby-input"],function(appSettings,appHost){"use strict";function loadForm(page,user){page.querySelector("#txtSyncPath").value=appSettings.syncPath()||"",page.querySelector("#chkWifi").checked=appSettings.syncOnlyOnWifi(),page.querySelector(".selectAudioBitrate").value=appSettings.maxStaticMusicBitrate()||""}function saveUser(page){var syncPath=page.querySelector("#txtSyncPath").value;appSettings.syncPath(syncPath),appSettings.syncOnlyOnWifi(page.querySelector("#chkWifi").checked),appSettings.maxStaticMusicBitrate(page.querySelector(".selectAudioBitrate").value||null),require(["localsync"],function(localSync){localSync.sync()})}return function(view,params){view.querySelector("form").addEventListener("submit",function(e){return saveUser(view),e.preventDefault(),!1}),view.querySelector("#btnSelectSyncPath").addEventListener("click",function(){require(["nativedirectorychooser"],function(){NativeDirectoryChooser.chooseDirectory().then(function(path){path&&(view.querySelector("#txtSyncPath").value=path)})})}),view.addEventListener("viewshow",function(){var page=this,userId=getParameterByName("userId")||Dashboard.getCurrentUserId();ApiClient.getUser(userId).then(function(user){loadForm(page,user)}),appHost.supports("customsyncpath")?page.querySelector(".fldSyncPath").classList.remove("hide"):page.querySelector(".fldSyncPath").classList.add("hide")}),view.addEventListener("viewbeforehide",function(){saveUser(this)})}}); \ No newline at end of file +define(["appSettings", "apphost", "emby-checkbox", "emby-select", "emby-input"], function(appSettings, appHost) { + "use strict"; + + function loadForm(page, user) { + page.querySelector("#txtSyncPath").value = appSettings.syncPath() || "", page.querySelector("#chkWifi").checked = appSettings.syncOnlyOnWifi(), page.querySelector(".selectAudioBitrate").value = appSettings.maxStaticMusicBitrate() || "" + } + + function saveUser(page) { + var syncPath = page.querySelector("#txtSyncPath").value; + appSettings.syncPath(syncPath), appSettings.syncOnlyOnWifi(page.querySelector("#chkWifi").checked), appSettings.maxStaticMusicBitrate(page.querySelector(".selectAudioBitrate").value || null), require(["localsync"], function(localSync) { + localSync.sync() + }) + } + return function(view, params) { + view.querySelector("form").addEventListener("submit", function(e) { + return saveUser(view), e.preventDefault(), !1 + }), view.querySelector("#btnSelectSyncPath").addEventListener("click", function() { + require(["nativedirectorychooser"], function() { + NativeDirectoryChooser.chooseDirectory().then(function(path) { + path && (view.querySelector("#txtSyncPath").value = path) + }) + }) + }), view.addEventListener("viewshow", function() { + var page = this, + userId = getParameterByName("userId") || Dashboard.getCurrentUserId(); + ApiClient.getUser(userId).then(function(user) { + loadForm(page, user) + }), appHost.supports("customsyncpath") ? page.querySelector(".fldSyncPath").classList.remove("hide") : page.querySelector(".fldSyncPath").classList.add("hide") + }), view.addEventListener("viewbeforehide", function() { + saveUser(this) + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/notificationsetting.js b/dashboard-ui/scripts/notificationsetting.js index 3262572212..a9333ba5a3 100644 --- a/dashboard-ui/scripts/notificationsetting.js +++ b/dashboard-ui/scripts/notificationsetting.js @@ -1 +1,85 @@ -define(["jQuery","emby-checkbox","fnchecked"],function($){"use strict";function fillItems(elem,items,cssClass,idPrefix,currentList,isEnabledList){var html='
    ';html+=items.map(function(u){var isChecked=isEnabledList?-1!=currentList.indexOf(u.Id):-1==currentList.indexOf(u.Id),checkedHtml=isChecked?' checked="checked"':"";return'"}).join(""),html+="
    ",elem.html(html).trigger("create")}function reload(page){var type=getParameterByName("type"),promise1=ApiClient.getUsers(),promise2=ApiClient.getNamedConfiguration(notificationsConfigurationKey),promise3=ApiClient.getJSON(ApiClient.getUrl("Notifications/Types")),promise4=ApiClient.getJSON(ApiClient.getUrl("Notifications/Services"));Promise.all([promise1,promise2,promise3,promise4]).then(function(responses){var users=responses[0],notificationOptions=responses[1],types=responses[2],services=responses[3],notificationConfig=notificationOptions.Options.filter(function(n){return n.Type==type})[0],typeInfo=types.filter(function(n){return n.Type==type})[0]||{};typeInfo.IsBasedOnUserEvent?$(".monitorUsers",page).show():$(".monitorUsers",page).hide(),$(".notificationType",page).html(typeInfo.Name||"Unknown Notification"),notificationConfig||(notificationConfig={DisabledMonitorUsers:[],SendToUsers:[],DisabledServices:[],SendToUserMode:"Admins"}),fillItems($(".monitorUsersList",page),users,"chkMonitor","chkMonitor",notificationConfig.DisabledMonitorUsers),fillItems($(".sendToUsersList",page),users,"chkSendTo","chkSendTo",notificationConfig.SendToUsers,!0),fillItems($(".servicesList",page),services,"chkService","chkService",notificationConfig.DisabledServices),$("#chkEnabled",page).checked(notificationConfig.Enabled||!1),$("#selectUsers",page).val(notificationConfig.SendToUserMode).trigger("change")})}function save(page){var type=getParameterByName("type"),promise1=ApiClient.getNamedConfiguration(notificationsConfigurationKey),promise2=ApiClient.getJSON(ApiClient.getUrl("Notifications/Types"));Promise.all([promise1,promise2]).then(function(responses){var notificationOptions=responses[0],types=responses[1],notificationConfig=notificationOptions.Options.filter(function(n){return n.Type==type})[0];notificationConfig||(notificationConfig={Type:type},notificationOptions.Options.push(notificationConfig));types.filter(function(n){return n.Type==type})[0];notificationConfig.Enabled=$("#chkEnabled",page).checked(),notificationConfig.SendToUserMode=$("#selectUsers",page).val(),notificationConfig.DisabledMonitorUsers=$(".chkMonitor",page).get().filter(function(c){return!c.checked}).map(function(c){return c.getAttribute("data-itemid")}),notificationConfig.SendToUsers=$(".chkSendTo",page).get().filter(function(c){return c.checked}).map(function(c){return c.getAttribute("data-itemid")}),notificationConfig.DisabledServices=$(".chkService",page).get().filter(function(c){return!c.checked}).map(function(c){return c.getAttribute("data-itemid")}),ApiClient.updateNamedConfiguration(notificationsConfigurationKey,notificationOptions).then(function(r){Dashboard.processServerConfigurationUpdateResult(),Dashboard.navigate("notificationsettings.html")})})}function onSubmit(){return save($(this).parents(".page")),!1}var notificationsConfigurationKey="notifications";$(document).on("pageinit","#notificationSettingPage",function(){var page=this;$("#selectUsers",page).on("change",function(){"Custom"==this.value?$(".selectCustomUsers",page).show():$(".selectCustomUsers",page).hide()}),$(".notificationSettingForm").off("submit",onSubmit).on("submit",onSubmit)}).on("pageshow","#notificationSettingPage",function(){reload(this)})}); \ No newline at end of file +define(["jQuery", "emby-checkbox", "fnchecked"], function($) { + "use strict"; + + function fillItems(elem, items, cssClass, idPrefix, currentList, isEnabledList) { + var html = '
    '; + html += items.map(function(u) { + var isChecked = isEnabledList ? -1 != currentList.indexOf(u.Id) : -1 == currentList.indexOf(u.Id), + checkedHtml = isChecked ? ' checked="checked"' : ""; + return '" + }).join(""), html += "
    ", elem.html(html).trigger("create") + } + + function reload(page) { + var type = getParameterByName("type"), + promise1 = ApiClient.getUsers(), + promise2 = ApiClient.getNamedConfiguration(notificationsConfigurationKey), + promise3 = ApiClient.getJSON(ApiClient.getUrl("Notifications/Types")), + promise4 = ApiClient.getJSON(ApiClient.getUrl("Notifications/Services")); + Promise.all([promise1, promise2, promise3, promise4]).then(function(responses) { + var users = responses[0], + notificationOptions = responses[1], + types = responses[2], + services = responses[3], + notificationConfig = notificationOptions.Options.filter(function(n) { + return n.Type == type + })[0], + typeInfo = types.filter(function(n) { + return n.Type == type + })[0] || {}; + typeInfo.IsBasedOnUserEvent ? $(".monitorUsers", page).show() : $(".monitorUsers", page).hide(), $(".notificationType", page).html(typeInfo.Name || "Unknown Notification"), notificationConfig || (notificationConfig = { + DisabledMonitorUsers: [], + SendToUsers: [], + DisabledServices: [], + SendToUserMode: "Admins" + }), fillItems($(".monitorUsersList", page), users, "chkMonitor", "chkMonitor", notificationConfig.DisabledMonitorUsers), fillItems($(".sendToUsersList", page), users, "chkSendTo", "chkSendTo", notificationConfig.SendToUsers, !0), fillItems($(".servicesList", page), services, "chkService", "chkService", notificationConfig.DisabledServices), $("#chkEnabled", page).checked(notificationConfig.Enabled || !1), $("#selectUsers", page).val(notificationConfig.SendToUserMode).trigger("change") + }) + } + + function save(page) { + var type = getParameterByName("type"), + promise1 = ApiClient.getNamedConfiguration(notificationsConfigurationKey), + promise2 = ApiClient.getJSON(ApiClient.getUrl("Notifications/Types")); + Promise.all([promise1, promise2]).then(function(responses) { + var notificationOptions = responses[0], + types = responses[1], + notificationConfig = notificationOptions.Options.filter(function(n) { + return n.Type == type + })[0]; + notificationConfig || (notificationConfig = { + Type: type + }, notificationOptions.Options.push(notificationConfig)); + types.filter(function(n) { + return n.Type == type + })[0]; + notificationConfig.Enabled = $("#chkEnabled", page).checked(), notificationConfig.SendToUserMode = $("#selectUsers", page).val(), notificationConfig.DisabledMonitorUsers = $(".chkMonitor", page).get().filter(function(c) { + return !c.checked + }).map(function(c) { + return c.getAttribute("data-itemid") + }), notificationConfig.SendToUsers = $(".chkSendTo", page).get().filter(function(c) { + return c.checked + }).map(function(c) { + return c.getAttribute("data-itemid") + }), notificationConfig.DisabledServices = $(".chkService", page).get().filter(function(c) { + return !c.checked + }).map(function(c) { + return c.getAttribute("data-itemid") + }), ApiClient.updateNamedConfiguration(notificationsConfigurationKey, notificationOptions).then(function(r) { + Dashboard.processServerConfigurationUpdateResult(), Dashboard.navigate("notificationsettings.html") + }) + }) + } + + function onSubmit() { + return save($(this).parents(".page")), !1 + } + var notificationsConfigurationKey = "notifications"; + $(document).on("pageinit", "#notificationSettingPage", function() { + var page = this; + $("#selectUsers", page).on("change", function() { + "Custom" == this.value ? $(".selectCustomUsers", page).show() : $(".selectCustomUsers", page).hide() + }), $(".notificationSettingForm").off("submit", onSubmit).on("submit", onSubmit) + }).on("pageshow", "#notificationSettingPage", function() { + reload(this) + }) +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/notificationsettings.js b/dashboard-ui/scripts/notificationsettings.js index d00c95d132..ed73752c32 100644 --- a/dashboard-ui/scripts/notificationsettings.js +++ b/dashboard-ui/scripts/notificationsettings.js @@ -1 +1,30 @@ -define(["loading","libraryMenu","globalize","listViewStyle","emby-linkbutton"],function(loading,libraryMenu,globalize){"use strict";function reload(page){loading.show(),ApiClient.getJSON(ApiClient.getUrl("Notifications/Types")).then(function(list){var html="",lastCategory="",showHelp=!0;html+=list.map(function(i){var itemHtml="";return i.Category!=lastCategory&&(lastCategory=i.Category,lastCategory&&(itemHtml+="
    ",itemHtml+="
    "),itemHtml+='
    ',itemHtml+='
    ',itemHtml+='

    ',itemHtml+=i.Category,itemHtml+="

    ",showHelp&&(showHelp=!1,itemHtml+=''+globalize.translate("Help")+""),itemHtml+="
    ",itemHtml+='",html+="
    "),page.querySelector(".notificationList").innerHTML=html,loading.hide()})}function getTabs(){return[{href:"notificationsettings.html",name:globalize.translate("TabNotifications")},{href:"appservices.html?context=notifications",name:globalize.translate("TabServices")}]}return function(view,params){view.addEventListener("viewshow",function(){libraryMenu.setTabs("notifications",0,getTabs),reload(view)})}}); \ No newline at end of file +define(["loading", "libraryMenu", "globalize", "listViewStyle", "emby-linkbutton"], function(loading, libraryMenu, globalize) { + "use strict"; + + function reload(page) { + loading.show(), ApiClient.getJSON(ApiClient.getUrl("Notifications/Types")).then(function(list) { + var html = "", + lastCategory = "", + showHelp = !0; + html += list.map(function(i) { + var itemHtml = ""; + return i.Category != lastCategory && (lastCategory = i.Category, lastCategory && (itemHtml += "
    ", itemHtml += "
    "), itemHtml += '
    ', itemHtml += '
    ', itemHtml += '

    ', itemHtml += i.Category, itemHtml += "

    ", showHelp && (showHelp = !1, itemHtml += '' + globalize.translate("Help") + ""), itemHtml += "
    ", itemHtml += '", html += "
    "), page.querySelector(".notificationList").innerHTML = html, loading.hide() + }) + } + + function getTabs() { + return [{ + href: "notificationsettings.html", + name: globalize.translate("TabNotifications") + }, { + href: "appservices.html?context=notifications", + name: globalize.translate("TabServices") + }] + } + return function(view, params) { + view.addEventListener("viewshow", function() { + libraryMenu.setTabs("notifications", 0, getTabs), reload(view) + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/nowplayingpage.js b/dashboard-ui/scripts/nowplayingpage.js index 2865d32147..77eb7c221c 100644 --- a/dashboard-ui/scripts/nowplayingpage.js +++ b/dashboard-ui/scripts/nowplayingpage.js @@ -1 +1,11 @@ -define(["components/remotecontrol","libraryMenu","emby-button"],function(remotecontrolFactory,libraryMenu){"use strict";return function(view,params){var remoteControl=new remotecontrolFactory;remoteControl.init(view,view.querySelector(".remoteControlContent")),view.addEventListener("viewshow",function(e){libraryMenu.setTransparentMenu(!0),remoteControl&&remoteControl.onShow()}),view.addEventListener("viewbeforehide",function(e){libraryMenu.setTransparentMenu(!1),remoteControl&&remoteControl.destroy()})}}); \ No newline at end of file +define(["components/remotecontrol", "libraryMenu", "emby-button"], function(remotecontrolFactory, libraryMenu) { + "use strict"; + return function(view, params) { + var remoteControl = new remotecontrolFactory; + remoteControl.init(view, view.querySelector(".remoteControlContent")), view.addEventListener("viewshow", function(e) { + libraryMenu.setTransparentMenu(!0), remoteControl && remoteControl.onShow() + }), view.addEventListener("viewbeforehide", function(e) { + libraryMenu.setTransparentMenu(!1), remoteControl && remoteControl.destroy() + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/playbackconfiguration.js b/dashboard-ui/scripts/playbackconfiguration.js index 2bce55f60d..64b1870183 100644 --- a/dashboard-ui/scripts/playbackconfiguration.js +++ b/dashboard-ui/scripts/playbackconfiguration.js @@ -1 +1,34 @@ -define(["jQuery","loading","libraryMenu"],function($,loading,libraryMenu){"use strict";function loadPage(page,config){$("#txtMinResumePct",page).val(config.MinResumePct),$("#txtMaxResumePct",page).val(config.MaxResumePct),$("#txtMinResumeDuration",page).val(config.MinResumeDurationSeconds),loading.hide()}function onSubmit(){loading.show();var form=this;return ApiClient.getServerConfiguration().then(function(config){config.MinResumePct=$("#txtMinResumePct",form).val(),config.MaxResumePct=$("#txtMaxResumePct",form).val(),config.MinResumeDurationSeconds=$("#txtMinResumeDuration",form).val(),ApiClient.updateServerConfiguration(config).then(Dashboard.processServerConfigurationUpdateResult)}),!1}function getTabs(){return[{href:"playbackconfiguration.html",name:Globalize.translate("TabResumeSettings")},{href:"streamingsettings.html",name:Globalize.translate("TabStreaming")}]}$(document).on("pageinit","#playbackConfigurationPage",function(){$(".playbackConfigurationForm").off("submit",onSubmit).on("submit",onSubmit)}).on("pageshow","#playbackConfigurationPage",function(){libraryMenu.setTabs("playback",0,getTabs),loading.show();var page=this;ApiClient.getServerConfiguration().then(function(config){loadPage(page,config)})})}); \ No newline at end of file +define(["jQuery", "loading", "libraryMenu"], function($, loading, libraryMenu) { + "use strict"; + + function loadPage(page, config) { + $("#txtMinResumePct", page).val(config.MinResumePct), $("#txtMaxResumePct", page).val(config.MaxResumePct), $("#txtMinResumeDuration", page).val(config.MinResumeDurationSeconds), loading.hide() + } + + function onSubmit() { + loading.show(); + var form = this; + return ApiClient.getServerConfiguration().then(function(config) { + config.MinResumePct = $("#txtMinResumePct", form).val(), config.MaxResumePct = $("#txtMaxResumePct", form).val(), config.MinResumeDurationSeconds = $("#txtMinResumeDuration", form).val(), ApiClient.updateServerConfiguration(config).then(Dashboard.processServerConfigurationUpdateResult) + }), !1 + } + + function getTabs() { + return [{ + href: "playbackconfiguration.html", + name: Globalize.translate("TabResumeSettings") + }, { + href: "streamingsettings.html", + name: Globalize.translate("TabStreaming") + }] + } + $(document).on("pageinit", "#playbackConfigurationPage", function() { + $(".playbackConfigurationForm").off("submit", onSubmit).on("submit", onSubmit) + }).on("pageshow", "#playbackConfigurationPage", function() { + libraryMenu.setTabs("playback", 0, getTabs), loading.show(); + var page = this; + ApiClient.getServerConfiguration().then(function(config) { + loadPage(page, config) + }) + }) +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/playlistedit.js b/dashboard-ui/scripts/playlistedit.js index 04976fcf1e..ef0615e2ba 100644 --- a/dashboard-ui/scripts/playlistedit.js +++ b/dashboard-ui/scripts/playlistedit.js @@ -1 +1,39 @@ -define(["listView"],function(listView){"use strict";function getFetchPlaylistItemsFn(itemId){return function(){var query={Fields:"PrimaryImageAspectRatio,UserData",EnableImageTypes:"Primary,Backdrop,Banner,Thumb",UserId:ApiClient.getCurrentUserId()};return ApiClient.getJSON(ApiClient.getUrl("Playlists/"+itemId+"/Items",query))}}function getItemsHtmlFn(itemId){return function(items){return listView.getListViewHtml({items:items,showIndex:!1,showRemoveFromPlaylist:!0,playFromHere:!0,action:"playallfromhere",smallIcon:!0,dragHandle:!0,playlistId:itemId})}}function init(page,item){var elem=page.querySelector("#childrenContent .itemsContainer");elem.classList.add("vertical-list"),elem.classList.remove("vertical-wrap"),elem.enableDragReordering(!0),elem.fetchData=getFetchPlaylistItemsFn(item.Id),elem.getItemsHtml=getItemsHtmlFn(item.Id)}window.PlaylistViewer={render:function(page,item){page.playlistInit||(page.playlistInit=!0,init(page,item)),page.querySelector("#childrenContent").classList.add("verticalSection-extrabottompadding"),page.querySelector("#childrenContent .itemsContainer").refreshItems()}}}); \ No newline at end of file +define(["listView"], function(listView) { + "use strict"; + + function getFetchPlaylistItemsFn(itemId) { + return function() { + var query = { + Fields: "PrimaryImageAspectRatio,UserData", + EnableImageTypes: "Primary,Backdrop,Banner,Thumb", + UserId: ApiClient.getCurrentUserId() + }; + return ApiClient.getJSON(ApiClient.getUrl("Playlists/" + itemId + "/Items", query)) + } + } + + function getItemsHtmlFn(itemId) { + return function(items) { + return listView.getListViewHtml({ + items: items, + showIndex: !1, + showRemoveFromPlaylist: !0, + playFromHere: !0, + action: "playallfromhere", + smallIcon: !0, + dragHandle: !0, + playlistId: itemId + }) + } + } + + function init(page, item) { + var elem = page.querySelector("#childrenContent .itemsContainer"); + elem.classList.add("vertical-list"), elem.classList.remove("vertical-wrap"), elem.enableDragReordering(!0), elem.fetchData = getFetchPlaylistItemsFn(item.Id), elem.getItemsHtml = getItemsHtmlFn(item.Id) + } + window.PlaylistViewer = { + render: function(page, item) { + page.playlistInit || (page.playlistInit = !0, init(page, item)), page.querySelector("#childrenContent").classList.add("verticalSection-extrabottompadding"), page.querySelector("#childrenContent .itemsContainer").refreshItems() + } + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/playlists.js b/dashboard-ui/scripts/playlists.js index f20992209d..bb5ea1fd02 100644 --- a/dashboard-ui/scripts/playlists.js +++ b/dashboard-ui/scripts/playlists.js @@ -1 +1,126 @@ -define(["loading","listView","cardBuilder","libraryMenu","libraryBrowser","apphost","imageLoader","emby-itemscontainer"],function(loading,listView,cardBuilder,libraryMenu,libraryBrowser,appHost,imageLoader){"use strict";return function(view,params){function getPageData(context){var key=getSavedQueryKey(context),pageData=data[key];return pageData||(pageData=data[key]={query:{SortBy:"SortName",SortOrder:"Ascending",IncludeItemTypes:"Playlist",Recursive:!0,Fields:"PrimaryImageAspectRatio,SortName,CumulativeRunTimeTicks,CanDelete",StartIndex:0,Limit:100},view:libraryBrowser.getSavedView(key)||"Poster"},pageData.query.ParentId=libraryMenu.getTopParentId(),libraryBrowser.loadSavedQueryValues(key,pageData.query)),pageData}function getQuery(context){return getPageData(context).query}function getSavedQueryKey(context){return context.savedQueryKey||(context.savedQueryKey=libraryBrowser.getSavedQueryKey()),context.savedQueryKey}function showLoadingMessage(){loading.show()}function hideLoadingMessage(){loading.hide()}function onViewStyleChange(){var viewStyle=getPageData(view).view,itemsContainer=view.querySelector(".itemsContainer");"List"==viewStyle?(itemsContainer.classList.add("vertical-list"),itemsContainer.classList.remove("vertical-wrap")):(itemsContainer.classList.remove("vertical-list"),itemsContainer.classList.add("vertical-wrap")),itemsContainer.innerHTML=""}function reloadItems(){showLoadingMessage();var query=getQuery(view),promise1=ApiClient.getItems(Dashboard.getCurrentUserId(),query),promise2=Dashboard.getCurrentUser();Promise.all([promise1,promise2]).then(function(responses){var result=responses[0];responses[1];window.scrollTo(0,0);var html="",viewStyle=getPageData(view).view;view.querySelector(".listTopPaging").innerHTML=libraryBrowser.getQueryPagingHtml({startIndex:query.StartIndex,limit:query.Limit,totalRecordCount:result.TotalRecordCount,viewButton:!1,showLimit:!1,updatePageSizeSetting:!1,addLayoutButton:!0,layouts:"List,Poster,PosterCard,Thumb,ThumbCard",currentLayout:viewStyle}),result.TotalRecordCount?(html="List"==viewStyle?listView.getListViewHtml({items:result.Items,sortBy:query.SortBy}):"PosterCard"==viewStyle?cardBuilder.getCardsHtml({items:result.Items,shape:"square",coverImage:!0,showTitle:!0,cardLayout:!0,vibrant:!0}):"Thumb"==viewStyle?cardBuilder.getCardsHtml({items:result.Items,shape:"backdrop",showTitle:!0,centerText:!0,preferThumb:!0,overlayPlayButton:!0}):"ThumbCard"==viewStyle?cardBuilder.getCardsHtml({items:result.Items,shape:"backdrop",showTitle:!0,preferThumb:!0,cardLayout:!0,vibrant:!0}):cardBuilder.getCardsHtml({items:result.Items,shape:"square",showTitle:!0,coverImage:!0,centerText:!0,overlayPlayButton:!0}),view.querySelector(".noItemsMessage").classList.add("hide")):view.querySelector(".noItemsMessage").classList.remove("hide");var elem=view.querySelector(".itemsContainer");elem.innerHTML=html,imageLoader.lazyChildren(elem);var btnNextPage=view.querySelector(".btnNextPage");btnNextPage&&btnNextPage.addEventListener("click",function(){query.StartIndex+=query.Limit,reloadItems()});var btnPreviousPage=view.querySelector(".btnPreviousPage");btnPreviousPage&&btnPreviousPage.addEventListener("click",function(){query.StartIndex-=query.Limit,reloadItems()});var btnChangeLayout=view.querySelector(".btnChangeLayout");btnChangeLayout&&btnChangeLayout.addEventListener("layoutchange",function(e){var layout=e.detail.viewStyle;getPageData(view).view=layout,libraryBrowser.saveViewSetting(getSavedQueryKey(view),layout),onViewStyleChange(),reloadItems()}),libraryBrowser.saveQueryValues(getSavedQueryKey(view),query),hideLoadingMessage()})}var data={};view.addEventListener("viewbeforeshow",function(){reloadItems()}),view.querySelector(".btnNewPlaylist").addEventListener("click",function(){require(["playlistEditor"],function(playlistEditor){var serverId=ApiClient.serverInfo().Id;(new playlistEditor).show({items:[],serverId:serverId})})}),onViewStyleChange()}}); \ No newline at end of file +define(["loading", "listView", "cardBuilder", "libraryMenu", "libraryBrowser", "apphost", "imageLoader", "emby-itemscontainer"], function(loading, listView, cardBuilder, libraryMenu, libraryBrowser, appHost, imageLoader) { + "use strict"; + return function(view, params) { + function getPageData(context) { + var key = getSavedQueryKey(context), + pageData = data[key]; + return pageData || (pageData = data[key] = { + query: { + SortBy: "SortName", + SortOrder: "Ascending", + IncludeItemTypes: "Playlist", + Recursive: !0, + Fields: "PrimaryImageAspectRatio,SortName,CumulativeRunTimeTicks,CanDelete", + StartIndex: 0, + Limit: 100 + }, + view: libraryBrowser.getSavedView(key) || "Poster" + }, pageData.query.ParentId = libraryMenu.getTopParentId(), libraryBrowser.loadSavedQueryValues(key, pageData.query)), pageData + } + + function getQuery(context) { + return getPageData(context).query + } + + function getSavedQueryKey(context) { + return context.savedQueryKey || (context.savedQueryKey = libraryBrowser.getSavedQueryKey()), context.savedQueryKey + } + + function showLoadingMessage() { + loading.show() + } + + function hideLoadingMessage() { + loading.hide() + } + + function onViewStyleChange() { + var viewStyle = getPageData(view).view, + itemsContainer = view.querySelector(".itemsContainer"); + "List" == viewStyle ? (itemsContainer.classList.add("vertical-list"), itemsContainer.classList.remove("vertical-wrap")) : (itemsContainer.classList.remove("vertical-list"), itemsContainer.classList.add("vertical-wrap")), itemsContainer.innerHTML = "" + } + + function reloadItems() { + showLoadingMessage(); + var query = getQuery(view), + promise1 = ApiClient.getItems(Dashboard.getCurrentUserId(), query), + promise2 = Dashboard.getCurrentUser(); + Promise.all([promise1, promise2]).then(function(responses) { + var result = responses[0]; + responses[1]; + window.scrollTo(0, 0); + var html = "", + viewStyle = getPageData(view).view; + view.querySelector(".listTopPaging").innerHTML = libraryBrowser.getQueryPagingHtml({ + startIndex: query.StartIndex, + limit: query.Limit, + totalRecordCount: result.TotalRecordCount, + viewButton: !1, + showLimit: !1, + updatePageSizeSetting: !1, + addLayoutButton: !0, + layouts: "List,Poster,PosterCard,Thumb,ThumbCard", + currentLayout: viewStyle + }), result.TotalRecordCount ? (html = "List" == viewStyle ? listView.getListViewHtml({ + items: result.Items, + sortBy: query.SortBy + }) : "PosterCard" == viewStyle ? cardBuilder.getCardsHtml({ + items: result.Items, + shape: "square", + coverImage: !0, + showTitle: !0, + cardLayout: !0, + vibrant: !0 + }) : "Thumb" == viewStyle ? cardBuilder.getCardsHtml({ + items: result.Items, + shape: "backdrop", + showTitle: !0, + centerText: !0, + preferThumb: !0, + overlayPlayButton: !0 + }) : "ThumbCard" == viewStyle ? cardBuilder.getCardsHtml({ + items: result.Items, + shape: "backdrop", + showTitle: !0, + preferThumb: !0, + cardLayout: !0, + vibrant: !0 + }) : cardBuilder.getCardsHtml({ + items: result.Items, + shape: "square", + showTitle: !0, + coverImage: !0, + centerText: !0, + overlayPlayButton: !0 + }), view.querySelector(".noItemsMessage").classList.add("hide")) : view.querySelector(".noItemsMessage").classList.remove("hide"); + var elem = view.querySelector(".itemsContainer"); + elem.innerHTML = html, imageLoader.lazyChildren(elem); + var btnNextPage = view.querySelector(".btnNextPage"); + btnNextPage && btnNextPage.addEventListener("click", function() { + query.StartIndex += query.Limit, reloadItems() + }); + var btnPreviousPage = view.querySelector(".btnPreviousPage"); + btnPreviousPage && btnPreviousPage.addEventListener("click", function() { + query.StartIndex -= query.Limit, reloadItems() + }); + var btnChangeLayout = view.querySelector(".btnChangeLayout"); + btnChangeLayout && btnChangeLayout.addEventListener("layoutchange", function(e) { + var layout = e.detail.viewStyle; + getPageData(view).view = layout, libraryBrowser.saveViewSetting(getSavedQueryKey(view), layout), onViewStyleChange(), reloadItems() + }), libraryBrowser.saveQueryValues(getSavedQueryKey(view), query), hideLoadingMessage() + }) + } + var data = {}; + view.addEventListener("viewbeforeshow", function() { + reloadItems() + }), view.querySelector(".btnNewPlaylist").addEventListener("click", function() { + require(["playlistEditor"], function(playlistEditor) { + var serverId = ApiClient.serverInfo().Id; + (new playlistEditor).show({ + items: [], + serverId: serverId + }) + }) + }), onViewStyleChange() + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/plugincatalogpage.js b/dashboard-ui/scripts/plugincatalogpage.js index 7fbaccd360..cebbbb08f3 100644 --- a/dashboard-ui/scripts/plugincatalogpage.js +++ b/dashboard-ui/scripts/plugincatalogpage.js @@ -1 +1,101 @@ -define(["loading","libraryMenu","globalize","cardStyle","emby-linkbutton","emby-checkbox","emby-select"],function(loading,libraryMenu,globalize){"use strict";function reloadList(page){loading.show(),query.IsAppStoreSafe=!0;var promise1=ApiClient.getAvailablePlugins(query),promise2=ApiClient.getInstalledPlugins();Promise.all([promise1,promise2]).then(function(responses){populateList({catalogElement:page.querySelector("#pluginTiles"),noItemsElement:page.querySelector("#noPlugins"),availablePlugins:responses[0],installedPlugins:responses[1]})})}function populateList(options){populateListInternal(options)}function getHeaderText(category){category.replace(" ","").replace(" ","");return"Channel"===category?category="Channels":"Theme"===category?category="Themes":"LiveTV"===category?category="HeaderLiveTV":"ScreenSaver"===category&&(category="HeaderScreenSavers"),globalize.translate(category)}function isUserInstalledPlugin(plugin){return-1===["02528C96-F727-44D7-BE87-9EEF040758C3","0277E613-3EC0-4360-A3DE-F8AF0AABB5E9","4DCB591C-0FA2-4C5D-A7E5-DABE37164C8B"].indexOf(plugin.guid)}function populateListInternal(options){var availablePlugins=options.availablePlugins,installedPlugins=options.installedPlugins,allPlugins=availablePlugins.filter(function(p){return p.category=p.category||"General",p.categoryDisplayName=getHeaderText(p.category),(!options.categories||-1!=options.categories.indexOf(p.category))&&((!options.targetSystem||p.targetSystem==options.targetSystem)&&"UserInstalled"==p.type)});availablePlugins=allPlugins.sort(function(a,b){var aName=a.category,bName=b.category;return aName>bName?1:bName>aName?-1:(aName=a.name,bName=b.name,aName>bName?1:bName>aName?-1:0)});var i,length,plugin,currentCategory,html="";if(!options.categories){currentCategory=globalize.translate("HeaderTopPlugins"),html+='
    ',html+='

    '+currentCategory+"

    ";var topPlugins=allPlugins.slice(0).sort(function(a,b){if(a.installs>b.installs)return-1;if(b.installs>a.installs)return 1;var aName=a.name,bName=b.name;return aName>bName?1:bName>aName?-1:0}).filter(isUserInstalledPlugin);html+='
    ';var limit=screen.availWidth>=1920?15:12;for(i=0,length=Math.min(topPlugins.length,limit);i",html+="
    "}var hasOpenTag=!1;for(currentCategory=null,!1===options.showCategory&&(html+='
    ',hasOpenTag=!0),i=0,length=availablePlugins.length;i",html+="
    "),html+='
    ',html+='

    '+category+"

    ",html+='
    ',hasOpenTag=!0),currentCategory=category),html+=getPluginHtml(plugin,options,installedPlugins)}hasOpenTag&&(html+="
    ",html+="
    "),!availablePlugins.length&&options.noItemsElement&&options.noItemsElement.classList.add("hide"),options.catalogElement.innerHTML=html,loading.hide()}function getPluginHtml(plugin,options,installedPlugins){var html="",href=plugin.externalUrl?plugin.externalUrl:"addplugin.html?name="+encodeURIComponent(plugin.name)+"&guid="+plugin.guid;options.context&&(href+="&context="+options.context);var target=plugin.externalUrl?' target="_blank"':"";html+="
    ",html+='
    ',html+='",html+='
    ',html+="
    ",html+=plugin.name,html+="
    ";var installedPlugin=plugin.isApp?null:installedPlugins.filter(function(ip){return ip.Id==plugin.guid})[0];return html+="
    ",html+=installedPlugin?globalize.translate("LabelVersionInstalled").replace("{0}",installedPlugin.Version):" ",html+="
    ",html+="
    ",html+="
    ",html+="
    "}function getTabs(){return[{href:"plugins.html",name:globalize.translate("TabMyPlugins")},{href:"plugincatalog.html",name:globalize.translate("TabCatalog")}]}var query={TargetSystems:"Server",IsAdult:!1};return window.PluginCatalog={renderCatalog:populateList},function(view,params){view.querySelector("#selectSystem").addEventListener("change",function(){query.TargetSystems=this.value,reloadList(view)}),view.addEventListener("viewshow",function(){libraryMenu.setTabs("plugins",1,getTabs),reloadList(this)})}}); \ No newline at end of file +define(["loading", "libraryMenu", "globalize", "cardStyle", "emby-linkbutton", "emby-checkbox", "emby-select"], function(loading, libraryMenu, globalize) { + "use strict"; + + function reloadList(page) { + loading.show(), query.IsAppStoreSafe = !0; + var promise1 = ApiClient.getAvailablePlugins(query), + promise2 = ApiClient.getInstalledPlugins(); + Promise.all([promise1, promise2]).then(function(responses) { + populateList({ + catalogElement: page.querySelector("#pluginTiles"), + noItemsElement: page.querySelector("#noPlugins"), + availablePlugins: responses[0], + installedPlugins: responses[1] + }) + }) + } + + function populateList(options) { + populateListInternal(options) + } + + function getHeaderText(category) { + category.replace(" ", "").replace(" ", ""); + return "Channel" === category ? category = "Channels" : "Theme" === category ? category = "Themes" : "LiveTV" === category ? category = "HeaderLiveTV" : "ScreenSaver" === category && (category = "HeaderScreenSavers"), globalize.translate(category) + } + + function isUserInstalledPlugin(plugin) { + return -1 === ["02528C96-F727-44D7-BE87-9EEF040758C3", "0277E613-3EC0-4360-A3DE-F8AF0AABB5E9", "4DCB591C-0FA2-4C5D-A7E5-DABE37164C8B"].indexOf(plugin.guid) + } + + function populateListInternal(options) { + var availablePlugins = options.availablePlugins, + installedPlugins = options.installedPlugins, + allPlugins = availablePlugins.filter(function(p) { + return p.category = p.category || "General", p.categoryDisplayName = getHeaderText(p.category), (!options.categories || -1 != options.categories.indexOf(p.category)) && ((!options.targetSystem || p.targetSystem == options.targetSystem) && "UserInstalled" == p.type) + }); + availablePlugins = allPlugins.sort(function(a, b) { + var aName = a.category, + bName = b.category; + return aName > bName ? 1 : bName > aName ? -1 : (aName = a.name, bName = b.name, aName > bName ? 1 : bName > aName ? -1 : 0) + }); + var i, length, plugin, currentCategory, html = ""; + if (!options.categories) { + currentCategory = globalize.translate("HeaderTopPlugins"), html += '
    ', html += '

    ' + currentCategory + "

    "; + var topPlugins = allPlugins.slice(0).sort(function(a, b) { + if (a.installs > b.installs) return -1; + if (b.installs > a.installs) return 1; + var aName = a.name, + bName = b.name; + return aName > bName ? 1 : bName > aName ? -1 : 0 + }).filter(isUserInstalledPlugin); + html += '
    '; + var limit = screen.availWidth >= 1920 ? 15 : 12; + for (i = 0, length = Math.min(topPlugins.length, limit); i < length; i++) html += getPluginHtml(topPlugins[i], options, installedPlugins); + html += "
    ", html += "
    " + } + var hasOpenTag = !1; + for (currentCategory = null, !1 === options.showCategory && (html += '
    ', hasOpenTag = !0), i = 0, length = availablePlugins.length; i < length; i++) { + plugin = availablePlugins[i]; + var category = plugin.categoryDisplayName; + category != currentCategory && (!1 !== options.showCategory && (currentCategory && (hasOpenTag = !1, html += "
    ", html += "
    "), html += '
    ', html += '

    ' + category + "

    ", html += '
    ', hasOpenTag = !0), currentCategory = category), html += getPluginHtml(plugin, options, installedPlugins) + } + hasOpenTag && (html += "
    ", html += "
    "), !availablePlugins.length && options.noItemsElement && options.noItemsElement.classList.add("hide"), options.catalogElement.innerHTML = html, loading.hide() + } + + function getPluginHtml(plugin, options, installedPlugins) { + var html = "", + href = plugin.externalUrl ? plugin.externalUrl : "addplugin.html?name=" + encodeURIComponent(plugin.name) + "&guid=" + plugin.guid; + options.context && (href += "&context=" + options.context); + var target = plugin.externalUrl ? ' target="_blank"' : ""; + html += "
    ", html += '
    ', html += '", html += '
    ', html += "
    ", html += plugin.name, html += "
    "; + var installedPlugin = plugin.isApp ? null : installedPlugins.filter(function(ip) { + return ip.Id == plugin.guid + })[0]; + return html += "
    ", html += installedPlugin ? globalize.translate("LabelVersionInstalled").replace("{0}", installedPlugin.Version) : " ", html += "
    ", html += "
    ", html += "
    ", html += "
    " + } + + function getTabs() { + return [{ + href: "plugins.html", + name: globalize.translate("TabMyPlugins") + }, { + href: "plugincatalog.html", + name: globalize.translate("TabCatalog") + }] + } + var query = { + TargetSystems: "Server", + IsAdult: !1 + }; + return window.PluginCatalog = { + renderCatalog: populateList + }, + function(view, params) { + view.querySelector("#selectSystem").addEventListener("change", function() { + query.TargetSystems = this.value, reloadList(view) + }), view.addEventListener("viewshow", function() { + libraryMenu.setTabs("plugins", 1, getTabs), reloadList(this) + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/pluginspage.js b/dashboard-ui/scripts/pluginspage.js index fbcb555fb1..69583403e8 100644 --- a/dashboard-ui/scripts/pluginspage.js +++ b/dashboard-ui/scripts/pluginspage.js @@ -1 +1,120 @@ -define(["loading","libraryMenu","dom","globalize","cardStyle","emby-linkbutton"],function(loading,libraryMenu,dom,globalize){"use strict";function deletePlugin(page,uniqueid,name){var msg=globalize.translate("UninstallPluginConfirmation").replace("{0}",name);require(["confirm"],function(confirm){confirm({title:globalize.translate("UninstallPluginHeader"),text:msg,primary:"cancel",confirmText:globalize.translate("UninstallPluginHeader")}).then(function(){loading.show(),ApiClient.uninstallPlugin(uniqueid).then(function(){reloadList(page)})})})}function showNoConfigurationMessage(){Dashboard.alert({message:globalize.translate("NoPluginConfigurationMessage")})}function showConnectMessage(){Dashboard.alert({message:globalize.translate("MessagePluginConfigurationRequiresLocalAccess")})}function getPluginCardHtml(plugin,pluginConfigurationPages){var configPage=pluginConfigurationPages.filter(function(pluginConfigurationPage){return pluginConfigurationPage.PluginId==plugin.Id})[0],html="",disallowPlugins=!Dashboard.allowPluginPages(plugin.Id),configPageUrl=configPage?Dashboard.getConfigurationPageUrl(configPage.Name):null,href=configPage&&!disallowPlugins?configPageUrl:null;return html+="
    ",html+='
    ',html+='
    ',html+='
    ',html+=href?'':configPageUrl?disallowPlugins?'
    ':'",html+='
    ',html+='
    ',html+='',html+="
    ",html+="
    ",html+=configPage?configPage.DisplayName||plugin.Name:plugin.Name,html+="
    ",html+="
    ",html+=plugin.Version,html+="
    ",html+="
    ",html+="
    ",html+="
    "}function renderPlugins(page,plugins,showNoPluginsMessage){ApiClient.getJSON(ApiClient.getUrl("web/configurationpages")+"?pageType=PluginConfiguration").then(function(configPages){populateList(page,plugins,configPages,showNoPluginsMessage)})}function populateList(page,plugins,pluginConfigurationPages,showNoPluginsMessage){plugins=plugins.sort(function(plugin1,plugin2){return plugin1.Name>plugin2.Name?1:-1});var html=plugins.map(function(p){return getPluginCardHtml(p,pluginConfigurationPages)}).join(""),installedPluginsElement=page.querySelector(".installedPlugins");installedPluginsElement.removeEventListener("click",onInstalledPluginsClick),installedPluginsElement.addEventListener("click",onInstalledPluginsClick),plugins.length?(installedPluginsElement.classList.add("itemsContainer"),installedPluginsElement.classList.add("vertical-wrap"),installedPluginsElement.innerHTML=html):(showNoPluginsMessage&&(html+='
    ',html+="

    "+globalize.translate("MessageNoPluginsInstalled")+"

    ",html+='

    ',html+=globalize.translate("BrowsePluginCatalogMessage"),html+="

    ",html+="
    "),installedPluginsElement.innerHTML=html),loading.hide()}function showPluginMenu(page,elem){var card=dom.parentWithClass(elem,"card"),id=card.getAttribute("data-id"),name=card.getAttribute("data-name"),configHref=card.querySelector(".cardContent").getAttribute("href"),menuItems=[];configHref&&menuItems.push({name:globalize.translate("ButtonSettings"),id:"open",ironIcon:"mode-edit"}),menuItems.push({name:globalize.translate("ButtonUninstall"),id:"delete",ironIcon:"delete"}),require(["actionsheet"],function(actionsheet){actionsheet.show({items:menuItems,positionTo:elem,callback:function(resultId){switch(resultId){case"open":Dashboard.navigate(configHref);break;case"delete":deletePlugin(page,id,name)}}})})}function reloadList(page){loading.show(),ApiClient.getInstalledPlugins().then(function(plugins){renderPlugins(page,plugins,!0)})}function getTabs(){return[{href:"plugins.html",name:globalize.translate("TabMyPlugins")},{href:"plugincatalog.html",name:globalize.translate("TabCatalog")}]}function onInstalledPluginsClick(e){if(dom.parentWithClass(e.target,"noConfigPluginCard"))showNoConfigurationMessage();else if(dom.parentWithClass(e.target,"connectModePluginCard"))showConnectMessage();else{var btnCardMenu=dom.parentWithClass(e.target,"btnCardMenu");btnCardMenu&&showPluginMenu(dom.parentWithClass(btnCardMenu,"page"),btnCardMenu)}}pageIdOn("pageshow","pluginsPage",function(){libraryMenu.setTabs("plugins",0,getTabs),reloadList(this)}),window.PluginsPage={renderPlugins:renderPlugins}}); \ No newline at end of file +define(["loading", "libraryMenu", "dom", "globalize", "cardStyle", "emby-linkbutton"], function(loading, libraryMenu, dom, globalize) { + "use strict"; + + function deletePlugin(page, uniqueid, name) { + var msg = globalize.translate("UninstallPluginConfirmation").replace("{0}", name); + require(["confirm"], function(confirm) { + confirm({ + title: globalize.translate("UninstallPluginHeader"), + text: msg, + primary: "cancel", + confirmText: globalize.translate("UninstallPluginHeader") + }).then(function() { + loading.show(), ApiClient.uninstallPlugin(uniqueid).then(function() { + reloadList(page) + }) + }) + }) + } + + function showNoConfigurationMessage() { + Dashboard.alert({ + message: globalize.translate("NoPluginConfigurationMessage") + }) + } + + function showConnectMessage() { + Dashboard.alert({ + message: globalize.translate("MessagePluginConfigurationRequiresLocalAccess") + }) + } + + function getPluginCardHtml(plugin, pluginConfigurationPages) { + var configPage = pluginConfigurationPages.filter(function(pluginConfigurationPage) { + return pluginConfigurationPage.PluginId == plugin.Id + })[0], + html = "", + disallowPlugins = !Dashboard.allowPluginPages(plugin.Id), + configPageUrl = configPage ? Dashboard.getConfigurationPageUrl(configPage.Name) : null, + href = configPage && !disallowPlugins ? configPageUrl : null; + return html += "
    ", html += '
    ', html += '
    ', html += '
    ', html += href ? '' : configPageUrl ? disallowPlugins ? '
    ' : '", html += '
    ', html += '
    ', html += '', html += "
    ", html += "
    ", html += configPage ? configPage.DisplayName || plugin.Name : plugin.Name, html += "
    ", html += "
    ", html += plugin.Version, html += "
    ", html += "
    ", html += "
    ", html += "
    " + } + + function renderPlugins(page, plugins, showNoPluginsMessage) { + ApiClient.getJSON(ApiClient.getUrl("web/configurationpages") + "?pageType=PluginConfiguration").then(function(configPages) { + populateList(page, plugins, configPages, showNoPluginsMessage) + }) + } + + function populateList(page, plugins, pluginConfigurationPages, showNoPluginsMessage) { + plugins = plugins.sort(function(plugin1, plugin2) { + return plugin1.Name > plugin2.Name ? 1 : -1 + }); + var html = plugins.map(function(p) { + return getPluginCardHtml(p, pluginConfigurationPages) + }).join(""), + installedPluginsElement = page.querySelector(".installedPlugins"); + installedPluginsElement.removeEventListener("click", onInstalledPluginsClick), installedPluginsElement.addEventListener("click", onInstalledPluginsClick), plugins.length ? (installedPluginsElement.classList.add("itemsContainer"), installedPluginsElement.classList.add("vertical-wrap"), installedPluginsElement.innerHTML = html) : (showNoPluginsMessage && (html += '
    ', html += "

    " + globalize.translate("MessageNoPluginsInstalled") + "

    ", html += '

    ', html += globalize.translate("BrowsePluginCatalogMessage"), html += "

    ", html += "
    "), installedPluginsElement.innerHTML = html), loading.hide() + } + + function showPluginMenu(page, elem) { + var card = dom.parentWithClass(elem, "card"), + id = card.getAttribute("data-id"), + name = card.getAttribute("data-name"), + configHref = card.querySelector(".cardContent").getAttribute("href"), + menuItems = []; + configHref && menuItems.push({ + name: globalize.translate("ButtonSettings"), + id: "open", + ironIcon: "mode-edit" + }), menuItems.push({ + name: globalize.translate("ButtonUninstall"), + id: "delete", + ironIcon: "delete" + }), require(["actionsheet"], function(actionsheet) { + actionsheet.show({ + items: menuItems, + positionTo: elem, + callback: function(resultId) { + switch (resultId) { + case "open": + Dashboard.navigate(configHref); + break; + case "delete": + deletePlugin(page, id, name) + } + } + }) + }) + } + + function reloadList(page) { + loading.show(), ApiClient.getInstalledPlugins().then(function(plugins) { + renderPlugins(page, plugins, !0) + }) + } + + function getTabs() { + return [{ + href: "plugins.html", + name: globalize.translate("TabMyPlugins") + }, { + href: "plugincatalog.html", + name: globalize.translate("TabCatalog") + }] + } + + function onInstalledPluginsClick(e) { + if (dom.parentWithClass(e.target, "noConfigPluginCard")) showNoConfigurationMessage(); + else if (dom.parentWithClass(e.target, "connectModePluginCard")) showConnectMessage(); + else { + var btnCardMenu = dom.parentWithClass(e.target, "btnCardMenu"); + btnCardMenu && showPluginMenu(dom.parentWithClass(btnCardMenu, "page"), btnCardMenu) + } + } + pageIdOn("pageshow", "pluginsPage", function() { + libraryMenu.setTabs("plugins", 0, getTabs), reloadList(this) + }), window.PluginsPage = { + renderPlugins: renderPlugins + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/scheduledtaskpage.js b/dashboard-ui/scripts/scheduledtaskpage.js index 8de47c4bf8..32838c6de3 100644 --- a/dashboard-ui/scripts/scheduledtaskpage.js +++ b/dashboard-ui/scripts/scheduledtaskpage.js @@ -1 +1,111 @@ -define(["jQuery","loading","datetime","dom","globalize","emby-input","emby-button","emby-select"],function($,loading,datetime,dom,globalize){"use strict";function fillTimeOfDay(select){for(var options=[],i=0;i<864e5;i+=9e5)options.push({name:ScheduledTaskPage.getDisplayTime(1e4*i),value:1e4*i});select.innerHTML=options.map(function(o){return'"}).join("")}Array.prototype.remove=function(from,to){var rest=this.slice((to||from)+1||this.length);return this.length=from<0?this.length+from:from,this.push.apply(this,rest)};var ScheduledTaskPage={refreshScheduledTask:function(view){loading.show();var id=getParameterByName("id");ApiClient.getScheduledTask(id).then(function(task){ScheduledTaskPage.loadScheduledTask(view,task)})},loadScheduledTask:function(view,task){$(".taskName",view).html(task.Name),$("#pTaskDescription",view).html(task.Description),require(["listViewStyle"],function(){ScheduledTaskPage.loadTaskTriggers(view,task)}),loading.hide()},loadTaskTriggers:function(context,task){var html="";html+='
    ';for(var i=0,length=task.Triggers.length;i',html+='schedule',trigger.MaxRuntimeTicks?html+='
    ':html+='
    ',html+="
    "+ScheduledTaskPage.getTriggerFriendlyName(trigger)+"
    ",trigger.MaxRuntimeTicks){html+='
    ';var hours=trigger.MaxRuntimeTicks/36e9;html+=1==hours?globalize.translate("ValueTimeLimitSingleHour"):globalize.translate("ValueTimeLimitMultiHour",hours),html+="
    "}html+="
    ",html+='',html+="
    "}html+="
    ",context.querySelector(".taskTriggers").innerHTML=html},getTriggerFriendlyName:function(trigger){if("DailyTrigger"==trigger.Type)return"Daily at "+ScheduledTaskPage.getDisplayTime(trigger.TimeOfDayTicks);if("WeeklyTrigger"==trigger.Type)return trigger.DayOfWeek+"s at "+ScheduledTaskPage.getDisplayTime(trigger.TimeOfDayTicks);if("SystemEventTrigger"==trigger.Type&&"WakeFromSleep"==trigger.SystemEvent)return"On wake from sleep";if("IntervalTrigger"==trigger.Type){var hours=trigger.IntervalTicks/36e9;return.25==hours?"Every 15 minutes":.5==hours?"Every 30 minutes":.75==hours?"Every 45 minutes":1==hours?"Every hour":"Every "+hours+" hours"}return"StartupTrigger"==trigger.Type?"On application startup":trigger.Type},getDisplayTime:function(ticks){var ms=ticks/1e4,now=new Date;return now.setHours(0,0,0,0),now.setTime(now.getTime()+ms),datetime.getDisplayTime(now)},showAddTriggerPopup:function(view){$("#selectTriggerType",view).val("DailyTrigger"),view.querySelector("#selectTriggerType").dispatchEvent(new CustomEvent("change",{})),$("#popupAddTrigger",view).removeClass("hide")},confirmDeleteTrigger:function(view,index){require(["confirm"],function(confirm){confirm(globalize.translate("MessageDeleteTaskTrigger"),globalize.translate("HeaderDeleteTaskTrigger")).then(function(){ScheduledTaskPage.deleteTrigger(view,index)})})},deleteTrigger:function(view,index){loading.show();var id=getParameterByName("id");ApiClient.getScheduledTask(id).then(function(task){task.Triggers.remove(index),ApiClient.updateScheduledTaskTriggers(task.Id,task.Triggers).then(function(){ScheduledTaskPage.refreshScheduledTask(view)})})},refreshTriggerFields:function(page,triggerType){"DailyTrigger"==triggerType?($("#fldTimeOfDay",page).show(),$("#fldDayOfWeek",page).hide(),$("#fldSelectSystemEvent",page).hide(),$("#fldSelectInterval",page).hide(),$("#selectTimeOfDay",page).attr("required","required")):"WeeklyTrigger"==triggerType?($("#fldTimeOfDay",page).show(),$("#fldDayOfWeek",page).show(),$("#fldSelectSystemEvent",page).hide(),$("#fldSelectInterval",page).hide(),$("#selectTimeOfDay",page).attr("required","required")):"SystemEventTrigger"==triggerType?($("#fldTimeOfDay",page).hide(),$("#fldDayOfWeek",page).hide(),$("#fldSelectSystemEvent",page).show(),$("#fldSelectInterval",page).hide(),$("#selectTimeOfDay",page).removeAttr("required")):"IntervalTrigger"==triggerType?($("#fldTimeOfDay",page).hide(),$("#fldDayOfWeek",page).hide(),$("#fldSelectSystemEvent",page).hide(),$("#fldSelectInterval",page).show(),$("#selectTimeOfDay",page).removeAttr("required")):"StartupTrigger"==triggerType&&($("#fldTimeOfDay",page).hide(),$("#fldDayOfWeek",page).hide(),$("#fldSelectSystemEvent",page).hide(),$("#fldSelectInterval",page).hide(),$("#selectTimeOfDay",page).removeAttr("required"))},getTriggerToAdd:function(page){var trigger={Type:$("#selectTriggerType",page).val()};"DailyTrigger"==trigger.Type?trigger.TimeOfDayTicks=$("#selectTimeOfDay",page).val():"WeeklyTrigger"==trigger.Type?(trigger.DayOfWeek=$("#selectDayOfWeek",page).val(),trigger.TimeOfDayTicks=$("#selectTimeOfDay",page).val()):"SystemEventTrigger"==trigger.Type?trigger.SystemEvent=$("#selectSystemEvent",page).val():"IntervalTrigger"==trigger.Type&&(trigger.IntervalTicks=$("#selectInterval",page).val());var timeLimit=$("#txtTimeLimit",page).val()||"0";return timeLimit=36e5*parseFloat(timeLimit),trigger.MaxRuntimeMs=timeLimit||null,trigger}};return function(view,params){function onSubmit(e){loading.show();var id=getParameterByName("id");ApiClient.getScheduledTask(id).then(function(task){task.Triggers.push(ScheduledTaskPage.getTriggerToAdd(view)),ApiClient.updateScheduledTaskTriggers(task.Id,task.Triggers).then(function(){$("#popupAddTrigger").addClass("hide"),ScheduledTaskPage.refreshScheduledTask(view)})}),e.preventDefault()}view.querySelector(".addTriggerForm").addEventListener("submit",onSubmit),fillTimeOfDay(view.querySelector("#selectTimeOfDay")),$(view.querySelector("#popupAddTrigger").parentNode).trigger("create"),view.querySelector(".selectTriggerType").addEventListener("change",function(){ScheduledTaskPage.refreshTriggerFields(view,this.value)}),view.querySelector(".btnAddTrigger").addEventListener("click",function(){ScheduledTaskPage.showAddTriggerPopup(view)}),view.addEventListener("click",function(e){var btnDeleteTrigger=dom.parentWithClass(e.target,"btnDeleteTrigger");btnDeleteTrigger&&ScheduledTaskPage.confirmDeleteTrigger(view,parseInt(btnDeleteTrigger.getAttribute("data-index")))}),view.addEventListener("viewshow",function(){ScheduledTaskPage.refreshScheduledTask(view)})}}); \ No newline at end of file +define(["jQuery", "loading", "datetime", "dom", "globalize", "emby-input", "emby-button", "emby-select"], function($, loading, datetime, dom, globalize) { + "use strict"; + + function fillTimeOfDay(select) { + for (var options = [], i = 0; i < 864e5; i += 9e5) options.push({ + name: ScheduledTaskPage.getDisplayTime(1e4 * i), + value: 1e4 * i + }); + select.innerHTML = options.map(function(o) { + return '" + }).join("") + } + Array.prototype.remove = function(from, to) { + var rest = this.slice((to || from) + 1 || this.length); + return this.length = from < 0 ? this.length + from : from, this.push.apply(this, rest) + }; + var ScheduledTaskPage = { + refreshScheduledTask: function(view) { + loading.show(); + var id = getParameterByName("id"); + ApiClient.getScheduledTask(id).then(function(task) { + ScheduledTaskPage.loadScheduledTask(view, task) + }) + }, + loadScheduledTask: function(view, task) { + $(".taskName", view).html(task.Name), $("#pTaskDescription", view).html(task.Description), require(["listViewStyle"], function() { + ScheduledTaskPage.loadTaskTriggers(view, task) + }), loading.hide() + }, + loadTaskTriggers: function(context, task) { + var html = ""; + html += '
    '; + for (var i = 0, length = task.Triggers.length; i < length; i++) { + var trigger = task.Triggers[i]; + if (html += '
    ', html += 'schedule', trigger.MaxRuntimeTicks ? html += '
    ' : html += '
    ', html += "
    " + ScheduledTaskPage.getTriggerFriendlyName(trigger) + "
    ", trigger.MaxRuntimeTicks) { + html += '
    '; + var hours = trigger.MaxRuntimeTicks / 36e9; + html += 1 == hours ? globalize.translate("ValueTimeLimitSingleHour") : globalize.translate("ValueTimeLimitMultiHour", hours), html += "
    " + } + html += "
    ", html += '', html += "
    " + } + html += "
    ", context.querySelector(".taskTriggers").innerHTML = html + }, + getTriggerFriendlyName: function(trigger) { + if ("DailyTrigger" == trigger.Type) return "Daily at " + ScheduledTaskPage.getDisplayTime(trigger.TimeOfDayTicks); + if ("WeeklyTrigger" == trigger.Type) return trigger.DayOfWeek + "s at " + ScheduledTaskPage.getDisplayTime(trigger.TimeOfDayTicks); + if ("SystemEventTrigger" == trigger.Type && "WakeFromSleep" == trigger.SystemEvent) return "On wake from sleep"; + if ("IntervalTrigger" == trigger.Type) { + var hours = trigger.IntervalTicks / 36e9; + return .25 == hours ? "Every 15 minutes" : .5 == hours ? "Every 30 minutes" : .75 == hours ? "Every 45 minutes" : 1 == hours ? "Every hour" : "Every " + hours + " hours" + } + return "StartupTrigger" == trigger.Type ? "On application startup" : trigger.Type + }, + getDisplayTime: function(ticks) { + var ms = ticks / 1e4, + now = new Date; + return now.setHours(0, 0, 0, 0), now.setTime(now.getTime() + ms), datetime.getDisplayTime(now) + }, + showAddTriggerPopup: function(view) { + $("#selectTriggerType", view).val("DailyTrigger"), view.querySelector("#selectTriggerType").dispatchEvent(new CustomEvent("change", {})), $("#popupAddTrigger", view).removeClass("hide") + }, + confirmDeleteTrigger: function(view, index) { + require(["confirm"], function(confirm) { + confirm(globalize.translate("MessageDeleteTaskTrigger"), globalize.translate("HeaderDeleteTaskTrigger")).then(function() { + ScheduledTaskPage.deleteTrigger(view, index) + }) + }) + }, + deleteTrigger: function(view, index) { + loading.show(); + var id = getParameterByName("id"); + ApiClient.getScheduledTask(id).then(function(task) { + task.Triggers.remove(index), ApiClient.updateScheduledTaskTriggers(task.Id, task.Triggers).then(function() { + ScheduledTaskPage.refreshScheduledTask(view) + }) + }) + }, + refreshTriggerFields: function(page, triggerType) { + "DailyTrigger" == triggerType ? ($("#fldTimeOfDay", page).show(), $("#fldDayOfWeek", page).hide(), $("#fldSelectSystemEvent", page).hide(), $("#fldSelectInterval", page).hide(), $("#selectTimeOfDay", page).attr("required", "required")) : "WeeklyTrigger" == triggerType ? ($("#fldTimeOfDay", page).show(), $("#fldDayOfWeek", page).show(), $("#fldSelectSystemEvent", page).hide(), $("#fldSelectInterval", page).hide(), $("#selectTimeOfDay", page).attr("required", "required")) : "SystemEventTrigger" == triggerType ? ($("#fldTimeOfDay", page).hide(), $("#fldDayOfWeek", page).hide(), $("#fldSelectSystemEvent", page).show(), $("#fldSelectInterval", page).hide(), $("#selectTimeOfDay", page).removeAttr("required")) : "IntervalTrigger" == triggerType ? ($("#fldTimeOfDay", page).hide(), $("#fldDayOfWeek", page).hide(), $("#fldSelectSystemEvent", page).hide(), $("#fldSelectInterval", page).show(), $("#selectTimeOfDay", page).removeAttr("required")) : "StartupTrigger" == triggerType && ($("#fldTimeOfDay", page).hide(), $("#fldDayOfWeek", page).hide(), $("#fldSelectSystemEvent", page).hide(), $("#fldSelectInterval", page).hide(), $("#selectTimeOfDay", page).removeAttr("required")) + }, + getTriggerToAdd: function(page) { + var trigger = { + Type: $("#selectTriggerType", page).val() + }; + "DailyTrigger" == trigger.Type ? trigger.TimeOfDayTicks = $("#selectTimeOfDay", page).val() : "WeeklyTrigger" == trigger.Type ? (trigger.DayOfWeek = $("#selectDayOfWeek", page).val(), trigger.TimeOfDayTicks = $("#selectTimeOfDay", page).val()) : "SystemEventTrigger" == trigger.Type ? trigger.SystemEvent = $("#selectSystemEvent", page).val() : "IntervalTrigger" == trigger.Type && (trigger.IntervalTicks = $("#selectInterval", page).val()); + var timeLimit = $("#txtTimeLimit", page).val() || "0"; + return timeLimit = 36e5 * parseFloat(timeLimit), trigger.MaxRuntimeMs = timeLimit || null, trigger + } + }; + return function(view, params) { + function onSubmit(e) { + loading.show(); + var id = getParameterByName("id"); + ApiClient.getScheduledTask(id).then(function(task) { + task.Triggers.push(ScheduledTaskPage.getTriggerToAdd(view)), ApiClient.updateScheduledTaskTriggers(task.Id, task.Triggers).then(function() { + $("#popupAddTrigger").addClass("hide"), ScheduledTaskPage.refreshScheduledTask(view) + }) + }), e.preventDefault() + } + view.querySelector(".addTriggerForm").addEventListener("submit", onSubmit), fillTimeOfDay(view.querySelector("#selectTimeOfDay")), $(view.querySelector("#popupAddTrigger").parentNode).trigger("create"), view.querySelector(".selectTriggerType").addEventListener("change", function() { + ScheduledTaskPage.refreshTriggerFields(view, this.value) + }), view.querySelector(".btnAddTrigger").addEventListener("click", function() { + ScheduledTaskPage.showAddTriggerPopup(view) + }), view.addEventListener("click", function(e) { + var btnDeleteTrigger = dom.parentWithClass(e.target, "btnDeleteTrigger"); + btnDeleteTrigger && ScheduledTaskPage.confirmDeleteTrigger(view, parseInt(btnDeleteTrigger.getAttribute("data-index"))) + }), view.addEventListener("viewshow", function() { + ScheduledTaskPage.refreshScheduledTask(view) + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/scheduledtaskspage.js b/dashboard-ui/scripts/scheduledtaskspage.js index 24cb320216..d3d273fa59 100644 --- a/dashboard-ui/scripts/scheduledtaskspage.js +++ b/dashboard-ui/scripts/scheduledtaskspage.js @@ -1 +1,91 @@ -define(["jQuery","loading","events","globalize","serverNotifications","humanedate","listViewStyle","emby-linkbutton"],function($,loading,events,globalize,serverNotifications){"use strict";function reloadList(page){ApiClient.getScheduledTasks({isHidden:!1}).then(function(tasks){populateList(page,tasks),loading.hide()})}function populateList(page,tasks){tasks=tasks.sort(function(a,b){return a=a.Category+" "+a.Name,b=b.Category+" "+b.Name,a==b?0:a",html+="
    "),html+='
    ',html+='
    ',html+='

    ',html+=currentCategory,html+="

    ",0===i&&(html+=''+globalize.translate("Help")+""),html+="
    ",html+='
    '),html+='
    ',html+="",html+='schedule',html+="",html+='","Idle"==task.State?html+='':"Running"==task.State?html+='':html+='',html+="
    "}tasks.length&&(html+="
    ",html+="
    "),page.querySelector(".divScheduledTasks").innerHTML=html}function humane_elapsed(firstDateStr,secondDateStr){var dt1=new Date(firstDateStr),dt2=new Date(secondDateStr),seconds=(dt2.getTime()-dt1.getTime())/1e3,numdays=Math.floor(seconds%31536e3/86400),numhours=Math.floor(seconds%31536e3%86400/3600),numminutes=Math.floor(seconds%31536e3%86400%3600/60),numseconds=Math.round(seconds%31536e3%86400%3600%60),elapsedStr="";return elapsedStr+=1==numdays?numdays+" day ":"",elapsedStr+=numdays>1?numdays+" days ":"",elapsedStr+=1==numhours?numhours+" hour ":"",elapsedStr+=numhours>1?numhours+" hours ":"",elapsedStr+=1==numminutes?numminutes+" minute ":"",elapsedStr+=numminutes>1?numminutes+" minutes ":"",elapsedStr+=elapsedStr.length>0?"and ":"",elapsedStr+=1==numseconds?numseconds+" second":"",elapsedStr+=0==numseconds||numseconds>1?numseconds+" seconds":""}function getTaskProgressHtml(task){var html="";if("Idle"==task.State)task.LastExecutionResult&&(html+=globalize.translate("LabelScheduledTaskLastRan").replace("{0}",humane_date(task.LastExecutionResult.EndTimeUtc)).replace("{1}",humane_elapsed(task.LastExecutionResult.StartTimeUtc,task.LastExecutionResult.EndTimeUtc)),"Failed"==task.LastExecutionResult.Status?html+=" ("+globalize.translate("LabelFailed")+")":"Cancelled"==task.LastExecutionResult.Status?html+=" ("+globalize.translate("LabelCancelled")+")":"Aborted"==task.LastExecutionResult.Status&&(html+=" "+globalize.translate("LabelAbortedByServerShutdown")+""));else if("Running"==task.State){var progress=(task.CurrentProgressPercentage||0).toFixed(1);html+='
    ',html+='
    ',html+='
    ',html+="
    ",html+="
    ",html+=""+progress+"%",html+="
    "}else html+=""+globalize.translate("LabelStopping")+"";return html}function updateTaskButton(elem,state){"Idle"==state?(elem.classList.add("btnStartTask"),elem.classList.remove("btnStopTask"),elem.classList.remove("hide"),elem.querySelector("i").innerHTML="play_arrow",elem.title=globalize.translate("ButtonStart")):"Running"==state?(elem.classList.remove("btnStartTask"),elem.classList.add("btnStopTask"),elem.classList.remove("hide"),elem.querySelector("i").innerHTML="stop",elem.title=globalize.translate("ButtonStop")):(elem.classList.add("btnStartTask"),elem.classList.remove("btnStopTask"),elem.classList.add("hide"),elem.querySelector("i").innerHTML="play_arrow",elem.title=globalize.translate("ButtonStart")),$(elem).parents(".listItem")[0].setAttribute("data-status",state)}return function(view,params){function updateTasks(tasks){for(var i=0,length=tasks.length;i"), html += "
    ", html += '
    '), html += '
    ', html += "", html += 'schedule', html += "", html += '", "Idle" == task.State ? html += '' : "Running" == task.State ? html += '' : html += '', html += "
    " + } + tasks.length && (html += "
    ", html += "
    "), page.querySelector(".divScheduledTasks").innerHTML = html + } + + function humane_elapsed(firstDateStr, secondDateStr) { + var dt1 = new Date(firstDateStr), + dt2 = new Date(secondDateStr), + seconds = (dt2.getTime() - dt1.getTime()) / 1e3, + numdays = Math.floor(seconds % 31536e3 / 86400), + numhours = Math.floor(seconds % 31536e3 % 86400 / 3600), + numminutes = Math.floor(seconds % 31536e3 % 86400 % 3600 / 60), + numseconds = Math.round(seconds % 31536e3 % 86400 % 3600 % 60), + elapsedStr = ""; + return elapsedStr += 1 == numdays ? numdays + " day " : "", elapsedStr += numdays > 1 ? numdays + " days " : "", elapsedStr += 1 == numhours ? numhours + " hour " : "", elapsedStr += numhours > 1 ? numhours + " hours " : "", elapsedStr += 1 == numminutes ? numminutes + " minute " : "", elapsedStr += numminutes > 1 ? numminutes + " minutes " : "", elapsedStr += elapsedStr.length > 0 ? "and " : "", elapsedStr += 1 == numseconds ? numseconds + " second" : "", elapsedStr += 0 == numseconds || numseconds > 1 ? numseconds + " seconds" : "" + } + + function getTaskProgressHtml(task) { + var html = ""; + if ("Idle" == task.State) task.LastExecutionResult && (html += globalize.translate("LabelScheduledTaskLastRan").replace("{0}", humane_date(task.LastExecutionResult.EndTimeUtc)).replace("{1}", humane_elapsed(task.LastExecutionResult.StartTimeUtc, task.LastExecutionResult.EndTimeUtc)), "Failed" == task.LastExecutionResult.Status ? html += " (" + globalize.translate("LabelFailed") + ")" : "Cancelled" == task.LastExecutionResult.Status ? html += " (" + globalize.translate("LabelCancelled") + ")" : "Aborted" == task.LastExecutionResult.Status && (html += " " + globalize.translate("LabelAbortedByServerShutdown") + "")); + else if ("Running" == task.State) { + var progress = (task.CurrentProgressPercentage || 0).toFixed(1); + html += '
    ', html += '
    ', html += '
    ', html += "
    ", html += "
    ", html += "" + progress + "%", html += "
    " + } else html += "" + globalize.translate("LabelStopping") + ""; + return html + } + + function updateTaskButton(elem, state) { + "Idle" == state ? (elem.classList.add("btnStartTask"), elem.classList.remove("btnStopTask"), elem.classList.remove("hide"), elem.querySelector("i").innerHTML = "play_arrow", elem.title = globalize.translate("ButtonStart")) : "Running" == state ? (elem.classList.remove("btnStartTask"), elem.classList.add("btnStopTask"), elem.classList.remove("hide"), elem.querySelector("i").innerHTML = "stop", elem.title = globalize.translate("ButtonStop")) : (elem.classList.add("btnStartTask"), elem.classList.remove("btnStopTask"), elem.classList.add("hide"), elem.querySelector("i").innerHTML = "play_arrow", elem.title = globalize.translate("ButtonStart")), $(elem).parents(".listItem")[0].setAttribute("data-status", state) + } + return function(view, params) { + function updateTasks(tasks) { + for (var i = 0, length = tasks.length; i < length; i++) { + var task = tasks[i]; + view.querySelector("#taskProgress" + task.Id).innerHTML = getTaskProgressHtml(task); + updateTaskButton(view.querySelector("#btnTask" + task.Id), task.State) + } + } + + function onPollIntervalFired() { + ApiClient.isMessageChannelOpen() || reloadList(view) + } + + function onScheduledTasksUpdate(e, apiClient, info) { + apiClient.serverId() === serverId && updateTasks(info) + } + + function startInterval() { + ApiClient.sendMessage("ScheduledTasksInfoStart", "1000,1000"), pollInterval && clearInterval(pollInterval), pollInterval = setInterval(onPollIntervalFired, 1e4) + } + + function stopInterval() { + ApiClient.sendMessage("ScheduledTasksInfoStop"), pollInterval && clearInterval(pollInterval) + } + var pollInterval, serverId = ApiClient.serverId(); + $(".divScheduledTasks", view).on("click", ".btnStartTask", function() { + var button = this, + id = button.getAttribute("data-taskid"); + ApiClient.startScheduledTask(id).then(function() { + updateTaskButton(button, "Running"), reloadList(view) + }) + }).on("click", ".btnStopTask", function() { + var button = this, + id = button.getAttribute("data-taskid"); + ApiClient.stopScheduledTask(id).then(function() { + updateTaskButton(button, ""), reloadList(view) + }) + }), view.addEventListener("viewbeforehide", function() { + events.off(serverNotifications, "ScheduledTasksInfo", onScheduledTasksUpdate), stopInterval() + }), view.addEventListener("viewshow", function() { + loading.show(), startInterval(), reloadList(view), events.on(serverNotifications, "ScheduledTasksInfo", onScheduledTasksUpdate) + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/searchpage.js b/dashboard-ui/scripts/searchpage.js index 669129b6d5..b188a8b318 100644 --- a/dashboard-ui/scripts/searchpage.js +++ b/dashboard-ui/scripts/searchpage.js @@ -1 +1,21 @@ -define(["focusManager","searchFields","searchResults","events"],function(focusManager,SearchFields,SearchResults,events){"use strict";return function(view,params){function onSearch(e,value){self.searchResults.search(value)}var self=this;view.addEventListener("viewshow",function(){self.searchFields||(self.searchFields=new SearchFields({element:view.querySelector(".searchFields")}),self.searchResults=new SearchResults({element:view.querySelector(".searchResults"),serverId:params.serverId||ApiClient.serverId(),parentId:params.parentId,collectionType:params.collectionType}),events.on(self.searchFields,"search",onSearch))}),view.addEventListener("viewdestroy",function(){self.searchFields&&(self.searchFields.destroy(),self.searchFields=null),self.searchResults&&(self.searchResults.destroy(),self.searchResults=null)})}}); \ No newline at end of file +define(["focusManager", "searchFields", "searchResults", "events"], function(focusManager, SearchFields, SearchResults, events) { + "use strict"; + return function(view, params) { + function onSearch(e, value) { + self.searchResults.search(value) + } + var self = this; + view.addEventListener("viewshow", function() { + self.searchFields || (self.searchFields = new SearchFields({ + element: view.querySelector(".searchFields") + }), self.searchResults = new SearchResults({ + element: view.querySelector(".searchResults"), + serverId: params.serverId || ApiClient.serverId(), + parentId: params.parentId, + collectionType: params.collectionType + }), events.on(self.searchFields, "search", onSearch)) + }), view.addEventListener("viewdestroy", function() { + self.searchFields && (self.searchFields.destroy(), self.searchFields = null), self.searchResults && (self.searchResults.destroy(), self.searchResults = null) + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/searchtab.js b/dashboard-ui/scripts/searchtab.js index c8916ad033..538770e42e 100644 --- a/dashboard-ui/scripts/searchtab.js +++ b/dashboard-ui/scripts/searchtab.js @@ -1 +1,30 @@ -define(["searchFields","searchResults","events"],function(SearchFields,SearchResults,events){"use strict";function init(instance,tabContent,options){tabContent.innerHTML='
    ',instance.searchFields=new SearchFields({element:tabContent.querySelector(".searchFields")}),instance.searchResults=new SearchResults({element:tabContent.querySelector(".searchResults"),serverId:ApiClient.serverId(),parentId:options.parentId,collectionType:options.collectionType}),events.on(instance.searchFields,"search",function(e,value){instance.searchResults.search(value)})}function SearchTab(view,tabContent,options){var self=this;options=options||{},init(this,tabContent,options),self.preRender=function(){},self.renderTab=function(){var searchFields=this.searchFields;searchFields&&searchFields.focus()}}return SearchTab.prototype.destroy=function(){var searchFields=this.searchFields;searchFields&&searchFields.destroy(),this.searchFields=null;var searchResults=this.searchResults;searchResults&&searchResults.destroy(),this.searchResults=null},SearchTab}); \ No newline at end of file +define(["searchFields", "searchResults", "events"], function(SearchFields, SearchResults, events) { + "use strict"; + + function init(instance, tabContent, options) { + tabContent.innerHTML = '
    ', instance.searchFields = new SearchFields({ + element: tabContent.querySelector(".searchFields") + }), instance.searchResults = new SearchResults({ + element: tabContent.querySelector(".searchResults"), + serverId: ApiClient.serverId(), + parentId: options.parentId, + collectionType: options.collectionType + }), events.on(instance.searchFields, "search", function(e, value) { + instance.searchResults.search(value) + }) + } + + function SearchTab(view, tabContent, options) { + var self = this; + options = options || {}, init(this, tabContent, options), self.preRender = function() {}, self.renderTab = function() { + var searchFields = this.searchFields; + searchFields && searchFields.focus() + } + } + return SearchTab.prototype.destroy = function() { + var searchFields = this.searchFields; + searchFields && searchFields.destroy(), this.searchFields = null; + var searchResults = this.searchResults; + searchResults && searchResults.destroy(), this.searchResults = null + }, SearchTab +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/selectserver.js b/dashboard-ui/scripts/selectserver.js index b51f8ab2e3..e8b9c8b75b 100644 --- a/dashboard-ui/scripts/selectserver.js +++ b/dashboard-ui/scripts/selectserver.js @@ -1 +1,246 @@ -define(["loading","appRouter","layoutManager","appSettings","apphost","focusManager","connectionManager","backdrop","globalize","staticBackdrops","actionsheet","dom","material-icons","flexStyles","emby-scroller","emby-itemscontainer","cardStyle","emby-button"],function(loading,appRouter,layoutManager,appSettings,appHost,focusManager,connectionManager,backdrop,globalize,staticBackdrops,actionSheet,dom){"use strict";function renderSelectServerItems(view,servers){var items=servers.map(function(server){return{name:server.Name,showIcon:!0,icon:"",cardType:"",id:server.Id,server:server}}),html=items.map(function(item){var cardImageContainer;cardImageContainer=item.showIcon?''+item.icon+"":'
    ';var cardBoxCssClass="cardBox";layoutManager.tv&&(cardBoxCssClass+=" cardBox-focustransform");var innerOpening='
    ';return'
    "}).join(""),itemsContainer=view.querySelector(".servers");items.length||(html="

    "+globalize.translate("sharedcomponents#MessageNoServersAvailableToConnect")+"

    "),itemsContainer.innerHTML=html,loading.hide()}function updatePageStyle(view,params){"1"==params.showuser?(view.classList.add("libraryPage"),view.classList.remove("standalonePage"),view.classList.add("noSecondaryNavPage")):(view.classList.add("standalonePage"),view.classList.remove("libraryPage"),view.classList.remove("noSecondaryNavPage"))}function showGeneralError(){loading.hide(),alertText(globalize.translate("sharedcomponents#DefaultErrorMessage"))}function alertText(text){alertTextWithOptions({text:text})}function alertTextWithOptions(options){require(["alert"],function(alert){alert(options)})}function showServerConnectionFailure(){alertText(globalize.translate("MessageUnableToConnectToServer"),globalize.translate("HeaderConnectionFailure"))}return function(view,params){function connectToServer(server){loading.show(),connectionManager.connectToServer(server,{enableAutoLogin:appSettings.enableAutoLogin()}).then(function(result){loading.hide();var apiClient=result.ApiClient;switch(result.State){case"SignedIn":Dashboard.onServerChanged(apiClient.getCurrentUserId(),apiClient.accessToken(),apiClient),Dashboard.navigate("home.html");break;case"ServerSignIn":Dashboard.onServerChanged(null,null,apiClient),Dashboard.navigate("login.html?serverid="+result.Servers[0].Id);break;case"ServerUpdateNeeded":alertTextWithOptions({text:globalize.translate("core#ServerUpdateNeeded","https://emby.media"),html:globalize.translate("core#ServerUpdateNeeded",'https://emby.media')});break;default:showServerConnectionFailure()}})}function deleteServer(server){loading.show(),connectionManager.deleteServer(server.Id).then(function(){loading.hide(),loadServers()},function(){loading.hide(),loadServers()})}function acceptInvitation(id){loading.show(),connectionManager.acceptServer(id).then(function(){loading.hide(),loadServers(),loadInvitations()},showGeneralError)}function rejectInvitation(id){loading.show(),connectionManager.rejectServer(id).then(function(){loading.hide(),loadServers(),loadInvitations()},showGeneralError)}function showPendingInviteMenu(elem){var card=dom.parentWithClass(elem,"inviteItem"),invitationId=card.getAttribute("data-id"),menuItems=[];menuItems.push({name:globalize.translate("sharedcomponents#Accept"),id:"accept"}),menuItems.push({name:globalize.translate("sharedcomponents#Reject"),id:"reject"}),require(["actionsheet"],function(actionsheet){actionsheet.show({items:menuItems,positionTo:elem,callback:function(id){switch(id){case"accept":acceptInvitation(invitationId);break;case"reject":rejectInvitation(invitationId)}}})})}function getPendingInviteHtml(item){var cardBoxCssClass="cardBox";layoutManager.tv&&(cardBoxCssClass+=" cardBox-focustransform");var innerOpening='
    ';return'
    "}function renderInvitations(list){list.length?view.querySelector(".invitationSection").classList.remove("hide"):view.querySelector(".invitationSection").classList.add("hide");var html=list.map(getPendingInviteHtml).join("");view.querySelector(".invitations").innerHTML=html}function loadInvitations(){connectionManager.isLoggedIntoConnect()?connectionManager.getUserInvitations().then(renderInvitations):renderInvitations([])}function onServerClick(server){var menuItems=[];menuItems.push({name:globalize.translate("sharedcomponents#Connect"),id:"connect"}),menuItems.push({name:globalize.translate("sharedcomponents#Delete"),id:"delete"});var apiClient=connectionManager.getApiClient(server.Id);apiClient&&apiClient.supportsWakeOnLan()&&menuItems.push({name:globalize.translate("sharedcomponents#WakeServer"),id:"wol"}),actionSheet.show({items:menuItems,title:server.Name}).then(function(id){switch(id){case"connect":connectToServer(server);break;case"delete":deleteServer(server);break;case"wol":sendWolPacket(server)}})}function sendWolPacket(server){var apiClient=connectionManager.getApiClient(server.Id);require(["loadingDialog"],function(LoadingDialog){var dlg=new LoadingDialog({title:globalize.translate("sharedcomponents#HeaderWakeServer"),text:globalize.translate("sharedcomponents#AttemptingWakeServer")});dlg.show();var afterWol=function(){setTimeout(function(){apiClient.getPublicSystemInfo().then(onWolSuccess.bind(dlg),onWolFail.bind(dlg))},12e3)};apiClient.wakeOnLan().then(afterWol,afterWol)})}function onWolSuccess(){var dlg=this;dlg.hide(),dlg.destroy(),require(["alert"],function(alert){alert({text:globalize.translate("sharedcomponents#WakeServerSuccess"),title:globalize.translate("sharedcomponents#HeaderWakeServer")})})}function onWolFail(){var dlg=this;dlg.hide(),dlg.destroy(),require(["alert"],function(alert){alert({text:globalize.translate("sharedcomponents#WakeServerError"),title:globalize.translate("sharedcomponents#HeaderWakeServer")})})}function onServersRetrieved(result){servers=result,renderSelectServerItems(view,result),layoutManager.tv&&focusManager.autoFocus(view)}function loadServers(){loading.show(),connectionManager.getAvailableServers().then(onServersRetrieved,function(result){onServersRetrieved([])})}var servers;layoutManager.desktop;(function(){updatePageStyle(view,params),view.querySelector(".btnOfflineText").innerHTML=globalize.translate("sharedcomponents#HeaderMyDownloads"),appHost.supports("sync")&&view.querySelector(".btnOffline").classList.remove("hide")})();var backdropUrl=staticBackdrops.getRandomImageUrl();view.addEventListener("viewshow",function(e){var isRestored=e.detail.isRestored;appRouter.setTitle(null),backdrop.setBackdrop(backdropUrl),isRestored||(loadServers(),loadInvitations())}),view.querySelector(".btnConnect").addEventListener("click",function(e){appRouter.show("/connectlogin.html?mode=connect")}),view.querySelector(".btnOffline").addEventListener("click",function(e){appRouter.show("/offline/offline.html")}),view.querySelector(".servers").addEventListener("click",function(e){var card=dom.parentWithClass(e.target,"card");if(card){var url=card.getAttribute("data-url");if(url)appRouter.show(url);else{var id=card.getAttribute("data-id");onServerClick(servers.filter(function(s){return s.Id===id})[0])}}}),view.querySelector(".invitations").addEventListener("click",function(e){var btnInviteMenu=dom.parentWithClass(e.target,"btnInviteMenu");btnInviteMenu&&showPendingInviteMenu(btnInviteMenu)})}}); \ No newline at end of file +define(["loading", "appRouter", "layoutManager", "appSettings", "apphost", "focusManager", "connectionManager", "backdrop", "globalize", "staticBackdrops", "actionsheet", "dom", "material-icons", "flexStyles", "emby-scroller", "emby-itemscontainer", "cardStyle", "emby-button"], function(loading, appRouter, layoutManager, appSettings, appHost, focusManager, connectionManager, backdrop, globalize, staticBackdrops, actionSheet, dom) { + "use strict"; + + function renderSelectServerItems(view, servers) { + var items = servers.map(function(server) { + return { + name: server.Name, + showIcon: !0, + icon: "", + cardType: "", + id: server.Id, + server: server + } + }), + html = items.map(function(item) { + var cardImageContainer; + cardImageContainer = item.showIcon ? '' + item.icon + "" : '
    '; + var cardBoxCssClass = "cardBox"; + layoutManager.tv && (cardBoxCssClass += " cardBox-focustransform"); + var innerOpening = '
    '; + return '
    " + }).join(""), + itemsContainer = view.querySelector(".servers"); + items.length || (html = "

    " + globalize.translate("sharedcomponents#MessageNoServersAvailableToConnect") + "

    "), itemsContainer.innerHTML = html, loading.hide() + } + + function updatePageStyle(view, params) { + "1" == params.showuser ? (view.classList.add("libraryPage"), view.classList.remove("standalonePage"), view.classList.add("noSecondaryNavPage")) : (view.classList.add("standalonePage"), view.classList.remove("libraryPage"), view.classList.remove("noSecondaryNavPage")) + } + + function showGeneralError() { + loading.hide(), alertText(globalize.translate("sharedcomponents#DefaultErrorMessage")) + } + + function alertText(text) { + alertTextWithOptions({ + text: text + }) + } + + function alertTextWithOptions(options) { + require(["alert"], function(alert) { + alert(options) + }) + } + + function showServerConnectionFailure() { + alertText(globalize.translate("MessageUnableToConnectToServer"), globalize.translate("HeaderConnectionFailure")) + } + return function(view, params) { + function connectToServer(server) { + loading.show(), connectionManager.connectToServer(server, { + enableAutoLogin: appSettings.enableAutoLogin() + }).then(function(result) { + loading.hide(); + var apiClient = result.ApiClient; + switch (result.State) { + case "SignedIn": + Dashboard.onServerChanged(apiClient.getCurrentUserId(), apiClient.accessToken(), apiClient), Dashboard.navigate("home.html"); + break; + case "ServerSignIn": + Dashboard.onServerChanged(null, null, apiClient), Dashboard.navigate("login.html?serverid=" + result.Servers[0].Id); + break; + case "ServerUpdateNeeded": + alertTextWithOptions({ + text: globalize.translate("core#ServerUpdateNeeded", "https://emby.media"), + html: globalize.translate("core#ServerUpdateNeeded", 'https://emby.media') + }); + break; + default: + showServerConnectionFailure() + } + }) + } + + function deleteServer(server) { + loading.show(), connectionManager.deleteServer(server.Id).then(function() { + loading.hide(), loadServers() + }, function() { + loading.hide(), loadServers() + }) + } + + function acceptInvitation(id) { + loading.show(), connectionManager.acceptServer(id).then(function() { + loading.hide(), loadServers(), loadInvitations() + }, showGeneralError) + } + + function rejectInvitation(id) { + loading.show(), connectionManager.rejectServer(id).then(function() { + loading.hide(), loadServers(), loadInvitations() + }, showGeneralError) + } + + function showPendingInviteMenu(elem) { + var card = dom.parentWithClass(elem, "inviteItem"), + invitationId = card.getAttribute("data-id"), + menuItems = []; + menuItems.push({ + name: globalize.translate("sharedcomponents#Accept"), + id: "accept" + }), menuItems.push({ + name: globalize.translate("sharedcomponents#Reject"), + id: "reject" + }), require(["actionsheet"], function(actionsheet) { + actionsheet.show({ + items: menuItems, + positionTo: elem, + callback: function(id) { + switch (id) { + case "accept": + acceptInvitation(invitationId); + break; + case "reject": + rejectInvitation(invitationId) + } + } + }) + }) + } + + function getPendingInviteHtml(item) { + var cardBoxCssClass = "cardBox"; + layoutManager.tv && (cardBoxCssClass += " cardBox-focustransform"); + var innerOpening = '
    '; + return '
    " + } + + function renderInvitations(list) { + list.length ? view.querySelector(".invitationSection").classList.remove("hide") : view.querySelector(".invitationSection").classList.add("hide"); + var html = list.map(getPendingInviteHtml).join(""); + view.querySelector(".invitations").innerHTML = html + } + + function loadInvitations() { + connectionManager.isLoggedIntoConnect() ? connectionManager.getUserInvitations().then(renderInvitations) : renderInvitations([]) + } + + function onServerClick(server) { + var menuItems = []; + menuItems.push({ + name: globalize.translate("sharedcomponents#Connect"), + id: "connect" + }), menuItems.push({ + name: globalize.translate("sharedcomponents#Delete"), + id: "delete" + }); + var apiClient = connectionManager.getApiClient(server.Id); + apiClient && apiClient.supportsWakeOnLan() && menuItems.push({ + name: globalize.translate("sharedcomponents#WakeServer"), + id: "wol" + }), actionSheet.show({ + items: menuItems, + title: server.Name + }).then(function(id) { + switch (id) { + case "connect": + connectToServer(server); + break; + case "delete": + deleteServer(server); + break; + case "wol": + sendWolPacket(server) + } + }) + } + + function sendWolPacket(server) { + var apiClient = connectionManager.getApiClient(server.Id); + require(["loadingDialog"], function(LoadingDialog) { + var dlg = new LoadingDialog({ + title: globalize.translate("sharedcomponents#HeaderWakeServer"), + text: globalize.translate("sharedcomponents#AttemptingWakeServer") + }); + dlg.show(); + var afterWol = function() { + setTimeout(function() { + apiClient.getPublicSystemInfo().then(onWolSuccess.bind(dlg), onWolFail.bind(dlg)) + }, 12e3) + }; + apiClient.wakeOnLan().then(afterWol, afterWol) + }) + } + + function onWolSuccess() { + var dlg = this; + dlg.hide(), dlg.destroy(), require(["alert"], function(alert) { + alert({ + text: globalize.translate("sharedcomponents#WakeServerSuccess"), + title: globalize.translate("sharedcomponents#HeaderWakeServer") + }) + }) + } + + function onWolFail() { + var dlg = this; + dlg.hide(), dlg.destroy(), require(["alert"], function(alert) { + alert({ + text: globalize.translate("sharedcomponents#WakeServerError"), + title: globalize.translate("sharedcomponents#HeaderWakeServer") + }) + }) + } + + function onServersRetrieved(result) { + servers = result, renderSelectServerItems(view, result), layoutManager.tv && focusManager.autoFocus(view) + } + + function loadServers() { + loading.show(), connectionManager.getAvailableServers().then(onServersRetrieved, function(result) { + onServersRetrieved([]) + }) + } + var servers; + layoutManager.desktop; + (function() { + updatePageStyle(view, params), view.querySelector(".btnOfflineText").innerHTML = globalize.translate("sharedcomponents#HeaderMyDownloads"), appHost.supports("sync") && view.querySelector(".btnOffline").classList.remove("hide") + })(); + var backdropUrl = staticBackdrops.getRandomImageUrl(); + view.addEventListener("viewshow", function(e) { + var isRestored = e.detail.isRestored; + appRouter.setTitle(null), backdrop.setBackdrop(backdropUrl), isRestored || (loadServers(), loadInvitations()) + }), view.querySelector(".btnConnect").addEventListener("click", function(e) { + appRouter.show("/connectlogin.html?mode=connect") + }), view.querySelector(".btnOffline").addEventListener("click", function(e) { + appRouter.show("/offline/offline.html") + }), view.querySelector(".servers").addEventListener("click", function(e) { + var card = dom.parentWithClass(e.target, "card"); + if (card) { + var url = card.getAttribute("data-url"); + if (url) appRouter.show(url); + else { + var id = card.getAttribute("data-id"); + onServerClick(servers.filter(function(s) { + return s.Id === id + })[0]) + } + } + }), view.querySelector(".invitations").addEventListener("click", function(e) { + var btnInviteMenu = dom.parentWithClass(e.target, "btnInviteMenu"); + btnInviteMenu && showPendingInviteMenu(btnInviteMenu) + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/serversecurity.js b/dashboard-ui/scripts/serversecurity.js index 9565ecc28a..a74a04c103 100644 --- a/dashboard-ui/scripts/serversecurity.js +++ b/dashboard-ui/scripts/serversecurity.js @@ -1 +1,72 @@ -define(["datetime","loading","libraryMenu","dom","globalize","emby-button"],function(datetime,loading,libraryMenu,dom,globalize){"use strict";function revoke(page,key){require(["confirm"],function(confirm){confirm(globalize.translate("MessageConfirmRevokeApiKey"),globalize.translate("HeaderConfirmRevokeApiKey")).then(function(){loading.show(),ApiClient.ajax({type:"DELETE",url:ApiClient.getUrl("Auth/Keys/"+key)}).then(function(){loadData(page)})})})}function renderKeys(page,keys){var rows=keys.map(function(item){var html="";html+='',html+='',html+='",html+="",html+='',html+=item.AccessToken,html+="",html+='',html+=item.AppName||"",html+="",html+='';var date=datetime.parseISO8601Date(item.DateCreated,!0);return html+=datetime.toLocaleDateString(date)+" "+datetime.getDisplayTime(date),html+="",html+=""}).join("");page.querySelector(".resultBody").innerHTML=rows,loading.hide()}function loadData(page){loading.show(),ApiClient.getJSON(ApiClient.getUrl("Auth/Keys")).then(function(result){renderKeys(page,result.Items)})}function showNewKeyPrompt(page){require(["prompt"],function(prompt){prompt({title:globalize.translate("HeaderNewApiKey"),label:globalize.translate("LabelAppName"),description:globalize.translate("LabelAppNameExample")}).then(function(value){ApiClient.ajax({type:"POST",url:ApiClient.getUrl("Auth/Keys",{App:value})}).then(function(){loadData(page)})})})}function getTabs(){return[{href:"dashboardhosting.html",name:globalize.translate("TabHosting")},{href:"serversecurity.html",name:globalize.translate("TabSecurity")}]}pageIdOn("pageinit","serverSecurityPage",function(){var page=this;page.querySelector(".btnNewKey").addEventListener("click",function(){showNewKeyPrompt(page)}),page.querySelector(".tblApiKeys").addEventListener("click",function(e){var btnRevoke=dom.parentWithClass(e.target,"btnRevoke");btnRevoke&&revoke(page,btnRevoke.getAttribute("data-token"))})}),pageIdOn("pagebeforeshow","serverSecurityPage",function(){libraryMenu.setTabs("adminadvanced",1,getTabs),loadData(this)})}); \ No newline at end of file +define(["datetime", "loading", "libraryMenu", "dom", "globalize", "emby-button"], function(datetime, loading, libraryMenu, dom, globalize) { + "use strict"; + + function revoke(page, key) { + require(["confirm"], function(confirm) { + confirm(globalize.translate("MessageConfirmRevokeApiKey"), globalize.translate("HeaderConfirmRevokeApiKey")).then(function() { + loading.show(), ApiClient.ajax({ + type: "DELETE", + url: ApiClient.getUrl("Auth/Keys/" + key) + }).then(function() { + loadData(page) + }) + }) + }) + } + + function renderKeys(page, keys) { + var rows = keys.map(function(item) { + var html = ""; + html += '', html += '', html += '", html += "", html += '', html += item.AccessToken, html += "", html += '', html += item.AppName || "", html += "", html += ''; + var date = datetime.parseISO8601Date(item.DateCreated, !0); + return html += datetime.toLocaleDateString(date) + " " + datetime.getDisplayTime(date), html += "", html += "" + }).join(""); + page.querySelector(".resultBody").innerHTML = rows, loading.hide() + } + + function loadData(page) { + loading.show(), ApiClient.getJSON(ApiClient.getUrl("Auth/Keys")).then(function(result) { + renderKeys(page, result.Items) + }) + } + + function showNewKeyPrompt(page) { + require(["prompt"], function(prompt) { + prompt({ + title: globalize.translate("HeaderNewApiKey"), + label: globalize.translate("LabelAppName"), + description: globalize.translate("LabelAppNameExample") + }).then(function(value) { + ApiClient.ajax({ + type: "POST", + url: ApiClient.getUrl("Auth/Keys", { + App: value + }) + }).then(function() { + loadData(page) + }) + }) + }) + } + + function getTabs() { + return [{ + href: "dashboardhosting.html", + name: globalize.translate("TabHosting") + }, { + href: "serversecurity.html", + name: globalize.translate("TabSecurity") + }] + } + pageIdOn("pageinit", "serverSecurityPage", function() { + var page = this; + page.querySelector(".btnNewKey").addEventListener("click", function() { + showNewKeyPrompt(page) + }), page.querySelector(".tblApiKeys").addEventListener("click", function(e) { + var btnRevoke = dom.parentWithClass(e.target, "btnRevoke"); + btnRevoke && revoke(page, btnRevoke.getAttribute("data-token")) + }) + }), pageIdOn("pagebeforeshow", "serverSecurityPage", function() { + libraryMenu.setTabs("adminadvanced", 1, getTabs), loadData(this) + }) +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/site.js b/dashboard-ui/scripts/site.js index b5dd159152..76a5459268 100644 --- a/dashboard-ui/scripts/site.js +++ b/dashboard-ui/scripts/site.js @@ -1,2 +1,1136 @@ -function getWindowLocationSearch(win){"use strict";var search=(win||window).location.search;if(!search){var index=window.location.href.indexOf("?");-1!=index&&(search=window.location.href.substring(index))}return search||""}function getParameterByName(name,url){"use strict";name=name.replace(/[\[]/,"\\[").replace(/[\]]/,"\\]");var regexS="[\\?&]"+name+"=([^&#]*)",regex=new RegExp(regexS,"i"),results=regex.exec(url||getWindowLocationSearch());return null==results?"":decodeURIComponent(results[1].replace(/\+/g," "))}function pageClassOn(eventName,className,fn){"use strict";document.addEventListener(eventName,function(e){var target=e.target;target.classList.contains(className)&&fn.call(target,e)})}function pageIdOn(eventName,id,fn){"use strict";document.addEventListener(eventName,function(e){var target=e.target;target.id===id&&fn.call(target,e)})}var Dashboard={isConnectMode:function(){if(AppInfo.isNativeApp)return!0;var url=window.location.href.toLowerCase();return-1!=url.indexOf("mediabrowser.tv")||-1!=url.indexOf("emby.media")},allowPluginPages:function(pluginId){var allowedPluginConfigs=["b0daa30f-2e09-4083-a6ce-459d9fecdd80","de228f12-e43e-4bd9-9fc0-2830819c3b92","899c12c7-5b40-4c4e-9afd-afd74a685eb1","14f5f69e-4c8d-491b-8917-8e90e8317530","02528C96-F727-44D7-BE87-9EEF040758C3","dc372f99-4e0e-4c6b-8c18-2b887ca4530c","830fc68f-b964-4d2f-b139-48e22cd143c","b9f0c474-e9a8-4292-ae41-eb3c1542f4cd","7cfbb821-e8fd-40ab-b64e-a7749386a6b2","4C2FDA1C-FD5E-433A-AD2B-718E0B73E9A9","cd5a19be-7676-48ef-b64f-a17c98f2b889","b2ff6a63-303a-4a84-b937-6e12f87e3eb9","0277E613-3EC0-4360-A3DE-F8AF0AABB5E9","9464BD84-D30D-4404-B2AD-DFF4E12D5FC5","9574ac10-bf23-49bc-949f-924f23cfa48f","66fd72a4-7e8e-4f22-8d1c-022ce4b9b0d5","4DCB591C-0FA2-4C5D-A7E5-DABE37164C8B","8e791e2a-058a-4b12-8493-8bf69d92d685","577f89eb-58a7-4013-be06-9a970ddb1377","6153FDF0-40CC-4457-8730-3B4A19512BAE","de228f12-e43e-4bd9-9fc0-2830819c3b92","6C3B6965-C257-47C2-AA02-64457AE21D91","2FE79C34-C9DC-4D94-9DF2-2F3F36764414","0417264b-5a93-4ad0-a1f0-b87569b7cf80","e711475e-efad-431b-8527-033ba9873a34","AB95885A-1D0E-445E-BDBF-80C1912C98C5","F015EA06-B413-47F1-BF15-F049A799658B","986a7283-205a-4436-862d-23135c067f8a","8abc6789-fde2-4705-8592-4028806fa343","2850d40d-9c66-4525-aa46-968e8ef04e97"].map(function(i){return i.toLowerCase()});return!(AppInfo.isNativeApp&&-1===allowedPluginConfigs.indexOf((pluginId||"").toLowerCase()))},getCurrentUser:function(){return window.ApiClient.getCurrentUser(!1)},serverAddress:function(){if(Dashboard.isConnectMode()){var apiClient=window.ApiClient;return apiClient?apiClient.serverAddress():null}var urlLower=window.location.href.toLowerCase(),index=urlLower.lastIndexOf("/web");if(-1!=index)return urlLower.substring(0,index);var loc=window.location,address=loc.protocol+"//"+loc.hostname;return loc.port&&(address+=":"+loc.port),address},getCurrentUserId:function(){var apiClient=window.ApiClient;return apiClient?apiClient.getCurrentUserId():null},onServerChanged:function(userId,accessToken,apiClient){apiClient=apiClient||window.ApiClient,window.ApiClient=apiClient},logout:function(logoutWithServer){function onLogoutDone(){var loginPage;Dashboard.isConnectMode()?(loginPage="connectlogin.html",window.ApiClient=null):loginPage="login.html",Dashboard.navigate(loginPage)}!1===logoutWithServer?onLogoutDone():ConnectionManager.logout().then(onLogoutDone)},getConfigurationPageUrl:function(name){return Dashboard.isConnectMode()?"configurationpageext?name="+encodeURIComponent(name):"configurationpage?name="+encodeURIComponent(name)},getConfigurationResourceUrl:function(name){return Dashboard.isConnectMode()?ApiClient.getUrl("web/ConfigurationPage",{name:name}):Dashboard.getConfigurationPageUrl(name)},navigate:function(url,preserveQueryString){if(!url)throw new Error("url cannot be null or empty");var queryString=getWindowLocationSearch();return preserveQueryString&&queryString&&(url+=queryString),new Promise(function(resolve,reject){require(["appRouter"],function(appRouter){return appRouter.show(url).then(resolve,reject)})})},processPluginConfigurationUpdateResult:function(){require(["loading","toast"],function(loading,toast){loading.hide(),toast(Globalize.translate("MessageSettingsSaved"))})},processServerConfigurationUpdateResult:function(result){require(["loading","toast"],function(loading,toast){loading.hide(),toast(Globalize.translate("MessageSettingsSaved"))})},processErrorResponse:function(response){require(["loading"],function(loading){loading.hide()});var status=""+response.status;response.statusText&&(status=response.statusText),Dashboard.alert({title:status,message:response.headers?response.headers.get("X-Application-Error-Code"):null})},alert:function(options){if("string"==typeof options)return void require(["toast"],function(toast){toast({text:options})});require(["alert"],function(alert){alert({title:options.title||Globalize.translate("HeaderAlert"),text:options.message}).then(options.callback||function(){})})},restartServer:function(){var apiClient=window.ApiClient;apiClient&&require(["serverRestartDialog","events"],function(ServerRestartDialog,events){var dialog=new ServerRestartDialog({apiClient:apiClient});events.on(dialog,"restarted",function(){Dashboard.isConnectMode()?apiClient.ensureWebSocket():window.location.reload(!0)}),dialog.show()})},capabilities:function(appHost){var caps={PlayableMediaTypes:["Audio","Video"],SupportedCommands:["MoveUp","MoveDown","MoveLeft","MoveRight","PageUp","PageDown","PreviousLetter","NextLetter","ToggleOsd","ToggleContextMenu","Select","Back","SendKey","SendString","GoHome","GoToSettings","VolumeUp","VolumeDown","Mute","Unmute","ToggleMute","SetVolume","SetAudioStreamIndex","SetSubtitleStreamIndex","DisplayContent","GoToSearch","DisplayMessage","SetRepeatMode","ChannelUp","ChannelDown","PlayMediaSource","PlayTrailers"],SupportsPersistentIdentifier:"cordova"===self.appMode||"android"===self.appMode,SupportsMediaControl:!0};caps.IconUrl=appHost.deviceIconUrl(),caps.SupportsSync=appHost.supports("sync"),caps.SupportsContentUploading=appHost.supports("cameraupload");appHost.getPushTokenInfo();return caps=Object.assign(caps,appHost.getPushTokenInfo())}},AppInfo={};!function(){"use strict";function initializeApiClient(apiClient){"cordova"!==self.appMode&&"android"!==self.appMode||(apiClient.getAvailablePlugins=function(){return Promise.resolve([])})}function onApiClientCreated(e,newApiClient){initializeApiClient(newApiClient),window.$&&($.ajax=newApiClient.ajax)}function defineConnectionManager(connectionManager){window.ConnectionManager=connectionManager,define("connectionManager",[],function(){return connectionManager})}function bindConnectionManagerEvents(connectionManager,events,userSettings){window.Events=events,events.on(ConnectionManager,"apiclientcreated",onApiClientCreated),connectionManager.currentApiClient=function(){if(!localApiClient){var server=connectionManager.getLastUsedServer();server&&(localApiClient=connectionManager.getApiClient(server.Id))}return localApiClient},connectionManager.onLocalUserSignedIn=function(user){return localApiClient=connectionManager.getApiClient(user.ServerId),window.ApiClient=localApiClient,userSettings.setUserInfo(user.Id,localApiClient)},events.on(connectionManager,"localusersignedout",function(){userSettings.setUserInfo(null,null)})}function createConnectionManager(){return new Promise(function(resolve,reject){require(["connectionManagerFactory","apphost","credentialprovider","events","userSettings"],function(ConnectionManager,apphost,credentialProvider,events,userSettings){var credentialProviderInstance=new credentialProvider,promises=[apphost.getSyncProfile(),apphost.init()];Promise.all(promises).then(function(responses){var deviceProfile=responses[0],capabilities=Dashboard.capabilities(apphost);capabilities.DeviceProfile=deviceProfile;var connectionManager=new ConnectionManager(credentialProviderInstance,apphost.appName(),apphost.appVersion(),apphost.deviceName(),apphost.deviceId(),capabilities,window.devicePixelRatio);if(defineConnectionManager(connectionManager),bindConnectionManagerEvents(connectionManager,events,userSettings),!Dashboard.isConnectMode())return console.log("loading ApiClient singleton"),getRequirePromise(["apiclient"]).then(function(apiClientFactory){console.log("creating ApiClient singleton");var apiClient=new apiClientFactory(Dashboard.serverAddress(),apphost.appName(),apphost.appVersion(),apphost.deviceName(),apphost.deviceId(),window.devicePixelRatio);apiClient.enableAutomaticNetworking=!1,apiClient.manualAddressOnly=!0,connectionManager.addApiClient(apiClient),window.ApiClient=apiClient,localApiClient=apiClient,console.log("loaded ApiClient singleton"),resolve()});resolve()})})})}function returnFirstDependency(obj){return obj}function getSettingsBuilder(UserSettings,layoutManager,browser){return UserSettings.prototype.enableThemeVideos=function(val){return null!=val?this.set("enableThemeVideos",val.toString(),!1):(val=this.get("enableThemeVideos",!1),val?"false"!==val:!layoutManager.mobile&&!browser.slow)},UserSettings}function getBowerPath(){return"bower_components"}function getPlaybackManager(playbackManager){return window.addEventListener("beforeunload",function(e){try{playbackManager.onAppClose()}catch(err){console.log("error in onAppClose: "+err)}}),playbackManager}function getLayoutManager(layoutManager,appHost){return appHost.getDefaultLayout&&(layoutManager.defaultLayout=appHost.getDefaultLayout()),layoutManager.init(),layoutManager}function getAppStorage(basePath){try{return localStorage.setItem("_test","0"),localStorage.removeItem("_test"),basePath+"/appstorage-localstorage"}catch(e){return basePath+"/appstorage-memory"}}function createWindowHeadroom(Headroom){var headroom=new Headroom([],{});return headroom.init(),headroom}function getCastSenderApiLoader(){var ccLoaded=!1;return{load:function(){return ccLoaded?Promise.resolve():new Promise(function(resolve,reject){var fileref=document.createElement("script");fileref.setAttribute("type","text/javascript"),fileref.onload=function(){ccLoaded=!0,resolve()},fileref.setAttribute("src","https://www.gstatic.com/cv/js/sender/v1/cast_sender.js"),document.querySelector("head").appendChild(fileref)})}}}function getDummyCastSenderApiLoader(){return{load:function(){return window.chrome=window.chrome||{},Promise.resolve()}}}function createSharedAppFooter(appFooter){return new appFooter({})}function onRequireJsError(requireType,requireModules){console.log("RequireJS error: "+(requireType||"unknown")+". Failed modules: "+(requireModules||[]).join(","))}function defineResizeObserver(){self.ResizeObserver?define("ResizeObserver",[],function(){return self.ResizeObserver}):define("ResizeObserver",["bower_components/emby-webcomponents/resize-observer-polyfill/ResizeObserver"],returnFirstDependency)}function initRequireWithBrowser(browser){var bowerPath=getBowerPath(),apiClientBowerPath=bowerPath+"/emby-apiclient",embyWebComponentsBowerPath=bowerPath+"/emby-webcomponents";"android"===self.appMode?define("iapManager",["cordova/iap"],returnFirstDependency):"cordova"===self.appMode?define("iapManager",["cordova/iap"],returnFirstDependency):define("iapManager",["components/iap"],returnFirstDependency),"android"===self.appMode?(define("filesystem",["cordova/filesystem"],returnFirstDependency),define("cameraRoll",["cordova/cameraroll"],returnFirstDependency)):(define("filesystem",[embyWebComponentsBowerPath+"/filesystem"],returnFirstDependency),define("cameraRoll",[apiClientBowerPath+"/cameraroll"],returnFirstDependency)),window.IntersectionObserver&&!browser.edge?define("lazyLoader",[embyWebComponentsBowerPath+"/lazyloader/lazyloader-intersectionobserver"],returnFirstDependency):define("lazyLoader",[embyWebComponentsBowerPath+"/lazyloader/lazyloader-scroll"],returnFirstDependency),"android"===self.appMode?define("shell",["cordova/shell"],returnFirstDependency):define("shell",[embyWebComponentsBowerPath+"/shell"],returnFirstDependency),"cordova"===self.appMode||"android"===self.appMode?(define("apiclientcore",["bower_components/emby-apiclient/apiclient"],returnFirstDependency),define("apiclient",["bower_components/emby-apiclient/apiclientex"],returnFirstDependency)):define("apiclient",["bower_components/emby-apiclient/apiclient"],returnFirstDependency),"cordova"===self.appMode||"android"===self.appMode?define("wakeOnLan",["cordova/wakeonlan"],returnFirstDependency):define("wakeOnLan",["bower_components/emby-apiclient/wakeonlan"],returnFirstDependency),define("actionsheet",["webActionSheet"],returnFirstDependency),"registerElement"in document?define("registerElement",[]):browser.msie?define("registerElement",[bowerPath+"/webcomponentsjs/webcomponents-lite.min.js"],returnFirstDependency):define("registerElement",[bowerPath+"/document-register-element/build/document-register-element"],returnFirstDependency),"android"===self.appMode?define("serverdiscovery",["cordova/serverdiscovery"],returnFirstDependency):"cordova"===self.appMode?define("serverdiscovery",["cordova/serverdiscovery"],returnFirstDependency):define("serverdiscovery",[apiClientBowerPath+"/serverdiscovery"],returnFirstDependency),"cordova"===self.appMode&&browser.iOSVersion&&browser.iOSVersion<11?define("imageFetcher",["cordova/imagestore"],returnFirstDependency):define("imageFetcher",[embyWebComponentsBowerPath+"/images/basicimagefetcher"],returnFirstDependency);var preferNativeAlerts=browser.tv;preferNativeAlerts&&window.alert?define("alert",[embyWebComponentsBowerPath+"/alert/nativealert"],returnFirstDependency):define("alert",[embyWebComponentsBowerPath+"/alert/alert"],returnFirstDependency),defineResizeObserver(),define("dialog",[embyWebComponentsBowerPath+"/dialog/dialog"],returnFirstDependency),preferNativeAlerts&&window.confirm?define("confirm",[embyWebComponentsBowerPath+"/confirm/nativeconfirm"],returnFirstDependency):define("confirm",[embyWebComponentsBowerPath+"/confirm/confirm"],returnFirstDependency),(preferNativeAlerts||browser.xboxOne)&&window.confirm?define("prompt",[embyWebComponentsBowerPath+"/prompt/nativeprompt"],returnFirstDependency):define("prompt",[embyWebComponentsBowerPath+"/prompt/prompt"],returnFirstDependency),browser.tizen||browser.operaTv||browser.chromecast||browser.orsay||browser.web0s||browser.ps4?define("loading",[embyWebComponentsBowerPath+"/loading/loading-legacy"],returnFirstDependency):define("loading",[embyWebComponentsBowerPath+"/loading/loading-lite"],returnFirstDependency),define("multi-download",[embyWebComponentsBowerPath+"/multidownload"],returnFirstDependency),"android"===self.appMode?define("fileDownloader",["cordova/filedownloader"],returnFirstDependency):define("fileDownloader",[embyWebComponentsBowerPath+"/filedownloader"],returnFirstDependency),define("localassetmanager",[apiClientBowerPath+"/localassetmanager"],returnFirstDependency),"cordova"===self.appMode||"android"===self.appMode?define("castSenderApiLoader",[],getDummyCastSenderApiLoader):define("castSenderApiLoader",[],getCastSenderApiLoader),self.Windows?(define("bgtaskregister",["environments/windows-uwp/bgtaskregister"],returnFirstDependency),define("transfermanager",["environments/windows-uwp/transfermanager"],returnFirstDependency),define("filerepository",["environments/windows-uwp/filerepository"],returnFirstDependency)):"cordova"===self.appMode?(define("filerepository",["cordova/filerepository"],returnFirstDependency),define("transfermanager",["filerepository"],returnFirstDependency)):"android"===self.appMode?(define("transfermanager",["cordova/transfermanager"],returnFirstDependency),define("filerepository",["cordova/filerepository"],returnFirstDependency)):(define("transfermanager",[apiClientBowerPath+"/sync/transfermanager"],returnFirstDependency),define("filerepository",[apiClientBowerPath+"/sync/filerepository"],returnFirstDependency)),"android"===self.appMode?define("localsync",["cordova/localsync"],returnFirstDependency):define("localsync",[apiClientBowerPath+"/sync/localsync"],returnFirstDependency)}function getRequirePromise(deps){return new Promise(function(resolve,reject){require(deps,resolve)})}function init(){"android"===self.appMode&&define("nativedirectorychooser",["cordova/nativedirectorychooser"],returnFirstDependency),define("livetvcss",["css!css/livetv.css"],returnFirstDependency),define("detailtablecss",["css!css/detailtable.css"],returnFirstDependency),define("buttonenabled",["legacy/buttonenabled"],returnFirstDependency);var list=[];window.fetch||list.push("fetch"),"function"!=typeof Object.assign&&list.push("objectassign"),Array.prototype.filter||list.push("arraypolyfills"),Function.prototype.bind||list.push("functionbind"),window.requestAnimationFrame||list.push("raf"),require(list,function(){createConnectionManager().then(function(){console.log("initAfterDependencies promises resolved"),require(["globalize","browser"],function(globalize,browser){window.Globalize=globalize,Promise.all([loadCoreDictionary(globalize),loadSharedComponentsDictionary(globalize)]).then(function(){onGlobalizeInit(browser)})})})})}function loadSharedComponentsDictionary(globalize){var languages=["ar","be-by","bg-bg","ca","cs","da","de","el","en-gb","en-us","es-ar","es-mx","es","fi","fr","gsw","he","hr","hu","id","it","kk","ko","lt-lt","ms","nb","nl","pl","pt-br","pt-pt","ro","ru","sk","sl-si","sv","tr","uk","vi","zh-cn","zh-hk","zh-tw"],translations=languages.map(function(i){return{lang:i,path:"bower_components/emby-webcomponents/strings/"+i+".json"}});globalize.loadStrings({name:"sharedcomponents",translations:translations})}function loadCoreDictionary(globalize){var languages=["ar","be-BY","bg-BG","ca","cs","da","de","el","en-GB","en-US","es","es-AR","es-MX","fa","fi","fr","fr-CA","gsw","he","hi-IN","hr","hu","id","it","kk","ko","lt-LT","ms","nb","nl","pl","pt-BR","pt-PT","ro","ru","sk","sl-SI","sv","tr","uk","vi","zh-CN","zh-HK","zh-TW"],translations=languages.map(function(i){return{lang:i,path:"strings/"+i+".json"}});return globalize.defaultModule("core"),globalize.loadStrings({name:"core",translations:translations})}function onGlobalizeInit(browser){if("android"===self.appMode){if(-1!==self.location.href.toString().toLowerCase().indexOf("start=backgroundsync"))return onAppReady(browser)}document.title=Globalize.translateDocument(document.title,"core");var deps=["apphost"];browser.tv&&!browser.android?(console.log("Using system fonts with explicit sizes"),deps.push("systemFontsSizedCss")):(console.log("Using default fonts"),deps.push("systemFontsCss")),deps.push("css!css/librarybrowser"),require(deps,function(appHost){loadPlugins([],appHost,browser).then(function(){onAppReady(browser)})})}function defineRoute(newRoute,dictionary){var baseRoute=Emby.Page.baseUrl(),path=newRoute.path;path=path.replace(baseRoute,""),console.log("Defining route: "+path),newRoute.dictionary=newRoute.dictionary||dictionary||"core",Emby.Page.addRoute(path,newRoute)}function defineCoreRoutes(appHost){console.log("Defining core routes"),defineRoute({path:"/addplugin.html",dependencies:[],autoFocus:!1,roles:"admin",controller:"scripts/addpluginpage"}),defineRoute({path:"/appservices.html",dependencies:[],autoFocus:!1,roles:"admin"}),defineRoute({path:"/autoorganizelog.html",dependencies:[],roles:"admin"}),defineRoute({path:"/channelsettings.html",dependencies:[],autoFocus:!1,roles:"admin"}),defineRoute({path:"/connectlogin.html",dependencies:["emby-button","emby-input"],autoFocus:!1,anonymous:!0,startup:!0,controller:"scripts/connectlogin"}),defineRoute({path:"/dashboard.html",dependencies:[],autoFocus:!1,roles:"admin",controller:"scripts/dashboardpage"}),defineRoute({path:"/dashboardgeneral.html",controller:"dashboard/dashboardgeneral",autoFocus:!1,roles:"admin"}),defineRoute({path:"/dashboardhosting.html",dependencies:["emby-input","emby-button"],autoFocus:!1,roles:"admin",controller:"dashboard/dashboardhosting"}),defineRoute({path:"/devices/devices.html",dependencies:[],autoFocus:!1,roles:"admin",controller:"devices/devices"}),defineRoute({path:"/devices/device.html",dependencies:[],autoFocus:!1,roles:"admin",controller:"devices/device"}),defineRoute({path:"/devicesupload.html",dependencies:[],autoFocus:!1,roles:"admin"}),defineRoute({path:"/dlnaprofile.html",dependencies:[],autoFocus:!1,roles:"admin"}),defineRoute({path:"/dlnaprofiles.html",dependencies:[],autoFocus:!1,roles:"admin"}),defineRoute({path:"/dlnaserversettings.html",dependencies:[],autoFocus:!1,roles:"admin"}),defineRoute({path:"/dlnasettings.html",dependencies:[],autoFocus:!1,roles:"admin"}),defineRoute({path:"/edititemmetadata.html",dependencies:[],controller:"scripts/edititemmetadata",autoFocus:!1}),defineRoute({path:"/encodingsettings.html",dependencies:[],autoFocus:!1,roles:"admin"}),defineRoute({path:"/forgotpassword.html",dependencies:["emby-input","emby-button"],anonymous:!0,startup:!0,controller:"scripts/forgotpassword"}),defineRoute({path:"/forgotpasswordpin.html",dependencies:["emby-input","emby-button"],autoFocus:!1,anonymous:!0,startup:!0,controller:"scripts/forgotpasswordpin"}),defineRoute({path:"/home.html",dependencies:[],autoFocus:!1,controller:"home/home",transition:"fade",type:"home"}),defineRoute({path:"/list/list.html",dependencies:[],autoFocus:!1,controller:"list/list",transition:"fade"}),defineRoute({path:"/index.html",dependencies:[],autoFocus:!1,isDefaultRoute:!0}),defineRoute({path:"/itemdetails.html",dependencies:["emby-button","scripts/livetvcomponents","paper-icon-button-light","emby-itemscontainer"],controller:"scripts/itemdetailpage",autoFocus:!1,transition:"fade"}),defineRoute({path:"/library.html",dependencies:[],autoFocus:!1,roles:"admin"}),defineRoute({path:"/librarydisplay.html",dependencies:[],autoFocus:!1,roles:"admin",controller:"dashboard/librarydisplay"}),defineRoute({path:"/librarysettings.html",dependencies:["emby-collapse","emby-input","emby-button","emby-select"],autoFocus:!1,roles:"admin",controller:"dashboard/librarysettings"}),defineRoute({path:"/livetv.html",dependencies:["emby-button","livetvcss"],controller:"scripts/livetvsuggested",autoFocus:!1,transition:"fade"}),defineRoute({path:"/livetvguideprovider.html",dependencies:[],autoFocus:!1,roles:"admin"}),defineRoute({path:"/livetvseriestimer.html",dependencies:["emby-checkbox","emby-input","emby-button","emby-collapse","scripts/livetvcomponents","scripts/livetvseriestimer","livetvcss"],autoFocus:!1,controller:"scripts/livetvseriestimer"}),defineRoute({path:"/livetvsettings.html",dependencies:[],autoFocus:!1}),defineRoute({path:"/livetvstatus.html",dependencies:[],autoFocus:!1,roles:"admin"}),defineRoute({path:"/livetvtuner.html",dependencies:[],autoFocus:!1,roles:"admin",controller:"dashboard/livetvtuner"}),defineRoute({path:"/log.html",dependencies:["emby-checkbox"],roles:"admin",controller:"dashboard/logpage"}),defineRoute({path:"/login.html",dependencies:["emby-button","emby-input"],autoFocus:!1,anonymous:!0,startup:!0,controller:"scripts/loginpage"}),defineRoute({path:"/metadataadvanced.html",dependencies:[],autoFocus:!1,roles:"admin"}),defineRoute({path:"/metadataimages.html",dependencies:[],autoFocus:!1,roles:"admin"}),defineRoute({path:"/metadatanfo.html",dependencies:[],autoFocus:!1,roles:"admin"}),defineRoute({path:"/movies.html",dependencies:["emby-button"],autoFocus:!1,controller:"scripts/moviesrecommended",transition:"fade"}),defineRoute({path:"/music.html",dependencies:[],controller:"scripts/musicrecommended",autoFocus:!1,transition:"fade"}),defineRoute({path:"/mypreferencesdisplay.html",dependencies:["emby-checkbox","emby-button","emby-select"],autoFocus:!1,transition:"fade",controller:"scripts/mypreferencesdisplay"}),defineRoute({path:"/mypreferenceshome.html",dependencies:[],autoFocus:!1,transition:"fade",controller:"scripts/mypreferenceshome"}),defineRoute({path:"/mypreferencessubtitles.html",dependencies:[],autoFocus:!1,transition:"fade",controller:"scripts/mypreferencessubtitles"}),defineRoute({path:"/mypreferenceslanguages.html",dependencies:["emby-button","emby-checkbox","emby-select"],autoFocus:!1,transition:"fade",controller:"scripts/mypreferenceslanguages"}),defineRoute({path:"/mypreferencesmenu.html",dependencies:["emby-button"],autoFocus:!1,transition:"fade",controller:"scripts/mypreferencescommon"}),defineRoute({path:"/myprofile.html",dependencies:["emby-button","emby-collapse","emby-checkbox","emby-input"],autoFocus:!1,transition:"fade",controller:"scripts/myprofile"}),defineRoute({path:"/offline/offline.html",transition:"fade",controller:"offline/offline",dependencies:[],anonymous:!0,startup:!1}),defineRoute({path:"/managedownloads.html",transition:"fade",controller:"scripts/managedownloads",dependencies:[]}),defineRoute({path:"/mysync.html",dependencies:[],autoFocus:!1,transition:"fade",controller:"scripts/mysync"}),defineRoute({path:"/camerauploadsettings.html",dependencies:[],autoFocus:!1,transition:"fade",controller:"scripts/camerauploadsettings"}),defineRoute({path:"/mysyncjob.html",dependencies:[],autoFocus:!1,transition:"fade",controller:"scripts/syncjob"}),defineRoute({path:"/mysyncsettings.html",dependencies:["emby-checkbox","emby-input","emby-button","paper-icon-button-light"],autoFocus:!1,transition:"fade",controller:"scripts/mysyncsettings"}),defineRoute({path:"/notificationsetting.html",dependencies:[],autoFocus:!1,roles:"admin"}),defineRoute({path:"/notificationsettings.html",controller:"scripts/notificationsettings",dependencies:[],autoFocus:!1,roles:"admin"}),defineRoute({path:"/nowplaying.html",dependencies:["paper-icon-button-light","emby-slider","emby-button","emby-input","emby-itemscontainer"],controller:"scripts/nowplayingpage",autoFocus:!1,transition:"fade",fullscreen:!0,supportsThemeMedia:!0,enableMediaControl:!1}),defineRoute({path:"/playbackconfiguration.html",dependencies:[],autoFocus:!1,roles:"admin"}),defineRoute({path:"/plugincatalog.html",dependencies:[],autoFocus:!1,roles:"admin",controller:"scripts/plugincatalogpage"}),defineRoute({path:"/plugins.html",dependencies:[],autoFocus:!1,roles:"admin"}),defineRoute({path:"/scheduledtask.html",dependencies:[],autoFocus:!1,roles:"admin",controller:"scripts/scheduledtaskpage"}),defineRoute({path:"/scheduledtasks.html",dependencies:[],autoFocus:!1,roles:"admin",controller:"scripts/scheduledtaskspage"}),defineRoute({path:"/search.html",dependencies:[],controller:"scripts/searchpage"}),defineRoute({path:"/selectserver.html",dependencies:["listViewStyle","emby-button"],autoFocus:!1,anonymous:!0,startup:!0,controller:"scripts/selectserver"}),defineRoute({path:"/serveractivity.html",dependencies:[],autoFocus:!1,roles:"admin",controller:"dashboard/serveractivity"}),defineRoute({path:"/serversecurity.html",dependencies:[],autoFocus:!1,roles:"admin"}),defineRoute({path:"/streamingsettings.html",dependencies:[],autoFocus:!1,roles:"admin"}),defineRoute({path:"/support.html",dependencies:[],autoFocus:!1,roles:"admin"}),defineRoute({path:"/supporterkey.html",dependencies:[],controller:"scripts/supporterkeypage",autoFocus:!1,roles:"admin"}),defineRoute({path:"/syncactivity.html",dependencies:[],autoFocus:!1,controller:"scripts/syncactivity"}),defineRoute({path:"/syncsettings.html",dependencies:[],autoFocus:!1}),defineRoute({path:"/tv.html",dependencies:["paper-icon-button-light","emby-button"],autoFocus:!1,controller:"scripts/tvrecommended",transition:"fade"}),defineRoute({path:"/useredit.html",dependencies:[],autoFocus:!1,roles:"admin"}),defineRoute({path:"/userlibraryaccess.html",dependencies:[],autoFocus:!1,roles:"admin"}),defineRoute({path:"/usernew.html",dependencies:[],autoFocus:!1,roles:"admin"}),defineRoute({path:"/userparentalcontrol.html",dependencies:[],autoFocus:!1,roles:"admin"}),defineRoute({path:"/userpassword.html",dependencies:["emby-input","emby-button","emby-checkbox"],autoFocus:!1,controller:"scripts/userpasswordpage"}),defineRoute({path:"/userprofiles.html",dependencies:[],autoFocus:!1,roles:"admin"}),defineRoute({path:"/wizardagreement.html",dependencies:["dashboardcss"],autoFocus:!1,anonymous:!0,controller:"scripts/wizardagreement"}),defineRoute({path:"/wizardremoteaccess.html",dependencies:["dashboardcss"],autoFocus:!1,anonymous:!0,controller:"dashboard/wizardremoteaccess"}),defineRoute({path:"/wizardfinish.html",dependencies:["emby-button","dashboardcss"],autoFocus:!1,anonymous:!0,controller:"dashboard/wizardfinishpage"}),defineRoute({path:"/wizardlibrary.html",dependencies:["dashboardcss"],autoFocus:!1,anonymous:!0}),defineRoute({path:"/wizardsettings.html",dependencies:["dashboardcss"],autoFocus:!1,anonymous:!0,controller:"dashboard/wizardsettings"}),defineRoute({path:"/wizardstart.html",dependencies:["dashboardcss"],autoFocus:!1,anonymous:!0,controller:"dashboard/wizardstart"}),defineRoute({path:"/wizarduser.html",dependencies:["dashboardcss","emby-input"],controller:"scripts/wizarduserpage",autoFocus:!1,anonymous:!0}),defineRoute({path:"/videoosd.html",dependencies:[],transition:"fade",controller:"scripts/videoosd",autoFocus:!1,type:"video-osd",supportsThemeMedia:!0,fullscreen:!0,enableMediaControl:!1}),defineRoute(Dashboard.isConnectMode()?{path:"/configurationpageext",dependencies:[],autoFocus:!1,enableCache:!1,enableContentQueryString:!0,roles:"admin",contentPath:getPluginPageContentPath}:{path:"/configurationpage",dependencies:[],autoFocus:!1,enableCache:!1,enableContentQueryString:!0,roles:"admin"}),defineRoute({path:"/",isDefaultRoute:!0,autoFocus:!1,dependencies:[]})}function getPluginPageContentPath(){return window.ApiClient?ApiClient.getUrl("web/ConfigurationPage"):null}function loadPlugins(externalPlugins,appHost,browser,shell){console.log("Loading installed plugins");var list=["bower_components/emby-webcomponents/playback/playbackvalidation","bower_components/emby-webcomponents/playback/playaccessvalidation","bower_components/emby-webcomponents/playback/experimentalwarnings"];"android"===self.appMode?self.MainActivity&&MainActivity.enableVlcPlayer()&&list.push("cordova/vlcplayer"):"cordova"===self.appMode&&(list.push("cordova/audioplayer"),(browser.iOSVersion||0)>=11&&list.push("cordova/mpvplayer")),list.push("bower_components/emby-webcomponents/htmlaudioplayer/plugin"),"cordova"===self.appMode&&list.push("cordova/chromecast"),"android"===self.appMode&&list.push("cordova/externalplayer"),list.push("bower_components/emby-webcomponents/htmlvideoplayer/plugin"),list.push("bower_components/emby-webcomponents/photoplayer/plugin"),appHost.supports("remotecontrol")&&(list.push("bower_components/emby-webcomponents/sessionplayer"),(browser.chrome||browser.opera)&&list.push("bower_components/emby-webcomponents/chromecast/chromecastplayer")),list.push("bower_components/emby-webcomponents/youtubeplayer/plugin");for(var i=0,length=externalPlugins.length;i= 11 && list.push("cordova/mpvplayer")), list.push("bower_components/emby-webcomponents/htmlaudioplayer/plugin"), "cordova" === self.appMode && list.push("cordova/chromecast"), "android" === self.appMode && list.push("cordova/externalplayer"), list.push("bower_components/emby-webcomponents/htmlvideoplayer/plugin"), list.push("bower_components/emby-webcomponents/photoplayer/plugin"), appHost.supports("remotecontrol") && (list.push("bower_components/emby-webcomponents/sessionplayer"), (browser.chrome || browser.opera) && list.push("bower_components/emby-webcomponents/chromecast/chromecastplayer")), list.push("bower_components/emby-webcomponents/youtubeplayer/plugin"); + for (var i = 0, length = externalPlugins.length; i < length; i++) list.push(externalPlugins[i]); + return new Promise(function(resolve, reject) { + Promise.all(list.map(loadPlugin)).then(function() { + require(["packageManager"], function(packageManager) { + packageManager.init().then(resolve, reject) + }) + }, reject) + }) + } + + function loadPlugin(url) { + return new Promise(function(resolve, reject) { + require(["pluginManager"], function(pluginManager) { + pluginManager.loadPlugin(url).then(resolve, reject) + }) + }) + } + + function enableNativeGamepadKeyMapping() { + return !(!window.navigator || "string" != typeof window.navigator.gamepadInputEmulation) && (window.navigator.gamepadInputEmulation = "keyboard", !0) + } + + function isGamepadSupported() { + return "ongamepadconnected" in window || navigator.getGamepads || navigator.webkitGetGamepads + } + + function onAppReady(browser) { + console.log("Begin onAppReady"); + var deps = [], + isBackgroundSync = -1 !== self.location.href.toString().toLowerCase().indexOf("start=backgroundsync"), + isInBackground = isBackgroundSync; + deps.push("apphost"), isInBackground || (deps.push("appRouter"), deps.push("scripts/themeloader"), browser.iOS && deps.push("css!devices/ios/ios.css"), "cordova" !== self.appMode && "android" !== self.appMode || deps.push("registrationServices"), deps.push("libraryMenu")), console.log("onAppReady - loading dependencies"), require(deps, function(appHost, pageObjects) { + if (console.log("Loaded dependencies in onAppReady"), window.Emby = {}, isBackgroundSync) return void syncNow(); + window.Emby.Page = pageObjects, defineCoreRoutes(appHost), Emby.Page.start({ + click: !1, + hashbang: !0 + }); + var postInitDependencies = []; + !enableNativeGamepadKeyMapping() && isGamepadSupported() && postInitDependencies.push("bower_components/emby-webcomponents/input/gamepadtokey"), postInitDependencies.push("bower_components/emby-webcomponents/thememediaplayer"), postInitDependencies.push("scripts/autobackdrops"), "cordova" !== self.appMode && "android" !== self.appMode || (browser.android ? (postInitDependencies.push("cordova/mediasession"), postInitDependencies.push("cordova/chromecast"), postInitDependencies.push("cordova/appshortcuts")) : browser.safari && (postInitDependencies.push("cordova/mediasession"), postInitDependencies.push("cordova/volume"), postInitDependencies.push("cordova/statusbar"), postInitDependencies.push("cordova/backgroundfetch"))), browser.tv || browser.xboxOne || browser.ps4 || postInitDependencies.push("bower_components/emby-webcomponents/nowplayingbar/nowplayingbar"), appHost.supports("remotecontrol") && (postInitDependencies.push("playerSelectionMenu"), postInitDependencies.push("bower_components/emby-webcomponents/playback/remotecontrolautoplay")), appHost.supports("physicalvolumecontrol") && !browser.touch || browser.edge || postInitDependencies.push("bower_components/emby-webcomponents/playback/volumeosd"), navigator.mediaSession && postInitDependencies.push("mediaSession"), postInitDependencies.push("apiInput"), postInitDependencies.push("mouseManager"), browser.tv || browser.xboxOne || (postInitDependencies.push("bower_components/emby-webcomponents/playback/playbackorientation"), registerServiceWorker(), window.Notification && postInitDependencies.push("bower_components/emby-webcomponents/notifications/notifications")), postInitDependencies.push("playerSelectionMenu"), appHost.supports("fullscreenchange") && (browser.edgeUwp || -1 !== navigator.userAgent.toLowerCase().indexOf("electron")) && require(["fullscreen-doubleclick"]), require(postInitDependencies), appHost.supports("sync") && initLocalSyncEvents(), Dashboard.isConnectMode() || window.ApiClient && require(["css!" + ApiClient.getUrl("Branding/Css")]) + }) + } + + function registerServiceWorker() { + if (navigator.serviceWorker && "cordova" !== self.appMode && "android" !== self.appMode) try { + navigator.serviceWorker.register("serviceworker.js").then(function() { + return navigator.serviceWorker.ready + }).then(function(reg) { + if (reg && reg.sync) return reg.sync.register("emby-sync").then(function() { + window.SyncRegistered = Dashboard.isConnectMode() + }) + }) + } catch (err) { + console.log("Error registering serviceWorker: " + err) + } + } + + function syncNow() { + require(["localsync"], function(localSync) { + localSync.sync() + }) + } + + function initLocalSyncEvents() { + require(["serverNotifications", "events"], function(serverNotifications, events) { + events.on(serverNotifications, "SyncJobItemReady", syncNow), events.on(serverNotifications, "SyncJobCancelled", syncNow), events.on(serverNotifications, "SyncJobItemCancelled", syncNow) + }) + } + + function onWebComponentsReady(browser) { + var initialDependencies = []; + window.Promise && !browser.web0s || initialDependencies.push("bower_components/emby-webcomponents/native-promise-only/lib/npo.src"), initRequireWithBrowser(browser), "cordova" !== self.appMode && "android" !== self.appMode || (AppInfo.isNativeApp = !0), require(initialDependencies, init) + } + var localApiClient; + ! function() { + var urlArgs = "v=" + (window.dashboardVersion || (new Date).getDate()), + bowerPath = getBowerPath(), + apiClientBowerPath = bowerPath + "/emby-apiclient", + embyWebComponentsBowerPath = bowerPath + "/emby-webcomponents", + paths = { + velocity: bowerPath + "/velocity/velocity.min", + vibrant: bowerPath + "/vibrant/dist/vibrant", + staticBackdrops: embyWebComponentsBowerPath + "/staticbackdrops", + ironCardList: "components/ironcardlist/ironcardlist", + scrollThreshold: "components/scrollthreshold", + playlisteditor: "components/playlisteditor/playlisteditor", + medialibrarycreator: "components/medialibrarycreator/medialibrarycreator", + medialibraryeditor: "components/medialibraryeditor/medialibraryeditor", + imageoptionseditor: "components/imageoptionseditor/imageoptionseditor", + howler: bowerPath + "/howlerjs/dist/howler.min", + sortable: bowerPath + "/Sortable/Sortable.min", + isMobile: bowerPath + "/isMobile/isMobile.min", + masonry: bowerPath + "/masonry/dist/masonry.pkgd.min", + humanedate: "components/humanedate", + libraryBrowser: "scripts/librarybrowser", + events: apiClientBowerPath + "/events", + credentialprovider: apiClientBowerPath + "/credentials", + connectionManagerFactory: bowerPath + "/emby-apiclient/connectionmanager", + visibleinviewport: embyWebComponentsBowerPath + "/visibleinviewport", + browserdeviceprofile: embyWebComponentsBowerPath + "/browserdeviceprofile", + browser: embyWebComponentsBowerPath + "/browser", + inputManager: embyWebComponentsBowerPath + "/inputmanager", + qualityoptions: embyWebComponentsBowerPath + "/qualityoptions", + hammer: bowerPath + "/hammerjs/hammer.min", + pageJs: embyWebComponentsBowerPath + "/pagejs/page", + focusManager: embyWebComponentsBowerPath + "/focusmanager", + datetime: embyWebComponentsBowerPath + "/datetime", + globalize: embyWebComponentsBowerPath + "/globalize", + itemHelper: embyWebComponentsBowerPath + "/itemhelper", + itemShortcuts: embyWebComponentsBowerPath + "/shortcuts", + playQueueManager: embyWebComponentsBowerPath + "/playback/playqueuemanager", + autoPlayDetect: embyWebComponentsBowerPath + "/playback/autoplaydetect", + nowPlayingHelper: embyWebComponentsBowerPath + "/playback/nowplayinghelper", + pluginManager: embyWebComponentsBowerPath + "/pluginmanager", + packageManager: embyWebComponentsBowerPath + "/packagemanager" + }; + paths.hlsjs = bowerPath + "/hlsjs/dist/hls.min", paths.flvjs = embyWebComponentsBowerPath + "/flvjs/flv.min", paths.shaka = embyWebComponentsBowerPath + "/shaka/shaka-player.compiled", define("chromecastHelper", [embyWebComponentsBowerPath + "/chromecast/chromecasthelpers"], returnFirstDependency), define("mediaSession", [embyWebComponentsBowerPath + "/playback/mediasession"], returnFirstDependency), define("webActionSheet", [embyWebComponentsBowerPath + "/actionsheet/actionsheet"], returnFirstDependency), define("libjass", [bowerPath + "/libjass/libjass.min", "css!" + bowerPath + "/libjass/libjass"], returnFirstDependency), define("tunerPicker", ["components/tunerpicker"], returnFirstDependency), define("mainTabsManager", [embyWebComponentsBowerPath + "/maintabsmanager"], returnFirstDependency), define("imageLoader", [embyWebComponentsBowerPath + "/images/imagehelper"], returnFirstDependency), define("appFooter", [embyWebComponentsBowerPath + "/appfooter/appfooter"], returnFirstDependency), define("directorybrowser", ["components/directorybrowser/directorybrowser"], returnFirstDependency), define("metadataEditor", [embyWebComponentsBowerPath + "/metadataeditor/metadataeditor"], returnFirstDependency), define("personEditor", [embyWebComponentsBowerPath + "/metadataeditor/personeditor"], returnFirstDependency), define("playerSelectionMenu", [embyWebComponentsBowerPath + "/playback/playerselection"], returnFirstDependency), define("playerSettingsMenu", [embyWebComponentsBowerPath + "/playback/playersettingsmenu"], returnFirstDependency), define("playMethodHelper", [embyWebComponentsBowerPath + "/playback/playmethodhelper"], returnFirstDependency), define("brightnessOsd", [embyWebComponentsBowerPath + "/playback/brightnessosd"], returnFirstDependency), define("libraryMenu", ["scripts/librarymenu"], returnFirstDependency), define("emby-collapse", [embyWebComponentsBowerPath + "/emby-collapse/emby-collapse"], returnFirstDependency), define("emby-button", [embyWebComponentsBowerPath + "/emby-button/emby-button"], returnFirstDependency), define("emby-linkbutton", ["emby-button"], returnFirstDependency), define("emby-itemscontainer", [embyWebComponentsBowerPath + "/emby-itemscontainer/emby-itemscontainer"], returnFirstDependency), define("alphaNumericShortcuts", [embyWebComponentsBowerPath + "/alphanumericshortcuts/alphanumericshortcuts"], returnFirstDependency), define("emby-scroller", [embyWebComponentsBowerPath + "/emby-scroller/emby-scroller"], returnFirstDependency), define("emby-tabs", [embyWebComponentsBowerPath + "/emby-tabs/emby-tabs"], returnFirstDependency), define("emby-scrollbuttons", [embyWebComponentsBowerPath + "/emby-scrollbuttons/emby-scrollbuttons"], returnFirstDependency), define("emby-progressring", [embyWebComponentsBowerPath + "/emby-progressring/emby-progressring"], returnFirstDependency), define("emby-itemrefreshindicator", [embyWebComponentsBowerPath + "/emby-itemrefreshindicator/emby-itemrefreshindicator"], returnFirstDependency), define("multiSelect", [embyWebComponentsBowerPath + "/multiselect/multiselect"], returnFirstDependency), define("alphaPicker", [embyWebComponentsBowerPath + "/alphapicker/alphapicker"], returnFirstDependency), define("paper-icon-button-light", [embyWebComponentsBowerPath + "/emby-button/paper-icon-button-light"], returnFirstDependency), define("tabbedView", [embyWebComponentsBowerPath + "/tabbedview/tabbedview"], returnFirstDependency), define("itemsTab", [embyWebComponentsBowerPath + "/tabbedview/itemstab"], returnFirstDependency), define("connectHelper", [embyWebComponentsBowerPath + "/emby-connect/connecthelper"], returnFirstDependency), define("emby-input", [embyWebComponentsBowerPath + "/emby-input/emby-input"], returnFirstDependency), define("emby-select", [embyWebComponentsBowerPath + "/emby-select/emby-select"], returnFirstDependency), define("emby-slider", [embyWebComponentsBowerPath + "/emby-slider/emby-slider"], returnFirstDependency), define("emby-checkbox", [embyWebComponentsBowerPath + "/emby-checkbox/emby-checkbox"], returnFirstDependency), define("emby-toggle", [embyWebComponentsBowerPath + "/emby-toggle/emby-toggle"], returnFirstDependency), define("emby-radio", [embyWebComponentsBowerPath + "/emby-radio/emby-radio"], returnFirstDependency), define("emby-textarea", [embyWebComponentsBowerPath + "/emby-textarea/emby-textarea"], returnFirstDependency), define("collectionEditor", [embyWebComponentsBowerPath + "/collectioneditor/collectioneditor"], returnFirstDependency), define("serverRestartDialog", [embyWebComponentsBowerPath + "/serverrestartdialog/serverrestartdialog"], returnFirstDependency), define("playlistEditor", [embyWebComponentsBowerPath + "/playlisteditor/playlisteditor"], returnFirstDependency), define("recordingCreator", [embyWebComponentsBowerPath + "/recordingcreator/recordingcreator"], returnFirstDependency), define("recordingEditor", [embyWebComponentsBowerPath + "/recordingcreator/recordingeditor"], returnFirstDependency), define("seriesRecordingEditor", [embyWebComponentsBowerPath + "/recordingcreator/seriesrecordingeditor"], returnFirstDependency), define("recordingFields", [embyWebComponentsBowerPath + "/recordingcreator/recordingfields"], returnFirstDependency), define("recordingButton", [embyWebComponentsBowerPath + "/recordingcreator/recordingbutton"], returnFirstDependency), define("recordingHelper", [embyWebComponentsBowerPath + "/recordingcreator/recordinghelper"], returnFirstDependency), define("subtitleEditor", [embyWebComponentsBowerPath + "/subtitleeditor/subtitleeditor"], returnFirstDependency), define("itemIdentifier", [embyWebComponentsBowerPath + "/itemidentifier/itemidentifier"], returnFirstDependency), define("mediaInfo", [embyWebComponentsBowerPath + "/mediainfo/mediainfo"], returnFirstDependency), define("itemContextMenu", [embyWebComponentsBowerPath + "/itemcontextmenu"], returnFirstDependency), define("imageEditor", [embyWebComponentsBowerPath + "/imageeditor/imageeditor"], returnFirstDependency), define("imageDownloader", [embyWebComponentsBowerPath + "/imagedownloader/imagedownloader"], returnFirstDependency), define("dom", [embyWebComponentsBowerPath + "/dom"], returnFirstDependency), define("playerStats", [embyWebComponentsBowerPath + "/playerstats/playerstats"], returnFirstDependency), define("searchFields", [embyWebComponentsBowerPath + "/search/searchfields"], returnFirstDependency), define("searchResults", [embyWebComponentsBowerPath + "/search/searchresults"], returnFirstDependency), define("upNextDialog", [embyWebComponentsBowerPath + "/upnextdialog/upnextdialog"], returnFirstDependency), define("fullscreen-doubleclick", [embyWebComponentsBowerPath + "/fullscreen/fullscreen-dc"], returnFirstDependency), define("fullscreenManager", [embyWebComponentsBowerPath + "/fullscreen/fullscreenmanager", "events"], returnFirstDependency), define("headroom", [embyWebComponentsBowerPath + "/headroom/headroom"], returnFirstDependency), define("subtitleAppearanceHelper", [embyWebComponentsBowerPath + "/subtitlesettings/subtitleappearancehelper"], returnFirstDependency), define("subtitleSettings", [embyWebComponentsBowerPath + "/subtitlesettings/subtitlesettings"], returnFirstDependency), define("displaySettings", [embyWebComponentsBowerPath + "/displaysettings/displaysettings"], returnFirstDependency), define("playbackSettings", [embyWebComponentsBowerPath + "/playbacksettings/playbacksettings"], returnFirstDependency), define("homescreenSettings", [embyWebComponentsBowerPath + "/homescreensettings/homescreensettings"], returnFirstDependency), define("homescreenSettingsDialog", [embyWebComponentsBowerPath + "/homescreensettings/homescreensettingsdialog"], returnFirstDependency), define("playbackManager", [embyWebComponentsBowerPath + "/playback/playbackmanager"], getPlaybackManager), define("layoutManager", [embyWebComponentsBowerPath + "/layoutmanager", "apphost"], getLayoutManager), define("homeSections", [embyWebComponentsBowerPath + "/homesections/homesections"], returnFirstDependency), define("playMenu", [embyWebComponentsBowerPath + "/playmenu"], returnFirstDependency), define("refreshDialog", [embyWebComponentsBowerPath + "/refreshdialog/refreshdialog"], returnFirstDependency), define("backdrop", [embyWebComponentsBowerPath + "/backdrop/backdrop"], returnFirstDependency), define("fetchHelper", [embyWebComponentsBowerPath + "/fetchhelper"], returnFirstDependency), define("roundCardStyle", ["cardStyle", "css!" + embyWebComponentsBowerPath + "/cardbuilder/roundcard"], returnFirstDependency), define("cardStyle", ["css!" + embyWebComponentsBowerPath + "/cardbuilder/card"], returnFirstDependency), define("cardBuilder", [embyWebComponentsBowerPath + "/cardbuilder/cardbuilder"], returnFirstDependency), define("peoplecardbuilder", [embyWebComponentsBowerPath + "/cardbuilder/peoplecardbuilder"], returnFirstDependency), define("chaptercardbuilder", [embyWebComponentsBowerPath + "/cardbuilder/chaptercardbuilder"], returnFirstDependency), define("mouseManager", [embyWebComponentsBowerPath + "/input/mouse"], returnFirstDependency), define("flexStyles", ["css!" + embyWebComponentsBowerPath + "/flexstyles"], returnFirstDependency), define("deleteHelper", [embyWebComponentsBowerPath + "/deletehelper"], returnFirstDependency), define("tvguide", [embyWebComponentsBowerPath + "/guide/guide"], returnFirstDependency), define("programStyles", ["css!" + embyWebComponentsBowerPath + "/guide/programs"], returnFirstDependency), define("guide-settings-dialog", [embyWebComponentsBowerPath + "/guide/guide-settings"], returnFirstDependency), define("loadingDialog", [embyWebComponentsBowerPath + "/loadingdialog/loadingdialog"], returnFirstDependency), define("syncDialog", [embyWebComponentsBowerPath + "/sync/sync"], returnFirstDependency), define("syncJobEditor", [embyWebComponentsBowerPath + "/sync/syncjobeditor"], returnFirstDependency), define("syncJobList", [embyWebComponentsBowerPath + "/sync/syncjoblist"], returnFirstDependency), define("viewManager", [embyWebComponentsBowerPath + "/viewmanager/viewmanager"], function(viewManager) { + return window.ViewManager = viewManager, viewManager.dispatchPageEvents(!0), viewManager + }), "cordova" === self.appMode || "android" === self.appMode ? paths.apphost = "cordova/apphost" : paths.apphost = "components/apphost", paths.appStorage = getAppStorage(apiClientBowerPath), requirejs.config({ + waitSeconds: 0, + map: { + "*": { + css: bowerPath + "/emby-webcomponents/require/requirecss", + text: bowerPath + "/emby-webcomponents/require/requiretext" + } + }, + urlArgs: urlArgs, + paths: paths, + onError: onRequireJsError + }), requirejs.onError = onRequireJsError, define("jstree", ["thirdparty/jstree/jstree", "css!thirdparty/jstree/themes/default/style.css"], returnFirstDependency), define("dashboardcss", ["css!css/dashboard"], returnFirstDependency), define("slideshow", [embyWebComponentsBowerPath + "/slideshow/slideshow"], returnFirstDependency), define("fetch", [bowerPath + "/fetch/fetch"], returnFirstDependency), define("raf", [embyWebComponentsBowerPath + "/polyfills/raf"], returnFirstDependency), define("functionbind", [embyWebComponentsBowerPath + "/polyfills/bind"], returnFirstDependency), define("arraypolyfills", [embyWebComponentsBowerPath + "/polyfills/array"], returnFirstDependency), define("objectassign", [embyWebComponentsBowerPath + "/polyfills/objectassign"], returnFirstDependency), define("clearButtonStyle", ["css!" + embyWebComponentsBowerPath + "/clearbutton"], returnFirstDependency), define("userdataButtons", [embyWebComponentsBowerPath + "/userdatabuttons/userdatabuttons"], returnFirstDependency), define("emby-playstatebutton", [embyWebComponentsBowerPath + "/userdatabuttons/emby-playstatebutton"], returnFirstDependency), define("emby-ratingbutton", [embyWebComponentsBowerPath + "/userdatabuttons/emby-ratingbutton"], returnFirstDependency), define("emby-downloadbutton", [embyWebComponentsBowerPath + "/sync/emby-downloadbutton"], returnFirstDependency), define("listView", [embyWebComponentsBowerPath + "/listview/listview"], returnFirstDependency), define("listViewStyle", ["css!" + embyWebComponentsBowerPath + "/listview/listview"], returnFirstDependency), define("formDialogStyle", ["css!" + embyWebComponentsBowerPath + "/formdialog"], returnFirstDependency), define("indicators", [embyWebComponentsBowerPath + "/indicators/indicators"], returnFirstDependency), define("viewSettings", [embyWebComponentsBowerPath + "/viewsettings/viewsettings"], returnFirstDependency), define("filterMenu", [embyWebComponentsBowerPath + "/filtermenu/filtermenu"], returnFirstDependency), define("sortMenu", [embyWebComponentsBowerPath + "/sortmenu/sortmenu"], returnFirstDependency), define("registrationServices", [embyWebComponentsBowerPath + "/registrationservices/registrationservices"], returnFirstDependency), "cordova" === self.appMode || "android" === self.appMode ? define("fileupload", ["cordova/fileupload"], returnFirstDependency) : define("fileupload", [apiClientBowerPath + "/fileupload"], returnFirstDependency), define("connectionmanager", [apiClientBowerPath + "/connectionmanager"]), define("contentuploader", [apiClientBowerPath + "/sync/contentuploader"], returnFirstDependency), define("serversync", [apiClientBowerPath + "/sync/serversync"], returnFirstDependency), define("multiserversync", [apiClientBowerPath + "/sync/multiserversync"], returnFirstDependency), define("mediasync", [apiClientBowerPath + "/sync/mediasync"], returnFirstDependency), define("idb", [embyWebComponentsBowerPath + "/idb"], returnFirstDependency), define("sanitizefilename", [embyWebComponentsBowerPath + "/sanitizefilename"], returnFirstDependency), define("itemrepository", [apiClientBowerPath + "/sync/itemrepository"], returnFirstDependency), define("useractionrepository", [apiClientBowerPath + "/sync/useractionrepository"], returnFirstDependency), define("swiper", [bowerPath + "/Swiper/dist/js/swiper.min", "css!" + bowerPath + "/Swiper/dist/css/swiper.min"], returnFirstDependency), define("scroller", [embyWebComponentsBowerPath + "/scroller/smoothscroller"], returnFirstDependency), define("toast", [embyWebComponentsBowerPath + "/toast/toast"], returnFirstDependency), define("scrollHelper", [embyWebComponentsBowerPath + "/scrollhelper"], returnFirstDependency), define("touchHelper", [embyWebComponentsBowerPath + "/touchhelper"], returnFirstDependency), define("appSettings", [embyWebComponentsBowerPath + "/appsettings"], returnFirstDependency), define("userSettings", [embyWebComponentsBowerPath + "/usersettings/usersettings"], returnFirstDependency), define("userSettingsBuilder", [embyWebComponentsBowerPath + "/usersettings/usersettingsbuilder", "layoutManager", "browser"], getSettingsBuilder), define("material-icons", ["css!" + embyWebComponentsBowerPath + "/fonts/material-icons/style"], returnFirstDependency), define("systemFontsCss", ["css!" + embyWebComponentsBowerPath + "/fonts/fonts"], returnFirstDependency), define("systemFontsSizedCss", ["css!" + embyWebComponentsBowerPath + "/fonts/fonts.sized"], returnFirstDependency), define("scrollStyles", ["css!" + embyWebComponentsBowerPath + "/scrollstyles"], returnFirstDependency), define("imageUploader", [embyWebComponentsBowerPath + "/imageuploader/imageuploader"], returnFirstDependency), define("navdrawer", ["components/navdrawer/navdrawer"], returnFirstDependency), define("htmlMediaHelper", [embyWebComponentsBowerPath + "/htmlvideoplayer/htmlmediahelper"], returnFirstDependency), define("viewcontainer", ["components/viewcontainer-lite", "css!" + embyWebComponentsBowerPath + "/viewmanager/viewcontainer-lite"], returnFirstDependency), define("queryString", [bowerPath + "/query-string/index"], function() { + return queryString + }), define("jQuery", [bowerPath + "/jquery/dist/jquery.slim.min"], function() { + return window.ApiClient && (jQuery.ajax = ApiClient.ajax), jQuery + }), define("fnchecked", ["legacy/fnchecked"], returnFirstDependency), define("dialogHelper", [embyWebComponentsBowerPath + "/dialoghelper/dialoghelper"], returnFirstDependency), define("inputmanager", ["inputManager"], returnFirstDependency), define("apiInput", [embyWebComponentsBowerPath + "/input/api"], returnFirstDependency), define("serverNotifications", ["apiInput"], returnFirstDependency), define("headroom-window", ["headroom"], createWindowHeadroom), define("appFooter-shared", ["appFooter"], createSharedAppFooter), define("skinManager", [embyWebComponentsBowerPath + "/skinmanager"], function(skinManager) { + return skinManager.loadUserSkin = function(options) { + require(["appRouter"], function(appRouter) { + options = options || {}, options.start ? appRouter.invokeShortcut(options.start) : appRouter.goHome() + }) + }, skinManager.getThemes = function() { + return [{ + name: "Apple TV", + id: "appletv" + }, { + name: "Blue Radiance", + id: "blueradiance" + }, { + name: "Dark", + id: "dark", + isDefault: !0 + }, { + name: "Dark (green accent)", + id: "dark-green" + }, { + name: "Dark (red accent)", + id: "dark-red" + }, { + name: "Halloween", + id: "halloween" + }, { + name: "Light", + id: "light", + isDefaultServerDashboard: !0 + }, { + name: "Light (blue accent)", + id: "light-blue" + }, { + name: "Light (green accent)", + id: "light-green" + }, { + name: "Light (pink accent)", + id: "light-pink" + }, { + name: "Light (purple accent)", + id: "light-purple" + }, { + name: "Light (red accent)", + id: "light-red" + }, { + name: "Windows Media Center", + id: "wmc" + }] + }, skinManager + }), define("connectionManager", [], function() { + return ConnectionManager + }), define("apiClientResolver", [], function() { + return function() { + return window.ApiClient + } + }), define("appRouter", [embyWebComponentsBowerPath + "/router", "itemHelper"], function(appRouter, itemHelper) { + function showItem(item, serverId, options) { + "string" == typeof item ? require(["connectionManager"], function(connectionManager) { + var apiClient = connectionManager.currentApiClient(); + apiClient.getItem(apiClient.getCurrentUserId(), item).then(function(item) { + appRouter.showItem(item, options) + }) + }) : (2 == arguments.length && (options = arguments[1]), appRouter.show("/" + appRouter.getRouteUrl(item, options), { + item: item + })) + } + return appRouter.showLocalLogin = function(serverId, manualLogin) { + Dashboard.navigate("login.html?serverid=" + serverId) + }, appRouter.showVideoOsd = function() { + return Dashboard.navigate("videoosd.html") + }, appRouter.showSelectServer = function() { + Dashboard.isConnectMode() ? Dashboard.navigate("selectserver.html") : Dashboard.navigate("login.html") + }, appRouter.showWelcome = function() { + Dashboard.isConnectMode() ? Dashboard.navigate("connectlogin.html?mode=welcome") : Dashboard.navigate("login.html") + }, appRouter.showConnectLogin = function() { + Dashboard.navigate("connectlogin.html") + }, appRouter.showSettings = function() { + Dashboard.navigate("mypreferencesmenu.html") + }, appRouter.showGuide = function() { + Dashboard.navigate("livetv.html?tab=1") + }, appRouter.goHome = function() { + Dashboard.navigate("home.html") + }, appRouter.showSearch = function() { + Dashboard.navigate("search.html") + }, appRouter.showLiveTV = function() { + Dashboard.navigate("livetv.html") + }, appRouter.showRecordedTV = function() { + Dashboard.navigate("livetv.html?tab=3") + }, appRouter.showFavorites = function() { + Dashboard.navigate("home.html?tab=1") + }, appRouter.showSettings = function() { + Dashboard.navigate("mypreferencesmenu.html") + }, appRouter.showNowPlaying = function() { + Dashboard.navigate("nowplaying.html") + }, appRouter.setTitle = function(title) { + LibraryMenu.setTitle(title) + }, appRouter.getRouteUrl = function(item, options) { + if (!item) throw new Error("item cannot be null"); + if (item.url) return item.url; + var context = options ? options.context : null, + id = item.Id || item.ItemId; + options || (options = {}); + var url, itemType = item.Type || (options ? options.itemType : null), + serverId = item.ServerId || options.serverId; + if ("settings" === item) return "mypreferencesmenu.html"; + if ("wizard" === item) return "wizardstart.html"; + if ("downloads" === item) return "offline/offline.html"; + if ("downloadsettings" === item) return "mysyncsettings.html"; + if ("premiere" === item) return "supporterkey.html"; + if ("managedownloads" === item) return "managedownloads.html"; + if ("manageserver" === item) return "dashboard.html"; + if ("recordedtv" === item) return "livetv.html?tab=3&serverId=" + options.serverId; + if ("nextup" === item) return "list/list.html?type=nextup&serverId=" + options.serverId; + if ("list" === item) { + var url = "list/list.html?serverId=" + options.serverId + "&type=" + options.itemTypes; + return options.isFavorite && (url += "&IsFavorite=true"), url + } + if ("livetv" === item) return "guide" === options.section ? "livetv.html?tab=1&serverId=" + options.serverId : "movies" === options.section ? "list/list.html?type=Programs&IsMovie=true&serverId=" + options.serverId : "shows" === options.section ? "list/list.html?type=Programs&IsSeries=true&IsMovie=false&IsNews=false&serverId=" + options.serverId : "sports" === options.section ? "list/list.html?type=Programs&IsSports=true&serverId=" + options.serverId : "kids" === options.section ? "list/list.html?type=Programs&IsKids=true&serverId=" + options.serverId : "news" === options.section ? "list/list.html?type=Programs&IsNews=true&serverId=" + options.serverId : "onnow" === options.section ? "list/list.html?type=Programs&IsAiring=true&serverId=" + options.serverId : "dvrschedule" === options.section ? "livetv.html?tab=4&serverId=" + options.serverId : "livetv.html?serverId=" + options.serverId; + if ("SeriesTimer" == itemType) return "itemdetails.html?seriesTimerId=" + id + "&serverId=" + serverId; + if ("livetv" == item.CollectionType) return "livetv.html"; + if ("Genre" === item.Type) return url = "list/list.html?genreId=" + item.Id + "&serverId=" + serverId, "livetv" === context && (url += "&type=Programs"), options.parentId && (url += "&parentId=" + options.parentId), url; + if ("GameGenre" === item.Type) return url = "list/list.html?gameGenreId=" + item.Id + "&serverId=" + serverId, options.parentId && (url += "&parentId=" + options.parentId), url; + if ("MusicGenre" === item.Type) return url = "list/list.html?musicGenreId=" + item.Id + "&serverId=" + serverId, options.parentId && (url += "&parentId=" + options.parentId), url; + if ("Studio" === item.Type) return url = "list/list.html?studioId=" + item.Id + "&serverId=" + serverId, options.parentId && (url += "&parentId=" + options.parentId), url; + if ("folders" !== context && !itemHelper.isLocalItem(item)) { + if ("movies" == item.CollectionType) return url = "movies.html?topParentId=" + item.Id, options && "latest" === options.section && (url += "&tab=1"), url; + if ("tvshows" == item.CollectionType) return url = "tv.html?topParentId=" + item.Id, options && "latest" === options.section && (url += "&tab=2"), url; + if ("music" == item.CollectionType) return "music.html?topParentId=" + item.Id + } + if ("Playlist" == itemType) return "itemdetails.html?id=" + id + "&serverId=" + serverId; + if ("TvChannel" == itemType) return "itemdetails.html?id=" + id + "&serverId=" + serverId; + if ("Program" == itemType) return "itemdetails.html?id=" + id + "&serverId=" + serverId; + if ("BoxSet" == itemType) return "itemdetails.html?id=" + id + "&serverId=" + serverId; + if ("MusicAlbum" == itemType) return "itemdetails.html?id=" + id + "&serverId=" + serverId; + if ("GameSystem" == itemType) return "itemdetails.html?id=" + id + "&serverId=" + serverId; + if ("MusicGenre" == itemType) return "itemdetails.html?id=" + id + "&serverId=" + serverId; + if ("Person" == itemType) return "itemdetails.html?id=" + id + "&serverId=" + serverId; + if ("Recording" == itemType) return "itemdetails.html?id=" + id + "&serverId=" + serverId; + if ("MusicArtist" == itemType) return "itemdetails.html?id=" + id + "&serverId=" + serverId; + var contextSuffix = context ? "&context=" + context : ""; + return "Series" == itemType || "Season" == itemType || "Episode" == itemType ? "itemdetails.html?id=" + id + contextSuffix + "&serverId=" + serverId : item.IsFolder ? id ? "list/list.html?parentId=" + id + "&serverId=" + serverId : "#" : "itemdetails.html?id=" + id + "&serverId=" + serverId + }, appRouter.showItem = showItem, appRouter + }) + }(), require(["css!css/site"]), require(["browser"], onWebComponentsReady) +}(), pageClassOn("viewshow", "standalonePage", function() { + document.querySelector(".skinHeader").classList.add("noHeaderRight") +}), pageClassOn("viewhide", "standalonePage", function() { + document.querySelector(".skinHeader").classList.remove("noHeaderRight") +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/songs.js b/dashboard-ui/scripts/songs.js index b3dc4fe38d..eeaef6e970 100644 --- a/dashboard-ui/scripts/songs.js +++ b/dashboard-ui/scripts/songs.js @@ -1 +1,127 @@ -define(["events","libraryBrowser","imageLoader","listView","loading","emby-itemscontainer"],function(events,libraryBrowser,imageLoader,listView,loading){"use strict";return function(view,params,tabContent){function getPageData(context){var key=getSavedQueryKey(context),pageData=data[key];return pageData||(pageData=data[key]={query:{SortBy:"Album,SortName",SortOrder:"Ascending",IncludeItemTypes:"Audio",Recursive:!0,Fields:"AudioInfo,ParentId",Limit:100,StartIndex:0,ImageTypeLimit:1,EnableImageTypes:"Primary"}},pageData.query.ParentId=params.topParentId,libraryBrowser.loadSavedQueryValues(key,pageData.query)),pageData}function getQuery(context){return getPageData(context).query}function getSavedQueryKey(context){return context.savedQueryKey||(context.savedQueryKey=libraryBrowser.getSavedQueryKey("songs")),context.savedQueryKey}function reloadItems(page){loading.show();var query=getQuery(page);ApiClient.getItems(Dashboard.getCurrentUserId(),query).then(function(result){function onNextPageClick(){query.StartIndex+=query.Limit,reloadItems(tabContent)}function onPreviousPageClick(){query.StartIndex-=query.Limit,reloadItems(tabContent)}window.scrollTo(0,0);var i,length,pagingHtml=libraryBrowser.getQueryPagingHtml({startIndex:query.StartIndex,limit:query.Limit,totalRecordCount:result.TotalRecordCount,showLimit:!1,updatePageSizeSetting:!1,addLayoutButton:!1,sortButton:!1,filterButton:!1}),html=listView.getListViewHtml({items:result.Items,action:"playallfromhere",smallIcon:!0,artist:!0,addToListButton:!0}),elems=tabContent.querySelectorAll(".paging");for(i=0,length=elems.length;i('+Globalize.translate("LabelFailed")+")"):"Cancelled"==lastResult?options.lastResultElem.html('('+Globalize.translate("LabelCancelled")+")"):"Aborted"==lastResult?options.lastResultElem.html(''+Globalize.translate("LabelAbortedByServerShutdown")+""):options.lastResultElem.html(lastResult)}}}function onScheduledTaskMessageConfirmed(id){connectionManager.getApiClient(serverId).startScheduledTask(id).then(pollTasks)}function onButtonClick(){onScheduledTaskMessageConfirmed(this.getAttribute("data-taskid"))}function onScheduledTasksUpdate(e,apiClient,info){apiClient.serverId()===serverId&&updateTasks(info)}function onPollIntervalFired(){connectionManager.getApiClient(serverId).isMessageChannelOpen()||pollTasks()}var pollInterval,button=options.button,serverId=ApiClient.serverId();options.panel&&options.panel.classList.add("hide"),"off"==options.mode?(button.removeEventListener("click",onButtonClick),events.off(serverNotifications,"ScheduledTasksInfo",onScheduledTasksUpdate),function(){connectionManager.getApiClient(serverId).sendMessage("ScheduledTasksInfoStop"),pollInterval&&clearInterval(pollInterval)}()):(button.addEventListener("click",onButtonClick),pollTasks(),function(){var apiClient=connectionManager.getApiClient(serverId);pollInterval&&clearInterval(pollInterval),apiClient.sendMessage("ScheduledTasksInfoStart","1000,1000"),pollInterval=setInterval(onPollIntervalFired,1e4)}(),events.on(serverNotifications,"ScheduledTasksInfo",onScheduledTasksUpdate))}}); \ No newline at end of file +define(["events", "userSettings", "serverNotifications", "connectionManager", "emby-button"], function(events, userSettings, serverNotifications, connectionManager) { + "use strict"; + return function(options) { + function pollTasks() { + connectionManager.getApiClient(serverId).getScheduledTasks({ + IsEnabled: !0 + }).then(updateTasks) + } + + function updateTasks(tasks) { + var task = tasks.filter(function(t) { + return t.Key == options.taskKey + })[0]; + if (options.panel && (task ? options.panel.classList.remove("hide") : options.panel.classList.add("hide")), task) { + "Idle" == task.State ? button.removeAttribute("disabled") : button.setAttribute("disabled", "disabled"), button.setAttribute("data-taskid", task.Id); + var progress = (task.CurrentProgressPercentage || 0).toFixed(1); + if (options.progressElem && (options.progressElem.value = progress, "Running" == task.State ? options.progressElem.classList.remove("hide") : options.progressElem.classList.add("hide")), options.lastResultElem) { + var lastResult = task.LastExecutionResult ? task.LastExecutionResult.Status : ""; + "Failed" == lastResult ? options.lastResultElem.html('(' + Globalize.translate("LabelFailed") + ")") : "Cancelled" == lastResult ? options.lastResultElem.html('(' + Globalize.translate("LabelCancelled") + ")") : "Aborted" == lastResult ? options.lastResultElem.html('' + Globalize.translate("LabelAbortedByServerShutdown") + "") : options.lastResultElem.html(lastResult) + } + } + } + + function onScheduledTaskMessageConfirmed(id) { + connectionManager.getApiClient(serverId).startScheduledTask(id).then(pollTasks) + } + + function onButtonClick() { + onScheduledTaskMessageConfirmed(this.getAttribute("data-taskid")) + } + + function onScheduledTasksUpdate(e, apiClient, info) { + apiClient.serverId() === serverId && updateTasks(info) + } + + function onPollIntervalFired() { + connectionManager.getApiClient(serverId).isMessageChannelOpen() || pollTasks() + } + var pollInterval, button = options.button, + serverId = ApiClient.serverId(); + options.panel && options.panel.classList.add("hide"), "off" == options.mode ? (button.removeEventListener("click", onButtonClick), events.off(serverNotifications, "ScheduledTasksInfo", onScheduledTasksUpdate), function() { + connectionManager.getApiClient(serverId).sendMessage("ScheduledTasksInfoStop"), pollInterval && clearInterval(pollInterval) + }()) : (button.addEventListener("click", onButtonClick), pollTasks(), function() { + var apiClient = connectionManager.getApiClient(serverId); + pollInterval && clearInterval(pollInterval), apiClient.sendMessage("ScheduledTasksInfoStart", "1000,1000"), pollInterval = setInterval(onPollIntervalFired, 1e4) + }(), events.on(serverNotifications, "ScheduledTasksInfo", onScheduledTasksUpdate)) + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/themeloader.js b/dashboard-ui/scripts/themeloader.js index aa245a733b..eb783b132d 100644 --- a/dashboard-ui/scripts/themeloader.js +++ b/dashboard-ui/scripts/themeloader.js @@ -1 +1,15 @@ -define(["userSettings","skinManager","connectionManager","events"],function(userSettings,skinManager,connectionManager,events){"use strict";var currentViewType;pageClassOn("viewbeforeshow","page",function(){var classList=this.classList,viewType=classList.contains("type-interior")||classList.contains("wizardPage")?"a":"b";if(viewType!==currentViewType){currentViewType=viewType;var theme,context;"a"===viewType?(theme=userSettings.dashboardTheme(),context="serverdashboard"):theme=userSettings.theme(),skinManager.setTheme(theme,context)}}),events.on(connectionManager,"localusersignedin",function(e,user){currentViewType=null})}); \ No newline at end of file +define(["userSettings", "skinManager", "connectionManager", "events"], function(userSettings, skinManager, connectionManager, events) { + "use strict"; + var currentViewType; + pageClassOn("viewbeforeshow", "page", function() { + var classList = this.classList, + viewType = classList.contains("type-interior") || classList.contains("wizardPage") ? "a" : "b"; + if (viewType !== currentViewType) { + currentViewType = viewType; + var theme, context; + "a" === viewType ? (theme = userSettings.dashboardTheme(), context = "serverdashboard") : theme = userSettings.theme(), skinManager.setTheme(theme, context) + } + }), events.on(connectionManager, "localusersignedin", function(e, user) { + currentViewType = null + }) +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/tvgenres.js b/dashboard-ui/scripts/tvgenres.js index fc96a04276..39191edd81 100644 --- a/dashboard-ui/scripts/tvgenres.js +++ b/dashboard-ui/scripts/tvgenres.js @@ -1 +1,141 @@ -define(["layoutManager","loading","libraryBrowser","cardBuilder","lazyLoader","apphost","globalize","appRouter","dom","emby-linkbutton"],function(layoutManager,loading,libraryBrowser,cardBuilder,lazyLoader,appHost,globalize,appRouter,dom){"use strict";return function(view,params,tabContent){function getPageData(){var key=getSavedQueryKey(),pageData=data[key];return pageData||(pageData=data[key]={query:{SortBy:"SortName",SortOrder:"Ascending",IncludeItemTypes:"Series",Recursive:!0,EnableTotalRecordCount:!1},view:"Poster"},pageData.query.ParentId=params.topParentId,libraryBrowser.loadSavedQueryValues(key,pageData.query)),pageData}function getQuery(){return getPageData().query}function getSavedQueryKey(){return libraryBrowser.getSavedQueryKey("seriesgenres")}function getPromise(){loading.show();var query=getQuery();return ApiClient.getGenres(ApiClient.getCurrentUserId(),query)}function enableScrollX(){return!layoutManager.desktop}function getThumbShape(){return enableScrollX()?"overflowBackdrop":"backdrop"}function getPortraitShape(){return enableScrollX()?"overflowPortrait":"portrait"}function fillItemsContainer(elem){var id=elem.getAttribute("data-id"),viewStyle=self.getCurrentViewStyle(),limit="Thumb"==viewStyle||"ThumbCard"==viewStyle?5:9;enableScrollX()&&(limit=10);var enableImageTypes="Thumb"==viewStyle||"ThumbCard"==viewStyle?"Primary,Backdrop,Thumb":"Primary",query={SortBy:"SortName",SortOrder:"Ascending",IncludeItemTypes:"Series",Recursive:!0,Fields:"PrimaryImageAspectRatio,MediaSourceCount,BasicSyncInfo",ImageTypeLimit:1,EnableImageTypes:enableImageTypes,Limit:limit,GenreIds:id,EnableTotalRecordCount:!1,ParentId:params.topParentId};ApiClient.getItems(ApiClient.getCurrentUserId(),query).then(function(result){var supportsImageAnalysis=appHost.supports("imageanalysis");"Thumb"==viewStyle?cardBuilder.buildCards(result.Items,{itemsContainer:elem,shape:getThumbShape(),preferThumb:!0,showTitle:!0,scalable:!0,centerText:!0,overlayMoreButton:!0,allowBottomPadding:!1}):"ThumbCard"==viewStyle?cardBuilder.buildCards(result.Items,{itemsContainer:elem,shape:getThumbShape(),preferThumb:!0,showTitle:!0,scalable:!0,centerText:!1,cardLayout:!0,vibrant:supportsImageAnalysis,showYear:!0}):"PosterCard"==viewStyle?cardBuilder.buildCards(result.Items,{itemsContainer:elem,shape:getPortraitShape(),showTitle:!0,scalable:!0,centerText:!1,cardLayout:!0,vibrant:supportsImageAnalysis,showYear:!0}):"Poster"==viewStyle&&cardBuilder.buildCards(result.Items,{itemsContainer:elem,shape:getPortraitShape(),scalable:!0,overlayMoreButton:!0,allowBottomPadding:!1}),result.Items.length>=query.Limit&&tabContent.querySelector(".btnMoreFromGenre"+id+" i").classList.remove("hide")})}function reloadItems(context,promise){var query=getQuery();promise.then(function(result){for(var elem=context.querySelector("#items"),html="",items=result.Items,i=0,length=items.length;i',html+='",enableScrollX()){var scrollXClass="scrollX hiddenScrollX";layoutManager.tv&&(scrollXClass+=" smoothScrollX"),html+='
    '}else html+='
    ';html+="
    ",html+="
    "}elem.innerHTML=html,lazyLoader.lazyChildren(elem,fillItemsContainer),libraryBrowser.saveQueryValues(getSavedQueryKey(),query),loading.hide()})}function fullyReload(){self.preRender(),self.renderTab()}var self=this,data={};self.getViewStyles=function(){return"Poster,PosterCard,Thumb,ThumbCard".split(",")},self.getCurrentViewStyle=function(){return getPageData(tabContent).view},self.setCurrentViewStyle=function(viewStyle){getPageData(tabContent).view=viewStyle,libraryBrowser.saveViewSetting(getSavedQueryKey(tabContent),viewStyle),fullyReload()},self.enableViewSelection=!0;var promise;self.preRender=function(){promise=getPromise()},self.renderTab=function(){reloadItems(tabContent,promise)}}}); \ No newline at end of file +define(["layoutManager", "loading", "libraryBrowser", "cardBuilder", "lazyLoader", "apphost", "globalize", "appRouter", "dom", "emby-linkbutton"], function(layoutManager, loading, libraryBrowser, cardBuilder, lazyLoader, appHost, globalize, appRouter, dom) { + "use strict"; + return function(view, params, tabContent) { + function getPageData() { + var key = getSavedQueryKey(), + pageData = data[key]; + return pageData || (pageData = data[key] = { + query: { + SortBy: "SortName", + SortOrder: "Ascending", + IncludeItemTypes: "Series", + Recursive: !0, + EnableTotalRecordCount: !1 + }, + view: "Poster" + }, pageData.query.ParentId = params.topParentId, libraryBrowser.loadSavedQueryValues(key, pageData.query)), pageData + } + + function getQuery() { + return getPageData().query + } + + function getSavedQueryKey() { + return libraryBrowser.getSavedQueryKey("seriesgenres") + } + + function getPromise() { + loading.show(); + var query = getQuery(); + return ApiClient.getGenres(ApiClient.getCurrentUserId(), query) + } + + function enableScrollX() { + return !layoutManager.desktop + } + + function getThumbShape() { + return enableScrollX() ? "overflowBackdrop" : "backdrop" + } + + function getPortraitShape() { + return enableScrollX() ? "overflowPortrait" : "portrait" + } + + function fillItemsContainer(elem) { + var id = elem.getAttribute("data-id"), + viewStyle = self.getCurrentViewStyle(), + limit = "Thumb" == viewStyle || "ThumbCard" == viewStyle ? 5 : 9; + enableScrollX() && (limit = 10); + var enableImageTypes = "Thumb" == viewStyle || "ThumbCard" == viewStyle ? "Primary,Backdrop,Thumb" : "Primary", + query = { + SortBy: "SortName", + SortOrder: "Ascending", + IncludeItemTypes: "Series", + Recursive: !0, + Fields: "PrimaryImageAspectRatio,MediaSourceCount,BasicSyncInfo", + ImageTypeLimit: 1, + EnableImageTypes: enableImageTypes, + Limit: limit, + GenreIds: id, + EnableTotalRecordCount: !1, + ParentId: params.topParentId + }; + ApiClient.getItems(ApiClient.getCurrentUserId(), query).then(function(result) { + var supportsImageAnalysis = appHost.supports("imageanalysis"); + "Thumb" == viewStyle ? cardBuilder.buildCards(result.Items, { + itemsContainer: elem, + shape: getThumbShape(), + preferThumb: !0, + showTitle: !0, + scalable: !0, + centerText: !0, + overlayMoreButton: !0, + allowBottomPadding: !1 + }) : "ThumbCard" == viewStyle ? cardBuilder.buildCards(result.Items, { + itemsContainer: elem, + shape: getThumbShape(), + preferThumb: !0, + showTitle: !0, + scalable: !0, + centerText: !1, + cardLayout: !0, + vibrant: supportsImageAnalysis, + showYear: !0 + }) : "PosterCard" == viewStyle ? cardBuilder.buildCards(result.Items, { + itemsContainer: elem, + shape: getPortraitShape(), + showTitle: !0, + scalable: !0, + centerText: !1, + cardLayout: !0, + vibrant: supportsImageAnalysis, + showYear: !0 + }) : "Poster" == viewStyle && cardBuilder.buildCards(result.Items, { + itemsContainer: elem, + shape: getPortraitShape(), + scalable: !0, + overlayMoreButton: !0, + allowBottomPadding: !1 + }), result.Items.length >= query.Limit && tabContent.querySelector(".btnMoreFromGenre" + id + " i").classList.remove("hide") + }) + } + + function reloadItems(context, promise) { + var query = getQuery(); + promise.then(function(result) { + for (var elem = context.querySelector("#items"), html = "", items = result.Items, i = 0, length = items.length; i < length; i++) { + var item = items[i]; + if (html += '
    ', html += '", enableScrollX()) { + var scrollXClass = "scrollX hiddenScrollX"; + layoutManager.tv && (scrollXClass += " smoothScrollX"), html += '
    ' + } else html += '
    '; + html += "
    ", html += "
    " + } + elem.innerHTML = html, lazyLoader.lazyChildren(elem, fillItemsContainer), libraryBrowser.saveQueryValues(getSavedQueryKey(), query), loading.hide() + }) + } + + function fullyReload() { + self.preRender(), self.renderTab() + } + var self = this, + data = {}; + self.getViewStyles = function() { + return "Poster,PosterCard,Thumb,ThumbCard".split(",") + }, self.getCurrentViewStyle = function() { + return getPageData(tabContent).view + }, self.setCurrentViewStyle = function(viewStyle) { + getPageData(tabContent).view = viewStyle, libraryBrowser.saveViewSetting(getSavedQueryKey(tabContent), viewStyle), fullyReload() + }, self.enableViewSelection = !0; + var promise; + self.preRender = function() { + promise = getPromise() + }, self.renderTab = function() { + reloadItems(tabContent, promise) + } + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/tvlatest.js b/dashboard-ui/scripts/tvlatest.js index 4344a56067..a3cebdd8ee 100644 --- a/dashboard-ui/scripts/tvlatest.js +++ b/dashboard-ui/scripts/tvlatest.js @@ -1 +1,54 @@ -define(["loading","components/categorysyncbuttons","components/groupedcards","cardBuilder","apphost","imageLoader"],function(loading,categorysyncbuttons,groupedcards,cardBuilder,appHost,imageLoader){"use strict";function getLatestPromise(context,params){loading.show();var userId=ApiClient.getCurrentUserId(),parentId=params.topParentId,options={IncludeItemTypes:"Episode",Limit:30,Fields:"PrimaryImageAspectRatio,BasicSyncInfo",ParentId:parentId,ImageTypeLimit:1,EnableImageTypes:"Primary,Backdrop,Thumb"};return ApiClient.getJSON(ApiClient.getUrl("Users/"+userId+"/Items/Latest",options))}function loadLatest(context,params,promise){promise.then(function(items){var html="";appHost.supports("imageanalysis");html+=cardBuilder.getCardsHtml({items:items,shape:"backdrop",preferThumb:!0,showTitle:!0,showSeriesYear:!0,showParentTitle:!0,overlayText:!1,cardLayout:!1,showUnplayedIndicator:!1,showChildCountIndicator:!0,centerText:!0,lazy:!0,overlayPlayButton:!0,vibrant:!1,lines:2});var elem=context.querySelector("#latestEpisodes");elem.innerHTML=html,imageLoader.lazyChildren(elem),loading.hide()})}return function(view,params,tabContent){var self=this;categorysyncbuttons.init(tabContent);var latestPromise;self.preRender=function(){latestPromise=getLatestPromise(view,params)},self.renderTab=function(){loadLatest(tabContent,params,latestPromise)},tabContent.querySelector("#latestEpisodes").addEventListener("click",groupedcards.onItemsContainerClick)}}); \ No newline at end of file +define(["loading", "components/categorysyncbuttons", "components/groupedcards", "cardBuilder", "apphost", "imageLoader"], function(loading, categorysyncbuttons, groupedcards, cardBuilder, appHost, imageLoader) { + "use strict"; + + function getLatestPromise(context, params) { + loading.show(); + var userId = ApiClient.getCurrentUserId(), + parentId = params.topParentId, + options = { + IncludeItemTypes: "Episode", + Limit: 30, + Fields: "PrimaryImageAspectRatio,BasicSyncInfo", + ParentId: parentId, + ImageTypeLimit: 1, + EnableImageTypes: "Primary,Backdrop,Thumb" + }; + return ApiClient.getJSON(ApiClient.getUrl("Users/" + userId + "/Items/Latest", options)) + } + + function loadLatest(context, params, promise) { + promise.then(function(items) { + var html = ""; + appHost.supports("imageanalysis"); + html += cardBuilder.getCardsHtml({ + items: items, + shape: "backdrop", + preferThumb: !0, + showTitle: !0, + showSeriesYear: !0, + showParentTitle: !0, + overlayText: !1, + cardLayout: !1, + showUnplayedIndicator: !1, + showChildCountIndicator: !0, + centerText: !0, + lazy: !0, + overlayPlayButton: !0, + vibrant: !1, + lines: 2 + }); + var elem = context.querySelector("#latestEpisodes"); + elem.innerHTML = html, imageLoader.lazyChildren(elem), loading.hide() + }) + } + return function(view, params, tabContent) { + var self = this; + categorysyncbuttons.init(tabContent); + var latestPromise; + self.preRender = function() { + latestPromise = getLatestPromise(view, params) + }, self.renderTab = function() { + loadLatest(tabContent, params, latestPromise) + }, tabContent.querySelector("#latestEpisodes").addEventListener("click", groupedcards.onItemsContainerClick) + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/tvrecommended.js b/dashboard-ui/scripts/tvrecommended.js index 2807c0b9a1..12fbd9081b 100644 --- a/dashboard-ui/scripts/tvrecommended.js +++ b/dashboard-ui/scripts/tvrecommended.js @@ -1 +1,229 @@ -define(["events","inputManager","libraryMenu","layoutManager","loading","dom","components/categorysyncbuttons","userSettings","cardBuilder","playbackManager","mainTabsManager","scrollStyles","emby-itemscontainer","emby-button"],function(events,inputManager,libraryMenu,layoutManager,loading,dom,categorysyncbuttons,userSettings,cardBuilder,playbackManager,mainTabsManager){"use strict";function getTabs(){return[{name:Globalize.translate("TabShows")},{name:Globalize.translate("TabSuggestions")},{name:Globalize.translate("TabLatest")},{name:Globalize.translate("TabUpcoming")},{name:Globalize.translate("TabGenres")},{name:Globalize.translate("TabNetworks")},{name:Globalize.translate("TabEpisodes")},{name:Globalize.translate("ButtonSearch"),cssClass:"searchTabButton"}]}function getDefaultTabIndex(folderId){switch(userSettings.get("landing-"+folderId)){case"suggestions":return 1;case"latest":return 2;case"favorites":return 1;case"genres":return 4;default:return 0}}function setScrollClasses(elem,scrollX){scrollX?(elem.classList.add("hiddenScrollX"),layoutManager.tv&&elem.classList.add("smoothScrollX"),elem.classList.add("scrollX"),elem.classList.remove("vertical-wrap")):(elem.classList.remove("hiddenScrollX"),elem.classList.remove("smoothScrollX"),elem.classList.remove("scrollX"),elem.classList.add("vertical-wrap"))}return function(view,params){function reload(){loading.show(),loadResume(),loadNextUp()}function loadNextUp(){var query={Limit:24,Fields:"PrimaryImageAspectRatio,SeriesInfo,DateCreated,BasicSyncInfo",UserId:ApiClient.getCurrentUserId(),ImageTypeLimit:1,EnableImageTypes:"Primary,Backdrop,Thumb",EnableTotalRecordCount:!1};query.ParentId=libraryMenu.getTopParentId(),ApiClient.getNextUpEpisodes(query).then(function(result){result.Items.length?view.querySelector(".noNextUpItems").classList.add("hide"):view.querySelector(".noNextUpItems").classList.remove("hide");var container=view.querySelector("#nextUpItems");cardBuilder.buildCards(result.Items,{itemsContainer:container,preferThumb:!0,shape:"backdrop",scalable:!0,showTitle:!0,showParentTitle:!0,overlayText:!1,centerText:!0,overlayPlayButton:!0,cardLayout:!1}),loading.hide()})}function enableScrollX(){return!layoutManager.desktop}function getThumbShape(){return enableScrollX()?"overflowBackdrop":"backdrop"}function loadResume(){var parentId=libraryMenu.getTopParentId(),screenWidth=dom.getWindowSize().innerWidth,limit=screenWidth>=1600?5:6,options={SortBy:"DatePlayed",SortOrder:"Descending",IncludeItemTypes:"Episode",Filters:"IsResumable",Limit:limit,Recursive:!0,Fields:"PrimaryImageAspectRatio,SeriesInfo,UserData,BasicSyncInfo",ExcludeLocationTypes:"Virtual",ParentId:parentId,ImageTypeLimit:1,EnableImageTypes:"Primary,Backdrop,Thumb",EnableTotalRecordCount:!1};ApiClient.getItems(ApiClient.getCurrentUserId(),options).then(function(result){result.Items.length?view.querySelector("#resumableSection").classList.remove("hide"):view.querySelector("#resumableSection").classList.add("hide");var allowBottomPadding=!enableScrollX(),container=view.querySelector("#resumableItems");cardBuilder.buildCards(result.Items,{itemsContainer:container,preferThumb:!0,shape:getThumbShape(),scalable:!0,showTitle:!0,showParentTitle:!0,overlayText:!1,centerText:!0,overlayPlayButton:!0,allowBottomPadding:allowBottomPadding,cardLayout:!1})})}function onBeforeTabChange(e){preLoadTab(view,parseInt(e.detail.selectedTabIndex))}function onTabChange(e){var newIndex=parseInt(e.detail.selectedTabIndex);loadTab(view,newIndex)}function getTabContainers(){return view.querySelectorAll(".pageTabContent")}function initTabs(){mainTabsManager.setTabs(view,currentTabIndex,getTabs,getTabContainers,onBeforeTabChange,onTabChange)}function getTabController(page,index,callback){var depends=[];switch(index){case 0:depends.push("scripts/tvshows");break;case 1:break;case 2:depends.push("scripts/tvlatest");break;case 3:depends.push("scripts/tvupcoming");break;case 4:depends.push("scripts/tvgenres");break;case 5:depends.push("scripts/tvstudios");break;case 6:depends.push("scripts/episodes");break;case 7:depends.push("scripts/searchtab")}require(depends,function(controllerFactory){var tabContent;1===index&&(tabContent=view.querySelector(".pageTabContent[data-index='"+index+"']"),self.tabContent=tabContent);var controller=tabControllers[index];controller||(tabContent=view.querySelector(".pageTabContent[data-index='"+index+"']"),controller=1===index?self:7===index?new controllerFactory(view,tabContent,{collectionType:"tvshows",parentId:params.topParentId}):new controllerFactory(view,params,tabContent),tabControllers[index]=controller,controller.initTab&&controller.initTab()),callback(controller)})}function preLoadTab(page,index){getTabController(page,index,function(controller){-1==renderedTabs.indexOf(index)&&controller.preRender&&controller.preRender()})}function loadTab(page,index){currentTabIndex=index,getTabController(page,index,function(controller){initialTabIndex=null,-1==renderedTabs.indexOf(index)&&(renderedTabs.push(index),controller.renderTab())})}function onPlaybackStop(e,state){state.NowPlayingItem&&"Video"==state.NowPlayingItem.MediaType&&(renderedTabs=[],mainTabsManager.getTabsElement().triggerTabChange())}function onWebSocketMessage(e,data){var msg=data;"UserDataChanged"===msg.MessageType&&msg.Data.UserId==ApiClient.getCurrentUserId()&&(renderedTabs=[])}function onInputCommand(e){switch(e.detail.command){case"search":e.preventDefault(),Dashboard.navigate("search.html?collectionType=tv&parentId="+params.topParentId)}}var isViewRestored,self=this,currentTabIndex=parseInt(params.tab||getDefaultTabIndex(params.topParentId)),initialTabIndex=currentTabIndex;self.initTab=function(){var tabContent=self.tabContent;setScrollClasses(tabContent.querySelector("#resumableItems"),enableScrollX()),categorysyncbuttons.init(tabContent)},self.renderTab=function(){reload()};var tabControllers=[],renderedTabs=[];setScrollClasses(view.querySelector("#resumableItems"),enableScrollX()),view.addEventListener("viewshow",function(e){if(isViewRestored=e.detail.isRestored,initTabs(),!view.getAttribute("data-title")){var parentId=params.topParentId;parentId?ApiClient.getItem(ApiClient.getCurrentUserId(),parentId).then(function(item){view.setAttribute("data-title",item.Name),libraryMenu.setTitle(item.Name)}):(view.setAttribute("data-title",Globalize.translate("TabShows")),libraryMenu.setTitle(Globalize.translate("TabShows")))}events.on(playbackManager,"playbackstop",onPlaybackStop),events.on(ApiClient,"message",onWebSocketMessage),inputManager.on(window,onInputCommand)}),view.addEventListener("viewbeforehide",function(e){inputManager.off(window,onInputCommand),events.off(playbackManager,"playbackstop",onPlaybackStop),events.off(ApiClient,"message",onWebSocketMessage)}),view.addEventListener("viewdestroy",function(e){tabControllers.forEach(function(t){t.destroy&&t.destroy()})})}}); \ No newline at end of file +define(["events", "inputManager", "libraryMenu", "layoutManager", "loading", "dom", "components/categorysyncbuttons", "userSettings", "cardBuilder", "playbackManager", "mainTabsManager", "scrollStyles", "emby-itemscontainer", "emby-button"], function(events, inputManager, libraryMenu, layoutManager, loading, dom, categorysyncbuttons, userSettings, cardBuilder, playbackManager, mainTabsManager) { + "use strict"; + + function getTabs() { + return [{ + name: Globalize.translate("TabShows") + }, { + name: Globalize.translate("TabSuggestions") + }, { + name: Globalize.translate("TabLatest") + }, { + name: Globalize.translate("TabUpcoming") + }, { + name: Globalize.translate("TabGenres") + }, { + name: Globalize.translate("TabNetworks") + }, { + name: Globalize.translate("TabEpisodes") + }, { + name: Globalize.translate("ButtonSearch"), + cssClass: "searchTabButton" + }] + } + + function getDefaultTabIndex(folderId) { + switch (userSettings.get("landing-" + folderId)) { + case "suggestions": + return 1; + case "latest": + return 2; + case "favorites": + return 1; + case "genres": + return 4; + default: + return 0 + } + } + + function setScrollClasses(elem, scrollX) { + scrollX ? (elem.classList.add("hiddenScrollX"), layoutManager.tv && elem.classList.add("smoothScrollX"), elem.classList.add("scrollX"), elem.classList.remove("vertical-wrap")) : (elem.classList.remove("hiddenScrollX"), elem.classList.remove("smoothScrollX"), elem.classList.remove("scrollX"), elem.classList.add("vertical-wrap")) + } + return function(view, params) { + function reload() { + loading.show(), loadResume(), loadNextUp() + } + + function loadNextUp() { + var query = { + Limit: 24, + Fields: "PrimaryImageAspectRatio,SeriesInfo,DateCreated,BasicSyncInfo", + UserId: ApiClient.getCurrentUserId(), + ImageTypeLimit: 1, + EnableImageTypes: "Primary,Backdrop,Thumb", + EnableTotalRecordCount: !1 + }; + query.ParentId = libraryMenu.getTopParentId(), ApiClient.getNextUpEpisodes(query).then(function(result) { + result.Items.length ? view.querySelector(".noNextUpItems").classList.add("hide") : view.querySelector(".noNextUpItems").classList.remove("hide"); + var container = view.querySelector("#nextUpItems"); + cardBuilder.buildCards(result.Items, { + itemsContainer: container, + preferThumb: !0, + shape: "backdrop", + scalable: !0, + showTitle: !0, + showParentTitle: !0, + overlayText: !1, + centerText: !0, + overlayPlayButton: !0, + cardLayout: !1 + }), loading.hide() + }) + } + + function enableScrollX() { + return !layoutManager.desktop + } + + function getThumbShape() { + return enableScrollX() ? "overflowBackdrop" : "backdrop" + } + + function loadResume() { + var parentId = libraryMenu.getTopParentId(), + screenWidth = dom.getWindowSize().innerWidth, + limit = screenWidth >= 1600 ? 5 : 6, + options = { + SortBy: "DatePlayed", + SortOrder: "Descending", + IncludeItemTypes: "Episode", + Filters: "IsResumable", + Limit: limit, + Recursive: !0, + Fields: "PrimaryImageAspectRatio,SeriesInfo,UserData,BasicSyncInfo", + ExcludeLocationTypes: "Virtual", + ParentId: parentId, + ImageTypeLimit: 1, + EnableImageTypes: "Primary,Backdrop,Thumb", + EnableTotalRecordCount: !1 + }; + ApiClient.getItems(ApiClient.getCurrentUserId(), options).then(function(result) { + result.Items.length ? view.querySelector("#resumableSection").classList.remove("hide") : view.querySelector("#resumableSection").classList.add("hide"); + var allowBottomPadding = !enableScrollX(), + container = view.querySelector("#resumableItems"); + cardBuilder.buildCards(result.Items, { + itemsContainer: container, + preferThumb: !0, + shape: getThumbShape(), + scalable: !0, + showTitle: !0, + showParentTitle: !0, + overlayText: !1, + centerText: !0, + overlayPlayButton: !0, + allowBottomPadding: allowBottomPadding, + cardLayout: !1 + }) + }) + } + + function onBeforeTabChange(e) { + preLoadTab(view, parseInt(e.detail.selectedTabIndex)) + } + + function onTabChange(e) { + var newIndex = parseInt(e.detail.selectedTabIndex); + loadTab(view, newIndex) + } + + function getTabContainers() { + return view.querySelectorAll(".pageTabContent") + } + + function initTabs() { + mainTabsManager.setTabs(view, currentTabIndex, getTabs, getTabContainers, onBeforeTabChange, onTabChange) + } + + function getTabController(page, index, callback) { + var depends = []; + switch (index) { + case 0: + depends.push("scripts/tvshows"); + break; + case 1: + break; + case 2: + depends.push("scripts/tvlatest"); + break; + case 3: + depends.push("scripts/tvupcoming"); + break; + case 4: + depends.push("scripts/tvgenres"); + break; + case 5: + depends.push("scripts/tvstudios"); + break; + case 6: + depends.push("scripts/episodes"); + break; + case 7: + depends.push("scripts/searchtab") + } + require(depends, function(controllerFactory) { + var tabContent; + 1 === index && (tabContent = view.querySelector(".pageTabContent[data-index='" + index + "']"), self.tabContent = tabContent); + var controller = tabControllers[index]; + controller || (tabContent = view.querySelector(".pageTabContent[data-index='" + index + "']"), controller = 1 === index ? self : 7 === index ? new controllerFactory(view, tabContent, { + collectionType: "tvshows", + parentId: params.topParentId + }) : new controllerFactory(view, params, tabContent), tabControllers[index] = controller, controller.initTab && controller.initTab()), callback(controller) + }) + } + + function preLoadTab(page, index) { + getTabController(page, index, function(controller) { + -1 == renderedTabs.indexOf(index) && controller.preRender && controller.preRender() + }) + } + + function loadTab(page, index) { + currentTabIndex = index, getTabController(page, index, function(controller) { + initialTabIndex = null, -1 == renderedTabs.indexOf(index) && (renderedTabs.push(index), controller.renderTab()) + }) + } + + function onPlaybackStop(e, state) { + state.NowPlayingItem && "Video" == state.NowPlayingItem.MediaType && (renderedTabs = [], mainTabsManager.getTabsElement().triggerTabChange()) + } + + function onWebSocketMessage(e, data) { + var msg = data; + "UserDataChanged" === msg.MessageType && msg.Data.UserId == ApiClient.getCurrentUserId() && (renderedTabs = []) + } + + function onInputCommand(e) { + switch (e.detail.command) { + case "search": + e.preventDefault(), Dashboard.navigate("search.html?collectionType=tv&parentId=" + params.topParentId) + } + } + var isViewRestored, self = this, + currentTabIndex = parseInt(params.tab || getDefaultTabIndex(params.topParentId)), + initialTabIndex = currentTabIndex; + self.initTab = function() { + var tabContent = self.tabContent; + setScrollClasses(tabContent.querySelector("#resumableItems"), enableScrollX()), categorysyncbuttons.init(tabContent) + }, self.renderTab = function() { + reload() + }; + var tabControllers = [], + renderedTabs = []; + setScrollClasses(view.querySelector("#resumableItems"), enableScrollX()), view.addEventListener("viewshow", function(e) { + if (isViewRestored = e.detail.isRestored, initTabs(), !view.getAttribute("data-title")) { + var parentId = params.topParentId; + parentId ? ApiClient.getItem(ApiClient.getCurrentUserId(), parentId).then(function(item) { + view.setAttribute("data-title", item.Name), libraryMenu.setTitle(item.Name) + }) : (view.setAttribute("data-title", Globalize.translate("TabShows")), libraryMenu.setTitle(Globalize.translate("TabShows"))) + } + events.on(playbackManager, "playbackstop", onPlaybackStop), events.on(ApiClient, "message", onWebSocketMessage), inputManager.on(window, onInputCommand) + }), view.addEventListener("viewbeforehide", function(e) { + inputManager.off(window, onInputCommand), events.off(playbackManager, "playbackstop", onPlaybackStop), events.off(ApiClient, "message", onWebSocketMessage) + }), view.addEventListener("viewdestroy", function(e) { + tabControllers.forEach(function(t) { + t.destroy && t.destroy() + }) + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/tvshows.js b/dashboard-ui/scripts/tvshows.js index a31eb507da..76e4a305eb 100644 --- a/dashboard-ui/scripts/tvshows.js +++ b/dashboard-ui/scripts/tvshows.js @@ -1 +1,186 @@ -define(["layoutManager","loading","events","libraryBrowser","imageLoader","listView","cardBuilder","alphaPicker","emby-itemscontainer"],function(layoutManager,loading,events,libraryBrowser,imageLoader,listView,cardBuilder,alphaPicker){"use strict";return function(view,params,tabContent){function getPageData(context){var key=getSavedQueryKey(context),pageData=data[key];return pageData||(pageData=data[key]={query:{SortBy:"SortName",SortOrder:"Ascending",IncludeItemTypes:"Series",Recursive:!0,Fields:"PrimaryImageAspectRatio,BasicSyncInfo",ImageTypeLimit:1,EnableImageTypes:"Primary,Backdrop,Banner,Thumb",StartIndex:0,Limit:pageSize},view:libraryBrowser.getSavedView(key)||"Poster"},pageData.query.ParentId=params.topParentId,libraryBrowser.loadSavedQueryValues(key,pageData.query)),pageData}function getQuery(context){return getPageData(context).query}function getSavedQueryKey(context){return context.savedQueryKey||(context.savedQueryKey=libraryBrowser.getSavedQueryKey("series")),context.savedQueryKey}function onViewStyleChange(){var viewStyle=self.getCurrentViewStyle(),itemsContainer=tabContent.querySelector(".itemsContainer");"List"==viewStyle?(itemsContainer.classList.add("vertical-list"),itemsContainer.classList.remove("vertical-wrap")):(itemsContainer.classList.remove("vertical-list"),itemsContainer.classList.add("vertical-wrap")),itemsContainer.innerHTML=""}function reloadItems(page){loading.show();var query=getQuery(page);ApiClient.getItems(ApiClient.getCurrentUserId(),query).then(function(result){function onNextPageClick(){query.StartIndex+=query.Limit,reloadItems(tabContent)}function onPreviousPageClick(){query.StartIndex-=query.Limit,reloadItems(tabContent)}window.scrollTo(0,0),updateFilterControls(page);var html,pagingHtml=libraryBrowser.getQueryPagingHtml({startIndex:query.StartIndex,limit:query.Limit,totalRecordCount:result.TotalRecordCount,showLimit:!1,updatePageSizeSetting:!1,addLayoutButton:!1,sortButton:!1,filterButton:!1}),viewStyle=self.getCurrentViewStyle();html="Thumb"==viewStyle?cardBuilder.getCardsHtml({items:result.Items,shape:"backdrop",preferThumb:!0,context:"tvshows",overlayMoreButton:!0,showTitle:!0,centerText:!0}):"ThumbCard"==viewStyle?cardBuilder.getCardsHtml({items:result.Items,shape:"backdrop",preferThumb:!0,context:"tvshows",cardLayout:!0,showTitle:!0,showYear:!0}):"Banner"==viewStyle?cardBuilder.getCardsHtml({items:result.Items,shape:"banner",preferBanner:!0,context:"tvshows"}):"List"==viewStyle?listView.getListViewHtml({items:result.Items,context:"tvshows",sortBy:query.SortBy}):"PosterCard"==viewStyle?cardBuilder.getCardsHtml({items:result.Items,shape:"portrait",context:"tvshows",showTitle:!0,showYear:!0,cardLayout:!0}):cardBuilder.getCardsHtml({items:result.Items,shape:"portrait",context:"tvshows",centerText:!0,lazy:!0,overlayMoreButton:!0,showTitle:!0});var i,length,elems=tabContent.querySelectorAll(".paging");for(i=0,length=elems.length;i',html+='

    '+group.name+"

    ";var allowBottomPadding=!0;if(enableScrollX()){allowBottomPadding=!1;var scrollXClass="scrollX hiddenScrollX";layoutManager.tv&&(scrollXClass+=" smoothScrollX"),html+='
    '}else html+='
    ';var supportsImageAnalysis=appHost.supports("imageanalysis");supportsImageAnalysis=!1,html+=cardBuilder.getCardsHtml({items:group.items,showLocationTypeIndicator:!1,shape:getThumbShape(),showTitle:!0,preferThumb:!0,lazy:!0,showDetailsMenu:!0,centerText:!supportsImageAnalysis,showParentTitle:!0,overlayText:!1,allowBottomPadding:allowBottomPadding,cardLayout:supportsImageAnalysis,vibrant:supportsImageAnalysis,overlayMoreButton:!0,missingIndicator:!1}),html+="
    ",html+="
    "}elem.innerHTML=html,imageLoader.lazyChildren(elem)}return function(view,params,tabContent){var upcomingPromise,self=this;self.preRender=function(){upcomingPromise=getUpcomingPromise(view,params)},self.renderTab=function(){loadUpcoming(tabContent,params,upcomingPromise)}}}); \ No newline at end of file +define(["layoutManager", "loading", "datetime", "libraryBrowser", "cardBuilder", "apphost", "imageLoader", "scrollStyles", "emby-itemscontainer"], function(layoutManager, loading, datetime, libraryBrowser, cardBuilder, appHost, imageLoader) { + "use strict"; + + function getUpcomingPromise(context, params) { + loading.show(); + var query = { + Limit: 48, + Fields: "AirTime,UserData", + UserId: ApiClient.getCurrentUserId(), + ImageTypeLimit: 1, + EnableImageTypes: "Primary,Backdrop,Banner,Thumb", + EnableTotalRecordCount: !1 + }; + return query.ParentId = params.topParentId, ApiClient.getJSON(ApiClient.getUrl("Shows/Upcoming", query)) + } + + function loadUpcoming(context, params, promise) { + promise.then(function(result) { + var items = result.Items; + items.length ? context.querySelector(".noItemsMessage").style.display = "none" : context.querySelector(".noItemsMessage").style.display = "block", renderUpcoming(context.querySelector("#upcomingItems"), items), loading.hide() + }) + } + + function enableScrollX() { + return !layoutManager.desktop + } + + function getThumbShape() { + return enableScrollX() ? "overflowBackdrop" : "backdrop" + } + + function renderUpcoming(elem, items) { + var i, length, groups = [], + currentGroupName = "", + currentGroup = []; + for (i = 0, length = items.length; i < length; i++) { + var item = items[i], + dateText = ""; + if (item.PremiereDate) try { + var premiereDate = datetime.parseISO8601Date(item.PremiereDate, !0); + dateText = datetime.isRelativeDay(premiereDate, -1) ? Globalize.translate("Yesterday") : datetime.toLocaleDateString(premiereDate, { + weekday: "long", + month: "short", + day: "numeric" + }) + } catch (err) {} + dateText != currentGroupName ? (currentGroup.length && groups.push({ + name: currentGroupName, + items: currentGroup + }), currentGroupName = dateText, currentGroup = [item]) : currentGroup.push(item) + } + var html = ""; + for (i = 0, length = groups.length; i < length; i++) { + var group = groups[i]; + html += '
    ', html += '

    ' + group.name + "

    "; + var allowBottomPadding = !0; + if (enableScrollX()) { + allowBottomPadding = !1; + var scrollXClass = "scrollX hiddenScrollX"; + layoutManager.tv && (scrollXClass += " smoothScrollX"), html += '
    ' + } else html += '
    '; + var supportsImageAnalysis = appHost.supports("imageanalysis"); + supportsImageAnalysis = !1, html += cardBuilder.getCardsHtml({ + items: group.items, + showLocationTypeIndicator: !1, + shape: getThumbShape(), + showTitle: !0, + preferThumb: !0, + lazy: !0, + showDetailsMenu: !0, + centerText: !supportsImageAnalysis, + showParentTitle: !0, + overlayText: !1, + allowBottomPadding: allowBottomPadding, + cardLayout: supportsImageAnalysis, + vibrant: supportsImageAnalysis, + overlayMoreButton: !0, + missingIndicator: !1 + }), html += "
    ", html += "
    " + } + elem.innerHTML = html, imageLoader.lazyChildren(elem) + } + return function(view, params, tabContent) { + var upcomingPromise, self = this; + self.preRender = function() { + upcomingPromise = getUpcomingPromise(view, params) + }, self.renderTab = function() { + loadUpcoming(tabContent, params, upcomingPromise) + } + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/useredit.js b/dashboard-ui/scripts/useredit.js index 1a7c44cc86..1cbce5dfbf 100644 --- a/dashboard-ui/scripts/useredit.js +++ b/dashboard-ui/scripts/useredit.js @@ -1 +1,85 @@ -define(["jQuery","loading","libraryMenu","fnchecked"],function($,loading,libraryMenu){"use strict";function loadDeleteFolders(page,user,mediaFolders){ApiClient.getJSON(ApiClient.getUrl("Channels",{SupportsMediaDeletion:!0})).then(function(channelsResult){var i,length,folder,isChecked,checkedAttribute,html="";for(i=0,length=mediaFolders.length;i"+folder.Name+"";for(i=0,length=channelsResult.Items.length;i"+folder.Name+"";$(".deleteAccess",page).html(html).trigger("create"),$("#chkEnableDeleteAllFolders",page).checked(user.Policy.EnableContentDeletion).trigger("change")})}function loadAuthProviders(page,user,providers){providers.length>1&&!user.Policy.IsAdministrator?page.querySelector(".fldSelectLoginProvider").classList.remove("hide"):page.querySelector(".fldSelectLoginProvider").classList.add("hide");var currentProviderId=user.Policy.AuthenticationProviderId;page.querySelector(".selectLoginProvider").innerHTML=providers.map(function(provider){var selected=provider.Id===currentProviderId||providers.length<2?" selected":"";return'"})}function loadUser(page,user){currentUser=user,ApiClient.getJSON(ApiClient.getUrl("Auth/Providers")).then(function(providers){loadAuthProviders(page,user,providers)}),ApiClient.getJSON(ApiClient.getUrl("Library/MediaFolders",{IsHidden:!1})).then(function(folders){loadDeleteFolders(page,user,folders.Items)}),user.Policy.IsDisabled?$(".disabledUserBanner",page).show():$(".disabledUserBanner",page).hide(),"Guest"==user.ConnectLinkType?($("#fldConnectInfo",page).hide(),$("#txtUserName",page).prop("disabled","disabled")):($("#txtUserName",page).prop("disabled","").removeAttr("disabled"),$("#fldConnectInfo",page).show()),$(".lnkEditUserPreferences",page).attr("href","mypreferencesmenu.html?userId="+user.Id),libraryMenu.setTitle(user.Name),page.querySelector(".username").innerHTML=user.Name,$("#txtUserName",page).val(user.Name),$("#txtConnectUserName",page).val(currentUser.ConnectUserName),$("#chkIsAdmin",page).checked(user.Policy.IsAdministrator),$("#chkDisabled",page).checked(user.Policy.IsDisabled),$("#chkIsHidden",page).checked(user.Policy.IsHidden),$("#chkRemoteControlSharedDevices",page).checked(user.Policy.EnableSharedDeviceControl),$("#chkEnableRemoteControlOtherUsers",page).checked(user.Policy.EnableRemoteControlOfOtherUsers),$("#chkEnableDownloading",page).checked(user.Policy.EnableContentDownloading),$("#chkManageLiveTv",page).checked(user.Policy.EnableLiveTvManagement),$("#chkEnableLiveTvAccess",page).checked(user.Policy.EnableLiveTvAccess),$("#chkEnableMediaPlayback",page).checked(user.Policy.EnableMediaPlayback),$("#chkEnableAudioPlaybackTranscoding",page).checked(user.Policy.EnableAudioPlaybackTranscoding),$("#chkEnableVideoPlaybackTranscoding",page).checked(user.Policy.EnableVideoPlaybackTranscoding),$("#chkEnableVideoPlaybackRemuxing",page).checked(user.Policy.EnablePlaybackRemuxing),$("#chkRemoteAccess",page).checked(null==user.Policy.EnableRemoteAccess||user.Policy.EnableRemoteAccess),$("#chkEnableSyncTranscoding",page).checked(user.Policy.EnableSyncTranscoding),$("#chkEnableConversion",page).checked(user.Policy.EnableMediaConversion||!1),$("#chkEnableSharing",page).checked(user.Policy.EnablePublicSharing),$("#txtRemoteClientBitrateLimit",page).val(user.Policy.RemoteClientBitrateLimit/1e6||""),loading.hide()}function onSaveComplete(page,user){loading.hide(),(currentUser.ConnectUserName||"")==$("#txtConnectUserName",page).val()?require(["toast"],function(toast){toast(Globalize.translate("SettingsSaved"))}):require(["connectHelper"],function(connectHelper){connectHelper.updateUserLink(ApiClient,user,$("#txtConnectUserName",page).val()).then(function(){loadData(page)})})}function saveUser(user,page){user.Name=$("#txtUserName",page).val(),user.Policy.IsAdministrator=$("#chkIsAdmin",page).checked(),user.Policy.IsHidden=$("#chkIsHidden",page).checked(),user.Policy.IsDisabled=$("#chkDisabled",page).checked(),user.Policy.EnableRemoteControlOfOtherUsers=$("#chkEnableRemoteControlOtherUsers",page).checked(),user.Policy.EnableLiveTvManagement=$("#chkManageLiveTv",page).checked(),user.Policy.EnableLiveTvAccess=$("#chkEnableLiveTvAccess",page).checked(),user.Policy.EnableSharedDeviceControl=$("#chkRemoteControlSharedDevices",page).checked(),user.Policy.EnableMediaPlayback=$("#chkEnableMediaPlayback",page).checked(),user.Policy.EnableAudioPlaybackTranscoding=$("#chkEnableAudioPlaybackTranscoding",page).checked(),user.Policy.EnableVideoPlaybackTranscoding=$("#chkEnableVideoPlaybackTranscoding",page).checked(),user.Policy.EnablePlaybackRemuxing=$("#chkEnableVideoPlaybackRemuxing",page).checked(),user.Policy.EnableContentDownloading=$("#chkEnableDownloading",page).checked(),user.Policy.EnableSyncTranscoding=$("#chkEnableSyncTranscoding",page).checked(),user.Policy.EnableMediaConversion=$("#chkEnableConversion",page).checked(),user.Policy.EnablePublicSharing=$("#chkEnableSharing",page).checked(),user.Policy.EnableRemoteAccess=$("#chkRemoteAccess",page).checked(),user.Policy.RemoteClientBitrateLimit=parseInt(1e6*parseFloat($("#txtRemoteClientBitrateLimit",page).val()||"0")),user.Policy.AuthenticationProviderId=page.querySelector(".selectLoginProvider").value,user.Policy.EnableContentDeletion=$("#chkEnableDeleteAllFolders",page).checked(),user.Policy.EnableContentDeletionFromFolders=user.Policy.EnableContentDeletion?[]:$(".chkFolder",page).get().filter(function(c){return c.checked}).map(function(c){return c.getAttribute("data-id")}),ApiClient.updateUser(user).then(function(){ApiClient.updateUserPolicy(user.Id,user.Policy).then(function(){onSaveComplete(page,user)})})}function onSubmit(){var page=$(this).parents(".page")[0];return loading.show(),getUser().then(function(result){saveUser(result,page)}),!1}function getUser(){var userId=getParameterByName("userId");return ApiClient.getUser(userId)}function loadData(page){loading.show(),getUser().then(function(user){loadUser(page,user)})}var currentUser;$(document).on("pageinit","#editUserPage",function(){$(".editUserProfileForm").off("submit",onSubmit).on("submit",onSubmit),this.querySelector(".sharingHelp").innerHTML=Globalize.translate("OptionAllowLinkSharingHelp",30);var page=this;$("#chkEnableDeleteAllFolders",this).on("change",function(){this.checked?$(".deleteAccess",page).hide():$(".deleteAccess",page).show()}),ApiClient.getServerConfiguration().then(function(config){config.EnableRemoteAccess?page.querySelector(".fldRemoteAccess").classList.remove("hide"):page.querySelector(".fldRemoteAccess").classList.add("hide")})}).on("pagebeforeshow","#editUserPage",function(){loadData(this)})}); \ No newline at end of file +define(["jQuery", "loading", "libraryMenu", "fnchecked"], function($, loading, libraryMenu) { + "use strict"; + + function loadDeleteFolders(page, user, mediaFolders) { + ApiClient.getJSON(ApiClient.getUrl("Channels", { + SupportsMediaDeletion: !0 + })).then(function(channelsResult) { + var i, length, folder, isChecked, checkedAttribute, html = ""; + for (i = 0, length = mediaFolders.length; i < length; i++) folder = mediaFolders[i], isChecked = user.Policy.EnableContentDeletion || -1 != user.Policy.EnableContentDeletionFromFolders.indexOf(folder.Id), checkedAttribute = isChecked ? ' checked="checked"' : "", html += '"; + for (i = 0, length = channelsResult.Items.length; i < length; i++) folder = channelsResult.Items[i], isChecked = user.Policy.EnableContentDeletion || -1 != user.Policy.EnableContentDeletionFromFolders.indexOf(folder.Id), checkedAttribute = isChecked ? ' checked="checked"' : "", html += '"; + $(".deleteAccess", page).html(html).trigger("create"), $("#chkEnableDeleteAllFolders", page).checked(user.Policy.EnableContentDeletion).trigger("change") + }) + } + + function loadAuthProviders(page, user, providers) { + providers.length > 1 && !user.Policy.IsAdministrator ? page.querySelector(".fldSelectLoginProvider").classList.remove("hide") : page.querySelector(".fldSelectLoginProvider").classList.add("hide"); + var currentProviderId = user.Policy.AuthenticationProviderId; + page.querySelector(".selectLoginProvider").innerHTML = providers.map(function(provider) { + var selected = provider.Id === currentProviderId || providers.length < 2 ? " selected" : ""; + return '" + }) + } + + function loadUser(page, user) { + currentUser = user, ApiClient.getJSON(ApiClient.getUrl("Auth/Providers")).then(function(providers) { + loadAuthProviders(page, user, providers) + }), ApiClient.getJSON(ApiClient.getUrl("Library/MediaFolders", { + IsHidden: !1 + })).then(function(folders) { + loadDeleteFolders(page, user, folders.Items) + }), user.Policy.IsDisabled ? $(".disabledUserBanner", page).show() : $(".disabledUserBanner", page).hide(), "Guest" == user.ConnectLinkType ? ($("#fldConnectInfo", page).hide(), $("#txtUserName", page).prop("disabled", "disabled")) : ($("#txtUserName", page).prop("disabled", "").removeAttr("disabled"), $("#fldConnectInfo", page).show()), $(".lnkEditUserPreferences", page).attr("href", "mypreferencesmenu.html?userId=" + user.Id), libraryMenu.setTitle(user.Name), page.querySelector(".username").innerHTML = user.Name, $("#txtUserName", page).val(user.Name), $("#txtConnectUserName", page).val(currentUser.ConnectUserName), $("#chkIsAdmin", page).checked(user.Policy.IsAdministrator), $("#chkDisabled", page).checked(user.Policy.IsDisabled), $("#chkIsHidden", page).checked(user.Policy.IsHidden), $("#chkRemoteControlSharedDevices", page).checked(user.Policy.EnableSharedDeviceControl), $("#chkEnableRemoteControlOtherUsers", page).checked(user.Policy.EnableRemoteControlOfOtherUsers), $("#chkEnableDownloading", page).checked(user.Policy.EnableContentDownloading), $("#chkManageLiveTv", page).checked(user.Policy.EnableLiveTvManagement), $("#chkEnableLiveTvAccess", page).checked(user.Policy.EnableLiveTvAccess), $("#chkEnableMediaPlayback", page).checked(user.Policy.EnableMediaPlayback), $("#chkEnableAudioPlaybackTranscoding", page).checked(user.Policy.EnableAudioPlaybackTranscoding), $("#chkEnableVideoPlaybackTranscoding", page).checked(user.Policy.EnableVideoPlaybackTranscoding), $("#chkEnableVideoPlaybackRemuxing", page).checked(user.Policy.EnablePlaybackRemuxing), $("#chkRemoteAccess", page).checked(null == user.Policy.EnableRemoteAccess || user.Policy.EnableRemoteAccess), $("#chkEnableSyncTranscoding", page).checked(user.Policy.EnableSyncTranscoding), $("#chkEnableConversion", page).checked(user.Policy.EnableMediaConversion || !1), $("#chkEnableSharing", page).checked(user.Policy.EnablePublicSharing), $("#txtRemoteClientBitrateLimit", page).val(user.Policy.RemoteClientBitrateLimit / 1e6 || ""), loading.hide() + } + + function onSaveComplete(page, user) { + loading.hide(), (currentUser.ConnectUserName || "") == $("#txtConnectUserName", page).val() ? require(["toast"], function(toast) { + toast(Globalize.translate("SettingsSaved")) + }) : require(["connectHelper"], function(connectHelper) { + connectHelper.updateUserLink(ApiClient, user, $("#txtConnectUserName", page).val()).then(function() { + loadData(page) + }) + }) + } + + function saveUser(user, page) { + user.Name = $("#txtUserName", page).val(), user.Policy.IsAdministrator = $("#chkIsAdmin", page).checked(), user.Policy.IsHidden = $("#chkIsHidden", page).checked(), user.Policy.IsDisabled = $("#chkDisabled", page).checked(), user.Policy.EnableRemoteControlOfOtherUsers = $("#chkEnableRemoteControlOtherUsers", page).checked(), user.Policy.EnableLiveTvManagement = $("#chkManageLiveTv", page).checked(), user.Policy.EnableLiveTvAccess = $("#chkEnableLiveTvAccess", page).checked(), user.Policy.EnableSharedDeviceControl = $("#chkRemoteControlSharedDevices", page).checked(), user.Policy.EnableMediaPlayback = $("#chkEnableMediaPlayback", page).checked(), user.Policy.EnableAudioPlaybackTranscoding = $("#chkEnableAudioPlaybackTranscoding", page).checked(), user.Policy.EnableVideoPlaybackTranscoding = $("#chkEnableVideoPlaybackTranscoding", page).checked(), user.Policy.EnablePlaybackRemuxing = $("#chkEnableVideoPlaybackRemuxing", page).checked(), user.Policy.EnableContentDownloading = $("#chkEnableDownloading", page).checked(), user.Policy.EnableSyncTranscoding = $("#chkEnableSyncTranscoding", page).checked(), user.Policy.EnableMediaConversion = $("#chkEnableConversion", page).checked(), user.Policy.EnablePublicSharing = $("#chkEnableSharing", page).checked(), user.Policy.EnableRemoteAccess = $("#chkRemoteAccess", page).checked(), user.Policy.RemoteClientBitrateLimit = parseInt(1e6 * parseFloat($("#txtRemoteClientBitrateLimit", page).val() || "0")), user.Policy.AuthenticationProviderId = page.querySelector(".selectLoginProvider").value, user.Policy.EnableContentDeletion = $("#chkEnableDeleteAllFolders", page).checked(), user.Policy.EnableContentDeletionFromFolders = user.Policy.EnableContentDeletion ? [] : $(".chkFolder", page).get().filter(function(c) { + return c.checked + }).map(function(c) { + return c.getAttribute("data-id") + }), ApiClient.updateUser(user).then(function() { + ApiClient.updateUserPolicy(user.Id, user.Policy).then(function() { + onSaveComplete(page, user) + }) + }) + } + + function onSubmit() { + var page = $(this).parents(".page")[0]; + return loading.show(), getUser().then(function(result) { + saveUser(result, page) + }), !1 + } + + function getUser() { + var userId = getParameterByName("userId"); + return ApiClient.getUser(userId) + } + + function loadData(page) { + loading.show(), getUser().then(function(user) { + loadUser(page, user) + }) + } + var currentUser; + $(document).on("pageinit", "#editUserPage", function() { + $(".editUserProfileForm").off("submit", onSubmit).on("submit", onSubmit), this.querySelector(".sharingHelp").innerHTML = Globalize.translate("OptionAllowLinkSharingHelp", 30); + var page = this; + $("#chkEnableDeleteAllFolders", this).on("change", function() { + this.checked ? $(".deleteAccess", page).hide() : $(".deleteAccess", page).show() + }), ApiClient.getServerConfiguration().then(function(config) { + config.EnableRemoteAccess ? page.querySelector(".fldRemoteAccess").classList.remove("hide") : page.querySelector(".fldRemoteAccess").classList.add("hide") + }) + }).on("pagebeforeshow", "#editUserPage", function() { + loadData(this) + }) +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/userlibraryaccess.js b/dashboard-ui/scripts/userlibraryaccess.js index 3d5f35182c..8352e90c3e 100644 --- a/dashboard-ui/scripts/userlibraryaccess.js +++ b/dashboard-ui/scripts/userlibraryaccess.js @@ -1 +1,112 @@ -define(["jQuery","loading","libraryMenu","fnchecked"],function($,loading,libraryMenu){"use strict";function triggerChange(select){var evt=document.createEvent("HTMLEvents");evt.initEvent("change",!1,!0),select.dispatchEvent(evt)}function loadMediaFolders(page,user,mediaFolders){var html="";html+='

    '+Globalize.translate("HeaderLibraries")+"

    ",html+='
    ';for(var i=0,length=mediaFolders.length;i"+folder.Name+""}html+="
    ",page.querySelector(".folderAccess").innerHTML=html;var chkEnableAllFolders=page.querySelector("#chkEnableAllFolders");chkEnableAllFolders.checked=user.Policy.EnableAllFolders,triggerChange(chkEnableAllFolders)}function loadChannels(page,user,channels){var html="";html+='

    '+Globalize.translate("HeaderChannels")+"

    ",html+='
    ';for(var i=0,length=channels.length;i"+folder.Name+""}html+="
    ",$(".channelAccess",page).show().html(html),channels.length?$(".channelAccessContainer",page).show():$(".channelAccessContainer",page).hide(),$("#chkEnableAllChannels",page).checked(user.Policy.EnableAllChannels).trigger("change")}function loadDevices(page,user,devices){var html="";html+='

    '+Globalize.translate("HeaderDevices")+"

    ",html+='
    ';for(var i=0,length=devices.length;i"+device.Name+" - "+device.AppName+""}html+="
    ",$(".deviceAccess",page).show().html(html),$("#chkEnableAllDevices",page).checked(user.Policy.EnableAllDevices).trigger("change"),user.Policy.IsAdministrator?page.querySelector(".deviceAccessContainer").classList.add("hide"):page.querySelector(".deviceAccessContainer").classList.remove("hide")}function loadUser(page,user,loggedInUser,mediaFolders,channels,devices){page.querySelector(".username").innerHTML=user.Name,libraryMenu.setTitle(user.Name),loadChannels(page,user,channels),loadMediaFolders(page,user,mediaFolders),loadDevices(page,user,devices),loading.hide()}function onSaveComplete(page){loading.hide(),require(["toast"],function(toast){toast(Globalize.translate("SettingsSaved"))})}function saveUser(user,page){user.Policy.EnableAllFolders=$("#chkEnableAllFolders",page).checked(),user.Policy.EnabledFolders=user.Policy.EnableAllFolders?[]:$(".chkFolder",page).get().filter(function(c){return c.checked}).map(function(c){return c.getAttribute("data-id")}),user.Policy.EnableAllChannels=$("#chkEnableAllChannels",page).checked(),user.Policy.EnabledChannels=user.Policy.EnableAllChannels?[]:$(".chkChannel",page).get().filter(function(c){return c.checked}).map(function(c){return c.getAttribute("data-id")}),user.Policy.EnableAllDevices=$("#chkEnableAllDevices",page).checked(),user.Policy.EnabledDevices=user.Policy.EnableAllDevices?[]:$(".chkDevice",page).get().filter(function(c){return c.checked}).map(function(c){return c.getAttribute("data-id")}),user.Policy.BlockedChannels=null,user.Policy.BlockedMediaFolders=null,ApiClient.updateUserPolicy(user.Id,user.Policy).then(function(){onSaveComplete(page)})}function onSubmit(){var page=$(this).parents(".page");loading.show();var userId=getParameterByName("userId");return ApiClient.getUser(userId).then(function(result){saveUser(result,page)}),!1}$(document).on("pageinit","#userLibraryAccessPage",function(){var page=this;$("#chkEnableAllDevices",page).on("change",function(){this.checked?$(".deviceAccessListContainer",page).hide():$(".deviceAccessListContainer",page).show()}),$("#chkEnableAllChannels",page).on("change",function(){this.checked?$(".channelAccessListContainer",page).hide():$(".channelAccessListContainer",page).show()}),page.querySelector("#chkEnableAllFolders").addEventListener("change",function(){this.checked?page.querySelector(".folderAccessListContainer").classList.add("hide"):page.querySelector(".folderAccessListContainer").classList.remove("hide")}),$(".userLibraryAccessForm").off("submit",onSubmit).on("submit",onSubmit)}).on("pageshow","#userLibraryAccessPage",function(){var page=this;loading.show();var promise1,userId=getParameterByName("userId");if(userId)promise1=ApiClient.getUser(userId);else{var deferred=$.Deferred();deferred.resolveWith(null,[{Configuration:{}}]),promise1=deferred.promise()}var promise2=Dashboard.getCurrentUser(),promise4=ApiClient.getJSON(ApiClient.getUrl("Library/MediaFolders",{IsHidden:!1})),promise5=ApiClient.getJSON(ApiClient.getUrl("Channels")),promise6=ApiClient.getJSON(ApiClient.getUrl("Devices"));Promise.all([promise1,promise2,promise4,promise5,promise6]).then(function(responses){loadUser(page,responses[0],responses[1],responses[2].Items,responses[3].Items,responses[4].Items)})})}); \ No newline at end of file +define(["jQuery", "loading", "libraryMenu", "fnchecked"], function($, loading, libraryMenu) { + "use strict"; + + function triggerChange(select) { + var evt = document.createEvent("HTMLEvents"); + evt.initEvent("change", !1, !0), select.dispatchEvent(evt) + } + + function loadMediaFolders(page, user, mediaFolders) { + var html = ""; + html += '

    ' + Globalize.translate("HeaderLibraries") + "

    ", html += '
    '; + for (var i = 0, length = mediaFolders.length; i < length; i++) { + var folder = mediaFolders[i], + isChecked = user.Policy.EnableAllFolders || -1 != user.Policy.EnabledFolders.indexOf(folder.Id), + checkedAttribute = isChecked ? ' checked="checked"' : ""; + html += '" + } + html += "
    ", page.querySelector(".folderAccess").innerHTML = html; + var chkEnableAllFolders = page.querySelector("#chkEnableAllFolders"); + chkEnableAllFolders.checked = user.Policy.EnableAllFolders, triggerChange(chkEnableAllFolders) + } + + function loadChannels(page, user, channels) { + var html = ""; + html += '

    ' + Globalize.translate("HeaderChannels") + "

    ", html += '
    '; + for (var i = 0, length = channels.length; i < length; i++) { + var folder = channels[i], + isChecked = user.Policy.EnableAllChannels || -1 != user.Policy.EnabledChannels.indexOf(folder.Id), + checkedAttribute = isChecked ? ' checked="checked"' : ""; + html += '" + } + html += "
    ", $(".channelAccess", page).show().html(html), channels.length ? $(".channelAccessContainer", page).show() : $(".channelAccessContainer", page).hide(), $("#chkEnableAllChannels", page).checked(user.Policy.EnableAllChannels).trigger("change") + } + + function loadDevices(page, user, devices) { + var html = ""; + html += '

    ' + Globalize.translate("HeaderDevices") + "

    ", html += '
    '; + for (var i = 0, length = devices.length; i < length; i++) { + var device = devices[i], + checkedAttribute = user.Policy.EnableAllDevices || -1 != user.Policy.EnabledDevices.indexOf(device.Id) ? ' checked="checked"' : ""; + html += '" + } + html += "
    ", $(".deviceAccess", page).show().html(html), $("#chkEnableAllDevices", page).checked(user.Policy.EnableAllDevices).trigger("change"), user.Policy.IsAdministrator ? page.querySelector(".deviceAccessContainer").classList.add("hide") : page.querySelector(".deviceAccessContainer").classList.remove("hide") + } + + function loadUser(page, user, loggedInUser, mediaFolders, channels, devices) { + page.querySelector(".username").innerHTML = user.Name, libraryMenu.setTitle(user.Name), loadChannels(page, user, channels), loadMediaFolders(page, user, mediaFolders), loadDevices(page, user, devices), loading.hide() + } + + function onSaveComplete(page) { + loading.hide(), require(["toast"], function(toast) { + toast(Globalize.translate("SettingsSaved")) + }) + } + + function saveUser(user, page) { + user.Policy.EnableAllFolders = $("#chkEnableAllFolders", page).checked(), user.Policy.EnabledFolders = user.Policy.EnableAllFolders ? [] : $(".chkFolder", page).get().filter(function(c) { + return c.checked + }).map(function(c) { + return c.getAttribute("data-id") + }), user.Policy.EnableAllChannels = $("#chkEnableAllChannels", page).checked(), user.Policy.EnabledChannels = user.Policy.EnableAllChannels ? [] : $(".chkChannel", page).get().filter(function(c) { + return c.checked + }).map(function(c) { + return c.getAttribute("data-id") + }), user.Policy.EnableAllDevices = $("#chkEnableAllDevices", page).checked(), user.Policy.EnabledDevices = user.Policy.EnableAllDevices ? [] : $(".chkDevice", page).get().filter(function(c) { + return c.checked + }).map(function(c) { + return c.getAttribute("data-id") + }), user.Policy.BlockedChannels = null, user.Policy.BlockedMediaFolders = null, ApiClient.updateUserPolicy(user.Id, user.Policy).then(function() { + onSaveComplete(page) + }) + } + + function onSubmit() { + var page = $(this).parents(".page"); + loading.show(); + var userId = getParameterByName("userId"); + return ApiClient.getUser(userId).then(function(result) { + saveUser(result, page) + }), !1 + } + $(document).on("pageinit", "#userLibraryAccessPage", function() { + var page = this; + $("#chkEnableAllDevices", page).on("change", function() { + this.checked ? $(".deviceAccessListContainer", page).hide() : $(".deviceAccessListContainer", page).show() + }), $("#chkEnableAllChannels", page).on("change", function() { + this.checked ? $(".channelAccessListContainer", page).hide() : $(".channelAccessListContainer", page).show() + }), page.querySelector("#chkEnableAllFolders").addEventListener("change", function() { + this.checked ? page.querySelector(".folderAccessListContainer").classList.add("hide") : page.querySelector(".folderAccessListContainer").classList.remove("hide") + }), $(".userLibraryAccessForm").off("submit", onSubmit).on("submit", onSubmit) + }).on("pageshow", "#userLibraryAccessPage", function() { + var page = this; + loading.show(); + var promise1, userId = getParameterByName("userId"); + if (userId) promise1 = ApiClient.getUser(userId); + else { + var deferred = $.Deferred(); + deferred.resolveWith(null, [{ + Configuration: {} + }]), promise1 = deferred.promise() + } + var promise2 = Dashboard.getCurrentUser(), + promise4 = ApiClient.getJSON(ApiClient.getUrl("Library/MediaFolders", { + IsHidden: !1 + })), + promise5 = ApiClient.getJSON(ApiClient.getUrl("Channels")), + promise6 = ApiClient.getJSON(ApiClient.getUrl("Devices")); + Promise.all([promise1, promise2, promise4, promise5, promise6]).then(function(responses) { + loadUser(page, responses[0], responses[1], responses[2].Items, responses[3].Items, responses[4].Items) + }) + }) +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/usernew.js b/dashboard-ui/scripts/usernew.js index eee5e45a8f..a9119a4aea 100644 --- a/dashboard-ui/scripts/usernew.js +++ b/dashboard-ui/scripts/usernew.js @@ -1 +1,76 @@ -define(["jQuery","loading","fnchecked","emby-checkbox"],function($,loading){"use strict";function loadMediaFolders(page,mediaFolders){var html="";html+='

    '+Globalize.translate("HeaderLibraries")+"

    ",html+='
    ';for(var i=0,length=mediaFolders.length;i'+folder.Name+""}html+="
    ",$(".folderAccess",page).html(html).trigger("create"),$("#chkEnableAllFolders",page).checked(!0).trigger("change")}function loadChannels(page,channels){var html="";html+='

    '+Globalize.translate("HeaderChannels")+"

    ",html+='
    ';for(var i=0,length=channels.length;i'+folder.Name+""}html+="
    ",$(".channelAccess",page).show().html(html).trigger("create"),channels.length?$(".channelAccessContainer",page).show():$(".channelAccessContainer",page).hide(),$("#chkEnableAllChannels",page).checked(!0).trigger("change")}function loadUser(page){$("#txtUserName",page).val(""),loading.show();var promise4=ApiClient.getJSON(ApiClient.getUrl("Library/MediaFolders",{IsHidden:!1})),promise5=ApiClient.getJSON(ApiClient.getUrl("Channels"));Promise.all([promise4,promise5]).then(function(responses){loadMediaFolders(page,responses[0].Items),loadChannels(page,responses[1].Items),loading.hide()})}function saveUser(page){var name=$("#txtUserName",page).val();ApiClient.createUser(name).then(function(user){user.Policy.EnableAllFolders=$("#chkEnableAllFolders",page).checked(),user.Policy.EnabledFolders=user.Policy.EnableAllFolders?[]:$(".chkFolder",page).get().filter(function(i){return i.checked}).map(function(i){return i.getAttribute("data-id")}),user.Policy.EnableAllChannels=$("#chkEnableAllChannels",page).checked(),user.Policy.EnabledChannels=user.Policy.EnableAllChannels?[]:$(".chkChannel",page).get().filter(function(i){return i.checked}).map(function(i){return i.getAttribute("data-id")}),ApiClient.updateUserPolicy(user.Id,user.Policy).then(function(){Dashboard.navigate("useredit.html?userId="+user.Id)})},function(response){400==response.status?Dashboard.alert({message:page.querySelector(".labelNewUserNameHelp").innerHTML}):require(["toast"],function(toast){toast(Globalize.translate("DefaultErrorMessage"))}),loading.hide()})}function onSubmit(){var page=$(this).parents(".page")[0];return loading.show(),saveUser(page),!1}function loadData(page){loadUser(page)}$(document).on("pageinit","#newUserPage",function(){var page=this;$("#chkEnableAllChannels",page).on("change",function(){this.checked?$(".channelAccessListContainer",page).hide():$(".channelAccessListContainer",page).show()}),$("#chkEnableAllFolders",page).on("change",function(){this.checked?$(".folderAccessListContainer",page).hide():$(".folderAccessListContainer",page).show()}),$(".newUserProfileForm").off("submit",onSubmit).on("submit",onSubmit)}).on("pageshow","#newUserPage",function(){loadData(this)})}); \ No newline at end of file +define(["jQuery", "loading", "fnchecked", "emby-checkbox"], function($, loading) { + "use strict"; + + function loadMediaFolders(page, mediaFolders) { + var html = ""; + html += '

    ' + Globalize.translate("HeaderLibraries") + "

    ", html += '
    '; + for (var i = 0, length = mediaFolders.length; i < length; i++) { + var folder = mediaFolders[i]; + html += '" + } + html += "
    ", $(".folderAccess", page).html(html).trigger("create"), $("#chkEnableAllFolders", page).checked(!0).trigger("change") + } + + function loadChannels(page, channels) { + var html = ""; + html += '

    ' + Globalize.translate("HeaderChannels") + "

    ", html += '
    '; + for (var i = 0, length = channels.length; i < length; i++) { + var folder = channels[i]; + html += '" + } + html += "
    ", $(".channelAccess", page).show().html(html).trigger("create"), channels.length ? $(".channelAccessContainer", page).show() : $(".channelAccessContainer", page).hide(), $("#chkEnableAllChannels", page).checked(!0).trigger("change") + } + + function loadUser(page) { + $("#txtUserName", page).val(""), loading.show(); + var promise4 = ApiClient.getJSON(ApiClient.getUrl("Library/MediaFolders", { + IsHidden: !1 + })), + promise5 = ApiClient.getJSON(ApiClient.getUrl("Channels")); + Promise.all([promise4, promise5]).then(function(responses) { + loadMediaFolders(page, responses[0].Items), loadChannels(page, responses[1].Items), loading.hide() + }) + } + + function saveUser(page) { + var name = $("#txtUserName", page).val(); + ApiClient.createUser(name).then(function(user) { + user.Policy.EnableAllFolders = $("#chkEnableAllFolders", page).checked(), user.Policy.EnabledFolders = user.Policy.EnableAllFolders ? [] : $(".chkFolder", page).get().filter(function(i) { + return i.checked + }).map(function(i) { + return i.getAttribute("data-id") + }), user.Policy.EnableAllChannels = $("#chkEnableAllChannels", page).checked(), user.Policy.EnabledChannels = user.Policy.EnableAllChannels ? [] : $(".chkChannel", page).get().filter(function(i) { + return i.checked + }).map(function(i) { + return i.getAttribute("data-id") + }), ApiClient.updateUserPolicy(user.Id, user.Policy).then(function() { + Dashboard.navigate("useredit.html?userId=" + user.Id) + }) + }, function(response) { + 400 == response.status ? Dashboard.alert({ + message: page.querySelector(".labelNewUserNameHelp").innerHTML + }) : require(["toast"], function(toast) { + toast(Globalize.translate("DefaultErrorMessage")) + }), loading.hide() + }) + } + + function onSubmit() { + var page = $(this).parents(".page")[0]; + return loading.show(), saveUser(page), !1 + } + + function loadData(page) { + loadUser(page) + } + $(document).on("pageinit", "#newUserPage", function() { + var page = this; + $("#chkEnableAllChannels", page).on("change", function() { + this.checked ? $(".channelAccessListContainer", page).hide() : $(".channelAccessListContainer", page).show() + }), $("#chkEnableAllFolders", page).on("change", function() { + this.checked ? $(".folderAccessListContainer", page).hide() : $(".folderAccessListContainer", page).show() + }), $(".newUserProfileForm").off("submit", onSubmit).on("submit", onSubmit) + }).on("pageshow", "#newUserPage", function() { + loadData(this) + }) +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/userparentalcontrol.js b/dashboard-ui/scripts/userparentalcontrol.js index 7d5773e6db..95062adff6 100644 --- a/dashboard-ui/scripts/userparentalcontrol.js +++ b/dashboard-ui/scripts/userparentalcontrol.js @@ -1 +1,188 @@ -define(["jQuery","datetime","loading","libraryMenu","listViewStyle","paper-icon-button-light"],function($,datetime,loading,libraryMenu){"use strict";function populateRatings(allParentalRatings,page){var html="";html+="";var i,length,rating,ratings=[];for(i=0,length=allParentalRatings.length;i"+rating.Name+"";$("#selectMaxParentalRating",page).html(html)}function loadUnratedItems(page,user){var items=[{name:Globalize.translate("OptionBlockBooks"),value:"Book"},{name:Globalize.translate("OptionBlockGames"),value:"Game"},{name:Globalize.translate("OptionBlockChannelContent"),value:"ChannelContent"},{name:Globalize.translate("OptionBlockLiveTvChannels"),value:"LiveTvChannel"},{name:Globalize.translate("OptionBlockMovies"),value:"Movie"},{name:Globalize.translate("OptionBlockMusic"),value:"Music"},{name:Globalize.translate("OptionBlockTrailers"),value:"Trailer"},{name:Globalize.translate("OptionBlockTvShows"),value:"Series"}],html="";html+='

    '+Globalize.translate("HeaderBlockItemsWithNoRating")+"

    ",html+='
    ';for(var i=0,length=items.length;i"+item.name+""}html+="
    ",$(".blockUnratedItems",page).html(html).trigger("create")}function loadUser(page,user,allParentalRatings){page.querySelector(".username").innerHTML=user.Name,libraryMenu.setTitle(user.Name),loadUnratedItems(page,user),loadBlockedTags(page,user.Policy.BlockedTags),populateRatings(allParentalRatings,page);var ratingValue="";if(user.Policy.MaxParentalRating)for(var i=0,length=allParentalRatings.length;i=rating.Value&&(ratingValue=rating.Value)}$("#selectMaxParentalRating",page).val(ratingValue),user.Policy.IsAdministrator?$(".accessScheduleSection",page).hide():$(".accessScheduleSection",page).show(),renderAccessSchedule(page,user.Policy.AccessSchedules||[]),loading.hide()}function loadBlockedTags(page,tags){var html=tags.map(function(h){var li='
    ';return li+='
    ',li+='

    ',li+=h,li+="

    ",li+="
    ",li+='',li+="
    "}).join("");html&&(html='
    '+html+"
    ");var elem=$(".blockedTags",page).html(html).trigger("create");$(".btnDeleteTag",elem).on("click",function(){var tag=this.getAttribute("data-tag"),newTags=tags.filter(function(t){return t!=tag});loadBlockedTags(page,newTags)})}function deleteAccessSchedule(page,schedules,index){schedules.splice(index,1),renderAccessSchedule(page,schedules)}function renderAccessSchedule(page,schedules){var html="",index=0;html+=schedules.map(function(a){var itemHtml="";return itemHtml+='
    ',itemHtml+='
    ',itemHtml+='

    ',itemHtml+=Globalize.translate("Option"+a.DayOfWeek),itemHtml+="

    ",itemHtml+='
    '+getDisplayTime(a.StartHour)+" - "+getDisplayTime(a.EndHour)+"
    ",itemHtml+="
    ",itemHtml+='',itemHtml+="
    ",index++,itemHtml}).join("");var accessScheduleList=page.querySelector(".accessScheduleList");accessScheduleList.innerHTML=html,$(".btnDelete",accessScheduleList).on("click",function(){deleteAccessSchedule(page,schedules,parseInt(this.getAttribute("data-index")))})}function onSaveComplete(page){loading.hide(),require(["toast"],function(toast){toast(Globalize.translate("SettingsSaved"))})}function saveUser(user,page){user.Policy.MaxParentalRating=$("#selectMaxParentalRating",page).val()||null,user.Policy.BlockUnratedItems=$(".chkUnratedItem",page).get().filter(function(i){return i.checked}).map(function(i){return i.getAttribute("data-itemtype")}),user.Policy.AccessSchedules=getSchedulesFromPage(page),user.Policy.BlockedTags=getBlockedTagsFromPage(page),ApiClient.updateUserPolicy(user.Id,user.Policy).then(function(){onSaveComplete(page)})}function getDisplayTime(hours){var minutes=0,pct=hours%1;return pct&&(minutes=parseInt(60*pct)),datetime.getDisplayTime(new Date(2e3,1,1,hours,minutes,0,0))}function showSchedulePopup(page,schedule,index){schedule=schedule||{},require(["components/accessschedule/accessschedule"],function(accessschedule){accessschedule.show({schedule:schedule}).then(function(updatedSchedule){var schedules=getSchedulesFromPage(page);-1==index&&(index=schedules.length),schedules[index]=updatedSchedule,renderAccessSchedule(page,schedules)})})}function getSchedulesFromPage(page){return $(".liSchedule",page).map(function(){return{DayOfWeek:this.getAttribute("data-day"),StartHour:this.getAttribute("data-start"),EndHour:this.getAttribute("data-end")}}).get()}function getBlockedTagsFromPage(page){return $(".blockedTag",page).map(function(){return this.getAttribute("data-tag")}).get()}function showBlockedTagPopup(page){require(["prompt"],function(prompt){prompt({label:Globalize.translate("LabelTag")}).then(function(value){var tags=getBlockedTagsFromPage(page);-1==tags.indexOf(value)&&(tags.push(value),loadBlockedTags(page,tags))})})}window.UserParentalControlPage={onSubmit:function(){var page=$(this).parents(".page");loading.show();var userId=getParameterByName("userId");return ApiClient.getUser(userId).then(function(result){saveUser(result,page)}),!1}},$(document).on("pageinit","#userParentalControlPage",function(){var page=this;$(".btnAddSchedule",page).on("click",function(){showSchedulePopup(page,{},-1)}),$(".btnAddBlockedTag",page).on("click",function(){showBlockedTagPopup(page)}),$(".userParentalControlForm").off("submit",UserParentalControlPage.onSubmit).on("submit",UserParentalControlPage.onSubmit)}).on("pageshow","#userParentalControlPage",function(){var page=this;loading.show();var userId=getParameterByName("userId"),promise1=ApiClient.getUser(userId),promise2=ApiClient.getParentalRatings();Promise.all([promise1,promise2]).then(function(responses){loadUser(page,responses[0],responses[1])})})}); \ No newline at end of file +define(["jQuery", "datetime", "loading", "libraryMenu", "listViewStyle", "paper-icon-button-light"], function($, datetime, loading, libraryMenu) { + "use strict"; + + function populateRatings(allParentalRatings, page) { + var html = ""; + html += ""; + var i, length, rating, ratings = []; + for (i = 0, length = allParentalRatings.length; i < length; i++) { + if (rating = allParentalRatings[i], ratings.length) { + var lastRating = ratings[ratings.length - 1]; + if (lastRating.Value === rating.Value) { + lastRating.Name += "/" + rating.Name; + continue + } + } + ratings.push({ + Name: rating.Name, + Value: rating.Value + }) + } + for (i = 0, length = ratings.length; i < length; i++) rating = ratings[i], html += ""; + $("#selectMaxParentalRating", page).html(html) + } + + function loadUnratedItems(page, user) { + var items = [{ + name: Globalize.translate("OptionBlockBooks"), + value: "Book" + }, { + name: Globalize.translate("OptionBlockGames"), + value: "Game" + }, { + name: Globalize.translate("OptionBlockChannelContent"), + value: "ChannelContent" + }, { + name: Globalize.translate("OptionBlockLiveTvChannels"), + value: "LiveTvChannel" + }, { + name: Globalize.translate("OptionBlockMovies"), + value: "Movie" + }, { + name: Globalize.translate("OptionBlockMusic"), + value: "Music" + }, { + name: Globalize.translate("OptionBlockTrailers"), + value: "Trailer" + }, { + name: Globalize.translate("OptionBlockTvShows"), + value: "Series" + }], + html = ""; + html += '

    ' + Globalize.translate("HeaderBlockItemsWithNoRating") + "

    ", html += '
    '; + for (var i = 0, length = items.length; i < length; i++) { + var item = items[i], + checkedAttribute = -1 != user.Policy.BlockUnratedItems.indexOf(item.value) ? ' checked="checked"' : ""; + html += '" + } + html += "
    ", $(".blockUnratedItems", page).html(html).trigger("create") + } + + function loadUser(page, user, allParentalRatings) { + page.querySelector(".username").innerHTML = user.Name, libraryMenu.setTitle(user.Name), loadUnratedItems(page, user), loadBlockedTags(page, user.Policy.BlockedTags), populateRatings(allParentalRatings, page); + var ratingValue = ""; + if (user.Policy.MaxParentalRating) + for (var i = 0, length = allParentalRatings.length; i < length; i++) { + var rating = allParentalRatings[i]; + user.Policy.MaxParentalRating >= rating.Value && (ratingValue = rating.Value) + } + $("#selectMaxParentalRating", page).val(ratingValue), user.Policy.IsAdministrator ? $(".accessScheduleSection", page).hide() : $(".accessScheduleSection", page).show(), renderAccessSchedule(page, user.Policy.AccessSchedules || []), loading.hide() + } + + function loadBlockedTags(page, tags) { + var html = tags.map(function(h) { + var li = '
    '; + return li += '
    ', li += '

    ', li += h, li += "

    ", li += "
    ", li += '', li += "
    " + }).join(""); + html && (html = '
    ' + html + "
    "); + var elem = $(".blockedTags", page).html(html).trigger("create"); + $(".btnDeleteTag", elem).on("click", function() { + var tag = this.getAttribute("data-tag"), + newTags = tags.filter(function(t) { + return t != tag + }); + loadBlockedTags(page, newTags) + }) + } + + function deleteAccessSchedule(page, schedules, index) { + schedules.splice(index, 1), renderAccessSchedule(page, schedules) + } + + function renderAccessSchedule(page, schedules) { + var html = "", + index = 0; + html += schedules.map(function(a) { + var itemHtml = ""; + return itemHtml += '
    ', itemHtml += '
    ', itemHtml += '

    ', itemHtml += Globalize.translate("Option" + a.DayOfWeek), itemHtml += "

    ", itemHtml += '
    ' + getDisplayTime(a.StartHour) + " - " + getDisplayTime(a.EndHour) + "
    ", itemHtml += "
    ", itemHtml += '', itemHtml += "
    ", index++, itemHtml + }).join(""); + var accessScheduleList = page.querySelector(".accessScheduleList"); + accessScheduleList.innerHTML = html, $(".btnDelete", accessScheduleList).on("click", function() { + deleteAccessSchedule(page, schedules, parseInt(this.getAttribute("data-index"))) + }) + } + + function onSaveComplete(page) { + loading.hide(), require(["toast"], function(toast) { + toast(Globalize.translate("SettingsSaved")) + }) + } + + function saveUser(user, page) { + user.Policy.MaxParentalRating = $("#selectMaxParentalRating", page).val() || null, user.Policy.BlockUnratedItems = $(".chkUnratedItem", page).get().filter(function(i) { + return i.checked + }).map(function(i) { + return i.getAttribute("data-itemtype") + }), user.Policy.AccessSchedules = getSchedulesFromPage(page), user.Policy.BlockedTags = getBlockedTagsFromPage(page), ApiClient.updateUserPolicy(user.Id, user.Policy).then(function() { + onSaveComplete(page) + }) + } + + function getDisplayTime(hours) { + var minutes = 0, + pct = hours % 1; + return pct && (minutes = parseInt(60 * pct)), datetime.getDisplayTime(new Date(2e3, 1, 1, hours, minutes, 0, 0)) + } + + function showSchedulePopup(page, schedule, index) { + schedule = schedule || {}, require(["components/accessschedule/accessschedule"], function(accessschedule) { + accessschedule.show({ + schedule: schedule + }).then(function(updatedSchedule) { + var schedules = getSchedulesFromPage(page); - 1 == index && (index = schedules.length), schedules[index] = updatedSchedule, renderAccessSchedule(page, schedules) + }) + }) + } + + function getSchedulesFromPage(page) { + return $(".liSchedule", page).map(function() { + return { + DayOfWeek: this.getAttribute("data-day"), + StartHour: this.getAttribute("data-start"), + EndHour: this.getAttribute("data-end") + } + }).get() + } + + function getBlockedTagsFromPage(page) { + return $(".blockedTag", page).map(function() { + return this.getAttribute("data-tag") + }).get() + } + + function showBlockedTagPopup(page) { + require(["prompt"], function(prompt) { + prompt({ + label: Globalize.translate("LabelTag") + }).then(function(value) { + var tags = getBlockedTagsFromPage(page); - 1 == tags.indexOf(value) && (tags.push(value), loadBlockedTags(page, tags)) + }) + }) + } + window.UserParentalControlPage = { + onSubmit: function() { + var page = $(this).parents(".page"); + loading.show(); + var userId = getParameterByName("userId"); + return ApiClient.getUser(userId).then(function(result) { + saveUser(result, page) + }), !1 + } + }, $(document).on("pageinit", "#userParentalControlPage", function() { + var page = this; + $(".btnAddSchedule", page).on("click", function() { + showSchedulePopup(page, {}, -1) + }), $(".btnAddBlockedTag", page).on("click", function() { + showBlockedTagPopup(page) + }), $(".userParentalControlForm").off("submit", UserParentalControlPage.onSubmit).on("submit", UserParentalControlPage.onSubmit) + }).on("pageshow", "#userParentalControlPage", function() { + var page = this; + loading.show(); + var userId = getParameterByName("userId"), + promise1 = ApiClient.getUser(userId), + promise2 = ApiClient.getParentalRatings(); + Promise.all([promise1, promise2]).then(function(responses) { + loadUser(page, responses[0], responses[1]) + }) + }) +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/userpassword.js b/dashboard-ui/scripts/userpassword.js index 79c340b979..41dc290248 100644 --- a/dashboard-ui/scripts/userpassword.js +++ b/dashboard-ui/scripts/userpassword.js @@ -1 +1,20 @@ -define(["jQuery","loading","libraryMenu"],function($,loading,libraryMenu){"use strict";function loadUser(page,user){libraryMenu.setTitle(user.Name),"Guest"==user.ConnectLinkType?$(".connectMessage",page).show():$(".connectMessage",page).hide(),loading.hide()}function loadData(page){loading.show();var userId=getParameterByName("userId");ApiClient.getUser(userId).then(function(user){loadUser(page,user)})}$(document).on("pageinit","#userPasswordPage",function(){$(".adminUpdatePasswordForm").off("submit",UpdatePasswordPage.onSubmit).on("submit",UpdatePasswordPage.onSubmit),$(".adminLocalAccessForm").off("submit",UpdatePasswordPage.onLocalAccessSubmit).on("submit",UpdatePasswordPage.onLocalAccessSubmit)}).on("pagebeforeshow","#userPasswordPage",function(){loadData(this)})}); \ No newline at end of file +define(["jQuery", "loading", "libraryMenu"], function($, loading, libraryMenu) { + "use strict"; + + function loadUser(page, user) { + libraryMenu.setTitle(user.Name), "Guest" == user.ConnectLinkType ? $(".connectMessage", page).show() : $(".connectMessage", page).hide(), loading.hide() + } + + function loadData(page) { + loading.show(); + var userId = getParameterByName("userId"); + ApiClient.getUser(userId).then(function(user) { + loadUser(page, user) + }) + } + $(document).on("pageinit", "#userPasswordPage", function() { + $(".adminUpdatePasswordForm").off("submit", UpdatePasswordPage.onSubmit).on("submit", UpdatePasswordPage.onSubmit), $(".adminLocalAccessForm").off("submit", UpdatePasswordPage.onLocalAccessSubmit).on("submit", UpdatePasswordPage.onLocalAccessSubmit) + }).on("pagebeforeshow", "#userPasswordPage", function() { + loadData(this) + }) +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/userpasswordpage.js b/dashboard-ui/scripts/userpasswordpage.js index 9562dcbf8a..1743e114b8 100644 --- a/dashboard-ui/scripts/userpasswordpage.js +++ b/dashboard-ui/scripts/userpasswordpage.js @@ -1 +1,96 @@ -define(["loading","libraryMenu","emby-linkbutton"],function(loading,libraryMenu){"use strict";function loadUser(page,params){var userid=params.userId;ApiClient.getUser(userid).then(function(user){Dashboard.getCurrentUser().then(function(loggedInUser){libraryMenu.setTitle(user.Name),page.querySelector(".username").innerHTML=user.Name;var showPasswordSection=!0,showLocalAccessSection=!1;"Guest"==user.ConnectLinkType?(page.querySelector(".localAccessSection").classList.add("hide"),showPasswordSection=!1):user.HasConfiguredPassword?(page.querySelector("#btnResetPassword").classList.remove("hide"),page.querySelector("#fldCurrentPassword").classList.remove("hide"),showLocalAccessSection=!0):(page.querySelector("#btnResetPassword").classList.add("hide"),page.querySelector("#fldCurrentPassword").classList.add("hide")),showPasswordSection&&(loggedInUser.Policy.IsAdministrator||user.Policy.EnableUserPreferenceAccess)?page.querySelector(".passwordSection").classList.remove("hide"):page.querySelector(".passwordSection").classList.add("hide"),showLocalAccessSection&&(loggedInUser.Policy.IsAdministrator||user.Policy.EnableUserPreferenceAccess)?page.querySelector(".localAccessSection").classList.remove("hide"):page.querySelector(".localAccessSection").classList.add("hide");var txtEasyPassword=page.querySelector("#txtEasyPassword");txtEasyPassword.value="",user.HasConfiguredEasyPassword?(txtEasyPassword.placeholder="******",page.querySelector("#btnResetEasyPassword").classList.remove("hide")):(txtEasyPassword.removeAttribute("placeholder"),txtEasyPassword.placeholder="",page.querySelector("#btnResetEasyPassword").classList.add("hide")),page.querySelector(".chkEnableLocalEasyPassword").checked=user.Configuration.EnableLocalPassword})}),page.querySelector("#txtCurrentPassword").value="",page.querySelector("#txtNewPassword").value="",page.querySelector("#txtNewPasswordConfirm").value=""}return function(view,params){function saveEasyPassword(){var userId=params.userId,easyPassword=view.querySelector("#txtEasyPassword").value;easyPassword?ApiClient.updateEasyPassword(userId,easyPassword).then(function(){onEasyPasswordSaved(userId)}):onEasyPasswordSaved(userId)}function onEasyPasswordSaved(userId){ApiClient.getUser(userId).then(function(user){user.Configuration.EnableLocalPassword=view.querySelector(".chkEnableLocalEasyPassword").checked,ApiClient.updateUserConfiguration(user.Id,user.Configuration).then(function(){loading.hide(),require(["toast"],function(toast){toast(Globalize.translate("MessageSettingsSaved"))}),loadUser(view,params)})})}function savePassword(){var userId=params.userId,currentPassword=view.querySelector("#txtCurrentPassword").value,newPassword=view.querySelector("#txtNewPassword").value;ApiClient.updateUserPassword(userId,currentPassword,newPassword).then(function(){loading.hide(),require(["toast"],function(toast){toast(Globalize.translate("PasswordSaved"))}),loadUser(view,params)},function(){loading.hide(),Dashboard.alert({title:Globalize.translate("HeaderLoginFailure"),message:Globalize.translate("MessageInvalidUser")})})}function onSubmit(e){var form=this;return form.querySelector("#txtNewPassword").value!=form.querySelector("#txtNewPasswordConfirm").value?require(["toast"],function(toast){toast(Globalize.translate("PasswordMatchError"))}):(loading.show(),savePassword()),e.preventDefault(),!1}function onLocalAccessSubmit(e){return loading.show(),saveEasyPassword(),e.preventDefault(),!1}function resetPassword(){var msg=Globalize.translate("PasswordResetConfirmation");require(["confirm"],function(confirm){confirm(msg,Globalize.translate("PasswordResetHeader")).then(function(){var userId=params.userId;loading.show(),ApiClient.resetUserPassword(userId).then(function(){loading.hide(),Dashboard.alert({message:Globalize.translate("PasswordResetComplete"),title:Globalize.translate("PasswordResetHeader")}),loadUser(view,params)})})})}function resetEasyPassword(){var msg=Globalize.translate("PinCodeResetConfirmation");require(["confirm"],function(confirm){confirm(msg,Globalize.translate("HeaderPinCodeReset")).then(function(){var userId=params.userId;loading.show(),ApiClient.resetEasyPassword(userId).then(function(){loading.hide(),Dashboard.alert({message:Globalize.translate("PinCodeResetComplete"),title:Globalize.translate("HeaderPinCodeReset")}),loadUser(view,params)})})})}view.querySelector(".updatePasswordForm").addEventListener("submit",onSubmit),view.querySelector(".localAccessForm").addEventListener("submit",onLocalAccessSubmit),view.querySelector("#btnResetEasyPassword").addEventListener("click",resetEasyPassword),view.querySelector("#btnResetPassword").addEventListener("click",resetPassword),view.addEventListener("viewshow",function(){loadUser(view,params)})}}); \ No newline at end of file +define(["loading", "libraryMenu", "emby-linkbutton"], function(loading, libraryMenu) { + "use strict"; + + function loadUser(page, params) { + var userid = params.userId; + ApiClient.getUser(userid).then(function(user) { + Dashboard.getCurrentUser().then(function(loggedInUser) { + libraryMenu.setTitle(user.Name), page.querySelector(".username").innerHTML = user.Name; + var showPasswordSection = !0, + showLocalAccessSection = !1; + "Guest" == user.ConnectLinkType ? (page.querySelector(".localAccessSection").classList.add("hide"), showPasswordSection = !1) : user.HasConfiguredPassword ? (page.querySelector("#btnResetPassword").classList.remove("hide"), page.querySelector("#fldCurrentPassword").classList.remove("hide"), showLocalAccessSection = !0) : (page.querySelector("#btnResetPassword").classList.add("hide"), page.querySelector("#fldCurrentPassword").classList.add("hide")), showPasswordSection && (loggedInUser.Policy.IsAdministrator || user.Policy.EnableUserPreferenceAccess) ? page.querySelector(".passwordSection").classList.remove("hide") : page.querySelector(".passwordSection").classList.add("hide"), showLocalAccessSection && (loggedInUser.Policy.IsAdministrator || user.Policy.EnableUserPreferenceAccess) ? page.querySelector(".localAccessSection").classList.remove("hide") : page.querySelector(".localAccessSection").classList.add("hide"); + var txtEasyPassword = page.querySelector("#txtEasyPassword"); + txtEasyPassword.value = "", user.HasConfiguredEasyPassword ? (txtEasyPassword.placeholder = "******", page.querySelector("#btnResetEasyPassword").classList.remove("hide")) : (txtEasyPassword.removeAttribute("placeholder"), txtEasyPassword.placeholder = "", page.querySelector("#btnResetEasyPassword").classList.add("hide")), page.querySelector(".chkEnableLocalEasyPassword").checked = user.Configuration.EnableLocalPassword + }) + }), page.querySelector("#txtCurrentPassword").value = "", page.querySelector("#txtNewPassword").value = "", page.querySelector("#txtNewPasswordConfirm").value = "" + } + return function(view, params) { + function saveEasyPassword() { + var userId = params.userId, + easyPassword = view.querySelector("#txtEasyPassword").value; + easyPassword ? ApiClient.updateEasyPassword(userId, easyPassword).then(function() { + onEasyPasswordSaved(userId) + }) : onEasyPasswordSaved(userId) + } + + function onEasyPasswordSaved(userId) { + ApiClient.getUser(userId).then(function(user) { + user.Configuration.EnableLocalPassword = view.querySelector(".chkEnableLocalEasyPassword").checked, ApiClient.updateUserConfiguration(user.Id, user.Configuration).then(function() { + loading.hide(), require(["toast"], function(toast) { + toast(Globalize.translate("MessageSettingsSaved")) + }), loadUser(view, params) + }) + }) + } + + function savePassword() { + var userId = params.userId, + currentPassword = view.querySelector("#txtCurrentPassword").value, + newPassword = view.querySelector("#txtNewPassword").value; + ApiClient.updateUserPassword(userId, currentPassword, newPassword).then(function() { + loading.hide(), require(["toast"], function(toast) { + toast(Globalize.translate("PasswordSaved")) + }), loadUser(view, params) + }, function() { + loading.hide(), Dashboard.alert({ + title: Globalize.translate("HeaderLoginFailure"), + message: Globalize.translate("MessageInvalidUser") + }) + }) + } + + function onSubmit(e) { + var form = this; + return form.querySelector("#txtNewPassword").value != form.querySelector("#txtNewPasswordConfirm").value ? require(["toast"], function(toast) { + toast(Globalize.translate("PasswordMatchError")) + }) : (loading.show(), savePassword()), e.preventDefault(), !1 + } + + function onLocalAccessSubmit(e) { + return loading.show(), saveEasyPassword(), e.preventDefault(), !1 + } + + function resetPassword() { + var msg = Globalize.translate("PasswordResetConfirmation"); + require(["confirm"], function(confirm) { + confirm(msg, Globalize.translate("PasswordResetHeader")).then(function() { + var userId = params.userId; + loading.show(), ApiClient.resetUserPassword(userId).then(function() { + loading.hide(), Dashboard.alert({ + message: Globalize.translate("PasswordResetComplete"), + title: Globalize.translate("PasswordResetHeader") + }), loadUser(view, params) + }) + }) + }) + } + + function resetEasyPassword() { + var msg = Globalize.translate("PinCodeResetConfirmation"); + require(["confirm"], function(confirm) { + confirm(msg, Globalize.translate("HeaderPinCodeReset")).then(function() { + var userId = params.userId; + loading.show(), ApiClient.resetEasyPassword(userId).then(function() { + loading.hide(), Dashboard.alert({ + message: Globalize.translate("PinCodeResetComplete"), + title: Globalize.translate("HeaderPinCodeReset") + }), loadUser(view, params) + }) + }) + }) + } + view.querySelector(".updatePasswordForm").addEventListener("submit", onSubmit), view.querySelector(".localAccessForm").addEventListener("submit", onLocalAccessSubmit), view.querySelector("#btnResetEasyPassword").addEventListener("click", resetEasyPassword), view.querySelector("#btnResetPassword").addEventListener("click", resetPassword), view.addEventListener("viewshow", function() { + loadUser(view, params) + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/userprofilespage.js b/dashboard-ui/scripts/userprofilespage.js index b3b9c616ae..2fc02b2fab 100644 --- a/dashboard-ui/scripts/userprofilespage.js +++ b/dashboard-ui/scripts/userprofilespage.js @@ -1 +1,207 @@ -define(["loading","dom","globalize","humanedate","paper-icon-button-light","cardStyle","emby-linkbutton","indicators","flexStyles"],function(loading,dom,globalize){"use strict";function deleteUser(page,id){var msg=globalize.translate("DeleteUserConfirmation");require(["confirm"],function(confirm){confirm({title:globalize.translate("DeleteUser"),text:msg,confirmText:globalize.translate("ButtonDelete"),primary:"cancel"}).then(function(){loading.show(),ApiClient.deleteUser(id).then(function(){loadData(page)})})})}function showUserMenu(elem){var card=dom.parentWithClass(elem,"card"),page=dom.parentWithClass(card,"page"),userId=card.getAttribute("data-userid"),menuItems=[];menuItems.push({name:globalize.translate("ButtonOpen"),id:"open",ironIcon:"mode-edit"}),menuItems.push({name:globalize.translate("ButtonLibraryAccess"),id:"access",ironIcon:"lock"}),menuItems.push({name:globalize.translate("ButtonParentalControl"),id:"parentalcontrol",ironIcon:"person"}),menuItems.push({name:globalize.translate("ButtonDelete"),id:"delete",ironIcon:"delete"}),require(["actionsheet"],function(actionsheet){actionsheet.show({items:menuItems,positionTo:card,callback:function(id){switch(id){case"open":Dashboard.navigate("useredit.html?userId="+userId);break;case"access":Dashboard.navigate("userlibraryaccess.html?userId="+userId);break;case"parentalcontrol":Dashboard.navigate("userparentalcontrol.html?userId="+userId);break;case"delete":deleteUser(page,userId)}}})})}function getUserHtml(user,addConnectIndicator){var html="",cssClass="card squareCard scalableCard squareCard-scalable";user.Policy.IsDisabled&&(cssClass+=" grayscale"),html+="
    ",html+='
    ',html+='
    ',html+='
    ',html+='';var imgUrl;user.PrimaryImageTag&&(imgUrl=ApiClient.getUserImageUrl(user.Id,{width:300,tag:user.PrimaryImageTag,type:"Primary"}));var imageClass="cardImage";user.Policy.IsDisabled&&(imageClass+=" disabledUser"),imgUrl?html+='",html+='
    ',html+='
    ',html+='
    ',html+=user.Name,html+="
    ",html+='',html+="
    ",html+='
    ';var lastSeen=getLastSeenText(user.LastActivityDate);return html+=""!=lastSeen?lastSeen:" ",html+="
    ",html+="
    ",html+="
    ",html+="
    "}function getLastSeenText(lastActivityDate){return lastActivityDate?"Last seen "+humane_date(lastActivityDate):""}function getUserSectionHtml(users,addConnectIndicator){var html="";return html+=users.map(function(u){return getUserHtml(u,addConnectIndicator)}).join("")}function renderUsers(page,users){page.querySelector(".localUsers").innerHTML=getUserSectionHtml(users,!0)}function showPendingUserMenu(elem){var menuItems=[];menuItems.push({name:globalize.translate("ButtonCancel"),id:"delete",ironIcon:"delete"}),require(["actionsheet"],function(actionsheet){var card=dom.parentWithClass(elem,"card"),page=dom.parentWithClass(card,"page"),id=card.getAttribute("data-id");actionsheet.show({items:menuItems,positionTo:card,callback:function(menuItemId){switch(menuItemId){case"delete":cancelAuthorization(page,id)}}})})}function getPendingUserHtml(user){var html="";html+="
    ",html+='
    ',html+='",html+='
    ',html+='
    ',html+='',html+="
    ",html+='
    ',html+=user.UserName,html+="
    ",html+="
    ",html+="
    ",html+="
    "}function renderPendingGuests(page,users){users.length?page.querySelector(".sectionPendingGuests").classList.remove("hide"):page.querySelector(".sectionPendingGuests").classList.add("hide");var html=users.map(getPendingUserHtml).join("");page.querySelector(".pending").innerHTML=html}function cancelAuthorization(page,id){loading.show(),ApiClient.ajax({type:"DELETE",url:ApiClient.getUrl("Connect/Pending",{Id:id})}).then(function(){loadData(page)})}function loadData(page){loading.show(),ApiClient.getUsers().then(function(users){renderUsers(page,users),loading.hide()}),ApiClient.getJSON(ApiClient.getUrl("Connect/Pending")).then(function(pending){renderPendingGuests(page,pending)})}function showLinkUser(page,userId){require(["components/guestinviter/connectlink"],function(connectlink){connectlink.show().then(function(){loadData(page)})})}function showInvitePopup(page){Dashboard.getCurrentUser().then(function(user){if(!user.ConnectUserId)return void showLinkUser(page,user.Id);require(["components/guestinviter/guestinviter"],function(guestinviter){guestinviter.show().then(function(){loadData(page)})})})}function showNewUserDialog(e){require(["dialog"],function(dialog){var items=[];items.push({name:globalize.translate("HeaderAddLocalUser"),id:"manual",type:"submit",description:globalize.translate("AddUserByManually")}),items.push({name:globalize.translate("HeaderInviteWithEmbyConnect"),id:"invite",description:globalize.translate("InviteAnEmbyConnectUser")}),items.push({name:globalize.translate("sharedcomponents#ButtonCancel"),id:"cancel",type:"cancel"});var options={title:globalize.translate("ButtonAddUser"),text:globalize.translate("HowWouldYouLikeToAddUser")};return options.buttons=items,dialog(options).then(function(result){var view=dom.parentWithClass(e.target,"page");"invite"===result?showInvitePopup(view):"manual"===result&&Dashboard.navigate("usernew.html")})})}pageIdOn("pageinit","userProfilesPage",function(){var page=this;page.querySelector(".btnAddUser").addEventListener("click",showNewUserDialog),page.querySelector(".localUsers").addEventListener("click",function(e){var btnUserMenu=dom.parentWithClass(e.target,"btnUserMenu");btnUserMenu&&showUserMenu(btnUserMenu)}),page.querySelector(".pending").addEventListener("click",function(e){var btnUserMenu=dom.parentWithClass(e.target,"btnUserMenu");btnUserMenu&&showPendingUserMenu(btnUserMenu)})}),pageIdOn("pagebeforeshow","userProfilesPage",function(){loadData(this)})}); \ No newline at end of file +define(["loading", "dom", "globalize", "humanedate", "paper-icon-button-light", "cardStyle", "emby-linkbutton", "indicators", "flexStyles"], function(loading, dom, globalize) { + "use strict"; + + function deleteUser(page, id) { + var msg = globalize.translate("DeleteUserConfirmation"); + require(["confirm"], function(confirm) { + confirm({ + title: globalize.translate("DeleteUser"), + text: msg, + confirmText: globalize.translate("ButtonDelete"), + primary: "cancel" + }).then(function() { + loading.show(), ApiClient.deleteUser(id).then(function() { + loadData(page) + }) + }) + }) + } + + function showUserMenu(elem) { + var card = dom.parentWithClass(elem, "card"), + page = dom.parentWithClass(card, "page"), + userId = card.getAttribute("data-userid"), + menuItems = []; + menuItems.push({ + name: globalize.translate("ButtonOpen"), + id: "open", + ironIcon: "mode-edit" + }), menuItems.push({ + name: globalize.translate("ButtonLibraryAccess"), + id: "access", + ironIcon: "lock" + }), menuItems.push({ + name: globalize.translate("ButtonParentalControl"), + id: "parentalcontrol", + ironIcon: "person" + }), menuItems.push({ + name: globalize.translate("ButtonDelete"), + id: "delete", + ironIcon: "delete" + }), require(["actionsheet"], function(actionsheet) { + actionsheet.show({ + items: menuItems, + positionTo: card, + callback: function(id) { + switch (id) { + case "open": + Dashboard.navigate("useredit.html?userId=" + userId); + break; + case "access": + Dashboard.navigate("userlibraryaccess.html?userId=" + userId); + break; + case "parentalcontrol": + Dashboard.navigate("userparentalcontrol.html?userId=" + userId); + break; + case "delete": + deleteUser(page, userId) + } + } + }) + }) + } + + function getUserHtml(user, addConnectIndicator) { + var html = "", + cssClass = "card squareCard scalableCard squareCard-scalable"; + user.Policy.IsDisabled && (cssClass += " grayscale"), html += "
    ", html += '
    ', html += '
    ', html += '
    ', html += ''; + var imgUrl; + user.PrimaryImageTag && (imgUrl = ApiClient.getUserImageUrl(user.Id, { + width: 300, + tag: user.PrimaryImageTag, + type: "Primary" + })); + var imageClass = "cardImage"; + user.Policy.IsDisabled && (imageClass += " disabledUser"), imgUrl ? html += '", html += '
    ', html += '
    ', html += '
    ', html += user.Name, html += "
    ", html += '', html += "
    ", html += '
    '; + var lastSeen = getLastSeenText(user.LastActivityDate); + return html += "" != lastSeen ? lastSeen : " ", html += "
    ", html += "
    ", html += "
    ", html += "
    " + } + + function getLastSeenText(lastActivityDate) { + return lastActivityDate ? "Last seen " + humane_date(lastActivityDate) : "" + } + + function getUserSectionHtml(users, addConnectIndicator) { + var html = ""; + return html += users.map(function(u) { + return getUserHtml(u, addConnectIndicator) + }).join("") + } + + function renderUsers(page, users) { + page.querySelector(".localUsers").innerHTML = getUserSectionHtml(users, !0) + } + + function showPendingUserMenu(elem) { + var menuItems = []; + menuItems.push({ + name: globalize.translate("ButtonCancel"), + id: "delete", + ironIcon: "delete" + }), require(["actionsheet"], function(actionsheet) { + var card = dom.parentWithClass(elem, "card"), + page = dom.parentWithClass(card, "page"), + id = card.getAttribute("data-id"); + actionsheet.show({ + items: menuItems, + positionTo: card, + callback: function(menuItemId) { + switch (menuItemId) { + case "delete": + cancelAuthorization(page, id) + } + } + }) + }) + } + + function getPendingUserHtml(user) { + var html = ""; + html += "
    ", html += '
    ', html += '", html += '
    ', html += '
    ', html += '', html += "
    ", html += '
    ', html += user.UserName, html += "
    ", html += "
    ", html += "
    ", html += "
    " + } + + function renderPendingGuests(page, users) { + users.length ? page.querySelector(".sectionPendingGuests").classList.remove("hide") : page.querySelector(".sectionPendingGuests").classList.add("hide"); + var html = users.map(getPendingUserHtml).join(""); + page.querySelector(".pending").innerHTML = html + } + + function cancelAuthorization(page, id) { + loading.show(), ApiClient.ajax({ + type: "DELETE", + url: ApiClient.getUrl("Connect/Pending", { + Id: id + }) + }).then(function() { + loadData(page) + }) + } + + function loadData(page) { + loading.show(), ApiClient.getUsers().then(function(users) { + renderUsers(page, users), loading.hide() + }), ApiClient.getJSON(ApiClient.getUrl("Connect/Pending")).then(function(pending) { + renderPendingGuests(page, pending) + }) + } + + function showLinkUser(page, userId) { + require(["components/guestinviter/connectlink"], function(connectlink) { + connectlink.show().then(function() { + loadData(page) + }) + }) + } + + function showInvitePopup(page) { + Dashboard.getCurrentUser().then(function(user) { + if (!user.ConnectUserId) return void showLinkUser(page, user.Id); + require(["components/guestinviter/guestinviter"], function(guestinviter) { + guestinviter.show().then(function() { + loadData(page) + }) + }) + }) + } + + function showNewUserDialog(e) { + require(["dialog"], function(dialog) { + var items = []; + items.push({ + name: globalize.translate("HeaderAddLocalUser"), + id: "manual", + type: "submit", + description: globalize.translate("AddUserByManually") + }), items.push({ + name: globalize.translate("HeaderInviteWithEmbyConnect"), + id: "invite", + description: globalize.translate("InviteAnEmbyConnectUser") + }), items.push({ + name: globalize.translate("sharedcomponents#ButtonCancel"), + id: "cancel", + type: "cancel" + }); + var options = { + title: globalize.translate("ButtonAddUser"), + text: globalize.translate("HowWouldYouLikeToAddUser") + }; + return options.buttons = items, dialog(options).then(function(result) { + var view = dom.parentWithClass(e.target, "page"); + "invite" === result ? showInvitePopup(view) : "manual" === result && Dashboard.navigate("usernew.html") + }) + }) + } + pageIdOn("pageinit", "userProfilesPage", function() { + var page = this; + page.querySelector(".btnAddUser").addEventListener("click", showNewUserDialog), page.querySelector(".localUsers").addEventListener("click", function(e) { + var btnUserMenu = dom.parentWithClass(e.target, "btnUserMenu"); + btnUserMenu && showUserMenu(btnUserMenu) + }), page.querySelector(".pending").addEventListener("click", function(e) { + var btnUserMenu = dom.parentWithClass(e.target, "btnUserMenu"); + btnUserMenu && showPendingUserMenu(btnUserMenu) + }) + }), pageIdOn("pagebeforeshow", "userProfilesPage", function() { + loadData(this) + }) +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/videoosd.js b/dashboard-ui/scripts/videoosd.js index 167b1e174e..97e8dddce1 100644 --- a/dashboard-ui/scripts/videoosd.js +++ b/dashboard-ui/scripts/videoosd.js @@ -1 +1,724 @@ -define(["playbackManager","dom","inputmanager","datetime","itemHelper","mediaInfo","focusManager","imageLoader","scrollHelper","events","connectionManager","browser","globalize","apphost","layoutManager","userSettings","scrollStyles","emby-slider","paper-icon-button-light","css!css/videoosd"],function(playbackManager,dom,inputManager,datetime,itemHelper,mediaInfo,focusManager,imageLoader,scrollHelper,events,connectionManager,browser,globalize,appHost,layoutManager,userSettings){"use strict";function seriesImageUrl(item,options){if("Episode"!==item.Type)return null;if(options=options||{},options.type=options.type||"Primary","Primary"===options.type&&item.SeriesPrimaryImageTag)return options.tag=item.SeriesPrimaryImageTag,connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.SeriesId,options);if("Thumb"===options.type){if(item.SeriesThumbImageTag)return options.tag=item.SeriesThumbImageTag,connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.SeriesId,options);if(item.ParentThumbImageTag)return options.tag=item.ParentThumbImageTag,connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.ParentThumbItemId,options)}return null}function imageUrl(item,options){return options=options||{},options.type=options.type||"Primary",item.ImageTags&&item.ImageTags[options.type]?(options.tag=item.ImageTags[options.type],connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.PrimaryImageItemId||item.Id,options)):"Primary"===options.type&&item.AlbumId&&item.AlbumPrimaryImageTag?(options.tag=item.AlbumPrimaryImageTag,connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.AlbumId,options)):null}function logoImageUrl(item,apiClient,options){return options=options||{},options.type="Logo",item.ImageTags&&item.ImageTags.Logo?(options.tag=item.ImageTags.Logo,apiClient.getScaledImageUrl(item.Id,options)):item.ParentLogoImageTag?(options.tag=item.ParentLogoImageTag,apiClient.getScaledImageUrl(item.ParentLogoItemId,options)):null}return function(view,params){function onVerticalSwipe(e,elem,data){var player=currentPlayer;if(player){var deltaY=data.currentDeltaY,windowSize=dom.getWindowSize();if(supportsBrightnessChange&&data.clientX1?view.querySelector(".btnAudio").classList.remove("hide"):view.querySelector(".btnAudio").classList.add("hide")}function setTitle(item,parentName){var url=logoImageUrl(item,connectionManager.getApiClient(item.ServerId),{});if(url){Emby.Page.setTitle("");var pageTitle=document.querySelector(".pageTitle");pageTitle.style.backgroundImage="url('"+url+"')",pageTitle.classList.add("pageTitleWithLogo"),pageTitle.classList.remove("pageTitleWithDefaultLogo"),pageTitle.innerHTML=""}else Emby.Page.setTitle(parentName||"");var documentTitle=parentName||(item?item.Name:null);documentTitle&&(document.title=documentTitle)}function setPoster(item,secondaryItem){var osdPoster=view.querySelector(".osdPoster");if(item){var imgUrl=seriesImageUrl(item,{type:"Primary"})||seriesImageUrl(item,{type:"Thumb"})||imageUrl(item,{type:"Primary"});if(!imgUrl&&secondaryItem&&(imgUrl=seriesImageUrl(secondaryItem,{type:"Primary"})||seriesImageUrl(secondaryItem,{type:"Thumb"})||imageUrl(secondaryItem,{type:"Primary"})),imgUrl)return void(osdPoster.innerHTML='')}osdPoster.innerHTML=""}function showOsd(){slideDownToShow(headerElement),showMainOsdControls(),startOsdHideTimer()}function hideOsd(){slideUpToHide(headerElement),hideMainOsdControls()}function toggleOsd(){"osd"===currentVisibleMenu?hideOsd():currentVisibleMenu||showOsd()}function startOsdHideTimer(){stopOsdHideTimer(),osdHideTimeout=setTimeout(hideOsd,5e3)}function stopOsdHideTimer(){osdHideTimeout&&(clearTimeout(osdHideTimeout),osdHideTimeout=null)}function slideDownToShow(elem){elem.classList.remove("osdHeader-hidden")}function slideUpToHide(elem){elem.classList.add("osdHeader-hidden")}function clearHideAnimationEventListeners(elem){dom.removeEventListener(elem,transitionEndEventName,onHideAnimationComplete,{once:!0})}function onHideAnimationComplete(e){var elem=e.target;elem.classList.add("hide"),dom.removeEventListener(elem,transitionEndEventName,onHideAnimationComplete,{once:!0})}function showMainOsdControls(){if(!currentVisibleMenu){var elem=osdBottomElement;currentVisibleMenu="osd",clearHideAnimationEventListeners(elem),elem.classList.remove("hide"),elem.offsetWidth,elem.classList.remove("videoOsdBottom-hidden"),layoutManager.mobile||setTimeout(function(){focusManager.focus(elem.querySelector(".btnPause"))},50)}}function hideMainOsdControls(){if("osd"===currentVisibleMenu){var elem=osdBottomElement;clearHideAnimationEventListeners(elem),elem.offsetWidth,elem.classList.add("videoOsdBottom-hidden"),dom.addEventListener(elem,transitionEndEventName,onHideAnimationComplete,{once:!0}),currentVisibleMenu=null}}function onPointerMove(e){if("mouse"===(e.pointerType||(layoutManager.mobile?"touch":"mouse"))){var eventX=e.screenX||0,eventY=e.screenY||0,obj=lastPointerMoveData;if(!obj)return void(lastPointerMoveData={x:eventX,y:eventY});if(Math.abs(eventX-obj.x)<10&&Math.abs(eventY-obj.y)<10)return;obj.x=eventX,obj.y=eventY,showOsd()}}function onInputCommand(e){var player=currentPlayer;switch(e.detail.command){case"left":"osd"===currentVisibleMenu?showOsd():currentVisibleMenu||(e.preventDefault(),playbackManager.rewind(player));break;case"right":"osd"===currentVisibleMenu?showOsd():currentVisibleMenu||(e.preventDefault(),playbackManager.fastForward(player));break;case"pageup":playbackManager.nextChapter(player);break;case"pagedown":playbackManager.previousChapter(player);break;case"up":case"down":case"select":case"menu":case"info":case"play":case"playpause":case"pause":case"fastforward":case"rewind":case"next":case"previous":showOsd();break;case"record":onRecordingCommand(),showOsd();break;case"togglestats":toggleStats()}}function onRecordingCommand(){var btnRecord=view.querySelector(".btnRecord");btnRecord.classList.contains("hide")||btnRecord.click()}function updateFullscreenIcon(){playbackManager.isFullscreen(currentPlayer)?(view.querySelector(".btnFullscreen").setAttribute("title",globalize.translate("ExitFullscreen")),view.querySelector(".btnFullscreen i").innerHTML=""):(view.querySelector(".btnFullscreen").setAttribute("title",globalize.translate("Fullscreen")),view.querySelector(".btnFullscreen i").innerHTML="")}function onPlayerChange(){bindToPlayer(playbackManager.getCurrentPlayer())}function onStateChanged(event,state){var player=this;state.NowPlayingItem&&(isEnabled=!0,updatePlayerStateInternal(event,player,state),updatePlaylist(player),enableStopOnBack(!0))}function onPlayPauseStateChanged(e){if(isEnabled){updatePlayPauseState(this.paused())}}function onVolumeChanged(e){if(isEnabled){var player=this;updatePlayerVolumeState(player,player.isMuted(),player.getVolume())}}function onPlaybackStart(e,state){console.log("nowplaying event: "+e.type);var player=this;onStateChanged.call(player,e,state),resetUpNextDialog()}function resetUpNextDialog(){comingUpNextDisplayed=!1;var dlg=currentUpNextDialog;dlg&&(dlg.destroy(),currentUpNextDialog=null)}function onPlaybackStopped(e,state){currentRuntimeTicks=null,resetUpNextDialog(),console.log("nowplaying event: "+e.type),"Video"!==state.NextMediaType&&(view.removeEventListener("viewbeforehide",onViewHideStopPlayback),Emby.Page.back())}function onMediaStreamsChanged(e){var player=this,state=playbackManager.getPlayerState(player);onStateChanged.call(player,{type:"init"},state)}function bindToPlayer(player){if(player!==currentPlayer&&(releaseCurrentPlayer(),currentPlayer=player,player)){var state=playbackManager.getPlayerState(player);onStateChanged.call(player,{type:"init"},state),events.on(player,"playbackstart",onPlaybackStart),events.on(player,"playbackstop",onPlaybackStopped),events.on(player,"volumechange",onVolumeChanged),events.on(player,"pause",onPlayPauseStateChanged),events.on(player,"unpause",onPlayPauseStateChanged),events.on(player,"timeupdate",onTimeUpdate),events.on(player,"fullscreenchange",updateFullscreenIcon),events.on(player,"mediastreamschange",onMediaStreamsChanged),resetUpNextDialog()}}function releaseCurrentPlayer(){destroyStats(),resetUpNextDialog();var player=currentPlayer;player&&(events.off(player,"playbackstart",onPlaybackStart),events.off(player,"playbackstop",onPlaybackStopped),events.off(player,"volumechange",onVolumeChanged),events.off(player,"pause",onPlayPauseStateChanged),events.off(player,"unpause",onPlayPauseStateChanged),events.off(player,"timeupdate",onTimeUpdate),events.off(player,"fullscreenchange",updateFullscreenIcon),events.off(player,"mediastreamschange",onMediaStreamsChanged),currentPlayer=null)}function onTimeUpdate(e){if(isEnabled){var now=(new Date).getTime();if(!(now-lastUpdateTime<700)){lastUpdateTime=now;var player=this;currentRuntimeTicks=playbackManager.duration(player);var currentTime=playbackManager.currentTime(player);updateTimeDisplay(currentTime,currentRuntimeTicks,playbackManager.playbackStartTime(player),playbackManager.getBufferedRanges(player));var item=currentItem;refreshProgramInfoIfNeeded(player,item),showComingUpNextIfNeeded(player,item,currentTime,currentRuntimeTicks)}}}function showComingUpNextIfNeeded(player,currentItem,currentTimeTicks,runtimeTicks){if(runtimeTicks&¤tTimeTicks&&!comingUpNextDisplayed&&!currentVisibleMenu&&"Episode"===currentItem.Type&&userSettings.enableNextVideoInfoOverlay()){var showAtSecondsLeft=runtimeTicks>=3e10?40:runtimeTicks>=24e9?35:30,showAtTicks=runtimeTicks-1e3*showAtSecondsLeft*1e4,timeRemainingTicks=runtimeTicks-currentTimeTicks;currentTimeTicks>=showAtTicks&&runtimeTicks>=6e9&&timeRemainingTicks>=2e8&&showComingUpNext(player)}}function onUpNextHidden(){"upnext"===currentVisibleMenu&&(currentVisibleMenu=null)}function showComingUpNext(player){require(["upNextDialog"],function(UpNextDialog){currentVisibleMenu||currentUpNextDialog||(currentVisibleMenu="upnext",comingUpNextDisplayed=!0,playbackManager.nextItem(player).then(function(nextItem){currentUpNextDialog=new UpNextDialog({parent:view.querySelector(".upNextContainer"),player:player,nextItem:nextItem}),events.on(currentUpNextDialog,"hide",onUpNextHidden)},onUpNextHidden))})}function refreshProgramInfoIfNeeded(player,item){if("TvChannel"===item.Type){var program=item.CurrentProgram;if(program&&program.EndDate)try{var endDate=datetime.parseISO8601Date(program.EndDate);if((new Date).getTime()>=endDate.getTime()){console.log("program info needs to be refreshed");var state=playbackManager.getPlayerState(player);onStateChanged.call(player,{type:"init"},state)}}catch(e){console.log("Error parsing date: "+program.EndDate)}}}function updatePlayPauseState(isPaused){view.querySelector(".btnPause i").innerHTML=isPaused?"":""}function updatePlayerStateInternal(event,player,state){var playState=state.PlayState||{};updatePlayPauseState(playState.IsPaused);var supportedCommands=playbackManager.getSupportedCommands(player);currentPlayerSupportedCommands=supportedCommands,supportsBrightnessChange=-1!==supportedCommands.indexOf("SetBrightness"),updatePlayerVolumeState(player,playState.IsMuted,playState.VolumeLevel),nowPlayingPositionSlider&&!nowPlayingPositionSlider.dragging&&(nowPlayingPositionSlider.disabled=!playState.CanSeek),btnFastForward.disabled=!playState.CanSeek,btnRewind.disabled=!playState.CanSeek;var nowPlayingItem=state.NowPlayingItem||{};playbackStartTimeTicks=playState.PlaybackStartTimeTicks,updateTimeDisplay(playState.PositionTicks,nowPlayingItem.RunTimeTicks,playState.PlaybackStartTimeTicks,playState.BufferedRanges||[]),updateNowPlayingInfo(player,state),state.MediaSource&&state.MediaSource.SupportsTranscoding&&-1!==supportedCommands.indexOf("SetMaxStreamingBitrate")?view.querySelector(".btnVideoOsdSettings").classList.remove("hide"):view.querySelector(".btnVideoOsdSettings").classList.add("hide");var isProgressClear=state.MediaSource&&null==state.MediaSource.RunTimeTicks;nowPlayingPositionSlider.setIsClear(isProgressClear),-1===supportedCommands.indexOf("ToggleFullscreen")||player.isLocalPlayer&&layoutManager.tv&&playbackManager.isFullscreen(player)?view.querySelector(".btnFullscreen").classList.add("hide"):view.querySelector(".btnFullscreen").classList.remove("hide"),-1===supportedCommands.indexOf("PictureInPicture")?view.querySelector(".btnPip").classList.add("hide"):view.querySelector(".btnPip").classList.remove("hide"),updateFullscreenIcon()}function getDisplayPercentByTimeOfDay(programStartDateMs,programRuntimeMs,currentTimeMs){return(currentTimeMs-programStartDateMs)/programRuntimeMs*100}function updateTimeDisplay(positionTicks,runtimeTicks,playbackStartTimeTicks,bufferedRanges){if(enableProgressByTimeOfDay){if(nowPlayingPositionSlider&&!nowPlayingPositionSlider.dragging)if(programStartDateMs&&programEndDateMs){var currentTimeMs=(playbackStartTimeTicks+(positionTicks||0))/1e4,programRuntimeMs=programEndDateMs-programStartDateMs;if(nowPlayingPositionSlider.value=getDisplayPercentByTimeOfDay(programStartDateMs,programRuntimeMs,currentTimeMs),bufferedRanges.length){var rangeStart=getDisplayPercentByTimeOfDay(programStartDateMs,programRuntimeMs,(playbackStartTimeTicks+(bufferedRanges[0].start||0))/1e4),rangeEnd=getDisplayPercentByTimeOfDay(programStartDateMs,programRuntimeMs,(playbackStartTimeTicks+(bufferedRanges[0].end||0))/1e4);nowPlayingPositionSlider.setBufferedRanges([{start:rangeStart,end:rangeEnd}])}else nowPlayingPositionSlider.setBufferedRanges([])}else nowPlayingPositionSlider.value=0,nowPlayingPositionSlider.setBufferedRanges([]);nowPlayingPositionText.innerHTML="",nowPlayingDurationText.innerHTML=""}else{if(nowPlayingPositionSlider&&!nowPlayingPositionSlider.dragging){if(runtimeTicks){var pct=positionTicks/runtimeTicks;pct*=100,nowPlayingPositionSlider.value=pct}else nowPlayingPositionSlider.value=0;runtimeTicks&&null!=positionTicks&¤tRuntimeTicks&&!enableProgressByTimeOfDay&¤tItem.RunTimeTicks&&"Recording"!==currentItem.Type?endsAtText.innerHTML="  -  "+mediaInfo.getEndsAtFromPosition(runtimeTicks,positionTicks,!0):endsAtText.innerHTML=""}nowPlayingPositionSlider&&nowPlayingPositionSlider.setBufferedRanges(bufferedRanges,runtimeTicks,positionTicks),updateTimeText(nowPlayingPositionText,positionTicks),updateTimeText(nowPlayingDurationText,runtimeTicks,!0)}}function updatePlayerVolumeState(player,isMuted,volumeLevel){var supportedCommands=currentPlayerSupportedCommands,showMuteButton=!0,showVolumeSlider=!0;-1===supportedCommands.indexOf("Mute")&&(showMuteButton=!1),-1===supportedCommands.indexOf("SetVolume")&&(showVolumeSlider=!1),player.isLocalPlayer&&appHost.supports("physicalvolumecontrol")&&(showMuteButton=!1,showVolumeSlider=!1),isMuted?(view.querySelector(".buttonMute").setAttribute("title",globalize.translate("Unmute")),view.querySelector(".buttonMute i").innerHTML=""):(view.querySelector(".buttonMute").setAttribute("title",globalize.translate("Mute")),view.querySelector(".buttonMute i").innerHTML=""),showMuteButton?view.querySelector(".buttonMute").classList.remove("hide"):view.querySelector(".buttonMute").classList.add("hide"),nowPlayingVolumeSlider&&(showVolumeSlider?nowPlayingVolumeSliderContainer.classList.remove("hide"):nowPlayingVolumeSliderContainer.classList.add("hide"),nowPlayingVolumeSlider.dragging||(nowPlayingVolumeSlider.value=volumeLevel||0))}function updatePlaylist(player){var btnPreviousTrack=view.querySelector(".btnPreviousTrack"),btnNextTrack=view.querySelector(".btnNextTrack");btnPreviousTrack.classList.remove("hide"),btnNextTrack.classList.remove("hide"),btnNextTrack.disabled=!1,btnPreviousTrack.disabled=!1}function updateTimeText(elem,ticks,divider){if(null==ticks)return void(elem.innerHTML="");var html=datetime.getDisplayRunningTime(ticks);divider&&(html=" / "+html),elem.innerHTML=html}function onSettingsButtonClick(e){var btn=this;require(["playerSettingsMenu"],function(playerSettingsMenu){var player=currentPlayer;player&&playerSettingsMenu.show({mediaType:"Video",player:player,positionTo:btn,stats:!0,onOption:onSettingsOption})})}function onSettingsOption(selectedOption){"stats"===selectedOption&&toggleStats()}function toggleStats(){require(["playerStats"],function(PlayerStats){var player=currentPlayer;player&&(statsOverlay?statsOverlay.toggle():statsOverlay=new PlayerStats({player:player}))})}function destroyStats(){statsOverlay&&(statsOverlay.destroy(),statsOverlay=null)}function showAudioTrackSelection(){var player=currentPlayer,audioTracks=playbackManager.audioTracks(player),currentIndex=playbackManager.getAudioStreamIndex(player),menuItems=audioTracks.map(function(stream){var opt={name:stream.DisplayTitle,id:stream.Index};return stream.Index===currentIndex&&(opt.selected=!0),opt}),positionTo=this;require(["actionsheet"],function(actionsheet){actionsheet.show({items:menuItems,title:globalize.translate("Audio"),positionTo:positionTo}).then(function(id){var index=parseInt(id);index!==currentIndex&&playbackManager.setAudioStreamIndex(index,player)})})}function showSubtitleTrackSelection(){var player=currentPlayer,streams=playbackManager.subtitleTracks(player),currentIndex=playbackManager.getSubtitleStreamIndex(player);null==currentIndex&&(currentIndex=-1),streams.unshift({Index:-1,DisplayTitle:globalize.translate("Off")});var menuItems=streams.map(function(stream){var opt={name:stream.DisplayTitle,id:stream.Index};return stream.Index===currentIndex&&(opt.selected=!0),opt}),positionTo=this;require(["actionsheet"],function(actionsheet){actionsheet.show({title:globalize.translate("Subtitles"),items:menuItems,positionTo:positionTo}).then(function(id){var index=parseInt(id);index!==currentIndex&&playbackManager.setSubtitleStreamIndex(index,player)})})}function onWindowKeyDown(e){if(!currentVisibleMenu&&(32===e.keyCode||13===e.keyCode))return playbackManager.playPause(currentPlayer),void showOsd();switch(e.key){case"f":e.ctrlKey||playbackManager.toggleFullscreen(currentPlayer);break;case"m":playbackManager.toggleMute(currentPlayer);break;case"ArrowLeft":case"Left":case"NavigationLeft":case"GamepadDPadLeft":case"GamepadLeftThumbstickLeft":e.shiftKey&&playbackManager.rewind(currentPlayer);break;case"ArrowRight":case"Right":case"NavigationRight":case"GamepadDPadRight":case"GamepadLeftThumbstickRight":e.shiftKey&&playbackManager.fastForward(currentPlayer)}}function getImgUrl(item,chapter,index,maxWidth,apiClient){return chapter.ImageTag?apiClient.getScaledImageUrl(item.Id,{maxWidth:maxWidth,tag:chapter.ImageTag,type:"Chapter",index:index}):null}function getChapterBubbleHtml(apiClient,item,chapters,positionTicks){for(var chapter,index=-1,i=0,length=chapters.length;i=currentChapter.StartPositionTicks&&(chapter=currentChapter,index=i)}if(!chapter)return null;var src=getImgUrl(item,chapter,index,400,apiClient);if(src){var html='
    ';return html+='',html+='
    ',html+='
    ',html+=chapter.Name,html+="
    ",html+='

    ',html+=datetime.getDisplayRunningTime(positionTicks),html+="

    ",html+="
    ",html+="
    "}return null}function onViewHideStopPlayback(){if(playbackManager.isPlayingVideo()){var player=currentPlayer;view.removeEventListener("viewbeforehide",onViewHideStopPlayback),releaseCurrentPlayer(),playbackManager.stop(player)}}function enableStopOnBack(enabled){view.removeEventListener("viewbeforehide",onViewHideStopPlayback),enabled&&playbackManager.isPlayingVideo(currentPlayer)&&view.addEventListener("viewbeforehide",onViewHideStopPlayback)}var currentPlayer,comingUpNextDisplayed,currentUpNextDialog,isEnabled,currentItem,recordingButtonManager,enableProgressByTimeOfDay,supportsBrightnessChange,currentVisibleMenu,statsOverlay,osdHideTimeout,lastPointerMoveData,self=this,currentPlayerSupportedCommands=[],currentRuntimeTicks=0,lastUpdateTime=0,programStartDateMs=0,programEndDateMs=0,playbackStartTimeTicks=0,nowPlayingVolumeSlider=view.querySelector(".osdVolumeSlider"),nowPlayingVolumeSliderContainer=view.querySelector(".osdVolumeSliderContainer"),nowPlayingPositionSlider=view.querySelector(".osdPositionSlider"),nowPlayingPositionText=view.querySelector(".osdPositionText"),nowPlayingDurationText=view.querySelector(".osdDurationText"),startTimeText=view.querySelector(".startTimeText"),endTimeText=view.querySelector(".endTimeText"),endsAtText=view.querySelector(".endsAtText"),btnRewind=view.querySelector(".btnRewind"),btnFastForward=view.querySelector(".btnFastForward"),transitionEndEventName=dom.whichTransitionEvent(),headerElement=document.querySelector(".skinHeader"),osdBottomElement=document.querySelector(".videoOsdBottom-maincontrols");view.addEventListener("viewbeforeshow",function(e){headerElement.classList.add("osdHeader"),Emby.Page.setTransparency("full")}),view.addEventListener("viewshow",function(e){events.on(playbackManager,"playerchange",onPlayerChange),bindToPlayer(playbackManager.getCurrentPlayer()),dom.addEventListener(document,window.PointerEvent?"pointermove":"mousemove",onPointerMove,{passive:!0}),document.body.classList.add("autoScrollY"),showOsd(),inputManager.on(window,onInputCommand),dom.addEventListener(window,"keydown",onWindowKeyDown,{passive:!0})}),view.addEventListener("viewbeforehide",function(){statsOverlay&&statsOverlay.enabled(!1),dom.removeEventListener(window,"keydown",onWindowKeyDown,{passive:!0}),stopOsdHideTimer(),headerElement.classList.remove("osdHeader"),headerElement.classList.remove("osdHeader-hidden"),dom.removeEventListener(document,window.PointerEvent?"pointermove":"mousemove",onPointerMove,{passive:!0}),document.body.classList.remove("autoScrollY"),inputManager.off(window,onInputCommand),events.off(playbackManager,"playerchange",onPlayerChange),releaseCurrentPlayer()}),view.querySelector(".btnFullscreen").addEventListener("click",function(){playbackManager.toggleFullscreen(currentPlayer)}),view.querySelector(".btnPip").addEventListener("click",function(){playbackManager.togglePictureInPicture(currentPlayer)}),view.querySelector(".btnVideoOsdSettings").addEventListener("click",onSettingsButtonClick),view.addEventListener("viewhide",function(){headerElement.classList.remove("hide")}),view.addEventListener("viewdestroy",function(){self.touchHelper&&(self.touchHelper.destroy(),self.touchHelper=null),recordingButtonManager&&(recordingButtonManager.destroy(),recordingButtonManager=null),destroyStats()});var lastPointerDown=0;dom.addEventListener(view,window.PointerEvent?"pointerdown":"click",function(e){if(dom.parentWithClass(e.target,["videoOsdBottom","upNextContainer"]))return void showOsd();var pointerType=e.pointerType||(layoutManager.mobile?"touch":"mouse"),now=(new Date).getTime();switch(pointerType){case"touch":now-lastPointerDown>300&&(lastPointerDown=now,toggleOsd());break;case"mouse":e.button||(playbackManager.playPause(currentPlayer),showOsd());break;default:playbackManager.playPause(currentPlayer),showOsd()}},{passive:!0}),browser.touch&&dom.addEventListener(view,"dblclick",onDoubleClick,{}),view.querySelector(".buttonMute").addEventListener("click",function(){playbackManager.toggleMute(currentPlayer)}),nowPlayingVolumeSlider.addEventListener("change",function(){playbackManager.setVolume(this.value,currentPlayer)}),nowPlayingPositionSlider.addEventListener("change",function(){var player=currentPlayer;if(player){var newPercent=parseFloat(this.value);if(enableProgressByTimeOfDay){var seekAirTimeTicks=newPercent/100*(programEndDateMs-programStartDateMs)*1e4;seekAirTimeTicks+=1e4*programStartDateMs,seekAirTimeTicks-=playbackStartTimeTicks,playbackManager.seek(seekAirTimeTicks,player)}else playbackManager.seekPercent(newPercent,player)}}),nowPlayingPositionSlider.getBubbleHtml=function(value){if(showOsd(),enableProgressByTimeOfDay){if(programStartDateMs&&programEndDateMs){var ms=programEndDateMs-programStartDateMs;ms/=100,ms*=value,ms+=programStartDateMs;return'

    '+getDisplayTimeWithoutAmPm(new Date(parseInt(ms)),!0)+"

    "}return"--:--"}if(!currentRuntimeTicks)return"--:--";var ticks=currentRuntimeTicks;ticks/=100,ticks*=value;var item=currentItem;if(item&&item.Chapters&&item.Chapters.length&&item.Chapters[0].ImageTag){var html=getChapterBubbleHtml(connectionManager.getApiClient(item.ServerId),item,item.Chapters,ticks);if(html)return html}return'

    '+datetime.getDisplayRunningTime(ticks)+"

    "},view.querySelector(".btnPreviousTrack").addEventListener("click",function(){playbackManager.previousTrack(currentPlayer)}),view.querySelector(".btnPause").addEventListener("click",function(){playbackManager.playPause(currentPlayer)}),view.querySelector(".btnNextTrack").addEventListener("click",function(){playbackManager.nextTrack(currentPlayer)}),btnRewind.addEventListener("click",function(){playbackManager.rewind(currentPlayer)}),btnFastForward.addEventListener("click",function(){playbackManager.fastForward(currentPlayer)}),view.querySelector(".btnAudio").addEventListener("click",showAudioTrackSelection),view.querySelector(".btnSubtitles").addEventListener("click",showSubtitleTrackSelection),browser.touch&&function(){require(["touchHelper"],function(TouchHelper){self.touchHelper=new TouchHelper(view,{swipeYThreshold:30,triggerOnMove:!0,preventDefaultOnMove:!0,ignoreTagNames:["BUTTON","INPUT","TEXTAREA"]}),events.on(self.touchHelper,"swipeup",onVerticalSwipe),events.on(self.touchHelper,"swipedown",onVerticalSwipe)})}()}}); \ No newline at end of file +define(["playbackManager", "dom", "inputmanager", "datetime", "itemHelper", "mediaInfo", "focusManager", "imageLoader", "scrollHelper", "events", "connectionManager", "browser", "globalize", "apphost", "layoutManager", "userSettings", "scrollStyles", "emby-slider", "paper-icon-button-light", "css!css/videoosd"], function(playbackManager, dom, inputManager, datetime, itemHelper, mediaInfo, focusManager, imageLoader, scrollHelper, events, connectionManager, browser, globalize, appHost, layoutManager, userSettings) { + "use strict"; + + function seriesImageUrl(item, options) { + if ("Episode" !== item.Type) return null; + if (options = options || {}, options.type = options.type || "Primary", "Primary" === options.type && item.SeriesPrimaryImageTag) return options.tag = item.SeriesPrimaryImageTag, connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.SeriesId, options); + if ("Thumb" === options.type) { + if (item.SeriesThumbImageTag) return options.tag = item.SeriesThumbImageTag, connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.SeriesId, options); + if (item.ParentThumbImageTag) return options.tag = item.ParentThumbImageTag, connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.ParentThumbItemId, options) + } + return null + } + + function imageUrl(item, options) { + return options = options || {}, options.type = options.type || "Primary", item.ImageTags && item.ImageTags[options.type] ? (options.tag = item.ImageTags[options.type], connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.PrimaryImageItemId || item.Id, options)) : "Primary" === options.type && item.AlbumId && item.AlbumPrimaryImageTag ? (options.tag = item.AlbumPrimaryImageTag, connectionManager.getApiClient(item.ServerId).getScaledImageUrl(item.AlbumId, options)) : null + } + + function logoImageUrl(item, apiClient, options) { + return options = options || {}, options.type = "Logo", item.ImageTags && item.ImageTags.Logo ? (options.tag = item.ImageTags.Logo, apiClient.getScaledImageUrl(item.Id, options)) : item.ParentLogoImageTag ? (options.tag = item.ParentLogoImageTag, apiClient.getScaledImageUrl(item.ParentLogoItemId, options)) : null + } + return function(view, params) { + function onVerticalSwipe(e, elem, data) { + var player = currentPlayer; + if (player) { + var deltaY = data.currentDeltaY, + windowSize = dom.getWindowSize(); + if (supportsBrightnessChange && data.clientX < windowSize.innerWidth / 2) return void doBrightnessTouch(deltaY, player, windowSize.innerHeight); + doVolumeTouch(deltaY, player, windowSize.innerHeight) + } + } + + function doBrightnessTouch(deltaY, player, viewHeight) { + var delta = -deltaY / viewHeight * 100, + newValue = playbackManager.getBrightness(player) + delta; + newValue = Math.min(newValue, 100), newValue = Math.max(newValue, 0), playbackManager.setBrightness(newValue, player) + } + + function doVolumeTouch(deltaY, player, viewHeight) { + var delta = -deltaY / viewHeight * 100, + newValue = playbackManager.getVolume(player) + delta; + newValue = Math.min(newValue, 100), newValue = Math.max(newValue, 0), playbackManager.setVolume(newValue, player) + } + + function onDoubleClick(e) { + var clientX = e.clientX; + if (null != clientX) { + clientX < dom.getWindowSize().innerWidth / 2 ? playbackManager.rewind(currentPlayer) : playbackManager.fastForward(currentPlayer), e.preventDefault(), e.stopPropagation() + } + } + + function getDisplayItem(item) { + if ("TvChannel" === item.Type) { + var apiClient = connectionManager.getApiClient(item.ServerId); + return apiClient.getItem(apiClient.getCurrentUserId(), item.Id).then(function(refreshedItem) { + return { + originalItem: refreshedItem, + displayItem: refreshedItem.CurrentProgram + } + }) + } + return Promise.resolve({ + originalItem: item + }) + } + + function updateRecordingButton(item) { + if (!item || "Program" !== item.Type) return recordingButtonManager && (recordingButtonManager.destroy(), recordingButtonManager = null), void view.querySelector(".btnRecord").classList.add("hide"); + connectionManager.getApiClient(item.ServerId).getCurrentUser().then(function(user) { + user.Policy.EnableLiveTvManagement && require(["recordingButton"], function(RecordingButton) { + if (recordingButtonManager) return void recordingButtonManager.refreshItem(item); + recordingButtonManager = new RecordingButton({ + item: item, + button: view.querySelector(".btnRecord") + }), view.querySelector(".btnRecord").classList.remove("hide") + }) + }) + } + + function updateDisplayItem(itemInfo) { + var item = itemInfo.originalItem; + currentItem = item; + var displayItem = itemInfo.displayItem || item; + updateRecordingButton(displayItem), setPoster(displayItem, item); + var parentName = displayItem.SeriesName || displayItem.Album; + (displayItem.EpisodeTitle || displayItem.IsSeries) && (parentName = displayItem.Name), setTitle(displayItem, parentName); + var titleElement, osdTitle = view.querySelector(".osdTitle"); + titleElement = osdTitle; + var displayName = itemHelper.getDisplayName(displayItem, { + includeParentInfo: "Program" !== displayItem.Type, + includeIndexNumber: "Program" !== displayItem.Type + }); + !displayName && displayItem.Type, titleElement.innerHTML = displayName, displayName ? titleElement.classList.remove("hide") : titleElement.classList.add("hide"); + var mediaInfoHtml = mediaInfo.getPrimaryMediaInfoHtml(displayItem, { + runtime: !1, + subtitles: !1, + tomatoes: !1, + endsAt: !1, + episodeTitle: !1, + originalAirDate: "Program" !== displayItem.Type, + episodeTitleIndexNumber: "Program" !== displayItem.Type, + programIndicator: !1 + }), + osdMediaInfo = view.querySelector(".osdMediaInfo"); + osdMediaInfo.innerHTML = mediaInfoHtml, mediaInfoHtml ? osdMediaInfo.classList.remove("hide") : osdMediaInfo.classList.add("hide"); + var secondaryMediaInfo = view.querySelector(".osdSecondaryMediaInfo"), + secondaryMediaInfoHtml = mediaInfo.getSecondaryMediaInfoHtml(displayItem, { + startDate: !1, + programTime: !1 + }); + secondaryMediaInfo.innerHTML = secondaryMediaInfoHtml, secondaryMediaInfoHtml ? secondaryMediaInfo.classList.remove("hide") : secondaryMediaInfo.classList.add("hide"), displayName ? view.querySelector(".osdMainTextContainer").classList.remove("hide") : view.querySelector(".osdMainTextContainer").classList.add("hide"), enableProgressByTimeOfDay ? (setDisplayTime(startTimeText, displayItem.StartDate), setDisplayTime(endTimeText, displayItem.EndDate), startTimeText.classList.remove("hide"), endTimeText.classList.remove("hide"), programStartDateMs = displayItem.StartDate ? datetime.parseISO8601Date(displayItem.StartDate).getTime() : 0, programEndDateMs = displayItem.EndDate ? datetime.parseISO8601Date(displayItem.EndDate).getTime() : 0) : (startTimeText.classList.add("hide"), endTimeText.classList.add("hide"), startTimeText.innerHTML = "", endTimeText.innerHTML = "", programStartDateMs = 0, programEndDateMs = 0) + } + + function getDisplayTimeWithoutAmPm(date, showSeconds) { + return showSeconds ? datetime.toLocaleTimeString(date, { + hour: "numeric", + minute: "2-digit", + second: "2-digit" + }).toLowerCase().replace("am", "").replace("pm", "").trim() : datetime.getDisplayTime(date).toLowerCase().replace("am", "").replace("pm", "").trim() + } + + function setDisplayTime(elem, date) { + var html; + date && (date = datetime.parseISO8601Date(date), html = getDisplayTimeWithoutAmPm(date)), elem.innerHTML = html || "" + } + + function shouldEnableProgressByTimeOfDay(item) { + return !("TvChannel" !== item.Type || !item.CurrentProgram) + } + + function updateNowPlayingInfo(player, state) { + var item = state.NowPlayingItem; + if (currentItem = item, !item) return setPoster(null), updateRecordingButton(null), Emby.Page.setTitle(""), nowPlayingVolumeSlider.disabled = !0, nowPlayingPositionSlider.disabled = !0, btnFastForward.disabled = !0, btnRewind.disabled = !0, view.querySelector(".btnSubtitles").classList.add("hide"), view.querySelector(".btnAudio").classList.add("hide"), view.querySelector(".osdTitle").innerHTML = "", void(view.querySelector(".osdMediaInfo").innerHTML = ""); + enableProgressByTimeOfDay = shouldEnableProgressByTimeOfDay(item), getDisplayItem(item).then(updateDisplayItem), nowPlayingVolumeSlider.disabled = !1, nowPlayingPositionSlider.disabled = !1, btnFastForward.disabled = !1, btnRewind.disabled = !1, playbackManager.subtitleTracks(player).length ? view.querySelector(".btnSubtitles").classList.remove("hide") : view.querySelector(".btnSubtitles").classList.add("hide"), playbackManager.audioTracks(player).length > 1 ? view.querySelector(".btnAudio").classList.remove("hide") : view.querySelector(".btnAudio").classList.add("hide") + } + + function setTitle(item, parentName) { + var url = logoImageUrl(item, connectionManager.getApiClient(item.ServerId), {}); + if (url) { + Emby.Page.setTitle(""); + var pageTitle = document.querySelector(".pageTitle"); + pageTitle.style.backgroundImage = "url('" + url + "')", pageTitle.classList.add("pageTitleWithLogo"), pageTitle.classList.remove("pageTitleWithDefaultLogo"), pageTitle.innerHTML = "" + } else Emby.Page.setTitle(parentName || ""); + var documentTitle = parentName || (item ? item.Name : null); + documentTitle && (document.title = documentTitle) + } + + function setPoster(item, secondaryItem) { + var osdPoster = view.querySelector(".osdPoster"); + if (item) { + var imgUrl = seriesImageUrl(item, { + type: "Primary" + }) || seriesImageUrl(item, { + type: "Thumb" + }) || imageUrl(item, { + type: "Primary" + }); + if (!imgUrl && secondaryItem && (imgUrl = seriesImageUrl(secondaryItem, { + type: "Primary" + }) || seriesImageUrl(secondaryItem, { + type: "Thumb" + }) || imageUrl(secondaryItem, { + type: "Primary" + })), imgUrl) return void(osdPoster.innerHTML = '') + } + osdPoster.innerHTML = "" + } + + function showOsd() { + slideDownToShow(headerElement), showMainOsdControls(), startOsdHideTimer() + } + + function hideOsd() { + slideUpToHide(headerElement), hideMainOsdControls() + } + + function toggleOsd() { + "osd" === currentVisibleMenu ? hideOsd() : currentVisibleMenu || showOsd() + } + + function startOsdHideTimer() { + stopOsdHideTimer(), osdHideTimeout = setTimeout(hideOsd, 5e3) + } + + function stopOsdHideTimer() { + osdHideTimeout && (clearTimeout(osdHideTimeout), osdHideTimeout = null) + } + + function slideDownToShow(elem) { + elem.classList.remove("osdHeader-hidden") + } + + function slideUpToHide(elem) { + elem.classList.add("osdHeader-hidden") + } + + function clearHideAnimationEventListeners(elem) { + dom.removeEventListener(elem, transitionEndEventName, onHideAnimationComplete, { + once: !0 + }) + } + + function onHideAnimationComplete(e) { + var elem = e.target; + elem.classList.add("hide"), dom.removeEventListener(elem, transitionEndEventName, onHideAnimationComplete, { + once: !0 + }) + } + + function showMainOsdControls() { + if (!currentVisibleMenu) { + var elem = osdBottomElement; + currentVisibleMenu = "osd", clearHideAnimationEventListeners(elem), elem.classList.remove("hide"), elem.offsetWidth, elem.classList.remove("videoOsdBottom-hidden"), layoutManager.mobile || setTimeout(function() { + focusManager.focus(elem.querySelector(".btnPause")) + }, 50) + } + } + + function hideMainOsdControls() { + if ("osd" === currentVisibleMenu) { + var elem = osdBottomElement; + clearHideAnimationEventListeners(elem), elem.offsetWidth, elem.classList.add("videoOsdBottom-hidden"), dom.addEventListener(elem, transitionEndEventName, onHideAnimationComplete, { + once: !0 + }), currentVisibleMenu = null + } + } + + function onPointerMove(e) { + if ("mouse" === (e.pointerType || (layoutManager.mobile ? "touch" : "mouse"))) { + var eventX = e.screenX || 0, + eventY = e.screenY || 0, + obj = lastPointerMoveData; + if (!obj) return void(lastPointerMoveData = { + x: eventX, + y: eventY + }); + if (Math.abs(eventX - obj.x) < 10 && Math.abs(eventY - obj.y) < 10) return; + obj.x = eventX, obj.y = eventY, showOsd() + } + } + + function onInputCommand(e) { + var player = currentPlayer; + switch (e.detail.command) { + case "left": + "osd" === currentVisibleMenu ? showOsd() : currentVisibleMenu || (e.preventDefault(), playbackManager.rewind(player)); + break; + case "right": + "osd" === currentVisibleMenu ? showOsd() : currentVisibleMenu || (e.preventDefault(), playbackManager.fastForward(player)); + break; + case "pageup": + playbackManager.nextChapter(player); + break; + case "pagedown": + playbackManager.previousChapter(player); + break; + case "up": + case "down": + case "select": + case "menu": + case "info": + case "play": + case "playpause": + case "pause": + case "fastforward": + case "rewind": + case "next": + case "previous": + showOsd(); + break; + case "record": + onRecordingCommand(), showOsd(); + break; + case "togglestats": + toggleStats() + } + } + + function onRecordingCommand() { + var btnRecord = view.querySelector(".btnRecord"); + btnRecord.classList.contains("hide") || btnRecord.click() + } + + function updateFullscreenIcon() { + playbackManager.isFullscreen(currentPlayer) ? (view.querySelector(".btnFullscreen").setAttribute("title", globalize.translate("ExitFullscreen")), view.querySelector(".btnFullscreen i").innerHTML = "") : (view.querySelector(".btnFullscreen").setAttribute("title", globalize.translate("Fullscreen")), view.querySelector(".btnFullscreen i").innerHTML = "") + } + + function onPlayerChange() { + bindToPlayer(playbackManager.getCurrentPlayer()) + } + + function onStateChanged(event, state) { + var player = this; + state.NowPlayingItem && (isEnabled = !0, updatePlayerStateInternal(event, player, state), updatePlaylist(player), enableStopOnBack(!0)) + } + + function onPlayPauseStateChanged(e) { + if (isEnabled) { + updatePlayPauseState(this.paused()) + } + } + + function onVolumeChanged(e) { + if (isEnabled) { + var player = this; + updatePlayerVolumeState(player, player.isMuted(), player.getVolume()) + } + } + + function onPlaybackStart(e, state) { + console.log("nowplaying event: " + e.type); + var player = this; + onStateChanged.call(player, e, state), resetUpNextDialog() + } + + function resetUpNextDialog() { + comingUpNextDisplayed = !1; + var dlg = currentUpNextDialog; + dlg && (dlg.destroy(), currentUpNextDialog = null) + } + + function onPlaybackStopped(e, state) { + currentRuntimeTicks = null, resetUpNextDialog(), console.log("nowplaying event: " + e.type), "Video" !== state.NextMediaType && (view.removeEventListener("viewbeforehide", onViewHideStopPlayback), Emby.Page.back()) + } + + function onMediaStreamsChanged(e) { + var player = this, + state = playbackManager.getPlayerState(player); + onStateChanged.call(player, { + type: "init" + }, state) + } + + function bindToPlayer(player) { + if (player !== currentPlayer && (releaseCurrentPlayer(), currentPlayer = player, player)) { + var state = playbackManager.getPlayerState(player); + onStateChanged.call(player, { + type: "init" + }, state), events.on(player, "playbackstart", onPlaybackStart), events.on(player, "playbackstop", onPlaybackStopped), events.on(player, "volumechange", onVolumeChanged), events.on(player, "pause", onPlayPauseStateChanged), events.on(player, "unpause", onPlayPauseStateChanged), events.on(player, "timeupdate", onTimeUpdate), events.on(player, "fullscreenchange", updateFullscreenIcon), events.on(player, "mediastreamschange", onMediaStreamsChanged), resetUpNextDialog() + } + } + + function releaseCurrentPlayer() { + destroyStats(), resetUpNextDialog(); + var player = currentPlayer; + player && (events.off(player, "playbackstart", onPlaybackStart), events.off(player, "playbackstop", onPlaybackStopped), events.off(player, "volumechange", onVolumeChanged), events.off(player, "pause", onPlayPauseStateChanged), events.off(player, "unpause", onPlayPauseStateChanged), events.off(player, "timeupdate", onTimeUpdate), events.off(player, "fullscreenchange", updateFullscreenIcon), events.off(player, "mediastreamschange", onMediaStreamsChanged), currentPlayer = null) + } + + function onTimeUpdate(e) { + if (isEnabled) { + var now = (new Date).getTime(); + if (!(now - lastUpdateTime < 700)) { + lastUpdateTime = now; + var player = this; + currentRuntimeTicks = playbackManager.duration(player); + var currentTime = playbackManager.currentTime(player); + updateTimeDisplay(currentTime, currentRuntimeTicks, playbackManager.playbackStartTime(player), playbackManager.getBufferedRanges(player)); + var item = currentItem; + refreshProgramInfoIfNeeded(player, item), showComingUpNextIfNeeded(player, item, currentTime, currentRuntimeTicks) + } + } + } + + function showComingUpNextIfNeeded(player, currentItem, currentTimeTicks, runtimeTicks) { + if (runtimeTicks && currentTimeTicks && !comingUpNextDisplayed && !currentVisibleMenu && "Episode" === currentItem.Type && userSettings.enableNextVideoInfoOverlay()) { + var showAtSecondsLeft = runtimeTicks >= 3e10 ? 40 : runtimeTicks >= 24e9 ? 35 : 30, + showAtTicks = runtimeTicks - 1e3 * showAtSecondsLeft * 1e4, + timeRemainingTicks = runtimeTicks - currentTimeTicks; + currentTimeTicks >= showAtTicks && runtimeTicks >= 6e9 && timeRemainingTicks >= 2e8 && showComingUpNext(player) + } + } + + function onUpNextHidden() { + "upnext" === currentVisibleMenu && (currentVisibleMenu = null) + } + + function showComingUpNext(player) { + require(["upNextDialog"], function(UpNextDialog) { + currentVisibleMenu || currentUpNextDialog || (currentVisibleMenu = "upnext", comingUpNextDisplayed = !0, playbackManager.nextItem(player).then(function(nextItem) { + currentUpNextDialog = new UpNextDialog({ + parent: view.querySelector(".upNextContainer"), + player: player, + nextItem: nextItem + }), events.on(currentUpNextDialog, "hide", onUpNextHidden) + }, onUpNextHidden)) + }) + } + + function refreshProgramInfoIfNeeded(player, item) { + if ("TvChannel" === item.Type) { + var program = item.CurrentProgram; + if (program && program.EndDate) try { + var endDate = datetime.parseISO8601Date(program.EndDate); + if ((new Date).getTime() >= endDate.getTime()) { + console.log("program info needs to be refreshed"); + var state = playbackManager.getPlayerState(player); + onStateChanged.call(player, { + type: "init" + }, state) + } + } catch (e) { + console.log("Error parsing date: " + program.EndDate) + } + } + } + + function updatePlayPauseState(isPaused) { + view.querySelector(".btnPause i").innerHTML = isPaused ? "" : "" + } + + function updatePlayerStateInternal(event, player, state) { + var playState = state.PlayState || {}; + updatePlayPauseState(playState.IsPaused); + var supportedCommands = playbackManager.getSupportedCommands(player); + currentPlayerSupportedCommands = supportedCommands, supportsBrightnessChange = -1 !== supportedCommands.indexOf("SetBrightness"), updatePlayerVolumeState(player, playState.IsMuted, playState.VolumeLevel), nowPlayingPositionSlider && !nowPlayingPositionSlider.dragging && (nowPlayingPositionSlider.disabled = !playState.CanSeek), btnFastForward.disabled = !playState.CanSeek, btnRewind.disabled = !playState.CanSeek; + var nowPlayingItem = state.NowPlayingItem || {}; + playbackStartTimeTicks = playState.PlaybackStartTimeTicks, updateTimeDisplay(playState.PositionTicks, nowPlayingItem.RunTimeTicks, playState.PlaybackStartTimeTicks, playState.BufferedRanges || []), updateNowPlayingInfo(player, state), state.MediaSource && state.MediaSource.SupportsTranscoding && -1 !== supportedCommands.indexOf("SetMaxStreamingBitrate") ? view.querySelector(".btnVideoOsdSettings").classList.remove("hide") : view.querySelector(".btnVideoOsdSettings").classList.add("hide"); + var isProgressClear = state.MediaSource && null == state.MediaSource.RunTimeTicks; + nowPlayingPositionSlider.setIsClear(isProgressClear), -1 === supportedCommands.indexOf("ToggleFullscreen") || player.isLocalPlayer && layoutManager.tv && playbackManager.isFullscreen(player) ? view.querySelector(".btnFullscreen").classList.add("hide") : view.querySelector(".btnFullscreen").classList.remove("hide"), -1 === supportedCommands.indexOf("PictureInPicture") ? view.querySelector(".btnPip").classList.add("hide") : view.querySelector(".btnPip").classList.remove("hide"), updateFullscreenIcon() + } + + function getDisplayPercentByTimeOfDay(programStartDateMs, programRuntimeMs, currentTimeMs) { + return (currentTimeMs - programStartDateMs) / programRuntimeMs * 100 + } + + function updateTimeDisplay(positionTicks, runtimeTicks, playbackStartTimeTicks, bufferedRanges) { + if (enableProgressByTimeOfDay) { + if (nowPlayingPositionSlider && !nowPlayingPositionSlider.dragging) + if (programStartDateMs && programEndDateMs) { + var currentTimeMs = (playbackStartTimeTicks + (positionTicks || 0)) / 1e4, + programRuntimeMs = programEndDateMs - programStartDateMs; + if (nowPlayingPositionSlider.value = getDisplayPercentByTimeOfDay(programStartDateMs, programRuntimeMs, currentTimeMs), bufferedRanges.length) { + var rangeStart = getDisplayPercentByTimeOfDay(programStartDateMs, programRuntimeMs, (playbackStartTimeTicks + (bufferedRanges[0].start || 0)) / 1e4), + rangeEnd = getDisplayPercentByTimeOfDay(programStartDateMs, programRuntimeMs, (playbackStartTimeTicks + (bufferedRanges[0].end || 0)) / 1e4); + nowPlayingPositionSlider.setBufferedRanges([{ + start: rangeStart, + end: rangeEnd + }]) + } else nowPlayingPositionSlider.setBufferedRanges([]) + } else nowPlayingPositionSlider.value = 0, nowPlayingPositionSlider.setBufferedRanges([]); + nowPlayingPositionText.innerHTML = "", nowPlayingDurationText.innerHTML = "" + } else { + if (nowPlayingPositionSlider && !nowPlayingPositionSlider.dragging) { + if (runtimeTicks) { + var pct = positionTicks / runtimeTicks; + pct *= 100, nowPlayingPositionSlider.value = pct + } else nowPlayingPositionSlider.value = 0; + runtimeTicks && null != positionTicks && currentRuntimeTicks && !enableProgressByTimeOfDay && currentItem.RunTimeTicks && "Recording" !== currentItem.Type ? endsAtText.innerHTML = "  -  " + mediaInfo.getEndsAtFromPosition(runtimeTicks, positionTicks, !0) : endsAtText.innerHTML = "" + } + nowPlayingPositionSlider && nowPlayingPositionSlider.setBufferedRanges(bufferedRanges, runtimeTicks, positionTicks), updateTimeText(nowPlayingPositionText, positionTicks), updateTimeText(nowPlayingDurationText, runtimeTicks, !0) + } + } + + function updatePlayerVolumeState(player, isMuted, volumeLevel) { + var supportedCommands = currentPlayerSupportedCommands, + showMuteButton = !0, + showVolumeSlider = !0; - 1 === supportedCommands.indexOf("Mute") && (showMuteButton = !1), -1 === supportedCommands.indexOf("SetVolume") && (showVolumeSlider = !1), player.isLocalPlayer && appHost.supports("physicalvolumecontrol") && (showMuteButton = !1, showVolumeSlider = !1), isMuted ? (view.querySelector(".buttonMute").setAttribute("title", globalize.translate("Unmute")), view.querySelector(".buttonMute i").innerHTML = "") : (view.querySelector(".buttonMute").setAttribute("title", globalize.translate("Mute")), view.querySelector(".buttonMute i").innerHTML = ""), showMuteButton ? view.querySelector(".buttonMute").classList.remove("hide") : view.querySelector(".buttonMute").classList.add("hide"), nowPlayingVolumeSlider && (showVolumeSlider ? nowPlayingVolumeSliderContainer.classList.remove("hide") : nowPlayingVolumeSliderContainer.classList.add("hide"), nowPlayingVolumeSlider.dragging || (nowPlayingVolumeSlider.value = volumeLevel || 0)) + } + + function updatePlaylist(player) { + var btnPreviousTrack = view.querySelector(".btnPreviousTrack"), + btnNextTrack = view.querySelector(".btnNextTrack"); + btnPreviousTrack.classList.remove("hide"), btnNextTrack.classList.remove("hide"), btnNextTrack.disabled = !1, btnPreviousTrack.disabled = !1 + } + + function updateTimeText(elem, ticks, divider) { + if (null == ticks) return void(elem.innerHTML = ""); + var html = datetime.getDisplayRunningTime(ticks); + divider && (html = " / " + html), elem.innerHTML = html + } + + function onSettingsButtonClick(e) { + var btn = this; + require(["playerSettingsMenu"], function(playerSettingsMenu) { + var player = currentPlayer; + player && playerSettingsMenu.show({ + mediaType: "Video", + player: player, + positionTo: btn, + stats: !0, + onOption: onSettingsOption + }) + }) + } + + function onSettingsOption(selectedOption) { + "stats" === selectedOption && toggleStats() + } + + function toggleStats() { + require(["playerStats"], function(PlayerStats) { + var player = currentPlayer; + player && (statsOverlay ? statsOverlay.toggle() : statsOverlay = new PlayerStats({ + player: player + })) + }) + } + + function destroyStats() { + statsOverlay && (statsOverlay.destroy(), statsOverlay = null) + } + + function showAudioTrackSelection() { + var player = currentPlayer, + audioTracks = playbackManager.audioTracks(player), + currentIndex = playbackManager.getAudioStreamIndex(player), + menuItems = audioTracks.map(function(stream) { + var opt = { + name: stream.DisplayTitle, + id: stream.Index + }; + return stream.Index === currentIndex && (opt.selected = !0), opt + }), + positionTo = this; + require(["actionsheet"], function(actionsheet) { + actionsheet.show({ + items: menuItems, + title: globalize.translate("Audio"), + positionTo: positionTo + }).then(function(id) { + var index = parseInt(id); + index !== currentIndex && playbackManager.setAudioStreamIndex(index, player) + }) + }) + } + + function showSubtitleTrackSelection() { + var player = currentPlayer, + streams = playbackManager.subtitleTracks(player), + currentIndex = playbackManager.getSubtitleStreamIndex(player); + null == currentIndex && (currentIndex = -1), streams.unshift({ + Index: -1, + DisplayTitle: globalize.translate("Off") + }); + var menuItems = streams.map(function(stream) { + var opt = { + name: stream.DisplayTitle, + id: stream.Index + }; + return stream.Index === currentIndex && (opt.selected = !0), opt + }), + positionTo = this; + require(["actionsheet"], function(actionsheet) { + actionsheet.show({ + title: globalize.translate("Subtitles"), + items: menuItems, + positionTo: positionTo + }).then(function(id) { + var index = parseInt(id); + index !== currentIndex && playbackManager.setSubtitleStreamIndex(index, player) + }) + }) + } + + function onWindowKeyDown(e) { + if (!currentVisibleMenu && (32 === e.keyCode || 13 === e.keyCode)) return playbackManager.playPause(currentPlayer), void showOsd(); + switch (e.key) { + case "f": + e.ctrlKey || playbackManager.toggleFullscreen(currentPlayer); + break; + case "m": + playbackManager.toggleMute(currentPlayer); + break; + case "ArrowLeft": + case "Left": + case "NavigationLeft": + case "GamepadDPadLeft": + case "GamepadLeftThumbstickLeft": + e.shiftKey && playbackManager.rewind(currentPlayer); + break; + case "ArrowRight": + case "Right": + case "NavigationRight": + case "GamepadDPadRight": + case "GamepadLeftThumbstickRight": + e.shiftKey && playbackManager.fastForward(currentPlayer) + } + } + + function getImgUrl(item, chapter, index, maxWidth, apiClient) { + return chapter.ImageTag ? apiClient.getScaledImageUrl(item.Id, { + maxWidth: maxWidth, + tag: chapter.ImageTag, + type: "Chapter", + index: index + }) : null + } + + function getChapterBubbleHtml(apiClient, item, chapters, positionTicks) { + for (var chapter, index = -1, i = 0, length = chapters.length; i < length; i++) { + var currentChapter = chapters[i]; + positionTicks >= currentChapter.StartPositionTicks && (chapter = currentChapter, index = i) + } + if (!chapter) return null; + var src = getImgUrl(item, chapter, index, 400, apiClient); + if (src) { + var html = '
    '; + return html += '', html += '
    ', html += '
    ', html += chapter.Name, html += "
    ", html += '

    ', html += datetime.getDisplayRunningTime(positionTicks), html += "

    ", html += "
    ", html += "
    " + } + return null + } + + function onViewHideStopPlayback() { + if (playbackManager.isPlayingVideo()) { + var player = currentPlayer; + view.removeEventListener("viewbeforehide", onViewHideStopPlayback), releaseCurrentPlayer(), playbackManager.stop(player) + } + } + + function enableStopOnBack(enabled) { + view.removeEventListener("viewbeforehide", onViewHideStopPlayback), enabled && playbackManager.isPlayingVideo(currentPlayer) && view.addEventListener("viewbeforehide", onViewHideStopPlayback) + } + var currentPlayer, comingUpNextDisplayed, currentUpNextDialog, isEnabled, currentItem, recordingButtonManager, enableProgressByTimeOfDay, supportsBrightnessChange, currentVisibleMenu, statsOverlay, osdHideTimeout, lastPointerMoveData, self = this, + currentPlayerSupportedCommands = [], + currentRuntimeTicks = 0, + lastUpdateTime = 0, + programStartDateMs = 0, + programEndDateMs = 0, + playbackStartTimeTicks = 0, + nowPlayingVolumeSlider = view.querySelector(".osdVolumeSlider"), + nowPlayingVolumeSliderContainer = view.querySelector(".osdVolumeSliderContainer"), + nowPlayingPositionSlider = view.querySelector(".osdPositionSlider"), + nowPlayingPositionText = view.querySelector(".osdPositionText"), + nowPlayingDurationText = view.querySelector(".osdDurationText"), + startTimeText = view.querySelector(".startTimeText"), + endTimeText = view.querySelector(".endTimeText"), + endsAtText = view.querySelector(".endsAtText"), + btnRewind = view.querySelector(".btnRewind"), + btnFastForward = view.querySelector(".btnFastForward"), + transitionEndEventName = dom.whichTransitionEvent(), + headerElement = document.querySelector(".skinHeader"), + osdBottomElement = document.querySelector(".videoOsdBottom-maincontrols"); + view.addEventListener("viewbeforeshow", function(e) { + headerElement.classList.add("osdHeader"), Emby.Page.setTransparency("full") + }), view.addEventListener("viewshow", function(e) { + events.on(playbackManager, "playerchange", onPlayerChange), bindToPlayer(playbackManager.getCurrentPlayer()), dom.addEventListener(document, window.PointerEvent ? "pointermove" : "mousemove", onPointerMove, { + passive: !0 + }), document.body.classList.add("autoScrollY"), showOsd(), inputManager.on(window, onInputCommand), dom.addEventListener(window, "keydown", onWindowKeyDown, { + passive: !0 + }) + }), view.addEventListener("viewbeforehide", function() { + statsOverlay && statsOverlay.enabled(!1), dom.removeEventListener(window, "keydown", onWindowKeyDown, { + passive: !0 + }), stopOsdHideTimer(), headerElement.classList.remove("osdHeader"), headerElement.classList.remove("osdHeader-hidden"), dom.removeEventListener(document, window.PointerEvent ? "pointermove" : "mousemove", onPointerMove, { + passive: !0 + }), document.body.classList.remove("autoScrollY"), inputManager.off(window, onInputCommand), events.off(playbackManager, "playerchange", onPlayerChange), releaseCurrentPlayer() + }), view.querySelector(".btnFullscreen").addEventListener("click", function() { + playbackManager.toggleFullscreen(currentPlayer) + }), view.querySelector(".btnPip").addEventListener("click", function() { + playbackManager.togglePictureInPicture(currentPlayer) + }), view.querySelector(".btnVideoOsdSettings").addEventListener("click", onSettingsButtonClick), view.addEventListener("viewhide", function() { + headerElement.classList.remove("hide") + }), view.addEventListener("viewdestroy", function() { + self.touchHelper && (self.touchHelper.destroy(), self.touchHelper = null), recordingButtonManager && (recordingButtonManager.destroy(), recordingButtonManager = null), destroyStats() + }); + var lastPointerDown = 0; + dom.addEventListener(view, window.PointerEvent ? "pointerdown" : "click", function(e) { + if (dom.parentWithClass(e.target, ["videoOsdBottom", "upNextContainer"])) return void showOsd(); + var pointerType = e.pointerType || (layoutManager.mobile ? "touch" : "mouse"), + now = (new Date).getTime(); + switch (pointerType) { + case "touch": + now - lastPointerDown > 300 && (lastPointerDown = now, toggleOsd()); + break; + case "mouse": + e.button || (playbackManager.playPause(currentPlayer), showOsd()); + break; + default: + playbackManager.playPause(currentPlayer), showOsd() + } + }, { + passive: !0 + }), browser.touch && dom.addEventListener(view, "dblclick", onDoubleClick, {}), view.querySelector(".buttonMute").addEventListener("click", function() { + playbackManager.toggleMute(currentPlayer) + }), nowPlayingVolumeSlider.addEventListener("change", function() { + playbackManager.setVolume(this.value, currentPlayer) + }), nowPlayingPositionSlider.addEventListener("change", function() { + var player = currentPlayer; + if (player) { + var newPercent = parseFloat(this.value); + if (enableProgressByTimeOfDay) { + var seekAirTimeTicks = newPercent / 100 * (programEndDateMs - programStartDateMs) * 1e4; + seekAirTimeTicks += 1e4 * programStartDateMs, seekAirTimeTicks -= playbackStartTimeTicks, playbackManager.seek(seekAirTimeTicks, player) + } else playbackManager.seekPercent(newPercent, player) + } + }), nowPlayingPositionSlider.getBubbleHtml = function(value) { + if (showOsd(), enableProgressByTimeOfDay) { + if (programStartDateMs && programEndDateMs) { + var ms = programEndDateMs - programStartDateMs; + ms /= 100, ms *= value, ms += programStartDateMs; + return '

    ' + getDisplayTimeWithoutAmPm(new Date(parseInt(ms)), !0) + "

    " + } + return "--:--" + } + if (!currentRuntimeTicks) return "--:--"; + var ticks = currentRuntimeTicks; + ticks /= 100, ticks *= value; + var item = currentItem; + if (item && item.Chapters && item.Chapters.length && item.Chapters[0].ImageTag) { + var html = getChapterBubbleHtml(connectionManager.getApiClient(item.ServerId), item, item.Chapters, ticks); + if (html) return html + } + return '

    ' + datetime.getDisplayRunningTime(ticks) + "

    " + }, view.querySelector(".btnPreviousTrack").addEventListener("click", function() { + playbackManager.previousTrack(currentPlayer) + }), view.querySelector(".btnPause").addEventListener("click", function() { + playbackManager.playPause(currentPlayer) + }), view.querySelector(".btnNextTrack").addEventListener("click", function() { + playbackManager.nextTrack(currentPlayer) + }), btnRewind.addEventListener("click", function() { + playbackManager.rewind(currentPlayer) + }), btnFastForward.addEventListener("click", function() { + playbackManager.fastForward(currentPlayer) + }), view.querySelector(".btnAudio").addEventListener("click", showAudioTrackSelection), view.querySelector(".btnSubtitles").addEventListener("click", showSubtitleTrackSelection), browser.touch && function() { + require(["touchHelper"], function(TouchHelper) { + self.touchHelper = new TouchHelper(view, { + swipeYThreshold: 30, + triggerOnMove: !0, + preventDefaultOnMove: !0, + ignoreTagNames: ["BUTTON", "INPUT", "TEXTAREA"] + }), events.on(self.touchHelper, "swipeup", onVerticalSwipe), events.on(self.touchHelper, "swipedown", onVerticalSwipe) + }) + }() + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/wizardagreement.js b/dashboard-ui/scripts/wizardagreement.js index df69d8388f..dfb9d70646 100644 --- a/dashboard-ui/scripts/wizardagreement.js +++ b/dashboard-ui/scripts/wizardagreement.js @@ -1 +1,17 @@ -define(["dom","emby-linkbutton"],function(dom){"use strict";function onSubmit(e){return dom.parentWithClass(this,"page").querySelector(".chkAccept").checked?Dashboard.navigate("wizardfinish.html"):Dashboard.alert({message:Globalize.translate("MessagePleaseAcceptTermsOfServiceBeforeContinuing"),title:""}),e.preventDefault(),!1}return function(view,params){view.querySelector(".wizardAgreementForm").addEventListener("submit",onSubmit),view.addEventListener("viewshow",function(){document.querySelector(".skinHeader").classList.add("noHomeButtonHeader")}),view.addEventListener("viewhide",function(){document.querySelector(".skinHeader").classList.remove("noHomeButtonHeader")})}}); \ No newline at end of file +define(["dom", "emby-linkbutton"], function(dom) { + "use strict"; + + function onSubmit(e) { + return dom.parentWithClass(this, "page").querySelector(".chkAccept").checked ? Dashboard.navigate("wizardfinish.html") : Dashboard.alert({ + message: Globalize.translate("MessagePleaseAcceptTermsOfServiceBeforeContinuing"), + title: "" + }), e.preventDefault(), !1 + } + return function(view, params) { + view.querySelector(".wizardAgreementForm").addEventListener("submit", onSubmit), view.addEventListener("viewshow", function() { + document.querySelector(".skinHeader").classList.add("noHomeButtonHeader") + }), view.addEventListener("viewhide", function() { + document.querySelector(".skinHeader").classList.remove("noHomeButtonHeader") + }) + } +}); \ No newline at end of file diff --git a/dashboard-ui/scripts/wizarduserpage.js b/dashboard-ui/scripts/wizarduserpage.js index df55ac9e37..b3bcfc7137 100644 --- a/dashboard-ui/scripts/wizarduserpage.js +++ b/dashboard-ui/scripts/wizarduserpage.js @@ -1 +1,59 @@ -define(["loading","connectHelper","globalize","dashboardcss","emby-input","emby-button","emby-linkbutton"],function(loading,connectHelper,globalize){"use strict";function getApiClient(){return ApiClient}function nextWizardPage(){Dashboard.navigate("wizardlibrary.html")}function onUpdateUserComplete(result){if(loading.hide(),result.UserLinkResult){var msgKey=result.UserLinkResult.IsPending?"MessagePendingEmbyAccountAdded":"MessageEmbyAccountAdded";Dashboard.alert({message:globalize.translate(msgKey),title:globalize.translate("HeaderEmbyAccountAdded"),callback:nextWizardPage})}else nextWizardPage()}function submit(form){loading.show();var apiClient=getApiClient();apiClient.ajax({type:"POST",data:{Name:form.querySelector("#txtUsername").value,ConnectUserName:form.querySelector("#txtConnectUserName").value},url:apiClient.getUrl("Startup/User"),dataType:"json"}).then(onUpdateUserComplete,function(response){response&&response.status;connectHelper.showLinkUserErrorMessage(form.querySelector("#txtConnectUserName").value)})}function onSubmit(e){return submit(this),e.preventDefault(),!1}function onViewShow(){loading.show();var page=this,apiClient=getApiClient();apiClient.getJSON(apiClient.getUrl("Startup/User")).then(function(user){page.querySelector("#txtUsername").value=user.Name||"",page.querySelector("#txtConnectUserName").value=user.ConnectUserName||"",loading.hide()})}return function(view,params){view.querySelector(".wizardUserForm").addEventListener("submit",onSubmit),view.addEventListener("viewshow",function(){document.querySelector(".skinHeader").classList.add("noHomeButtonHeader")}),view.addEventListener("viewhide",function(){document.querySelector(".skinHeader").classList.remove("noHomeButtonHeader")}),view.addEventListener("viewshow",onViewShow)}}); \ No newline at end of file +define(["loading", "connectHelper", "globalize", "dashboardcss", "emby-input", "emby-button", "emby-linkbutton"], function(loading, connectHelper, globalize) { + "use strict"; + + function getApiClient() { + return ApiClient + } + + function nextWizardPage() { + Dashboard.navigate("wizardlibrary.html") + } + + function onUpdateUserComplete(result) { + if (loading.hide(), result.UserLinkResult) { + var msgKey = result.UserLinkResult.IsPending ? "MessagePendingEmbyAccountAdded" : "MessageEmbyAccountAdded"; + Dashboard.alert({ + message: globalize.translate(msgKey), + title: globalize.translate("HeaderEmbyAccountAdded"), + callback: nextWizardPage + }) + } else nextWizardPage() + } + + function submit(form) { + loading.show(); + var apiClient = getApiClient(); + apiClient.ajax({ + type: "POST", + data: { + Name: form.querySelector("#txtUsername").value, + ConnectUserName: form.querySelector("#txtConnectUserName").value + }, + url: apiClient.getUrl("Startup/User"), + dataType: "json" + }).then(onUpdateUserComplete, function(response) { + response && response.status; + connectHelper.showLinkUserErrorMessage(form.querySelector("#txtConnectUserName").value) + }) + } + + function onSubmit(e) { + return submit(this), e.preventDefault(), !1 + } + + function onViewShow() { + loading.show(); + var page = this, + apiClient = getApiClient(); + apiClient.getJSON(apiClient.getUrl("Startup/User")).then(function(user) { + page.querySelector("#txtUsername").value = user.Name || "", page.querySelector("#txtConnectUserName").value = user.ConnectUserName || "", loading.hide() + }) + } + return function(view, params) { + view.querySelector(".wizardUserForm").addEventListener("submit", onSubmit), view.addEventListener("viewshow", function() { + document.querySelector(".skinHeader").classList.add("noHomeButtonHeader") + }), view.addEventListener("viewhide", function() { + document.querySelector(".skinHeader").classList.remove("noHomeButtonHeader") + }), view.addEventListener("viewshow", onViewShow) + } +}); \ No newline at end of file diff --git a/dashboard-ui/serviceworker.js b/dashboard-ui/serviceworker.js index 99ceb2d6ca..fba101b81f 100644 --- a/dashboard-ui/serviceworker.js +++ b/dashboard-ui/serviceworker.js @@ -1 +1 @@ -importScripts("bower_components/emby-webcomponents/serviceworker/notifications.js","bower_components/emby-webcomponents/serviceworker/sync.js"); \ No newline at end of file +importScripts("bower_components/emby-webcomponents/serviceworker/notifications.js", "bower_components/emby-webcomponents/serviceworker/sync.js"); \ No newline at end of file diff --git a/dashboard-ui/thirdparty/jstree/jstree.js b/dashboard-ui/thirdparty/jstree/jstree.js index 218efbb37d..c53a496bc2 100644 --- a/dashboard-ui/thirdparty/jstree/jstree.js +++ b/dashboard-ui/thirdparty/jstree/jstree.js @@ -1,5 +1,2926 @@ -!function(factory){"use strict";"function"==typeof define&&define.amd?define(["jquery"],factory):factory("object"==typeof exports?require("jquery"):jQuery)}(function($,undefined){"use strict";if(!$.jstree){var _temp1,_temp2,instance_counter=0,ccp_node=!1,ccp_mode=!1,ccp_inst=!1,themes_loaded=[],src=$("script:last").attr("src"),document=window.document,_node=document.createElement("LI");_node.setAttribute("role","treeitem"),_temp1=document.createElement("I"),_temp1.className="jstree-icon jstree-ocl",_temp1.setAttribute("role","presentation"),_node.appendChild(_temp1),_temp1=document.createElement("A"),_temp1.className="jstree-anchor",_temp1.setAttribute("href","#"),_temp1.setAttribute("tabindex","-1"),_temp2=document.createElement("I"),_temp2.className="jstree-icon jstree-themeicon",_temp2.setAttribute("role","presentation"),_temp1.appendChild(_temp2),_node.appendChild(_temp1),_temp1=_temp2=null,$.jstree={version:"3.1.1",defaults:{plugins:[]},plugins:{},path:src&&-1!==src.indexOf("/")?src.replace(/\/[^\/]+$/,""):"",idregex:/[\\:&!^|()\[\]<>@*'+~#";.,=\- \/${}%?`]/g},$.jstree.create=function(el,options){var tmp=new $.jstree.core(++instance_counter),opt=options;return options=$.extend(!0,{},$.jstree.defaults,options),opt&&opt.plugins&&(options.plugins=opt.plugins),$.each(options.plugins,function(i,k){"core"!==i&&(tmp=tmp.plugin(k,options[k]))}),$(el).data("jstree",tmp),tmp.init(el,options),tmp},$.jstree.destroy=function(){$(".jstree:jstree").jstree("destroy"),$(document).off(".jstree")},$.jstree.core=function(id){this._id=id,this._cnt=0,this._wrk=null,this._data={core:{themes:{name:!1,dots:!1,icons:!1},selected:[],last_error:{},working:!1,worker_queue:[],focused:null}}},$.jstree.reference=function(needle){var tmp=null,obj=null;if(!needle||!needle.id||needle.tagName&&needle.nodeType||(needle=needle.id),!obj||!obj.length)try{obj=$(needle)}catch(ignore){}if(!obj||!obj.length)try{obj=$("#"+needle.replace($.jstree.idregex,"\\$&"))}catch(ignore){}return obj&&obj.length&&(obj=obj.closest(".jstree")).length&&(obj=obj.data("jstree"))?tmp=obj:$(".jstree").each(function(){var inst=$(this).data("jstree");if(inst&&inst._model.data[needle])return tmp=inst,!1}),tmp},$.fn.jstree=function(arg){var is_method="string"==typeof arg,args=Array.prototype.slice.call(arguments,1),result=null;return!(!0===arg&&!this.length)&&(this.each(function(){var instance=$.jstree.reference(this),method=is_method&&instance?instance[arg]:null;if(result=is_method&&method?method.apply(instance,args):null,instance||is_method||arg!==undefined&&!$.isPlainObject(arg)||$.jstree.create(this,arg),(instance&&!is_method||!0===arg)&&(result=instance||!1),null!==result&&result!==undefined)return!1}),null!==result&&result!==undefined?result:this)},$.expr[":"].jstree=$.expr.createPseudo(function(search){return function(a){return $(a).hasClass("jstree")&&$(a).data("jstree")!==undefined}}),$.jstree.defaults.core={data:!1,strings:!1,check_callback:!1,error:$.noop,animation:200,multiple:!0,themes:{name:!1,url:!1,dir:!1,dots:!0,icons:!0,stripes:!1,variant:!1,responsive:!1},expand_selected_onload:!0,worker:!0,force_text:!1,dblclick_toggle:!0},$.jstree.core.prototype={plugin:function(deco,opts){var Child=$.jstree.plugins[deco];return Child?(this._data[deco]={},Child.prototype=this,new Child(opts,this)):this},init:function(el,options){this._model={data:{"#":{id:"#",parent:null,parents:[],children:[],children_d:[],state:{loaded:!1}}},changed:[],force_full_redraw:!1,redraw_timeout:!1,default_state:{loaded:!0,opened:!1,selected:!1,disabled:!1}},this.element=$(el).addClass("jstree jstree-"+this._id),this.settings=options,this._data.core.ready=!1,this._data.core.loaded=!1,this._data.core.rtl="rtl"===this.element.css("direction"),this.element[this._data.core.rtl?"addClass":"removeClass"]("jstree-rtl"),this.element.attr("role","tree"),this.settings.core.multiple&&this.element.attr("aria-multiselectable",!0),this.element.attr("tabindex")||this.element.attr("tabindex","0"),this.bind(),this.trigger("init"),this._data.core.original_container_html=this.element.find(" > ul > li").clone(!0),this._data.core.original_container_html.find("li").addBack().contents().filter(function(){return 3===this.nodeType&&(!this.nodeValue||/^\s+$/.test(this.nodeValue))}).remove(),this.element.html(""),this.element.attr("aria-activedescendant","j"+this._id+"_loading"),this._data.core.li_height=this.get_container_ul().children("li").first().height()||24,this.trigger("loading"),this.load_node("#")},destroy:function(keep_html){if(this._wrk)try{window.URL.revokeObjectURL(this._wrk),this._wrk=null}catch(ignore){}keep_html||this.element.empty(),this.teardown()},teardown:function(){this.unbind(),this.element.removeClass("jstree").removeData("jstree").find("[class^='jstree']").addBack().attr("class",function(){return this.className.replace(/jstree[^ ]*|$/gi,"")}),this.element=null},bind:function(){var word="",tout=null,was_click=0;this.element.on("dblclick.jstree",function(){if(document.selection&&document.selection.empty)document.selection.empty();else if(window.getSelection){var sel=window.getSelection();try{sel.removeAllRanges(),sel.collapse()}catch(ignore){}}}).on("mousedown.jstree",$.proxy(function(e){e.target===this.element[0]&&(e.preventDefault(),was_click=+new Date)},this)).on("mousedown.jstree",".jstree-ocl",function(e){e.preventDefault()}).on("click.jstree",".jstree-ocl",$.proxy(function(e){this.toggle_node(e.target)},this)).on("dblclick.jstree",".jstree-anchor",$.proxy(function(e){this.settings.core.dblclick_toggle&&this.toggle_node(e.target)},this)).on("click.jstree",".jstree-anchor",$.proxy(function(e){e.preventDefault(),e.currentTarget!==document.activeElement&&$(e.currentTarget).focus(),this.activate_node(e.currentTarget,e)},this)).on("keydown.jstree",".jstree-anchor",$.proxy(function(e){if("INPUT"===e.target.tagName)return!0;if(32!==e.which&&13!==e.which&&(e.shiftKey||e.ctrlKey||e.altKey||e.metaKey))return!0;var o=null;switch(this._data.core.rtl&&(37===e.which?e.which=39:39===e.which&&(e.which=37)),e.which){case 32:e.ctrlKey&&(e.type="click",$(e.currentTarget).trigger(e));break;case 13:e.type="click",$(e.currentTarget).trigger(e);break;case 37:e.preventDefault(),this.is_open(e.currentTarget)?this.close_node(e.currentTarget):(o=this.get_parent(e.currentTarget))&&"#"!==o.id&&this.get_node(o,!0).children(".jstree-anchor").focus();break;case 38:e.preventDefault(),o=this.get_prev_dom(e.currentTarget),o&&o.length&&o.children(".jstree-anchor").focus();break;case 39:e.preventDefault(),this.is_closed(e.currentTarget)?this.open_node(e.currentTarget,function(o){this.get_node(o,!0).children(".jstree-anchor").focus()}):this.is_open(e.currentTarget)&&(o=this.get_node(e.currentTarget,!0).children(".jstree-children")[0])&&$(this._firstChild(o)).children(".jstree-anchor").focus();break;case 40:e.preventDefault(),o=this.get_next_dom(e.currentTarget),o&&o.length&&o.children(".jstree-anchor").focus();break;case 106:this.open_all();break;case 36:e.preventDefault(),o=this._firstChild(this.get_container_ul()[0]),o&&$(o).children(".jstree-anchor").filter(":visible").focus();break;case 35:e.preventDefault(),this.element.find(".jstree-anchor").filter(":visible").last().focus()}},this)).on("load_node.jstree",$.proxy(function(e,data){data.status&&("#"!==data.node.id||this._data.core.loaded||(this._data.core.loaded=!0,this._firstChild(this.get_container_ul()[0])&&this.element.attr("aria-activedescendant",this._firstChild(this.get_container_ul()[0]).id),this.trigger("loaded")),this._data.core.ready||setTimeout($.proxy(function(){if(this.element&&!this.get_container_ul().find(".jstree-loading").length){if(this._data.core.ready=!0,this._data.core.selected.length){if(this.settings.core.expand_selected_onload){var i,j,tmp=[];for(i=0,j=this._data.core.selected.length;i1){if(col.slice(ind).each($.proxy(function(i,v){if(0===$(v).text().toLowerCase().indexOf(word))return $(v).focus(),end=!0,!1},this)),end)return;if(col.slice(0,ind).each($.proxy(function(i,v){if(0===$(v).text().toLowerCase().indexOf(word))return $(v).focus(),end=!0,!1},this)),end)return}if(new RegExp("^"+chr+"+$").test(word)){if(col.slice(ind+1).each($.proxy(function(i,v){if($(v).text().toLowerCase().charAt(0)===chr)return $(v).focus(),end=!0,!1},this)),end)return;if(col.slice(0,ind+1).each($.proxy(function(i,v){if($(v).text().toLowerCase().charAt(0)===chr)return $(v).focus(),end=!0,!1},this)),end)return}},this)).on("init.jstree",$.proxy(function(){var s=this.settings.core.themes;this._data.core.themes.dots=s.dots,this._data.core.themes.stripes=s.stripes,this._data.core.themes.icons=s.icons,this.set_theme(s.name||"default",s.url),this.set_theme_variant(s.variant)},this)).on("loading.jstree",$.proxy(function(){this[this._data.core.themes.dots?"show_dots":"hide_dots"](),this[this._data.core.themes.icons?"show_icons":"hide_icons"](),this[this._data.core.themes.stripes?"show_stripes":"hide_stripes"]()},this)).on("blur.jstree",".jstree-anchor",$.proxy(function(e){this._data.core.focused=null,$(e.currentTarget).filter(".jstree-hovered").mouseleave(),this.element.attr("tabindex","0")},this)).on("focus.jstree",".jstree-anchor",$.proxy(function(e){var tmp=this.get_node(e.currentTarget);tmp&&tmp.id&&(this._data.core.focused=tmp.id),this.element.find(".jstree-hovered").not(e.currentTarget).mouseleave(),$(e.currentTarget).mouseenter(),this.element.attr("tabindex","-1")},this)).on("focus.jstree",$.proxy(function(){if(+new Date-was_click>500&&!this._data.core.focused){was_click=0;var act=this.get_node(this.element.attr("aria-activedescendant"),!0);act&&act.find("> .jstree-anchor").focus()}},this)).on("mouseenter.jstree",".jstree-anchor",$.proxy(function(e){this.hover_node(e.currentTarget)},this)).on("mouseleave.jstree",".jstree-anchor",$.proxy(function(e){this.dehover_node(e.currentTarget)},this))},unbind:function(){this.element.off(".jstree"),$(document).off(".jstree-"+this._id)},trigger:function(ev,data){data||(data={}),data.instance=this,this.element.triggerHandler(ev.replace(".jstree","")+".jstree",data)},get_container:function(){return this.element},get_container_ul:function(){return this.element.children(".jstree-children").first()},get_string:function(key){var a=this.settings.core.strings;return $.isFunction(a)?a.call(this,key):a&&a[key]?a[key]:key},_firstChild:function(dom){for(dom=dom?dom.firstChild:null;null!==dom&&1!==dom.nodeType;)dom=dom.nextSibling;return dom},_nextSibling:function(dom){for(dom=dom?dom.nextSibling:null;null!==dom&&1!==dom.nodeType;)dom=dom.nextSibling;return dom},_previousSibling:function(dom){for(dom=dom?dom.previousSibling:null;null!==dom&&1!==dom.nodeType;)dom=dom.previousSibling;return dom},get_node:function(obj,as_dom){obj&&obj.id&&(obj=obj.id);var dom;try{if(this._model.data[obj])obj=this._model.data[obj];else if("string"==typeof obj&&this._model.data[obj.replace(/^#/,"")])obj=this._model.data[obj.replace(/^#/,"")];else if("string"==typeof obj&&(dom=$("#"+obj.replace($.jstree.idregex,"\\$&"),this.element)).length&&this._model.data[dom.closest(".jstree-node").attr("id")])obj=this._model.data[dom.closest(".jstree-node").attr("id")];else if((dom=$(obj,this.element)).length&&this._model.data[dom.closest(".jstree-node").attr("id")])obj=this._model.data[dom.closest(".jstree-node").attr("id")];else{if(!(dom=$(obj,this.element)).length||!dom.hasClass("jstree"))return!1;obj=this._model.data["#"]}return as_dom&&(obj="#"===obj.id?this.element:$("#"+obj.id.replace($.jstree.idregex,"\\$&"),this.element)),obj}catch(ex){return!1}},get_path:function(obj,glue,ids){if(!(obj=obj.parents?obj:this.get_node(obj))||"#"===obj.id||!obj.parents)return!1;var i,j,p=[];for(p.push(ids?obj.id:obj.text),i=0,j=obj.parents.length;i0)},is_loaded:function(obj){return(obj=this.get_node(obj))&&obj.state.loaded},is_loading:function(obj){return(obj=this.get_node(obj))&&obj.state&&obj.state.loading},is_open:function(obj){return(obj=this.get_node(obj))&&obj.state.opened},is_closed:function(obj){return(obj=this.get_node(obj))&&this.is_parent(obj)&&!obj.state.opened},is_leaf:function(obj){return!this.is_parent(obj)},load_node:function(obj,callback){var k,l,i,j,c;if($.isArray(obj))return this._load_nodes(obj.slice(),callback),!0;if(!(obj=this.get_node(obj)))return callback&&callback.call(this,obj,!1),!1;if(obj.state.loaded){for(obj.state.loaded=!1,k=0,l=obj.children_d.length;k").html(tmp),data.text=this.settings.core.force_text?tmp.text():tmp.html(),tmp=d.data(),data.data=tmp?$.extend(!0,{},tmp):null,data.state.opened=d.hasClass("jstree-open"),data.state.selected=d.children("a").hasClass("jstree-clicked"),data.state.disabled=d.children("a").hasClass("jstree-disabled"),data.data&&data.data.jstree)for(i in data.data.jstree)data.data.jstree.hasOwnProperty(i)&&(data.state[i]=data.data.jstree[i]);tmp=d.children("a").children(".jstree-themeicon"),tmp.length&&(data.icon=!tmp.hasClass("jstree-themeicon-hidden")&&tmp.attr("rel")),data.state.icon!==undefined&&(data.icon=data.state.icon),data.icon!==undefined&&null!==data.icon&&""!==data.icon||(data.icon=!0),tmp=d.children("ul").children("li");do{tid="j"+this._id+"_"+ ++this._cnt}while(m[tid]);return data.id=data.li_attr.id?data.li_attr.id.toString():tid,tmp.length?(tmp.each($.proxy(function(i,v){c=this._parse_model_from_html($(v),data.id,ps),e=this._model.data[c],data.children.push(c),e.children_d.length&&(data.children_d=data.children_d.concat(e.children_d))},this)),data.children_d=data.children_d.concat(data.children)):d.hasClass("jstree-closed")&&(data.state.loaded=!1),data.li_attr.class&&(data.li_attr.class=data.li_attr.class.replace("jstree-closed","").replace("jstree-open","")),data.a_attr.class&&(data.a_attr.class=data.a_attr.class.replace("jstree-clicked","").replace("jstree-disabled","")),m[data.id]=data,data.state.selected&&this._data.core.selected.push(data.id),data.id},_parse_model_from_flat_json:function(d,p,ps){ps=ps?ps.concat():[],p&&ps.unshift(p);var i,j,c,e,tid=d.id.toString(),m=this._model.data,df=this._model.default_state,tmp={id:tid,text:d.text||"",icon:d.icon===undefined||d.icon,parent:p,parents:ps,children:d.children||[],children_d:d.children_d||[],data:d.data,state:{},li_attr:{id:!1},a_attr:{href:"#"},original:!1};for(i in df)df.hasOwnProperty(i)&&(tmp.state[i]=df[i]);if(d&&d.data&&d.data.jstree&&d.data.jstree.icon&&(tmp.icon=d.data.jstree.icon),tmp.icon!==undefined&&null!==tmp.icon&&""!==tmp.icon||(tmp.icon=!0),d&&d.data&&(tmp.data=d.data,d.data.jstree))for(i in d.data.jstree)d.data.jstree.hasOwnProperty(i)&&(tmp.state[i]=d.data.jstree[i]);if(d&&"object"==typeof d.state)for(i in d.state)d.state.hasOwnProperty(i)&&(tmp.state[i]=d.state[i]);if(d&&"object"==typeof d.li_attr)for(i in d.li_attr)d.li_attr.hasOwnProperty(i)&&(tmp.li_attr[i]=d.li_attr[i]);if(tmp.li_attr.id||(tmp.li_attr.id=tid),d&&"object"==typeof d.a_attr)for(i in d.a_attr)d.a_attr.hasOwnProperty(i)&&(tmp.a_attr[i]=d.a_attr[i]);for(d&&d.children&&!0===d.children&&(tmp.state.loaded=!1,tmp.children=[],tmp.children_d=[]),m[tmp.id]=tmp,i=0,j=tmp.children.length;i
  • "+this.get_string("Loading ...")+"
  • "),this.element.attr("aria-activedescendant","j"+this._id+"_loading")),this.load_node("#",function(o,s){s&&(this.get_container_ul()[0].className=c,this._firstChild(this.get_container_ul()[0])&&this.element.attr("aria-activedescendant",this._firstChild(this.get_container_ul()[0]).id),this.set_state($.extend(!0,{},this._data.core.state),function(){this.trigger("refresh")})),this._data.core.state=null})},refresh_node:function(obj){if(!(obj=this.get_node(obj))||"#"===obj.id)return!1;var opened=[],to_load=[];this._data.core.selected.concat([]);to_load.push(obj.id),!0===obj.state.opened&&opened.push(obj.id),this.get_node(obj,!0).find(".jstree-open").each(function(){opened.push(this.id)}),this._load_nodes(to_load,$.proxy(function(nodes){this.open_node(opened,!1,0),this.select_node(this._data.core.selected),this.trigger("refresh_node",{node:obj,nodes:nodes})},this))},set_id:function(obj,id){if(!(obj=this.get_node(obj))||"#"===obj.id)return!1;var i,j,m=this._model.data;for(id=id.toString(),m[obj.parent].children[$.inArray(obj.id,m[obj.parent].children)]=id,i=0,j=obj.parents.length;ipar.children.length&&(pos=par.children.length),node.id||(node.id=!0),!this.check("create_node",node,par,pos))return this.settings.core.error.call(this,this._data.core.last_error),!1;if(!0===node.id&&delete node.id,!(node=this._parse_model_from_json(node,par.id,par.parents.concat())))return!1;for(tmp=this.get_node(node),dpc=[],dpc.push(node),dpc=dpc.concat(tmp.children_d),this.trigger("model",{nodes:dpc,parent:par.id}),par.children_d=par.children_d.concat(dpc),i=0,j=par.parents.length;i=pos?i+1:i]=par.children[i];return tmp[pos]=node.id,par.children=tmp,this.redraw_node(par,!0),callback&&callback.call(this,this.get_node(node)),this.trigger("create_node",{node:this.get_node(node),parent:par.id,position:pos}),node.id},rename_node:function(obj,val){var t1,t2,old;if($.isArray(obj)){for(obj=obj.slice(),t1=0,t2=obj.length;t1new_par.children.length&&(pos=new_par.children.length),!this.check("move_node",obj,new_par,pos,{core:!0,origin:origin,is_multi:old_ins&&old_ins._id&&old_ins._id!==this._id,is_foreign:!old_ins||!old_ins._id}))return this.settings.core.error.call(this,this._data.core.last_error),!1;if(obj.parent===new_par.id){for(dpc=new_par.children.concat(),tmp=$.inArray(obj.id,dpc),-1!==tmp&&(dpc=$.vakata.array_remove(dpc,tmp),pos>tmp&&pos--),tmp=[],i=0,j=dpc.length;i=pos?i+1:i]=dpc[i];tmp[pos]=obj.id,new_par.children=tmp,this._node_changed(new_par.id),this.redraw("#"===new_par.id)}else{for(tmp=obj.children_d.concat(),tmp.push(obj.id),i=0,j=obj.parents.length;i=pos?i+1:i]=new_par.children[i];for(dpc[pos]=obj.id,new_par.children=dpc,new_par.children_d.push(obj.id),new_par.children_d=new_par.children_d.concat(obj.children_d),obj.parent=new_par.id,tmp=new_par.parents.concat(),tmp.unshift(new_par.id),p=obj.parents.length,obj.parents=tmp,tmp=tmp.concat(),i=0,j=obj.children_d.length;inew_par.children.length&&(pos=new_par.children.length),!this.check("copy_node",obj,new_par,pos,{core:!0,origin:origin,is_multi:old_ins&&old_ins._id&&old_ins._id!==this._id,is_foreign:!old_ins||!old_ins._id}))return this.settings.core.error.call(this,this._data.core.last_error),!1;if(!(node=old_ins?old_ins.get_json(obj,{no_id:!0,no_data:!0,no_state:!0}):obj))return!1;if(!0===node.id&&delete node.id,!(node=this._parse_model_from_json(node,new_par.id,new_par.parents.concat())))return!1;for(tmp=this.get_node(node),obj&&obj.state&&!1===obj.state.loaded&&(tmp.state.loaded=!1),dpc=[],dpc.push(node),dpc=dpc.concat(tmp.children_d),this.trigger("model",{nodes:dpc,parent:new_par.id}),i=0,j=new_par.parents.length;i=pos?i+1:i]=new_par.children[i];return dpc[pos]=tmp.id,new_par.children=dpc,new_par.children_d.push(tmp.id),new_par.children_d=new_par.children_d.concat(tmp.children_d),"#"===new_par.id&&(this._model.force_full_redraw=!0),this._model.force_full_redraw||this._node_changed(new_par.id),skip_redraw||this.redraw("#"===new_par.id),callback&&callback.call(this,tmp,new_par,pos),this.trigger("copy_node",{node:tmp,original:obj,parent:new_par.id,position:pos,old_parent:old_par,old_position:old_ins&&old_ins._id&&old_par&&old_ins._model.data[old_par]&&old_ins._model.data[old_par].children?$.inArray(obj.id,old_ins._model.data[old_par].children):-1,is_multi:old_ins&&old_ins._id&&old_ins._id!==this._id,is_foreign:!old_ins||!old_ins._id,old_instance:old_ins,new_instance:this}),tmp.id},cut:function(obj){if(obj||(obj=this._data.core.selected.concat()),$.isArray(obj)||(obj=[obj]),!obj.length)return!1;var o,t1,t2,tmp=[];for(t1=0,t2=obj.length;t1"),t=default_text,h1=$("
    ",{css:{position:"absolute",top:"-200px",left:rtl?"0px":"-1000px",visibility:"hidden"}}).appendTo("body"),h2=$("",{value:t,class:"jstree-rename-input",css:{padding:"0",border:"1px solid silver","box-sizing":"border-box",display:"inline-block",height:this._data.core.li_height+"px",lineHeight:this._data.core.li_height+"px",width:"150px"},blur:$.proxy(function(){var nv,i=s.children(".jstree-rename-input"),v=i.val(),f=this.settings.core.force_text;""===v&&(v=t),h1.remove(),s.replaceWith(a),s.remove(),t=f?t:$("
    ").append($.parseHTML(t)).html(),this.set_text(obj,t),nv=!!this.rename_node(obj,f?$("
    ").text(v).text():$("
    ").append($.parseHTML(v)).html()),nv||this.set_text(obj,t),callback&&callback.call(this,tmp,nv)},this),keydown:function(event){var key=event.which;27===key&&(this.value=t),27!==key&&13!==key&&37!==key&&38!==key&&39!==key&&40!==key&&32!==key||event.stopImmediatePropagation(),27!==key&&13!==key||(event.preventDefault(),this.blur())},click:function(e){e.stopImmediatePropagation()},mousedown:function(e){e.stopImmediatePropagation()},keyup:function(event){h2.width(Math.min(h1.text("pW"+this.value).width(),w))},keypress:function(event){if(13===event.which)return!1}}),fn={fontFamily:a.css("fontFamily")||"",fontSize:a.css("fontSize")||"",fontWeight:a.css("fontWeight")||"",fontStyle:a.css("fontStyle")||"",fontStretch:a.css("fontStretch")||"",fontVariant:a.css("fontVariant")||"",letterSpacing:a.css("letterSpacing")||"",wordSpacing:a.css("wordSpacing")||""},s.attr("class",a.attr("class")).append(a.contents().clone()).append(h2),a.replaceWith(s),h1.css(fn),void h2.css(fn).width(Math.min(h1.text("pW"+h2[0].value).width(),w))[0].select()))},set_theme:function(theme_name,theme_url){if(!theme_name)return!1;if(!0===theme_url){var dir=this.settings.core.themes.dir;dir||(dir=$.jstree.path+"/themes"),theme_url=dir+"/"+theme_name+"/style.css"}theme_url&&-1===$.inArray(theme_url,themes_loaded)&&($("head").append(''),themes_loaded.push(theme_url)),this._data.core.themes.name&&this.element.removeClass("jstree-"+this._data.core.themes.name),this._data.core.themes.name=theme_name,this.element.addClass("jstree-"+theme_name),this.element[this.settings.core.themes.responsive?"addClass":"removeClass"]("jstree-"+theme_name+"-responsive"),this.trigger("set_theme",{theme:theme_name})},get_theme:function(){return this._data.core.themes.name},set_theme_variant:function(variant_name){this._data.core.themes.variant&&this.element.removeClass("jstree-"+this._data.core.themes.name+"-"+this._data.core.themes.variant),this._data.core.themes.variant=variant_name,variant_name&&this.element.addClass("jstree-"+this._data.core.themes.name+"-"+this._data.core.themes.variant)},get_theme_variant:function(){return this._data.core.themes.variant},show_stripes:function(){this._data.core.themes.stripes=!0,this.get_container_ul().addClass("jstree-striped")},hide_stripes:function(){this._data.core.themes.stripes=!1,this.get_container_ul().removeClass("jstree-striped")},toggle_stripes:function(){this._data.core.themes.stripes?this.hide_stripes():this.show_stripes()},show_dots:function(){this._data.core.themes.dots=!0,this.get_container_ul().removeClass("jstree-no-dots")},hide_dots:function(){this._data.core.themes.dots=!1,this.get_container_ul().addClass("jstree-no-dots")},toggle_dots:function(){this._data.core.themes.dots?this.hide_dots():this.show_dots()},show_icons:function(){this._data.core.themes.icons=!0,this.get_container_ul().removeClass("jstree-no-icons")},hide_icons:function(){this._data.core.themes.icons=!1,this.get_container_ul().addClass("jstree-no-icons")},toggle_icons:function(){this._data.core.themes.icons?this.hide_icons():this.show_icons()},set_icon:function(obj,icon){var t1,t2,dom,old;if($.isArray(obj)){for(obj=obj.slice(),t1=0,t2=obj.length;t1250)&&$.vakata.context.hide(),last_ts=0},this)).on("touchstart.jstree",".jstree-anchor",function(e){e.originalEvent&&e.originalEvent.changedTouches&&e.originalEvent.changedTouches[0]&&(ex=e.pageX,ey=e.pageY,cto=setTimeout(function(){$(e.currentTarget).trigger("contextmenu",!0)},750))}).on("touchmove.vakata.jstree",function(e){cto&&e.originalEvent&&e.originalEvent.changedTouches&&e.originalEvent.changedTouches[0]&&(Math.abs(ex-e.pageX)>50||Math.abs(ey-e.pageY)>50)&&clearTimeout(cto)}).on("touchend.vakata.jstree",function(e){cto&&clearTimeout(cto)}),$(document).on("context_hide.vakata.jstree",$.proxy(function(){this._data.contextmenu.visible=!1},this))},this.teardown=function(){this._data.contextmenu.visible&&$.vakata.context.hide(),parent.teardown.call(this)},this.show_contextmenu=function(obj,x,y,e){if(!(obj=this.get_node(obj))||"#"===obj.id)return!1;var s=this.settings.contextmenu,d=this.get_node(obj,!0),a=d.children(".jstree-anchor"),o=!1,i=!1;(s.show_at_node||x===undefined||y===undefined)&&(o=a.offset(),x=o.left,y=o.top+this._data.core.li_height),this.settings.contextmenu.select_node&&!this.is_selected(obj)&&this.activate_node(obj,e),i=s.items,$.isFunction(i)&&(i=i.call(this,obj,$.proxy(function(i){this._show_contextmenu(obj,x,y,i)},this))),$.isPlainObject(i)&&this._show_contextmenu(obj,x,y,i)},this._show_contextmenu=function(obj,x,y,i){var d=this.get_node(obj,!0),a=d.children(".jstree-anchor");$(document).one("context_show.vakata.jstree",$.proxy(function(e,data){var cls="jstree-contextmenu jstree-"+this.get_theme()+"-contextmenu";$(data.element).addClass(cls)},this)),this._data.contextmenu.visible=!0,$.vakata.context.show(a,{x:x,y:y},i),this.trigger("show_contextmenu",{node:obj,x:x,y:y})}},function($){var right_to_left=!1,vakata_context={element:!1,reference:!1,position_x:0,position_y:0,items:[],html:"",is_visible:!1};$.vakata.context={settings:{hide_onmouseleave:0,icons:!0},_trigger:function(event_name){$(document).triggerHandler("context_"+event_name+".vakata",{reference:vakata_context.reference,element:vakata_context.element,position:{x:vakata_context.position_x,y:vakata_context.position_y}})},_execute:function(i){return!(!(i=vakata_context.items[i])||i._disabled&&(!$.isFunction(i._disabled)||i._disabled({item:i,reference:vakata_context.reference,element:vakata_context.element}))||!i.action)&&i.action.call(null,{item:i,reference:vakata_context.reference,element:vakata_context.element,position:{x:vakata_context.position_x,y:vakata_context.position_y}})},_parse:function(o,is_callback){if(!o)return!1;is_callback||(vakata_context.html="",vakata_context.items=[]);var tmp,str="",sep=!1;return is_callback&&(str+=""),is_callback||(vakata_context.html=str,$.vakata.context._trigger("parse")),str.length>10&&str},_show_submenu:function(o){if(o=$(o),o.length&&o.children("ul").length){var e=o.children("ul"),x=o.offset().left+o.outerWidth(),y=o.offset().top,w=e.width(),h=e.height(),dw=$(window).width()+$(window).scrollLeft(),dh=$(window).height()+$(window).scrollTop();right_to_left?o[x-(w+10+o.outerWidth())<0?"addClass":"removeClass"]("vakata-context-left"):o[x+w+10>dw?"addClass":"removeClass"]("vakata-context-right"),y+h+10>dh&&e.css("bottom","-1px"), -e.show()}},show:function(reference,position,data){var o,e,x,y,w,h,dw,dh;switch(vakata_context.element&&vakata_context.element.length&&vakata_context.element.width(""),!0){case!position&&!reference:return!1;case!!position&&!!reference:vakata_context.reference=reference,vakata_context.position_x=position.x,vakata_context.position_y=position.y;break;case!position&&!!reference:vakata_context.reference=reference,o=reference.offset(),vakata_context.position_x=o.left+reference.outerHeight(),vakata_context.position_y=o.top;break;case!!position&&!reference:vakata_context.position_x=position.x,vakata_context.position_y=position.y}reference&&!data&&$(reference).data("vakata_contextmenu")&&(data=$(reference).data("vakata_contextmenu")),$.vakata.context._parse(data)&&vakata_context.element.html(vakata_context.html),vakata_context.items.length&&(vakata_context.element.appendTo("body"),e=vakata_context.element,x=vakata_context.position_x,y=vakata_context.position_y,w=e.width(),h=e.height(),dw=$(window).width()+$(window).scrollLeft(),dh=$(window).height()+$(window).scrollTop(),right_to_left&&(x-=e.outerWidth()-$(reference).outerWidth())<$(window).scrollLeft()+20&&(x=$(window).scrollLeft()+20),x+w+20>dw&&(x=dw-(w+20)),y+h+20>dh&&(y=dh-(h+20)),vakata_context.element.css({left:x,top:y}).show().find("a").first().focus().parent().addClass("vakata-context-hover"),vakata_context.is_visible=!0,$.vakata.context._trigger("show"))},hide:function(){vakata_context.is_visible&&(vakata_context.element.hide().find("ul").hide().end().find(":focus").blur().end().detach(),vakata_context.is_visible=!1,$.vakata.context._trigger("hide"))}},$(function(){right_to_left="rtl"===$("body").css("direction");var to=!1;vakata_context.element=$("
      "),vakata_context.element.on("mouseenter","li",function(e){e.stopImmediatePropagation(),$.contains(this,e.relatedTarget)||(to&&clearTimeout(to),vakata_context.element.find(".vakata-context-hover").removeClass("vakata-context-hover").end(),$(this).siblings().find("ul").hide().end().end().parentsUntil(".vakata-context","li").addBack().addClass("vakata-context-hover"),$.vakata.context._show_submenu(this))}).on("mouseleave","li",function(e){$.contains(this,e.relatedTarget)||$(this).find(".vakata-context-hover").addBack().removeClass("vakata-context-hover")}).on("mouseleave",function(e){$(this).find(".vakata-context-hover").removeClass("vakata-context-hover"),$.vakata.context.settings.hide_onmouseleave&&(to=setTimeout(function(t){return function(){$.vakata.context.hide()}}(),$.vakata.context.settings.hide_onmouseleave))}).on("click","a",function(e){e.preventDefault(),$(this).blur().parent().hasClass("vakata-context-disabled")||!1===$.vakata.context._execute($(this).attr("rel"))||$.vakata.context.hide()}).on("keydown","a",function(e){var o=null;switch(e.which){case 13:case 32:e.type="mouseup",e.preventDefault(),$(e.currentTarget).trigger(e);break;case 37:vakata_context.is_visible&&(vakata_context.element.find(".vakata-context-hover").last().closest("li").first().find("ul").hide().find(".vakata-context-hover").removeClass("vakata-context-hover").end().end().children("a").focus(),e.stopImmediatePropagation(),e.preventDefault());break;case 38:vakata_context.is_visible&&(o=vakata_context.element.find("ul:visible").addBack().last().children(".vakata-context-hover").removeClass("vakata-context-hover").prevAll("li:not(.vakata-context-separator)").first(),o.length||(o=vakata_context.element.find("ul:visible").addBack().last().children("li:not(.vakata-context-separator)").last()),o.addClass("vakata-context-hover").children("a").focus(),e.stopImmediatePropagation(),e.preventDefault());break;case 39:vakata_context.is_visible&&(vakata_context.element.find(".vakata-context-hover").last().children("ul").show().children("li:not(.vakata-context-separator)").removeClass("vakata-context-hover").first().addClass("vakata-context-hover").children("a").focus(),e.stopImmediatePropagation(),e.preventDefault());break;case 40:vakata_context.is_visible&&(o=vakata_context.element.find("ul:visible").addBack().last().children(".vakata-context-hover").removeClass("vakata-context-hover").nextAll("li:not(.vakata-context-separator)").first(),o.length||(o=vakata_context.element.find("ul:visible").addBack().last().children("li:not(.vakata-context-separator)").first()),o.addClass("vakata-context-hover").children("a").focus(),e.stopImmediatePropagation(),e.preventDefault());break;case 27:$.vakata.context.hide(),e.preventDefault()}}).on("keydown",function(e){e.preventDefault();var a=vakata_context.element.find(".vakata-contextmenu-shortcut-"+e.which).parent();a.parent().not(".vakata-context-disabled")&&a.click()}),$(document).on("mousedown.vakata.jstree",function(e){vakata_context.is_visible&&!$.contains(vakata_context.element[0],e.target)&&$.vakata.context.hide()}).on("context_show.vakata.jstree",function(e,data){vakata_context.element.find("li:has(ul)").children("a").addClass("vakata-context-parent"),right_to_left&&vakata_context.element.addClass("vakata-context-rtl").css("direction","rtl"),vakata_context.element.find("ul").hide().end()})})}($),$.jstree.defaults.dnd={copy:!0,open_timeout:500,is_draggable:!0,check_while_dragging:!0,always_copy:!1,inside_pos:0,drag_selection:!0,touch:!0,large_drop_target:!1,large_drag_target:!1},$.jstree.plugins.dnd=function(options,parent){this.bind=function(){parent.bind.call(this),this.element.on("mousedown.jstree touchstart.jstree",this.settings.dnd.large_drag_target?".jstree-node":".jstree-anchor",$.proxy(function(e){if(this.settings.dnd.large_drag_target&&$(e.target).closest(".jstree-node")[0]!==e.currentTarget)return!0;if("touchstart"===e.type&&(!this.settings.dnd.touch||"selected"===this.settings.dnd.touch&&!$(e.currentTarget).closest(".jstree-node").children(".jstree-anchor").hasClass("jstree-clicked")))return!0;var obj=this.get_node(e.target),mlt=this.is_selected(obj)&&this.settings.dnd.drag_selection?this.get_top_selected().length:1,txt=mlt>1?mlt+" "+this.get_string("nodes"):this.get_text(e.currentTarget);return this.settings.core.force_text&&(txt=$.vakata.html.escape(txt)),obj&&obj.id&&"#"!==obj.id&&(1===e.which||"touchstart"===e.type)&&(!0===this.settings.dnd.is_draggable||$.isFunction(this.settings.dnd.is_draggable)&&this.settings.dnd.is_draggable.call(this,mlt>1?this.get_top_selected(!0):[obj]))?(this.element.trigger("mousedown.jstree"),$.vakata.dnd.start(e,{jstree:!0,origin:this,obj:this.get_node(obj,!0),nodes:mlt>1?this.get_top_selected():[obj.id]},'
      '+txt+'
      ')):void 0},this))}},$(function(){var lastmv=!1,laster=!1,opento=!1,marker=$('
       
      ').hide();$(document).on("dnd_start.vakata.jstree",function(e,data){lastmv=!1,data&&data.data&&data.data.jstree&&marker.appendTo("body")}).on("dnd_move.vakata.jstree",function(e,data){if(opento&&clearTimeout(opento),data&&data.data&&data.data.jstree&&(!data.event.target.id||"jstree-marker"!==data.event.target.id)){var l,t,h,p,i,o,ok,t1,t2,op,ps,pr,ip,tm,ins=$.jstree.reference(data.event.target),ref=!1,off=!1,rel=!1;if(ins&&ins._data&&ins._data.dnd)if(marker.attr("class","jstree-"+ins.get_theme()+(ins.settings.core.themes.responsive?" jstree-dnd-responsive":"")),data.helper.children().attr("class","jstree-"+ins.get_theme()+" jstree-"+ins.get_theme()+"-"+ins.get_theme_variant()+" "+(ins.settings.core.themes.responsive?" jstree-dnd-responsive":"")).find(".jstree-copy").first()[data.data.origin&&(data.data.origin.settings.dnd.always_copy||data.data.origin.settings.dnd.copy&&(data.event.metaKey||data.event.ctrlKey))?"show":"hide"](),data.event.target!==ins.element[0]&&data.event.target!==ins.get_container_ul()[0]||0!==ins.get_container_ul().children().length){if((ref=ins.settings.dnd.large_drop_target?$(data.event.target).closest(".jstree-node").children(".jstree-anchor"):$(data.event.target).closest(".jstree-anchor"))&&ref.length&&ref.parent().is(".jstree-closed, .jstree-open, .jstree-leaf")&&(off=ref.offset(),rel=data.event.pageY-off.top,h=ref.outerHeight(),o=relh-h/3?["a","i","b"]:rel>h/2?["i","a","b"]:["i","b","a"],$.each(o,function(j,v){switch(v){case"b":l=off.left-6,t=off.top,p=ins.get_parent(ref),i=ref.parent().index();break;case"i":ip=ins.settings.dnd.inside_pos,tm=ins.get_node(ref.parent()),l=off.left-2,t=off.top+h/2+1,p=tm.id,i="first"===ip?0:"last"===ip?tm.children.length:Math.min(ip,tm.children.length);break;case"a":l=off.left-6,t=off.top+h,p=ins.get_parent(ref),i=ref.parent().index()+1}for(ok=!0,t1=0,t2=data.data.nodes.length;t1$.inArray(data.data.nodes[t1],pr.children)&&(ps-=1)),!(ok=ok&&(ins&&ins.settings&&ins.settings.dnd&&!1===ins.settings.dnd.check_while_dragging||ins.check(op,data.data.origin&&data.data.origin!==ins?data.data.origin.get_node(data.data.nodes[t1]):data.data.nodes[t1],p,ps,{dnd:!0,ref:ins.get_node(ref.parent()),pos:v,origin:data.data.origin,is_multi:data.data.origin&&data.data.origin!==ins,is_foreign:!data.data.origin})))){ins&&ins.last_error&&(laster=ins.last_error());break}if("i"===v&&ref.parent().is(".jstree-closed")&&ins.settings.dnd.open_timeout&&(opento=setTimeout(function(x,z){return function(){x.open_node(z)}}(ins,ref),ins.settings.dnd.open_timeout)),ok)return lastmv={ins:ins,par:p,pos:"i"!==v||"last"!==ip||0!==i||ins.is_loaded(tm)?i:"last"},marker.css({left:l+"px",top:t+"px"}).show(),data.helper.find(".jstree-icon").first().removeClass("jstree-er").addClass("jstree-ok"),laster={},o=!0,!1}),!0===o))return}else{for(ok=!0,t1=0,t2=data.data.nodes.length;t1"),escape:function(str){return $.vakata.html.div.text(str).html()},strip:function(str){return $.vakata.html.div.empty().append($.parseHTML(str)).text()}};var vakata_dnd={element:!1,target:!1,is_down:!1,is_drag:!1,helper:!1,helper_w:0,data:!1,init_x:0,init_y:0,scroll_l:0,scroll_t:0,scroll_e:!1,scroll_i:!1,is_touch:!1};$.vakata.dnd={settings:{scroll_speed:10,scroll_proximity:20,helper_left:5,helper_top:10,threshold:5,threshold_touch:50},_trigger:function(event_name,e){var data=$.vakata.dnd._get();data.event=e,$(document).triggerHandler("dnd_"+event_name+".vakata",data)},_get:function(){return{data:vakata_dnd.data,element:vakata_dnd.element,helper:vakata_dnd.helper}},_clean:function(){vakata_dnd.helper&&vakata_dnd.helper.remove(),vakata_dnd.scroll_i&&(clearInterval(vakata_dnd.scroll_i),vakata_dnd.scroll_i=!1),vakata_dnd={element:!1,target:!1,is_down:!1,is_drag:!1,helper:!1,helper_w:0,data:!1,init_x:0,init_y:0,scroll_l:0,scroll_t:0,scroll_e:!1,scroll_i:!1,is_touch:!1},$(document).off("mousemove.vakata.jstree touchmove.vakata.jstree",$.vakata.dnd.drag),$(document).off("mouseup.vakata.jstree touchend.vakata.jstree",$.vakata.dnd.stop)},_scroll:function(init_only){if(!vakata_dnd.scroll_e||!vakata_dnd.scroll_l&&!vakata_dnd.scroll_t)return vakata_dnd.scroll_i&&(clearInterval(vakata_dnd.scroll_i),vakata_dnd.scroll_i=!1),!1;if(!vakata_dnd.scroll_i)return vakata_dnd.scroll_i=setInterval($.vakata.dnd._scroll,100),!1;if(!0===init_only)return!1;var i=vakata_dnd.scroll_e.scrollTop(),j=vakata_dnd.scroll_e.scrollLeft();vakata_dnd.scroll_e.scrollTop(i+vakata_dnd.scroll_t*$.vakata.dnd.settings.scroll_speed),vakata_dnd.scroll_e.scrollLeft(j+vakata_dnd.scroll_l*$.vakata.dnd.settings.scroll_speed),i===vakata_dnd.scroll_e.scrollTop()&&j===vakata_dnd.scroll_e.scrollLeft()||$.vakata.dnd._trigger("scroll",vakata_dnd.scroll_e)},start:function(e,data,html){"touchstart"===e.type&&e.originalEvent&&e.originalEvent.changedTouches&&e.originalEvent.changedTouches[0]&&(e.pageX=e.originalEvent.changedTouches[0].pageX,e.pageY=e.originalEvent.changedTouches[0].pageY,e.target=document.elementFromPoint(e.originalEvent.changedTouches[0].pageX-window.pageXOffset,e.originalEvent.changedTouches[0].pageY-window.pageYOffset)),vakata_dnd.is_drag&&$.vakata.dnd.stop({});try{e.currentTarget.unselectable="on",e.currentTarget.onselectstart=function(){return!1},e.currentTarget.style&&(e.currentTarget.style.MozUserSelect="none")}catch(ignore){}return vakata_dnd.init_x=e.pageX,vakata_dnd.init_y=e.pageY,vakata_dnd.data=data,vakata_dnd.is_down=!0,vakata_dnd.element=e.currentTarget,vakata_dnd.target=e.target,vakata_dnd.is_touch="touchstart"===e.type,!1!==html&&(vakata_dnd.helper=$("
      ").html(html).css({display:"block",margin:"0",padding:"0",position:"absolute",top:"-2000px",lineHeight:"16px",zIndex:"10000"})),$(document).on("mousemove.vakata.jstree touchmove.vakata.jstree",$.vakata.dnd.drag),$(document).on("mouseup.vakata.jstree touchend.vakata.jstree",$.vakata.dnd.stop),!1},drag:function(e){if("touchmove"===e.type&&e.originalEvent&&e.originalEvent.changedTouches&&e.originalEvent.changedTouches[0]&&(e.pageX=e.originalEvent.changedTouches[0].pageX,e.pageY=e.originalEvent.changedTouches[0].pageY,e.target=document.elementFromPoint(e.originalEvent.changedTouches[0].pageX-window.pageXOffset,e.originalEvent.changedTouches[0].pageY-window.pageYOffset)),vakata_dnd.is_down){if(!vakata_dnd.is_drag){if(!(Math.abs(e.pageX-vakata_dnd.init_x)>(vakata_dnd.is_touch?$.vakata.dnd.settings.threshold_touch:$.vakata.dnd.settings.threshold)||Math.abs(e.pageY-vakata_dnd.init_y)>(vakata_dnd.is_touch?$.vakata.dnd.settings.threshold_touch:$.vakata.dnd.settings.threshold)))return;vakata_dnd.helper&&(vakata_dnd.helper.appendTo("body"),vakata_dnd.helper_w=vakata_dnd.helper.outerWidth()),vakata_dnd.is_drag=!0,$.vakata.dnd._trigger("start",e)}var d=!1,w=!1,dh=!1,wh=!1,dw=!1,ww=!1,dt=!1,dl=!1,ht=!1,hl=!1;return vakata_dnd.scroll_t=0,vakata_dnd.scroll_l=0,vakata_dnd.scroll_e=!1,$($(e.target).parentsUntil("body").addBack().get().reverse()).filter(function(){return/^auto|scroll$/.test($(this).css("overflow"))&&(this.scrollHeight>this.offsetHeight||this.scrollWidth>this.offsetWidth)}).each(function(){var t=$(this),o=t.offset();if(this.scrollHeight>this.offsetHeight&&(o.top+t.height()-e.pageY<$.vakata.dnd.settings.scroll_proximity&&(vakata_dnd.scroll_t=1),e.pageY-o.top<$.vakata.dnd.settings.scroll_proximity&&(vakata_dnd.scroll_t=-1)),this.scrollWidth>this.offsetWidth&&(o.left+t.width()-e.pageX<$.vakata.dnd.settings.scroll_proximity&&(vakata_dnd.scroll_l=1),e.pageX-o.left<$.vakata.dnd.settings.scroll_proximity&&(vakata_dnd.scroll_l=-1)),vakata_dnd.scroll_t||vakata_dnd.scroll_l)return vakata_dnd.scroll_e=$(this),!1}),vakata_dnd.scroll_e||(d=$(document),w=$(window),dh=d.height(),wh=w.height(),dw=d.width(),ww=w.width(),dt=d.scrollTop(),dl=d.scrollLeft(),dh>wh&&e.pageY-dt<$.vakata.dnd.settings.scroll_proximity&&(vakata_dnd.scroll_t=-1),dh>wh&&wh-(e.pageY-dt)<$.vakata.dnd.settings.scroll_proximity&&(vakata_dnd.scroll_t=1),dw>ww&&e.pageX-dl<$.vakata.dnd.settings.scroll_proximity&&(vakata_dnd.scroll_l=-1),dw>ww&&ww-(e.pageX-dl)<$.vakata.dnd.settings.scroll_proximity&&(vakata_dnd.scroll_l=1),(vakata_dnd.scroll_t||vakata_dnd.scroll_l)&&(vakata_dnd.scroll_e=d)),vakata_dnd.scroll_e&&$.vakata.dnd._scroll(!0),vakata_dnd.helper&&(ht=parseInt(e.pageY+$.vakata.dnd.settings.helper_top,10),hl=parseInt(e.pageX+$.vakata.dnd.settings.helper_left,10),dh&&ht+25>dh&&(ht=dh-50),dw&&hl+vakata_dnd.helper_w>dw&&(hl=dw-(vakata_dnd.helper_w+2)),vakata_dnd.helper.css({left:hl+"px",top:ht+"px"})),$.vakata.dnd._trigger("move",e),!1}},stop:function(e){if("touchend"===e.type&&e.originalEvent&&e.originalEvent.changedTouches&&e.originalEvent.changedTouches[0]&&(e.pageX=e.originalEvent.changedTouches[0].pageX,e.pageY=e.originalEvent.changedTouches[0].pageY,e.target=document.elementFromPoint(e.originalEvent.changedTouches[0].pageX-window.pageXOffset,e.originalEvent.changedTouches[0].pageY-window.pageYOffset)),vakata_dnd.is_drag)$.vakata.dnd._trigger("stop",e);else if("touchend"===e.type&&e.target===vakata_dnd.target){var to=setTimeout(function(){$(e.target).click()},100);$(e.target).one("click",function(){to&&clearTimeout(to)})}return $.vakata.dnd._clean(),!1}}}($),$.jstree.defaults.massload=null,$.jstree.plugins.massload=function(options,parent){this.init=function(el,options){parent.init.call(this,el,options),this._data.massload={}},this._load_nodes=function(nodes,callback,is_callback){var s=this.settings.massload;return is_callback&&!$.isEmptyObject(this._data.massload)?parent._load_nodes.call(this,nodes,callback,is_callback):$.isFunction(s)?s.call(this,nodes,$.proxy(function(data){if(data)for(var i in data)data.hasOwnProperty(i)&&(this._data.massload[i]=data[i]);parent._load_nodes.call(this,nodes,callback,is_callback)},this)):"object"==typeof s&&s&&s.url?(s=$.extend(!0,{},s),$.isFunction(s.url)&&(s.url=s.url.call(this,nodes)),$.isFunction(s.data)&&(s.data=s.data.call(this,nodes)),$.ajax(s).done($.proxy(function(data,t,x){if(data)for(var i in data)data.hasOwnProperty(i)&&(this._data.massload[i]=data[i]);parent._load_nodes.call(this,nodes,callback,is_callback)},this)).fail($.proxy(function(f){parent._load_nodes.call(this,nodes,callback,is_callback)},this))):parent._load_nodes.call(this,nodes,callback,is_callback)},this._load_node=function(obj,callback){var d=this._data.massload[obj.id];return d?this["string"==typeof d?"_append_html_data":"_append_json_data"](obj,"string"==typeof d?$($.parseHTML(d)).filter(function(){return 3!==this.nodeType}):d,function(status){callback.call(this,status),delete this._data.massload[obj.id]}):parent._load_node.call(this,obj,callback)}},$.jstree.defaults.search={ajax:!1,fuzzy:!1,case_sensitive:!1,show_only_matches:!1,show_only_matches_children:!1,close_opened_onclear:!0,search_leaves_only:!1,search_callback:!1},$.jstree.plugins.search=function(options,parent){this.bind=function(){parent.bind.call(this),this._data.search.str="",this._data.search.dom=$(),this._data.search.res=[],this._data.search.opn=[],this._data.search.som=!1,this._data.search.smc=!1,this.element.on("before_open.jstree",$.proxy(function(e,data){var i,j,r=this._data.search.res,s=[],o=$();if(r&&r.length&&(this._data.search.dom=$(this.element[0].querySelectorAll("#"+$.map(r,function(v){return-1!=="0123456789".indexOf(v[0])?"\\3"+v[0]+" "+v.substr(1).replace($.jstree.idregex,"\\$&"):v.replace($.jstree.idregex,"\\$&")}).join(", #"))),this._data.search.dom.children(".jstree-anchor").addClass("jstree-search"),this._data.search.som&&this._data.search.res.length)){for(i=0,j=r.length;i32&&(options.fuzzy=!1),options.fuzzy&&(matchmask=1<=start;j--)if(charMatch=pattern_alphabet[text.charAt(j-1)],rd[j]=0===i?(rd[j+1]<<1|1)&charMatch:(rd[j+1]<<1|1)&charMatch|(lastRd[j+1]|lastRd[j])<<1|1|lastRd[j+1],rd[j]&matchmask&&(score=match_bitapScore(i,j-1))<=scoreThreshold){if(scoreThreshold=score,bestLoc=j-1,locations.push(bestLoc),!(bestLoc>MATCH_LOCATION))break;start=Math.max(1,2*MATCH_LOCATION-bestLoc)}if(match_bitapScore(i+1,MATCH_LOCATION)>scoreThreshold)break;lastRd=rd}return{isMatch:bestLoc>=0,score:score}},!0===txt?{search:search}:search(txt)},$.vakata.search.defaults={location:0,distance:100,threshold:.6,fuzzy:!1,caseSensitive:!1}}($),$.jstree.defaults.sort=function(a,b){return this.get_text(a)>this.get_text(b)?1:-1},$.jstree.plugins.sort=function(options,parent){this.bind=function(){parent.bind.call(this),this.element.on("model.jstree",$.proxy(function(e,data){this.sort(data.parent,!0)},this)).on("rename_node.jstree create_node.jstree",$.proxy(function(e,data){this.sort(data.parent||data.node.parent,!1),this.redraw_node(data.parent||data.node.parent,!0)},this)).on("move_node.jstree copy_node.jstree",$.proxy(function(e,data){this.sort(data.parent,!1),this.redraw_node(data.parent,!0)},this))},this.sort=function(obj,deep){var i,j;if((obj=this.get_node(obj))&&obj.children&&obj.children.length&&(obj.children.sort($.proxy(this.settings.sort,this)),deep))for(i=0,j=obj.children_d.length;ik.ttl)&&(k&&k.state&&(k=k.state),k&&$.isFunction(this.settings.state.filter)&&(k=this.settings.state.filter.call(this,k)),!!k&&(this.element.one("set_state.jstree",function(e,data){data.instance.trigger("restore_state",{state:$.extend(!0,{},k)})}),this.set_state(k),!0))},this.clear_state=function(){return $.vakata.storage.del(this.settings.state.key)}},function($,undefined){$.vakata.storage={set:function(key,val){return window.localStorage.setItem(key,val)},get:function(key){return window.localStorage.getItem(key)},del:function(key){return window.localStorage.removeItem(key)}}}($),$.jstree.defaults.types={"#":{},default:{}},$.jstree.plugins.types=function(options,parent){this.init=function(el,options){var i,j;if(options&&options.types&&options.types.default)for(i in options.types)if("default"!==i&&"#"!==i&&options.types.hasOwnProperty(i))for(j in options.types.default)options.types.default.hasOwnProperty(j)&&options.types[i][j]===undefined&&(options.types[i][j]=options.types.default[j]);parent.init.call(this,el,options),this._model.data["#"].type="#"},this.refresh=function(skip_loading,forget_state){parent.refresh.call(this,skip_loading,forget_state),this._model.data["#"].type="#"},this.bind=function(){this.element.on("model.jstree",$.proxy(function(e,data){var i,j,m=this._model.data,dpc=data.nodes,t=this.settings.types,c="default";for(i=0,j=dpc.length;i .jstree-ocl",$.proxy(function(e){e.stopImmediatePropagation();var tmp=$.Event("click",{metaKey:e.metaKey,ctrlKey:e.ctrlKey,altKey:e.altKey,shiftKey:e.shiftKey});$(e.currentTarget).closest(".jstree-node").children(".jstree-anchor").first().trigger(tmp).focus()},this)).on("mouseover.jstree",".jstree-wholerow, .jstree-icon",$.proxy(function(e){return e.stopImmediatePropagation(),this.is_disabled(e.currentTarget)||this.hover_node(e.currentTarget),!1},this)).on("mouseleave.jstree",".jstree-node",$.proxy(function(e){this.dehover_node(e.currentTarget)},this))},this.teardown=function(){this.settings.wholerow&&this.element.find(".jstree-wholerow").remove(),parent.teardown.call(this)},this.redraw_node=function(obj,deep,callback,force_render){if(obj=parent.redraw_node.apply(this,arguments)){var tmp=div.cloneNode(!0);-1!==$.inArray(obj.id,this._data.core.selected)&&(tmp.className+=" jstree-wholerow-clicked"),this._data.core.focused&&this._data.core.focused===obj.id&&(tmp.className+=" jstree-wholerow-hovered"),obj.insertBefore(tmp,obj.childNodes[0])}return obj}},document.registerElement&&Object&&Object.create){var proto=Object.create(HTMLElement.prototype);proto.createdCallback=function(){var i,c={core:{},plugins:[]};for(i in $.jstree.plugins)$.jstree.plugins.hasOwnProperty(i)&&this.attributes[i]&&(c.plugins.push(i),this.getAttribute(i)&&JSON.parse(this.getAttribute(i))&&(c[i]=JSON.parse(this.getAttribute(i))));for(i in $.jstree.defaults.core)$.jstree.defaults.core.hasOwnProperty(i)&&this.attributes[i]&&(c.core[i]=JSON.parse(this.getAttribute(i))||this.getAttribute(i));$(this).jstree(c)};try{document.registerElement("vakata-jstree",{prototype:proto})}catch(ignore){}}}}); \ No newline at end of file +! function(factory) { + "use strict"; + "function" == typeof define && define.amd ? define(["jquery"], factory) : factory("object" == typeof exports ? require("jquery") : jQuery) +}(function($, undefined) { + "use strict"; + if (!$.jstree) { + var _temp1, _temp2, instance_counter = 0, + ccp_node = !1, + ccp_mode = !1, + ccp_inst = !1, + themes_loaded = [], + src = $("script:last").attr("src"), + document = window.document, + _node = document.createElement("LI"); + _node.setAttribute("role", "treeitem"), _temp1 = document.createElement("I"), _temp1.className = "jstree-icon jstree-ocl", _temp1.setAttribute("role", "presentation"), _node.appendChild(_temp1), _temp1 = document.createElement("A"), _temp1.className = "jstree-anchor", _temp1.setAttribute("href", "#"), _temp1.setAttribute("tabindex", "-1"), _temp2 = document.createElement("I"), _temp2.className = "jstree-icon jstree-themeicon", _temp2.setAttribute("role", "presentation"), _temp1.appendChild(_temp2), _node.appendChild(_temp1), _temp1 = _temp2 = null, $.jstree = { + version: "3.1.1", + defaults: { + plugins: [] + }, + plugins: {}, + path: src && -1 !== src.indexOf("/") ? src.replace(/\/[^\/]+$/, "") : "", + idregex: /[\\:&!^|()\[\]<>@*'+~#";.,=\- \/${}%?`]/g + }, $.jstree.create = function(el, options) { + var tmp = new $.jstree.core(++instance_counter), + opt = options; + return options = $.extend(!0, {}, $.jstree.defaults, options), opt && opt.plugins && (options.plugins = opt.plugins), $.each(options.plugins, function(i, k) { + "core" !== i && (tmp = tmp.plugin(k, options[k])) + }), $(el).data("jstree", tmp), tmp.init(el, options), tmp + }, $.jstree.destroy = function() { + $(".jstree:jstree").jstree("destroy"), $(document).off(".jstree") + }, $.jstree.core = function(id) { + this._id = id, this._cnt = 0, this._wrk = null, this._data = { + core: { + themes: { + name: !1, + dots: !1, + icons: !1 + }, + selected: [], + last_error: {}, + working: !1, + worker_queue: [], + focused: null + } + } + }, $.jstree.reference = function(needle) { + var tmp = null, + obj = null; + if (!needle || !needle.id || needle.tagName && needle.nodeType || (needle = needle.id), !obj || !obj.length) try { + obj = $(needle) + } catch (ignore) {} + if (!obj || !obj.length) try { + obj = $("#" + needle.replace($.jstree.idregex, "\\$&")) + } catch (ignore) {} + return obj && obj.length && (obj = obj.closest(".jstree")).length && (obj = obj.data("jstree")) ? tmp = obj : $(".jstree").each(function() { + var inst = $(this).data("jstree"); + if (inst && inst._model.data[needle]) return tmp = inst, !1 + }), tmp + }, $.fn.jstree = function(arg) { + var is_method = "string" == typeof arg, + args = Array.prototype.slice.call(arguments, 1), + result = null; + return !(!0 === arg && !this.length) && (this.each(function() { + var instance = $.jstree.reference(this), + method = is_method && instance ? instance[arg] : null; + if (result = is_method && method ? method.apply(instance, args) : null, instance || is_method || arg !== undefined && !$.isPlainObject(arg) || $.jstree.create(this, arg), (instance && !is_method || !0 === arg) && (result = instance || !1), null !== result && result !== undefined) return !1 + }), null !== result && result !== undefined ? result : this) + }, $.expr[":"].jstree = $.expr.createPseudo(function(search) { + return function(a) { + return $(a).hasClass("jstree") && $(a).data("jstree") !== undefined + } + }), $.jstree.defaults.core = { + data: !1, + strings: !1, + check_callback: !1, + error: $.noop, + animation: 200, + multiple: !0, + themes: { + name: !1, + url: !1, + dir: !1, + dots: !0, + icons: !0, + stripes: !1, + variant: !1, + responsive: !1 + }, + expand_selected_onload: !0, + worker: !0, + force_text: !1, + dblclick_toggle: !0 + }, $.jstree.core.prototype = { + plugin: function(deco, opts) { + var Child = $.jstree.plugins[deco]; + return Child ? (this._data[deco] = {}, Child.prototype = this, new Child(opts, this)) : this + }, + init: function(el, options) { + this._model = { + data: { + "#": { + id: "#", + parent: null, + parents: [], + children: [], + children_d: [], + state: { + loaded: !1 + } + } + }, + changed: [], + force_full_redraw: !1, + redraw_timeout: !1, + default_state: { + loaded: !0, + opened: !1, + selected: !1, + disabled: !1 + } + }, this.element = $(el).addClass("jstree jstree-" + this._id), this.settings = options, this._data.core.ready = !1, this._data.core.loaded = !1, this._data.core.rtl = "rtl" === this.element.css("direction"), this.element[this._data.core.rtl ? "addClass" : "removeClass"]("jstree-rtl"), this.element.attr("role", "tree"), this.settings.core.multiple && this.element.attr("aria-multiselectable", !0), this.element.attr("tabindex") || this.element.attr("tabindex", "0"), this.bind(), this.trigger("init"), this._data.core.original_container_html = this.element.find(" > ul > li").clone(!0), this._data.core.original_container_html.find("li").addBack().contents().filter(function() { + return 3 === this.nodeType && (!this.nodeValue || /^\s+$/.test(this.nodeValue)) + }).remove(), this.element.html(""), this.element.attr("aria-activedescendant", "j" + this._id + "_loading"), this._data.core.li_height = this.get_container_ul().children("li").first().height() || 24, this.trigger("loading"), this.load_node("#") + }, + destroy: function(keep_html) { + if (this._wrk) try { + window.URL.revokeObjectURL(this._wrk), this._wrk = null + } catch (ignore) {} + keep_html || this.element.empty(), this.teardown() + }, + teardown: function() { + this.unbind(), this.element.removeClass("jstree").removeData("jstree").find("[class^='jstree']").addBack().attr("class", function() { + return this.className.replace(/jstree[^ ]*|$/gi, "") + }), this.element = null + }, + bind: function() { + var word = "", + tout = null, + was_click = 0; + this.element.on("dblclick.jstree", function() { + if (document.selection && document.selection.empty) document.selection.empty(); + else if (window.getSelection) { + var sel = window.getSelection(); + try { + sel.removeAllRanges(), sel.collapse() + } catch (ignore) {} + } + }).on("mousedown.jstree", $.proxy(function(e) { + e.target === this.element[0] && (e.preventDefault(), was_click = +new Date) + }, this)).on("mousedown.jstree", ".jstree-ocl", function(e) { + e.preventDefault() + }).on("click.jstree", ".jstree-ocl", $.proxy(function(e) { + this.toggle_node(e.target) + }, this)).on("dblclick.jstree", ".jstree-anchor", $.proxy(function(e) { + this.settings.core.dblclick_toggle && this.toggle_node(e.target) + }, this)).on("click.jstree", ".jstree-anchor", $.proxy(function(e) { + e.preventDefault(), e.currentTarget !== document.activeElement && $(e.currentTarget).focus(), this.activate_node(e.currentTarget, e) + }, this)).on("keydown.jstree", ".jstree-anchor", $.proxy(function(e) { + if ("INPUT" === e.target.tagName) return !0; + if (32 !== e.which && 13 !== e.which && (e.shiftKey || e.ctrlKey || e.altKey || e.metaKey)) return !0; + var o = null; + switch (this._data.core.rtl && (37 === e.which ? e.which = 39 : 39 === e.which && (e.which = 37)), e.which) { + case 32: + e.ctrlKey && (e.type = "click", $(e.currentTarget).trigger(e)); + break; + case 13: + e.type = "click", $(e.currentTarget).trigger(e); + break; + case 37: + e.preventDefault(), this.is_open(e.currentTarget) ? this.close_node(e.currentTarget) : (o = this.get_parent(e.currentTarget)) && "#" !== o.id && this.get_node(o, !0).children(".jstree-anchor").focus(); + break; + case 38: + e.preventDefault(), o = this.get_prev_dom(e.currentTarget), o && o.length && o.children(".jstree-anchor").focus(); + break; + case 39: + e.preventDefault(), this.is_closed(e.currentTarget) ? this.open_node(e.currentTarget, function(o) { + this.get_node(o, !0).children(".jstree-anchor").focus() + }) : this.is_open(e.currentTarget) && (o = this.get_node(e.currentTarget, !0).children(".jstree-children")[0]) && $(this._firstChild(o)).children(".jstree-anchor").focus(); + break; + case 40: + e.preventDefault(), o = this.get_next_dom(e.currentTarget), o && o.length && o.children(".jstree-anchor").focus(); + break; + case 106: + this.open_all(); + break; + case 36: + e.preventDefault(), o = this._firstChild(this.get_container_ul()[0]), o && $(o).children(".jstree-anchor").filter(":visible").focus(); + break; + case 35: + e.preventDefault(), this.element.find(".jstree-anchor").filter(":visible").last().focus() + } + }, this)).on("load_node.jstree", $.proxy(function(e, data) { + data.status && ("#" !== data.node.id || this._data.core.loaded || (this._data.core.loaded = !0, this._firstChild(this.get_container_ul()[0]) && this.element.attr("aria-activedescendant", this._firstChild(this.get_container_ul()[0]).id), this.trigger("loaded")), this._data.core.ready || setTimeout($.proxy(function() { + if (this.element && !this.get_container_ul().find(".jstree-loading").length) { + if (this._data.core.ready = !0, this._data.core.selected.length) { + if (this.settings.core.expand_selected_onload) { + var i, j, tmp = []; + for (i = 0, j = this._data.core.selected.length; i < j; i++) tmp = tmp.concat(this._model.data[this._data.core.selected[i]].parents); + for (tmp = $.vakata.array_unique(tmp), i = 0, j = tmp.length; i < j; i++) this.open_node(tmp[i], !1, 0) + } + this.trigger("changed", { + action: "ready", + selected: this._data.core.selected + }) + } + this.trigger("ready") + } + }, this), 0)) + }, this)).on("keypress.jstree", $.proxy(function(e) { + if ("INPUT" === e.target.tagName) return !0; + tout && clearTimeout(tout), tout = setTimeout(function() { + word = "" + }, 500); + var chr = String.fromCharCode(e.which).toLowerCase(), + col = this.element.find(".jstree-anchor").filter(":visible"), + ind = col.index(document.activeElement) || 0, + end = !1; + if (word += chr, word.length > 1) { + if (col.slice(ind).each($.proxy(function(i, v) { + if (0 === $(v).text().toLowerCase().indexOf(word)) return $(v).focus(), end = !0, !1 + }, this)), end) return; + if (col.slice(0, ind).each($.proxy(function(i, v) { + if (0 === $(v).text().toLowerCase().indexOf(word)) return $(v).focus(), end = !0, !1 + }, this)), end) return + } + if (new RegExp("^" + chr + "+$").test(word)) { + if (col.slice(ind + 1).each($.proxy(function(i, v) { + if ($(v).text().toLowerCase().charAt(0) === chr) return $(v).focus(), end = !0, !1 + }, this)), end) return; + if (col.slice(0, ind + 1).each($.proxy(function(i, v) { + if ($(v).text().toLowerCase().charAt(0) === chr) return $(v).focus(), end = !0, !1 + }, this)), end) return + } + }, this)).on("init.jstree", $.proxy(function() { + var s = this.settings.core.themes; + this._data.core.themes.dots = s.dots, this._data.core.themes.stripes = s.stripes, this._data.core.themes.icons = s.icons, this.set_theme(s.name || "default", s.url), this.set_theme_variant(s.variant) + }, this)).on("loading.jstree", $.proxy(function() { + this[this._data.core.themes.dots ? "show_dots" : "hide_dots"](), this[this._data.core.themes.icons ? "show_icons" : "hide_icons"](), this[this._data.core.themes.stripes ? "show_stripes" : "hide_stripes"]() + }, this)).on("blur.jstree", ".jstree-anchor", $.proxy(function(e) { + this._data.core.focused = null, $(e.currentTarget).filter(".jstree-hovered").mouseleave(), this.element.attr("tabindex", "0") + }, this)).on("focus.jstree", ".jstree-anchor", $.proxy(function(e) { + var tmp = this.get_node(e.currentTarget); + tmp && tmp.id && (this._data.core.focused = tmp.id), this.element.find(".jstree-hovered").not(e.currentTarget).mouseleave(), $(e.currentTarget).mouseenter(), this.element.attr("tabindex", "-1") + }, this)).on("focus.jstree", $.proxy(function() { + if (+new Date - was_click > 500 && !this._data.core.focused) { + was_click = 0; + var act = this.get_node(this.element.attr("aria-activedescendant"), !0); + act && act.find("> .jstree-anchor").focus() + } + }, this)).on("mouseenter.jstree", ".jstree-anchor", $.proxy(function(e) { + this.hover_node(e.currentTarget) + }, this)).on("mouseleave.jstree", ".jstree-anchor", $.proxy(function(e) { + this.dehover_node(e.currentTarget) + }, this)) + }, + unbind: function() { + this.element.off(".jstree"), $(document).off(".jstree-" + this._id) + }, + trigger: function(ev, data) { + data || (data = {}), data.instance = this, this.element.triggerHandler(ev.replace(".jstree", "") + ".jstree", data) + }, + get_container: function() { + return this.element + }, + get_container_ul: function() { + return this.element.children(".jstree-children").first() + }, + get_string: function(key) { + var a = this.settings.core.strings; + return $.isFunction(a) ? a.call(this, key) : a && a[key] ? a[key] : key + }, + _firstChild: function(dom) { + for (dom = dom ? dom.firstChild : null; null !== dom && 1 !== dom.nodeType;) dom = dom.nextSibling; + return dom + }, + _nextSibling: function(dom) { + for (dom = dom ? dom.nextSibling : null; null !== dom && 1 !== dom.nodeType;) dom = dom.nextSibling; + return dom + }, + _previousSibling: function(dom) { + for (dom = dom ? dom.previousSibling : null; null !== dom && 1 !== dom.nodeType;) dom = dom.previousSibling; + return dom + }, + get_node: function(obj, as_dom) { + obj && obj.id && (obj = obj.id); + var dom; + try { + if (this._model.data[obj]) obj = this._model.data[obj]; + else if ("string" == typeof obj && this._model.data[obj.replace(/^#/, "")]) obj = this._model.data[obj.replace(/^#/, "")]; + else if ("string" == typeof obj && (dom = $("#" + obj.replace($.jstree.idregex, "\\$&"), this.element)).length && this._model.data[dom.closest(".jstree-node").attr("id")]) obj = this._model.data[dom.closest(".jstree-node").attr("id")]; + else if ((dom = $(obj, this.element)).length && this._model.data[dom.closest(".jstree-node").attr("id")]) obj = this._model.data[dom.closest(".jstree-node").attr("id")]; + else { + if (!(dom = $(obj, this.element)).length || !dom.hasClass("jstree")) return !1; + obj = this._model.data["#"] + } + return as_dom && (obj = "#" === obj.id ? this.element : $("#" + obj.id.replace($.jstree.idregex, "\\$&"), this.element)), obj + } catch (ex) { + return !1 + } + }, + get_path: function(obj, glue, ids) { + if (!(obj = obj.parents ? obj : this.get_node(obj)) || "#" === obj.id || !obj.parents) return !1; + var i, j, p = []; + for (p.push(ids ? obj.id : obj.text), i = 0, j = obj.parents.length; i < j; i++) p.push(ids ? obj.parents[i] : this.get_text(obj.parents[i])); + return p = p.reverse().slice(1), glue ? p.join(glue) : p + }, + get_next_dom: function(obj, strict) { + var tmp; + if (obj = this.get_node(obj, !0), obj[0] === this.element[0]) { + for (tmp = this._firstChild(this.get_container_ul()[0]); tmp && 0 === tmp.offsetHeight;) tmp = this._nextSibling(tmp); + return !!tmp && $(tmp) + } + if (!obj || !obj.length) return !1; + if (strict) { + tmp = obj[0]; + do { + tmp = this._nextSibling(tmp) + } while (tmp && 0 === tmp.offsetHeight); + return !!tmp && $(tmp) + } + if (obj.hasClass("jstree-open")) { + for (tmp = this._firstChild(obj.children(".jstree-children")[0]); tmp && 0 === tmp.offsetHeight;) tmp = this._nextSibling(tmp); + if (null !== tmp) return $(tmp) + } + tmp = obj[0]; + do { + tmp = this._nextSibling(tmp) + } while (tmp && 0 === tmp.offsetHeight); + return null !== tmp ? $(tmp) : obj.parentsUntil(".jstree", ".jstree-node").nextAll(".jstree-node:visible").first() + }, + get_prev_dom: function(obj, strict) { + var tmp; + if (obj = this.get_node(obj, !0), obj[0] === this.element[0]) { + for (tmp = this.get_container_ul()[0].lastChild; tmp && 0 === tmp.offsetHeight;) tmp = this._previousSibling(tmp); + return !!tmp && $(tmp) + } + if (!obj || !obj.length) return !1; + if (strict) { + tmp = obj[0]; + do { + tmp = this._previousSibling(tmp) + } while (tmp && 0 === tmp.offsetHeight); + return !!tmp && $(tmp) + } + tmp = obj[0]; + do { + tmp = this._previousSibling(tmp) + } while (tmp && 0 === tmp.offsetHeight); + if (null !== tmp) { + for (obj = $(tmp); obj.hasClass("jstree-open");) obj = obj.children(".jstree-children").first().children(".jstree-node:visible:last"); + return obj + } + return !(!(tmp = obj[0].parentNode.parentNode) || !tmp.className || -1 === tmp.className.indexOf("jstree-node")) && $(tmp) + }, + get_parent: function(obj) { + return !(!(obj = this.get_node(obj)) || "#" === obj.id) && obj.parent + }, + get_children_dom: function(obj) { + return obj = this.get_node(obj, !0), obj[0] === this.element[0] ? this.get_container_ul().children(".jstree-node") : !(!obj || !obj.length) && obj.children(".jstree-children").children(".jstree-node") + }, + is_parent: function(obj) { + return (obj = this.get_node(obj)) && (!1 === obj.state.loaded || obj.children.length > 0) + }, + is_loaded: function(obj) { + return (obj = this.get_node(obj)) && obj.state.loaded + }, + is_loading: function(obj) { + return (obj = this.get_node(obj)) && obj.state && obj.state.loading + }, + is_open: function(obj) { + return (obj = this.get_node(obj)) && obj.state.opened + }, + is_closed: function(obj) { + return (obj = this.get_node(obj)) && this.is_parent(obj) && !obj.state.opened + }, + is_leaf: function(obj) { + return !this.is_parent(obj) + }, + load_node: function(obj, callback) { + var k, l, i, j, c; + if ($.isArray(obj)) return this._load_nodes(obj.slice(), callback), !0; + if (!(obj = this.get_node(obj))) return callback && callback.call(this, obj, !1), !1; + if (obj.state.loaded) { + for (obj.state.loaded = !1, k = 0, l = obj.children_d.length; k < l; k++) { + for (i = 0, j = obj.parents.length; i < j; i++) this._model.data[obj.parents[i]].children_d = $.vakata.array_remove_item(this._model.data[obj.parents[i]].children_d, obj.children_d[k]); + this._model.data[obj.children_d[k]].state.selected && (c = !0, this._data.core.selected = $.vakata.array_remove_item(this._data.core.selected, obj.children_d[k])), delete this._model.data[obj.children_d[k]] + } + obj.children = [], obj.children_d = [], c && this.trigger("changed", { + action: "load_node", + node: obj, + selected: this._data.core.selected + }) + } + return obj.state.failed = !1, obj.state.loading = !0, this.get_node(obj, !0).addClass("jstree-loading").attr("aria-busy", !0), this._load_node(obj, $.proxy(function(status) { + obj = this._model.data[obj.id], obj.state.loading = !1, obj.state.loaded = status, obj.state.failed = !obj.state.loaded; + var dom = this.get_node(obj, !0); + obj.state.loaded && !obj.children.length && dom && dom.length && !dom.hasClass("jstree-leaf") && dom.removeClass("jstree-closed jstree-open").addClass("jstree-leaf"), dom.removeClass("jstree-loading").attr("aria-busy", !1), this.trigger("load_node", { + node: obj, + status: status + }), callback && callback.call(this, obj, status) + }, this)), !0 + }, + _load_nodes: function(nodes, callback, is_callback) { + var i, j, r = !0, + c = function() { + this._load_nodes(nodes, callback, !0) + }, + m = this._model.data, + tmp = []; + for (i = 0, j = nodes.length; i < j; i++) !m[nodes[i]] || (m[nodes[i]].state.loaded || m[nodes[i]].state.failed) && is_callback || (this.is_loading(nodes[i]) || this.load_node(nodes[i], c), r = !1); + if (r) { + for (i = 0, j = nodes.length; i < j; i++) m[nodes[i]] && m[nodes[i]].state.loaded && tmp.push(nodes[i]); + callback && !callback.done && (callback.call(this, tmp), callback.done = !0) + } + }, + load_all: function(obj, callback) { + if (obj || (obj = "#"), !(obj = this.get_node(obj))) return !1; + var i, j, to_load = [], + m = this._model.data, + c = m[obj.id].children_d; + for (obj.state && !obj.state.loaded && to_load.push(obj.id), i = 0, j = c.length; i < j; i++) m[c[i]] && m[c[i]].state && !m[c[i]].state.loaded && to_load.push(c[i]); + to_load.length ? this._load_nodes(to_load, function() { + this.load_all(obj, callback) + }) : (callback && callback.call(this, obj), this.trigger("load_all", { + node: obj + })) + }, + _load_node: function(obj, callback) { + var t, s = this.settings.core.data; + return s ? $.isFunction(s) ? s.call(this, obj, $.proxy(function(d) { + !1 === d && callback.call(this, !1), this["string" == typeof d ? "_append_html_data" : "_append_json_data"](obj, "string" == typeof d ? $($.parseHTML(d)).filter(function() { + return 3 !== this.nodeType + }) : d, function(status) { + callback.call(this, status) + }) + }, this)) : "object" == typeof s ? s.url ? (s = $.extend(!0, {}, s), $.isFunction(s.url) && (s.url = s.url.call(this, obj)), $.isFunction(s.data) && (s.data = s.data.call(this, obj)), $.ajax(s).done($.proxy(function(d, t, x) { + var type = x.getResponseHeader("Content-Type"); + return type && -1 !== type.indexOf("json") || "object" == typeof d ? this._append_json_data(obj, d, function(status) { + callback.call(this, status) + }) : type && -1 !== type.indexOf("html") || "string" == typeof d ? this._append_html_data(obj, $($.parseHTML(d)).filter(function() { + return 3 !== this.nodeType + }), function(status) { + callback.call(this, status) + }) : (this._data.core.last_error = { + error: "ajax", + plugin: "core", + id: "core_04", + reason: "Could not load node", + data: JSON.stringify({ + id: obj.id, + xhr: x + }) + }, this.settings.core.error.call(this, this._data.core.last_error), callback.call(this, !1)) + }, this)).fail($.proxy(function(f) { + callback.call(this, !1), this._data.core.last_error = { + error: "ajax", + plugin: "core", + id: "core_04", + reason: "Could not load node", + data: JSON.stringify({ + id: obj.id, + xhr: f + }) + }, this.settings.core.error.call(this, this._data.core.last_error) + }, this))) : (t = $.isArray(s) || $.isPlainObject(s) ? JSON.parse(JSON.stringify(s)) : s, "#" === obj.id ? this._append_json_data(obj, t, function(status) { + callback.call(this, status) + }) : (this._data.core.last_error = { + error: "nodata", + plugin: "core", + id: "core_05", + reason: "Could not load node", + data: JSON.stringify({ + id: obj.id + }) + }, this.settings.core.error.call(this, this._data.core.last_error), callback.call(this, !1))) : "string" == typeof s ? "#" === obj.id ? this._append_html_data(obj, $($.parseHTML(s)).filter(function() { + return 3 !== this.nodeType + }), function(status) { + callback.call(this, status) + }) : (this._data.core.last_error = { + error: "nodata", + plugin: "core", + id: "core_06", + reason: "Could not load node", + data: JSON.stringify({ + id: obj.id + }) + }, this.settings.core.error.call(this, this._data.core.last_error), callback.call(this, !1)) : callback.call(this, !1) : "#" === obj.id ? this._append_html_data(obj, this._data.core.original_container_html.clone(!0), function(status) { + callback.call(this, status) + }) : callback.call(this, !1) + }, + _node_changed: function(obj) { + (obj = this.get_node(obj)) && this._model.changed.push(obj.id) + }, + _append_html_data: function(dom, data, cb) { + dom = this.get_node(dom), dom.children = [], dom.children_d = []; + var tmp, i, j, dat = data.is("ul") ? data.children() : data, + par = dom.id, + chd = [], + dpc = [], + m = this._model.data, + p = m[par], + s = this._data.core.selected.length; + for (dat.each($.proxy(function(i, v) { + (tmp = this._parse_model_from_html($(v), par, p.parents.concat())) && (chd.push(tmp), dpc.push(tmp), m[tmp].children_d.length && (dpc = dpc.concat(m[tmp].children_d))) + }, this)), p.children = chd, p.children_d = dpc, i = 0, j = p.parents.length; i < j; i++) m[p.parents[i]].children_d = m[p.parents[i]].children_d.concat(dpc); + this.trigger("model", { + nodes: dpc, + parent: par + }), "#" !== par ? (this._node_changed(par), this.redraw()) : (this.get_container_ul().children(".jstree-initial-node").remove(), this.redraw(!0)), this._data.core.selected.length !== s && this.trigger("changed", { + action: "model", + selected: this._data.core.selected + }), cb.call(this, !0) + }, + _append_json_data: function(dom, data, cb, force_processing) { + if (null !== this.element) { + dom = this.get_node(dom), dom.children = [], dom.children_d = [], data.d && "string" == typeof(data = data.d) && (data = JSON.parse(data)), $.isArray(data) || (data = [data]); + var w = null, + args = { + df: this._model.default_state, + dat: data, + par: dom.id, + m: this._model.data, + t_id: this._id, + t_cnt: this._cnt, + sel: this._data.core.selected + }, + func = function(data, undefined) { + data.data && (data = data.data); + var tmp, i, j, rslt, dat = data.dat, + par = data.par, + chd = [], + dpc = [], + add = [], + df = data.df, + t_id = data.t_id, + t_cnt = data.t_cnt, + m = data.m, + p = m[par], + sel = data.sel, + parse_flat = function(d, p, ps) { + ps = ps ? ps.concat() : [], p && ps.unshift(p); + var i, j, c, e, tid = d.id.toString(), + tmp = { + id: tid, + text: d.text || "", + icon: d.icon === undefined || d.icon, + parent: p, + parents: ps, + children: d.children || [], + children_d: d.children_d || [], + data: d.data, + state: {}, + li_attr: { + id: !1 + }, + a_attr: { + href: "#" + }, + original: !1 + }; + for (i in df) df.hasOwnProperty(i) && (tmp.state[i] = df[i]); + if (d && d.data && d.data.jstree && d.data.jstree.icon && (tmp.icon = d.data.jstree.icon), tmp.icon !== undefined && null !== tmp.icon && "" !== tmp.icon || (tmp.icon = !0), d && d.data && (tmp.data = d.data, d.data.jstree)) + for (i in d.data.jstree) d.data.jstree.hasOwnProperty(i) && (tmp.state[i] = d.data.jstree[i]); + if (d && "object" == typeof d.state) + for (i in d.state) d.state.hasOwnProperty(i) && (tmp.state[i] = d.state[i]); + if (d && "object" == typeof d.li_attr) + for (i in d.li_attr) d.li_attr.hasOwnProperty(i) && (tmp.li_attr[i] = d.li_attr[i]); + if (tmp.li_attr.id || (tmp.li_attr.id = tid), d && "object" == typeof d.a_attr) + for (i in d.a_attr) d.a_attr.hasOwnProperty(i) && (tmp.a_attr[i] = d.a_attr[i]); + for (d && d.children && !0 === d.children && (tmp.state.loaded = !1, tmp.children = [], tmp.children_d = []), m[tmp.id] = tmp, i = 0, j = tmp.children.length; i < j; i++) c = parse_flat(m[tmp.children[i]], tmp.id, ps), e = m[c], tmp.children_d.push(c), e.children_d.length && (tmp.children_d = tmp.children_d.concat(e.children_d)); + return delete d.data, delete d.children, m[tmp.id].original = d, tmp.state.selected && add.push(tmp.id), tmp.id + }, + parse_nest = function(d, p, ps) { + ps = ps ? ps.concat() : [], p && ps.unshift(p); + var i, j, c, e, tmp, tid = !1; + do { + tid = "j" + t_id + "_" + ++t_cnt + } while (m[tid]); + tmp = { + id: !1, + text: "string" == typeof d ? d : "", + icon: "object" != typeof d || d.icon === undefined || d.icon, + parent: p, + parents: ps, + children: [], + children_d: [], + data: null, + state: {}, + li_attr: { + id: !1 + }, + a_attr: { + href: "#" + }, + original: !1 + }; + for (i in df) df.hasOwnProperty(i) && (tmp.state[i] = df[i]); + if (d && d.id && (tmp.id = d.id.toString()), d && d.text && (tmp.text = d.text), d && d.data && d.data.jstree && d.data.jstree.icon && (tmp.icon = d.data.jstree.icon), tmp.icon !== undefined && null !== tmp.icon && "" !== tmp.icon || (tmp.icon = !0), d && d.data && (tmp.data = d.data, d.data.jstree)) + for (i in d.data.jstree) d.data.jstree.hasOwnProperty(i) && (tmp.state[i] = d.data.jstree[i]); + if (d && "object" == typeof d.state) + for (i in d.state) d.state.hasOwnProperty(i) && (tmp.state[i] = d.state[i]); + if (d && "object" == typeof d.li_attr) + for (i in d.li_attr) d.li_attr.hasOwnProperty(i) && (tmp.li_attr[i] = d.li_attr[i]); + if (tmp.li_attr.id && !tmp.id && (tmp.id = tmp.li_attr.id.toString()), tmp.id || (tmp.id = tid), tmp.li_attr.id || (tmp.li_attr.id = tmp.id), d && "object" == typeof d.a_attr) + for (i in d.a_attr) d.a_attr.hasOwnProperty(i) && (tmp.a_attr[i] = d.a_attr[i]); + if (d && d.children && d.children.length) { + for (i = 0, j = d.children.length; i < j; i++) c = parse_nest(d.children[i], tmp.id, ps), e = m[c], tmp.children.push(c), e.children_d.length && (tmp.children_d = tmp.children_d.concat(e.children_d)); + tmp.children_d = tmp.children_d.concat(tmp.children) + } + return d && d.children && !0 === d.children && (tmp.state.loaded = !1, tmp.children = [], tmp.children_d = []), delete d.data, delete d.children, tmp.original = d, m[tmp.id] = tmp, tmp.state.selected && add.push(tmp.id), tmp.id + }; + if (dat.length && dat[0].id !== undefined && dat[0].parent !== undefined) { + for (i = 0, j = dat.length; i < j; i++) dat[i].children || (dat[i].children = []), m[dat[i].id.toString()] = dat[i]; + for (i = 0, j = dat.length; i < j; i++) m[dat[i].parent.toString()].children.push(dat[i].id.toString()), p.children_d.push(dat[i].id.toString()); + for (i = 0, j = p.children.length; i < j; i++) tmp = parse_flat(m[p.children[i]], par, p.parents.concat()), dpc.push(tmp), m[tmp].children_d.length && (dpc = dpc.concat(m[tmp].children_d)); + for (i = 0, j = p.parents.length; i < j; i++) m[p.parents[i]].children_d = m[p.parents[i]].children_d.concat(dpc); + rslt = { + cnt: t_cnt, + mod: m, + sel: sel, + par: par, + dpc: dpc, + add: add + } + } else { + for (i = 0, j = dat.length; i < j; i++)(tmp = parse_nest(dat[i], par, p.parents.concat())) && (chd.push(tmp), dpc.push(tmp), m[tmp].children_d.length && (dpc = dpc.concat(m[tmp].children_d))); + for (p.children = chd, p.children_d = dpc, i = 0, j = p.parents.length; i < j; i++) m[p.parents[i]].children_d = m[p.parents[i]].children_d.concat(dpc); + rslt = { + cnt: t_cnt, + mod: m, + sel: sel, + par: par, + dpc: dpc, + add: add + } + } + if ("undefined" != typeof window && void 0 !== window.document) return rslt; + postMessage(rslt) + }, + rslt = function(rslt, worker) { + if (null !== this.element) { + if (this._cnt = rslt.cnt, this._model.data = rslt.mod, worker) { + var i, j, a = rslt.add, + r = rslt.sel, + s = this._data.core.selected.slice(), + m = this._model.data; + if (r.length !== s.length || $.vakata.array_unique(r.concat(s)).length !== r.length) { + for (i = 0, j = r.length; i < j; i++) - 1 === $.inArray(r[i], a) && -1 === $.inArray(r[i], s) && (m[r[i]].state.selected = !1); + for (i = 0, j = s.length; i < j; i++) - 1 === $.inArray(s[i], r) && (m[s[i]].state.selected = !0) + } + } + rslt.add.length && (this._data.core.selected = this._data.core.selected.concat(rslt.add)), this.trigger("model", { + nodes: rslt.dpc, + parent: rslt.par + }), "#" !== rslt.par ? (this._node_changed(rslt.par), this.redraw()) : this.redraw(!0), rslt.add.length && this.trigger("changed", { + action: "model", + selected: this._data.core.selected + }), cb.call(this, !0) + } + }; + if (this.settings.core.worker && window.Blob && window.URL && window.Worker) try { + null === this._wrk && (this._wrk = window.URL.createObjectURL(new window.Blob(["self.onmessage = " + func.toString()], { + type: "text/javascript" + }))), !this._data.core.working || force_processing ? (this._data.core.working = !0, w = new window.Worker(this._wrk), w.onmessage = $.proxy(function(e) { + rslt.call(this, e.data, !0); + try { + w.terminate(), w = null + } catch (ignore) {} + this._data.core.worker_queue.length ? this._append_json_data.apply(this, this._data.core.worker_queue.shift()) : this._data.core.working = !1 + }, this), args.par ? w.postMessage(args) : this._data.core.worker_queue.length ? this._append_json_data.apply(this, this._data.core.worker_queue.shift()) : this._data.core.working = !1) : this._data.core.worker_queue.push([dom, data, cb, !0]) + } catch (e) { + rslt.call(this, func(args), !1), this._data.core.worker_queue.length ? this._append_json_data.apply(this, this._data.core.worker_queue.shift()) : this._data.core.working = !1 + } else rslt.call(this, func(args), !1) + } + }, + _parse_model_from_html: function(d, p, ps) { + ps = ps ? [].concat(ps) : [], p && ps.unshift(p); + var c, e, i, tmp, tid, m = this._model.data, + data = { + id: !1, + text: !1, + icon: !0, + parent: p, + parents: ps, + children: [], + children_d: [], + data: null, + state: {}, + li_attr: { + id: !1 + }, + a_attr: { + href: "#" + }, + original: !1 + }; + for (i in this._model.default_state) this._model.default_state.hasOwnProperty(i) && (data.state[i] = this._model.default_state[i]); + if (tmp = $.vakata.attributes(d, !0), $.each(tmp, function(i, v) { + if (v = $.trim(v), !v.length) return !0; + data.li_attr[i] = v, "id" === i && (data.id = v.toString()) + }), tmp = d.children("a").first(), tmp.length && (tmp = $.vakata.attributes(tmp, !0), $.each(tmp, function(i, v) { + v = $.trim(v), v.length && (data.a_attr[i] = v) + })), tmp = d.children("a").first().length ? d.children("a").first().clone() : d.clone(), tmp.children("ins, i, ul").remove(), tmp = tmp.html(), tmp = $("
      ").html(tmp), data.text = this.settings.core.force_text ? tmp.text() : tmp.html(), tmp = d.data(), data.data = tmp ? $.extend(!0, {}, tmp) : null, data.state.opened = d.hasClass("jstree-open"), data.state.selected = d.children("a").hasClass("jstree-clicked"), data.state.disabled = d.children("a").hasClass("jstree-disabled"), data.data && data.data.jstree) + for (i in data.data.jstree) data.data.jstree.hasOwnProperty(i) && (data.state[i] = data.data.jstree[i]); + tmp = d.children("a").children(".jstree-themeicon"), tmp.length && (data.icon = !tmp.hasClass("jstree-themeicon-hidden") && tmp.attr("rel")), data.state.icon !== undefined && (data.icon = data.state.icon), data.icon !== undefined && null !== data.icon && "" !== data.icon || (data.icon = !0), tmp = d.children("ul").children("li"); + do { + tid = "j" + this._id + "_" + ++this._cnt + } while (m[tid]); + return data.id = data.li_attr.id ? data.li_attr.id.toString() : tid, tmp.length ? (tmp.each($.proxy(function(i, v) { + c = this._parse_model_from_html($(v), data.id, ps), e = this._model.data[c], data.children.push(c), e.children_d.length && (data.children_d = data.children_d.concat(e.children_d)) + }, this)), data.children_d = data.children_d.concat(data.children)) : d.hasClass("jstree-closed") && (data.state.loaded = !1), data.li_attr.class && (data.li_attr.class = data.li_attr.class.replace("jstree-closed", "").replace("jstree-open", "")), data.a_attr.class && (data.a_attr.class = data.a_attr.class.replace("jstree-clicked", "").replace("jstree-disabled", "")), m[data.id] = data, data.state.selected && this._data.core.selected.push(data.id), data.id + }, + _parse_model_from_flat_json: function(d, p, ps) { + ps = ps ? ps.concat() : [], p && ps.unshift(p); + var i, j, c, e, tid = d.id.toString(), + m = this._model.data, + df = this._model.default_state, + tmp = { + id: tid, + text: d.text || "", + icon: d.icon === undefined || d.icon, + parent: p, + parents: ps, + children: d.children || [], + children_d: d.children_d || [], + data: d.data, + state: {}, + li_attr: { + id: !1 + }, + a_attr: { + href: "#" + }, + original: !1 + }; + for (i in df) df.hasOwnProperty(i) && (tmp.state[i] = df[i]); + if (d && d.data && d.data.jstree && d.data.jstree.icon && (tmp.icon = d.data.jstree.icon), tmp.icon !== undefined && null !== tmp.icon && "" !== tmp.icon || (tmp.icon = !0), d && d.data && (tmp.data = d.data, d.data.jstree)) + for (i in d.data.jstree) d.data.jstree.hasOwnProperty(i) && (tmp.state[i] = d.data.jstree[i]); + if (d && "object" == typeof d.state) + for (i in d.state) d.state.hasOwnProperty(i) && (tmp.state[i] = d.state[i]); + if (d && "object" == typeof d.li_attr) + for (i in d.li_attr) d.li_attr.hasOwnProperty(i) && (tmp.li_attr[i] = d.li_attr[i]); + if (tmp.li_attr.id || (tmp.li_attr.id = tid), d && "object" == typeof d.a_attr) + for (i in d.a_attr) d.a_attr.hasOwnProperty(i) && (tmp.a_attr[i] = d.a_attr[i]); + for (d && d.children && !0 === d.children && (tmp.state.loaded = !1, tmp.children = [], tmp.children_d = []), m[tmp.id] = tmp, i = 0, j = tmp.children.length; i < j; i++) c = this._parse_model_from_flat_json(m[tmp.children[i]], tmp.id, ps), e = m[c], tmp.children_d.push(c), e.children_d.length && (tmp.children_d = tmp.children_d.concat(e.children_d)); + return delete d.data, delete d.children, m[tmp.id].original = d, tmp.state.selected && this._data.core.selected.push(tmp.id), tmp.id + }, + _parse_model_from_json: function(d, p, ps) { + ps = ps ? ps.concat() : [], p && ps.unshift(p); + var i, j, c, e, tmp, tid = !1, + m = this._model.data, + df = this._model.default_state; + do { + tid = "j" + this._id + "_" + ++this._cnt + } while (m[tid]); + tmp = { + id: !1, + text: "string" == typeof d ? d : "", + icon: "object" != typeof d || d.icon === undefined || d.icon, + parent: p, + parents: ps, + children: [], + children_d: [], + data: null, + state: {}, + li_attr: { + id: !1 + }, + a_attr: { + href: "#" + }, + original: !1 + }; + for (i in df) df.hasOwnProperty(i) && (tmp.state[i] = df[i]); + if (d && d.id && (tmp.id = d.id.toString()), d && d.text && (tmp.text = d.text), d && d.data && d.data.jstree && d.data.jstree.icon && (tmp.icon = d.data.jstree.icon), tmp.icon !== undefined && null !== tmp.icon && "" !== tmp.icon || (tmp.icon = !0), d && d.data && (tmp.data = d.data, d.data.jstree)) + for (i in d.data.jstree) d.data.jstree.hasOwnProperty(i) && (tmp.state[i] = d.data.jstree[i]); + if (d && "object" == typeof d.state) + for (i in d.state) d.state.hasOwnProperty(i) && (tmp.state[i] = d.state[i]); + if (d && "object" == typeof d.li_attr) + for (i in d.li_attr) d.li_attr.hasOwnProperty(i) && (tmp.li_attr[i] = d.li_attr[i]); + if (tmp.li_attr.id && !tmp.id && (tmp.id = tmp.li_attr.id.toString()), tmp.id || (tmp.id = tid), tmp.li_attr.id || (tmp.li_attr.id = tmp.id), + d && "object" == typeof d.a_attr) + for (i in d.a_attr) d.a_attr.hasOwnProperty(i) && (tmp.a_attr[i] = d.a_attr[i]); + if (d && d.children && d.children.length) { + for (i = 0, j = d.children.length; i < j; i++) c = this._parse_model_from_json(d.children[i], tmp.id, ps), e = m[c], tmp.children.push(c), e.children_d.length && (tmp.children_d = tmp.children_d.concat(e.children_d)); + tmp.children_d = tmp.children_d.concat(tmp.children) + } + return d && d.children && !0 === d.children && (tmp.state.loaded = !1, tmp.children = [], tmp.children_d = []), delete d.data, delete d.children, tmp.original = d, m[tmp.id] = tmp, tmp.state.selected && this._data.core.selected.push(tmp.id), tmp.id + }, + _redraw: function() { + var tmp, i, j, nodes = this._model.force_full_redraw ? this._model.data["#"].children.concat([]) : this._model.changed.concat([]), + f = document.createElement("UL"), + fe = this._data.core.focused; + for (i = 0, j = nodes.length; i < j; i++)(tmp = this.redraw_node(nodes[i], !0, this._model.force_full_redraw)) && this._model.force_full_redraw && f.appendChild(tmp); + this._model.force_full_redraw && (f.className = this.get_container_ul()[0].className, f.setAttribute("role", "group"), this.element.empty().append(f)), null !== fe && (tmp = this.get_node(fe, !0), tmp && tmp.length && tmp.children(".jstree-anchor")[0] !== document.activeElement ? tmp.children(".jstree-anchor").focus() : this._data.core.focused = null), this._model.force_full_redraw = !1, this._model.changed = [], this.trigger("redraw", { + nodes: nodes + }) + }, + redraw: function(full) { + full && (this._model.force_full_redraw = !0), this._redraw() + }, + draw_children: function(node) { + var obj = this.get_node(node), + i = !1, + j = !1, + k = !1, + d = document; + if (!obj) return !1; + if ("#" === obj.id) return this.redraw(!0); + if (!(node = this.get_node(node, !0)) || !node.length) return !1; + if (node.children(".jstree-children").remove(), node = node[0], obj.children.length && obj.state.loaded) { + for (k = d.createElement("UL"), k.setAttribute("role", "group"), k.className = "jstree-children", i = 0, j = obj.children.length; i < j; i++) k.appendChild(this.redraw_node(obj.children[i], !0, !0)); + node.appendChild(k) + } + }, + redraw_node: function(node, deep, is_callback, force_render) { + var obj = this.get_node(node), + par = !1, + ind = !1, + old = !1, + i = !1, + j = !1, + k = !1, + c = "", + d = document, + m = this._model.data, + f = !1, + tmp = null, + t = 0, + l = 0; + if (!obj) return !1; + if ("#" === obj.id) return this.redraw(!0); + if (deep = deep || 0 === obj.children.length, node = document.querySelector ? this.element[0].querySelector("#" + (-1 !== "0123456789".indexOf(obj.id[0]) ? "\\3" + obj.id[0] + " " + obj.id.substr(1).replace($.jstree.idregex, "\\$&") : obj.id.replace($.jstree.idregex, "\\$&"))) : document.getElementById(obj.id)) node = $(node), is_callback || (par = node.parent().parent()[0], par === this.element[0] && (par = null), ind = node.index()), deep || !obj.children.length || node.children(".jstree-children").length || (deep = !0), deep || (old = node.children(".jstree-children")[0]), f = node.children(".jstree-anchor")[0] === document.activeElement, node.remove(); + else if (deep = !0, !is_callback) { + if (!(null === (par = "#" !== obj.parent ? $("#" + obj.parent.replace($.jstree.idregex, "\\$&"), this.element)[0] : null) || par && m[obj.parent].state.opened)) return !1; + ind = $.inArray(obj.id, null === par ? m["#"].children : m[obj.parent].children) + } + node = _node.cloneNode(!0), c = "jstree-node "; + for (i in obj.li_attr) + if (obj.li_attr.hasOwnProperty(i)) { + if ("id" === i) continue; + "class" !== i ? node.setAttribute(i, obj.li_attr[i]) : c += obj.li_attr[i] + } obj.a_attr.id || (obj.a_attr.id = obj.id + "_anchor"), node.setAttribute("aria-selected", !!obj.state.selected), node.setAttribute("aria-level", obj.parents.length), node.setAttribute("aria-labelledby", obj.a_attr.id), obj.state.disabled && node.setAttribute("aria-disabled", !0), obj.state.loaded && !obj.children.length ? c += " jstree-leaf" : (c += obj.state.opened && obj.state.loaded ? " jstree-open" : " jstree-closed", node.setAttribute("aria-expanded", obj.state.opened && obj.state.loaded)), null !== obj.parent && m[obj.parent].children[m[obj.parent].children.length - 1] === obj.id && (c += " jstree-last"), node.id = obj.id, node.className = c, c = (obj.state.selected ? " jstree-clicked" : "") + (obj.state.disabled ? " jstree-disabled" : ""); + for (j in obj.a_attr) + if (obj.a_attr.hasOwnProperty(j)) { + if ("href" === j && "#" === obj.a_attr[j]) continue; + "class" !== j ? node.childNodes[1].setAttribute(j, obj.a_attr[j]) : c += " " + obj.a_attr[j] + } if (c.length && (node.childNodes[1].className = "jstree-anchor " + c), (obj.icon && !0 !== obj.icon || !1 === obj.icon) && (!1 === obj.icon ? node.childNodes[1].childNodes[0].className += " jstree-themeicon-hidden" : -1 === obj.icon.indexOf("/") && -1 === obj.icon.indexOf(".") ? node.childNodes[1].childNodes[0].className += " " + obj.icon + " jstree-themeicon-custom" : (node.childNodes[1].childNodes[0].style.backgroundImage = "url(" + obj.icon + ")", node.childNodes[1].childNodes[0].style.backgroundPosition = "center center", node.childNodes[1].childNodes[0].style.backgroundSize = "auto", node.childNodes[1].childNodes[0].className += " jstree-themeicon-custom")), this.settings.core.force_text ? node.childNodes[1].appendChild(d.createTextNode(obj.text)) : node.childNodes[1].innerHTML += obj.text, deep && obj.children.length && (obj.state.opened || force_render) && obj.state.loaded) { + for (k = d.createElement("UL"), k.setAttribute("role", "group"), k.className = "jstree-children", i = 0, j = obj.children.length; i < j; i++) k.appendChild(this.redraw_node(obj.children[i], deep, !0)); + node.appendChild(k) + } + if (old && node.appendChild(old), !is_callback) { + for (par || (par = this.element[0]), i = 0, j = par.childNodes.length; i < j; i++) + if (par.childNodes[i] && par.childNodes[i].className && -1 !== par.childNodes[i].className.indexOf("jstree-children")) { + tmp = par.childNodes[i]; + break + } tmp || (tmp = d.createElement("UL"), tmp.setAttribute("role", "group"), tmp.className = "jstree-children", par.appendChild(tmp)), par = tmp, ind < par.childNodes.length ? par.insertBefore(node, par.childNodes[ind]) : par.appendChild(node), f && (t = this.element[0].scrollTop, l = this.element[0].scrollLeft, node.childNodes[1].focus(), this.element[0].scrollTop = t, this.element[0].scrollLeft = l) + } + return obj.state.opened && !obj.state.loaded && (obj.state.opened = !1, setTimeout($.proxy(function() { + this.open_node(obj.id, !1, 0) + }, this), 0)), node + }, + open_node: function(obj, callback, animation) { + var t1, t2, d, t; + if ($.isArray(obj)) { + for (obj = obj.slice(), t1 = 0, t2 = obj.length; t1 < t2; t1++) this.open_node(obj[t1], callback, animation); + return !0 + } + if (!(obj = this.get_node(obj)) || "#" === obj.id) return !1; + if (animation = animation === undefined ? this.settings.core.animation : animation, !this.is_closed(obj)) return callback && callback.call(this, obj, !1), !1; + if (this.is_loaded(obj)) d = this.get_node(obj, !0), t = this, d.length && (animation && d.children(".jstree-children").length, obj.children.length && !this._firstChild(d.children(".jstree-children")[0]) && this.draw_children(obj), animation ? (this.trigger("before_open", { + node: obj + }), d.children(".jstree-children").css("display", "none").end().removeClass("jstree-closed").addClass("jstree-open").attr("aria-expanded", !0).children(".jstree-children").show(), t.trigger("after_open", { + node: obj + })) : (this.trigger("before_open", { + node: obj + }), d[0].className = d[0].className.replace("jstree-closed", "jstree-open"), d[0].setAttribute("aria-expanded", !0))), obj.state.opened = !0, callback && callback.call(this, obj, !0), d.length || this.trigger("before_open", { + node: obj + }), this.trigger("open_node", { + node: obj + }), animation && d.length || this.trigger("after_open", { + node: obj + }); + else { + if (this.is_loading(obj)) return setTimeout($.proxy(function() { + this.open_node(obj, callback, animation) + }, this), 500); + this.load_node(obj, function(o, ok) { + return ok ? this.open_node(o, callback, animation) : !!callback && callback.call(this, o, !1) + }) + } + }, + _open_to: function(obj) { + if (!(obj = this.get_node(obj)) || "#" === obj.id) return !1; + var i, j, p = obj.parents; + for (i = 0, j = p.length; i < j; i += 1) "#" !== i && this.open_node(p[i], !1, 0); + return $("#" + obj.id.replace($.jstree.idregex, "\\$&"), this.element) + }, + close_node: function(obj, animation) { + var t1, t2, t, d; + if ($.isArray(obj)) { + for (obj = obj.slice(), t1 = 0, t2 = obj.length; t1 < t2; t1++) this.close_node(obj[t1], animation); + return !0 + } + return !(!(obj = this.get_node(obj)) || "#" === obj.id) && (!this.is_closed(obj) && (animation = animation === undefined ? this.settings.core.animation : animation, t = this, d = this.get_node(obj, !0), d.length && (animation ? (d.children(".jstree-children").attr("style", "display:block !important").end().removeClass("jstree-open").addClass("jstree-closed").attr("aria-expanded", !1).children(".jstree-children").hide(), d.children(".jstree-children").remove(), t.trigger("after_close", { + node: obj + })) : (d[0].className = d[0].className.replace("jstree-open", "jstree-closed"), d.attr("aria-expanded", !1).children(".jstree-children").remove())), obj.state.opened = !1, this.trigger("close_node", { + node: obj + }), void(animation && d.length || this.trigger("after_close", { + node: obj + })))) + }, + toggle_node: function(obj) { + var t1, t2; + if ($.isArray(obj)) { + for (obj = obj.slice(), t1 = 0, t2 = obj.length; t1 < t2; t1++) this.toggle_node(obj[t1]); + return !0 + } + return this.is_closed(obj) ? this.open_node(obj) : this.is_open(obj) ? this.close_node(obj) : void 0 + }, + open_all: function(obj, animation, original_obj) { + if (obj || (obj = "#"), !(obj = this.get_node(obj))) return !1; + var i, j, _this, dom = "#" === obj.id ? this.get_container_ul() : this.get_node(obj, !0); + if (!dom.length) { + for (i = 0, j = obj.children_d.length; i < j; i++) this.is_closed(this._model.data[obj.children_d[i]]) && (this._model.data[obj.children_d[i]].state.opened = !0); + return this.trigger("open_all", { + node: obj + }) + } + original_obj = original_obj || dom, _this = this, dom = this.is_closed(obj) ? dom.find(".jstree-closed").addBack() : dom.find(".jstree-closed"), dom.each(function() { + _this.open_node(this, function(node, status) { + status && this.is_parent(node) && this.open_all(node, animation, original_obj) + }, animation || 0) + }), 0 === original_obj.find(".jstree-closed").length && this.trigger("open_all", { + node: this.get_node(original_obj) + }) + }, + close_all: function(obj, animation) { + if (obj || (obj = "#"), !(obj = this.get_node(obj))) return !1; + var i, j, dom = "#" === obj.id ? this.get_container_ul() : this.get_node(obj, !0), + _this = this; + if (!dom.length) { + for (i = 0, j = obj.children_d.length; i < j; i++) this._model.data[obj.children_d[i]].state.opened = !1; + return this.trigger("close_all", { + node: obj + }) + } + dom = this.is_open(obj) ? dom.find(".jstree-open").addBack() : dom.find(".jstree-open"), $(dom.get().reverse()).each(function() { + _this.close_node(this, animation || 0) + }), this.trigger("close_all", { + node: obj + }) + }, + is_disabled: function(obj) { + return (obj = this.get_node(obj)) && obj.state && obj.state.disabled + }, + enable_node: function(obj) { + var t1, t2; + if ($.isArray(obj)) { + for (obj = obj.slice(), t1 = 0, t2 = obj.length; t1 < t2; t1++) this.enable_node(obj[t1]); + return !0 + } + if (!(obj = this.get_node(obj)) || "#" === obj.id) return !1; + obj.state.disabled = !1, this.get_node(obj, !0).children(".jstree-anchor").removeClass("jstree-disabled").attr("aria-disabled", !1), this.trigger("enable_node", { + node: obj + }) + }, + disable_node: function(obj) { + var t1, t2; + if ($.isArray(obj)) { + for (obj = obj.slice(), t1 = 0, t2 = obj.length; t1 < t2; t1++) this.disable_node(obj[t1]); + return !0 + } + if (!(obj = this.get_node(obj)) || "#" === obj.id) return !1; + obj.state.disabled = !0, this.get_node(obj, !0).children(".jstree-anchor").addClass("jstree-disabled").attr("aria-disabled", !0), this.trigger("disable_node", { + node: obj + }) + }, + activate_node: function(obj, e) { + if (this.is_disabled(obj)) return !1; + if (this._data.core.last_clicked = this._data.core.last_clicked && this._data.core.last_clicked.id !== undefined ? this.get_node(this._data.core.last_clicked.id) : null, this._data.core.last_clicked && !this._data.core.last_clicked.state.selected && (this._data.core.last_clicked = null), !this._data.core.last_clicked && this._data.core.selected.length && (this._data.core.last_clicked = this.get_node(this._data.core.selected[this._data.core.selected.length - 1])), this.settings.core.multiple && (e.metaKey || e.ctrlKey || e.shiftKey) && (!e.shiftKey || this._data.core.last_clicked && this.get_parent(obj) && this.get_parent(obj) === this._data.core.last_clicked.parent)) + if (e.shiftKey) { + var i, j, o = this.get_node(obj).id, + l = this._data.core.last_clicked.id, + p = this.get_node(this._data.core.last_clicked.parent).children, + c = !1; + for (i = 0, j = p.length; i < j; i += 1) p[i] === o && (c = !c), p[i] === l && (c = !c), this.is_disabled(p[i]) || !c && p[i] !== o && p[i] !== l ? this.deselect_node(p[i], !0, e) : this.select_node(p[i], !0, !1, e); + this.trigger("changed", { + action: "select_node", + node: this.get_node(obj), + selected: this._data.core.selected, + event: e + }) + } else this.is_selected(obj) ? this.deselect_node(obj, !1, e) : this.select_node(obj, !1, !1, e); + else !this.settings.core.multiple && (e.metaKey || e.ctrlKey || e.shiftKey) && this.is_selected(obj) ? this.deselect_node(obj, !1, e) : (this.deselect_all(!0), this.select_node(obj, !1, !1, e), this._data.core.last_clicked = this.get_node(obj)); + this.trigger("activate_node", { + node: this.get_node(obj) + }) + }, + hover_node: function(obj) { + if (!(obj = this.get_node(obj, !0)) || !obj.length || obj.children(".jstree-hovered").length) return !1; + var o = this.element.find(".jstree-hovered"), + t = this.element; + o && o.length && this.dehover_node(o), obj.children(".jstree-anchor").addClass("jstree-hovered"), this.trigger("hover_node", { + node: this.get_node(obj) + }), setTimeout(function() { + t.attr("aria-activedescendant", obj[0].id) + }, 0) + }, + dehover_node: function(obj) { + if (!(obj = this.get_node(obj, !0)) || !obj.length || !obj.children(".jstree-hovered").length) return !1; + obj.children(".jstree-anchor").removeClass("jstree-hovered"), this.trigger("dehover_node", { + node: this.get_node(obj) + }) + }, + select_node: function(obj, supress_event, prevent_open, e) { + var dom, t1, t2; + if ($.isArray(obj)) { + for (obj = obj.slice(), t1 = 0, t2 = obj.length; t1 < t2; t1++) this.select_node(obj[t1], supress_event, prevent_open, e); + return !0 + } + if (!(obj = this.get_node(obj)) || "#" === obj.id) return !1; + dom = this.get_node(obj, !0), obj.state.selected || (obj.state.selected = !0, this._data.core.selected.push(obj.id), prevent_open || (dom = this._open_to(obj)), dom && dom.length && dom.attr("aria-selected", !0).children(".jstree-anchor").addClass("jstree-clicked"), this.trigger("select_node", { + node: obj, + selected: this._data.core.selected, + event: e + }), supress_event || this.trigger("changed", { + action: "select_node", + node: obj, + selected: this._data.core.selected, + event: e + })) + }, + deselect_node: function(obj, supress_event, e) { + var t1, t2, dom; + if ($.isArray(obj)) { + for (obj = obj.slice(), t1 = 0, t2 = obj.length; t1 < t2; t1++) this.deselect_node(obj[t1], supress_event, e); + return !0 + } + if (!(obj = this.get_node(obj)) || "#" === obj.id) return !1; + dom = this.get_node(obj, !0), obj.state.selected && (obj.state.selected = !1, this._data.core.selected = $.vakata.array_remove_item(this._data.core.selected, obj.id), dom.length && dom.attr("aria-selected", !1).children(".jstree-anchor").removeClass("jstree-clicked"), this.trigger("deselect_node", { + node: obj, + selected: this._data.core.selected, + event: e + }), supress_event || this.trigger("changed", { + action: "deselect_node", + node: obj, + selected: this._data.core.selected, + event: e + })) + }, + select_all: function(supress_event) { + var i, j, tmp = this._data.core.selected.concat([]); + for (this._data.core.selected = this._model.data["#"].children_d.concat(), i = 0, j = this._data.core.selected.length; i < j; i++) this._model.data[this._data.core.selected[i]] && (this._model.data[this._data.core.selected[i]].state.selected = !0); + this.redraw(!0), this.trigger("select_all", { + selected: this._data.core.selected + }), supress_event || this.trigger("changed", { + action: "select_all", + selected: this._data.core.selected, + old_selection: tmp + }) + }, + deselect_all: function(supress_event) { + var i, j, tmp = this._data.core.selected.concat([]); + for (i = 0, j = this._data.core.selected.length; i < j; i++) this._model.data[this._data.core.selected[i]] && (this._model.data[this._data.core.selected[i]].state.selected = !1); + this._data.core.selected = [], this.element.find(".jstree-clicked").removeClass("jstree-clicked").parent().attr("aria-selected", !1), this.trigger("deselect_all", { + selected: this._data.core.selected, + node: tmp + }), supress_event || this.trigger("changed", { + action: "deselect_all", + selected: this._data.core.selected, + old_selection: tmp + }) + }, + is_selected: function(obj) { + return !(!(obj = this.get_node(obj)) || "#" === obj.id) && obj.state.selected + }, + get_selected: function(full) { + return full ? $.map(this._data.core.selected, $.proxy(function(i) { + return this.get_node(i) + }, this)) : this._data.core.selected.slice() + }, + get_top_selected: function(full) { + var i, j, k, l, tmp = this.get_selected(!0), + obj = {}; + for (i = 0, j = tmp.length; i < j; i++) obj[tmp[i].id] = tmp[i]; + for (i = 0, j = tmp.length; i < j; i++) + for (k = 0, l = tmp[i].children_d.length; k < l; k++) obj[tmp[i].children_d[k]] && delete obj[tmp[i].children_d[k]]; + tmp = []; + for (i in obj) obj.hasOwnProperty(i) && tmp.push(i); + return full ? $.map(tmp, $.proxy(function(i) { + return this.get_node(i) + }, this)) : tmp + }, + get_bottom_selected: function(full) { + var i, j, tmp = this.get_selected(!0), + obj = []; + for (i = 0, j = tmp.length; i < j; i++) tmp[i].children.length || obj.push(tmp[i].id); + return full ? $.map(obj, $.proxy(function(i) { + return this.get_node(i) + }, this)) : obj + }, + get_state: function() { + var i, state = { + core: { + open: [], + scroll: { + left: this.element.scrollLeft(), + top: this.element.scrollTop() + }, + selected: [] + } + }; + for (i in this._model.data) this._model.data.hasOwnProperty(i) && "#" !== i && (this._model.data[i].state.opened && state.core.open.push(i), this._model.data[i].state.selected && state.core.selected.push(i)); + return state + }, + set_state: function(state, callback) { + if (state) { + if (state.core) { + var _this, i; + if (state.core.open) return $.isArray(state.core.open) && state.core.open.length ? this._load_nodes(state.core.open, function(nodes) { + this.open_node(nodes, !1, 0), delete state.core.open, this.set_state(state, callback) + }, !0) : (delete state.core.open, this.set_state(state, callback)), !1; + if (state.core.scroll) return state.core.scroll && state.core.scroll.left !== undefined && this.element.scrollLeft(state.core.scroll.left), state.core.scroll && state.core.scroll.top !== undefined && this.element.scrollTop(state.core.scroll.top), delete state.core.scroll, this.set_state(state, callback), !1; + if (state.core.selected) return _this = this, this.deselect_all(), $.each(state.core.selected, function(i, v) { + _this.select_node(v, !1, !0) + }), delete state.core.selected, this.set_state(state, callback), !1; + for (i in state) state.hasOwnProperty(i) && "core" !== i && -1 === $.inArray(i, this.settings.plugins) && delete state[i]; + if ($.isEmptyObject(state.core)) return delete state.core, this.set_state(state, callback), !1 + } + return !$.isEmptyObject(state) || (state = null, callback && callback.call(this), this.trigger("set_state"), !1) + } + return !1 + }, + refresh: function(skip_loading, forget_state) { + this._data.core.state = !0 === forget_state ? {} : this.get_state(), forget_state && $.isFunction(forget_state) && (this._data.core.state = forget_state.call(this, this._data.core.state)), this._cnt = 0, this._model.data = { + "#": { + id: "#", + parent: null, + parents: [], + children: [], + children_d: [], + state: { + loaded: !1 + } + } + }; + var c = this.get_container_ul()[0].className; + skip_loading || (this.element.html(""), this.element.attr("aria-activedescendant", "j" + this._id + "_loading")), this.load_node("#", function(o, s) { + s && (this.get_container_ul()[0].className = c, this._firstChild(this.get_container_ul()[0]) && this.element.attr("aria-activedescendant", this._firstChild(this.get_container_ul()[0]).id), this.set_state($.extend(!0, {}, this._data.core.state), function() { + this.trigger("refresh") + })), this._data.core.state = null + }) + }, + refresh_node: function(obj) { + if (!(obj = this.get_node(obj)) || "#" === obj.id) return !1; + var opened = [], + to_load = []; + this._data.core.selected.concat([]); + to_load.push(obj.id), !0 === obj.state.opened && opened.push(obj.id), this.get_node(obj, !0).find(".jstree-open").each(function() { + opened.push(this.id) + }), this._load_nodes(to_load, $.proxy(function(nodes) { + this.open_node(opened, !1, 0), this.select_node(this._data.core.selected), this.trigger("refresh_node", { + node: obj, + nodes: nodes + }) + }, this)) + }, + set_id: function(obj, id) { + if (!(obj = this.get_node(obj)) || "#" === obj.id) return !1; + var i, j, m = this._model.data; + for (id = id.toString(), m[obj.parent].children[$.inArray(obj.id, m[obj.parent].children)] = id, i = 0, j = obj.parents.length; i < j; i++) m[obj.parents[i]].children_d[$.inArray(obj.id, m[obj.parents[i]].children_d)] = id; + for (i = 0, j = obj.children.length; i < j; i++) m[obj.children[i]].parent = id; + for (i = 0, j = obj.children_d.length; i < j; i++) m[obj.children_d[i]].parents[$.inArray(obj.id, m[obj.children_d[i]].parents)] = id; + return i = $.inArray(obj.id, this._data.core.selected), -1 !== i && (this._data.core.selected[i] = id), i = this.get_node(obj.id, !0), i && (i.attr("id", id).children(".jstree-anchor").attr("id", id + "_anchor").end().attr("aria-labelledby", id + "_anchor"), this.element.attr("aria-activedescendant") === obj.id && this.element.attr("aria-activedescendant", id)), delete m[obj.id], obj.id = id, obj.li_attr.id = id, m[id] = obj, !0 + }, + get_text: function(obj) { + return !(!(obj = this.get_node(obj)) || "#" === obj.id) && obj.text + }, + set_text: function(obj, val) { + var t1, t2; + if ($.isArray(obj)) { + for (obj = obj.slice(), t1 = 0, t2 = obj.length; t1 < t2; t1++) this.set_text(obj[t1], val); + return !0 + } + return !(!(obj = this.get_node(obj)) || "#" === obj.id) && (obj.text = val, this.get_node(obj, !0).length && this.redraw_node(obj.id), this.trigger("set_text", { + obj: obj, + text: val + }), !0) + }, + get_json: function(obj, options, flat) { + if (!(obj = this.get_node(obj || "#"))) return !1; + options && options.flat && !flat && (flat = []); + var i, j, tmp = { + id: obj.id, + text: obj.text, + icon: this.get_icon(obj), + li_attr: $.extend(!0, {}, obj.li_attr), + a_attr: $.extend(!0, {}, obj.a_attr), + state: {}, + data: (!options || !options.no_data) && $.extend(!0, {}, obj.data) + }; + if (options && options.flat ? tmp.parent = obj.parent : tmp.children = [], !options || !options.no_state) + for (i in obj.state) obj.state.hasOwnProperty(i) && (tmp.state[i] = obj.state[i]); + if (options && options.no_id && (delete tmp.id, tmp.li_attr && tmp.li_attr.id && delete tmp.li_attr.id, tmp.a_attr && tmp.a_attr.id && delete tmp.a_attr.id), options && options.flat && "#" !== obj.id && flat.push(tmp), !options || !options.no_children) + for (i = 0, j = obj.children.length; i < j; i++) options && options.flat ? this.get_json(obj.children[i], options, flat) : tmp.children.push(this.get_json(obj.children[i], options)); + return options && options.flat ? flat : "#" === obj.id ? tmp.children : tmp + }, + create_node: function(par, node, pos, callback, is_loaded) { + if (null === par && (par = "#"), !(par = this.get_node(par))) return !1; + if (pos = pos === undefined ? "last" : pos, !pos.toString().match(/^(before|after)$/) && !is_loaded && !this.is_loaded(par)) return this.load_node(par, function() { + this.create_node(par, node, pos, callback, !0) + }); + node || (node = { + text: this.get_string("New node") + }), "string" == typeof node && (node = { + text: node + }), node.text === undefined && (node.text = this.get_string("New node")); + var tmp, dpc, i, j; + switch ("#" === par.id && ("before" === pos && (pos = "first"), "after" === pos && (pos = "last")), pos) { + case "before": + tmp = this.get_node(par.parent), pos = $.inArray(par.id, tmp.children), par = tmp; + break; + case "after": + tmp = this.get_node(par.parent), pos = $.inArray(par.id, tmp.children) + 1, par = tmp; + break; + case "inside": + case "first": + pos = 0; + break; + case "last": + pos = par.children.length; + break; + default: + pos || (pos = 0) + } + if (pos > par.children.length && (pos = par.children.length), node.id || (node.id = !0), !this.check("create_node", node, par, pos)) return this.settings.core.error.call(this, this._data.core.last_error), !1; + if (!0 === node.id && delete node.id, !(node = this._parse_model_from_json(node, par.id, par.parents.concat()))) return !1; + for (tmp = this.get_node(node), dpc = [], dpc.push(node), dpc = dpc.concat(tmp.children_d), this.trigger("model", { + nodes: dpc, + parent: par.id + }), par.children_d = par.children_d.concat(dpc), i = 0, j = par.parents.length; i < j; i++) this._model.data[par.parents[i]].children_d = this._model.data[par.parents[i]].children_d.concat(dpc); + for (node = tmp, tmp = [], i = 0, j = par.children.length; i < j; i++) tmp[i >= pos ? i + 1 : i] = par.children[i]; + return tmp[pos] = node.id, par.children = tmp, this.redraw_node(par, !0), callback && callback.call(this, this.get_node(node)), this.trigger("create_node", { + node: this.get_node(node), + parent: par.id, + position: pos + }), node.id + }, + rename_node: function(obj, val) { + var t1, t2, old; + if ($.isArray(obj)) { + for (obj = obj.slice(), t1 = 0, t2 = obj.length; t1 < t2; t1++) this.rename_node(obj[t1], val); + return !0 + } + return !(!(obj = this.get_node(obj)) || "#" === obj.id) && (old = obj.text, this.check("rename_node", obj, this.get_parent(obj), val) ? (this.set_text(obj, val), this.trigger("rename_node", { + node: obj, + text: val, + old: old + }), !0) : (this.settings.core.error.call(this, this._data.core.last_error), !1)) + }, + delete_node: function(obj) { + var t1, t2, par, pos, tmp, i, j, k, l, c; + if ($.isArray(obj)) { + for (obj = obj.slice(), t1 = 0, t2 = obj.length; t1 < t2; t1++) this.delete_node(obj[t1]); + return !0 + } + if (!(obj = this.get_node(obj)) || "#" === obj.id) return !1; + if (par = this.get_node(obj.parent), pos = $.inArray(obj.id, par.children), c = !1, !this.check("delete_node", obj, par, pos)) return this.settings.core.error.call(this, this._data.core.last_error), !1; + for (-1 !== pos && (par.children = $.vakata.array_remove(par.children, pos)), tmp = obj.children_d.concat([]), tmp.push(obj.id), k = 0, l = tmp.length; k < l; k++) { + for (i = 0, j = obj.parents.length; i < j; i++) - 1 !== (pos = $.inArray(tmp[k], this._model.data[obj.parents[i]].children_d)) && (this._model.data[obj.parents[i]].children_d = $.vakata.array_remove(this._model.data[obj.parents[i]].children_d, pos)); + this._model.data[tmp[k]].state.selected && (c = !0, -1 !== (pos = $.inArray(tmp[k], this._data.core.selected)) && (this._data.core.selected = $.vakata.array_remove(this._data.core.selected, pos))) + } + for (this.trigger("delete_node", { + node: obj, + parent: par.id + }), c && this.trigger("changed", { + action: "delete_node", + node: obj, + selected: this._data.core.selected, + parent: par.id + }), k = 0, l = tmp.length; k < l; k++) delete this._model.data[tmp[k]]; + return this.redraw_node(par, !0), !0 + }, + check: function(chk, obj, par, pos, more) { + obj = obj && obj.id ? obj : this.get_node(obj), par = par && par.id ? par : this.get_node(par); + var tmp = chk.match(/^move_node|copy_node|create_node$/i) ? par : obj, + chc = this.settings.core.check_callback; + return "move_node" !== chk && "copy_node" !== chk || more && more.is_multi || obj.id !== par.id && $.inArray(obj.id, par.children) !== pos && -1 === $.inArray(par.id, obj.children_d) ? (tmp && tmp.data && (tmp = tmp.data), tmp && tmp.functions && (!1 === tmp.functions[chk] || !0 === tmp.functions[chk]) ? (!1 === tmp.functions[chk] && (this._data.core.last_error = { + error: "check", + plugin: "core", + id: "core_02", + reason: "Node data prevents function: " + chk, + data: JSON.stringify({ + chk: chk, + pos: pos, + obj: !(!obj || !obj.id) && obj.id, + par: !(!par || !par.id) && par.id + }) + }), tmp.functions[chk]) : !(!1 === chc || $.isFunction(chc) && !1 === chc.call(this, chk, obj, par, pos, more) || chc && !1 === chc[chk]) || (this._data.core.last_error = { + error: "check", + plugin: "core", + id: "core_03", + reason: "User config for core.check_callback prevents function: " + chk, + data: JSON.stringify({ + chk: chk, + pos: pos, + obj: !(!obj || !obj.id) && obj.id, + par: !(!par || !par.id) && par.id + }) + }, !1)) : (this._data.core.last_error = { + error: "check", + plugin: "core", + id: "core_01", + reason: "Moving parent inside child", + data: JSON.stringify({ + chk: chk, + pos: pos, + obj: !(!obj || !obj.id) && obj.id, + par: !(!par || !par.id) && par.id + }) + }, !1) + }, + last_error: function() { + return this._data.core.last_error + }, + move_node: function(obj, par, pos, callback, is_loaded, skip_redraw, origin) { + var t1, t2, old_par, old_pos, new_par, old_ins, is_multi, dpc, tmp, i, j, k, l, p; + if (par = this.get_node(par), pos = pos === undefined ? 0 : pos, !par) return !1; + if (!pos.toString().match(/^(before|after)$/) && !is_loaded && !this.is_loaded(par)) return this.load_node(par, function() { + this.move_node(obj, par, pos, callback, !0, !1, origin) + }); + if ($.isArray(obj)) { + if (1 !== obj.length) { + for (t1 = 0, t2 = obj.length; t1 < t2; t1++)(tmp = this.move_node(obj[t1], par, pos, callback, is_loaded, !1, origin)) && (par = tmp, pos = "after"); + return this.redraw(), !0 + } + obj = obj[0] + } + if (!(obj = obj && obj.id ? obj : this.get_node(obj)) || "#" === obj.id) return !1; + if (old_par = (obj.parent || "#").toString(), new_par = pos.toString().match(/^(before|after)$/) && "#" !== par.id ? this.get_node(par.parent) : par, old_ins = origin || (this._model.data[obj.id] ? this : $.jstree.reference(obj.id)), is_multi = !old_ins || !old_ins._id || this._id !== old_ins._id, old_pos = old_ins && old_ins._id && old_par && old_ins._model.data[old_par] && old_ins._model.data[old_par].children ? $.inArray(obj.id, old_ins._model.data[old_par].children) : -1, old_ins && old_ins._id && (obj = old_ins._model.data[obj.id]), is_multi) return !!(tmp = this.copy_node(obj, par, pos, callback, is_loaded, !1, origin)) && (old_ins && old_ins.delete_node(obj), tmp); + switch ("#" === par.id && ("before" === pos && (pos = "first"), "after" === pos && (pos = "last")), pos) { + case "before": + pos = $.inArray(par.id, new_par.children); + break; + case "after": + pos = $.inArray(par.id, new_par.children) + 1; + break; + case "inside": + case "first": + pos = 0; + break; + case "last": + pos = new_par.children.length; + break; + default: + pos || (pos = 0) + } + if (pos > new_par.children.length && (pos = new_par.children.length), !this.check("move_node", obj, new_par, pos, { + core: !0, + origin: origin, + is_multi: old_ins && old_ins._id && old_ins._id !== this._id, + is_foreign: !old_ins || !old_ins._id + })) return this.settings.core.error.call(this, this._data.core.last_error), !1; + if (obj.parent === new_par.id) { + for (dpc = new_par.children.concat(), tmp = $.inArray(obj.id, dpc), -1 !== tmp && (dpc = $.vakata.array_remove(dpc, tmp), pos > tmp && pos--), tmp = [], i = 0, j = dpc.length; i < j; i++) tmp[i >= pos ? i + 1 : i] = dpc[i]; + tmp[pos] = obj.id, new_par.children = tmp, this._node_changed(new_par.id), this.redraw("#" === new_par.id) + } else { + for (tmp = obj.children_d.concat(), tmp.push(obj.id), i = 0, j = obj.parents.length; i < j; i++) { + for (dpc = [], p = old_ins._model.data[obj.parents[i]].children_d, k = 0, l = p.length; k < l; k++) - 1 === $.inArray(p[k], tmp) && dpc.push(p[k]); + old_ins._model.data[obj.parents[i]].children_d = dpc + } + for (old_ins._model.data[old_par].children = $.vakata.array_remove_item(old_ins._model.data[old_par].children, obj.id), i = 0, j = new_par.parents.length; i < j; i++) this._model.data[new_par.parents[i]].children_d = this._model.data[new_par.parents[i]].children_d.concat(tmp); + for (dpc = [], i = 0, j = new_par.children.length; i < j; i++) dpc[i >= pos ? i + 1 : i] = new_par.children[i]; + for (dpc[pos] = obj.id, new_par.children = dpc, new_par.children_d.push(obj.id), new_par.children_d = new_par.children_d.concat(obj.children_d), obj.parent = new_par.id, tmp = new_par.parents.concat(), tmp.unshift(new_par.id), p = obj.parents.length, obj.parents = tmp, tmp = tmp.concat(), i = 0, j = obj.children_d.length; i < j; i++) this._model.data[obj.children_d[i]].parents = this._model.data[obj.children_d[i]].parents.slice(0, -1 * p), Array.prototype.push.apply(this._model.data[obj.children_d[i]].parents, tmp); + "#" !== old_par && "#" !== new_par.id || (this._model.force_full_redraw = !0), this._model.force_full_redraw || (this._node_changed(old_par), this._node_changed(new_par.id)), skip_redraw || this.redraw() + } + return callback && callback.call(this, obj, new_par, pos), this.trigger("move_node", { + node: obj, + parent: new_par.id, + position: pos, + old_parent: old_par, + old_position: old_pos, + is_multi: old_ins && old_ins._id && old_ins._id !== this._id, + is_foreign: !old_ins || !old_ins._id, + old_instance: old_ins, + new_instance: this + }), obj.id + }, + copy_node: function(obj, par, pos, callback, is_loaded, skip_redraw, origin) { + var t1, t2, dpc, tmp, i, j, node, old_par, new_par, old_ins; + if (par = this.get_node(par), pos = pos === undefined ? 0 : pos, !par) return !1; + if (!pos.toString().match(/^(before|after)$/) && !is_loaded && !this.is_loaded(par)) return this.load_node(par, function() { + this.copy_node(obj, par, pos, callback, !0, !1, origin) + }); + if ($.isArray(obj)) { + if (1 !== obj.length) { + for (t1 = 0, t2 = obj.length; t1 < t2; t1++)(tmp = this.copy_node(obj[t1], par, pos, callback, is_loaded, !0, origin)) && (par = tmp, pos = "after"); + return this.redraw(), !0 + } + obj = obj[0] + } + if (!(obj = obj && obj.id ? obj : this.get_node(obj)) || "#" === obj.id) return !1; + switch (old_par = (obj.parent || "#").toString(), new_par = pos.toString().match(/^(before|after)$/) && "#" !== par.id ? this.get_node(par.parent) : par, old_ins = origin || (this._model.data[obj.id] ? this : $.jstree.reference(obj.id)), !old_ins || !old_ins._id || this._id !== old_ins._id, old_ins && old_ins._id && (obj = old_ins._model.data[obj.id]), "#" === par.id && ("before" === pos && (pos = "first"), "after" === pos && (pos = "last")), pos) { + case "before": + pos = $.inArray(par.id, new_par.children); + break; + case "after": + pos = $.inArray(par.id, new_par.children) + 1; + break; + case "inside": + case "first": + pos = 0; + break; + case "last": + pos = new_par.children.length; + break; + default: + pos || (pos = 0) + } + if (pos > new_par.children.length && (pos = new_par.children.length), !this.check("copy_node", obj, new_par, pos, { + core: !0, + origin: origin, + is_multi: old_ins && old_ins._id && old_ins._id !== this._id, + is_foreign: !old_ins || !old_ins._id + })) return this.settings.core.error.call(this, this._data.core.last_error), !1; + if (!(node = old_ins ? old_ins.get_json(obj, { + no_id: !0, + no_data: !0, + no_state: !0 + }) : obj)) return !1; + if (!0 === node.id && delete node.id, !(node = this._parse_model_from_json(node, new_par.id, new_par.parents.concat()))) return !1; + for (tmp = this.get_node(node), obj && obj.state && !1 === obj.state.loaded && (tmp.state.loaded = !1), dpc = [], dpc.push(node), dpc = dpc.concat(tmp.children_d), this.trigger("model", { + nodes: dpc, + parent: new_par.id + }), i = 0, j = new_par.parents.length; i < j; i++) this._model.data[new_par.parents[i]].children_d = this._model.data[new_par.parents[i]].children_d.concat(dpc); + for (dpc = [], i = 0, + j = new_par.children.length; i < j; i++) dpc[i >= pos ? i + 1 : i] = new_par.children[i]; + return dpc[pos] = tmp.id, new_par.children = dpc, new_par.children_d.push(tmp.id), new_par.children_d = new_par.children_d.concat(tmp.children_d), "#" === new_par.id && (this._model.force_full_redraw = !0), this._model.force_full_redraw || this._node_changed(new_par.id), skip_redraw || this.redraw("#" === new_par.id), callback && callback.call(this, tmp, new_par, pos), this.trigger("copy_node", { + node: tmp, + original: obj, + parent: new_par.id, + position: pos, + old_parent: old_par, + old_position: old_ins && old_ins._id && old_par && old_ins._model.data[old_par] && old_ins._model.data[old_par].children ? $.inArray(obj.id, old_ins._model.data[old_par].children) : -1, + is_multi: old_ins && old_ins._id && old_ins._id !== this._id, + is_foreign: !old_ins || !old_ins._id, + old_instance: old_ins, + new_instance: this + }), tmp.id + }, + cut: function(obj) { + if (obj || (obj = this._data.core.selected.concat()), $.isArray(obj) || (obj = [obj]), !obj.length) return !1; + var o, t1, t2, tmp = []; + for (t1 = 0, t2 = obj.length; t1 < t2; t1++)(o = this.get_node(obj[t1])) && o.id && "#" !== o.id && tmp.push(o); + if (!tmp.length) return !1; + ccp_node = tmp, ccp_inst = this, ccp_mode = "move_node", this.trigger("cut", { + node: obj + }) + }, + copy: function(obj) { + if (obj || (obj = this._data.core.selected.concat()), $.isArray(obj) || (obj = [obj]), !obj.length) return !1; + var o, t1, t2, tmp = []; + for (t1 = 0, t2 = obj.length; t1 < t2; t1++)(o = this.get_node(obj[t1])) && o.id && "#" !== o.id && tmp.push(o); + if (!tmp.length) return !1; + ccp_node = tmp, ccp_inst = this, ccp_mode = "copy_node", this.trigger("copy", { + node: obj + }) + }, + get_buffer: function() { + return { + mode: ccp_mode, + node: ccp_node, + inst: ccp_inst + } + }, + can_paste: function() { + return !1 !== ccp_mode && !1 !== ccp_node + }, + paste: function(obj, pos) { + if (!((obj = this.get_node(obj)) && ccp_mode && ccp_mode.match(/^(copy_node|move_node)$/) && ccp_node)) return !1; + this[ccp_mode](ccp_node, obj, pos, !1, !1, !1, ccp_inst) && this.trigger("paste", { + parent: obj.id, + node: ccp_node, + mode: ccp_mode + }), ccp_node = !1, ccp_mode = !1, ccp_inst = !1 + }, + clear_buffer: function() { + ccp_node = !1, ccp_mode = !1, ccp_inst = !1, this.trigger("clear_buffer") + }, + edit: function(obj, default_text, callback) { + var rtl, w, a, s, t, h1, h2, fn, tmp; + return !!(obj = this.get_node(obj)) && (!1 === this.settings.core.check_callback ? (this._data.core.last_error = { + error: "check", + plugin: "core", + id: "core_07", + reason: "Could not edit node because of check_callback" + }, this.settings.core.error.call(this, this._data.core.last_error), !1) : (tmp = obj, default_text = "string" == typeof default_text ? default_text : obj.text, this.set_text(obj, ""), obj = this._open_to(obj), tmp.text = default_text, rtl = this._data.core.rtl, w = this.element.width(), a = obj.children(".jstree-anchor"), s = $(""), t = default_text, h1 = $("
      ", { + css: { + position: "absolute", + top: "-200px", + left: rtl ? "0px" : "-1000px", + visibility: "hidden" + } + }).appendTo("body"), h2 = $("", { + value: t, + class: "jstree-rename-input", + css: { + padding: "0", + border: "1px solid silver", + "box-sizing": "border-box", + display: "inline-block", + height: this._data.core.li_height + "px", + lineHeight: this._data.core.li_height + "px", + width: "150px" + }, + blur: $.proxy(function() { + var nv, i = s.children(".jstree-rename-input"), + v = i.val(), + f = this.settings.core.force_text; + "" === v && (v = t), h1.remove(), s.replaceWith(a), s.remove(), t = f ? t : $("
      ").append($.parseHTML(t)).html(), this.set_text(obj, t), nv = !!this.rename_node(obj, f ? $("
      ").text(v).text() : $("
      ").append($.parseHTML(v)).html()), nv || this.set_text(obj, t), callback && callback.call(this, tmp, nv) + }, this), + keydown: function(event) { + var key = event.which; + 27 === key && (this.value = t), 27 !== key && 13 !== key && 37 !== key && 38 !== key && 39 !== key && 40 !== key && 32 !== key || event.stopImmediatePropagation(), 27 !== key && 13 !== key || (event.preventDefault(), this.blur()) + }, + click: function(e) { + e.stopImmediatePropagation() + }, + mousedown: function(e) { + e.stopImmediatePropagation() + }, + keyup: function(event) { + h2.width(Math.min(h1.text("pW" + this.value).width(), w)) + }, + keypress: function(event) { + if (13 === event.which) return !1 + } + }), fn = { + fontFamily: a.css("fontFamily") || "", + fontSize: a.css("fontSize") || "", + fontWeight: a.css("fontWeight") || "", + fontStyle: a.css("fontStyle") || "", + fontStretch: a.css("fontStretch") || "", + fontVariant: a.css("fontVariant") || "", + letterSpacing: a.css("letterSpacing") || "", + wordSpacing: a.css("wordSpacing") || "" + }, s.attr("class", a.attr("class")).append(a.contents().clone()).append(h2), a.replaceWith(s), h1.css(fn), void h2.css(fn).width(Math.min(h1.text("pW" + h2[0].value).width(), w))[0].select())) + }, + set_theme: function(theme_name, theme_url) { + if (!theme_name) return !1; + if (!0 === theme_url) { + var dir = this.settings.core.themes.dir; + dir || (dir = $.jstree.path + "/themes"), theme_url = dir + "/" + theme_name + "/style.css" + } + theme_url && -1 === $.inArray(theme_url, themes_loaded) && ($("head").append(''), themes_loaded.push(theme_url)), this._data.core.themes.name && this.element.removeClass("jstree-" + this._data.core.themes.name), this._data.core.themes.name = theme_name, this.element.addClass("jstree-" + theme_name), this.element[this.settings.core.themes.responsive ? "addClass" : "removeClass"]("jstree-" + theme_name + "-responsive"), this.trigger("set_theme", { + theme: theme_name + }) + }, + get_theme: function() { + return this._data.core.themes.name + }, + set_theme_variant: function(variant_name) { + this._data.core.themes.variant && this.element.removeClass("jstree-" + this._data.core.themes.name + "-" + this._data.core.themes.variant), this._data.core.themes.variant = variant_name, variant_name && this.element.addClass("jstree-" + this._data.core.themes.name + "-" + this._data.core.themes.variant) + }, + get_theme_variant: function() { + return this._data.core.themes.variant + }, + show_stripes: function() { + this._data.core.themes.stripes = !0, this.get_container_ul().addClass("jstree-striped") + }, + hide_stripes: function() { + this._data.core.themes.stripes = !1, this.get_container_ul().removeClass("jstree-striped") + }, + toggle_stripes: function() { + this._data.core.themes.stripes ? this.hide_stripes() : this.show_stripes() + }, + show_dots: function() { + this._data.core.themes.dots = !0, this.get_container_ul().removeClass("jstree-no-dots") + }, + hide_dots: function() { + this._data.core.themes.dots = !1, this.get_container_ul().addClass("jstree-no-dots") + }, + toggle_dots: function() { + this._data.core.themes.dots ? this.hide_dots() : this.show_dots() + }, + show_icons: function() { + this._data.core.themes.icons = !0, this.get_container_ul().removeClass("jstree-no-icons") + }, + hide_icons: function() { + this._data.core.themes.icons = !1, this.get_container_ul().addClass("jstree-no-icons") + }, + toggle_icons: function() { + this._data.core.themes.icons ? this.hide_icons() : this.show_icons() + }, + set_icon: function(obj, icon) { + var t1, t2, dom, old; + if ($.isArray(obj)) { + for (obj = obj.slice(), t1 = 0, t2 = obj.length; t1 < t2; t1++) this.set_icon(obj[t1], icon); + return !0 + } + return !(!(obj = this.get_node(obj)) || "#" === obj.id) && (old = obj.icon, obj.icon = !0 === icon || null === icon || icon === undefined || "" === icon || icon, dom = this.get_node(obj, !0).children(".jstree-anchor").children(".jstree-themeicon"), !1 === icon ? this.hide_icon(obj) : !0 === icon || null === icon || icon === undefined || "" === icon ? (dom.removeClass("jstree-themeicon-custom " + old).css("background", "").removeAttr("rel"), !1 === old && this.show_icon(obj)) : -1 === icon.indexOf("/") && -1 === icon.indexOf(".") ? (dom.removeClass(old).css("background", ""), dom.addClass(icon + " jstree-themeicon-custom").attr("rel", icon), !1 === old && this.show_icon(obj)) : (dom.removeClass(old).css("background", ""), dom.addClass("jstree-themeicon-custom").css("background", "url('" + icon + "') center center no-repeat").attr("rel", icon), !1 === old && this.show_icon(obj)), !0) + }, + get_icon: function(obj) { + return !(!(obj = this.get_node(obj)) || "#" === obj.id) && obj.icon + }, + hide_icon: function(obj) { + var t1, t2; + if ($.isArray(obj)) { + for (obj = obj.slice(), t1 = 0, t2 = obj.length; t1 < t2; t1++) this.hide_icon(obj[t1]); + return !0 + } + return !(!(obj = this.get_node(obj)) || "#" === obj) && (obj.icon = !1, this.get_node(obj, !0).children(".jstree-anchor").children(".jstree-themeicon").addClass("jstree-themeicon-hidden"), !0) + }, + show_icon: function(obj) { + var t1, t2, dom; + if ($.isArray(obj)) { + for (obj = obj.slice(), t1 = 0, t2 = obj.length; t1 < t2; t1++) this.show_icon(obj[t1]); + return !0 + } + return !(!(obj = this.get_node(obj)) || "#" === obj) && (dom = this.get_node(obj, !0), obj.icon = !dom.length || dom.children(".jstree-anchor").children(".jstree-themeicon").attr("rel"), obj.icon || (obj.icon = !0), dom.children(".jstree-anchor").children(".jstree-themeicon").removeClass("jstree-themeicon-hidden"), !0) + } + }, $.vakata = {}, $.vakata.attributes = function(node, with_values) { + node = $(node)[0]; + var attr = with_values ? {} : []; + return node && node.attributes && $.each(node.attributes, function(i, v) { + -1 === $.inArray(v.name.toLowerCase(), ["style", "contenteditable", "hasfocus", "tabindex"]) && null !== v.value && "" !== $.trim(v.value) && (with_values ? attr[v.name] = v.value : attr.push(v.name)) + }), attr + }, $.vakata.array_unique = function(array) { + var i, l, a = [], + o = {}; + for (i = 0, l = array.length; i < l; i++) o[array[i]] === undefined && (a.push(array[i]), o[array[i]] = !0); + return a + }, $.vakata.array_remove = function(array, from, to) { + var rest = array.slice((to || from) + 1 || array.length); + return array.length = from < 0 ? array.length + from : from, array.push.apply(array, rest), array + }, $.vakata.array_remove_item = function(array, item) { + var tmp = $.inArray(item, array); + return -1 !== tmp ? $.vakata.array_remove(array, tmp) : array + }; + var _i = document.createElement("I"); + _i.className = "jstree-icon jstree-checkbox", _i.setAttribute("role", "presentation"), $.jstree.defaults.checkbox = { + visible: !0, + three_state: !0, + whole_node: !0, + keep_selected_style: !0, + cascade: "", + tie_selection: !0 + }, $.jstree.plugins.checkbox = function(options, parent) { + this.bind = function() { + parent.bind.call(this), this._data.checkbox.uto = !1, this._data.checkbox.selected = [], this.settings.checkbox.three_state && (this.settings.checkbox.cascade = "up+down+undetermined"), this.element.on("init.jstree", $.proxy(function() { + this._data.checkbox.visible = this.settings.checkbox.visible, this.settings.checkbox.keep_selected_style || this.element.addClass("jstree-checkbox-no-clicked"), this.settings.checkbox.tie_selection && this.element.addClass("jstree-checkbox-selection") + }, this)).on("loading.jstree", $.proxy(function() { + this[this._data.checkbox.visible ? "show_checkboxes" : "hide_checkboxes"]() + }, this)), -1 !== this.settings.checkbox.cascade.indexOf("undetermined") && this.element.on("changed.jstree uncheck_node.jstree check_node.jstree uncheck_all.jstree check_all.jstree move_node.jstree copy_node.jstree redraw.jstree open_node.jstree", $.proxy(function() { + this._data.checkbox.uto && clearTimeout(this._data.checkbox.uto), this._data.checkbox.uto = setTimeout($.proxy(this._undetermined, this), 50) + }, this)), this.settings.checkbox.tie_selection || this.element.on("model.jstree", $.proxy(function(e, data) { + var i, j, m = this._model.data, + dpc = (m[data.parent], data.nodes); + for (i = 0, j = dpc.length; i < j; i++) m[dpc[i]].state.checked = m[dpc[i]].original && m[dpc[i]].original.state && m[dpc[i]].original.state.checked, m[dpc[i]].state.checked && this._data.checkbox.selected.push(dpc[i]) + }, this)), -1 === this.settings.checkbox.cascade.indexOf("up") && -1 === this.settings.checkbox.cascade.indexOf("down") || this.element.on("model.jstree", $.proxy(function(e, data) { + var c, i, j, k, l, tmp, m = this._model.data, + p = m[data.parent], + dpc = data.nodes, + chd = [], + s = this.settings.checkbox.cascade, + t = this.settings.checkbox.tie_selection; + if (-1 !== s.indexOf("down")) + if (p.state[t ? "selected" : "checked"]) { + for (i = 0, j = dpc.length; i < j; i++) m[dpc[i]].state[t ? "selected" : "checked"] = !0; + this._data[t ? "core" : "checkbox"].selected = this._data[t ? "core" : "checkbox"].selected.concat(dpc) + } else + for (i = 0, j = dpc.length; i < j; i++) + if (m[dpc[i]].state[t ? "selected" : "checked"]) { + for (k = 0, l = m[dpc[i]].children_d.length; k < l; k++) m[m[dpc[i]].children_d[k]].state[t ? "selected" : "checked"] = !0; + this._data[t ? "core" : "checkbox"].selected = this._data[t ? "core" : "checkbox"].selected.concat(m[dpc[i]].children_d) + } if (-1 !== s.indexOf("up")) { + for (i = 0, j = p.children_d.length; i < j; i++) m[p.children_d[i]].children.length || chd.push(m[p.children_d[i]].parent); + for (chd = $.vakata.array_unique(chd), k = 0, l = chd.length; k < l; k++) + for (p = m[chd[k]]; p && "#" !== p.id;) { + for (c = 0, i = 0, j = p.children.length; i < j; i++) c += m[p.children[i]].state[t ? "selected" : "checked"]; + if (c !== j) break; + p.state[t ? "selected" : "checked"] = !0, this._data[t ? "core" : "checkbox"].selected.push(p.id), (tmp = this.get_node(p, !0)) && tmp.length && tmp.attr("aria-selected", !0).children(".jstree-anchor").addClass(t ? "jstree-clicked" : "jstree-checked"), p = this.get_node(p.parent) + } + } + this._data[t ? "core" : "checkbox"].selected = $.vakata.array_unique(this._data[t ? "core" : "checkbox"].selected) + }, this)).on(this.settings.checkbox.tie_selection ? "select_node.jstree" : "check_node.jstree", $.proxy(function(e, data) { + var i, j, c, tmp, obj = data.node, + m = this._model.data, + par = this.get_node(obj.parent), + dom = this.get_node(obj, !0), + s = this.settings.checkbox.cascade, + t = this.settings.checkbox.tie_selection; + if (-1 !== s.indexOf("down")) + for (this._data[t ? "core" : "checkbox"].selected = $.vakata.array_unique(this._data[t ? "core" : "checkbox"].selected.concat(obj.children_d)), i = 0, j = obj.children_d.length; i < j; i++) tmp = m[obj.children_d[i]], tmp.state[t ? "selected" : "checked"] = !0, tmp && tmp.original && tmp.original.state && tmp.original.state.undetermined && (tmp.original.state.undetermined = !1); + if (-1 !== s.indexOf("up")) + for (; par && "#" !== par.id;) { + for (c = 0, i = 0, j = par.children.length; i < j; i++) c += m[par.children[i]].state[t ? "selected" : "checked"]; + if (c !== j) break; + par.state[t ? "selected" : "checked"] = !0, this._data[t ? "core" : "checkbox"].selected.push(par.id), (tmp = this.get_node(par, !0)) && tmp.length && tmp.attr("aria-selected", !0).children(".jstree-anchor").addClass(t ? "jstree-clicked" : "jstree-checked"), par = this.get_node(par.parent) + } - 1 !== s.indexOf("down") && dom.length && dom.find(".jstree-anchor").addClass(t ? "jstree-clicked" : "jstree-checked").parent().attr("aria-selected", !0) + }, this)).on(this.settings.checkbox.tie_selection ? "deselect_all.jstree" : "uncheck_all.jstree", $.proxy(function(e, data) { + var i, j, tmp, obj = this.get_node("#"), + m = this._model.data; + for (i = 0, j = obj.children_d.length; i < j; i++)(tmp = m[obj.children_d[i]]) && tmp.original && tmp.original.state && tmp.original.state.undetermined && (tmp.original.state.undetermined = !1) + }, this)).on(this.settings.checkbox.tie_selection ? "deselect_node.jstree" : "uncheck_node.jstree", $.proxy(function(e, data) { + var i, j, tmp, obj = data.node, + dom = this.get_node(obj, !0), + s = this.settings.checkbox.cascade, + t = this.settings.checkbox.tie_selection; + if (obj && obj.original && obj.original.state && obj.original.state.undetermined && (obj.original.state.undetermined = !1), -1 !== s.indexOf("down")) + for (i = 0, j = obj.children_d.length; i < j; i++) tmp = this._model.data[obj.children_d[i]], tmp.state[t ? "selected" : "checked"] = !1, tmp && tmp.original && tmp.original.state && tmp.original.state.undetermined && (tmp.original.state.undetermined = !1); + if (-1 !== s.indexOf("up")) + for (i = 0, j = obj.parents.length; i < j; i++) tmp = this._model.data[obj.parents[i]], tmp.state[t ? "selected" : "checked"] = !1, tmp && tmp.original && tmp.original.state && tmp.original.state.undetermined && (tmp.original.state.undetermined = !1), (tmp = this.get_node(obj.parents[i], !0)) && tmp.length && tmp.attr("aria-selected", !1).children(".jstree-anchor").removeClass(t ? "jstree-clicked" : "jstree-checked"); + for (tmp = [], i = 0, j = this._data[t ? "core" : "checkbox"].selected.length; i < j; i++) - 1 !== s.indexOf("down") && -1 !== $.inArray(this._data[t ? "core" : "checkbox"].selected[i], obj.children_d) || -1 !== s.indexOf("up") && -1 !== $.inArray(this._data[t ? "core" : "checkbox"].selected[i], obj.parents) || tmp.push(this._data[t ? "core" : "checkbox"].selected[i]); + this._data[t ? "core" : "checkbox"].selected = $.vakata.array_unique(tmp), -1 !== s.indexOf("down") && dom.length && dom.find(".jstree-anchor").removeClass(t ? "jstree-clicked" : "jstree-checked").parent().attr("aria-selected", !1) + }, this)), -1 !== this.settings.checkbox.cascade.indexOf("up") && this.element.on("delete_node.jstree", $.proxy(function(e, data) { + for (var i, j, c, tmp, p = this.get_node(data.parent), m = this._model.data, t = this.settings.checkbox.tie_selection; p && "#" !== p.id;) { + for (c = 0, i = 0, j = p.children.length; i < j; i++) c += m[p.children[i]].state[t ? "selected" : "checked"]; + if (c !== j) break; + p.state[t ? "selected" : "checked"] = !0, this._data[t ? "core" : "checkbox"].selected.push(p.id), (tmp = this.get_node(p, !0)) && tmp.length && tmp.attr("aria-selected", !0).children(".jstree-anchor").addClass(t ? "jstree-clicked" : "jstree-checked"), p = this.get_node(p.parent) + } + }, this)).on("move_node.jstree", $.proxy(function(e, data) { + var p, c, i, j, tmp, is_multi = data.is_multi, + old_par = data.old_parent, + new_par = this.get_node(data.parent), + m = this._model.data, + t = this.settings.checkbox.tie_selection; + if (!is_multi) + for (p = this.get_node(old_par); p && "#" !== p.id;) { + for (c = 0, i = 0, j = p.children.length; i < j; i++) c += m[p.children[i]].state[t ? "selected" : "checked"]; + if (c !== j) break; + p.state[t ? "selected" : "checked"] = !0, this._data[t ? "core" : "checkbox"].selected.push(p.id), (tmp = this.get_node(p, !0)) && tmp.length && tmp.attr("aria-selected", !0).children(".jstree-anchor").addClass(t ? "jstree-clicked" : "jstree-checked"), p = this.get_node(p.parent) + } + for (p = new_par; p && "#" !== p.id;) { + for (c = 0, i = 0, j = p.children.length; i < j; i++) c += m[p.children[i]].state[t ? "selected" : "checked"]; + if (c === j) p.state[t ? "selected" : "checked"] || (p.state[t ? "selected" : "checked"] = !0, this._data[t ? "core" : "checkbox"].selected.push(p.id), (tmp = this.get_node(p, !0)) && tmp.length && tmp.attr("aria-selected", !0).children(".jstree-anchor").addClass(t ? "jstree-clicked" : "jstree-checked")); + else { + if (!p.state[t ? "selected" : "checked"]) break; + p.state[t ? "selected" : "checked"] = !1, this._data[t ? "core" : "checkbox"].selected = $.vakata.array_remove_item(this._data[t ? "core" : "checkbox"].selected, p.id), (tmp = this.get_node(p, !0)) && tmp.length && tmp.attr("aria-selected", !1).children(".jstree-anchor").removeClass(t ? "jstree-clicked" : "jstree-checked") + } + p = this.get_node(p.parent) + } + }, this)) + }, this._undetermined = function() { + if (null !== this.element) { + var i, j, k, l, o = {}, + m = this._model.data, + t = this.settings.checkbox.tie_selection, + s = this._data[t ? "core" : "checkbox"].selected, + p = [], + tt = this; + for (i = 0, j = s.length; i < j; i++) + if (m[s[i]] && m[s[i]].parents) + for (k = 0, l = m[s[i]].parents.length; k < l; k++) o[m[s[i]].parents[k]] === undefined && "#" !== m[s[i]].parents[k] && (o[m[s[i]].parents[k]] = !0, p.push(m[s[i]].parents[k])); + for (this.element.find(".jstree-closed").not(":has(.jstree-children)").each(function() { + var tmp2, tmp = tt.get_node(this); + if (tmp.state.loaded) { + for (i = 0, j = tmp.children_d.length; i < j; i++) + if (tmp2 = m[tmp.children_d[i]], !tmp2.state.loaded && tmp2.original && tmp2.original.state && tmp2.original.state.undetermined && !0 === tmp2.original.state.undetermined) + for (o[tmp2.id] === undefined && "#" !== tmp2.id && (o[tmp2.id] = !0, p.push(tmp2.id)), k = 0, l = tmp2.parents.length; k < l; k++) o[tmp2.parents[k]] === undefined && "#" !== tmp2.parents[k] && (o[tmp2.parents[k]] = !0, p.push(tmp2.parents[k])) + } else if (tmp.original && tmp.original.state && tmp.original.state.undetermined && !0 === tmp.original.state.undetermined) + for (o[tmp.id] === undefined && "#" !== tmp.id && (o[tmp.id] = !0, p.push(tmp.id)), k = 0, l = tmp.parents.length; k < l; k++) o[tmp.parents[k]] === undefined && "#" !== tmp.parents[k] && (o[tmp.parents[k]] = !0, p.push(tmp.parents[k])) + }), this.element.find(".jstree-undetermined").removeClass("jstree-undetermined"), i = 0, j = p.length; i < j; i++) m[p[i]].state[t ? "selected" : "checked"] || (s = this.get_node(p[i], !0)) && s.length && s.children(".jstree-anchor").children(".jstree-checkbox").addClass("jstree-undetermined") + } + }, this.redraw_node = function(obj, deep, is_callback, force_render) { + if (obj = parent.redraw_node.apply(this, arguments)) { + var i, j, tmp = null; + for (i = 0, j = obj.childNodes.length; i < j; i++) + if (obj.childNodes[i] && obj.childNodes[i].className && -1 !== obj.childNodes[i].className.indexOf("jstree-anchor")) { + tmp = obj.childNodes[i]; + break + } tmp && (!this.settings.checkbox.tie_selection && this._model.data[obj.id].state.checked && (tmp.className += " jstree-checked"), tmp.insertBefore(_i.cloneNode(!1), tmp.childNodes[0])) + } + return is_callback || -1 === this.settings.checkbox.cascade.indexOf("undetermined") || (this._data.checkbox.uto && clearTimeout(this._data.checkbox.uto), this._data.checkbox.uto = setTimeout($.proxy(this._undetermined, this), 50)), obj + }, this.show_checkboxes = function() { + this._data.core.themes.checkboxes = !0, this.get_container_ul().removeClass("jstree-no-checkboxes") + }, this.hide_checkboxes = function() { + this._data.core.themes.checkboxes = !1, this.get_container_ul().addClass("jstree-no-checkboxes") + }, this.toggle_checkboxes = function() { + this._data.core.themes.checkboxes ? this.hide_checkboxes() : this.show_checkboxes() + }, this.is_undetermined = function(obj) { + obj = this.get_node(obj); + var i, j, s = this.settings.checkbox.cascade, + t = this.settings.checkbox.tie_selection, + d = this._data[t ? "core" : "checkbox"].selected, + m = this._model.data; + if (!obj || !0 === obj.state[t ? "selected" : "checked"] || -1 === s.indexOf("undetermined") || -1 === s.indexOf("down") && -1 === s.indexOf("up")) return !1; + if (!obj.state.loaded && !0 === obj.original.state.undetermined) return !0; + for (i = 0, j = obj.children_d.length; i < j; i++) + if (-1 !== $.inArray(obj.children_d[i], d) || !m[obj.children_d[i]].state.loaded && m[obj.children_d[i]].original.state.undetermined) return !0; + return !1 + }, this.activate_node = function(obj, e) { + return this.settings.checkbox.tie_selection && (this.settings.checkbox.whole_node || $(e.target).hasClass("jstree-checkbox")) && (e.ctrlKey = !0), this.settings.checkbox.tie_selection || !this.settings.checkbox.whole_node && !$(e.target).hasClass("jstree-checkbox") ? parent.activate_node.call(this, obj, e) : !this.is_disabled(obj) && (this.is_checked(obj) ? this.uncheck_node(obj, e) : this.check_node(obj, e), void this.trigger("activate_node", { + node: this.get_node(obj) + })) + }, this.check_node = function(obj, e) { + if (this.settings.checkbox.tie_selection) return this.select_node(obj, !1, !0, e); + var dom, t1, t2; + if ($.isArray(obj)) { + for (obj = obj.slice(), t1 = 0, t2 = obj.length; t1 < t2; t1++) this.check_node(obj[t1], e); + return !0 + } + if (!(obj = this.get_node(obj)) || "#" === obj.id) return !1; + dom = this.get_node(obj, !0), obj.state.checked || (obj.state.checked = !0, this._data.checkbox.selected.push(obj.id), dom && dom.length && dom.children(".jstree-anchor").addClass("jstree-checked"), this.trigger("check_node", { + node: obj, + selected: this._data.checkbox.selected, + event: e + })) + }, this.uncheck_node = function(obj, e) { + if (this.settings.checkbox.tie_selection) return this.deselect_node(obj, !1, e); + var t1, t2, dom; + if ($.isArray(obj)) { + for (obj = obj.slice(), t1 = 0, t2 = obj.length; t1 < t2; t1++) this.uncheck_node(obj[t1], e); + return !0 + } + if (!(obj = this.get_node(obj)) || "#" === obj.id) return !1; + dom = this.get_node(obj, !0), obj.state.checked && (obj.state.checked = !1, this._data.checkbox.selected = $.vakata.array_remove_item(this._data.checkbox.selected, obj.id), dom.length && dom.children(".jstree-anchor").removeClass("jstree-checked"), this.trigger("uncheck_node", { + node: obj, + selected: this._data.checkbox.selected, + event: e + })) + }, this.check_all = function() { + if (this.settings.checkbox.tie_selection) return this.select_all(); + var i, j; + this._data.checkbox.selected.concat([]); + for (this._data.checkbox.selected = this._model.data["#"].children_d.concat(), i = 0, j = this._data.checkbox.selected.length; i < j; i++) this._model.data[this._data.checkbox.selected[i]] && (this._model.data[this._data.checkbox.selected[i]].state.checked = !0); + this.redraw(!0), this.trigger("check_all", { + selected: this._data.checkbox.selected + }) + }, this.uncheck_all = function() { + if (this.settings.checkbox.tie_selection) return this.deselect_all(); + var i, j, tmp = this._data.checkbox.selected.concat([]); + for (i = 0, j = this._data.checkbox.selected.length; i < j; i++) this._model.data[this._data.checkbox.selected[i]] && (this._model.data[this._data.checkbox.selected[i]].state.checked = !1); + this._data.checkbox.selected = [], this.element.find(".jstree-checked").removeClass("jstree-checked"), this.trigger("uncheck_all", { + selected: this._data.checkbox.selected, + node: tmp + }) + }, this.is_checked = function(obj) { + return this.settings.checkbox.tie_selection ? this.is_selected(obj) : !(!(obj = this.get_node(obj)) || "#" === obj.id) && obj.state.checked + }, this.get_checked = function(full) { + return this.settings.checkbox.tie_selection ? this.get_selected(full) : full ? $.map(this._data.checkbox.selected, $.proxy(function(i) { + return this.get_node(i) + }, this)) : this._data.checkbox.selected + }, this.get_top_checked = function(full) { + if (this.settings.checkbox.tie_selection) return this.get_top_selected(full); + var i, j, k, l, tmp = this.get_checked(!0), + obj = {}; + for (i = 0, j = tmp.length; i < j; i++) obj[tmp[i].id] = tmp[i]; + for (i = 0, j = tmp.length; i < j; i++) + for (k = 0, l = tmp[i].children_d.length; k < l; k++) obj[tmp[i].children_d[k]] && delete obj[tmp[i].children_d[k]]; + tmp = []; + for (i in obj) obj.hasOwnProperty(i) && tmp.push(i); + return full ? $.map(tmp, $.proxy(function(i) { + return this.get_node(i) + }, this)) : tmp + }, this.get_bottom_checked = function(full) { + if (this.settings.checkbox.tie_selection) return this.get_bottom_selected(full); + var i, j, tmp = this.get_checked(!0), + obj = []; + for (i = 0, j = tmp.length; i < j; i++) tmp[i].children.length || obj.push(tmp[i].id); + return full ? $.map(obj, $.proxy(function(i) { + return this.get_node(i) + }, this)) : obj + }, this.load_node = function(obj, callback) { + var k, l, tmp; + if (!$.isArray(obj) && !this.settings.checkbox.tie_selection && (tmp = this.get_node(obj)) && tmp.state.loaded) + for (k = 0, l = tmp.children_d.length; k < l; k++) this._model.data[tmp.children_d[k]].state.checked && (!0, this._data.checkbox.selected = $.vakata.array_remove_item(this._data.checkbox.selected, tmp.children_d[k])); + return parent.load_node.apply(this, arguments) + }, this.get_state = function() { + var state = parent.get_state.apply(this, arguments); + return this.settings.checkbox.tie_selection ? state : (state.checkbox = this._data.checkbox.selected.slice(), state) + }, this.set_state = function(state, callback) { + var res = parent.set_state.apply(this, arguments); + if (res && state.checkbox) { + if (!this.settings.checkbox.tie_selection) { + this.uncheck_all(); + var _this = this; + $.each(state.checkbox, function(i, v) { + _this.check_node(v) + }) + } + return delete state.checkbox, this.set_state(state, callback), !1 + } + return res + } + }, $.jstree.defaults.contextmenu = { + select_node: !0, + show_at_node: !0, + items: function(o, cb) { + return { + create: { + separator_before: !1, + separator_after: !0, + _disabled: !1, + label: "Create", + action: function(data) { + var inst = $.jstree.reference(data.reference), + obj = inst.get_node(data.reference); + inst.create_node(obj, {}, "last", function(new_node) { + setTimeout(function() { + inst.edit(new_node) + }, 0) + }) + } + }, + rename: { + separator_before: !1, + separator_after: !1, + _disabled: !1, + label: "Rename", + action: function(data) { + var inst = $.jstree.reference(data.reference), + obj = inst.get_node(data.reference); + inst.edit(obj) + } + }, + remove: { + separator_before: !1, + icon: !1, + separator_after: !1, + _disabled: !1, + label: "Delete", + action: function(data) { + var inst = $.jstree.reference(data.reference), + obj = inst.get_node(data.reference); + inst.is_selected(obj) ? inst.delete_node(inst.get_selected()) : inst.delete_node(obj) + } + }, + ccp: { + separator_before: !0, + icon: !1, + separator_after: !1, + label: "Edit", + action: !1, + submenu: { + cut: { + separator_before: !1, + separator_after: !1, + label: "Cut", + action: function(data) { + var inst = $.jstree.reference(data.reference), + obj = inst.get_node(data.reference); + inst.is_selected(obj) ? inst.cut(inst.get_top_selected()) : inst.cut(obj) + } + }, + copy: { + separator_before: !1, + icon: !1, + separator_after: !1, + label: "Copy", + action: function(data) { + var inst = $.jstree.reference(data.reference), + obj = inst.get_node(data.reference); + inst.is_selected(obj) ? inst.copy(inst.get_top_selected()) : inst.copy(obj) + } + }, + paste: { + separator_before: !1, + icon: !1, + _disabled: function(data) { + return !$.jstree.reference(data.reference).can_paste() + }, + separator_after: !1, + label: "Paste", + action: function(data) { + var inst = $.jstree.reference(data.reference), + obj = inst.get_node(data.reference); + inst.paste(obj) + } + } + } + } + } + } + }, $.jstree.plugins.contextmenu = function(options, parent) { + this.bind = function() { + parent.bind.call(this); + var ex, ey, last_ts = 0, + cto = null; + this.element.on("contextmenu.jstree", ".jstree-anchor", $.proxy(function(e, data) { + e.preventDefault(), last_ts = e.ctrlKey ? +new Date : 0, (data || cto) && (last_ts = +new Date + 1e4), cto && clearTimeout(cto), this.is_loading(e.currentTarget) || this.show_contextmenu(e.currentTarget, e.pageX, e.pageY, e) + }, this)).on("click.jstree", ".jstree-anchor", $.proxy(function(e) { + this._data.contextmenu.visible && (!last_ts || +new Date - last_ts > 250) && $.vakata.context.hide(), last_ts = 0 + }, this)).on("touchstart.jstree", ".jstree-anchor", function(e) { + e.originalEvent && e.originalEvent.changedTouches && e.originalEvent.changedTouches[0] && (ex = e.pageX, ey = e.pageY, cto = setTimeout(function() { + $(e.currentTarget).trigger("contextmenu", !0) + }, 750)) + }).on("touchmove.vakata.jstree", function(e) { + cto && e.originalEvent && e.originalEvent.changedTouches && e.originalEvent.changedTouches[0] && (Math.abs(ex - e.pageX) > 50 || Math.abs(ey - e.pageY) > 50) && clearTimeout(cto) + }).on("touchend.vakata.jstree", function(e) { + cto && clearTimeout(cto) + }), $(document).on("context_hide.vakata.jstree", $.proxy(function() { + this._data.contextmenu.visible = !1 + }, this)) + }, this.teardown = function() { + this._data.contextmenu.visible && $.vakata.context.hide(), parent.teardown.call(this) + }, this.show_contextmenu = function(obj, x, y, e) { + if (!(obj = this.get_node(obj)) || "#" === obj.id) return !1; + var s = this.settings.contextmenu, + d = this.get_node(obj, !0), + a = d.children(".jstree-anchor"), + o = !1, + i = !1; + (s.show_at_node || x === undefined || y === undefined) && (o = a.offset(), x = o.left, y = o.top + this._data.core.li_height), this.settings.contextmenu.select_node && !this.is_selected(obj) && this.activate_node(obj, e), i = s.items, $.isFunction(i) && (i = i.call(this, obj, $.proxy(function(i) { + this._show_contextmenu(obj, x, y, i) + }, this))), $.isPlainObject(i) && this._show_contextmenu(obj, x, y, i) + }, this._show_contextmenu = function(obj, x, y, i) { + var d = this.get_node(obj, !0), + a = d.children(".jstree-anchor"); + $(document).one("context_show.vakata.jstree", $.proxy(function(e, data) { + var cls = "jstree-contextmenu jstree-" + this.get_theme() + "-contextmenu"; + $(data.element).addClass(cls) + }, this)), this._data.contextmenu.visible = !0, $.vakata.context.show(a, { + x: x, + y: y + }, i), this.trigger("show_contextmenu", { + node: obj, + x: x, + y: y + }) + } + }, + function($) { + var right_to_left = !1, + vakata_context = { + element: !1, + reference: !1, + position_x: 0, + position_y: 0, + items: [], + html: "", + is_visible: !1 + }; + $.vakata.context = { + settings: { + hide_onmouseleave: 0, + icons: !0 + }, + _trigger: function(event_name) { + $(document).triggerHandler("context_" + event_name + ".vakata", { + reference: vakata_context.reference, + element: vakata_context.element, + position: { + x: vakata_context.position_x, + y: vakata_context.position_y + } + }) + }, + _execute: function(i) { + return !(!(i = vakata_context.items[i]) || i._disabled && (!$.isFunction(i._disabled) || i._disabled({ + item: i, + reference: vakata_context.reference, + element: vakata_context.element + })) || !i.action) && i.action.call(null, { + item: i, + reference: vakata_context.reference, + element: vakata_context.element, + position: { + x: vakata_context.position_x, + y: vakata_context.position_y + } + }) + }, + _parse: function(o, is_callback) { + if (!o) return !1; + is_callback || (vakata_context.html = "", vakata_context.items = []); + var tmp, str = "", + sep = !1; + return is_callback && (str += ""), is_callback || (vakata_context.html = str, $.vakata.context._trigger("parse")), str.length > 10 && str + }, + _show_submenu: function(o) { + if (o = $(o), o.length && o.children("ul").length) { + var e = o.children("ul"), + x = o.offset().left + o.outerWidth(), + y = o.offset().top, + w = e.width(), + h = e.height(), + dw = $(window).width() + $(window).scrollLeft(), + dh = $(window).height() + $(window).scrollTop(); + right_to_left ? o[x - (w + 10 + o.outerWidth()) < 0 ? "addClass" : "removeClass"]("vakata-context-left") : o[x + w + 10 > dw ? "addClass" : "removeClass"]("vakata-context-right"), y + h + 10 > dh && e.css("bottom", "-1px"), + e.show() + } + }, + show: function(reference, position, data) { + var o, e, x, y, w, h, dw, dh; + switch (vakata_context.element && vakata_context.element.length && vakata_context.element.width(""), !0) { + case !position && !reference: + return !1; + case !!position && !!reference: + vakata_context.reference = reference, vakata_context.position_x = position.x, vakata_context.position_y = position.y; + break; + case !position && !!reference: + vakata_context.reference = reference, o = reference.offset(), vakata_context.position_x = o.left + reference.outerHeight(), vakata_context.position_y = o.top; + break; + case !!position && !reference: + vakata_context.position_x = position.x, vakata_context.position_y = position.y + } + reference && !data && $(reference).data("vakata_contextmenu") && (data = $(reference).data("vakata_contextmenu")), $.vakata.context._parse(data) && vakata_context.element.html(vakata_context.html), vakata_context.items.length && (vakata_context.element.appendTo("body"), e = vakata_context.element, x = vakata_context.position_x, y = vakata_context.position_y, w = e.width(), h = e.height(), dw = $(window).width() + $(window).scrollLeft(), dh = $(window).height() + $(window).scrollTop(), right_to_left && (x -= e.outerWidth() - $(reference).outerWidth()) < $(window).scrollLeft() + 20 && (x = $(window).scrollLeft() + 20), x + w + 20 > dw && (x = dw - (w + 20)), y + h + 20 > dh && (y = dh - (h + 20)), vakata_context.element.css({ + left: x, + top: y + }).show().find("a").first().focus().parent().addClass("vakata-context-hover"), vakata_context.is_visible = !0, $.vakata.context._trigger("show")) + }, + hide: function() { + vakata_context.is_visible && (vakata_context.element.hide().find("ul").hide().end().find(":focus").blur().end().detach(), vakata_context.is_visible = !1, $.vakata.context._trigger("hide")) + } + }, $(function() { + right_to_left = "rtl" === $("body").css("direction"); + var to = !1; + vakata_context.element = $("
        "), vakata_context.element.on("mouseenter", "li", function(e) { + e.stopImmediatePropagation(), $.contains(this, e.relatedTarget) || (to && clearTimeout(to), vakata_context.element.find(".vakata-context-hover").removeClass("vakata-context-hover").end(), $(this).siblings().find("ul").hide().end().end().parentsUntil(".vakata-context", "li").addBack().addClass("vakata-context-hover"), $.vakata.context._show_submenu(this)) + }).on("mouseleave", "li", function(e) { + $.contains(this, e.relatedTarget) || $(this).find(".vakata-context-hover").addBack().removeClass("vakata-context-hover") + }).on("mouseleave", function(e) { + $(this).find(".vakata-context-hover").removeClass("vakata-context-hover"), $.vakata.context.settings.hide_onmouseleave && (to = setTimeout(function(t) { + return function() { + $.vakata.context.hide() + } + }(), $.vakata.context.settings.hide_onmouseleave)) + }).on("click", "a", function(e) { + e.preventDefault(), $(this).blur().parent().hasClass("vakata-context-disabled") || !1 === $.vakata.context._execute($(this).attr("rel")) || $.vakata.context.hide() + }).on("keydown", "a", function(e) { + var o = null; + switch (e.which) { + case 13: + case 32: + e.type = "mouseup", e.preventDefault(), $(e.currentTarget).trigger(e); + break; + case 37: + vakata_context.is_visible && (vakata_context.element.find(".vakata-context-hover").last().closest("li").first().find("ul").hide().find(".vakata-context-hover").removeClass("vakata-context-hover").end().end().children("a").focus(), e.stopImmediatePropagation(), e.preventDefault()); + break; + case 38: + vakata_context.is_visible && (o = vakata_context.element.find("ul:visible").addBack().last().children(".vakata-context-hover").removeClass("vakata-context-hover").prevAll("li:not(.vakata-context-separator)").first(), o.length || (o = vakata_context.element.find("ul:visible").addBack().last().children("li:not(.vakata-context-separator)").last()), o.addClass("vakata-context-hover").children("a").focus(), e.stopImmediatePropagation(), e.preventDefault()); + break; + case 39: + vakata_context.is_visible && (vakata_context.element.find(".vakata-context-hover").last().children("ul").show().children("li:not(.vakata-context-separator)").removeClass("vakata-context-hover").first().addClass("vakata-context-hover").children("a").focus(), e.stopImmediatePropagation(), e.preventDefault()); + break; + case 40: + vakata_context.is_visible && (o = vakata_context.element.find("ul:visible").addBack().last().children(".vakata-context-hover").removeClass("vakata-context-hover").nextAll("li:not(.vakata-context-separator)").first(), o.length || (o = vakata_context.element.find("ul:visible").addBack().last().children("li:not(.vakata-context-separator)").first()), o.addClass("vakata-context-hover").children("a").focus(), e.stopImmediatePropagation(), e.preventDefault()); + break; + case 27: + $.vakata.context.hide(), e.preventDefault() + } + }).on("keydown", function(e) { + e.preventDefault(); + var a = vakata_context.element.find(".vakata-contextmenu-shortcut-" + e.which).parent(); + a.parent().not(".vakata-context-disabled") && a.click() + }), $(document).on("mousedown.vakata.jstree", function(e) { + vakata_context.is_visible && !$.contains(vakata_context.element[0], e.target) && $.vakata.context.hide() + }).on("context_show.vakata.jstree", function(e, data) { + vakata_context.element.find("li:has(ul)").children("a").addClass("vakata-context-parent"), right_to_left && vakata_context.element.addClass("vakata-context-rtl").css("direction", "rtl"), vakata_context.element.find("ul").hide().end() + }) + }) + }($), $.jstree.defaults.dnd = { + copy: !0, + open_timeout: 500, + is_draggable: !0, + check_while_dragging: !0, + always_copy: !1, + inside_pos: 0, + drag_selection: !0, + touch: !0, + large_drop_target: !1, + large_drag_target: !1 + }, $.jstree.plugins.dnd = function(options, parent) { + this.bind = function() { + parent.bind.call(this), this.element.on("mousedown.jstree touchstart.jstree", this.settings.dnd.large_drag_target ? ".jstree-node" : ".jstree-anchor", $.proxy(function(e) { + if (this.settings.dnd.large_drag_target && $(e.target).closest(".jstree-node")[0] !== e.currentTarget) return !0; + if ("touchstart" === e.type && (!this.settings.dnd.touch || "selected" === this.settings.dnd.touch && !$(e.currentTarget).closest(".jstree-node").children(".jstree-anchor").hasClass("jstree-clicked"))) return !0; + var obj = this.get_node(e.target), + mlt = this.is_selected(obj) && this.settings.dnd.drag_selection ? this.get_top_selected().length : 1, + txt = mlt > 1 ? mlt + " " + this.get_string("nodes") : this.get_text(e.currentTarget); + return this.settings.core.force_text && (txt = $.vakata.html.escape(txt)), obj && obj.id && "#" !== obj.id && (1 === e.which || "touchstart" === e.type) && (!0 === this.settings.dnd.is_draggable || $.isFunction(this.settings.dnd.is_draggable) && this.settings.dnd.is_draggable.call(this, mlt > 1 ? this.get_top_selected(!0) : [obj])) ? (this.element.trigger("mousedown.jstree"), $.vakata.dnd.start(e, { + jstree: !0, + origin: this, + obj: this.get_node(obj, !0), + nodes: mlt > 1 ? this.get_top_selected() : [obj.id] + }, '
        ' + txt + '
        ')) : void 0 + }, this)) + } + }, $(function() { + var lastmv = !1, + laster = !1, + opento = !1, + marker = $('
         
        ').hide(); + $(document).on("dnd_start.vakata.jstree", function(e, data) { + lastmv = !1, data && data.data && data.data.jstree && marker.appendTo("body") + }).on("dnd_move.vakata.jstree", function(e, data) { + if (opento && clearTimeout(opento), data && data.data && data.data.jstree && (!data.event.target.id || "jstree-marker" !== data.event.target.id)) { + var l, t, h, p, i, o, ok, t1, t2, op, ps, pr, ip, tm, ins = $.jstree.reference(data.event.target), + ref = !1, + off = !1, + rel = !1; + if (ins && ins._data && ins._data.dnd) + if (marker.attr("class", "jstree-" + ins.get_theme() + (ins.settings.core.themes.responsive ? " jstree-dnd-responsive" : "")), data.helper.children().attr("class", "jstree-" + ins.get_theme() + " jstree-" + ins.get_theme() + "-" + ins.get_theme_variant() + " " + (ins.settings.core.themes.responsive ? " jstree-dnd-responsive" : "")).find(".jstree-copy").first()[data.data.origin && (data.data.origin.settings.dnd.always_copy || data.data.origin.settings.dnd.copy && (data.event.metaKey || data.event.ctrlKey)) ? "show" : "hide"](), data.event.target !== ins.element[0] && data.event.target !== ins.get_container_ul()[0] || 0 !== ins.get_container_ul().children().length) { + if ((ref = ins.settings.dnd.large_drop_target ? $(data.event.target).closest(".jstree-node").children(".jstree-anchor") : $(data.event.target).closest(".jstree-anchor")) && ref.length && ref.parent().is(".jstree-closed, .jstree-open, .jstree-leaf") && (off = ref.offset(), rel = data.event.pageY - off.top, h = ref.outerHeight(), o = rel < h / 3 ? ["b", "i", "a"] : rel > h - h / 3 ? ["a", "i", "b"] : rel > h / 2 ? ["i", "a", "b"] : ["i", "b", "a"], $.each(o, function(j, v) { + switch (v) { + case "b": + l = off.left - 6, t = off.top, p = ins.get_parent(ref), i = ref.parent().index(); + break; + case "i": + ip = ins.settings.dnd.inside_pos, tm = ins.get_node(ref.parent()), l = off.left - 2, t = off.top + h / 2 + 1, p = tm.id, i = "first" === ip ? 0 : "last" === ip ? tm.children.length : Math.min(ip, tm.children.length); + break; + case "a": + l = off.left - 6, t = off.top + h, p = ins.get_parent(ref), i = ref.parent().index() + 1 + } + for (ok = !0, t1 = 0, t2 = data.data.nodes.length; t1 < t2; t1++) + if (op = data.data.origin && (data.data.origin.settings.dnd.always_copy || data.data.origin.settings.dnd.copy && (data.event.metaKey || data.event.ctrlKey)) ? "copy_node" : "move_node", ps = i, "move_node" === op && "a" === v && data.data.origin && data.data.origin === ins && p === ins.get_parent(data.data.nodes[t1]) && (pr = ins.get_node(p), ps > $.inArray(data.data.nodes[t1], pr.children) && (ps -= 1)), !(ok = ok && (ins && ins.settings && ins.settings.dnd && !1 === ins.settings.dnd.check_while_dragging || ins.check(op, data.data.origin && data.data.origin !== ins ? data.data.origin.get_node(data.data.nodes[t1]) : data.data.nodes[t1], p, ps, { + dnd: !0, + ref: ins.get_node(ref.parent()), + pos: v, + origin: data.data.origin, + is_multi: data.data.origin && data.data.origin !== ins, + is_foreign: !data.data.origin + })))) { + ins && ins.last_error && (laster = ins.last_error()); + break + } if ("i" === v && ref.parent().is(".jstree-closed") && ins.settings.dnd.open_timeout && (opento = setTimeout(function(x, z) { + return function() { + x.open_node(z) + } + }(ins, ref), ins.settings.dnd.open_timeout)), ok) return lastmv = { + ins: ins, + par: p, + pos: "i" !== v || "last" !== ip || 0 !== i || ins.is_loaded(tm) ? i : "last" + }, marker.css({ + left: l + "px", + top: t + "px" + }).show(), data.helper.find(".jstree-icon").first().removeClass("jstree-er").addClass("jstree-ok"), laster = {}, o = !0, !1 + }), !0 === o)) return + } else { + for (ok = !0, t1 = 0, t2 = data.data.nodes.length; t1 < t2 && (ok = ok && ins.check(data.data.origin && (data.data.origin.settings.dnd.always_copy || data.data.origin.settings.dnd.copy && (data.event.metaKey || data.event.ctrlKey)) ? "copy_node" : "move_node", data.data.origin && data.data.origin !== ins ? data.data.origin.get_node(data.data.nodes[t1]) : data.data.nodes[t1], "#", "last", { + dnd: !0, + ref: ins.get_node("#"), + pos: "i", + origin: data.data.origin, + is_multi: data.data.origin && data.data.origin !== ins, + is_foreign: !data.data.origin + })); t1++); + if (ok) return lastmv = { + ins: ins, + par: "#", + pos: "last" + }, marker.hide(), void data.helper.find(".jstree-icon").first().removeClass("jstree-er").addClass("jstree-ok") + } lastmv = !1, data.helper.find(".jstree-icon").removeClass("jstree-ok").addClass("jstree-er"), marker.hide() + } + }).on("dnd_scroll.vakata.jstree", function(e, data) { + data && data.data && data.data.jstree && (marker.hide(), lastmv = !1, data.helper.find(".jstree-icon").first().removeClass("jstree-ok").addClass("jstree-er")) + }).on("dnd_stop.vakata.jstree", function(e, data) { + if (opento && clearTimeout(opento), data && data.data && data.data.jstree) { + marker.hide().detach(); + var i, j, nodes = []; + if (lastmv) { + for (i = 0, j = data.data.nodes.length; i < j; i++) nodes[i] = data.data.origin ? data.data.origin.get_node(data.data.nodes[i]) : data.data.nodes[i]; + lastmv.ins[data.data.origin && (data.data.origin.settings.dnd.always_copy || data.data.origin.settings.dnd.copy && (data.event.metaKey || data.event.ctrlKey)) ? "copy_node" : "move_node"](nodes, lastmv.par, lastmv.pos, !1, !1, !1, data.data.origin) + } else i = $(data.event.target).closest(".jstree"), i.length && laster && laster.error && "check" === laster.error && (i = i.jstree(!0)) && i.settings.core.error.call(this, laster) + } + }).on("keyup.jstree keydown.jstree", function(e, data) { + (data = $.vakata.dnd._get()) && data.data && data.data.jstree && data.helper.find(".jstree-copy").first()[data.data.origin && (data.data.origin.settings.dnd.always_copy || data.data.origin.settings.dnd.copy && (e.metaKey || e.ctrlKey)) ? "show" : "hide"]() + }) + }), + function($) { + $.vakata.html = { + div: $("
        "), + escape: function(str) { + return $.vakata.html.div.text(str).html() + }, + strip: function(str) { + return $.vakata.html.div.empty().append($.parseHTML(str)).text() + } + }; + var vakata_dnd = { + element: !1, + target: !1, + is_down: !1, + is_drag: !1, + helper: !1, + helper_w: 0, + data: !1, + init_x: 0, + init_y: 0, + scroll_l: 0, + scroll_t: 0, + scroll_e: !1, + scroll_i: !1, + is_touch: !1 + }; + $.vakata.dnd = { + settings: { + scroll_speed: 10, + scroll_proximity: 20, + helper_left: 5, + helper_top: 10, + threshold: 5, + threshold_touch: 50 + }, + _trigger: function(event_name, e) { + var data = $.vakata.dnd._get(); + data.event = e, $(document).triggerHandler("dnd_" + event_name + ".vakata", data) + }, + _get: function() { + return { + data: vakata_dnd.data, + element: vakata_dnd.element, + helper: vakata_dnd.helper + } + }, + _clean: function() { + vakata_dnd.helper && vakata_dnd.helper.remove(), vakata_dnd.scroll_i && (clearInterval(vakata_dnd.scroll_i), vakata_dnd.scroll_i = !1), vakata_dnd = { + element: !1, + target: !1, + is_down: !1, + is_drag: !1, + helper: !1, + helper_w: 0, + data: !1, + init_x: 0, + init_y: 0, + scroll_l: 0, + scroll_t: 0, + scroll_e: !1, + scroll_i: !1, + is_touch: !1 + }, $(document).off("mousemove.vakata.jstree touchmove.vakata.jstree", $.vakata.dnd.drag), $(document).off("mouseup.vakata.jstree touchend.vakata.jstree", $.vakata.dnd.stop) + }, + _scroll: function(init_only) { + if (!vakata_dnd.scroll_e || !vakata_dnd.scroll_l && !vakata_dnd.scroll_t) return vakata_dnd.scroll_i && (clearInterval(vakata_dnd.scroll_i), vakata_dnd.scroll_i = !1), !1; + if (!vakata_dnd.scroll_i) return vakata_dnd.scroll_i = setInterval($.vakata.dnd._scroll, 100), !1; + if (!0 === init_only) return !1; + var i = vakata_dnd.scroll_e.scrollTop(), + j = vakata_dnd.scroll_e.scrollLeft(); + vakata_dnd.scroll_e.scrollTop(i + vakata_dnd.scroll_t * $.vakata.dnd.settings.scroll_speed), vakata_dnd.scroll_e.scrollLeft(j + vakata_dnd.scroll_l * $.vakata.dnd.settings.scroll_speed), i === vakata_dnd.scroll_e.scrollTop() && j === vakata_dnd.scroll_e.scrollLeft() || $.vakata.dnd._trigger("scroll", vakata_dnd.scroll_e) + }, + start: function(e, data, html) { + "touchstart" === e.type && e.originalEvent && e.originalEvent.changedTouches && e.originalEvent.changedTouches[0] && (e.pageX = e.originalEvent.changedTouches[0].pageX, e.pageY = e.originalEvent.changedTouches[0].pageY, e.target = document.elementFromPoint(e.originalEvent.changedTouches[0].pageX - window.pageXOffset, e.originalEvent.changedTouches[0].pageY - window.pageYOffset)), vakata_dnd.is_drag && $.vakata.dnd.stop({}); + try { + e.currentTarget.unselectable = "on", e.currentTarget.onselectstart = function() { + return !1 + }, e.currentTarget.style && (e.currentTarget.style.MozUserSelect = "none") + } catch (ignore) {} + return vakata_dnd.init_x = e.pageX, vakata_dnd.init_y = e.pageY, vakata_dnd.data = data, vakata_dnd.is_down = !0, vakata_dnd.element = e.currentTarget, vakata_dnd.target = e.target, vakata_dnd.is_touch = "touchstart" === e.type, !1 !== html && (vakata_dnd.helper = $("
        ").html(html).css({ + display: "block", + margin: "0", + padding: "0", + position: "absolute", + top: "-2000px", + lineHeight: "16px", + zIndex: "10000" + })), $(document).on("mousemove.vakata.jstree touchmove.vakata.jstree", $.vakata.dnd.drag), $(document).on("mouseup.vakata.jstree touchend.vakata.jstree", $.vakata.dnd.stop), !1 + }, + drag: function(e) { + if ("touchmove" === e.type && e.originalEvent && e.originalEvent.changedTouches && e.originalEvent.changedTouches[0] && (e.pageX = e.originalEvent.changedTouches[0].pageX, e.pageY = e.originalEvent.changedTouches[0].pageY, e.target = document.elementFromPoint(e.originalEvent.changedTouches[0].pageX - window.pageXOffset, e.originalEvent.changedTouches[0].pageY - window.pageYOffset)), vakata_dnd.is_down) { + if (!vakata_dnd.is_drag) { + if (!(Math.abs(e.pageX - vakata_dnd.init_x) > (vakata_dnd.is_touch ? $.vakata.dnd.settings.threshold_touch : $.vakata.dnd.settings.threshold) || Math.abs(e.pageY - vakata_dnd.init_y) > (vakata_dnd.is_touch ? $.vakata.dnd.settings.threshold_touch : $.vakata.dnd.settings.threshold))) return; + vakata_dnd.helper && (vakata_dnd.helper.appendTo("body"), vakata_dnd.helper_w = vakata_dnd.helper.outerWidth()), vakata_dnd.is_drag = !0, $.vakata.dnd._trigger("start", e) + } + var d = !1, + w = !1, + dh = !1, + wh = !1, + dw = !1, + ww = !1, + dt = !1, + dl = !1, + ht = !1, + hl = !1; + return vakata_dnd.scroll_t = 0, vakata_dnd.scroll_l = 0, vakata_dnd.scroll_e = !1, $($(e.target).parentsUntil("body").addBack().get().reverse()).filter(function() { + return /^auto|scroll$/.test($(this).css("overflow")) && (this.scrollHeight > this.offsetHeight || this.scrollWidth > this.offsetWidth) + }).each(function() { + var t = $(this), + o = t.offset(); + if (this.scrollHeight > this.offsetHeight && (o.top + t.height() - e.pageY < $.vakata.dnd.settings.scroll_proximity && (vakata_dnd.scroll_t = 1), e.pageY - o.top < $.vakata.dnd.settings.scroll_proximity && (vakata_dnd.scroll_t = -1)), this.scrollWidth > this.offsetWidth && (o.left + t.width() - e.pageX < $.vakata.dnd.settings.scroll_proximity && (vakata_dnd.scroll_l = 1), e.pageX - o.left < $.vakata.dnd.settings.scroll_proximity && (vakata_dnd.scroll_l = -1)), vakata_dnd.scroll_t || vakata_dnd.scroll_l) return vakata_dnd.scroll_e = $(this), !1 + }), vakata_dnd.scroll_e || (d = $(document), w = $(window), dh = d.height(), wh = w.height(), dw = d.width(), ww = w.width(), dt = d.scrollTop(), dl = d.scrollLeft(), dh > wh && e.pageY - dt < $.vakata.dnd.settings.scroll_proximity && (vakata_dnd.scroll_t = -1), dh > wh && wh - (e.pageY - dt) < $.vakata.dnd.settings.scroll_proximity && (vakata_dnd.scroll_t = 1), dw > ww && e.pageX - dl < $.vakata.dnd.settings.scroll_proximity && (vakata_dnd.scroll_l = -1), dw > ww && ww - (e.pageX - dl) < $.vakata.dnd.settings.scroll_proximity && (vakata_dnd.scroll_l = 1), (vakata_dnd.scroll_t || vakata_dnd.scroll_l) && (vakata_dnd.scroll_e = d)), vakata_dnd.scroll_e && $.vakata.dnd._scroll(!0), vakata_dnd.helper && (ht = parseInt(e.pageY + $.vakata.dnd.settings.helper_top, 10), hl = parseInt(e.pageX + $.vakata.dnd.settings.helper_left, 10), dh && ht + 25 > dh && (ht = dh - 50), dw && hl + vakata_dnd.helper_w > dw && (hl = dw - (vakata_dnd.helper_w + 2)), vakata_dnd.helper.css({ + left: hl + "px", + top: ht + "px" + })), $.vakata.dnd._trigger("move", e), !1 + } + }, + stop: function(e) { + if ("touchend" === e.type && e.originalEvent && e.originalEvent.changedTouches && e.originalEvent.changedTouches[0] && (e.pageX = e.originalEvent.changedTouches[0].pageX, e.pageY = e.originalEvent.changedTouches[0].pageY, e.target = document.elementFromPoint(e.originalEvent.changedTouches[0].pageX - window.pageXOffset, e.originalEvent.changedTouches[0].pageY - window.pageYOffset)), vakata_dnd.is_drag) $.vakata.dnd._trigger("stop", e); + else if ("touchend" === e.type && e.target === vakata_dnd.target) { + var to = setTimeout(function() { + $(e.target).click() + }, 100); + $(e.target).one("click", function() { + to && clearTimeout(to) + }) + } + return $.vakata.dnd._clean(), !1 + } + } + }($), $.jstree.defaults.massload = null, $.jstree.plugins.massload = function(options, parent) { + this.init = function(el, options) { + parent.init.call(this, el, options), this._data.massload = {} + }, this._load_nodes = function(nodes, callback, is_callback) { + var s = this.settings.massload; + return is_callback && !$.isEmptyObject(this._data.massload) ? parent._load_nodes.call(this, nodes, callback, is_callback) : $.isFunction(s) ? s.call(this, nodes, $.proxy(function(data) { + if (data) + for (var i in data) data.hasOwnProperty(i) && (this._data.massload[i] = data[i]); + parent._load_nodes.call(this, nodes, callback, is_callback) + }, this)) : "object" == typeof s && s && s.url ? (s = $.extend(!0, {}, s), $.isFunction(s.url) && (s.url = s.url.call(this, nodes)), $.isFunction(s.data) && (s.data = s.data.call(this, nodes)), $.ajax(s).done($.proxy(function(data, t, x) { + if (data) + for (var i in data) data.hasOwnProperty(i) && (this._data.massload[i] = data[i]); + parent._load_nodes.call(this, nodes, callback, is_callback) + }, this)).fail($.proxy(function(f) { + parent._load_nodes.call(this, nodes, callback, is_callback) + }, this))) : parent._load_nodes.call(this, nodes, callback, is_callback) + }, this._load_node = function(obj, callback) { + var d = this._data.massload[obj.id]; + return d ? this["string" == typeof d ? "_append_html_data" : "_append_json_data"](obj, "string" == typeof d ? $($.parseHTML(d)).filter(function() { + return 3 !== this.nodeType + }) : d, function(status) { + callback.call(this, status), delete this._data.massload[obj.id] + }) : parent._load_node.call(this, obj, callback) + } + }, $.jstree.defaults.search = { + ajax: !1, + fuzzy: !1, + case_sensitive: !1, + show_only_matches: !1, + show_only_matches_children: !1, + close_opened_onclear: !0, + search_leaves_only: !1, + search_callback: !1 + }, $.jstree.plugins.search = function(options, parent) { + this.bind = function() { + parent.bind.call(this), this._data.search.str = "", this._data.search.dom = $(), this._data.search.res = [], this._data.search.opn = [], this._data.search.som = !1, this._data.search.smc = !1, this.element.on("before_open.jstree", $.proxy(function(e, data) { + var i, j, r = this._data.search.res, + s = [], + o = $(); + if (r && r.length && (this._data.search.dom = $(this.element[0].querySelectorAll("#" + $.map(r, function(v) { + return -1 !== "0123456789".indexOf(v[0]) ? "\\3" + v[0] + " " + v.substr(1).replace($.jstree.idregex, "\\$&") : v.replace($.jstree.idregex, "\\$&") + }).join(", #"))), this._data.search.dom.children(".jstree-anchor").addClass("jstree-search"), this._data.search.som && this._data.search.res.length)) { + for (i = 0, j = r.length; i < j; i++) s = s.concat(this.get_node(r[i]).parents); + s = $.vakata.array_remove_item($.vakata.array_unique(s), "#"), o = s.length ? $(this.element[0].querySelectorAll("#" + $.map(s, function(v) { + return -1 !== "0123456789".indexOf(v[0]) ? "\\3" + v[0] + " " + v.substr(1).replace($.jstree.idregex, "\\$&") : v.replace($.jstree.idregex, "\\$&") + }).join(", #"))) : $(), this.element.find(".jstree-node").hide().filter(".jstree-last").filter(function() { + return this.nextSibling + }).removeClass("jstree-last"), o = o.add(this._data.search.dom), this._data.search.smc && this._data.search.dom.children(".jstree-children").find(".jstree-node").show(), o.parentsUntil(".jstree").addBack().show().filter(".jstree-children").each(function() { + $(this).children(".jstree-node:visible").eq(-1).addClass("jstree-last") + }) + } + }, this)).on("search.jstree", $.proxy(function(e, data) { + this._data.search.som && data.nodes.length && (this.element.find(".jstree-node").hide().filter(".jstree-last").filter(function() { + return this.nextSibling + }).removeClass("jstree-last"), this._data.search.smc && data.nodes.children(".jstree-children").find(".jstree-node").show(), data.nodes.parentsUntil(".jstree").addBack().show().filter(".jstree-children").each(function() { + $(this).children(".jstree-node:visible").eq(-1).addClass("jstree-last") + })) + }, this)).on("clear_search.jstree", $.proxy(function(e, data) { + this._data.search.som && data.nodes.length && this.element.find(".jstree-node").css("display", "").filter(".jstree-last").filter(function() { + return this.nextSibling + }).removeClass("jstree-last") + }, this)) + }, this.search = function(str, skip_async, show_only_matches, inside, append, show_only_matches_children) { + if (!1 === str || "" === $.trim(str.toString())) return this.clear_search(); + inside = this.get_node(inside), inside = inside && inside.id ? inside.id : null, str = str.toString(); + var s = this.settings.search, + a = !!s.ajax && s.ajax, + m = this._model.data, + f = null, + r = [], + p = []; + if (this._data.search.res.length && !append && this.clear_search(), show_only_matches === undefined && (show_only_matches = s.show_only_matches), show_only_matches_children === undefined && (show_only_matches_children = s.show_only_matches_children), !skip_async && !1 !== a) return $.isFunction(a) ? a.call(this, str, $.proxy(function(d) { + d && d.d && (d = d.d), this._load_nodes($.isArray(d) ? $.vakata.array_unique(d) : [], function() { + this.search(str, !0, show_only_matches, inside, append) + }, !0) + }, this), inside) : (a = $.extend({}, a), a.data || (a.data = {}), a.data.str = str, inside && (a.data.inside = inside), $.ajax(a).fail($.proxy(function() { + this._data.core.last_error = { + error: "ajax", + plugin: "search", + id: "search_01", + reason: "Could not load search parents", + data: JSON.stringify(a) + }, this.settings.core.error.call(this, this._data.core.last_error) + }, this)).done($.proxy(function(d) { + d && d.d && (d = d.d), this._load_nodes($.isArray(d) ? $.vakata.array_unique(d) : [], function() { + this.search(str, !0, show_only_matches, inside, append) + }, !0) + }, this))); + append || (this._data.search.str = str, this._data.search.dom = $(), this._data.search.res = [], this._data.search.opn = [], this._data.search.som = show_only_matches, this._data.search.smc = show_only_matches_children), f = new $.vakata.search(str, !0, { + caseSensitive: s.case_sensitive, + fuzzy: s.fuzzy + }), $.each(m[inside || "#"].children_d, function(ii, i) { + var v = m[i]; + v.text && (s.search_callback && s.search_callback.call(this, str, v) || !s.search_callback && f.search(v.text).isMatch) && (!s.search_leaves_only || v.state.loaded && 0 === v.children.length) && (r.push(i), p = p.concat(v.parents)) + }), r.length && (p = $.vakata.array_unique(p), this._search_open(p), append ? (this._data.search.dom = this._data.search.dom.add($(this.element[0].querySelectorAll("#" + $.map(r, function(v) { + return -1 !== "0123456789".indexOf(v[0]) ? "\\3" + v[0] + " " + v.substr(1).replace($.jstree.idregex, "\\$&") : v.replace($.jstree.idregex, "\\$&") + }).join(", #")))), this._data.search.res = $.vakata.array_unique(this._data.search.res.concat(r))) : (this._data.search.dom = $(this.element[0].querySelectorAll("#" + $.map(r, function(v) { + return -1 !== "0123456789".indexOf(v[0]) ? "\\3" + v[0] + " " + v.substr(1).replace($.jstree.idregex, "\\$&") : v.replace($.jstree.idregex, "\\$&") + }).join(", #"))), this._data.search.res = r), this._data.search.dom.children(".jstree-anchor").addClass("jstree-search")), this.trigger("search", { + nodes: this._data.search.dom, + str: str, + res: this._data.search.res, + show_only_matches: show_only_matches + }) + }, this.clear_search = function() { + this._data.search.dom.children(".jstree-anchor").removeClass("jstree-search"), this.settings.search.close_opened_onclear && this.close_node(this._data.search.opn, 0), this.trigger("clear_search", { + nodes: this._data.search.dom, + str: this._data.search.str, + res: this._data.search.res + }), this._data.search.str = "", this._data.search.res = [], this._data.search.opn = [], this._data.search.dom = $() + }, this._search_open = function(d) { + var t = this; + $.each(d.concat([]), function(i, v) { + if ("#" === v) return !0; + try { + v = $("#" + v.replace($.jstree.idregex, "\\$&"), t.element) + } catch (ignore) {} + v && v.length && t.is_closed(v) && (t._data.search.opn.push(v[0].id), t.open_node(v, function() { + t._search_open(d) + }, 0)) + }) + } + }, + function($) { + $.vakata.search = function(pattern, txt, options) { + options = options || {}, options = $.extend({}, $.vakata.search.defaults, options), !1 !== options.fuzzy && (options.fuzzy = !0), pattern = options.caseSensitive ? pattern : pattern.toLowerCase(); + var matchmask, pattern_alphabet, match_bitapScore, search, MATCH_LOCATION = options.location, + MATCH_DISTANCE = options.distance, + MATCH_THRESHOLD = options.threshold, + patternLen = pattern.length; + return patternLen > 32 && (options.fuzzy = !1), options.fuzzy && (matchmask = 1 << patternLen - 1, pattern_alphabet = function() { + var mask = {}, + i = 0; + for (i = 0; i < patternLen; i++) mask[pattern.charAt(i)] = 0; + for (i = 0; i < patternLen; i++) mask[pattern.charAt(i)] |= 1 << patternLen - i - 1; + return mask + }(), match_bitapScore = function(e, x) { + var accuracy = e / patternLen, + proximity = Math.abs(MATCH_LOCATION - x); + return MATCH_DISTANCE ? accuracy + proximity / MATCH_DISTANCE : proximity ? 1 : accuracy + }), search = function(text) { + if (text = options.caseSensitive ? text : text.toLowerCase(), pattern === text || -1 !== text.indexOf(pattern)) return { + isMatch: !0, + score: 0 + }; + if (!options.fuzzy) return { + isMatch: !1, + score: 1 + }; + var i, j, binMin, binMid, lastRd, start, finish, rd, charMatch, textLen = text.length, + scoreThreshold = MATCH_THRESHOLD, + bestLoc = text.indexOf(pattern, MATCH_LOCATION), + binMax = patternLen + textLen, + score = 1, + locations = []; + for (-1 !== bestLoc && (scoreThreshold = Math.min(match_bitapScore(0, bestLoc), scoreThreshold), -1 !== (bestLoc = text.lastIndexOf(pattern, MATCH_LOCATION + patternLen)) && (scoreThreshold = Math.min(match_bitapScore(0, bestLoc), scoreThreshold))), bestLoc = -1, i = 0; i < patternLen; i++) { + for (binMin = 0, binMid = binMax; binMin < binMid;) match_bitapScore(i, MATCH_LOCATION + binMid) <= scoreThreshold ? binMin = binMid : binMax = binMid, binMid = Math.floor((binMax - binMin) / 2 + binMin); + for (binMax = binMid, start = Math.max(1, MATCH_LOCATION - binMid + 1), finish = Math.min(MATCH_LOCATION + binMid, textLen) + patternLen, rd = new Array(finish + 2), rd[finish + 1] = (1 << i) - 1, j = finish; j >= start; j--) + if (charMatch = pattern_alphabet[text.charAt(j - 1)], rd[j] = 0 === i ? (rd[j + 1] << 1 | 1) & charMatch : (rd[j + 1] << 1 | 1) & charMatch | (lastRd[j + 1] | lastRd[j]) << 1 | 1 | lastRd[j + 1], rd[j] & matchmask && (score = match_bitapScore(i, j - 1)) <= scoreThreshold) { + if (scoreThreshold = score, bestLoc = j - 1, locations.push(bestLoc), !(bestLoc > MATCH_LOCATION)) break; + start = Math.max(1, 2 * MATCH_LOCATION - bestLoc) + } if (match_bitapScore(i + 1, MATCH_LOCATION) > scoreThreshold) break; + lastRd = rd + } + return { + isMatch: bestLoc >= 0, + score: score + } + }, !0 === txt ? { + search: search + } : search(txt) + }, $.vakata.search.defaults = { + location: 0, + distance: 100, + threshold: .6, + fuzzy: !1, + caseSensitive: !1 + } + }($), $.jstree.defaults.sort = function(a, b) { + return this.get_text(a) > this.get_text(b) ? 1 : -1 + }, $.jstree.plugins.sort = function(options, parent) { + this.bind = function() { + parent.bind.call(this), this.element.on("model.jstree", $.proxy(function(e, data) { + this.sort(data.parent, !0) + }, this)).on("rename_node.jstree create_node.jstree", $.proxy(function(e, data) { + this.sort(data.parent || data.node.parent, !1), this.redraw_node(data.parent || data.node.parent, !0) + }, this)).on("move_node.jstree copy_node.jstree", $.proxy(function(e, data) { + this.sort(data.parent, !1), this.redraw_node(data.parent, !0) + }, this)) + }, this.sort = function(obj, deep) { + var i, j; + if ((obj = this.get_node(obj)) && obj.children && obj.children.length && (obj.children.sort($.proxy(this.settings.sort, this)), deep)) + for (i = 0, j = obj.children_d.length; i < j; i++) this.sort(obj.children_d[i], !1) + } + }; + var to = !1; + $.jstree.defaults.state = { + key: "jstree", + events: "changed.jstree open_node.jstree close_node.jstree check_node.jstree uncheck_node.jstree", + ttl: !1, + filter: !1 + }, $.jstree.plugins.state = function(options, parent) { + this.bind = function() { + parent.bind.call(this); + var bind = $.proxy(function() { + this.element.on(this.settings.state.events, $.proxy(function() { + to && clearTimeout(to), to = setTimeout($.proxy(function() { + this.save_state() + }, this), 100) + }, this)), this.trigger("state_ready") + }, this); + this.element.on("ready.jstree", $.proxy(function(e, data) { + this.element.one("restore_state.jstree", bind), this.restore_state() || bind() + }, this)) + }, this.save_state = function() { + var st = { + state: this.get_state(), + ttl: this.settings.state.ttl, + sec: +new Date + }; + $.vakata.storage.set(this.settings.state.key, JSON.stringify(st)) + }, this.restore_state = function() { + var k = $.vakata.storage.get(this.settings.state.key); + if (k) try { + k = JSON.parse(k) + } catch (ex) { + return !1 + } + return !(k && k.ttl && k.sec && +new Date - k.sec > k.ttl) && (k && k.state && (k = k.state), k && $.isFunction(this.settings.state.filter) && (k = this.settings.state.filter.call(this, k)), !!k && (this.element.one("set_state.jstree", function(e, data) { + data.instance.trigger("restore_state", { + state: $.extend(!0, {}, k) + }) + }), this.set_state(k), !0)) + }, this.clear_state = function() { + return $.vakata.storage.del(this.settings.state.key) + } + }, + function($, undefined) { + $.vakata.storage = { + set: function(key, val) { + return window.localStorage.setItem(key, val) + }, + get: function(key) { + return window.localStorage.getItem(key) + }, + del: function(key) { + return window.localStorage.removeItem(key) + } + } + }($), $.jstree.defaults.types = { + "#": {}, + default: {} + }, $.jstree.plugins.types = function(options, parent) { + this.init = function(el, options) { + var i, j; + if (options && options.types && options.types.default) + for (i in options.types) + if ("default" !== i && "#" !== i && options.types.hasOwnProperty(i)) + for (j in options.types.default) options.types.default.hasOwnProperty(j) && options.types[i][j] === undefined && (options.types[i][j] = options.types.default[j]); + parent.init.call(this, el, options), this._model.data["#"].type = "#" + }, this.refresh = function(skip_loading, forget_state) { + parent.refresh.call(this, skip_loading, forget_state), this._model.data["#"].type = "#" + }, this.bind = function() { + this.element.on("model.jstree", $.proxy(function(e, data) { + var i, j, m = this._model.data, + dpc = data.nodes, + t = this.settings.types, + c = "default"; + for (i = 0, j = dpc.length; i < j; i++) c = "default", m[dpc[i]].original && m[dpc[i]].original.type && t[m[dpc[i]].original.type] && (c = m[dpc[i]].original.type), m[dpc[i]].data && m[dpc[i]].data.jstree && m[dpc[i]].data.jstree.type && t[m[dpc[i]].data.jstree.type] && (c = m[dpc[i]].data.jstree.type), m[dpc[i]].type = c, !0 === m[dpc[i]].icon && t[c].icon !== undefined && (m[dpc[i]].icon = t[c].icon); + m["#"].type = "#" + }, this)), parent.bind.call(this) + }, this.get_json = function(obj, options, flat) { + var i, j, m = this._model.data, + opt = options ? $.extend(!0, {}, options, { + no_id: !1 + }) : {}, + tmp = parent.get_json.call(this, obj, opt, flat); + if (!1 === tmp) return !1; + if ($.isArray(tmp)) + for (i = 0, j = tmp.length; i < j; i++) tmp[i].type = tmp[i].id && m[tmp[i].id] && m[tmp[i].id].type ? m[tmp[i].id].type : "default", options && options.no_id && (delete tmp[i].id, tmp[i].li_attr && tmp[i].li_attr.id && delete tmp[i].li_attr.id, + tmp[i].a_attr && tmp[i].a_attr.id && delete tmp[i].a_attr.id); + else tmp.type = tmp.id && m[tmp.id] && m[tmp.id].type ? m[tmp.id].type : "default", options && options.no_id && (tmp = this._delete_ids(tmp)); + return tmp + }, this._delete_ids = function(tmp) { + if ($.isArray(tmp)) { + for (var i = 0, j = tmp.length; i < j; i++) tmp[i] = this._delete_ids(tmp[i]); + return tmp + } + return delete tmp.id, tmp.li_attr && tmp.li_attr.id && delete tmp.li_attr.id, tmp.a_attr && tmp.a_attr.id && delete tmp.a_attr.id, tmp.children && $.isArray(tmp.children) && (tmp.children = this._delete_ids(tmp.children)), tmp + }, this.check = function(chk, obj, par, pos, more) { + if (!1 === parent.check.call(this, chk, obj, par, pos, more)) return !1; + obj = obj && obj.id ? obj : this.get_node(obj), par = par && par.id ? par : this.get_node(par); + var tmp, d, i, j, m = obj && obj.id ? more && more.origin ? more.origin : $.jstree.reference(obj.id) : null; + switch (m = m && m._model && m._model.data ? m._model.data : null, chk) { + case "create_node": + case "move_node": + case "copy_node": + if ("move_node" !== chk || -1 === $.inArray(obj.id, par.children)) { + if (tmp = this.get_rules(par), tmp.max_children !== undefined && -1 !== tmp.max_children && tmp.max_children === par.children.length) return this._data.core.last_error = { + error: "check", + plugin: "types", + id: "types_01", + reason: "max_children prevents function: " + chk, + data: JSON.stringify({ + chk: chk, + pos: pos, + obj: !(!obj || !obj.id) && obj.id, + par: !(!par || !par.id) && par.id + }) + }, !1; + if (tmp.valid_children !== undefined && -1 !== tmp.valid_children && -1 === $.inArray(obj.type || "default", tmp.valid_children)) return this._data.core.last_error = { + error: "check", + plugin: "types", + id: "types_02", + reason: "valid_children prevents function: " + chk, + data: JSON.stringify({ + chk: chk, + pos: pos, + obj: !(!obj || !obj.id) && obj.id, + par: !(!par || !par.id) && par.id + }) + }, !1; + if (m && obj.children_d && obj.parents) { + for (d = 0, i = 0, j = obj.children_d.length; i < j; i++) d = Math.max(d, m[obj.children_d[i]].parents.length); + d = d - obj.parents.length + 1 + }(d <= 0 || d === undefined) && (d = 1); + do { + if (tmp.max_depth !== undefined && -1 !== tmp.max_depth && tmp.max_depth < d) return this._data.core.last_error = { + error: "check", + plugin: "types", + id: "types_03", + reason: "max_depth prevents function: " + chk, + data: JSON.stringify({ + chk: chk, + pos: pos, + obj: !(!obj || !obj.id) && obj.id, + par: !(!par || !par.id) && par.id + }) + }, !1; + par = this.get_node(par.parent), tmp = this.get_rules(par), d++ + } while (par) + } + } + return !0 + }, this.get_rules = function(obj) { + if (!(obj = this.get_node(obj))) return !1; + var tmp = this.get_type(obj, !0); + return tmp.max_depth === undefined && (tmp.max_depth = -1), tmp.max_children === undefined && (tmp.max_children = -1), tmp.valid_children === undefined && (tmp.valid_children = -1), tmp + }, this.get_type = function(obj, rules) { + return !!(obj = this.get_node(obj)) && (rules ? $.extend({ + type: obj.type + }, this.settings.types[obj.type]) : obj.type) + }, this.set_type = function(obj, type) { + var t, t1, t2, old_type, old_icon; + if ($.isArray(obj)) { + for (obj = obj.slice(), t1 = 0, t2 = obj.length; t1 < t2; t1++) this.set_type(obj[t1], type); + return !0 + } + return t = this.settings.types, obj = this.get_node(obj), !(!t[type] || !obj) && (old_type = obj.type, old_icon = this.get_icon(obj), obj.type = type, (!0 === old_icon || t[old_type] && t[old_type].icon !== undefined && old_icon === t[old_type].icon) && this.set_icon(obj, t[type].icon === undefined || t[type].icon), !0) + } + }, $.jstree.defaults.unique = { + case_sensitive: !1, + duplicate: function(name, counter) { + return name + " (" + counter + ")" + } + }, $.jstree.plugins.unique = function(options, parent) { + this.check = function(chk, obj, par, pos, more) { + if (!1 === parent.check.call(this, chk, obj, par, pos, more)) return !1; + if (obj = obj && obj.id ? obj : this.get_node(obj), !(par = par && par.id ? par : this.get_node(par)) || !par.children) return !0; + var i, j, n = "rename_node" === chk ? pos : obj.text, + c = [], + s = this.settings.unique.case_sensitive, + m = this._model.data; + for (i = 0, j = par.children.length; i < j; i++) c.push(s ? m[par.children[i]].text : m[par.children[i]].text.toLowerCase()); + switch (s || (n = n.toLowerCase()), chk) { + case "delete_node": + return !0; + case "rename_node": + return i = -1 === $.inArray(n, c) || obj.text && obj.text[s ? "toString" : "toLowerCase"]() === n, i || (this._data.core.last_error = { + error: "check", + plugin: "unique", + id: "unique_01", + reason: "Child with name " + n + " already exists. Preventing: " + chk, + data: JSON.stringify({ + chk: chk, + pos: pos, + obj: !(!obj || !obj.id) && obj.id, + par: !(!par || !par.id) && par.id + }) + }), i; + case "create_node": + return i = -1 === $.inArray(n, c), i || (this._data.core.last_error = { + error: "check", + plugin: "unique", + id: "unique_04", + reason: "Child with name " + n + " already exists. Preventing: " + chk, + data: JSON.stringify({ + chk: chk, + pos: pos, + obj: !(!obj || !obj.id) && obj.id, + par: !(!par || !par.id) && par.id + }) + }), i; + case "copy_node": + return i = -1 === $.inArray(n, c), i || (this._data.core.last_error = { + error: "check", + plugin: "unique", + id: "unique_02", + reason: "Child with name " + n + " already exists. Preventing: " + chk, + data: JSON.stringify({ + chk: chk, + pos: pos, + obj: !(!obj || !obj.id) && obj.id, + par: !(!par || !par.id) && par.id + }) + }), i; + case "move_node": + return i = obj.parent === par.id && (!more || !more.is_multi) || -1 === $.inArray(n, c), i || (this._data.core.last_error = { + error: "check", + plugin: "unique", + id: "unique_03", + reason: "Child with name " + n + " already exists. Preventing: " + chk, + data: JSON.stringify({ + chk: chk, + pos: pos, + obj: !(!obj || !obj.id) && obj.id, + par: !(!par || !par.id) && par.id + }) + }), i + } + return !0 + }, this.create_node = function(par, node, pos, callback, is_loaded) { + if (!node || node.text === undefined) { + if (null === par && (par = "#"), !(par = this.get_node(par))) return parent.create_node.call(this, par, node, pos, callback, is_loaded); + if (pos = pos === undefined ? "last" : pos, !pos.toString().match(/^(before|after)$/) && !is_loaded && !this.is_loaded(par)) return parent.create_node.call(this, par, node, pos, callback, is_loaded); + node || (node = {}); + var tmp, n, dpc, i, j, m = this._model.data, + s = this.settings.unique.case_sensitive, + cb = this.settings.unique.duplicate; + for (n = tmp = this.get_string("New node"), dpc = [], i = 0, j = par.children.length; i < j; i++) dpc.push(s ? m[par.children[i]].text : m[par.children[i]].text.toLowerCase()); + for (i = 1; - 1 !== $.inArray(s ? n : n.toLowerCase(), dpc);) n = cb.call(this, tmp, ++i).toString(); + node.text = n + } + return parent.create_node.call(this, par, node, pos, callback, is_loaded) + } + }; + var div = document.createElement("DIV"); + if (div.setAttribute("unselectable", "on"), div.setAttribute("role", "presentation"), div.className = "jstree-wholerow", div.innerHTML = " ", $.jstree.plugins.wholerow = function(options, parent) { + this.bind = function() { + parent.bind.call(this), this.element.on("ready.jstree set_state.jstree", $.proxy(function() { + this.hide_dots() + }, this)).on("init.jstree loading.jstree ready.jstree", $.proxy(function() { + this.get_container_ul().addClass("jstree-wholerow-ul") + }, this)).on("deselect_all.jstree", $.proxy(function(e, data) { + this.element.find(".jstree-wholerow-clicked").removeClass("jstree-wholerow-clicked") + }, this)).on("changed.jstree", $.proxy(function(e, data) { + this.element.find(".jstree-wholerow-clicked").removeClass("jstree-wholerow-clicked"); + var i, j, tmp = !1; + for (i = 0, j = data.selected.length; i < j; i++)(tmp = this.get_node(data.selected[i], !0)) && tmp.length && tmp.children(".jstree-wholerow").addClass("jstree-wholerow-clicked") + }, this)).on("open_node.jstree", $.proxy(function(e, data) { + this.get_node(data.node, !0).find(".jstree-clicked").parent().children(".jstree-wholerow").addClass("jstree-wholerow-clicked") + }, this)).on("hover_node.jstree dehover_node.jstree", $.proxy(function(e, data) { + "hover_node" === e.type && this.is_disabled(data.node) || this.get_node(data.node, !0).children(".jstree-wholerow")["hover_node" === e.type ? "addClass" : "removeClass"]("jstree-wholerow-hovered") + }, this)).on("contextmenu.jstree", ".jstree-wholerow", $.proxy(function(e) { + e.preventDefault(); + var tmp = $.Event("contextmenu", { + metaKey: e.metaKey, + ctrlKey: e.ctrlKey, + altKey: e.altKey, + shiftKey: e.shiftKey, + pageX: e.pageX, + pageY: e.pageY + }); + $(e.currentTarget).closest(".jstree-node").children(".jstree-anchor").first().trigger(tmp) + }, this)).on("click.jstree", ".jstree-wholerow", function(e) { + e.stopImmediatePropagation(); + var tmp = $.Event("click", { + metaKey: e.metaKey, + ctrlKey: e.ctrlKey, + altKey: e.altKey, + shiftKey: e.shiftKey + }); + $(e.currentTarget).closest(".jstree-node").children(".jstree-anchor").first().trigger(tmp).focus() + }).on("click.jstree", ".jstree-leaf > .jstree-ocl", $.proxy(function(e) { + e.stopImmediatePropagation(); + var tmp = $.Event("click", { + metaKey: e.metaKey, + ctrlKey: e.ctrlKey, + altKey: e.altKey, + shiftKey: e.shiftKey + }); + $(e.currentTarget).closest(".jstree-node").children(".jstree-anchor").first().trigger(tmp).focus() + }, this)).on("mouseover.jstree", ".jstree-wholerow, .jstree-icon", $.proxy(function(e) { + return e.stopImmediatePropagation(), this.is_disabled(e.currentTarget) || this.hover_node(e.currentTarget), !1 + }, this)).on("mouseleave.jstree", ".jstree-node", $.proxy(function(e) { + this.dehover_node(e.currentTarget) + }, this)) + }, this.teardown = function() { + this.settings.wholerow && this.element.find(".jstree-wholerow").remove(), parent.teardown.call(this) + }, this.redraw_node = function(obj, deep, callback, force_render) { + if (obj = parent.redraw_node.apply(this, arguments)) { + var tmp = div.cloneNode(!0); - 1 !== $.inArray(obj.id, this._data.core.selected) && (tmp.className += " jstree-wholerow-clicked"), this._data.core.focused && this._data.core.focused === obj.id && (tmp.className += " jstree-wholerow-hovered"), obj.insertBefore(tmp, obj.childNodes[0]) + } + return obj + } + }, document.registerElement && Object && Object.create) { + var proto = Object.create(HTMLElement.prototype); + proto.createdCallback = function() { + var i, c = { + core: {}, + plugins: [] + }; + for (i in $.jstree.plugins) $.jstree.plugins.hasOwnProperty(i) && this.attributes[i] && (c.plugins.push(i), this.getAttribute(i) && JSON.parse(this.getAttribute(i)) && (c[i] = JSON.parse(this.getAttribute(i)))); + for (i in $.jstree.defaults.core) $.jstree.defaults.core.hasOwnProperty(i) && this.attributes[i] && (c.core[i] = JSON.parse(this.getAttribute(i)) || this.getAttribute(i)); + $(this).jstree(c) + }; + try { + document.registerElement("vakata-jstree", { + prototype: proto + }) + } catch (ignore) {} + } + } +}); \ No newline at end of file