mirror of
https://github.com/openseadragon/openseadragon.git
synced 2024-11-21 20:56:09 +03:00
commit
e25cdd85f9
241
src/drawer.js
241
src/drawer.js
@ -87,8 +87,7 @@ $.Drawer = function( options ) {
|
||||
|
||||
|
||||
//internal state / configurable settings
|
||||
overlays: [], // An unordered list of Overlays added.
|
||||
collectionOverlays: {},
|
||||
collectionOverlays: {}, // For collection mode. Here an overlay is actually a viewer.
|
||||
|
||||
//configurable settings
|
||||
maxImageCacheCount: $.DEFAULT_SETTINGS.maxImageCacheCount,
|
||||
@ -148,18 +147,6 @@ $.Drawer = function( options ) {
|
||||
this.container.style.textAlign = "left";
|
||||
this.container.appendChild( this.canvas );
|
||||
|
||||
//create the correct type of overlay by convention if the overlays
|
||||
//are not already OpenSeadragon.Overlays
|
||||
for( i = 0; i < this.overlays.length; i++ ){
|
||||
if( $.isPlainObject( this.overlays[ i ] ) ){
|
||||
|
||||
this.overlays[ i ] = addOverlayFromConfiguration( this, this.overlays[ i ]);
|
||||
|
||||
} else if ( $.isFunction( this.overlays[ i ] ) ){
|
||||
//TODO
|
||||
}
|
||||
}
|
||||
|
||||
//this.profiler = new $.Profiler();
|
||||
};
|
||||
|
||||
@ -177,57 +164,15 @@ $.Drawer.prototype = /** @lends OpenSeadragon.Drawer.prototype */{
|
||||
* @param {OpenSeadragon.OverlayPlacement} placement - The position of the
|
||||
* viewport which the location coordinates will be treated as relative
|
||||
* to.
|
||||
* @param {function} onDraw - If supplied the callback is called when the overlay
|
||||
* @param {function} onDraw - If supplied the callback is called when the overlay
|
||||
* needs to be drawn. It it the responsibility of the callback to do any drawing/positioning.
|
||||
* It is passed position, size and element.
|
||||
* @fires OpenSeadragon.Viewer.event:add-overlay
|
||||
* @deprecated - use {@link OpenSeadragon.Viewer#addOverlay} instead.
|
||||
*/
|
||||
addOverlay: function( element, location, placement, onDraw ) {
|
||||
var options;
|
||||
if( $.isPlainObject( element ) ){
|
||||
options = element;
|
||||
} else {
|
||||
options = {
|
||||
element: element,
|
||||
location: location,
|
||||
placement: placement,
|
||||
onDraw: onDraw
|
||||
};
|
||||
}
|
||||
|
||||
element = $.getElement(options.element);
|
||||
|
||||
if ( getOverlayIndex( this.overlays, element ) >= 0 ) {
|
||||
// they're trying to add a duplicate overlay
|
||||
return;
|
||||
}
|
||||
|
||||
this.overlays.push( new $.Overlay({
|
||||
element: element,
|
||||
location: options.location,
|
||||
placement: options.placement,
|
||||
onDraw: options.onDraw
|
||||
}) );
|
||||
this.updateAgain = true;
|
||||
if( this.viewer ){
|
||||
/**
|
||||
* Raised when an overlay is added to the viewer (see {@link OpenSeadragon.Drawer#addOverlay}).
|
||||
*
|
||||
* @event add-overlay
|
||||
* @memberof OpenSeadragon.Viewer
|
||||
* @type {object}
|
||||
* @property {OpenSeadragon.Viewer} eventSource - A reference to the Viewer which raised the event.
|
||||
* @property {Element} element - The overlay element.
|
||||
* @property {OpenSeadragon.Point|OpenSeadragon.Rect} location
|
||||
* @property {OpenSeadragon.OverlayPlacement} placement
|
||||
* @property {?Object} userData - Arbitrary subscriber-defined object.
|
||||
*/
|
||||
this.viewer.raiseEvent( 'add-overlay', {
|
||||
element: element,
|
||||
location: options.location,
|
||||
placement: options.placement
|
||||
});
|
||||
}
|
||||
$.console.error("drawer.addOverlay is deprecated. Use viewer.addOverlay instead.");
|
||||
this.viewer.addOverlay( element, location, placement, onDraw );
|
||||
return this;
|
||||
},
|
||||
|
||||
@ -242,36 +187,11 @@ $.Drawer.prototype = /** @lends OpenSeadragon.Drawer.prototype */{
|
||||
* to.
|
||||
* @return {OpenSeadragon.Drawer} Chainable.
|
||||
* @fires OpenSeadragon.Viewer.event:update-overlay
|
||||
* @deprecated - use {@link OpenSeadragon.Viewer#updateOverlay} instead.
|
||||
*/
|
||||
updateOverlay: function( element, location, placement ) {
|
||||
var i;
|
||||
|
||||
element = $.getElement( element );
|
||||
i = getOverlayIndex( this.overlays, element );
|
||||
|
||||
if ( i >= 0 ) {
|
||||
this.overlays[ i ].update( location, placement );
|
||||
this.updateAgain = true;
|
||||
}
|
||||
if( this.viewer ){
|
||||
/**
|
||||
* Raised when an overlay's location or placement changes (see {@link OpenSeadragon.Drawer#updateOverlay}).
|
||||
*
|
||||
* @event update-overlay
|
||||
* @memberof OpenSeadragon.Viewer
|
||||
* @type {object}
|
||||
* @property {OpenSeadragon.Viewer} eventSource - A reference to the Viewer which raised the event.
|
||||
* @property {Element} element
|
||||
* @property {OpenSeadragon.Point|OpenSeadragon.Rect} location
|
||||
* @property {OpenSeadragon.OverlayPlacement} placement
|
||||
* @property {?Object} userData - Arbitrary subscriber-defined object.
|
||||
*/
|
||||
this.viewer.raiseEvent( 'update-overlay', {
|
||||
element: element,
|
||||
location: location,
|
||||
placement: placement
|
||||
});
|
||||
}
|
||||
$.console.error("drawer.updateOverlay is deprecated. Use viewer.updateOverlay instead.");
|
||||
this.viewer.updateOverlay( element, location, placement );
|
||||
return this;
|
||||
},
|
||||
|
||||
@ -283,33 +203,11 @@ $.Drawer.prototype = /** @lends OpenSeadragon.Drawer.prototype */{
|
||||
* element id which represent the ovelay content to be removed.
|
||||
* @return {OpenSeadragon.Drawer} Chainable.
|
||||
* @fires OpenSeadragon.Viewer.event:remove-overlay
|
||||
* @deprecated - use {@link OpenSeadragon.Viewer#removeOverlay} instead.
|
||||
*/
|
||||
removeOverlay: function( element ) {
|
||||
var i;
|
||||
|
||||
element = $.getElement( element );
|
||||
i = getOverlayIndex( this.overlays, element );
|
||||
|
||||
if ( i >= 0 ) {
|
||||
this.overlays[ i ].destroy();
|
||||
this.overlays.splice( i, 1 );
|
||||
this.updateAgain = true;
|
||||
}
|
||||
if( this.viewer ){
|
||||
/**
|
||||
* Raised when an overlay is removed from the viewer (see {@link OpenSeadragon.Drawer#removeOverlay}).
|
||||
*
|
||||
* @event remove-overlay
|
||||
* @memberof OpenSeadragon.Viewer
|
||||
* @type {object}
|
||||
* @property {OpenSeadragon.Viewer} eventSource - A reference to the Viewer which raised the event.
|
||||
* @property {Element} element - The overlay element.
|
||||
* @property {?Object} userData - Arbitrary subscriber-defined object.
|
||||
*/
|
||||
this.viewer.raiseEvent( 'remove-overlay', {
|
||||
element: element
|
||||
});
|
||||
}
|
||||
$.console.error("drawer.removeOverlay is deprecated. Use viewer.removeOverlay instead.");
|
||||
this.viewer.updateOverlay( element );
|
||||
return this;
|
||||
},
|
||||
|
||||
@ -319,28 +217,14 @@ $.Drawer.prototype = /** @lends OpenSeadragon.Drawer.prototype */{
|
||||
* @method
|
||||
* @return {OpenSeadragon.Drawer} Chainable.
|
||||
* @fires OpenSeadragon.Viewer.event:clear-overlay
|
||||
* @deprecated - use {@link OpenSeadragon.Viewer#clearOverlays} instead.
|
||||
*/
|
||||
clearOverlays: function() {
|
||||
while ( this.overlays.length > 0 ) {
|
||||
this.overlays.pop().destroy();
|
||||
this.updateAgain = true;
|
||||
}
|
||||
if( this.viewer ){
|
||||
/**
|
||||
* Raised when all overlays are removed from the viewer (see {@link OpenSeadragon.Drawer#clearOverlays}).
|
||||
*
|
||||
* @event clear-overlay
|
||||
* @memberof OpenSeadragon.Viewer
|
||||
* @type {object}
|
||||
* @property {OpenSeadragon.Viewer} eventSource - A reference to the Viewer which raised the event.
|
||||
* @property {?Object} userData - Arbitrary subscriber-defined object.
|
||||
*/
|
||||
this.viewer.raiseEvent( 'clear-overlay', {} );
|
||||
}
|
||||
$.console.error("drawer.clearOverlays is deprecated. Use viewer.clearOverlays instead.");
|
||||
this.viewer.clearOverlays();
|
||||
return this;
|
||||
},
|
||||
|
||||
|
||||
/**
|
||||
* Returns whether the Drawer is scheduled for an update at the
|
||||
* soonest possible opportunity.
|
||||
@ -467,61 +351,6 @@ $.Drawer.prototype = /** @lends OpenSeadragon.Drawer.prototype */{
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @inner
|
||||
*/
|
||||
function addOverlayFromConfiguration( drawer, overlay ){
|
||||
|
||||
var element = null,
|
||||
rect = ( overlay.height && overlay.width ) ? new $.Rect(
|
||||
overlay.x || overlay.px,
|
||||
overlay.y || overlay.py,
|
||||
overlay.width,
|
||||
overlay.height
|
||||
) : new $.Point(
|
||||
overlay.x || overlay.px,
|
||||
overlay.y || overlay.py
|
||||
),
|
||||
id = overlay.id ?
|
||||
overlay.id :
|
||||
"openseadragon-overlay-"+Math.floor(Math.random()*10000000);
|
||||
|
||||
element = $.getElement(overlay.id);
|
||||
if( !element ){
|
||||
element = document.createElement("a");
|
||||
element.href = "#/overlay/"+id;
|
||||
}
|
||||
element.id = id;
|
||||
$.addClass( element, overlay.className ?
|
||||
overlay.className :
|
||||
"openseadragon-overlay"
|
||||
);
|
||||
|
||||
|
||||
if(overlay.px !== undefined){
|
||||
//if they specified 'px' so it's in pixel coordinates so
|
||||
//we need to translate to viewport coordinates
|
||||
rect = drawer.viewport.imageToViewportRectangle( rect );
|
||||
}
|
||||
|
||||
if( overlay.placement ){
|
||||
return new $.Overlay({
|
||||
element: element,
|
||||
location: drawer.viewport.pointFromPixel(rect),
|
||||
placement: $.OverlayPlacement[overlay.placement.toUpperCase()],
|
||||
onDraw: overlay.onDraw
|
||||
});
|
||||
}else{
|
||||
return new $.Overlay({
|
||||
element: element,
|
||||
location: rect,
|
||||
onDraw: overlay.onDraw
|
||||
});
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @inner
|
||||
@ -695,7 +524,6 @@ function updateViewport( drawer ) {
|
||||
|
||||
//TODO
|
||||
drawTiles( drawer, drawer.lastDrawn );
|
||||
drawOverlays( drawer.viewport, drawer.overlays, drawer.container );
|
||||
|
||||
//TODO
|
||||
if ( best ) {
|
||||
@ -1142,23 +970,6 @@ function resetCoverage( coverage, level ) {
|
||||
coverage[ level ] = {};
|
||||
}
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @inner
|
||||
* Determines the 'z-index' of the given overlay. Overlays are ordered in
|
||||
* a z-index based on the order they are added to the Drawer.
|
||||
*/
|
||||
function getOverlayIndex( overlays, element ) {
|
||||
var i;
|
||||
for ( i = overlays.length - 1; i >= 0; i-- ) {
|
||||
if ( overlays[ i ].element == element ) {
|
||||
return i;
|
||||
}
|
||||
}
|
||||
|
||||
return -1;
|
||||
}
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @inner
|
||||
@ -1196,28 +1007,6 @@ function finishLoadingImage( image, callback, successful, jobid ){
|
||||
|
||||
}
|
||||
|
||||
|
||||
function drawOverlays( viewport, overlays, container ){
|
||||
var i,
|
||||
length = overlays.length;
|
||||
for ( i = 0; i < length; i++ ) {
|
||||
drawOverlay( viewport, overlays[ i ], container );
|
||||
}
|
||||
}
|
||||
|
||||
function drawOverlay( viewport, overlay, container ){
|
||||
|
||||
overlay.position = viewport.pixelFromPoint(
|
||||
overlay.bounds.getTopLeft(),
|
||||
true
|
||||
);
|
||||
overlay.size = viewport.deltaPixelsFromPoints(
|
||||
overlay.bounds.getSize(),
|
||||
true
|
||||
);
|
||||
overlay.drawHTML( container, viewport );
|
||||
}
|
||||
|
||||
function drawTiles( drawer, lastDrawn ){
|
||||
var i,
|
||||
tile,
|
||||
@ -1297,7 +1086,7 @@ function drawTiles( drawer, lastDrawn ){
|
||||
')';
|
||||
}
|
||||
|
||||
drawer.addOverlay(
|
||||
drawer.viewer.addOverlay(
|
||||
viewer.element,
|
||||
tile.bounds
|
||||
);
|
||||
|
@ -136,6 +136,28 @@
|
||||
* is an Array of objects, it is used to create a
|
||||
* {@link OpenSeadragon.LegacyTileSource}.
|
||||
*
|
||||
* @property {Array} overlays Array of objects defining permanent overlays of
|
||||
* the viewer. The overlays added via this option and later removed with
|
||||
* {@link OpenSeadragon.Viewer#removeOverlay} will be added back when a new
|
||||
* image is opened.
|
||||
* To add overlays which can be definitively removed, one must use
|
||||
* {@link OpenSeadragon.Viewer#addOverlay}
|
||||
* If displaying a sequence of images, the overlays can be associated
|
||||
* with a specific page by passing the overlays array to the page's
|
||||
* tile source configuration.
|
||||
* Expected properties:
|
||||
* * x, y, (or px, py for pixel coordinates) to define the location.
|
||||
* * width, height in point if using x,y or in pixels if using px,py. If width
|
||||
* and height are specified, the overlay size is adjusted when zooming,
|
||||
* otherwise the size stays the size of the content (or the size defined by CSS).
|
||||
* * className to associate a class to the overlay
|
||||
* * id to set the overlay element. If an element with this id already exists,
|
||||
* it is reused, otherwise it is created. If not specified, a new element is
|
||||
* created.
|
||||
* * placement a string to define the relative position to the viewport.
|
||||
* Only used if no width and height are specified. Default: 'TOP_LEFT'.
|
||||
* See {@link OpenSeadragon.OverlayPlacement} for possible values.
|
||||
*
|
||||
* @property {String} [xmlPath=null]
|
||||
* <strong>DEPRECATED</strong>. A relative path to load a DZI file from the server.
|
||||
* Prefer the newer Options.tileSources.
|
||||
|
@ -35,7 +35,8 @@
|
||||
(function( $ ){
|
||||
|
||||
/**
|
||||
* An enumeration of positions that an overlay may be assigned relative to the viewport.
|
||||
* An enumeration of positions that an overlay may be assigned relative to
|
||||
* the viewport.
|
||||
* @member OverlayPlacement
|
||||
* @memberof OpenSeadragon
|
||||
* @static
|
||||
@ -69,8 +70,14 @@
|
||||
* @memberof OpenSeadragon
|
||||
* @param {Object} options
|
||||
* @param {Element} options.element
|
||||
* @param {OpenSeadragon.Point|OpenSeadragon.Rect} options.location
|
||||
* @param {OpenSeadragon.OverlayPlacement} options.placement - Only used if location is an {@link OpenSeadragon.Point}.
|
||||
* @param {OpenSeadragon.Point|OpenSeadragon.Rect} options.location - The
|
||||
* location of the overlay on the image. If a {@link OpenSeadragon.Point}
|
||||
* is specified, the overlay will keep a constant size independently of the
|
||||
* zoom. If a {@link OpenSeadragon.Rect} is specified, the overlay size will
|
||||
* be adjusted when the zoom changes.
|
||||
* @param {OpenSeadragon.OverlayPlacement} [options.placement=OpenSeadragon.OverlayPlacement.TOP_LEFT]
|
||||
* Relative position to the viewport.
|
||||
* Only used if location is a {@link OpenSeadragon.Point}.
|
||||
* @param {OpenSeadragon.Overlay.OnDrawCallback} options.onDraw
|
||||
*/
|
||||
$.Overlay = function( element, location, placement ) {
|
||||
@ -86,9 +93,9 @@
|
||||
*/
|
||||
|
||||
var options;
|
||||
if( $.isPlainObject( element ) ){
|
||||
if ( $.isPlainObject( element ) ) {
|
||||
options = element;
|
||||
} else{
|
||||
} else {
|
||||
options = {
|
||||
element: element,
|
||||
location: location,
|
||||
@ -174,7 +181,7 @@
|
||||
element.parentNode.removeChild( element );
|
||||
//this should allow us to preserve overlays when required between
|
||||
//pages
|
||||
if( element.prevElementParent ){
|
||||
if ( element.prevElementParent ) {
|
||||
style.display = 'none';
|
||||
//element.prevElementParent.insertBefore(
|
||||
// element,
|
||||
@ -209,9 +216,15 @@
|
||||
viewport.viewer.drawer.canvas.width / 2,
|
||||
viewport.viewer.drawer.canvas.height / 2
|
||||
),
|
||||
degrees = viewport.degrees,
|
||||
position,
|
||||
size,
|
||||
degrees = viewport.degrees,
|
||||
position = viewport.pixelFromPoint(
|
||||
this.bounds.getTopLeft(),
|
||||
true
|
||||
),
|
||||
size = viewport.deltaPixelsFromPoints(
|
||||
this.bounds.getSize(),
|
||||
true
|
||||
),
|
||||
overlayCenter;
|
||||
|
||||
if ( element.parentNode != container ) {
|
||||
@ -225,8 +238,8 @@
|
||||
this.size = $.getElementSize( element );
|
||||
}
|
||||
|
||||
position = this.position;
|
||||
size = this.size;
|
||||
this.position = position;
|
||||
this.size = size;
|
||||
|
||||
this.adjust( position, size );
|
||||
|
||||
|
56
src/point.js
56
src/point.js
@ -76,10 +76,10 @@ $.Point.prototype = /** @lends OpenSeadragon.Point.prototype */{
|
||||
},
|
||||
|
||||
/**
|
||||
* Add another Point to this point and return a new Point.
|
||||
* Substract another Point to this point and return a new Point.
|
||||
* @function
|
||||
* @param {OpenSeadragon.Point} point The point to add vector components.
|
||||
* @returns {OpenSeadragon.Point} A new point representing the sum of the
|
||||
* @param {OpenSeadragon.Point} point The point to substract vector components.
|
||||
* @returns {OpenSeadragon.Point} A new point representing the substraction of the
|
||||
* vector components
|
||||
*/
|
||||
minus: function( point ) {
|
||||
@ -90,11 +90,11 @@ $.Point.prototype = /** @lends OpenSeadragon.Point.prototype */{
|
||||
},
|
||||
|
||||
/**
|
||||
* Add another Point to this point and return a new Point.
|
||||
* Multiply this point by a factor and return a new Point.
|
||||
* @function
|
||||
* @param {OpenSeadragon.Point} point The point to add vector components.
|
||||
* @returns {OpenSeadragon.Point} A new point representing the sum of the
|
||||
* vector components
|
||||
* @param {Number} factor The factor to multiply vector components.
|
||||
* @returns {OpenSeadragon.Point} A new point representing the multiplication
|
||||
* of the vector components by the factor
|
||||
*/
|
||||
times: function( factor ) {
|
||||
return new $.Point(
|
||||
@ -104,11 +104,11 @@ $.Point.prototype = /** @lends OpenSeadragon.Point.prototype */{
|
||||
},
|
||||
|
||||
/**
|
||||
* Add another Point to this point and return a new Point.
|
||||
* Divide this point by a factor and return a new Point.
|
||||
* @function
|
||||
* @param {OpenSeadragon.Point} point The point to add vector components.
|
||||
* @returns {OpenSeadragon.Point} A new point representing the sum of the
|
||||
* vector components
|
||||
* @param {Number} factor The factor to divide vector components.
|
||||
* @returns {OpenSeadragon.Point} A new point representing the division of the
|
||||
* vector components by the factor
|
||||
*/
|
||||
divide: function( factor ) {
|
||||
return new $.Point(
|
||||
@ -118,10 +118,9 @@ $.Point.prototype = /** @lends OpenSeadragon.Point.prototype */{
|
||||
},
|
||||
|
||||
/**
|
||||
* Add another Point to this point and return a new Point.
|
||||
* Compute the opposite of this point and return a new Point.
|
||||
* @function
|
||||
* @param {OpenSeadragon.Point} point The point to add vector components.
|
||||
* @returns {OpenSeadragon.Point} A new point representing the sum of the
|
||||
* @returns {OpenSeadragon.Point} A new point representing the opposite of the
|
||||
* vector components
|
||||
*/
|
||||
negate: function() {
|
||||
@ -129,11 +128,10 @@ $.Point.prototype = /** @lends OpenSeadragon.Point.prototype */{
|
||||
},
|
||||
|
||||
/**
|
||||
* Add another Point to this point and return a new Point.
|
||||
* Compute the distance between this point and another point.
|
||||
* @function
|
||||
* @param {OpenSeadragon.Point} point The point to add vector components.
|
||||
* @returns {OpenSeadragon.Point} A new point representing the sum of the
|
||||
* vector components
|
||||
* @param {OpenSeadragon.Point} point The point to compute the distance with.
|
||||
* @returns {Number} The distance between the 2 points
|
||||
*/
|
||||
distanceTo: function( point ) {
|
||||
return Math.sqrt(
|
||||
@ -143,22 +141,21 @@ $.Point.prototype = /** @lends OpenSeadragon.Point.prototype */{
|
||||
},
|
||||
|
||||
/**
|
||||
* Add another Point to this point and return a new Point.
|
||||
* Apply a function to each coordinate of this point and return a new point.
|
||||
* @function
|
||||
* @param {OpenSeadragon.Point} point The point to add vector components.
|
||||
* @returns {OpenSeadragon.Point} A new point representing the sum of the
|
||||
* vector components
|
||||
* @param {function} func The function to apply to each coordinate.
|
||||
* @returns {OpenSeadragon.Point} A new point with the coordinates computed
|
||||
* by the specified function
|
||||
*/
|
||||
apply: function( func ) {
|
||||
return new $.Point( func( this.x ), func( this.y ) );
|
||||
},
|
||||
|
||||
/**
|
||||
* Add another Point to this point and return a new Point.
|
||||
* Check if this point is equal to another one.
|
||||
* @function
|
||||
* @param {OpenSeadragon.Point} point The point to add vector components.
|
||||
* @returns {OpenSeadragon.Point} A new point representing the sum of the
|
||||
* vector components
|
||||
* @param {OpenSeadragon.Point} point The point to compare this point with.
|
||||
* @returns {Boolean} true if they are equal, false otherwise.
|
||||
*/
|
||||
equals: function( point ) {
|
||||
return (
|
||||
@ -186,11 +183,10 @@ $.Point.prototype = /** @lends OpenSeadragon.Point.prototype */{
|
||||
},
|
||||
|
||||
/**
|
||||
* Add another Point to this point and return a new Point.
|
||||
* Convert this point to a string in the format (x,y) where x and y are
|
||||
* rounded to the nearest integer.
|
||||
* @function
|
||||
* @param {OpenSeadragon.Point} point The point to add vector components.
|
||||
* @returns {OpenSeadragon.Point} A new point representing the sum of the
|
||||
* vector components
|
||||
* @returns {String} A string representation of this point.
|
||||
*/
|
||||
toString: function() {
|
||||
return "(" + Math.round(this.x) + "," + Math.round(this.y) + ")";
|
||||
|
316
src/viewer.js
316
src/viewer.js
@ -74,8 +74,7 @@ $.Viewer = function( options ) {
|
||||
xmlPath: args.length > 1 ? args[ 1 ] : undefined,
|
||||
prefixUrl: args.length > 2 ? args[ 2 ] : undefined,
|
||||
controls: args.length > 3 ? args[ 3 ] : undefined,
|
||||
overlays: args.length > 4 ? args[ 4 ] : undefined,
|
||||
overlayControls: args.length > 5 ? args[ 5 ] : undefined
|
||||
overlays: args.length > 4 ? args[ 4 ] : undefined
|
||||
};
|
||||
}
|
||||
|
||||
@ -127,9 +126,8 @@ $.Viewer = function( options ) {
|
||||
*/
|
||||
canvas: null,
|
||||
|
||||
//TODO: not sure how to best describe these
|
||||
overlays: [],
|
||||
overlayControls:[],
|
||||
// Overlays list. An overlay allows to add html on top of the viewer.
|
||||
overlays: [],
|
||||
|
||||
//private state properties
|
||||
previousBody: [],
|
||||
@ -211,6 +209,7 @@ $.Viewer = function( options ) {
|
||||
};
|
||||
|
||||
this._updateRequestId = null;
|
||||
this.currentOverlays = [];
|
||||
|
||||
//Inherit some behaviors and properties
|
||||
$.EventSource.call( this );
|
||||
@ -572,9 +571,7 @@ $.extend( $.Viewer.prototype, $.EventSource.prototype, $.ControlDock.prototype,
|
||||
this.navigator.close();
|
||||
}
|
||||
|
||||
if ( this.drawer ) {
|
||||
this.drawer.clearOverlays();
|
||||
}
|
||||
this.clearOverlays();
|
||||
|
||||
this.source = null;
|
||||
this.drawer = null;
|
||||
@ -1334,6 +1331,173 @@ $.extend( $.Viewer.prototype, $.EventSource.prototype, $.ControlDock.prototype,
|
||||
return this;
|
||||
},
|
||||
|
||||
/**
|
||||
* Adds an html element as an overlay to the current viewport. Useful for
|
||||
* highlighting words or areas of interest on an image or other zoomable
|
||||
* interface. The overlays added via this method are removed when the viewport
|
||||
* is closed which include when changing page.
|
||||
* @method
|
||||
* @param {Element|String|Object} element - A reference to an element or an id for
|
||||
* the element which will overlayed. Or an Object specifying the configuration for the overlay
|
||||
* @param {OpenSeadragon.Point|OpenSeadragon.Rect} location - The point or
|
||||
* rectangle which will be overlayed.
|
||||
* @param {OpenSeadragon.OverlayPlacement} placement - The position of the
|
||||
* viewport which the location coordinates will be treated as relative
|
||||
* to.
|
||||
* @param {function} onDraw - If supplied the callback is called when the overlay
|
||||
* needs to be drawn. It it the responsibility of the callback to do any drawing/positioning.
|
||||
* It is passed position, size and element.
|
||||
* @return {OpenSeadragon.Viewer} Chainable.
|
||||
* @fires OpenSeadragon.Viewer.event:add-overlay
|
||||
*/
|
||||
addOverlay: function( element, location, placement, onDraw ) {
|
||||
var options;
|
||||
if( $.isPlainObject( element ) ){
|
||||
options = element;
|
||||
} else {
|
||||
options = {
|
||||
element: element,
|
||||
location: location,
|
||||
placement: placement,
|
||||
onDraw: onDraw
|
||||
};
|
||||
}
|
||||
|
||||
element = $.getElement( options.element );
|
||||
|
||||
if ( getOverlayIndex( this.currentOverlays, element ) >= 0 ) {
|
||||
// they're trying to add a duplicate overlay
|
||||
return this;
|
||||
}
|
||||
this.currentOverlays.push( getOverlayObject( this, options ) );
|
||||
THIS[ this.hash ].forceRedraw = true;
|
||||
/**
|
||||
* Raised when an overlay is added to the viewer (see {@link OpenSeadragon.Viewer#addOverlay}).
|
||||
*
|
||||
* @event add-overlay
|
||||
* @memberof OpenSeadragon.Viewer
|
||||
* @type {object}
|
||||
* @property {OpenSeadragon.Viewer} eventSource - A reference to the Viewer which raised the event.
|
||||
* @property {Element} element - The overlay element.
|
||||
* @property {OpenSeadragon.Point|OpenSeadragon.Rect} location
|
||||
* @property {OpenSeadragon.OverlayPlacement} placement
|
||||
* @property {?Object} userData - Arbitrary subscriber-defined object.
|
||||
*/
|
||||
this.raiseEvent( 'add-overlay', {
|
||||
element: element,
|
||||
location: options.location,
|
||||
placement: options.placement
|
||||
});
|
||||
return this;
|
||||
},
|
||||
|
||||
/**
|
||||
* Updates the overlay represented by the reference to the element or
|
||||
* element id moving it to the new location, relative to the new placement.
|
||||
* @method
|
||||
* @param {OpenSeadragon.Point|OpenSeadragon.Rect} location - The point or
|
||||
* rectangle which will be overlayed.
|
||||
* @param {OpenSeadragon.OverlayPlacement} placement - The position of the
|
||||
* viewport which the location coordinates will be treated as relative
|
||||
* to.
|
||||
* @return {OpenSeadragon.Viewer} Chainable.
|
||||
* @fires OpenSeadragon.Viewer.event:update-overlay
|
||||
*/
|
||||
updateOverlay: function( element, location, placement ) {
|
||||
var i;
|
||||
|
||||
element = $.getElement( element );
|
||||
i = getOverlayIndex( this.currentOverlays, element );
|
||||
|
||||
if ( i >= 0 ) {
|
||||
this.currentOverlays[ i ].update( location, placement );
|
||||
THIS[ this.hash ].forceRedraw = true;
|
||||
/**
|
||||
* Raised when an overlay's location or placement changes
|
||||
* (see {@link OpenSeadragon.Viewer#updateOverlay}).
|
||||
*
|
||||
* @event update-overlay
|
||||
* @memberof OpenSeadragon.Viewer
|
||||
* @type {object}
|
||||
* @property {OpenSeadragon.Viewer} eventSource - A reference to the
|
||||
* Viewer which raised the event.
|
||||
* @property {Element} element
|
||||
* @property {OpenSeadragon.Point|OpenSeadragon.Rect} location
|
||||
* @property {OpenSeadragon.OverlayPlacement} placement
|
||||
* @property {?Object} userData - Arbitrary subscriber-defined object.
|
||||
*/
|
||||
this.raiseEvent( 'update-overlay', {
|
||||
element: element,
|
||||
location: location,
|
||||
placement: placement
|
||||
});
|
||||
}
|
||||
return this;
|
||||
},
|
||||
|
||||
/**
|
||||
* Removes an overlay identified by the reference element or element id
|
||||
* and schedules an update.
|
||||
* @method
|
||||
* @param {Element|String} element - A reference to the element or an
|
||||
* element id which represent the ovelay content to be removed.
|
||||
* @return {OpenSeadragon.Viewer} Chainable.
|
||||
* @fires OpenSeadragon.Viewer.event:remove-overlay
|
||||
*/
|
||||
removeOverlay: function( element ) {
|
||||
var i;
|
||||
|
||||
element = $.getElement( element );
|
||||
i = getOverlayIndex( this.currentOverlays, element );
|
||||
|
||||
if ( i >= 0 ) {
|
||||
this.currentOverlays[ i ].destroy();
|
||||
this.currentOverlays.splice( i, 1 );
|
||||
THIS[ this.hash ].forceRedraw = true;
|
||||
/**
|
||||
* Raised when an overlay is removed from the viewer
|
||||
* (see {@link OpenSeadragon.Viewer#removeOverlay}).
|
||||
*
|
||||
* @event remove-overlay
|
||||
* @memberof OpenSeadragon.Viewer
|
||||
* @type {object}
|
||||
* @property {OpenSeadragon.Viewer} eventSource - A reference to the
|
||||
* Viewer which raised the event.
|
||||
* @property {Element} element - The overlay element.
|
||||
* @property {?Object} userData - Arbitrary subscriber-defined object.
|
||||
*/
|
||||
this.raiseEvent( 'remove-overlay', {
|
||||
element: element
|
||||
});
|
||||
}
|
||||
return this;
|
||||
},
|
||||
|
||||
/**
|
||||
* Removes all currently configured Overlays from this Viewer and schedules
|
||||
* an update.
|
||||
* @method
|
||||
* @return {OpenSeadragon.Viewer} Chainable.
|
||||
* @fires OpenSeadragon.Viewer.event:clear-overlay
|
||||
*/
|
||||
clearOverlays: function() {
|
||||
while ( this.currentOverlays.length > 0 ) {
|
||||
this.currentOverlays.pop().destroy();
|
||||
}
|
||||
THIS[ this.hash ].forceRedraw = true;
|
||||
/**
|
||||
* Raised when all overlays are removed from the viewer (see {@link OpenSeadragon.Drawer#clearOverlays}).
|
||||
*
|
||||
* @event clear-overlay
|
||||
* @memberof OpenSeadragon.Viewer
|
||||
* @type {object}
|
||||
* @property {OpenSeadragon.Viewer} eventSource - A reference to the Viewer which raised the event.
|
||||
* @property {?Object} userData - Arbitrary subscriber-defined object.
|
||||
*/
|
||||
this.raiseEvent( 'clear-overlay', {} );
|
||||
return this;
|
||||
},
|
||||
|
||||
/**
|
||||
* Updates the sequence buttons.
|
||||
* @function OpenSeadragon.Viewer.prototype._updateSequenceButtons
|
||||
@ -1419,9 +1583,8 @@ function _getSafeElemSize (oElement) {
|
||||
* @private
|
||||
*/
|
||||
function openTileSource( viewer, source ) {
|
||||
var _this = viewer,
|
||||
overlay,
|
||||
i;
|
||||
var i,
|
||||
_this = viewer;
|
||||
|
||||
if ( _this.source ) {
|
||||
_this.close( );
|
||||
@ -1455,7 +1618,7 @@ function openTileSource( viewer, source ) {
|
||||
//minZoomLevel: this.minZoomLevel,
|
||||
//maxZoomLevel: this.maxZoomLevel
|
||||
});
|
||||
}else{
|
||||
} else {
|
||||
if( source ){
|
||||
_this.source = source;
|
||||
}
|
||||
@ -1488,7 +1651,6 @@ function openTileSource( viewer, source ) {
|
||||
source: _this.source,
|
||||
viewport: _this.viewport,
|
||||
element: _this.canvas,
|
||||
overlays: [].concat( _this.overlays ).concat( _this.source.overlays ),
|
||||
maxImageCacheCount: _this.maxImageCacheCount,
|
||||
imageLoaderLimit: _this.imageLoaderLimit,
|
||||
minZoomImageRatio: _this.minZoomImageRatio,
|
||||
@ -1538,7 +1700,6 @@ function openTileSource( viewer, source ) {
|
||||
tileSources: source,
|
||||
tileHost: _this.tileHost,
|
||||
prefixUrl: _this.prefixUrl,
|
||||
overlays: _this.overlays,
|
||||
viewer: _this
|
||||
});
|
||||
}
|
||||
@ -1556,7 +1717,6 @@ function openTileSource( viewer, source ) {
|
||||
tileSources: _this.tileSources,
|
||||
tileHost: _this.tileHost,
|
||||
prefixUrl: _this.prefixUrl,
|
||||
overlays: _this.overlays,
|
||||
viewer: _this
|
||||
});
|
||||
}
|
||||
@ -1567,40 +1727,10 @@ function openTileSource( viewer, source ) {
|
||||
THIS[ _this.hash ].forceRedraw = true;
|
||||
_this._updateRequestId = scheduleUpdate( _this, updateMulti );
|
||||
|
||||
//Assuming you had programatically created a bunch of overlays
|
||||
//and added them via configuration
|
||||
for ( i = 0; i < _this.overlayControls.length; i++ ) {
|
||||
|
||||
overlay = _this.overlayControls[ i ];
|
||||
|
||||
if ( overlay.point ) {
|
||||
|
||||
_this.drawer.addOverlay(
|
||||
overlay.id,
|
||||
new $.Point(
|
||||
overlay.point.X,
|
||||
overlay.point.Y
|
||||
),
|
||||
$.OverlayPlacement.TOP_LEFT
|
||||
);
|
||||
|
||||
} else {
|
||||
|
||||
_this.drawer.addOverlay(
|
||||
overlay.id,
|
||||
new $.Rect(
|
||||
overlay.rect.Point.X,
|
||||
overlay.rect.Point.Y,
|
||||
overlay.rect.Width,
|
||||
overlay.rect.Height
|
||||
),
|
||||
overlay.placement
|
||||
);
|
||||
|
||||
}
|
||||
}
|
||||
VIEWERS[ _this.hash ] = _this;
|
||||
|
||||
loadOverlays( _this );
|
||||
|
||||
/**
|
||||
* Raised when the viewer has opened and loaded one or more TileSources.
|
||||
*
|
||||
@ -1616,8 +1746,98 @@ function openTileSource( viewer, source ) {
|
||||
return _this;
|
||||
}
|
||||
|
||||
function loadOverlays( _this ) {
|
||||
_this.currentOverlays = [];
|
||||
for ( var i = 0; i < _this.overlays.length; i++ ) {
|
||||
_this.currentOverlays[ i ] = getOverlayObject( _this, _this.overlays[ i ] );
|
||||
}
|
||||
for ( var j = 0; j < _this.source.overlays.length; j++ ) {
|
||||
_this.currentOverlays[ i + j ] =
|
||||
getOverlayObject( _this, _this.source.overlays[ j ] );
|
||||
}
|
||||
}
|
||||
|
||||
function getOverlayObject( viewer, overlay ) {
|
||||
if ( overlay instanceof $.Overlay ) {
|
||||
return overlay;
|
||||
}
|
||||
|
||||
var element = null;
|
||||
if ( overlay.element ) {
|
||||
element = $.getElement( overlay.element );
|
||||
} else {
|
||||
var id = overlay.id ?
|
||||
overlay.id :
|
||||
"openseadragon-overlay-" + Math.floor( Math.random() * 10000000 );
|
||||
|
||||
element = $.getElement( overlay.id );
|
||||
if ( !element ) {
|
||||
element = document.createElement( "a" );
|
||||
element.href = "#/overlay/" + id;
|
||||
}
|
||||
element.id = id;
|
||||
$.addClass( element, overlay.className ?
|
||||
overlay.className :
|
||||
"openseadragon-overlay"
|
||||
);
|
||||
}
|
||||
|
||||
var location = overlay.location;
|
||||
if ( !location ) {
|
||||
var rect = ( overlay.height && overlay.width ) ? new $.Rect(
|
||||
overlay.x || overlay.px,
|
||||
overlay.y || overlay.py,
|
||||
overlay.width,
|
||||
overlay.height
|
||||
) : new $.Point(
|
||||
overlay.x || overlay.px,
|
||||
overlay.y || overlay.py
|
||||
);
|
||||
if( overlay.px !== undefined ) {
|
||||
//if they specified 'px' so it's in pixel coordinates so
|
||||
//we need to translate to viewport coordinates
|
||||
rect = viewer.viewport.imageToViewportRectangle( rect );
|
||||
}
|
||||
location = overlay.placement ? viewer.viewport.pointFromPixel( rect ) :
|
||||
rect;
|
||||
}
|
||||
|
||||
var placement = overlay.placement;
|
||||
if ( placement && ( $.type( placement ) === "string" ) ) {
|
||||
placement = $.OverlayPlacement[ overlay.placement.toUpperCase() ];
|
||||
}
|
||||
|
||||
return new $.Overlay({
|
||||
element: element,
|
||||
location: location,
|
||||
placement: placement,
|
||||
onDraw: overlay.onDraw
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @inner
|
||||
* Determines the index of the given overlay in the given overlays array.
|
||||
*/
|
||||
function getOverlayIndex( overlays, element ) {
|
||||
var i;
|
||||
for ( i = overlays.length - 1; i >= 0; i-- ) {
|
||||
if ( overlays[ i ].element === element ) {
|
||||
return i;
|
||||
}
|
||||
}
|
||||
|
||||
return -1;
|
||||
}
|
||||
|
||||
function drawOverlays( viewport, overlays, container ) {
|
||||
var i,
|
||||
length = overlays.length;
|
||||
for ( i = 0; i < length; i++ ) {
|
||||
overlays[ i ].drawHTML( container, viewport );
|
||||
}
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
// Schedulers provide the general engine for animation
|
||||
@ -1991,6 +2211,7 @@ function updateOnce( viewer ) {
|
||||
|
||||
if ( animated ) {
|
||||
viewer.drawer.update();
|
||||
drawOverlays( viewer.viewport, viewer.currentOverlays, viewer.canvas );
|
||||
if( viewer.navigator ){
|
||||
viewer.navigator.update( viewer.viewport );
|
||||
}
|
||||
@ -2006,6 +2227,7 @@ function updateOnce( viewer ) {
|
||||
viewer.raiseEvent( "animation" );
|
||||
} else if ( THIS[ viewer.hash ].forceRedraw || viewer.drawer.needsUpdate() ) {
|
||||
viewer.drawer.update();
|
||||
drawOverlays( viewer.viewport, viewer.currentOverlays, viewer.canvas );
|
||||
if( viewer.navigator ){
|
||||
viewer.navigator.update( viewer.viewport );
|
||||
}
|
||||
|
@ -920,12 +920,12 @@ $.Viewport.prototype = /** @lends OpenSeadragon.Viewport.prototype */{
|
||||
/**
|
||||
* Convert pixel coordinates relative to the image to
|
||||
* viewer element coordinates.
|
||||
* @param {OpenSeadragon.Point} point
|
||||
* @param {OpenSeadragon.Point} pixel
|
||||
* @returns {OpenSeadragon.Point}
|
||||
*/
|
||||
imageToViewerElementCoordinates: function( point ) {
|
||||
var pixel = this.pixelFromPoint( point, true );
|
||||
return this.imageToViewportCoordinates( pixel );
|
||||
imageToViewerElementCoordinates: function( pixel ) {
|
||||
var point = this.imageToViewportCoordinates( pixel );
|
||||
return this.pixelFromPoint( point, true );
|
||||
},
|
||||
|
||||
/**
|
||||
|
344
test/overlays.js
Normal file
344
test/overlays.js
Normal file
@ -0,0 +1,344 @@
|
||||
/* global QUnit, module, Util, $, console, test, asyncTest, start, ok, equal */
|
||||
|
||||
( function() {
|
||||
var viewer;
|
||||
|
||||
module( "Overlays", {
|
||||
setup: function() {
|
||||
var example = $( '<div id="example-overlays"></div>' ).appendTo( "#qunit-fixture" );
|
||||
var fixedOverlay = $( '<div id="fixed-overlay"></div>' ).appendTo(example);
|
||||
fixedOverlay.width(70);
|
||||
fixedOverlay.height(60);
|
||||
|
||||
testLog.reset();
|
||||
},
|
||||
teardown: function() {
|
||||
resetTestVariables();
|
||||
}
|
||||
} );
|
||||
|
||||
var resetTestVariables = function() {
|
||||
if ( viewer ) {
|
||||
viewer.close();
|
||||
}
|
||||
};
|
||||
|
||||
function waitForViewer( handler, count ) {
|
||||
if ( typeof count !== "number" ) {
|
||||
count = 0;
|
||||
}
|
||||
var ready = viewer.isOpen() &&
|
||||
viewer.drawer !== null &&
|
||||
!viewer.drawer.needsUpdate() &&
|
||||
Util.equalsWithVariance( viewer.viewport.getBounds( true ).x,
|
||||
viewer.viewport.getBounds().x, 0.000 ) &&
|
||||
Util.equalsWithVariance( viewer.viewport.getBounds( true ).y,
|
||||
viewer.viewport.getBounds().y, 0.000 ) &&
|
||||
Util.equalsWithVariance( viewer.viewport.getBounds( true ).width,
|
||||
viewer.viewport.getBounds().width, 0.000 );
|
||||
|
||||
if ( ready ) {
|
||||
handler();
|
||||
} else if ( count < 50 ) {
|
||||
count++;
|
||||
setTimeout( function() {
|
||||
waitForViewer( handler, count );
|
||||
}, 100 );
|
||||
} else {
|
||||
console.log( "waitForViewer:" + viewer.isOpen( ) + ":" + viewer.drawer +
|
||||
":" + viewer.drawer.needsUpdate() );
|
||||
handler();
|
||||
}
|
||||
}
|
||||
|
||||
asyncTest( 'Overlays via viewer options', function() {
|
||||
|
||||
viewer = OpenSeadragon( {
|
||||
id: 'example-overlays',
|
||||
prefixUrl: '/build/openseadragon/images/',
|
||||
tileSources: [ '/test/data/testpattern.dzi', '/test/data/testpattern.dzi' ],
|
||||
springStiffness: 100, // Faster animation = faster tests
|
||||
overlays: [ {
|
||||
x: 0.1,
|
||||
y: 0.4,
|
||||
width: 0.09,
|
||||
height: 0.09,
|
||||
id: "overlay"
|
||||
} ]
|
||||
} );
|
||||
viewer.addHandler( 'open', openHandler );
|
||||
|
||||
function openHandler() {
|
||||
viewer.removeHandler( 'open', openHandler );
|
||||
|
||||
equal( viewer.overlays.length, 1, "Global overlay should be added." );
|
||||
equal( viewer.currentOverlays.length, 1, "Global overlay should be open." );
|
||||
|
||||
viewer.addHandler( 'open', openPageHandler );
|
||||
viewer.goToPage( 1 );
|
||||
}
|
||||
|
||||
function openPageHandler() {
|
||||
viewer.removeHandler( 'open', openPageHandler );
|
||||
|
||||
equal( viewer.overlays.length, 1, "Global overlay should stay after page switch." );
|
||||
equal( viewer.currentOverlays.length, 1, "Global overlay should re-open after page switch." );
|
||||
|
||||
viewer.addHandler( 'close', closeHandler );
|
||||
viewer.close();
|
||||
}
|
||||
|
||||
function closeHandler() {
|
||||
viewer.removeHandler( 'close', closeHandler );
|
||||
|
||||
equal( viewer.overlays.length, 1, "Global overlay should not be removed on close." );
|
||||
equal( viewer.currentOverlays.length, 0, "Global overlay should be closed on close." );
|
||||
|
||||
start();
|
||||
}
|
||||
} );
|
||||
|
||||
asyncTest( 'Page Overlays via viewer options', function() {
|
||||
|
||||
viewer = OpenSeadragon( {
|
||||
id: 'example-overlays',
|
||||
prefixUrl: '/build/openseadragon/images/',
|
||||
tileSources: [ {
|
||||
Image: {
|
||||
xmlns: "http://schemas.microsoft.com/deepzoom/2008",
|
||||
Url: "/test/data/testpattern_files/",
|
||||
Format: "jpg",
|
||||
Overlap: "1",
|
||||
TileSize: "254",
|
||||
Size: {
|
||||
Width: 1000,
|
||||
Height: 1000
|
||||
}
|
||||
},
|
||||
overlays: [ {
|
||||
x: 0.1,
|
||||
y: 0.4,
|
||||
width: 0.09,
|
||||
height: 0.09,
|
||||
id: "overlay"
|
||||
} ]
|
||||
}, {
|
||||
Image: {
|
||||
xmlns: "http://schemas.microsoft.com/deepzoom/2008",
|
||||
Url: "/test/data/testpattern_files/",
|
||||
Format: "jpg",
|
||||
Overlap: "1",
|
||||
TileSize: "254",
|
||||
Size: {
|
||||
Width: 1000,
|
||||
Height: 1000
|
||||
}
|
||||
}
|
||||
} ],
|
||||
springStiffness: 100 // Faster animation = faster tests
|
||||
} );
|
||||
viewer.addHandler( 'open', openHandler );
|
||||
|
||||
function openHandler() {
|
||||
viewer.removeHandler( 'open', openHandler );
|
||||
|
||||
equal( viewer.overlays.length, 0, "No global overlay should be added." );
|
||||
equal( viewer.currentOverlays.length, 1, "Page overlay should be open." );
|
||||
|
||||
viewer.addHandler( 'open', openPageHandler );
|
||||
viewer.goToPage( 1 );
|
||||
}
|
||||
|
||||
function openPageHandler() {
|
||||
viewer.removeHandler( 'open', openPageHandler );
|
||||
|
||||
equal( viewer.overlays.length, 0, "No global overlay should be added after page switch." );
|
||||
equal( viewer.currentOverlays.length, 0, "No page overlay should be opened after page switch." );
|
||||
|
||||
viewer.addHandler( 'close', closeHandler );
|
||||
viewer.close();
|
||||
}
|
||||
|
||||
function closeHandler() {
|
||||
viewer.removeHandler( 'close', closeHandler );
|
||||
|
||||
equal( viewer.overlays.length, 0, "No global overlay should be added on close." );
|
||||
equal( viewer.currentOverlays.length, 0, "Page overlay should be closed on close." );
|
||||
|
||||
start();
|
||||
}
|
||||
} );
|
||||
|
||||
asyncTest( 'Overlays via addOverlay method', function() {
|
||||
|
||||
viewer = OpenSeadragon( {
|
||||
id: 'example-overlays',
|
||||
prefixUrl: '/build/openseadragon/images/',
|
||||
tileSources: [ '/test/data/testpattern.dzi', '/test/data/testpattern.dzi' ],
|
||||
springStiffness: 100 // Faster animation = faster tests
|
||||
} );
|
||||
viewer.addHandler( 'open', openHandler );
|
||||
|
||||
function openHandler() {
|
||||
viewer.removeHandler( 'open', openHandler );
|
||||
|
||||
equal( viewer.overlays.length, 0, "No global overlay should be added." );
|
||||
equal( viewer.currentOverlays.length, 0, "No overlay should be open." );
|
||||
|
||||
var rect = new OpenSeadragon.Rect( 0.1, 0.1, 0.1, 0.1 );
|
||||
var overlay = $( "<div/>" ).prop("id", "overlay").get( 0 );
|
||||
viewer.addOverlay( overlay, rect );
|
||||
equal( viewer.overlays.length, 0, "No manual overlay should be added as global overlay." );
|
||||
equal( viewer.currentOverlays.length, 1, "A manual overlay should be open." );
|
||||
|
||||
viewer.addHandler( 'open', openPageHandler );
|
||||
viewer.goToPage( 1 );
|
||||
}
|
||||
|
||||
function openPageHandler() {
|
||||
viewer.removeHandler( 'open', openPageHandler );
|
||||
|
||||
equal( viewer.overlays.length, 0, "No global overlay should be added after page switch." );
|
||||
equal( viewer.currentOverlays.length, 0, "Manual overlay should be removed after page switch." );
|
||||
|
||||
viewer.addHandler( 'close', closeHandler );
|
||||
viewer.close();
|
||||
}
|
||||
|
||||
function closeHandler() {
|
||||
viewer.removeHandler( 'close', closeHandler );
|
||||
|
||||
equal( viewer.overlays.length, 0, "No global overlay should be added on close." );
|
||||
equal( viewer.currentOverlays.length, 0, "Manual overlay should be removed on close." );
|
||||
|
||||
start();
|
||||
}
|
||||
|
||||
} );
|
||||
|
||||
asyncTest( 'Overlays size in pixels', function() {
|
||||
|
||||
viewer = OpenSeadragon( {
|
||||
id: 'example-overlays',
|
||||
prefixUrl: '/build/openseadragon/images/',
|
||||
tileSources: [ '/test/data/testpattern.dzi', '/test/data/testpattern.dzi' ],
|
||||
springStiffness: 100, // Faster animation = faster tests
|
||||
overlays: [ {
|
||||
px: 13,
|
||||
py: 120,
|
||||
width: 124,
|
||||
height: 132,
|
||||
id: "overlay"
|
||||
}, {
|
||||
px: 400,
|
||||
py: 500,
|
||||
id: "fixed-overlay"
|
||||
}]
|
||||
} );
|
||||
|
||||
function checkOverlayPosition( contextMessage ) {
|
||||
var viewport = viewer.viewport;
|
||||
|
||||
var expPosition = viewport.imageToViewerElementCoordinates(
|
||||
new OpenSeadragon.Point( 13, 120 ) ).apply( Math.floor );
|
||||
var actPosition = $( "#overlay" ).position();
|
||||
equal( actPosition.left, expPosition.x, "X position mismatch " + contextMessage );
|
||||
equal( actPosition.top, expPosition.y, "Y position mismatch " + contextMessage );
|
||||
|
||||
var zoom = viewport.viewportToImageZoom( viewport.getZoom( true ) );
|
||||
var expectedWidth = Math.ceil( 124 * zoom );
|
||||
var expectedHeight = Math.ceil( 132 * zoom );
|
||||
equal( $( "#overlay" ).width(), expectedWidth, "Width mismatch " + contextMessage );
|
||||
equal( $( "#overlay" ).height( ), expectedHeight, "Height mismatch " + contextMessage );
|
||||
|
||||
|
||||
expPosition = viewport.imageToViewerElementCoordinates(
|
||||
new OpenSeadragon.Point( 400, 500 ) ).apply( Math.floor );
|
||||
actPosition = $( "#fixed-overlay" ).position();
|
||||
equal( actPosition.left, expPosition.x, "Fixed overlay X position mismatch " + contextMessage );
|
||||
equal( actPosition.top, expPosition.y, "Fixed overlay Y position mismatch " + contextMessage );
|
||||
|
||||
equal( $( "#fixed-overlay" ).width(), 70, "Fixed overlay width mismatch " + contextMessage );
|
||||
equal( $( "#fixed-overlay" ).height( ), 60, "Fixed overlay height mismatch " + contextMessage );
|
||||
}
|
||||
|
||||
waitForViewer( function() {
|
||||
checkOverlayPosition( "after opening using image coordinates" );
|
||||
|
||||
viewer.viewport.zoomBy( 1.1 ).panBy( new OpenSeadragon.Point( 0.1, 0.2 ) );
|
||||
waitForViewer( function() {
|
||||
checkOverlayPosition( "after zoom and pan using image coordinates" );
|
||||
|
||||
viewer.viewport.goHome();
|
||||
waitForViewer( function() {
|
||||
checkOverlayPosition( "after goHome using image coordinates" );
|
||||
start();
|
||||
} );
|
||||
} );
|
||||
|
||||
} );
|
||||
} );
|
||||
|
||||
asyncTest( 'Overlays size in points', function() {
|
||||
|
||||
viewer = OpenSeadragon( {
|
||||
id: 'example-overlays',
|
||||
prefixUrl: '/build/openseadragon/images/',
|
||||
tileSources: [ '/test/data/testpattern.dzi', '/test/data/testpattern.dzi' ],
|
||||
springStiffness: 100, // Faster animation = faster tests
|
||||
overlays: [ {
|
||||
x: 0.2,
|
||||
y: 0.1,
|
||||
width: 0.5,
|
||||
height: 0.1,
|
||||
id: "overlay"
|
||||
},{
|
||||
x: 0.5,
|
||||
y: 0.6,
|
||||
id: "fixed-overlay"
|
||||
} ]
|
||||
} );
|
||||
|
||||
function checkOverlayPosition( contextMessage ) {
|
||||
var viewport = viewer.viewport;
|
||||
|
||||
var expPosition = viewport.viewportToViewerElementCoordinates(
|
||||
new OpenSeadragon.Point( 0.2, 0.1 ) ).apply( Math.floor );
|
||||
var actPosition = $( "#overlay" ).position();
|
||||
equal( actPosition.left, expPosition.x, "X position mismatch " + contextMessage );
|
||||
equal( actPosition.top, expPosition.y, "Y position mismatch " + contextMessage );
|
||||
|
||||
var expectedSize = viewport.deltaPixelsFromPoints(
|
||||
new OpenSeadragon.Point(0.5, 0.1));
|
||||
equal( $( "#overlay" ).width(), expectedSize.x, "Width mismatch " + contextMessage );
|
||||
equal( $( "#overlay" ).height( ), expectedSize.y, "Height mismatch " + contextMessage );
|
||||
|
||||
|
||||
expPosition = viewport.viewportToViewerElementCoordinates(
|
||||
new OpenSeadragon.Point( 0.5, 0.6 ) ).apply( Math.floor );
|
||||
actPosition = $( "#fixed-overlay" ).position();
|
||||
equal( actPosition.left, expPosition.x, "Fixed overlay X position mismatch " + contextMessage );
|
||||
equal( actPosition.top, expPosition.y, "Fixed overlay Y position mismatch " + contextMessage );
|
||||
|
||||
equal( $( "#fixed-overlay" ).width(), 70, "Fixed overlay width mismatch " + contextMessage );
|
||||
equal( $( "#fixed-overlay" ).height( ), 60, "Fixed overlay height mismatch " + contextMessage );
|
||||
}
|
||||
|
||||
waitForViewer( function() {
|
||||
checkOverlayPosition( "after opening using viewport coordinates" );
|
||||
|
||||
viewer.viewport.zoomBy( 1.1 ).panBy( new OpenSeadragon.Point( 0.1, 0.2 ) );
|
||||
waitForViewer( function() {
|
||||
checkOverlayPosition( "after zoom and pan using viewport coordinates" );
|
||||
|
||||
viewer.viewport.goHome();
|
||||
waitForViewer( function() {
|
||||
checkOverlayPosition( "after goHome using viewport coordinates" );
|
||||
start();
|
||||
} );
|
||||
} );
|
||||
|
||||
} );
|
||||
} );
|
||||
|
||||
} )();
|
@ -18,7 +18,7 @@
|
||||
width: 300px;
|
||||
}
|
||||
|
||||
#unitsexample {
|
||||
#unitsexample, #example-overlays {
|
||||
height: 500px;
|
||||
width: 500px;
|
||||
}
|
||||
|
@ -27,6 +27,7 @@
|
||||
<script src="/test/utils.js"></script>
|
||||
<script src="/test/events.js"></script>
|
||||
<script src="/test/units.js"></script>
|
||||
<script src="/test/overlays.js"></script>
|
||||
<script src="/test/rotate.js"></script>
|
||||
</body>
|
||||
</html>
|
||||
|
@ -26,12 +26,34 @@
|
||||
|
||||
|
||||
function pointEqual(a, b, message) {
|
||||
ok(a.x === b.x && a.y === b.y, message);
|
||||
Util.assessNumericValue(a.x, b.x, 0.00000001, message);
|
||||
Util.assessNumericValue(a.y, b.y, 0.00000001, message);
|
||||
}
|
||||
|
||||
// ----------
|
||||
asyncTest('Coordinates conversions', function() {
|
||||
|
||||
function checkPoint(context) {
|
||||
var viewport = viewer.viewport;
|
||||
|
||||
var point = new OpenSeadragon.Point(15, 12);
|
||||
var result = viewport.viewerElementToImageCoordinates(
|
||||
viewport.imageToViewerElementCoordinates(point));
|
||||
pointEqual(result, point, 'viewerElement and image ' + context);
|
||||
|
||||
var result = viewport.windowToImageCoordinates(
|
||||
viewport.imageToWindowCoordinates(point));
|
||||
pointEqual(result, point, 'window and image ' + context);
|
||||
|
||||
var result = viewport.viewerElementToViewportCoordinates(
|
||||
viewport.viewportToViewerElementCoordinates(point));
|
||||
pointEqual(result, point, 'viewerElement and viewport ' + context);
|
||||
|
||||
var result = viewport.windowToViewportCoordinates(
|
||||
viewport.viewportToWindowCoordinates(point));
|
||||
pointEqual(result, point, 'window and viewport ' + context);
|
||||
}
|
||||
|
||||
viewer.addHandler("open", function () {
|
||||
var viewport = viewer.viewport;
|
||||
|
||||
@ -52,24 +74,13 @@
|
||||
var pixel = viewport.viewerElementToImageCoordinates(viewerTopRight);
|
||||
pointEqual(pixel, imageTopRight, 'Viewer top right has viewport coordinates imageWidth,0.');
|
||||
|
||||
var point = new OpenSeadragon.Point(15, 12);
|
||||
var result = viewport.viewerElementToImageCoordinates(
|
||||
viewport.imageToViewerElementCoordinates(point));
|
||||
pointEqual(result, point, 'viewerElement and image');
|
||||
|
||||
var result = viewport.windowToImageCoordinates(
|
||||
viewport.imageToWindowCoordinates(point));
|
||||
pointEqual(result, point, 'window and image');
|
||||
|
||||
var result = viewport.viewerElementToViewportCoordinates(
|
||||
viewport.viewportToViewerElementCoordinates(point));
|
||||
pointEqual(result, point, 'viewerElement and viewport');
|
||||
|
||||
var result = viewport.windowToViewportCoordinates(
|
||||
viewport.viewportToWindowCoordinates(point));
|
||||
pointEqual(result, point, 'window and viewport');
|
||||
|
||||
start();
|
||||
checkPoint('after opening');
|
||||
viewer.addHandler('animation-finish', function animationHandler() {
|
||||
viewer.removeHandler('animation-finish', animationHandler);
|
||||
checkPoint('after zoom and pan');
|
||||
start();
|
||||
});
|
||||
viewer.viewport.zoomTo(0.8).panTo(new OpenSeadragon.Point(0.1, 0.2));
|
||||
});
|
||||
viewer.open('/test/data/testpattern.dzi');
|
||||
});
|
||||
@ -104,14 +115,13 @@
|
||||
checkZoom();
|
||||
|
||||
var zoomHandler = function() {
|
||||
viewer.removeHandler('animationfinish', zoomHandler);
|
||||
viewer.removeHandler('animation-finish', zoomHandler);
|
||||
checkZoom();
|
||||
start();
|
||||
};
|
||||
|
||||
viewer.addHandler('animationfinish', zoomHandler);
|
||||
viewer.addHandler('animation-finish', zoomHandler);
|
||||
viewport.zoomTo(2);
|
||||
start();
|
||||
});
|
||||
|
||||
viewer.open('/test/data/testpattern.dzi');
|
||||
|
Loading…
Reference in New Issue
Block a user