mirror of
https://github.com/openseadragon/openseadragon.git
synced 2024-11-22 05:06:09 +03:00
cleaning up drawer APIs
This commit is contained in:
parent
5eece7d73a
commit
467597e2c2
487
src/drawer.js
487
src/drawer.js
@ -37,7 +37,7 @@
|
||||
/**
|
||||
* @class Drawer
|
||||
* @memberof OpenSeadragon
|
||||
* @classdesc Handles rendering of tiles for an {@link OpenSeadragon.Viewer}.
|
||||
* @classdesc Default implementation of Drawer for an {@link OpenSeadragon.Viewer}.
|
||||
* @param {Object} options - Options for this Drawer.
|
||||
* @param {OpenSeadragon.Viewer} options.viewer - The Viewer that owns this Drawer.
|
||||
* @param {OpenSeadragon.Viewport} options.viewport - Reference to Viewer viewport.
|
||||
@ -48,55 +48,12 @@ $.Drawer = function(options) {
|
||||
|
||||
$.DrawerBase.call(this, options);
|
||||
|
||||
$.console.assert( options.viewer, "[Drawer] options.viewer is required" );
|
||||
|
||||
//backward compatibility for positional args while preferring more
|
||||
//idiomatic javascript options object as the only argument
|
||||
var args = arguments;
|
||||
|
||||
if( !$.isPlainObject( options ) ){
|
||||
options = {
|
||||
source: args[ 0 ], // Reference to Viewer tile source.
|
||||
viewport: args[ 1 ], // Reference to Viewer viewport.
|
||||
element: args[ 2 ] // Parent element.
|
||||
};
|
||||
}
|
||||
|
||||
$.console.assert( options.viewport, "[Drawer] options.viewport is required" );
|
||||
$.console.assert( options.element, "[Drawer] options.element is required" );
|
||||
|
||||
if ( options.source ) {
|
||||
$.console.error( "[Drawer] options.source is no longer accepted; use TiledImage instead" );
|
||||
}
|
||||
|
||||
this.viewer = options.viewer;
|
||||
this.viewport = options.viewport;
|
||||
this.debugGridColor = typeof options.debugGridColor === 'string' ? [options.debugGridColor] : options.debugGridColor || $.DEFAULT_SETTINGS.debugGridColor;
|
||||
if (options.opacity) {
|
||||
$.console.error( "[Drawer] options.opacity is no longer accepted; set the opacity on the TiledImage instead" );
|
||||
}
|
||||
|
||||
this.useCanvas = $.supportsCanvas && ( this.viewer ? this.viewer.useCanvas : true );
|
||||
/**
|
||||
* The parent element of this Drawer instance, passed in when the Drawer was created.
|
||||
* The parent of {@link OpenSeadragon.Drawer#canvas}.
|
||||
* @member {Element} container
|
||||
* @memberof OpenSeadragon.Drawer#
|
||||
*/
|
||||
this.container = $.getElement( options.element );
|
||||
/**
|
||||
* A <canvas> element if the browser supports them, otherwise a <div> element.
|
||||
* Child element of {@link OpenSeadragon.Drawer#container}.
|
||||
* @member {Element} canvas
|
||||
* @memberof OpenSeadragon.Drawer#
|
||||
*/
|
||||
this.canvas = $.makeNeutralElement( this.useCanvas ? "canvas" : "div" );
|
||||
/**
|
||||
* 2d drawing context for {@link OpenSeadragon.Drawer#canvas} if it's a <canvas> element, otherwise null.
|
||||
* @member {Object} context
|
||||
* @memberof OpenSeadragon.Drawer#
|
||||
*/
|
||||
this.context = this.useCanvas ? this.canvas.getContext( this.useCanvas.contextType || "2d" ) : null;
|
||||
this.context = this.useCanvas ? this.canvas.getContext( '2d' ) : null;
|
||||
|
||||
/**
|
||||
* Sketch canvas used to temporarily draw tiles which cannot be drawn directly
|
||||
@ -105,60 +62,35 @@ $.Drawer = function(options) {
|
||||
this.sketchCanvas = null;
|
||||
this.sketchContext = null;
|
||||
|
||||
/**
|
||||
* @member {Element} element
|
||||
* @memberof OpenSeadragon.Drawer#
|
||||
* @deprecated Alias for {@link OpenSeadragon.Drawer#container}.
|
||||
*/
|
||||
this.element = this.container;
|
||||
|
||||
// We force our container to ltr because our drawing math doesn't work in rtl.
|
||||
// This issue only affects our canvas renderer, but we do it always for consistency.
|
||||
// Note that this means overlays you want to be rtl need to be explicitly set to rtl.
|
||||
this.container.dir = 'ltr';
|
||||
|
||||
// check canvas available width and height, set canvas width and height such that the canvas backing store is set to the proper pixel density
|
||||
if (this.useCanvas) {
|
||||
var viewportSize = this._calculateCanvasSize();
|
||||
this.canvas.width = viewportSize.x;
|
||||
this.canvas.height = viewportSize.y;
|
||||
}
|
||||
|
||||
this.canvas.style.width = "100%";
|
||||
this.canvas.style.height = "100%";
|
||||
this.canvas.style.position = "absolute";
|
||||
$.setElementOpacity( this.canvas, this.opacity, true );
|
||||
// Allow pointer events to pass through the canvas element so implicit
|
||||
// pointer capture works on touch devices
|
||||
$.setElementPointerEventsNone( this.canvas );
|
||||
$.setElementTouchActionNone( this.canvas );
|
||||
|
||||
// explicit left-align
|
||||
this.container.style.textAlign = "left";
|
||||
this.container.appendChild( this.canvas );
|
||||
|
||||
// Image smoothing for canvas rendering (only if canvas is used).
|
||||
// Canvas default is "true", so this will only be changed if user specified "false".
|
||||
this._imageSmoothingEnabled = true;
|
||||
|
||||
|
||||
};
|
||||
|
||||
$.extend( $.Drawer.prototype, $.DrawerBase.prototype, /** @lends OpenSeadragon.Drawer.prototype */ {
|
||||
|
||||
/**
|
||||
* Draws the TiledImage to its Drawer.
|
||||
* Draws the TiledImages
|
||||
*/
|
||||
draw: function(tiledImage) {
|
||||
if (tiledImage.opacity !== 0 || tiledImage._preload) {
|
||||
tiledImage._midDraw = true;
|
||||
this._updateViewport(tiledImage);
|
||||
tiledImage._midDraw = false;
|
||||
}
|
||||
// Images with opacity 0 should not need to be drawn in future. this._needsDraw = false is set in this._updateViewport() for other images.
|
||||
else {
|
||||
tiledImage._needsDraw = false;
|
||||
}
|
||||
draw: function(tiledImages) {
|
||||
var _this = this;
|
||||
this._prepareNewFrame(); // prepare to draw a new frame
|
||||
tiledImages.forEach(function(tiledImage){
|
||||
if (tiledImage.opacity !== 0 || tiledImage._preload) {
|
||||
tiledImage._midDraw = true;
|
||||
_this._updateViewportWithTiledImage(tiledImage);
|
||||
tiledImage._midDraw = false;
|
||||
}
|
||||
else {
|
||||
tiledImage._needsDraw = false;
|
||||
}
|
||||
});
|
||||
|
||||
},
|
||||
|
||||
/**
|
||||
@ -180,9 +112,51 @@ $.extend( $.Drawer.prototype, $.DrawerBase.prototype, /** @lends OpenSeadragon.D
|
||||
},
|
||||
|
||||
/**
|
||||
* Clears the Drawer so it's ready to draw another frame.
|
||||
* Turns image smoothing on or off for this viewer. Note: Ignored in some (especially older) browsers that do not support this property.
|
||||
*
|
||||
* @function
|
||||
* @param {Boolean} [imageSmoothingEnabled] - Whether or not the image is
|
||||
* drawn smoothly on the canvas; see imageSmoothingEnabled in
|
||||
* {@link OpenSeadragon.Options} for more explanation.
|
||||
*/
|
||||
clear: function() {
|
||||
setImageSmoothingEnabled: function(imageSmoothingEnabled){
|
||||
if ( this.useCanvas ) {
|
||||
this._imageSmoothingEnabled = imageSmoothingEnabled;
|
||||
this._updateImageSmoothingEnabled(this.context);
|
||||
this.viewer.forceRedraw();
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
* Draw a rectangle onto the canvas
|
||||
* @param {OpenSeadragon.Rect} rect
|
||||
*/
|
||||
drawDebuggingRect: function(rect) {
|
||||
if ( this.useCanvas ) {
|
||||
var context = this.context;
|
||||
context.save();
|
||||
context.lineWidth = 2 * $.pixelDensityRatio;
|
||||
context.strokeStyle = this.debugGridColor[0];
|
||||
context.fillStyle = this.debugGridColor[0];
|
||||
|
||||
context.strokeRect(
|
||||
rect.x * $.pixelDensityRatio,
|
||||
rect.y * $.pixelDensityRatio,
|
||||
rect.width * $.pixelDensityRatio,
|
||||
rect.height * $.pixelDensityRatio
|
||||
);
|
||||
|
||||
context.restore();
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @inner
|
||||
* Clears the Drawer so it's ready to draw another frame.
|
||||
*
|
||||
*/
|
||||
_prepareNewFrame: function() {
|
||||
this.canvas.innerHTML = "";
|
||||
if ( this.useCanvas ) {
|
||||
var viewportSize = this._calculateCanvasSize();
|
||||
@ -202,31 +176,33 @@ $.extend( $.Drawer.prototype, $.DrawerBase.prototype, /** @lends OpenSeadragon.D
|
||||
}
|
||||
},
|
||||
|
||||
_clear: function (useSketch, bounds) {
|
||||
if (!this.useCanvas) {
|
||||
return;
|
||||
}
|
||||
var context = this._getContext(useSketch);
|
||||
if (bounds) {
|
||||
context.clearRect(bounds.x, bounds.y, bounds.width, bounds.height);
|
||||
} else {
|
||||
var canvas = context.canvas;
|
||||
context.clearRect(0, 0, canvas.width, canvas.height);
|
||||
/**
|
||||
* @private
|
||||
* @inner
|
||||
* @param {Boolean} useSketch Whether to clear sketch canvas or main canvas
|
||||
* @param {OpenSeadragon.Rect} [bounds] The rectangle to clear
|
||||
*/
|
||||
_clear: function(useSketch, bounds){
|
||||
if( this.useCanvas ){
|
||||
var context = this._getContext(useSketch);
|
||||
if (bounds) {
|
||||
context.clearRect(bounds.x, bounds.y, bounds.width, bounds.height);
|
||||
} else {
|
||||
var canvas = context.canvas;
|
||||
context.clearRect(0, 0, canvas.width, canvas.height);
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
/* Methods from TiledImage */
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @inner
|
||||
* Pretty much every other line in this needs to be documented so it's clear
|
||||
* how each piece of this routine contributes to the drawing process. That's
|
||||
* why there are so many TODO's inside this function.
|
||||
* Handles drawing a single TiledImage to the canvas
|
||||
*
|
||||
*/
|
||||
_updateViewport: function(tiledImage) {
|
||||
_updateViewportWithTiledImage: function(tiledImage) {
|
||||
var _this = this;
|
||||
tiledImage._needsDraw = false;
|
||||
tiledImage._tilesLoading = 0;
|
||||
@ -265,7 +241,7 @@ $.extend( $.Drawer.prototype, $.DrawerBase.prototype, /** @lends OpenSeadragon.D
|
||||
var infoArray = tiledImage.getTileInfoForDrawing();
|
||||
infoArray.forEach(updateTile);
|
||||
|
||||
this._drawTiles(tiledImage, tiledImage.lastDrawn);
|
||||
this._drawTiles(tiledImage);
|
||||
|
||||
},
|
||||
|
||||
@ -348,7 +324,7 @@ $.extend( $.Drawer.prototype, $.DrawerBase.prototype, /** @lends OpenSeadragon.D
|
||||
if (lastDrawn.length > 1 &&
|
||||
imageZoom > tiledImage.smoothTileEdgesMinZoom &&
|
||||
!tiledImage.iOSDevice &&
|
||||
tiledImage.getRotation(true) % 360 === 0 && // TODO: support tile edge smoothing with tiled image rotation.
|
||||
tiledImage.getRotation(true) % 360 === 0 && // TO DO: support tile edge smoothing with tiled image rotation.
|
||||
$.supportsCanvas && this.viewer.useCanvas) {
|
||||
// When zoomed in a lot (>100%) the tile edges are visible.
|
||||
// So we have to composite them at ~100% and scale them up together.
|
||||
@ -356,8 +332,8 @@ $.extend( $.Drawer.prototype, $.DrawerBase.prototype, /** @lends OpenSeadragon.D
|
||||
useSketch = true;
|
||||
sketchScale = tile.getScaleForEdgeSmoothing();
|
||||
sketchTranslate = tile.getTranslationForEdgeSmoothing(sketchScale,
|
||||
this.getCanvasSize(false),
|
||||
this.getCanvasSize(true));
|
||||
this._getCanvasSize(false),
|
||||
this._getCanvasSize(true));
|
||||
}
|
||||
|
||||
var bounds;
|
||||
@ -409,39 +385,42 @@ $.extend( $.Drawer.prototype, $.DrawerBase.prototype, /** @lends OpenSeadragon.D
|
||||
|
||||
var usedClip = false;
|
||||
if ( tiledImage._clip ) {
|
||||
this.saveContext(useSketch);
|
||||
this._saveContext(useSketch);
|
||||
|
||||
var box = tiledImage.imageToViewportRectangle(tiledImage._clip, true);
|
||||
box = box.rotate(-tiledImage.getRotation(true), tiledImage._getRotationPoint(true));
|
||||
var clipRect = this.viewportToDrawerRectangle(box);
|
||||
var clipRect = this._viewportToDrawerRectangle(box);
|
||||
if (sketchScale) {
|
||||
clipRect = clipRect.times(sketchScale);
|
||||
}
|
||||
if (sketchTranslate) {
|
||||
clipRect = clipRect.translate(sketchTranslate);
|
||||
}
|
||||
this.setClip(clipRect, useSketch);
|
||||
this._setClip(clipRect, useSketch);
|
||||
|
||||
usedClip = true;
|
||||
}
|
||||
|
||||
if (tiledImage._croppingPolygons) {
|
||||
var self = this;
|
||||
this.saveContext(useSketch);
|
||||
this._saveContext(useSketch);
|
||||
try {
|
||||
var polygons = tiledImage._croppingPolygons.map(function (polygon) {
|
||||
return polygon.map(function (coord) {
|
||||
var point = tiledImage
|
||||
.imageToViewportCoordinates(coord.x, coord.y, true)
|
||||
.rotate(-tiledImage.getRotation(true), tiledImage._getRotationPoint(true));
|
||||
var clipPoint = self.viewportCoordToDrawerCoord(point);
|
||||
var clipPoint = self._viewportCoordToDrawerCoord(point);
|
||||
if (sketchScale) {
|
||||
clipPoint = clipPoint.times(sketchScale);
|
||||
}
|
||||
if (sketchTranslate) { // mostly fixes #2312
|
||||
clipPoint = clipPoint.plus(sketchTranslate);
|
||||
}
|
||||
return clipPoint;
|
||||
});
|
||||
});
|
||||
this.clipWithPolygons(polygons, useSketch);
|
||||
this._clipWithPolygons(polygons, useSketch);
|
||||
} catch (e) {
|
||||
$.console.error(e);
|
||||
}
|
||||
@ -449,7 +428,7 @@ $.extend( $.Drawer.prototype, $.DrawerBase.prototype, /** @lends OpenSeadragon.D
|
||||
}
|
||||
|
||||
if ( tiledImage.placeholderFillStyle && tiledImage._hasOpaqueTile === false ) {
|
||||
var placeholderRect = this.viewportToDrawerRectangle(tiledImage.getBounds(true));
|
||||
var placeholderRect = this._viewportToDrawerRectangle(tiledImage.getBounds(true));
|
||||
if (sketchScale) {
|
||||
placeholderRect = placeholderRect.times(sketchScale);
|
||||
}
|
||||
@ -479,15 +458,16 @@ $.extend( $.Drawer.prototype, $.DrawerBase.prototype, /** @lends OpenSeadragon.D
|
||||
shouldRoundPositionAndSize = !isAnimating;
|
||||
}
|
||||
|
||||
// Iterate over the tiles to draw, and draw them
|
||||
for (var i = lastDrawn.length - 1; i >= 0; i--) {
|
||||
tile = lastDrawn[ i ];
|
||||
this.drawTile( tile, tiledImage._drawingHandler, useSketch, sketchScale,
|
||||
this._drawTile( tile, tiledImage._drawingHandler, useSketch, sketchScale,
|
||||
sketchTranslate, shouldRoundPositionAndSize, tiledImage.source );
|
||||
tile.beingDrawn = true;
|
||||
|
||||
if( this.viewer ){
|
||||
/**
|
||||
* <em>- Needs documentation -</em>
|
||||
* Raised when a tile is drawn to the canvas
|
||||
*
|
||||
* @event tile-drawn
|
||||
* @memberof OpenSeadragon.Viewer
|
||||
@ -505,7 +485,7 @@ $.extend( $.Drawer.prototype, $.DrawerBase.prototype, /** @lends OpenSeadragon.D
|
||||
}
|
||||
|
||||
if ( usedClip ) {
|
||||
this.restoreContext( useSketch );
|
||||
this._restoreContext( useSketch );
|
||||
}
|
||||
|
||||
if (!sketchScale) {
|
||||
@ -584,31 +564,15 @@ $.extend( $.Drawer.prototype, $.DrawerBase.prototype, /** @lends OpenSeadragon.D
|
||||
|
||||
/* Methods from Tile */
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* This function converts the given point from to the drawer coordinate by
|
||||
* multiplying it with the pixel density.
|
||||
* This function does not take rotation into account, thus assuming provided
|
||||
* point is at 0 degree.
|
||||
* @param {OpenSeadragon.Point} point - the pixel point to convert
|
||||
* @returns {OpenSeadragon.Point} Point in drawer coordinate system.
|
||||
*/
|
||||
viewportCoordToDrawerCoord: function(point) {
|
||||
var vpPoint = this.viewport.pixelFromPointNoRotate(point, true);
|
||||
return new $.Point(
|
||||
vpPoint.x * $.pixelDensityRatio,
|
||||
vpPoint.y * $.pixelDensityRatio
|
||||
);
|
||||
},
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @inner
|
||||
* This function will create multiple polygon paths on the drawing context by provided polygons,
|
||||
* then clip the context to the paths.
|
||||
* @param {OpenSeadragon.Point[][]} polygons - an array of polygons. A polygon is an array of OpenSeadragon.Point
|
||||
* @param {Boolean} useSketch - Whether to use the sketch canvas or not.
|
||||
*/
|
||||
clipWithPolygons: function (polygons, useSketch) {
|
||||
_clipWithPolygons: function (polygons, useSketch) {
|
||||
if (!this.useCanvas) {
|
||||
return;
|
||||
}
|
||||
@ -622,31 +586,9 @@ $.extend( $.Drawer.prototype, $.DrawerBase.prototype, /** @lends OpenSeadragon.D
|
||||
context.clip();
|
||||
},
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* Scale from OpenSeadragon viewer rectangle to drawer rectangle
|
||||
* (ignoring rotation)
|
||||
* @param {OpenSeadragon.Rect} rectangle - The rectangle in viewport coordinate system.
|
||||
* @returns {OpenSeadragon.Rect} Rectangle in drawer coordinate system.
|
||||
*/
|
||||
viewportToDrawerRectangle: function(rectangle) {
|
||||
var topLeft = this.viewport.pixelFromPointNoRotate(rectangle.getTopLeft(), true);
|
||||
var size = this.viewport.deltaPixelsFromPointsNoRotate(rectangle.getSize(), true);
|
||||
|
||||
return new $.Rect(
|
||||
topLeft.x * $.pixelDensityRatio,
|
||||
topLeft.y * $.pixelDensityRatio,
|
||||
size.x * $.pixelDensityRatio,
|
||||
size.y * $.pixelDensityRatio
|
||||
);
|
||||
},
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @inner
|
||||
* Draws the given tile.
|
||||
* @param {OpenSeadragon.Tile} tile - The tile to draw.
|
||||
* @param {Function} drawingHandler - Method for firing the drawing event if using canvas.
|
||||
@ -660,35 +602,37 @@ $.extend( $.Drawer.prototype, $.DrawerBase.prototype, /** @lends OpenSeadragon.D
|
||||
* context.
|
||||
* @param {OpenSeadragon.TileSource} source - The source specification of the tile.
|
||||
*/
|
||||
drawTile: function( tile, drawingHandler, useSketch, scale, translate, shouldRoundPositionAndSize, source) {
|
||||
$.console.assert(tile, '[Drawer.drawTile] tile is required');
|
||||
$.console.assert(drawingHandler, '[Drawer.drawTile] drawingHandler is required');
|
||||
_drawTile: function( tile, drawingHandler, useSketch, scale, translate, shouldRoundPositionAndSize, source) {
|
||||
$.console.assert(tile, '[Drawer._drawTile] tile is required');
|
||||
$.console.assert(drawingHandler, '[Drawer._drawTile] drawingHandler is required');
|
||||
|
||||
if (this.useCanvas) {
|
||||
var context = this._getContext(useSketch);
|
||||
scale = scale || 1;
|
||||
this.drawTileToCanvas(tile, context, drawingHandler, scale, translate, shouldRoundPositionAndSize, source);
|
||||
this._drawTileToCanvas(tile, context, drawingHandler, scale, translate, shouldRoundPositionAndSize, source);
|
||||
} else {
|
||||
tile.drawTileToHTML( tile, this.canvas );
|
||||
tile._drawTileToHTML( tile, this.canvas );
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
* Renders the tile in a canvas-based context.
|
||||
* @function
|
||||
* @param {OpenSeadragon.Tile} tile - the tile to draw to the canvas
|
||||
* @param {Canvas} context
|
||||
* @param {Function} drawingHandler - Method for firing the drawing event.
|
||||
* drawingHandler({context, tile, rendered})
|
||||
* where <code>rendered</code> is the context with the pre-drawn image.
|
||||
* @param {Number} [scale=1] - Apply a scale to position and size
|
||||
* @param {OpenSeadragon.Point} [translate] - A translation vector
|
||||
* @param {Boolean} [shouldRoundPositionAndSize] - Tells whether to round
|
||||
* position and size of tiles supporting alpha channel in non-transparency
|
||||
* context.
|
||||
* @param {OpenSeadragon.TileSource} source - The source specification of the tile.
|
||||
*/
|
||||
drawTileToCanvas: function( tile, context, drawingHandler, scale, translate, shouldRoundPositionAndSize, source) {
|
||||
* @private
|
||||
* @inner
|
||||
* Renders the tile in a canvas-based context.
|
||||
* @function
|
||||
* @param {OpenSeadragon.Tile} tile - the tile to draw to the canvas
|
||||
* @param {Canvas} context
|
||||
* @param {Function} drawingHandler - Method for firing the drawing event.
|
||||
* drawingHandler({context, tile, rendered})
|
||||
* where <code>rendered</code> is the context with the pre-drawn image.
|
||||
* @param {Number} [scale=1] - Apply a scale to position and size
|
||||
* @param {OpenSeadragon.Point} [translate] - A translation vector
|
||||
* @param {Boolean} [shouldRoundPositionAndSize] - Tells whether to round
|
||||
* position and size of tiles supporting alpha channel in non-transparency
|
||||
* context.
|
||||
* @param {OpenSeadragon.TileSource} source - The source specification of the tile.
|
||||
*/
|
||||
_drawTileToCanvas: function( tile, context, drawingHandler, scale, translate, shouldRoundPositionAndSize, source) {
|
||||
|
||||
var position = tile.position.times($.pixelDensityRatio),
|
||||
size = tile.size.times($.pixelDensityRatio),
|
||||
@ -696,7 +640,7 @@ $.extend( $.Drawer.prototype, $.DrawerBase.prototype, /** @lends OpenSeadragon.D
|
||||
|
||||
if (!tile.context2D && !tile.cacheImageRecord) {
|
||||
$.console.warn(
|
||||
'[Drawer.drawTileToCanvas] attempting to draw tile %s when it\'s not cached',
|
||||
'[Drawer._drawTileToCanvas] attempting to draw tile %s when it\'s not cached',
|
||||
tile.toString());
|
||||
return;
|
||||
}
|
||||
@ -782,15 +726,17 @@ $.extend( $.Drawer.prototype, $.DrawerBase.prototype, /** @lends OpenSeadragon.D
|
||||
},
|
||||
|
||||
/**
|
||||
* Renders the tile in an html container.
|
||||
* @function
|
||||
* @param {OpenSeadragon.Tile} tile
|
||||
* @param {Element} container
|
||||
*/
|
||||
drawTileToHTML: function( tile, container ) {
|
||||
* @private
|
||||
* @inner
|
||||
* Renders the tile in an html container.
|
||||
* @function
|
||||
* @param {OpenSeadragon.Tile} tile
|
||||
* @param {Element} container
|
||||
*/
|
||||
_drawTileToHTML: function( tile, container ) {
|
||||
if (!tile.cacheImageRecord) {
|
||||
$.console.warn(
|
||||
'[Drawer.drawTileToHTML] attempting to draw tile %s when it\'s not cached',
|
||||
'[Drawer._drawTileToHTML] attempting to draw tile %s when it\'s not cached',
|
||||
tile.toString());
|
||||
return;
|
||||
}
|
||||
@ -840,6 +786,13 @@ $.extend( $.Drawer.prototype, $.DrawerBase.prototype, /** @lends OpenSeadragon.D
|
||||
$.setElementOpacity( tile.element, tile.opacity );
|
||||
},
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @inner
|
||||
* Get the context of the main or sketch canvas
|
||||
* @param {Boolean} useSketch
|
||||
* @returns
|
||||
*/
|
||||
_getContext: function( useSketch ) {
|
||||
var context = this.context;
|
||||
if ( useSketch ) {
|
||||
@ -872,8 +825,14 @@ $.extend( $.Drawer.prototype, $.DrawerBase.prototype, /** @lends OpenSeadragon.D
|
||||
return context;
|
||||
},
|
||||
|
||||
// private
|
||||
saveContext: function( useSketch ) {
|
||||
/**
|
||||
* @private
|
||||
* @inner
|
||||
* Save the context of the main or sketch canvas
|
||||
* @param {Boolean} useSketch
|
||||
* @returns
|
||||
*/
|
||||
_saveContext: function( useSketch ) {
|
||||
if (!this.useCanvas) {
|
||||
return;
|
||||
}
|
||||
@ -881,8 +840,14 @@ $.extend( $.Drawer.prototype, $.DrawerBase.prototype, /** @lends OpenSeadragon.D
|
||||
this._getContext( useSketch ).save();
|
||||
},
|
||||
|
||||
// private
|
||||
restoreContext: function( useSketch ) {
|
||||
/**
|
||||
* @private
|
||||
* @inner
|
||||
* Restore the context of the main or sketch canvas
|
||||
* @param {Boolean} useSketch
|
||||
* @returns
|
||||
*/
|
||||
_restoreContext: function( useSketch ) {
|
||||
if (!this.useCanvas) {
|
||||
return;
|
||||
}
|
||||
@ -891,7 +856,7 @@ $.extend( $.Drawer.prototype, $.DrawerBase.prototype, /** @lends OpenSeadragon.D
|
||||
},
|
||||
|
||||
// private
|
||||
setClip: function(rect, useSketch) {
|
||||
_setClip: function(rect, useSketch) {
|
||||
if (!this.useCanvas) {
|
||||
return;
|
||||
}
|
||||
@ -1118,42 +1083,6 @@ $.extend( $.Drawer.prototype, $.DrawerBase.prototype, /** @lends OpenSeadragon.D
|
||||
context.restore();
|
||||
},
|
||||
|
||||
// private
|
||||
debugRect: function(rect) {
|
||||
if ( this.useCanvas ) {
|
||||
var context = this.context;
|
||||
context.save();
|
||||
context.lineWidth = 2 * $.pixelDensityRatio;
|
||||
context.strokeStyle = this.debugGridColor[0];
|
||||
context.fillStyle = this.debugGridColor[0];
|
||||
|
||||
context.strokeRect(
|
||||
rect.x * $.pixelDensityRatio,
|
||||
rect.y * $.pixelDensityRatio,
|
||||
rect.width * $.pixelDensityRatio,
|
||||
rect.height * $.pixelDensityRatio
|
||||
);
|
||||
|
||||
context.restore();
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
* Turns image smoothing on or off for this viewer. Note: Ignored in some (especially older) browsers that do not support this property.
|
||||
*
|
||||
* @function
|
||||
* @param {Boolean} [imageSmoothingEnabled] - Whether or not the image is
|
||||
* drawn smoothly on the canvas; see imageSmoothingEnabled in
|
||||
* {@link OpenSeadragon.Options} for more explanation.
|
||||
*/
|
||||
setImageSmoothingEnabled: function(imageSmoothingEnabled){
|
||||
if ( this.useCanvas ) {
|
||||
this._imageSmoothingEnabled = imageSmoothingEnabled;
|
||||
this._updateImageSmoothingEnabled(this.context);
|
||||
this.viewer.forceRedraw();
|
||||
}
|
||||
},
|
||||
|
||||
// private
|
||||
_updateImageSmoothingEnabled: function(context){
|
||||
context.msImageSmoothingEnabled = this._imageSmoothingEnabled;
|
||||
@ -1161,16 +1090,25 @@ $.extend( $.Drawer.prototype, $.DrawerBase.prototype, /** @lends OpenSeadragon.D
|
||||
},
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @inner
|
||||
* Get the canvas size
|
||||
* @param {Boolean} sketch If set to true return the size of the sketch canvas
|
||||
* @returns {OpenSeadragon.Point} The size of the canvas
|
||||
*/
|
||||
getCanvasSize: function(sketch) {
|
||||
_getCanvasSize: function(sketch) {
|
||||
var canvas = this._getContext(sketch).canvas;
|
||||
return new $.Point(canvas.width, canvas.height);
|
||||
},
|
||||
|
||||
getCanvasCenter: function() {
|
||||
/**
|
||||
* @private
|
||||
* @inner
|
||||
* Get the canvas center
|
||||
* @param {Boolean} sketch If set to true return the center point of the sketch canvas
|
||||
* @returns {OpenSeadragon.Point} The center point of the canvas
|
||||
*/
|
||||
_getCanvasCenter: function() {
|
||||
return new $.Point(this.canvas.width / 2, this.canvas.height / 2);
|
||||
},
|
||||
|
||||
@ -1178,7 +1116,7 @@ $.extend( $.Drawer.prototype, $.DrawerBase.prototype, /** @lends OpenSeadragon.D
|
||||
_offsetForRotation: function(options) {
|
||||
var point = options.point ?
|
||||
options.point.times($.pixelDensityRatio) :
|
||||
this.getCanvasCenter();
|
||||
this._getCanvasCenter();
|
||||
|
||||
var context = this._getContext(options.useSketch);
|
||||
context.save();
|
||||
@ -1198,7 +1136,7 @@ $.extend( $.Drawer.prototype, $.DrawerBase.prototype, /** @lends OpenSeadragon.D
|
||||
options = options || {};
|
||||
var point = options.point ?
|
||||
options.point.times($.pixelDensityRatio) :
|
||||
this.getCanvasCenter();
|
||||
this._getCanvasCenter();
|
||||
var context = this._getContext(options.useSketch);
|
||||
|
||||
context.translate(point.x, 0);
|
||||
@ -1240,90 +1178,7 @@ $.extend( $.Drawer.prototype, $.DrawerBase.prototype, /** @lends OpenSeadragon.D
|
||||
};
|
||||
},
|
||||
|
||||
// deprecated functions
|
||||
// deprecated
|
||||
addOverlay: function( element, location, placement, onDraw ) {
|
||||
$.console.error("drawer.addOverlay is deprecated. Use viewer.addOverlay instead.");
|
||||
this.viewer.addOverlay( element, location, placement, onDraw );
|
||||
return this;
|
||||
},
|
||||
|
||||
// deprecated
|
||||
updateOverlay: function( element, location, placement ) {
|
||||
$.console.error("drawer.updateOverlay is deprecated. Use viewer.updateOverlay instead.");
|
||||
this.viewer.updateOverlay( element, location, placement );
|
||||
return this;
|
||||
},
|
||||
|
||||
// deprecated
|
||||
removeOverlay: function( element ) {
|
||||
$.console.error("drawer.removeOverlay is deprecated. Use viewer.removeOverlay instead.");
|
||||
this.viewer.removeOverlay( element );
|
||||
return this;
|
||||
},
|
||||
|
||||
// deprecated
|
||||
clearOverlays: function() {
|
||||
$.console.error("drawer.clearOverlays is deprecated. Use viewer.clearOverlays instead.");
|
||||
this.viewer.clearOverlays();
|
||||
return this;
|
||||
},
|
||||
// deprecated
|
||||
needsUpdate: function() {
|
||||
$.console.error( "[Drawer.needsUpdate] this function is deprecated. Use World.needsDraw instead." );
|
||||
return this.viewer.world.needsDraw();
|
||||
},
|
||||
|
||||
// deprecated
|
||||
numTilesLoaded: function() {
|
||||
$.console.error( "[Drawer.numTilesLoaded] this function is deprecated. Use TileCache.numTilesLoaded instead." );
|
||||
return this.viewer.tileCache.numTilesLoaded();
|
||||
},
|
||||
|
||||
// deprecated
|
||||
reset: function() {
|
||||
$.console.error( "[Drawer.reset] this function is deprecated. Use World.resetItems instead." );
|
||||
this.viewer.world.resetItems();
|
||||
return this;
|
||||
},
|
||||
|
||||
// deprecated
|
||||
update: function() {
|
||||
$.console.error( "[Drawer.update] this function is deprecated. Use Drawer.clear and World.draw instead." );
|
||||
this.clear();
|
||||
this.viewer.world.draw();
|
||||
return this;
|
||||
},
|
||||
/**
|
||||
* Set the opacity of the drawer.
|
||||
* @param {Number} opacity
|
||||
* @returns {OpenSeadragon.Drawer} Chainable.
|
||||
*/
|
||||
setOpacity: function( opacity ) {
|
||||
$.console.error("drawer.setOpacity is deprecated. Use tiledImage.setOpacity instead.");
|
||||
var world = this.viewer.world;
|
||||
for (var i = 0; i < world.getItemCount(); i++) {
|
||||
world.getItemAt( i ).setOpacity( opacity );
|
||||
}
|
||||
return this;
|
||||
},
|
||||
|
||||
/**
|
||||
* Get the opacity of the drawer.
|
||||
* @returns {Number}
|
||||
*/
|
||||
getOpacity: function() {
|
||||
$.console.error("drawer.getOpacity is deprecated. Use tiledImage.getOpacity instead.");
|
||||
var world = this.viewer.world;
|
||||
var maxOpacity = 0;
|
||||
for (var i = 0; i < world.getItemCount(); i++) {
|
||||
var opacity = world.getItemAt( i ).getOpacity();
|
||||
if ( opacity > maxOpacity ) {
|
||||
maxOpacity = opacity;
|
||||
}
|
||||
}
|
||||
return maxOpacity;
|
||||
},
|
||||
});
|
||||
|
||||
|
||||
|
@ -98,6 +98,7 @@ $.DrawerBase = function( options ) {
|
||||
*/
|
||||
this.element = this.container;
|
||||
|
||||
// TO DO: Does this need to be in DrawerBase, or only in Drawer implementations?
|
||||
// We force our container to ltr because our drawing math doesn't work in rtl.
|
||||
// This issue only affects our canvas renderer, but we do it always for consistency.
|
||||
// Note that this means overlays you want to be rtl need to be explicitly set to rtl.
|
||||
@ -123,10 +124,6 @@ $.DrawerBase = function( options ) {
|
||||
this.container.style.textAlign = "left";
|
||||
this.container.appendChild( this.canvas );
|
||||
|
||||
// Image smoothing for canvas rendering (only if canvas is used).
|
||||
// Canvas default is "true", so this will only be changed if user specified "false".
|
||||
this._imageSmoothingEnabled = true;
|
||||
|
||||
this._checkForAPIOverrides();
|
||||
};
|
||||
|
||||
@ -134,14 +131,10 @@ $.DrawerBase = function( options ) {
|
||||
$.DrawerBase.prototype = {
|
||||
|
||||
// Drawer implementaions must define the next four methods. These are called
|
||||
// by core OSD, and forcing overrides (even for nullop methods) makes the
|
||||
// by core OSD and/or public APIs, and forcing overrides (even for nullop methods) makes the
|
||||
// behavior of the implementations explicitly clear in the code.
|
||||
// Whether these have been overridden by child classes is checked in the
|
||||
// constructor (via _checkForAPIOverrides). It could make sense to consolidate
|
||||
// these a bit (e.g. by making `draw` take an array of `TiledImage`s and
|
||||
// clearing the view as needed, rather than the existing pattern of
|
||||
// `drawer.clear(); world.draw()` in the calling code), but they have been
|
||||
// left as-is to maintain backwards compatibility.
|
||||
// constructor (via _checkForAPIOverrides).
|
||||
|
||||
/**
|
||||
* @param tiledImage the TiledImage that is ready to be drawn
|
||||
@ -164,13 +157,6 @@ $.DrawerBase.prototype = {
|
||||
$.console.error('Drawer.destroy must be implemented by child class');
|
||||
},
|
||||
|
||||
/**
|
||||
* Clears the Drawer so it's ready to draw another frame.
|
||||
*/
|
||||
clear: function() {
|
||||
$.console.error('Drawer.clear must be implemented by child class');
|
||||
},
|
||||
|
||||
/**
|
||||
* Turns image smoothing on or off for this viewer. Note: Ignored in some (especially older) browsers that do not support this property.
|
||||
*
|
||||
@ -184,8 +170,26 @@ $.DrawerBase.prototype = {
|
||||
},
|
||||
|
||||
/**
|
||||
* Ensures that child classes have provided implementations for API methods
|
||||
* draw, canRotate, destroy, and clear. Throws an exception if the original
|
||||
* Optional public API to draw a rectangle (e.g. for debugging purposes)
|
||||
* Child classes can override this method if they wish to support this
|
||||
* @param {OpenSeadragon.Rect} rect
|
||||
*/
|
||||
drawDebuggingRect: function(rect) {
|
||||
$.console.warn('[drawer].drawDebuggingRect is not implemented by this drawer');
|
||||
},
|
||||
|
||||
// Deprecated functions
|
||||
clear: function(){
|
||||
$.console.warn('[drawer].clear() is deprecated. The drawer is responsible for clearing itself as needed before drawing tiles.');
|
||||
},
|
||||
|
||||
// Private functions
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @inner
|
||||
* Ensures that child classes have provided implementations for public API methods
|
||||
* draw, canRotate, destroy, and setImageSmoothinEnabled. Throws an exception if the original
|
||||
* placeholder methods are still in place.
|
||||
*/
|
||||
_checkForAPIOverrides: function(){
|
||||
@ -198,21 +202,24 @@ $.DrawerBase.prototype = {
|
||||
if(this.destroy === $.DrawerBase.prototype.destroy){
|
||||
throw("[drawer].destroy must be implemented by child class");
|
||||
}
|
||||
if(this.clear === $.DrawerBase.prototype.clear){
|
||||
throw("[drawer].clear must be implemented by child class");
|
||||
}
|
||||
|
||||
if(this.setImageSmoothingEnabled === $.DrawerBase.prototype.setImageSmoothingEnabled){
|
||||
throw("[drawer].setImageSmoothingEnabled must be implemented by child class");
|
||||
}
|
||||
},
|
||||
|
||||
|
||||
// Utility functions internal API
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @inner
|
||||
* Scale from OpenSeadragon viewer rectangle to drawer rectangle
|
||||
* (ignoring rotation)
|
||||
* @param {OpenSeadragon.Rect} rectangle - The rectangle in viewport coordinate system.
|
||||
* @returns {OpenSeadragon.Rect} Rectangle in drawer coordinate system.
|
||||
*/
|
||||
viewportToDrawerRectangle: function(rectangle) {
|
||||
_viewportToDrawerRectangle: function(rectangle) {
|
||||
var topLeft = this.viewport.pixelFromPointNoRotate(rectangle.getTopLeft(), true);
|
||||
var size = this.viewport.deltaPixelsFromPointsNoRotate(rectangle.getSize(), true);
|
||||
|
||||
@ -225,6 +232,8 @@ $.DrawerBase.prototype = {
|
||||
},
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @inner
|
||||
* This function converts the given point from to the drawer coordinate by
|
||||
* multiplying it with the pixel density.
|
||||
* This function does not take rotation into account, thus assuming provided
|
||||
@ -232,7 +241,7 @@ $.DrawerBase.prototype = {
|
||||
* @param {OpenSeadragon.Point} point - the pixel point to convert
|
||||
* @returns {OpenSeadragon.Point} Point in drawer coordinate system.
|
||||
*/
|
||||
viewportCoordToDrawerCoord: function(point) {
|
||||
_viewportCoordToDrawerCoord: function(point) {
|
||||
var vpPoint = this.viewport.pixelFromPointNoRotate(point, true);
|
||||
return new $.Point(
|
||||
vpPoint.x * $.pixelDensityRatio,
|
||||
@ -240,8 +249,13 @@ $.DrawerBase.prototype = {
|
||||
);
|
||||
},
|
||||
|
||||
|
||||
// private
|
||||
/**
|
||||
* @private
|
||||
* @inner
|
||||
* Calculate width and height of the canvas based on viewport dimensions
|
||||
* and pixelDensityRatio
|
||||
* @returns {Dictionary} {x, y} size of the canvas
|
||||
*/
|
||||
_calculateCanvasSize: function() {
|
||||
var pixelDensityRatio = $.pixelDensityRatio;
|
||||
var viewportSize = this.viewport.getContainerSize();
|
||||
@ -252,86 +266,6 @@ $.DrawerBase.prototype = {
|
||||
};
|
||||
},
|
||||
|
||||
|
||||
/* Deprecated Functions */
|
||||
|
||||
// deprecated
|
||||
addOverlay: function( element, location, placement, onDraw ) {
|
||||
$.console.error("drawer.addOverlay is deprecated. Use viewer.addOverlay instead.");
|
||||
this.viewer.addOverlay( element, location, placement, onDraw );
|
||||
return this;
|
||||
},
|
||||
|
||||
// deprecated
|
||||
updateOverlay: function( element, location, placement ) {
|
||||
$.console.error("drawer.updateOverlay is deprecated. Use viewer.updateOverlay instead.");
|
||||
this.viewer.updateOverlay( element, location, placement );
|
||||
return this;
|
||||
},
|
||||
|
||||
// deprecated
|
||||
removeOverlay: function( element ) {
|
||||
$.console.error("drawer.removeOverlay is deprecated. Use viewer.removeOverlay instead.");
|
||||
this.viewer.removeOverlay( element );
|
||||
return this;
|
||||
},
|
||||
|
||||
// deprecated
|
||||
clearOverlays: function() {
|
||||
$.console.error("drawer.clearOverlays is deprecated. Use viewer.clearOverlays instead.");
|
||||
this.viewer.clearOverlays();
|
||||
return this;
|
||||
},
|
||||
// deprecated
|
||||
needsUpdate: function() {
|
||||
$.console.error( "[Drawer.needsUpdate] this function is deprecated. Use World.needsDraw instead." );
|
||||
return this.viewer.world.needsDraw();
|
||||
},
|
||||
|
||||
// deprecated
|
||||
numTilesLoaded: function() {
|
||||
$.console.error( "[Drawer.numTilesLoaded] this function is deprecated. Use TileCache.numTilesLoaded instead." );
|
||||
return this.viewer.tileCache.numTilesLoaded();
|
||||
},
|
||||
|
||||
// deprecated
|
||||
reset: function() {
|
||||
$.console.error( "[Drawer.reset] this function is deprecated. Use World.resetItems instead." );
|
||||
this.viewer.world.resetItems();
|
||||
return this;
|
||||
},
|
||||
|
||||
// deprecated
|
||||
update: function() {
|
||||
$.console.error( "[Drawer.update] this function is deprecated. Use Drawer.clear and World.draw instead." );
|
||||
this.clear();
|
||||
this.viewer.world.draw();
|
||||
return this;
|
||||
},
|
||||
|
||||
// deprecated
|
||||
setOpacity: function( opacity ) {
|
||||
$.console.error("drawer.setOpacity is deprecated. Use tiledImage.setOpacity instead.");
|
||||
var world = this.viewer.world;
|
||||
for (var i = 0; i < world.getItemCount(); i++) {
|
||||
world.getItemAt( i ).setOpacity( opacity );
|
||||
}
|
||||
return this;
|
||||
},
|
||||
|
||||
// deprecated
|
||||
getOpacity: function() {
|
||||
$.console.error("drawer.getOpacity is deprecated. Use tiledImage.getOpacity instead.");
|
||||
var world = this.viewer.world;
|
||||
var maxOpacity = 0;
|
||||
for (var i = 0; i < world.getItemCount(); i++) {
|
||||
var opacity = world.getItemAt( i ).getOpacity();
|
||||
if ( opacity > maxOpacity ) {
|
||||
maxOpacity = opacity;
|
||||
}
|
||||
}
|
||||
return maxOpacity;
|
||||
},
|
||||
};
|
||||
|
||||
Object.defineProperty($.DrawerBase.prototype, "isOpenSeadragonDrawer", {
|
||||
|
@ -310,7 +310,6 @@ $.extend( $.Navigator.prototype, $.EventSource.prototype, $.Viewer.prototype, /*
|
||||
this.viewport.resize( containerSize, true );
|
||||
this.viewport.goHome(true);
|
||||
this.oldContainerSize = containerSize;
|
||||
this.drawer.clear();
|
||||
this.world.draw();
|
||||
}
|
||||
}
|
||||
|
@ -1238,6 +1238,10 @@ $.extend($.TiledImage.prototype, $.EventSource.prototype, /** @lends OpenSeadrag
|
||||
};
|
||||
},
|
||||
|
||||
/**
|
||||
*
|
||||
* @returns {Array} Array of Tiles within the viewport which should be drawn
|
||||
*/
|
||||
getTileInfoForDrawing: function(){
|
||||
return this._tilesToDraw;
|
||||
},
|
||||
@ -1342,9 +1346,6 @@ $.extend($.TiledImage.prototype, $.EventSource.prototype, /** @lends OpenSeadrag
|
||||
} else {
|
||||
this._setFullyLoaded(this._tilesLoading === 0);
|
||||
}
|
||||
|
||||
|
||||
// return bestTile;
|
||||
},
|
||||
|
||||
/**
|
||||
|
@ -3811,7 +3811,6 @@ function updateOnce( viewer ) {
|
||||
|
||||
function drawWorld( viewer ) {
|
||||
viewer.imageLoader.clear();
|
||||
viewer.drawer.clear();
|
||||
viewer.world.draw();
|
||||
|
||||
/**
|
||||
|
@ -256,10 +256,7 @@ $.extend( $.World.prototype, $.EventSource.prototype, /** @lends OpenSeadragon.W
|
||||
* Draws all items.
|
||||
*/
|
||||
draw: function() {
|
||||
for ( var i = 0; i < this._items.length; i++ ) {
|
||||
this.viewer.drawer.draw(this._items[i]);
|
||||
}
|
||||
|
||||
this.viewer.drawer.draw(this._items);
|
||||
this._needsDraw = false;
|
||||
},
|
||||
|
||||
|
@ -131,8 +131,8 @@
|
||||
var box = new OpenSeadragon.Rect(margins.left, margins.top,
|
||||
$('#contentDiv').width() - (margins.left + margins.right),
|
||||
$('#contentDiv').height() - (margins.top + margins.bottom));
|
||||
|
||||
self.viewer.drawer.debugRect(box);
|
||||
// if drawDebuggingRect is implemented, use it to show the box
|
||||
self.viewer.drawer.drawDebuggingRect(box);
|
||||
});
|
||||
}
|
||||
|
||||
|
@ -106,7 +106,9 @@ export class ThreeJSDrawer extends OpenSeadragon.DrawerBase{
|
||||
}
|
||||
|
||||
// Public API required by all Drawer implementations
|
||||
|
||||
/**
|
||||
* Clean up the renderer, removing all resources
|
||||
*/
|
||||
destroy(){
|
||||
// clear all resources used by the renderer, geometries, textures etc
|
||||
|
||||
@ -123,26 +125,61 @@ export class ThreeJSDrawer extends OpenSeadragon.DrawerBase{
|
||||
this._camera = null;
|
||||
|
||||
}
|
||||
clear(){
|
||||
//not needed by this implementation
|
||||
}
|
||||
|
||||
// Public API required by all Drawer implementations
|
||||
/**
|
||||
*
|
||||
* @returns true if the drawer supports rotation
|
||||
*/
|
||||
canRotate(){
|
||||
return true;
|
||||
}
|
||||
draw(tiledImage){
|
||||
|
||||
// Public API required by all Drawer implementations
|
||||
/**
|
||||
*
|
||||
* @param {Array} tiledImages Array of TiledImage objects to draw
|
||||
*/
|
||||
draw(tiledImages){
|
||||
// actual drawing is handled by event listeneners
|
||||
// just mark this tiledImage as having been drawn (possibly unnecessary)
|
||||
tiledImage._needsDraw = false;
|
||||
// just mark the tiledImages as having been drawn (possibly unnecessary)
|
||||
tiledImages.forEach(tiledImage => tiledImage._needsDraw = false);
|
||||
}
|
||||
|
||||
// Public API required by all Drawer implementations
|
||||
/**
|
||||
* Set the context2d imageSmoothingEnabled parameter
|
||||
* @param {Boolean} enabled
|
||||
*/
|
||||
setImageSmoothingEnabled(enabled){
|
||||
this._clippingContext.imageSmoothingEnabled = enabled;
|
||||
this._outputContext.imageSmoothingEnabled = enabled;
|
||||
}
|
||||
|
||||
/**
|
||||
* Draw a rect onto the output canvas for debugging purposes
|
||||
* @param {OpenSeadragon.Rect} rect
|
||||
*/
|
||||
drawDebuggingRect(rect){
|
||||
let context = this._outputContext;
|
||||
context.save();
|
||||
context.lineWidth = 2 * OpenSeadragon.pixelDensityRatio;
|
||||
context.strokeStyle = this.debugGridColor[0];
|
||||
context.fillStyle = this.debugGridColor[0];
|
||||
|
||||
context.strokeRect(
|
||||
rect.x * OpenSeadragon.pixelDensityRatio,
|
||||
rect.y * OpenSeadragon.pixelDensityRatio,
|
||||
rect.width * OpenSeadragon.pixelDensityRatio,
|
||||
rect.height * OpenSeadragon.pixelDensityRatio
|
||||
);
|
||||
|
||||
context.restore();
|
||||
}
|
||||
|
||||
// Private methods
|
||||
|
||||
_setupRenderer(){
|
||||
//to do: test support for pages of sequence mode
|
||||
|
||||
let viewerBounds = this.viewer.viewport.getBoundsNoRotate();
|
||||
this._camera = new THREE.OrthographicCamera(
|
||||
@ -171,13 +208,6 @@ export class ThreeJSDrawer extends OpenSeadragon.DrawerBase{
|
||||
this.viewer.addHandler("viewport-change", () => this._viewportChangeHandler());
|
||||
this.viewer.addHandler("home", () => this._viewportChangeHandler());
|
||||
|
||||
// this.viewer.world.addHandler("item-index-change", () => this.renderFrame());
|
||||
// this.viewer.addHandler("crop-change", () => this.renderFrame());
|
||||
// this.viewer.addHandler("clip-change", () => this.renderFrame());
|
||||
// this.viewer.addHandler("opacity-change", () => this.renderFrame());
|
||||
// this.viewer.addHandler("composite-operation-change", () => this.renderFrame());
|
||||
|
||||
|
||||
this.viewer.addHandler("update-viewport", () => this.renderFrame());
|
||||
|
||||
this._viewportChangeHandler();
|
||||
@ -476,7 +506,7 @@ export class ThreeJSDrawer extends OpenSeadragon.DrawerBase{
|
||||
|
||||
if(item._clip){
|
||||
var box = item.imageToViewportRectangle(item._clip, true);
|
||||
var rect = this.viewportToDrawerRectangle(box);
|
||||
var rect = this._viewportToDrawerRectangle(box);
|
||||
this._clippingContext.beginPath();
|
||||
this._clippingContext.rect(rect.x, rect.y, rect.width, rect.height);
|
||||
this._clippingContext.clip();
|
||||
@ -486,7 +516,7 @@ export class ThreeJSDrawer extends OpenSeadragon.DrawerBase{
|
||||
return polygon.map(function (coord) {
|
||||
let point = item.imageToViewportCoordinates(coord.x, coord.y, true)
|
||||
.rotate(_this.viewer.viewport.getRotation(true), _this.viewer.viewport.getCenter(true));
|
||||
let clipPoint = _this.viewportCoordToDrawerCoord(point);
|
||||
let clipPoint = _this._viewportCoordToDrawerCoord(point);
|
||||
return clipPoint;
|
||||
});
|
||||
});
|
||||
@ -625,6 +655,7 @@ export class ThreeJSDrawer extends OpenSeadragon.DrawerBase{
|
||||
context.restore();
|
||||
}
|
||||
|
||||
// private
|
||||
_drawDebugInfo( tiledImage ) {
|
||||
let scene = this._tiledImageMap[tiledImage[this._uuid]];
|
||||
let level = scene.userData.currentLevel;
|
||||
@ -641,25 +672,6 @@ export class ThreeJSDrawer extends OpenSeadragon.DrawerBase{
|
||||
}
|
||||
}
|
||||
|
||||
// private
|
||||
_debugRect(rect) {
|
||||
if ( this.useCanvas ) {
|
||||
var context = this._outputContext;
|
||||
context.save();
|
||||
context.lineWidth = 2 * OpenSeadragon.pixelDensityRatio;
|
||||
context.strokeStyle = this.debugGridColor[0];
|
||||
context.fillStyle = this.debugGridColor[0];
|
||||
|
||||
context.strokeRect(
|
||||
rect.x * OpenSeadragon.pixelDensityRatio,
|
||||
rect.y * OpenSeadragon.pixelDensityRatio,
|
||||
rect.width * OpenSeadragon.pixelDensityRatio,
|
||||
rect.height * OpenSeadragon.pixelDensityRatio
|
||||
);
|
||||
|
||||
context.restore();
|
||||
}
|
||||
}
|
||||
|
||||
// private
|
||||
_restoreRotationChanges() {
|
||||
|
@ -111,7 +111,7 @@
|
||||
|
||||
<div id="image-picker">
|
||||
<h3>Image options (drag and drop to re-order images)</h3>
|
||||
<div class="image-options">
|
||||
<!-- <div class="image-options">
|
||||
<span class="ui-icon ui-icon-arrowthick-2-n-s"></span>
|
||||
<label><input type="checkbox" checked data-image="rainbow" class="toggle"> Rainbow Grid</label>
|
||||
<div class="option-grid">
|
||||
@ -159,7 +159,7 @@
|
||||
<label>Composite: <select data-image="bblue" data-field="composite"></select></label>
|
||||
<label>Wrapping: <select data-image="bblue" data-field="wrapping"></select></label>
|
||||
</div>
|
||||
</div>
|
||||
</div> -->
|
||||
|
||||
</div>
|
||||
|
||||
|
@ -10,11 +10,24 @@ const sources = {
|
||||
type:'image',
|
||||
url: "../data/BBlue.png",
|
||||
},
|
||||
"duomo":"https://openseadragon.github.io/example-images/duomo/duomo.dzi",
|
||||
}
|
||||
const labels = {
|
||||
rainbow: 'Rainbow Grid',
|
||||
leaves: 'Leaves',
|
||||
bblue: 'Blue B',
|
||||
duomo: 'Duomo',
|
||||
}
|
||||
var viewer = window.viewer = OpenSeadragon({
|
||||
id: "contentDiv",
|
||||
prefixUrl: "../../build/openseadragon/images/",
|
||||
// minZoomImageRatio:0.8,
|
||||
// maxZoomPixelRatio:0.5,
|
||||
minZoomImageRatio:0.01,
|
||||
maxZoomPixelRatio:100,
|
||||
smoothTileEdgesMinZoom:1.1,
|
||||
crossOriginPolicy: 'Anonymous',
|
||||
ajaxWithCredentials: false
|
||||
});
|
||||
|
||||
let threeRenderer = window.threeRenderer = new ThreeJSDrawer({viewer, viewport: viewer.viewport, element:viewer.element});
|
||||
@ -24,8 +37,11 @@ var viewer2 = window.viewer2 = OpenSeadragon({
|
||||
prefixUrl: "../../build/openseadragon/images/",
|
||||
minZoomImageRatio:0.01,
|
||||
customDrawer: ThreeJSDrawer,
|
||||
tileSources: sources['leaves'],
|
||||
tileSources: [sources['leaves'], sources['rainbow'], sources['duomo']],
|
||||
sequenceMode: true,
|
||||
imageSmoothingEnabled: false,
|
||||
crossOriginPolicy: 'Anonymous',
|
||||
ajaxWithCredentials: false
|
||||
});
|
||||
|
||||
//make the test canvas mirror all changes to the viewer canvas
|
||||
@ -54,6 +70,13 @@ $('#image-picker').sortable({
|
||||
}
|
||||
});
|
||||
|
||||
Object.keys(sources).forEach((key, index)=>{
|
||||
let element = makeImagePickerElement(key, labels[key])
|
||||
$('#image-picker').append(element);
|
||||
if(index === 0){
|
||||
element.find('.toggle').prop('checked',true);
|
||||
}
|
||||
})
|
||||
|
||||
$('#image-picker input.toggle').on('change',function(){
|
||||
let data = $(this).data();
|
||||
@ -193,7 +216,26 @@ function addTileSource(image, checkbox){
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
function makeImagePickerElement(key, label){
|
||||
return $(`<div class="image-options">
|
||||
<span class="ui-icon ui-icon-arrowthick-2-n-s"></span>
|
||||
<label><input type="checkbox" data-image="" class="toggle"> __title__</label>
|
||||
<div class="option-grid">
|
||||
<label>X: <input type="number" value="0" data-image="" data-field="x"> </label>
|
||||
<label>Y: <input type="number" value="0" data-image="" data-field="y"> </label>
|
||||
<label>Width: <input type="number" value="1" data-image="" data-field="width" min="0"> </label>
|
||||
<label>Degrees: <input type="number" value="0" data-image="" data-field="degrees"> </label>
|
||||
<label>Opacity: <input type="number" value="1" data-image="" data-field="opacity" min="0" max="1" step="0.2"> </label>
|
||||
<label>Flipped: <input type="checkbox" data-image="" data-field="flipped"></label>
|
||||
<label>Cropped: <input type="checkbox" data-image="" data-field="cropped"></label>
|
||||
<label>Debug: <input type="checkbox" data-image="" data-field="debug"></label>
|
||||
<label>Composite: <select data-image="" data-field="composite"></select></label>
|
||||
<label>Wrapping: <select data-image="" data-field="wrapping"></select></label>
|
||||
</div>
|
||||
|
||||
</div>`.replaceAll('data-image=""', `data-image="${key}"`).replace('__title__', label));
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
@ -181,7 +181,8 @@
|
||||
done();
|
||||
});
|
||||
|
||||
image.draw();
|
||||
//image.draw(); // TO DO: Is this necessary for the test? It will now fail since tiledImage.draw() is not a thing.
|
||||
viewer.drawer.draw( [ image ] );
|
||||
});
|
||||
|
||||
viewer.open('/test/data/testpattern.dzi');
|
||||
@ -225,7 +226,7 @@
|
||||
image.setClip(clip);
|
||||
assert.propEqual(image.getClip(), clip, 'clip is set correctly');
|
||||
|
||||
Util.spyOnce(viewer.drawer, 'setClip', function(rect) {
|
||||
Util.spyOnce(viewer.drawer, '_setClip', function(rect) {
|
||||
var homeBounds = viewer.viewport.getHomeBounds();
|
||||
var canvasClip = viewer.drawer
|
||||
.viewportToDrawerRectangle(homeBounds);
|
||||
|
Loading…
Reference in New Issue
Block a user