<script>var io=null;</script>
<%
data.name='SHINOBI_'+data.ke+'_'+data.id;
if(config.ssl&&config.ssl.port&&data.protocol==='https'){
    data.port=config.ssl.port
}else{
    data.port=config.port
}
if(!data.port||data.port===''||data.port==80||data.port==443){data.url=baseUrl}else{data.url=baseUrl+':'+data.port}
if(data.addon || data.addon.indexOf('relative')>-1){
    data.url = ''
}else if(config.baseURL){
    data.url = config.baseURL
}
if(data.url.charAt(data.url.length - 1) !== '/'){
    data.url += '/'
}
%>
<script src="<%=data.url%>libs/js/socket.io.js"></script>
<script src="<%=data.url%>libs/js/poseidon.js"></script>
<script src="<%=data.url%>libs/js/hls.min.js"></script>
<script src="<%=data.url%>libs/js/flv.min.js"></script>
<script src="<%=data.url%>libs/js/libde265.min.js"></script>
<% if(data.addon){
    var ar={}
    decodeURI(data.addon).split('|').forEach(function(v){
        if(v.indexOf('=')>-1){
            v=v.split('=');
            ar[v[0]]=v[1];
        }
    })
    if(!ar.width){ar.width=640;}
    if(!ar.height){ar.height=480;}
    if(data.addon.indexOf('jquery')>-1){ %>
<script src="<%=data.url%>libs/js/jquery.min.js"></script>
<% };
if(data.addon.indexOf('gui')>-1){ %>
<style>
    body {position:relative;}
    .shinobi_stream{position:absolute;width:100%;height:100%;top:0;left:0;}
    .shinobi_hud{position:absolute;width:100%;height:100%;top:0;left:0;opacity:0;transition:0.2s}
    .shinobi_hud:hover{opacity:1}
    .shinobi_hud .shinobi_viewers{position:absolute;top:5px;left:5px;}
    .shinobi_hud .shinobi_viewers{
        display: inline-block;
        min-width: 10px;
        padding: 3px 7px;
        font-size: 12px;
        font-weight: 700;
        line-height: 1;
        color: #fff;
        text-align: center;
        white-space: nowrap;
        vertical-align: middle;
        background-color: #777;
        border-radius: 10px;
        font-family: sans-serif;
    }
    iframe.stream-element{border:0;}
/* All-CSS Toggle Switch (Checkbox Hack) by Marcus Burnette - https://codepen.io/mburnette/pen/LxNxNg */
    .shinobi_ws_http_toggle {
        width: 50px;
        height: 20px;
        position: absolute;
        bottom: 10px;
        left: 10px;
    }
    .shinobi_ws_http_toggle input[type=checkbox]{
        height: 0;
        width: 0;
        visibility: hidden;
    }

    .shinobi_ws_http_toggle label {
        cursor: pointer;
        text-indent: -9999px;
        width: 100px;
        height: 20px;
        background: grey;
        display: block;
        border-radius: 100px;
        position: relative;
    }

    .shinobi_ws_http_toggle label:after {
        content: '';
        position: absolute;
        top: 5px;
        left: 5px;
        width: 10px;
        height: 10px;
        background: #fff;
        border-radius: 90px;
        transition: 0.3s;
    }

    .shinobi_ws_http_toggle input:checked + label {
        background: #00118c;
    }

    .shinobi_ws_http_toggle input:checked + label:after {
        left: calc(100% - 5px);
        transform: translateX(-100%);
    }

    .shinobi_ws_http_toggle label:active:after {
        width: 10px;
    }
</style>
<% };
if(data.addon.indexOf('fullscreen')>-1){ %>
<style>
    body,html{overflow: hidden;height:100%}
    *{margin:0;padding:0;border:0}
    .stream-element,.shinobi_stream{position:absolute;top:0;left:0;height:100%}
    .shinobi_stream video{object-fit: fill}
</style>
<script>
$(window).resize(function(){
    $('.stream-element').attr('width',$('body').width())
    $('.stream-element').attr('height',$('body').height())
})
</script>
<% } %>
<% }else{
    //no addon set, do defaults
    var ar={};
    ar.width=640;
    ar.height=480;
} %>
<script>
$(document).ready(function(){
    $('#<%= data.name %> canvas').attr('width',<%=ar.width%>).attr('height',<%=ar.height%>)
})
</script>
<div class="shinobi_stream" id="<%= data.name %>">

    <% switch(mon.details.stream_type){
        case'jpeg':
            %><img class="stream-element"><%
        break;
        case'flv':case'hls':case'mp4':
            %><video class="stream-element" autoplay></video><%
        break;
        case'mjpeg':
            %><iframe class="stream-element"></iframe><%
        break;
        default:
            %><canvas class="stream-element"></canvas><%
        break;
    } %>


