10 lines
12 KiB
JavaScript
10 lines
12 KiB
JavaScript
/*
|
|
* noVNC: HTML5 VNC client
|
|
* Copyright (C) 2012 Joel Martin
|
|
* Copyright (C) 2015 Samuel Mannehed for Cendio AB
|
|
* Licensed under MPL 2.0 (see LICENSE.txt)
|
|
*
|
|
* See README.md for usage and integration instructions.
|
|
*/
|
|
|
|
var Display;!function(){"use strict";var t=!1;try{new ImageData(new Uint8ClampedArray(1),1,1),t=!0}catch(t){}Display=function(t){if(this._drawCtx=null,this._c_forceCanvas=!1,this._renderQ=[],this._fb_width=0,this._fb_height=0,this._maxWidth=0,this._maxHeight=0,this._viewportLoc={x:0,y:0,w:0,h:0},this._cleanRect={x1:0,y1:0,x2:-1,y2:-1},this._prevDrawStyle="",this._tile=null,this._tile16x16=null,this._tile_x=0,this._tile_y=0,Util.set_defaults(this,t,{true_color:!0,colourMap:[],scale:1,viewport:!1,render_mode:""}),Util.Debug(">> Display.constructor"),!this._target)throw new Error("Target must be set");if("string"==typeof this._target)throw new Error("target must be a DOM element");if(!this._target.getContext)throw new Error("no getContext method");if(this._drawCtx||(this._drawCtx=this._target.getContext("2d")),Util.Debug("User Agent: "+navigator.userAgent),Util.Engine.gecko&&Util.Debug("Browser: gecko "+Util.Engine.gecko),Util.Engine.webkit&&Util.Debug("Browser: webkit "+Util.Engine.webkit),Util.Engine.trident&&Util.Debug("Browser: trident "+Util.Engine.trident),Util.Engine.presto&&Util.Debug("Browser: presto "+Util.Engine.presto),this.clear(),!("createImageData"in this._drawCtx))throw new Error("Canvas does not support createImageData");this._render_mode="canvas rendering",null===this._prefer_js&&(Util.Info("Prefering javascript operations"),this._prefer_js=!0),(this._cursor_uri||null===this._cursor_uri||void 0===this._cursor_uri)&&(this._cursor_uri=Util.browserSupportsCursorURIs()),Util.Debug("<< Display.constructor")},Display.prototype={viewportChangePos:function(t,i){var e=this._viewportLoc;t=Math.floor(t),i=Math.floor(i),this._viewport||(t=-e.w,i=-e.h);var h=e.x+e.w-1,r=e.y+e.h-1;if(t<0&&e.x+t<0&&(t=-e.x),h+t>=this._fb_width&&(t-=h+t-this._fb_width+1),e.y+i<0&&(i=-e.y),r+i>=this._fb_height&&(i-=r+i-this._fb_height+1),0!==t||0!==i){Util.Debug("viewportChange deltaX: "+t+", deltaY: "+i),e.x+=t,h+=t,e.y+=i,r+=i;var s=this._cleanRect;e.x>s.x1&&(s.x1=e.x),h<s.x2&&(s.x2=h),e.y>s.y1&&(s.y1=e.y),r<s.y2&&(s.y2=r);var a,o;t<0?(a=0,o=-t):(a=e.w-t,o=t);var _,n;i<0?(_=0,n=-i):(_=e.h-i,n=i);var l=this._drawCtx.fillStyle,g=this._target;this._drawCtx.fillStyle="rgb(255,255,255)",this._drawCtx.mozImageSmoothingEnabled?this._drawCtx.mozImageSmoothingEnabled=!1:this._drawCtx.webkitImageSmoothingEnabled?this._drawCtx.webkitImageSmoothingEnabled=!1:this._drawCtx.msImageSmoothingEnabled?this._drawCtx.msImageSmoothingEnabled=!1:this._drawCtx.imageSmoothingEnabled&&(this._drawCtx.imageSmoothingEnabled=!1),this._drawCtx.drawImage(g,0,0,e.w,e.h,-t,-i,e.w,e.h),0!==t&&this._drawCtx.fillRect(a,0,o,e.h),0!==i&&this._drawCtx.fillRect(0,_,e.w,n),this._drawCtx.fillStyle=l}},viewportChangeSize:function(t,i){void 0!==t&&void 0!==i||(Util.Debug("Setting viewport to full display region"),t=this._fb_width,i=this._fb_height);var e=this._viewportLoc;if(e.w!==t||e.h!==i){this._viewport&&(0!==this._maxWidth&&t>this._maxWidth&&(t=this._maxWidth),0!==this._maxHeight&&i>this._maxHeight&&(i=this._maxHeight));var h=this._cleanRect;t<e.w&&h.x2>e.x+t-1&&(h.x2=e.x+t-1),i<e.h&&h.y2>e.y+i-1&&(h.y2=e.y+i-1),e.w=t,e.h=i;var r=this._target;if(r.width!==t||r.height!==i){var s=null;if(e.w>0&&e.h>0&&r.width>0&&r.height>0){var a=r.width<e.w?r.width:e.w,o=r.height<e.h?r.height:e.h;s=this._drawCtx.getImageData(0,0,a,o)}r.width!==t&&(r.width=t,r.style.width=t+"px"),r.height!==i&&(r.height=i,r.style.height=i+"px"),s&&this._drawCtx.putImageData(s,0,0)}}},getCleanDirtyReset:function(){var t=this._viewportLoc,i=this._cleanRect,e={x:i.x1,y:i.y1,w:i.x2-i.x1+1,h:i.y2-i.y1+1},h=[];if(i.x1>=i.x2||i.y1>=i.y2)h.push({x:t.x,y:t.y,w:t.w,h:t.h});else{var r=t.x+t.w-1,s=t.y+t.h-1;t.x<i.x1&&h.push({x:t.x,y:t.y,w:i.x1-t.x+1,h:t.h}),r>i.x2&&h.push({x:i.x2+1,y:t.y,w:r-i.x2,h:t.h}),t.y<i.y1&&h.push({x:i.x1,y:t.y,w:i.x2-i.x1+1,h:i.y1-t.y}),s>i.y2&&h.push({x:i.x1,y:i.y2+1,w:i.x2-i.x1+1,h:s-i.y2})}return this._cleanRect={x1:t.x,y1:t.y,x2:t.x+t.w-1,y2:t.y+t.h-1},{cleanBox:e,dirtyBoxes:h}},absX:function(t){return t+this._viewportLoc.x},absY:function(t){return t+this._viewportLoc.y},resize:function(t,i){this._prevDrawStyle="",this._fb_width=t,this._fb_height=i,this._rescale(this._scale),this.viewportChangeSize()},clear:function(){this._logo?(this.resize(this._logo.width,this._logo.height),this.blitStringImage(this._logo.data,0,0)):(6===Util.Engine.trident&&this._drawCtx.clearRect(0,0,this._viewportLoc.w,this._viewportLoc.h),this.resize(240,20),this._drawCtx.clearRect(0,0,this._viewportLoc.w,this._viewportLoc.h)),this._renderQ=[]},fillRect:function(t,i,e,h,r,s){0===this._renderQ.length||s?(this._setFillColor(r),this._drawCtx.fillRect(t-this._viewportLoc.x,i-this._viewportLoc.y,e,h)):this.renderQ_push({type:"fill",x:t,y:i,width:e,height:h,color:r})},copyImage:function(t,i,e,h,r,s,a){if(0===this._renderQ.length||a){var o=t-this._viewportLoc.x,_=i-this._viewportLoc.y,n=e-this._viewportLoc.x,l=h-this._viewportLoc.y;this._drawCtx.drawImage(this._target,o,_,r,s,n,l,r,s)}else this.renderQ_push({type:"copy",old_x:t,old_y:i,x:e,y:h,width:r,height:s})},startTile:function(t,i,e,h,r){if(this._tile_x=t,this._tile_y=i,this._tile=16===e&&16===h?this._tile16x16:this._drawCtx.createImageData(e,h),this._prefer_js){var s;s=this._true_color?r:this._colourMap[r[0]];for(var a=s[2],o=s[1],_=s[0],n=this._tile.data,l=0;l<e*h*4;l+=4)n[l]=a,n[l+1]=o,n[l+2]=_,n[l+3]=255}else this.fillRect(t,i,e,h,r,!0)},subTile:function(t,i,e,h,r){if(this._prefer_js){var s;s=this._true_color?r:this._colourMap[r[0]];for(var a=s[2],o=s[1],_=s[0],n=t+e,l=i+h,g=this._tile.data,w=this._tile.width,c=i;c<l;c++)for(var u=t;u<n;u++){var d=4*(u+c*w);g[d]=a,g[d+1]=o,g[d+2]=_,g[d+3]=255}}else this.fillRect(this._tile_x+t,this._tile_y+i,e,h,r,!0)},finishTile:function(){this._prefer_js&&this._drawCtx.putImageData(this._tile,this._tile_x-this._viewportLoc.x,this._tile_y-this._viewportLoc.y)},blitImage:function(t,i,e,h,r,s,a){if(0===this._renderQ.length||a)this._true_color?this._bgrxImageData(t,i,this._viewportLoc.x,this._viewportLoc.y,e,h,r,s):this._cmapImageData(t,i,this._viewportLoc.x,this._viewportLoc.y,e,h,r,s);else{var o=new Uint8Array(e*h*4);o.set(new Uint8Array(r.buffer,0,o.length)),this.renderQ_push({type:"blit",data:o,x:t,y:i,width:e,height:h})}},blitRgbImage:function(t,i,e,h,r,s,a){if(0===this._renderQ.length||a)this._true_color?this._rgbImageData(t,i,this._viewportLoc.x,this._viewportLoc.y,e,h,r,s):this._cmapImageData(t,i,this._viewportLoc.x,this._viewportLoc.y,e,h,r,s);else{var o=new Uint8Array(e*h*4);o.set(new Uint8Array(r.buffer,0,o.length)),this.renderQ_push({type:"blitRgb",data:o,x:t,y:i,width:e,height:h})}},blitRgbxImage:function(t,i,e,h,r,s,a){if(0===this._renderQ.length||a)this._rgbxImageData(t,i,this._viewportLoc.x,this._viewportLoc.y,e,h,r,s);else{var o=new Uint8Array(e*h*4);o.set(new Uint8Array(r.buffer,0,o.length)),this.renderQ_push({type:"blitRgbx",data:o,x:t,y:i,width:e,height:h})}},blitStringImage:function(t,i,e){var h=new Image;return h.onload=function(){this._drawCtx.drawImage(h,i-this._viewportLoc.x,e-this._viewportLoc.y)}.bind(this),h.src=t,h},drawImage:function(t,i,e){this._drawCtx.drawImage(t,i-this._viewportLoc.x,e-this._viewportLoc.y)},renderQ_push:function(t){this._renderQ.push(t),1===this._renderQ.length&&this._scan_renderQ()},changeCursor:function(t,i,e,h,r,s){if(!1===this._cursor_uri)return void Util.Warn("changeCursor called but no cursor data URI support");this._true_color?Display.changeCursor(this._target,t,i,e,h,r,s):Display.changeCursor(this._target,t,i,e,h,r,s,this._colourMap)},defaultCursor:function(){this._target.style.cursor="default"},disableLocalCursor:function(){this._target.style.cursor="none"},clippingDisplay:function(){var t=this._viewportLoc,i=this._fb_width>t.w||this._fb_height>t.h,e=0!==this._maxWidth&&0!==this._maxHeight,h=!1;return e&&(h=t.w>this._maxWidth||t.h>this._maxHeight),i||e&&h},get_context:function(){return this._drawCtx},set_scale:function(t){this._rescale(t)},set_width:function(t){this._fb_width=t},get_width:function(){return this._fb_width},set_height:function(t){this._fb_height=t},get_height:function(){return this._fb_height},autoscale:function(t,i,e){var h,r=t/i,s=this._fb_width/this._fb_height;h=s>=r?t/this._fb_width:i/this._fb_height;var a,o;return h>1&&e?(a=this._fb_width,o=this._fb_height,h=1):s>=r?(a=t,o=Math.round(t/s)):(a=Math.round(i*s),o=i),this._target.style.width=a+"px",this._target.style.height=o+"px",this._scale=h,h},_rescale:function(t){this._scale=t;var i,e;this._viewport&&0!==this._maxWidth&&0!==this._maxHeight?(i=Math.min(this._fb_width,this._maxWidth),e=Math.min(this._fb_height,this._maxHeight)):(i=this._fb_width,e=this._fb_height),this._target.style.width=Math.round(t*i)+"px",this._target.style.height=Math.round(t*e)+"px"},_setFillColor:function(t){var i;i=this._true_color?t:this._colourMap[t];var e="rgb("+i[2]+","+i[1]+","+i[0]+")";e!==this._prevDrawStyle&&(this._drawCtx.fillStyle=e,this._prevDrawStyle=e)},_rgbImageData:function(t,i,e,h,r,s,a,o){for(var _=this._drawCtx.createImageData(r,s),n=_.data,l=0,g=o;l<r*s*4;l+=4,g+=3)n[l]=a[g],n[l+1]=a[g+1],n[l+2]=a[g+2],n[l+3]=255;this._drawCtx.putImageData(_,t-e,i-h)},_bgrxImageData:function(t,i,e,h,r,s,a,o){for(var _=this._drawCtx.createImageData(r,s),n=_.data,l=0,g=o;l<r*s*4;l+=4,g+=4)n[l]=a[g+2],n[l+1]=a[g+1],n[l+2]=a[g],n[l+3]=255;this._drawCtx.putImageData(_,t-e,i-h)},_rgbxImageData:function(i,e,h,r,s,a,o,_){var n;t?n=new ImageData(new Uint8ClampedArray(o.buffer,o.byteOffset,s*a*4),s,a):(n=this._drawCtx.createImageData(s,a),n.data.set(new Uint8ClampedArray(o.buffer,o.byteOffset,s*a*4))),this._drawCtx.putImageData(n,i-h,e-r)},_cmapImageData:function(t,i,e,h,r,s,a,o){for(var _=this._drawCtx.createImageData(r,s),n=_.data,l=this._colourMap,g=0,w=o;g<r*s*4;g+=4,w++){var c=l[a[w]];n[g]=c[2],n[g+1]=c[1],n[g+2]=c[0],n[g+3]=255}this._drawCtx.putImageData(_,t-e,i-h)},_scan_renderQ:function(){for(var t=!0;t&&this._renderQ.length>0;){var i=this._renderQ[0];switch(i.type){case"copy":this.copyImage(i.old_x,i.old_y,i.x,i.y,i.width,i.height,!0);break;case"fill":this.fillRect(i.x,i.y,i.width,i.height,i.color,!0);break;case"blit":this.blitImage(i.x,i.y,i.width,i.height,i.data,0,!0);break;case"blitRgb":this.blitRgbImage(i.x,i.y,i.width,i.height,i.data,0,!0);break;case"blitRgbx":this.blitRgbxImage(i.x,i.y,i.width,i.height,i.data,0,!0);break;case"img":i.img.complete?this.drawImage(i.img,i.x,i.y):t=!1}t&&this._renderQ.shift()}this._renderQ.length>0&&requestAnimFrame(this._scan_renderQ.bind(this))}},Util.make_properties(Display,[["target","wo","dom"],["context","ro","raw"],["logo","rw","raw"],["true_color","rw","bool"],["colourMap","rw","arr"],["scale","rw","float"],["viewport","rw","bool"],["width","rw","int"],["height","rw","int"],["maxWidth","rw","int"],["maxHeight","rw","int"],["render_mode","ro","str"],["prefer_js","rw","str"],["cursor_uri","rw","raw"]]),Display.changeCursor=function(t,i,e,h,r,s,a,o){var _=s,n=a;n<_?n=_:_=n;var l=[];l.push16le=function(t){this.push(255&t,t>>8&255)},l.push32le=function(t){this.push(255&t,t>>8&255,t>>16&255,t>>24&255)};var g=_*n*4,w=Math.ceil(_*n/8),c=Math.ceil(_*n/8);l.push16le(0),l.push16le(2),l.push16le(1),l.push(_),l.push(n),l.push(0),l.push(0),l.push16le(h),l.push16le(r),l.push32le(40+g+w+c),l.push32le(22),l.push32le(40),l.push32le(_),l.push32le(2*n),l.push16le(1),l.push16le(32),l.push32le(0),l.push32le(w+c),l.push32le(0),l.push32le(0),l.push32le(0),l.push32le(0);var u,d;for(u=n-1;u>=0;u--)for(d=0;d<_;d++)if(d>=s||u>=a)l.push(0),l.push(0),l.push(0),l.push(0);else{var p=u*Math.ceil(s/8)+Math.floor(d/8),x=e[p]<<d%8&128?255:0;if(o){p=s*u+d;var f=o[i[p]];l.push(f[2]),l.push(f[1]),l.push(f[0]),l.push(x)}else p=4*(s*u+d),l.push(i[p+2]),l.push(i[p+1]),l.push(i[p]),l.push(x)}for(u=0;u<n;u++)for(d=0;d<Math.ceil(_/8);d++)l.push(0);for(u=0;u<n;u++)for(d=0;d<Math.ceil(_/8);d++)l.push(0);var y="data:image/x-icon;base64,"+Base64.encode(l);t.style.cursor="url("+y+")"+h+" "+r+", default"}}(); |