Merge pull request #699 from CendioOssman/double
Display double buffering
This commit is contained in:
+2
-1
@@ -2,7 +2,8 @@
|
||||
chai.use(function (_chai, utils) {
|
||||
_chai.Assertion.addMethod('displayed', function (target_data) {
|
||||
var obj = this._obj;
|
||||
var data_cl = obj._drawCtx.getImageData(0, 0, obj._viewportLoc.w, obj._viewportLoc.h).data;
|
||||
var ctx = obj._target.getContext('2d');
|
||||
var data_cl = ctx.getImageData(0, 0, obj._target.width, obj._target.height).data;
|
||||
// NB(directxman12): PhantomJS 1.x doesn't implement Uint8ClampedArray, so work around that
|
||||
var data = new Uint8Array(data_cl);
|
||||
var same = true;
|
||||
|
||||
+70
-6
@@ -12,13 +12,50 @@ var rfb, mode, test_state, frame_idx, frame_length,
|
||||
iteration, iterations, istart_time, encoding,
|
||||
|
||||
// Pre-declarations for jslint
|
||||
send_array, next_iteration, queue_next_packet, do_packet, enable_test_mode;
|
||||
send_array, next_iteration, end_iteration, queue_next_packet,
|
||||
do_packet, enable_test_mode;
|
||||
|
||||
// Override send_array
|
||||
send_array = function (arr) {
|
||||
// Stub out send_array
|
||||
};
|
||||
|
||||
// Immediate polyfill
|
||||
if (window.setImmediate === undefined) {
|
||||
var _immediateIdCounter = 1;
|
||||
var _immediateFuncs = {};
|
||||
|
||||
window.setImmediate = function (func) {
|
||||
var index = Util._immediateIdCounter++;
|
||||
_immediateFuncs[index] = func;
|
||||
window.postMessage("noVNC immediate trigger:" + index, "*");
|
||||
return index;
|
||||
};
|
||||
|
||||
window.clearImmediate = function (id) {
|
||||
_immediateFuncs[id];
|
||||
};
|
||||
|
||||
var _onMessage = function (event) {
|
||||
if ((typeof event.data !== "string") ||
|
||||
(event.data.indexOf("noVNC immediate trigger:") !== 0)) {
|
||||
return;
|
||||
}
|
||||
|
||||
var index = event.data.slice("noVNC immediate trigger:".length);
|
||||
|
||||
var callback = _immediateFuncs[index];
|
||||
if (callback === undefined) {
|
||||
return;
|
||||
}
|
||||
|
||||
delete _immediateFuncs[index];
|
||||
|
||||
callback();
|
||||
};
|
||||
window.addEventListener("message", _onMessage);
|
||||
}
|
||||
|
||||
enable_test_mode = function () {
|
||||
rfb._sock.send = send_array;
|
||||
rfb._sock.close = function () {};
|
||||
@@ -30,13 +67,16 @@ enable_test_mode = function () {
|
||||
this._rfb_password = (password !== undefined) ? password : "";
|
||||
this._rfb_path = (path !== undefined) ? path : "";
|
||||
this._sock.init('binary', 'ws');
|
||||
this._updateState('ProtocolVersion', "Starting VNC handshake");
|
||||
this._rfb_connection_state = 'connecting';
|
||||
this._rfb_init_state = 'ProtocolVersion';
|
||||
};
|
||||
};
|
||||
|
||||
next_iteration = function () {
|
||||
rfb = new RFB({'target': document.getElementById('VNC_canvas'),
|
||||
'onUpdateState': updateState});
|
||||
'view_only': true,
|
||||
'onDisconnected': disconnected,
|
||||
'onNotification': notification});
|
||||
enable_test_mode();
|
||||
|
||||
// Missing in older recordings
|
||||
@@ -73,6 +113,20 @@ next_iteration = function () {
|
||||
|
||||
};
|
||||
|
||||
end_iteration = function () {
|
||||
if (rfb._display.pending()) {
|
||||
rfb._display.set_onFlush(function () {
|
||||
if (rfb._flushing) {
|
||||
rfb._onFlush();
|
||||
}
|
||||
end_iteration();
|
||||
});
|
||||
rfb._display.flush();
|
||||
} else {
|
||||
next_iteration();
|
||||
}
|
||||
};
|
||||
|
||||
queue_next_packet = function () {
|
||||
var frame, foffset, toffset, delay;
|
||||
if (test_state !== 'running') { return; }
|
||||
@@ -86,12 +140,12 @@ queue_next_packet = function () {
|
||||
|
||||
if (frame === 'EOF') {
|
||||
Util.Debug("Finished, found EOF");
|
||||
next_iteration();
|
||||
end_iteration();
|
||||
return;
|
||||
}
|
||||
if (frame_idx >= frame_length) {
|
||||
Util.Debug("Finished, no more frames");
|
||||
next_iteration();
|
||||
end_iteration();
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -105,13 +159,23 @@ queue_next_packet = function () {
|
||||
|
||||
setTimeout(do_packet, delay);
|
||||
} else {
|
||||
setTimeout(do_packet, 0);
|
||||
window.setImmediate(do_packet);
|
||||
}
|
||||
};
|
||||
|
||||
var bytes_processed = 0;
|
||||
|
||||
do_packet = function () {
|
||||
// Avoid having an excessive queue buildup
|
||||
if (rfb._flushing && (mode !== 'realtime')) {
|
||||
rfb._display.set_onFlush(function () {
|
||||
rfb._display.set_onFlush(rfb._onFlush.bind(rfb));
|
||||
rfb._onFlush();
|
||||
do_packet();
|
||||
});
|
||||
return;
|
||||
}
|
||||
|
||||
//Util.Debug("Processing frame: " + frame_idx);
|
||||
var frame = VNC_frame_data[frame_idx],
|
||||
start = frame.indexOf('{', 1) + 1;
|
||||
|
||||
+166
-96
@@ -26,6 +26,13 @@ describe('Display/Canvas Helper', function () {
|
||||
return canvas;
|
||||
}
|
||||
|
||||
function make_image_png (input_data) {
|
||||
var canvas = make_image_canvas(input_data);
|
||||
var url = canvas.toDataURL();
|
||||
var data = url.split(",")[1];
|
||||
return Base64.decode(data);
|
||||
}
|
||||
|
||||
describe('checking for cursor uri support', function () {
|
||||
beforeEach(function () {
|
||||
this._old_browser_supports_cursor_uris = Util.browserSupportsCursorURIs;
|
||||
@@ -61,14 +68,13 @@ describe('Display/Canvas Helper', function () {
|
||||
display.resize(5, 5);
|
||||
display.viewportChangeSize(3, 3);
|
||||
display.viewportChangePos(1, 1);
|
||||
display.getCleanDirtyReset();
|
||||
});
|
||||
|
||||
it('should take viewport location into consideration when drawing images', function () {
|
||||
display.set_width(4);
|
||||
display.set_height(4);
|
||||
display.resize(4, 4);
|
||||
display.viewportChangeSize(2, 2);
|
||||
display.drawImage(make_image_canvas(basic_data), 1, 1);
|
||||
display.flip();
|
||||
|
||||
var expected = new Uint8Array(16);
|
||||
var i;
|
||||
@@ -77,96 +83,82 @@ describe('Display/Canvas Helper', function () {
|
||||
expect(display).to.have.displayed(expected);
|
||||
});
|
||||
|
||||
it('should redraw the left side when shifted left', function () {
|
||||
display.viewportChangePos(-1, 0);
|
||||
var cdr = display.getCleanDirtyReset();
|
||||
expect(cdr.cleanBox).to.deep.equal({ x: 1, y: 1, w: 2, h: 3 });
|
||||
expect(cdr.dirtyBoxes).to.have.length(1);
|
||||
expect(cdr.dirtyBoxes[0]).to.deep.equal({ x: 0, y: 1, w: 2, h: 3 });
|
||||
it('should resize the target canvas when resizing the viewport', function() {
|
||||
display.viewportChangeSize(2, 2);
|
||||
expect(display._target.width).to.equal(2);
|
||||
expect(display._target.height).to.equal(2);
|
||||
});
|
||||
|
||||
it('should redraw the right side when shifted right', function () {
|
||||
display.viewportChangePos(1, 0);
|
||||
var cdr = display.getCleanDirtyReset();
|
||||
expect(cdr.cleanBox).to.deep.equal({ x: 2, y: 1, w: 2, h: 3 });
|
||||
expect(cdr.dirtyBoxes).to.have.length(1);
|
||||
expect(cdr.dirtyBoxes[0]).to.deep.equal({ x: 4, y: 1, w: 1, h: 3 });
|
||||
it('should move the viewport if necessary', function() {
|
||||
display.viewportChangeSize(5, 5);
|
||||
expect(display.absX(0)).to.equal(0);
|
||||
expect(display.absY(0)).to.equal(0);
|
||||
expect(display._target.width).to.equal(5);
|
||||
expect(display._target.height).to.equal(5);
|
||||
});
|
||||
|
||||
it('should redraw the top part when shifted up', function () {
|
||||
display.viewportChangePos(0, -1);
|
||||
var cdr = display.getCleanDirtyReset();
|
||||
expect(cdr.cleanBox).to.deep.equal({ x: 1, y: 1, w: 3, h: 2 });
|
||||
expect(cdr.dirtyBoxes).to.have.length(1);
|
||||
expect(cdr.dirtyBoxes[0]).to.deep.equal({ x: 1, y: 0, w: 3, h: 1 });
|
||||
it('should limit the viewport to the framebuffer size', function() {
|
||||
display.viewportChangeSize(6, 6);
|
||||
expect(display._target.width).to.equal(5);
|
||||
expect(display._target.height).to.equal(5);
|
||||
});
|
||||
|
||||
it('should redraw the bottom part when shifted down', function () {
|
||||
display.viewportChangePos(0, 1);
|
||||
var cdr = display.getCleanDirtyReset();
|
||||
expect(cdr.cleanBox).to.deep.equal({ x: 1, y: 2, w: 3, h: 2 });
|
||||
expect(cdr.dirtyBoxes).to.have.length(1);
|
||||
expect(cdr.dirtyBoxes[0]).to.deep.equal({ x: 1, y: 4, w: 3, h: 1 });
|
||||
it('should redraw when moving the viewport', function () {
|
||||
display.flip = sinon.spy();
|
||||
display.viewportChangePos(-1, 1);
|
||||
expect(display.flip).to.have.been.calledOnce;
|
||||
});
|
||||
|
||||
it('should reset the entire viewport to being clean after calculating the clean/dirty boxes', function () {
|
||||
display.viewportChangePos(0, 1);
|
||||
var cdr1 = display.getCleanDirtyReset();
|
||||
var cdr2 = display.getCleanDirtyReset();
|
||||
expect(cdr1).to.not.deep.equal(cdr2);
|
||||
expect(cdr2.cleanBox).to.deep.equal({ x: 1, y: 2, w: 3, h: 3 });
|
||||
expect(cdr2.dirtyBoxes).to.be.empty;
|
||||
it('should redraw when resizing the viewport', function () {
|
||||
display.flip = sinon.spy();
|
||||
display.viewportChangeSize(2, 2);
|
||||
expect(display.flip).to.have.been.calledOnce;
|
||||
});
|
||||
|
||||
it('should simply mark the whole display area as dirty if not using viewports', function () {
|
||||
display = new Display({ target: document.createElement('canvas'), prefer_js: false, viewport: false });
|
||||
display.resize(5, 5);
|
||||
var cdr = display.getCleanDirtyReset();
|
||||
expect(cdr.cleanBox).to.deep.equal({ x: 0, y: 0, w: 0, h: 0 });
|
||||
expect(cdr.dirtyBoxes).to.have.length(1);
|
||||
expect(cdr.dirtyBoxes[0]).to.deep.equal({ x: 0, y: 0, w: 5, h: 5 });
|
||||
});
|
||||
});
|
||||
|
||||
describe('clipping', function () {
|
||||
var display;
|
||||
beforeEach(function () {
|
||||
display = new Display({ target: document.createElement('canvas'), prefer_js: false, viewport: true });
|
||||
display.resize(4, 3);
|
||||
});
|
||||
|
||||
it('should report true when no max-size and framebuffer > viewport', function () {
|
||||
display.viewportChangeSize(2,2);
|
||||
it('should report clipping when framebuffer > viewport', function () {
|
||||
var clipping = display.clippingDisplay();
|
||||
expect(clipping).to.be.true;
|
||||
});
|
||||
|
||||
it('should report false when no max-size and framebuffer = viewport', function () {
|
||||
it('should report not clipping when framebuffer = viewport', function () {
|
||||
display.viewportChangeSize(5, 5);
|
||||
var clipping = display.clippingDisplay();
|
||||
expect(clipping).to.be.false;
|
||||
});
|
||||
|
||||
it('should report true when viewport > max-size and framebuffer > viewport', function () {
|
||||
display.viewportChangeSize(2,2);
|
||||
display.set_maxWidth(1);
|
||||
display.set_maxHeight(2);
|
||||
var clipping = display.clippingDisplay();
|
||||
expect(clipping).to.be.true;
|
||||
it('should show the entire framebuffer when disabling the viewport', function() {
|
||||
display.set_viewport(false);
|
||||
expect(display.absX(0)).to.equal(0);
|
||||
expect(display.absY(0)).to.equal(0);
|
||||
expect(display._target.width).to.equal(5);
|
||||
expect(display._target.height).to.equal(5);
|
||||
});
|
||||
|
||||
it('should report true when viewport > max-size and framebuffer = viewport', function () {
|
||||
display.set_maxWidth(1);
|
||||
display.set_maxHeight(2);
|
||||
var clipping = display.clippingDisplay();
|
||||
expect(clipping).to.be.true;
|
||||
it('should ignore viewport changes when the viewport is disabled', function() {
|
||||
display.set_viewport(false);
|
||||
display.viewportChangeSize(2, 2);
|
||||
display.viewportChangePos(1, 1);
|
||||
expect(display.absX(0)).to.equal(0);
|
||||
expect(display.absY(0)).to.equal(0);
|
||||
expect(display._target.width).to.equal(5);
|
||||
expect(display._target.height).to.equal(5);
|
||||
});
|
||||
|
||||
it('should show the entire framebuffer just after enabling the viewport', function() {
|
||||
display.set_viewport(false);
|
||||
display.set_viewport(true);
|
||||
expect(display.absX(0)).to.equal(0);
|
||||
expect(display.absY(0)).to.equal(0);
|
||||
expect(display._target.width).to.equal(5);
|
||||
expect(display._target.height).to.equal(5);
|
||||
});
|
||||
});
|
||||
|
||||
describe('resizing', function () {
|
||||
var display;
|
||||
beforeEach(function () {
|
||||
display = new Display({ target: document.createElement('canvas'), prefer_js: false, viewport: true });
|
||||
display.resize(4, 3);
|
||||
display = new Display({ target: document.createElement('canvas'), prefer_js: false, viewport: false });
|
||||
display.resize(4, 4);
|
||||
});
|
||||
|
||||
it('should change the size of the logical canvas', function () {
|
||||
@@ -175,10 +167,49 @@ describe('Display/Canvas Helper', function () {
|
||||
expect(display._fb_height).to.equal(7);
|
||||
});
|
||||
|
||||
it('should update the viewport dimensions', function () {
|
||||
sinon.spy(display, 'viewportChangeSize');
|
||||
it('should keep the framebuffer data', function () {
|
||||
display.fillRect(0, 0, 4, 4, [0, 0, 0xff]);
|
||||
display.resize(2, 2);
|
||||
expect(display.viewportChangeSize).to.have.been.calledOnce;
|
||||
display.flip();
|
||||
var expected = [];
|
||||
for (var i = 0; i < 4 * 2*2; i += 4) {
|
||||
expected[i] = 0xff;
|
||||
expected[i+1] = expected[i+2] = 0;
|
||||
expected[i+3] = 0xff;
|
||||
}
|
||||
expect(display).to.have.displayed(new Uint8Array(expected));
|
||||
});
|
||||
|
||||
describe('viewport', function () {
|
||||
beforeEach(function () {
|
||||
display.set_viewport(true);
|
||||
display.viewportChangeSize(3, 3);
|
||||
display.viewportChangePos(1, 1);
|
||||
});
|
||||
|
||||
it('should keep the viewport position and size if possible', function () {
|
||||
display.resize(6, 6);
|
||||
expect(display.absX(0)).to.equal(1);
|
||||
expect(display.absY(0)).to.equal(1);
|
||||
expect(display._target.width).to.equal(3);
|
||||
expect(display._target.height).to.equal(3);
|
||||
});
|
||||
|
||||
it('should move the viewport if necessary', function () {
|
||||
display.resize(3, 3);
|
||||
expect(display.absX(0)).to.equal(0);
|
||||
expect(display.absY(0)).to.equal(0);
|
||||
expect(display._target.width).to.equal(3);
|
||||
expect(display._target.height).to.equal(3);
|
||||
});
|
||||
|
||||
it('should shrink the viewport if necessary', function () {
|
||||
display.resize(2, 2);
|
||||
expect(display.absX(0)).to.equal(0);
|
||||
expect(display.absY(0)).to.equal(0);
|
||||
expect(display._target.width).to.equal(2);
|
||||
expect(display._target.height).to.equal(2);
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
@@ -188,7 +219,9 @@ describe('Display/Canvas Helper', function () {
|
||||
|
||||
beforeEach(function () {
|
||||
display = new Display({ target: document.createElement('canvas'), prefer_js: false, viewport: true });
|
||||
display.resize(4, 3);
|
||||
display.resize(4, 4);
|
||||
display.viewportChangeSize(3, 3);
|
||||
display.viewportChangePos(1, 1);
|
||||
canvas = display.get_target();
|
||||
document.body.appendChild(canvas);
|
||||
});
|
||||
@@ -198,15 +231,25 @@ describe('Display/Canvas Helper', function () {
|
||||
});
|
||||
|
||||
it('should not change the bitmap size of the canvas', function () {
|
||||
display.set_scale(0.5);
|
||||
expect(canvas.width).to.equal(4);
|
||||
display.set_scale(2.0);
|
||||
expect(canvas.width).to.equal(3);
|
||||
expect(canvas.height).to.equal(3);
|
||||
});
|
||||
|
||||
it('should change the effective rendered size of the canvas', function () {
|
||||
display.set_scale(0.5);
|
||||
expect(canvas.clientWidth).to.equal(2);
|
||||
expect(canvas.clientHeight).to.equal(2);
|
||||
display.set_scale(2.0);
|
||||
expect(canvas.clientWidth).to.equal(6);
|
||||
expect(canvas.clientHeight).to.equal(6);
|
||||
});
|
||||
|
||||
it('should not change when resizing', function () {
|
||||
display.set_scale(2.0);
|
||||
display.resize(5, 5);
|
||||
expect(display.get_scale()).to.equal(2.0);
|
||||
expect(canvas.width).to.equal(3);
|
||||
expect(canvas.height).to.equal(3);
|
||||
expect(canvas.clientWidth).to.equal(6);
|
||||
expect(canvas.clientHeight).to.equal(6);
|
||||
});
|
||||
});
|
||||
|
||||
@@ -282,22 +325,35 @@ describe('Display/Canvas Helper', function () {
|
||||
});
|
||||
|
||||
it('should draw the logo on #clear with a logo set', function (done) {
|
||||
display._logo = { width: 4, height: 4, data: make_image_canvas(checked_data).toDataURL() };
|
||||
display._drawCtx._act_drawImg = display._drawCtx.drawImage;
|
||||
display._drawCtx.drawImage = function (img, x, y) {
|
||||
this._act_drawImg(img, x, y);
|
||||
expect(display).to.have.displayed(checked_data);
|
||||
done();
|
||||
};
|
||||
display._logo = { width: 4, height: 4, type: "image/png", data: make_image_png(checked_data) };
|
||||
display.clear();
|
||||
expect(display._fb_width).to.equal(4);
|
||||
expect(display._fb_height).to.equal(4);
|
||||
display.set_onFlush(function () {
|
||||
expect(display).to.have.displayed(checked_data);
|
||||
expect(display._fb_width).to.equal(4);
|
||||
expect(display._fb_height).to.equal(4);
|
||||
done();
|
||||
});
|
||||
display.flush();
|
||||
});
|
||||
|
||||
it('should not draw directly on the target canvas', function () {
|
||||
display.fillRect(0, 0, 4, 4, [0, 0, 0xff]);
|
||||
display.flip();
|
||||
display.fillRect(0, 0, 4, 4, [0, 0xff, 0]);
|
||||
var expected = [];
|
||||
for (var i = 0; i < 4 * display._fb_width * display._fb_height; i += 4) {
|
||||
expected[i] = 0xff;
|
||||
expected[i+1] = expected[i+2] = 0;
|
||||
expected[i+3] = 0xff;
|
||||
}
|
||||
expect(display).to.have.displayed(new Uint8Array(expected));
|
||||
});
|
||||
|
||||
it('should support filling a rectangle with particular color via #fillRect', function () {
|
||||
display.fillRect(0, 0, 4, 4, [0, 0xff, 0]);
|
||||
display.fillRect(0, 0, 2, 2, [0xff, 0, 0]);
|
||||
display.fillRect(2, 2, 2, 2, [0xff, 0, 0]);
|
||||
display.flip();
|
||||
expect(display).to.have.displayed(checked_data);
|
||||
});
|
||||
|
||||
@@ -305,14 +361,26 @@ describe('Display/Canvas Helper', function () {
|
||||
display.fillRect(0, 0, 4, 4, [0, 0xff, 0]);
|
||||
display.fillRect(0, 0, 2, 2, [0xff, 0, 0x00]);
|
||||
display.copyImage(0, 0, 2, 2, 2, 2);
|
||||
display.flip();
|
||||
expect(display).to.have.displayed(checked_data);
|
||||
});
|
||||
|
||||
it('should support drawing images via #imageRect', function (done) {
|
||||
display.imageRect(0, 0, "image/png", make_image_png(checked_data));
|
||||
display.flip();
|
||||
display.set_onFlush(function () {
|
||||
expect(display).to.have.displayed(checked_data);
|
||||
done();
|
||||
});
|
||||
display.flush();
|
||||
});
|
||||
|
||||
it('should support drawing tile data with a background color and sub tiles', function () {
|
||||
display.startTile(0, 0, 4, 4, [0, 0xff, 0]);
|
||||
display.subTile(0, 0, 2, 2, [0xff, 0, 0]);
|
||||
display.subTile(2, 2, 2, 2, [0xff, 0, 0]);
|
||||
display.finishTile();
|
||||
display.flip();
|
||||
expect(display).to.have.displayed(checked_data);
|
||||
});
|
||||
|
||||
@@ -325,6 +393,7 @@ describe('Display/Canvas Helper', function () {
|
||||
data[i * 4 + 3] = checked_data[i * 4 + 3];
|
||||
}
|
||||
display.blitImage(0, 0, 4, 4, data, 0);
|
||||
display.flip();
|
||||
expect(display).to.have.displayed(checked_data);
|
||||
});
|
||||
|
||||
@@ -336,26 +405,17 @@ describe('Display/Canvas Helper', function () {
|
||||
data[i * 3 + 2] = checked_data[i * 4 + 2];
|
||||
}
|
||||
display.blitRgbImage(0, 0, 4, 4, data, 0);
|
||||
display.flip();
|
||||
expect(display).to.have.displayed(checked_data);
|
||||
});
|
||||
|
||||
it('should support drawing blit images from a data URL via #blitStringImage', function (done) {
|
||||
var img_url = make_image_canvas(checked_data).toDataURL();
|
||||
display._drawCtx._act_drawImg = display._drawCtx.drawImage;
|
||||
display._drawCtx.drawImage = function (img, x, y) {
|
||||
this._act_drawImg(img, x, y);
|
||||
expect(display).to.have.displayed(checked_data);
|
||||
done();
|
||||
};
|
||||
display.blitStringImage(img_url, 0, 0);
|
||||
});
|
||||
|
||||
it('should support drawing solid colors with color maps', function () {
|
||||
display._true_color = false;
|
||||
display.set_colourMap({ 0: [0xff, 0, 0], 1: [0, 0xff, 0] });
|
||||
display.fillRect(0, 0, 4, 4, 1);
|
||||
display.fillRect(0, 0, 2, 2, 0);
|
||||
display.fillRect(2, 2, 2, 2, 0);
|
||||
display.flip();
|
||||
expect(display).to.have.displayed(checked_data);
|
||||
});
|
||||
|
||||
@@ -364,12 +424,14 @@ describe('Display/Canvas Helper', function () {
|
||||
display.set_colourMap({ 1: [0xff, 0, 0], 0: [0, 0xff, 0] });
|
||||
var data = [1, 1, 0, 0, 1, 1, 0, 0, 0, 0, 1, 1, 0, 0, 1, 1].map(function (elem) { return [elem]; });
|
||||
display.blitImage(0, 0, 4, 4, data, 0);
|
||||
display.flip();
|
||||
expect(display).to.have.displayed(checked_data);
|
||||
});
|
||||
|
||||
it('should support drawing an image object via #drawImage', function () {
|
||||
var img = make_image_canvas(checked_data);
|
||||
display.drawImage(img, 0, 0);
|
||||
display.flip();
|
||||
expect(display).to.have.displayed(checked_data);
|
||||
});
|
||||
}
|
||||
@@ -420,6 +482,14 @@ describe('Display/Canvas Helper', function () {
|
||||
expect(img.addEventListener).to.have.been.calledOnce;
|
||||
});
|
||||
|
||||
it('should call callback when queue is flushed', function () {
|
||||
display.set_onFlush(sinon.spy());
|
||||
display.fillRect(0, 0, 4, 4, [0, 0xff, 0]);
|
||||
expect(display.get_onFlush()).to.not.have.been.called;
|
||||
display.flush();
|
||||
expect(display.get_onFlush()).to.have.been.calledOnce;
|
||||
});
|
||||
|
||||
it('should draw a blit image on type "blit"', function () {
|
||||
display.blitImage = sinon.spy();
|
||||
display._renderQ_push({ type: 'blit', x: 3, y: 4, width: 5, height: 6, data: [7, 8, 9] });
|
||||
|
||||
+10
-60
@@ -1274,7 +1274,7 @@ describe('Remote Frame Buffer Protocol Client', function() {
|
||||
|
||||
it('should send an update request if there is sufficient data', function () {
|
||||
var expected_msg = {_sQ: new Uint8Array(10), _sQlen: 0, flush: function() {}};
|
||||
RFB.messages.fbUpdateRequest(expected_msg, false, 0, 0, 240, 20);
|
||||
RFB.messages.fbUpdateRequest(expected_msg, true, 0, 0, 640, 20);
|
||||
|
||||
client._framebufferUpdate = function () { return true; };
|
||||
client._sock._websocket._receive_data(new Uint8Array([0]));
|
||||
@@ -1289,7 +1289,7 @@ describe('Remote Frame Buffer Protocol Client', function() {
|
||||
|
||||
it('should resume receiving an update if we previously did not have enough data', function () {
|
||||
var expected_msg = {_sQ: new Uint8Array(10), _sQlen: 0, flush: function() {}};
|
||||
RFB.messages.fbUpdateRequest(expected_msg, false, 0, 0, 240, 20);
|
||||
RFB.messages.fbUpdateRequest(expected_msg, true, 0, 0, 640, 20);
|
||||
|
||||
// just enough to set FBU.rects
|
||||
client._sock._websocket._receive_data(new Uint8Array([0, 0, 0, 3]));
|
||||
@@ -1301,43 +1301,9 @@ describe('Remote Frame Buffer Protocol Client', function() {
|
||||
expect(client._sock).to.have.sent(expected_msg._sQ);
|
||||
});
|
||||
|
||||
it('should send a request for both clean and dirty areas', function () {
|
||||
var expected_msg = {_sQ: new Uint8Array(20), _sQlen: 0, flush: function() {}};
|
||||
var expected_cdr = { cleanBox: { x: 0, y: 0, w: 120, h: 20 },
|
||||
dirtyBoxes: [ { x: 120, y: 0, w: 120, h: 20 } ] };
|
||||
|
||||
RFB.messages.fbUpdateRequest(expected_msg, true, 0, 0, 120, 20);
|
||||
RFB.messages.fbUpdateRequest(expected_msg, false, 120, 0, 120, 20);
|
||||
|
||||
client._framebufferUpdate = function () { return true; };
|
||||
client._display.getCleanDirtyReset = function () { return expected_cdr; };
|
||||
client._sock._websocket._receive_data(new Uint8Array([0]));
|
||||
|
||||
expect(client._sock).to.have.sent(expected_msg._sQ);
|
||||
});
|
||||
|
||||
it('should only request non-incremental rects in continuous updates mode', function () {
|
||||
var expected_msg = {_sQ: new Uint8Array(10), _sQlen: 0, flush: function() {}};
|
||||
var expected_cdr = { cleanBox: { x: 0, y: 0, w: 120, h: 20 },
|
||||
dirtyBoxes: [ { x: 120, y: 0, w: 120, h: 20 } ] };
|
||||
|
||||
RFB.messages.fbUpdateRequest(expected_msg, false, 120, 0, 120, 20);
|
||||
|
||||
it('should not send a request in continuous updates mode', function () {
|
||||
client._enabledContinuousUpdates = true;
|
||||
client._framebufferUpdate = function () { return true; };
|
||||
client._display.getCleanDirtyReset = function () { return expected_cdr; };
|
||||
client._sock._websocket._receive_data(new Uint8Array([0]));
|
||||
|
||||
expect(client._sock).to.have.sent(expected_msg._sQ);
|
||||
});
|
||||
|
||||
it('should not send a request in continuous updates mode when clean', function () {
|
||||
var expected_cdr = { cleanBox: { x: 0, y: 0, w: 240, h: 20 },
|
||||
dirtyBoxes: [] };
|
||||
|
||||
client._enabledContinuousUpdates = true;
|
||||
client._framebufferUpdate = function () { return true; };
|
||||
client._display.getCleanDirtyReset = function () { return expected_cdr; };
|
||||
client._sock._websocket._receive_data(new Uint8Array([0]));
|
||||
|
||||
expect(client._sock._websocket._get_sent_data()).to.have.length(0);
|
||||
@@ -1389,14 +1355,11 @@ describe('Remote Frame Buffer Protocol Client', function() {
|
||||
client._fb_width = 4;
|
||||
client._fb_height = 4;
|
||||
client._display.resize(4, 4);
|
||||
var initial_data = client._display._drawCtx.createImageData(4, 2);
|
||||
var initial_data_arr = target_data_check_arr.slice(0, 32);
|
||||
for (var i = 0; i < 32; i++) { initial_data.data[i] = initial_data_arr[i]; }
|
||||
client._display._drawCtx.putImageData(initial_data, 0, 0);
|
||||
client._display.blitRgbxImage(0, 0, 4, 2, new Uint8Array(target_data_check_arr.slice(0, 32)), 0);
|
||||
|
||||
var info = [{ x: 0, y: 2, width: 2, height: 2, encoding: 0x01},
|
||||
{ x: 2, y: 2, width: 2, height: 2, encoding: 0x01}];
|
||||
// data says [{ old_x: 0, old_y: 0 }, { old_x: 0, old_y: 0 }]
|
||||
// data says [{ old_x: 2, old_y: 0 }, { old_x: 0, old_y: 0 }]
|
||||
var rects = [[0, 2, 0, 0], [0, 0, 0, 0]];
|
||||
send_fbu_msg([info[0]], [rects[0]], client, 2);
|
||||
send_fbu_msg([info[1]], [rects[1]], client, -1);
|
||||
@@ -1415,10 +1378,7 @@ describe('Remote Frame Buffer Protocol Client', function() {
|
||||
// a really small frame
|
||||
client._fb_width = 4;
|
||||
client._fb_height = 4;
|
||||
client._display._fb_width = 4;
|
||||
client._display._fb_height = 4;
|
||||
client._display._viewportLoc.w = 4;
|
||||
client._display._viewportLoc.h = 4;
|
||||
client._display.resize(4, 4);
|
||||
client._fb_Bpp = 4;
|
||||
});
|
||||
|
||||
@@ -1439,10 +1399,7 @@ describe('Remote Frame Buffer Protocol Client', function() {
|
||||
|
||||
it('should handle the COPYRECT encoding', function () {
|
||||
// seed some initial data to copy
|
||||
var initial_data = client._display._drawCtx.createImageData(4, 2);
|
||||
var initial_data_arr = target_data_check_arr.slice(0, 32);
|
||||
for (var i = 0; i < 32; i++) { initial_data.data[i] = initial_data_arr[i]; }
|
||||
client._display._drawCtx.putImageData(initial_data, 0, 0);
|
||||
client._display.blitRgbxImage(0, 0, 4, 2, new Uint8Array(target_data_check_arr.slice(0, 32)), 0);
|
||||
|
||||
var info = [{ x: 0, y: 2, width: 2, height: 2, encoding: 0x01},
|
||||
{ x: 2, y: 2, width: 2, height: 2, encoding: 0x01}];
|
||||
@@ -1492,10 +1449,7 @@ describe('Remote Frame Buffer Protocol Client', function() {
|
||||
// a really small frame
|
||||
client._fb_width = 4;
|
||||
client._fb_height = 4;
|
||||
client._display._fb_width = 4;
|
||||
client._display._fb_height = 4;
|
||||
client._display._viewportLoc.w = 4;
|
||||
client._display._viewportLoc.h = 4;
|
||||
client._display.resize(4, 4);
|
||||
client._fb_Bpp = 4;
|
||||
});
|
||||
|
||||
@@ -1546,8 +1500,7 @@ describe('Remote Frame Buffer Protocol Client', function() {
|
||||
it('should handle a tile with only bg specified and an empty frame afterwards', function () {
|
||||
// set the width so we can have two tiles
|
||||
client._fb_width = 8;
|
||||
client._display._fb_width = 8;
|
||||
client._display._viewportLoc.w = 8;
|
||||
client._display.resize(8, 4);
|
||||
|
||||
var info = [{ x: 0, y: 0, width: 32, height: 4, encoding: 0x05 }];
|
||||
|
||||
@@ -1670,10 +1623,7 @@ describe('Remote Frame Buffer Protocol Client', function() {
|
||||
// a really small frame
|
||||
client._fb_width = 4;
|
||||
client._fb_height = 4;
|
||||
client._display._fb_width = 4;
|
||||
client._display._fb_height = 4;
|
||||
client._display._viewportLoc.w = 4;
|
||||
client._display._viewportLoc.h = 4;
|
||||
client._display.resize(4, 4);
|
||||
client._fb_Bpp = 4;
|
||||
sinon.spy(client._display, 'resize');
|
||||
client.set_onFBResize(sinon.spy());
|
||||
|
||||
+11
-16
@@ -74,25 +74,20 @@
|
||||
}
|
||||
}
|
||||
|
||||
updateState = function (rfb, state, oldstate, mesg) {
|
||||
switch (state) {
|
||||
case 'failed':
|
||||
case 'fatal':
|
||||
msg("noVNC sent '" + state +
|
||||
"' state during pass " + pass +
|
||||
", iteration " + iteration +
|
||||
" frame " + frame_idx);
|
||||
test_state = 'failed';
|
||||
break;
|
||||
case 'loaded':
|
||||
document.getElementById('startButton').disabled = false;
|
||||
break;
|
||||
}
|
||||
if (typeof mesg !== 'undefined') {
|
||||
document.getElementById('VNC_status').innerHTML = mesg;
|
||||
disconnected = function (rfb, reason) {
|
||||
if (reason) {
|
||||
msg("noVNC sent '" + state +
|
||||
"' state during pass " + pass +
|
||||
", iteration " + iteration +
|
||||
" frame " + frame_idx);
|
||||
test_state = 'failed';
|
||||
}
|
||||
}
|
||||
|
||||
notification = function (rfb, mesg, level, options) {
|
||||
document.getElementById('VNC_status').innerHTML = mesg;
|
||||
}
|
||||
|
||||
function do_test() {
|
||||
document.getElementById('startButton').value = "Running";
|
||||
document.getElementById('startButton').disabled = true;
|
||||
|
||||
+8
-12
@@ -68,21 +68,17 @@
|
||||
message("Must specify data=FOO in query string.");
|
||||
}
|
||||
|
||||
updateState = function (rfb, state, oldstate, msg) {
|
||||
switch (state) {
|
||||
case 'failed':
|
||||
case 'fatal':
|
||||
message("noVNC sent '" + state + "' state during iteration " + iteration + " frame " + frame_idx);
|
||||
test_state = 'failed';
|
||||
break;
|
||||
case 'loaded':
|
||||
break;
|
||||
}
|
||||
if (typeof msg !== 'undefined') {
|
||||
document.getElementById('VNC_status').innerHTML = msg;
|
||||
disconnected = function (rfb, reason) {
|
||||
if (reason) {
|
||||
message("noVNC sent '" + state + "' state during iteration " + iteration + " frame " + frame_idx);
|
||||
test_state = 'failed';
|
||||
}
|
||||
}
|
||||
|
||||
notification = function (rfb, mesg, level, options) {
|
||||
document.getElementById('VNC_status').innerHTML = mesg;
|
||||
}
|
||||
|
||||
function start() {
|
||||
document.getElementById('startButton').value = "Running";
|
||||
document.getElementById('startButton').disabled = true;
|
||||
|
||||
Reference in New Issue
Block a user