<% if(data.addon&&data.addon.indexOf('gui')>-1){ %>
    <div class="shinobi_hud">
        <div class="shinobi_viewers" title="Current number of viewers"></div>
        <div class="shinobi_ws_http_toggle" style="display:none">
            <input type="checkbox" id="shinobi_ws_http_toggle" <% if(mon.details.stream_flv_type === 'ws'){ %>checked<% } %> /><label for="shinobi_ws_http_toggle">WebSocket</label>
        </div>
    </div>
<% } %>
</div>
<script>
    var SHINOBI_TIMER=setInterval(function(){
        if(io){
            clearInterval(SHINOBI_TIMER);delete(SHINOBI_TIMER);
            if(!$.shinobi){
                $.shinobi={}
            };
            if(!$.shinobi.mon){
                $.shinobi.mon={}
            };
            $.shinobi.init=function(d){
                  if($.shinobi.mon[d.id].Base64 && $.shinobi.mon[d.id].Base64.connected){
                      $.shinobi.mon[d.id].Base64.disconnect()
                  }
                  if($.shinobi.mon[d.id].Poseidon){
                      $.shinobi.mon[d.id].Poseidon.stop()
                  }
                  if ($.shinobi.mon[d.id].h265Player) {
                      $.shinobi.mon[d.id].h265Player.stop()
                  }
                  if($.shinobi.mon[d.id].h265Socket && $.shinobi.mon[d.id].h265Socket.connected){
                      $.shinobi.mon[d.id].h265Socket.disconnect()
                  }
                  if($.shinobi.mon[d.id].h265HttpStream && $.shinobi.mon[d.id].abort){
                      $.shinobi.mon[d.id].h265HttpStream.abort()
                  }
                  if($.shinobi.mon[d.id].flv){
                      $.shinobi.mon[d.id].flv.destroy()
                  }
                  if($.shinobi.mon[d.id].hls){
                      $.shinobi.mon[d.id].hls.destroy()
                  }
                  clearInterval($.shinobi.mon[d.id].jpegInterval);
                  switch($.shinobi.mon[d.id].details.stream_type){
                    case'b64':
                        $.shinobi.mon[d.id].Base64 = io('<%=data.url%>',{transports: ['websocket'], forceNew: false})
                        var ws = $.shinobi.mon[d.id].Base64
                        ws.on('diconnect',function(){
                            console.log('Base64 Stream Disconnected')
                        })
                        ws.on('connect',function(){
                            ws.emit('Base64',{
                                auth:'<%=data.auth%>',
                                ke:d.ke,
                                uid:'<%=data.uid%>',
                                id:d.id,
                                url: '<%=data.url%>'
                            })
                            if(!$.shinobi.mon[d.id].ctx||$.shinobi.mon[d.id].ctx.length===0){
                                $.shinobi.mon[d.id].ctx = $('#SHINOBI_'+d.ke+'_'+d.id+' .stream-element')
                            }
                            var ctx = $.shinobi.mon[d.id].ctx[0]
                            $.shinobi.mon[d.id].image = new Image()
                            var image = $.shinobi.mon[d.id].image
                            image.onload = function() {
                                $.shinobi.mon[d.id].imageLoading = false
                                d.x = 0
                                d.y = 0
        //                        d.ratio = Math.min(ctx.width/image.width,ctx.height/image.height)
        //                        d.height = image.height * d.ratio
        //                        d.width = image.width * d.ratio
        //                        if(d.width < ctx.width){
        //                            d.x = (ctx.width / 2) - (d.width / 2)
        //                        }
        //                        if(d.height < ctx.height){
        //                            d.y = (ctx.height / 2) - (d.height / 2)
        //                        }
        //                        ctx.getContext("2d").drawImage(image,d.x,d.y,d.width,d.height)
                                ctx.getContext("2d").drawImage(image,d.x,d.y,ctx.width,ctx.height)
                                URL.revokeObjectURL($.shinobi.mon[d.id].imageUrl)
                            }
                            ws.on('data',function(imageData){
                                try{
                                    if($.shinobi.mon[d.id].imageLoading === true)return console.log('drop');
//                                    var base64Frame = 'data:image/jpeg;base64,'+$.ccio.base64ArrayBuffer(imageData)
                                    $.shinobi.mon[d.id].imageLoading = true
//                                    $.shinobi.mon[d.id].image.src = base64Frame
                                    var arrayBufferView = new Uint8Array(imageData);
                                    var blob = new Blob( [ arrayBufferView ], { type: "image/jpeg" } );
                                    $.shinobi.mon[d.id].imageUrl = URL.createObjectURL( blob );
                                    $.shinobi.mon[d.id].image.src = $.shinobi.mon[d.id].imageUrl
                                    $.shinobi.mon[d.id].last_frame = 'data:image/jpeg;base64,'+$.ccio.base64ArrayBuffer(imageData)
                                }catch(er){
                                    console.log(er)
                                }
                            })
                        })
                    break;
                    case'mp4':
                        var stream = $('#SHINOBI_'+d.ke+'_'+d.id+' .stream-element');
                        if($.shinobi.mon[d.id].details.stream_flv_type==='ws'){
                            var createPoseidon = function(){
                                var onPoseidonError = function(){
                                    // setTimeout(function(){
                                    //     $.ccio.cx({f:'monitor',ff:'watch_on',id:d.id},user)
                                    // },2000)
                                }
                                $.shinobi.mon[d.id].Poseidon = new Poseidon({
                                    video: stream[0],
                                    auth_token:'<%=data.auth%>',
                                    ke:d.ke,
                                    uid:'<%=data.uid%>',
                                    id:d.id,
                                    url: '<%=data.url%>',
                                    onError : onPoseidonError
                                });
                                $.shinobi.mon[d.id].Poseidon.start();
                                $.shinobi.mon[d.id].Poseidon._socket.on('data',function(res){
                                    console.log(res)
                                })
                            }
                            try{
                                createPoseidon()
                            }catch(err){
                                console.log(err)
                                setTimeout(function(){
                                    createPoseidon()
                                },3000)
                            }
                        }else{
                            stream.attr('src','<%=data.url%><%=data.auth%>/mp4/'+d.ke+'/'+d.id+'/s.mp4')
                        }
                    break;
                    case'h265':
                        var player = $.shinobi.mon[d.id].h265Player
                        var video = $('#SHINOBI_'+d.ke+'_'+d.id+' .stream-element')[0]
                        player = new libde265.RawPlayer(video)
                        player.set_status_callback(function(msg, fps) {
                        })
                        player.launch()
                        if($.shinobi.mon[d.id].details.stream_flv_type==='ws'){
                          $.shinobi.mon[d.id].h265Socket = io(url,{transports: ['websocket'], forceNew: false})
                          var ws = $.shinobi.mon[d.id].h265Socket
                          ws.on('diconnect',function(){
                              console.log('h265Socket Stream Disconnected')
                          })
                          ws.on('connect',function(){
                              ws.emit('h265',{
                                auth:'<%=data.auth%>',
                                ke:d.ke,
                                uid:'<%=data.uid%>',
                                id:d.id,
                                url: '<%=data.url%>'
  //                                channel: channel
                              })
                              ws.on('data',function(imageData){
                                  player._handle_onChunk(imageData)
                              })
                          })
                        }else{
                          $.shinobi.mon[d.id].h265HttpStream = player.createHttpStream('<%=data.url%><%=data.auth%>/h265/'+d.ke+'/'+d.id+'/s.hevc')
                        }
                    break;
                    case'flv':
                        if (flvjs.isSupported()) {
                            var options = {};
//                            if($.shinobi.mon[d.id].details.stream_flv_type==='ws'){
//                                if($.shinobi.mon[d.id].details.stream_flv_maxLatency&&$.shinobi.mon[d.id].details.stream_flv_maxLatency!==''){
//                                    $.shinobi.mon[d.id].details.stream_flv_maxLatency = parseInt($.shinobi.mon[d.id].details.stream_flv_maxLatency)
//                                }else{
//                                    $.shinobi.mon[d.id].details.stream_flv_maxLatency = 20000;
//                                }
//                                options = {
//                                    type: 'flv',
//                                    isLive: true,
//                                    auth_token:'<%=data.auth%>',
//                                    ke:d.ke,
//                                    uid:'<%=data.uid%>',
//                                    id:d.id,
//                                    maxLatency:$.shinobi.mon[d.id].details.stream_flv_maxLatency,
//                                    hasAudio:false,
//                                    url: '<%=data.url%>'
//                                }
//                            }else{
                                options = {
                                    type: 'flv',
                                    isLive: true,
                                    url: '<%=data.url%><%=data.auth%>/flv/'+d.ke+'/'+d.id+'/s.flv'
                                }
//                            }
                            $.shinobi.mon[d.id].flv = flvjs.createPlayer(options);
                            $.shinobi.mon[d.id].flv.attachMediaElement($('#SHINOBI_'+d.ke+'_'+d.id+' .stream-element')[0]);
                            $.shinobi.mon[d.id].flv.on('error',function(err){
                                console.log(err)
                            });
                            $.shinobi.mon[d.id].flv.load();
                            $.shinobi.mon[d.id].flv.play();
                        }else{
                            alert({title:'Stream cannot be started',text:'FLV.js is not supported on this browser. Try another stream type.',type:'error'})
                        }
                    break;
                    case'jpeg':
                        d.mon=$.shinobi.mon[d.id]
                        k=d.mon.details;
                        k.jpegInterval=parseFloat(k.jpegInterval);
                        if(!k.jpegInterval||k.jpegInterval===''||isNaN(k.jpegInterval)){k.jpegInterval=1}
                        if(!$.shinobi.mon[d.id].jpegInterval){
                            clearInterval($.shinobi.mon[d.id].jpegInterval);
                            $.shinobi.mon[d.id].jpegInterval=setInterval(function(){
                                $('#SHINOBI_'+d.ke+'_'+d.id+' .stream-element').attr('src','<%=data.url%><%=data.auth%>/jpeg/'+d.mon.ke+'/'+d.mon.mid+'/s.jpg?time='+(new Date()).getTime())
                            },1000/k.jpegInterval);
                        }
                    break;
                    case'hls':
                    var video = $('#SHINOBI_'+d.ke+'_'+d.id+' .stream-element')[0];
                    d.url='<%=data.url%><%=data.auth%>/hls/'+d.ke+'/'+d.id+'/s.m3u8';
                    if (navigator.userAgent.match(/(iPod|iPhone|iPad)/)||(navigator.userAgent.match(/(Safari)/)&&!navigator.userAgent.match('Chrome'))) {
                        video.src=d.url;
                        video.play();
                    }else{
                        $.shinobi.mon[d.id].hls = new Hls();
                        $.shinobi.mon[d.id].hls.loadSource(d.url);
                        $.shinobi.mon[d.id].hls.attachMedia(video);
                        $.shinobi.mon[d.id].hls.on(Hls.Events.MANIFEST_PARSED,function() {
                          video.play();
                        });
                    }
                    break;
                    case'mjpeg':
                        $('#SHINOBI_'+d.ke+'_'+d.id+' .stream-element').attr('src','<%=data.url%><%=data.auth%>/mjpeg/'+d.ke+'/'+d.id+'?full=true')
                    break;
                }
            }
            $.shinobi.mon['<%=data.id%>']=<%- JSON.stringify(mon) %>;
            if(!$.shinobi.callback){$.shinobi.callback=function(){}}
            if(!$.shinobi.ws||$.shinobi.ws.connected===false){
                $.shinobi.ws=io('<%=data.url%>');
                $.shinobi.ws.on('f',function (d){
                if(d.viewers){
                    $('#SHINOBI_'+d.ke+'_'+d.id+' .shinobi_viewers').html(d.viewers);
                }
                switch(d.f){
                    case'monitor_frame':
                        var image = new Image();
                        var ctx = $('#SHINOBI_'+d.ke+'_'+d.id+' canvas')[0];
                        image.onload = function() {
                            ctx.getContext("2d").drawImage(image,0,0,ctx.width,ctx.height);
                            delete(d.frame);
                            delete(image);
                        };
                        image.src='data:image/jpeg;base64,'+d.frame
                    break;
                    case'monitor_watch_off':case'monitor_watch_on':
                        $('#SHINOBI_'+d.ke+'_'+d.id+' .shinobi_viewers').html(d.viewers)
                        $.shinobi.init(d)
                    break;
                    case'monitor_edit':
                        if(!d.id){d.id=d.mon.mid;}
                        if($.shinobi.mon[d.id]){
                            clearInterval($.shinobi.mon[d.id].jpegInterval);
                        }
                        d.e=$('#SHINOBI_'+d.ke+'_'+d.id+'');
                        d.e.find('.stream-element').remove();
                        d.tmp='';
                        switch(d.mon.details.stream_type){
                            case'hls':
                                d.tmp+='<video class="stream-element" controls autoplay></video>';
                            break;
                            case'mjpeg':
                                d.tmp+='<iframe class="stream-element"></iframe>';
                            break;
                            case'jpeg'://base64
                                d.tmp+='<img class="stream-element">';
                            break;
                            default://base64
                                d.tmp+='<canvas class="stream-element"></canvas>';
                            break;
                        }
                        d.e.append(d.tmp).find('.stream-element').resize();
                        $(window).resize();
//                        d.mon.details=JSON.stringify(d.mon.details);
                        d.mon.id = d.mon.mid
                        $.shinobi.mon[d.id] = d.mon;
                        $.shinobi.init(d.mon);
                    break;
                  }
                    $.shinobi.callback()
                });
            };
            $.shinobi.ws.emit('e',{f:'init',auth:'<%=data.auth%>',id:'<%=data.id%>',ke:'<%=data.ke%>'})
            $(window).resize();
        }
    },1000);
    //websocket / http toggle
    $('#shinobi_ws_http_toggle').change(function(){
        var monitor = $.shinobi.mon['<%=data.id%>'];
        var parent = $(this).parents('.shinobi_ws_http_toggle')
        var label = parent.find('label')
        if(monitor.details.stream_flv_type !== 'ws'){
            label.text('WebSocket')
            monitor.details.stream_flv_type = 'ws'
        }else{
            label.text('HTTP')
            monitor.details.stream_flv_type = 'http'
        }
        monitor.id = monitor.mid
        $.shinobi.init(monitor);
    })
    $('.shinobi_ws_http_toggle').show()
</script>
