mirror of
https://github.com/openseadragon/openseadragon.git
synced 2024-11-25 14:46:10 +03:00
Merge pull request #927 from avandecreme/perf
Optimize sketch canvas clearing and blending.
This commit is contained in:
commit
07429f5890
@ -259,13 +259,17 @@ $.Drawer.prototype = {
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
_clear: function ( useSketch ) {
|
_clear: function (useSketch, bounds) {
|
||||||
if (!this.useCanvas) {
|
if (!this.useCanvas) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
var context = this._getContext(useSketch);
|
var context = this._getContext(useSketch);
|
||||||
|
if (bounds) {
|
||||||
|
context.clearRect(bounds.x, bounds.y, bounds.width, bounds.height);
|
||||||
|
} else {
|
||||||
var canvas = context.canvas;
|
var canvas = context.canvas;
|
||||||
context.clearRect(0, 0, canvas.width, canvas.height);
|
context.clearRect(0, 0, canvas.width, canvas.height);
|
||||||
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -382,21 +386,59 @@ $.Drawer.prototype = {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Blends the sketch canvas in the main canvas.
|
* Blends the sketch canvas in the main canvas.
|
||||||
* @param {Float} opacity The opacity of the blending.
|
* @param {Object} options The options
|
||||||
* @param {Float} [scale=1] The scale at which tiles were drawn on the sketch. Default is 1.
|
* @param {Float} options.opacity The opacity of the blending.
|
||||||
|
* @param {Float} [options.scale=1] The scale at which tiles were drawn on
|
||||||
|
* the sketch. Default is 1.
|
||||||
* Use scale to draw at a lower scale and then enlarge onto the main canvas.
|
* Use scale to draw at a lower scale and then enlarge onto the main canvas.
|
||||||
* @param {OpenSeadragon.Point} [translate] A translation vector that was used to draw the tiles
|
* @param {OpenSeadragon.Point} [options.translate] A translation vector
|
||||||
* @param {String} [options.compositeOperation] - How the image is composited onto other images; see compositeOperation in {@link OpenSeadragon.Options} for possible values.
|
* that was used to draw the tiles
|
||||||
* @returns {undefined}
|
* @param {String} [options.compositeOperation] - How the image is
|
||||||
|
* composited onto other images; see compositeOperation in
|
||||||
|
* {@link OpenSeadragon.Options} for possible values.
|
||||||
|
* @param {OpenSeadragon.Rect} [options.bounds] The part of the sketch
|
||||||
|
* canvas to blend in the main canvas. If specified, options.scale and
|
||||||
|
* options.translate get ignored.
|
||||||
*/
|
*/
|
||||||
blendSketch: function(opacity, scale, translate, compositeOperation) {
|
blendSketch: function(opacity, scale, translate, compositeOperation) {
|
||||||
|
var options = opacity;
|
||||||
|
if (!$.isPlainObject(options)) {
|
||||||
|
options = {
|
||||||
|
opacity: opacity,
|
||||||
|
scale: scale,
|
||||||
|
translate: translate,
|
||||||
|
compositeOperation: compositeOperation
|
||||||
|
};
|
||||||
|
}
|
||||||
if (!this.useCanvas || !this.sketchCanvas) {
|
if (!this.useCanvas || !this.sketchCanvas) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
scale = scale || 1;
|
opacity = options.opacity;
|
||||||
|
compositeOperation = options.compositeOperation;
|
||||||
|
var bounds = options.bounds;
|
||||||
|
|
||||||
|
this.context.save();
|
||||||
|
this.context.globalAlpha = opacity;
|
||||||
|
if (compositeOperation) {
|
||||||
|
this.context.globalCompositeOperation = compositeOperation;
|
||||||
|
}
|
||||||
|
if (bounds) {
|
||||||
|
this.context.drawImage(
|
||||||
|
this.sketchCanvas,
|
||||||
|
bounds.x,
|
||||||
|
bounds.y,
|
||||||
|
bounds.width,
|
||||||
|
bounds.height,
|
||||||
|
bounds.x,
|
||||||
|
bounds.y,
|
||||||
|
bounds.width,
|
||||||
|
bounds.height
|
||||||
|
);
|
||||||
|
} else {
|
||||||
|
scale = options.scale || 1;
|
||||||
|
translate = options.translate;
|
||||||
var position = translate instanceof $.Point ?
|
var position = translate instanceof $.Point ?
|
||||||
translate :
|
translate : new $.Point(0, 0);
|
||||||
new $.Point(0, 0);
|
|
||||||
|
|
||||||
var widthExt = 0;
|
var widthExt = 0;
|
||||||
var heightExt = 0;
|
var heightExt = 0;
|
||||||
@ -406,12 +448,6 @@ $.Drawer.prototype = {
|
|||||||
widthExt = Math.round(widthDiff / 2);
|
widthExt = Math.round(widthDiff / 2);
|
||||||
heightExt = Math.round(heightDiff / 2);
|
heightExt = Math.round(heightDiff / 2);
|
||||||
}
|
}
|
||||||
|
|
||||||
this.context.save();
|
|
||||||
this.context.globalAlpha = opacity;
|
|
||||||
if (compositeOperation) {
|
|
||||||
this.context.globalCompositeOperation = compositeOperation;
|
|
||||||
}
|
|
||||||
this.context.drawImage(
|
this.context.drawImage(
|
||||||
this.sketchCanvas,
|
this.sketchCanvas,
|
||||||
position.x - widthExt * scale,
|
position.x - widthExt * scale,
|
||||||
@ -423,6 +459,7 @@ $.Drawer.prototype = {
|
|||||||
this.canvas.width + 2 * widthExt,
|
this.canvas.width + 2 * widthExt,
|
||||||
this.canvas.height + 2 * heightExt
|
this.canvas.height + 2 * heightExt
|
||||||
);
|
);
|
||||||
|
}
|
||||||
this.context.restore();
|
this.context.restore();
|
||||||
},
|
},
|
||||||
|
|
||||||
|
@ -367,6 +367,20 @@ $.Rect.prototype = {
|
|||||||
maxY - minY);
|
maxY - minY);
|
||||||
},
|
},
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Retrieves the smallest horizontal (degrees=0) rectangle which contains
|
||||||
|
* this rectangle and has integers x, y, width and height
|
||||||
|
* @returns {OpenSeadragon.Rect}
|
||||||
|
*/
|
||||||
|
getIntegerBoundingBox: function() {
|
||||||
|
var boundingBox = this.getBoundingBox();
|
||||||
|
var x = Math.floor(boundingBox.x);
|
||||||
|
var y = Math.floor(boundingBox.y);
|
||||||
|
var width = Math.ceil(boundingBox.width + boundingBox.x - x);
|
||||||
|
var height = Math.ceil(boundingBox.height + boundingBox.y - y);
|
||||||
|
return new $.Rect(x, y, width, height);
|
||||||
|
},
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Provides a string representation of the rectangle which is useful for
|
* Provides a string representation of the rectangle which is useful for
|
||||||
* debugging.
|
* debugging.
|
||||||
|
@ -195,7 +195,7 @@ $.Tile.prototype = {
|
|||||||
|
|
||||||
// private
|
// private
|
||||||
_hasTransparencyChannel: function() {
|
_hasTransparencyChannel: function() {
|
||||||
return this.context2D || this.url.match('.png');
|
return !!this.context2D || this.url.match('.png');
|
||||||
},
|
},
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -1448,8 +1448,17 @@ function drawTiles( tiledImage, lastDrawn ) {
|
|||||||
tiledImage._drawer.getCanvasSize(true));
|
tiledImage._drawer.getCanvasSize(true));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
var bounds;
|
||||||
if (useSketch) {
|
if (useSketch) {
|
||||||
tiledImage._drawer._clear( true );
|
if (!sketchScale) {
|
||||||
|
// Except when edge smoothing, we only clean the part of the
|
||||||
|
// sketch canvas we are going to use for performance reasons.
|
||||||
|
bounds = tiledImage.viewport.viewportToViewerElementRectangle(
|
||||||
|
tiledImage.getClippedBounds(true))
|
||||||
|
.getIntegerBoundingBox()
|
||||||
|
.times($.pixelDensityRatio);
|
||||||
|
}
|
||||||
|
tiledImage._drawer._clear(true, bounds);
|
||||||
}
|
}
|
||||||
|
|
||||||
// When scaling, we must rotate only when blending the sketch canvas to avoid
|
// When scaling, we must rotate only when blending the sketch canvas to avoid
|
||||||
@ -1532,7 +1541,13 @@ function drawTiles( tiledImage, lastDrawn ) {
|
|||||||
if (offsetForRotation) {
|
if (offsetForRotation) {
|
||||||
tiledImage._drawer._offsetForRotation(tiledImage.viewport.degrees, false);
|
tiledImage._drawer._offsetForRotation(tiledImage.viewport.degrees, false);
|
||||||
}
|
}
|
||||||
tiledImage._drawer.blendSketch(tiledImage.opacity, sketchScale, sketchTranslate, tiledImage.compositeOperation);
|
tiledImage._drawer.blendSketch({
|
||||||
|
opacity: tiledImage.opacity,
|
||||||
|
scale: sketchScale,
|
||||||
|
translate: sketchTranslate,
|
||||||
|
compositeOperation: tiledImage.compositeOperation,
|
||||||
|
bounds: bounds
|
||||||
|
});
|
||||||
if (offsetForRotation) {
|
if (offsetForRotation) {
|
||||||
tiledImage._drawer._restoreRotationChanges(false);
|
tiledImage._drawer._restoreRotationChanges(false);
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user