Rename drawHandler to onDraw. Also make it a notification style callback

(does not override the draw functionality).
Add an overlay option 'useTransform' that will transform the overlay
element instead of moving it's postion - useful for SVG elements
This commit is contained in:
Luke Murray 2013-07-16 12:04:37 +10:00
parent 233c3a357a
commit df877493a9
2 changed files with 81 additions and 40 deletions

View File

@ -144,7 +144,7 @@ $.Drawer = function( options ) {
for( i = 0; i < this.overlays.length; i++ ){ for( i = 0; i < this.overlays.length; i++ ){
if( $.isPlainObject( this.overlays[ i ] ) ){ if( $.isPlainObject( this.overlays[ i ] ) ){
this.overlays[ i ] = addOverlayFromConfiguration( this, this.overlays[ i ]); this.overlays[ i ] = addOverlayFromConfiguration( this, this.overlays[ i ], this.source.dimensions);
} else if ( $.isFunction( this.overlays[ i ] ) ){ } else if ( $.isFunction( this.overlays[ i ] ) ){
//TODO //TODO
@ -168,8 +168,12 @@ $.Drawer.prototype = {
* @param {OpenSeadragon.OverlayPlacement} placement - The position of the * @param {OpenSeadragon.OverlayPlacement} placement - The position of the
* viewport which the location coordinates will be treated as relative * viewport which the location coordinates will be treated as relative
* to. * to.
* @param {function} onDraw - A callback that is called when the overlay
* needs to be drawn. It is passed position, size and element.
* @param {boolean} useTransform - Overlay will be scaled and moved using
* the SVG transform argument. Overlay should be a SVG g element.
*/ */
addOverlay: function( element, location, placement ) { addOverlay: function( element, location, placement, onDraw, useTransform ) {
element = $.getElement( element ); element = $.getElement( element );
if ( getOverlayIndex( this.overlays, element ) >= 0 ) { if ( getOverlayIndex( this.overlays, element ) >= 0 ) {
@ -177,7 +181,14 @@ $.Drawer.prototype = {
return; return;
} }
this.overlays.push( new $.Overlay( element, location, placement ) ); this.overlays.push( new $.Overlay({
element: element,
location: location,
placement: placement,
onDraw: onDraw,
useTransform: useTransform,
imageFullSize: this.source.dimensions
}) );
this.updateAgain = true; this.updateAgain = true;
if( this.viewer ){ if( this.viewer ){
this.viewer.raiseEvent( 'add-overlay', { this.viewer.raiseEvent( 'add-overlay', {
@ -390,7 +401,7 @@ $.Drawer.prototype = {
* @private * @private
* @inner * @inner
*/ */
function addOverlayFromConfiguration( drawer, overlay ){ function addOverlayFromConfiguration( drawer, overlay, dimensions ){
var element = null, var element = null,
rect = ( overlay.height && overlay.width ) ? new $.Rect( rect = ( overlay.height && overlay.width ) ? new $.Rect(
@ -423,17 +434,24 @@ $.Drawer.prototype = {
//we need to translate to viewport coordinates //we need to translate to viewport coordinates
rect = drawer.viewport.imageToViewportRectangle( rect ); rect = drawer.viewport.imageToViewportRectangle( rect );
} }
if( overlay.placement ){ if( overlay.placement ){
return new $.Overlay( return new $.Overlay({
element, element: element,
drawer.viewport.pointFromPixel(rect), location: drawer.viewport.pointFromPixel(rect),
$.OverlayPlacement[overlay.placement.toUpperCase()] placement: $.OverlayPlacement[overlay.placement.toUpperCase()],
); onDraw: overlay.onDraw,
useTransform: overlay.useTransform,
imageFullSize: dimensions
});
}else{ }else{
var newOverlay = new $.Overlay(element, rect); return new $.Overlay({
if (overlay.zoomHandler) element: element,
newOverlay.zoomHandler = overlay.zoomHandler; location: rect,
return newOverlay; onDraw: overlay.onDraw,
useTransform: overlay.useTransform,
imageFullSize: dimensions
});
} }
} }

View File

@ -57,27 +57,42 @@
* @class * @class
*/ */
$.Overlay = function( element, location, placement ) { $.Overlay = function( element, location, placement ) {
this.element = element;
this.scales = location instanceof $.Rect; var options;
if( $.isPlainObject( element ) ){
options = element;
} else{
options = {
element: element,
location: location,
placement: placement
};
}
this.element = options.element;
this.scales = options.location instanceof $.Rect;
this.bounds = new $.Rect( this.bounds = new $.Rect(
location.x, options.location.x,
location.y, options.location.y,
location.width, options.location.width,
location.height options.location.height
); );
this.position = new $.Point( this.position = new $.Point(
location.x, options.location.x,
location.y options.location.y
); );
this.size = new $.Point( this.size = new $.Point(
location.width, options.location.width,
location.height options.location.height
); );
this.style = element.style; this.style = options.element.style;
// rects are always top-left // rects are always top-left
this.placement = location instanceof $.Point ? this.placement = options.location instanceof $.Point ?
placement : options.placement :
$.OverlayPlacement.TOP_LEFT; $.OverlayPlacement.TOP_LEFT;
this.onDraw = options.onDraw;
this.useTransform = options.useTransform;
this.imageFullSize = options.imageFullSize;
}; };
$.Overlay.prototype = { $.Overlay.prototype = {
@ -176,27 +191,35 @@
this.size = $.getElementSize( element ); this.size = $.getElementSize( element );
} }
if (this.zoomHandler) {
this.zoomHandler(this.position, this.size, element);
return;
}
position = this.position; position = this.position;
size = this.size; size = this.size;
this.adjust( position, size ); this.adjust( position, size );
position = position.apply( Math.floor ); if(this.useTransform){
size = size.apply( Math.ceil ); var scale = Math.min(this.size.x / this.imageFullSize.x, this.size.y / this.imageFullSize.y);
style.left = position.x + "px"; var attrValue = 'translate(' + position.x + ', ' + position.y + ') scale(' + scale + ')';
style.top = position.y + "px"; // we expect the first element to be the g element of the SVG element that we can transform
style.position = "absolute"; element.firstElementChild.setAttribute('transform', attrValue);
style.display = 'block'; }else{
position = position.apply( Math.floor );
size = size.apply( Math.ceil );
if ( scales ) { style.left = position.x + "px";
style.width = size.x + "px"; style.top = position.y + "px";
style.height = size.y + "px"; style.position = "absolute";
style.display = 'block';
if ( scales ) {
style.width = size.x + "px";
style.height = size.y + "px";
}
}
// call the onDraw callback if there is one to allow them to dping
if (this.onDraw) {
this.onDraw(this.position, this.size, element);
} }
}, },