aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorScott González <scott.gonzalez@gmail.com>2011-03-22 12:25:25 -0400
committerScott González <scott.gonzalez@gmail.com>2011-03-22 12:25:25 -0400
commit6f051d5d6a8eaf6fcc2a08ff68dbf5378029abc2 (patch)
treede1f0fd9b2cc00769c4117f58198a6c2784262d2
parentd4dadd14c293dfcbb4a7a214430ec511fea7a1da (diff)
downloadjquery-ui-6f051d5d6a8eaf6fcc2a08ff68dbf5378029abc2.tar.gz
jquery-ui-6f051d5d6a8eaf6fcc2a08ff68dbf5378029abc2.zip
Position: Merged offset option into my and at options and added support for percentage-based offsets. Fixes #6981 - Position: Merge offset option into my and at options. Fixes #7028 - Position: Allow percent-based offsets.
-rw-r--r--demos/position/cycler.html6
-rw-r--r--tests/unit/position/position_core.js36
-rw-r--r--ui/jquery.ui.position.js90
3 files changed, 114 insertions, 18 deletions
diff --git a/demos/position/cycler.html b/demos/position/cycler.html
index b52e22724..521b8d565 100644
--- a/demos/position/cycler.html
+++ b/demos/position/cycler.html
@@ -33,16 +33,14 @@
$.fn.left = function( using ) {
return this.position2({
my: "right middle",
- at: "left middle",
- offset: "25 0",
+ at: "left+25 middle",
using: using
});
}
$.fn.right = function( using ) {
return this.position2({
my: "left middle",
- at: "right middle",
- offset: "-25 0",
+ at: "right-25 middle",
using: using
});
}
diff --git a/tests/unit/position/position_core.js b/tests/unit/position/position_core.js
index 643561c20..66f7a8504 100644
--- a/tests/unit/position/position_core.js
+++ b/tests/unit/position/position_core.js
@@ -207,7 +207,41 @@ test('of', function() {
}, 'event - left top, right bottom');
});
-test('offset', function() {
+test('offsets', function() {
+ $('#elx').position({
+ my: 'left top',
+ at: 'left+10 bottom+10',
+ of: '#parentx',
+ collision: 'none'
+ });
+ same($('#elx').offset(), { top: 70, left: 50 }, 'offsets in at');
+
+ $('#elx').position({
+ my: 'left+10 top-10',
+ at: 'left bottom',
+ of: '#parentx',
+ collision: 'none'
+ });
+ same($('#elx').offset(), { top: 50, left: 50 }, 'offsets in my');
+
+ $('#elx').position({
+ my: 'left top',
+ at: 'left+50% bottom-10%',
+ of: '#parentx',
+ collision: 'none'
+ });
+ same($('#elx').offset(), { top: 58, left: 50 }, 'percentage offsets in at');
+
+ $('#elx').position({
+ my: 'left-30% top+50%',
+ at: 'left bottom',
+ of: '#parentx',
+ collision: 'none'
+ });
+ same($('#elx').offset(), { top: 65, left: 37 }, 'percentage offsets in my');
+});
+
+test('offset - deprecated', function() {
$('#elx').position({
my: 'left top',
at: 'left bottom',
diff --git a/ui/jquery.ui.position.js b/ui/jquery.ui.position.js
index 9d436ccf3..2108c1d7c 100644
--- a/ui/jquery.ui.position.js
+++ b/ui/jquery.ui.position.js
@@ -13,6 +13,9 @@ $.ui = $.ui || {};
var horizontalPositions = /left|center|right/,
verticalPositions = /top|center|bottom/,
+ roffset = /[+-]\d+%?/,
+ rposition = /^\w+/,
+ rpercent = /%$/,
center = "center",
_position = $.fn.position;
@@ -27,7 +30,8 @@ $.fn.position = function( options ) {
var target = $( options.of ),
targetElem = target[0],
collision = ( options.collision || "flip" ).split( " " ),
- offset = options.offset ? options.offset.split( " " ) : [ 0, 0 ],
+ offsets = {},
+ atOffset,
targetWidth,
targetHeight,
basePosition;
@@ -54,7 +58,10 @@ $.fn.position = function( options ) {
// force my and at to have valid horizontal and vertical positions
// if a value is missing or invalid, it will be converted to center
$.each( [ "my", "at" ], function() {
- var pos = ( options[this] || "" ).split( " " );
+ var pos = ( options[this] || "" ).split( " " ),
+ horizontalOffset,
+ verticalOffset;
+
if ( pos.length === 1) {
pos = horizontalPositions.test( pos[0] ) ?
pos.concat( [center] ) :
@@ -64,7 +71,20 @@ $.fn.position = function( options ) {
}
pos[ 0 ] = horizontalPositions.test( pos[0] ) ? pos[ 0 ] : center;
pos[ 1 ] = verticalPositions.test( pos[1] ) ? pos[ 1 ] : center;
- options[ this ] = pos;
+
+ // calculate offsets
+ horizontalOffset = roffset.exec( pos[ 0 ] );
+ verticalOffset = roffset.exec( pos [ 1 ] );
+ offsets[ this ] = [
+ horizontalOffset ? horizontalOffset[ 0 ] : 0,
+ verticalOffset ? verticalOffset[ 0 ] : 0
+ ];
+
+ // reduce to just the positions without the offsets
+ options[ this ] = [
+ rposition.exec( pos[ 0 ] )[ 0 ],
+ rposition.exec( pos[ 1 ] )[ 0 ]
+ ];
});
// normalize collision option
@@ -72,13 +92,6 @@ $.fn.position = function( options ) {
collision[ 1 ] = collision[ 0 ];
}
- // normalize offset option
- offset[ 0 ] = parseInt( offset[0], 10 ) || 0;
- if ( offset.length === 1 ) {
- offset[ 1 ] = offset[ 0 ];
- }
- offset[ 1 ] = parseInt( offset[1], 10 ) || 0;
-
if ( options.at[0] === "right" ) {
basePosition.left += targetWidth;
} else if ( options.at[0] === center ) {
@@ -91,8 +104,14 @@ $.fn.position = function( options ) {
basePosition.top += targetHeight / 2;
}
- basePosition.left += offset[ 0 ];
- basePosition.top += offset[ 1 ];
+ atOffset = [
+ parseInt( offsets.at[ 0 ], 10 ) *
+ ( rpercent.test( offsets.at[ 0 ] ) ? targetWidth / 100 : 1 ),
+ parseInt( offsets.at[ 1 ], 10 ) *
+ ( rpercent.test( offsets.at[ 1 ] ) ? targetHeight / 100 : 1 )
+ ];
+ basePosition.left += atOffset[ 0 ],
+ basePosition.top += atOffset[ 1 ];
return this.each(function() {
var elem = $( this ),
@@ -105,6 +124,12 @@ $.fn.position = function( options ) {
collisionHeight = elemHeight + marginTop +
( parseInt( $.curCSS( this, "marginBottom", true ) ) || 0 ),
position = $.extend( {}, basePosition ),
+ myOffset = [
+ parseInt( offsets.my[ 0 ], 10 ) *
+ ( rpercent.test( offsets.my[ 0 ] ) ? elem.outerWidth() / 100 : 1 ),
+ parseInt( offsets.my[ 1 ], 10 ) *
+ ( rpercent.test( offsets.my[ 1 ] ) ? elem.outerHeight() / 100 : 1 )
+ ],
collisionPosition;
if ( options.my[0] === "right" ) {
@@ -119,6 +144,9 @@ $.fn.position = function( options ) {
position.top -= elemHeight / 2;
}
+ position.left += myOffset[ 0 ];
+ position.top += myOffset[ 1 ];
+
// prevent fractions (see #5280)
position.left = Math.round( position.left );
position.top = Math.round( position.top );
@@ -138,7 +166,7 @@ $.fn.position = function( options ) {
collisionPosition: collisionPosition,
collisionWidth: collisionWidth,
collisionHeight: collisionHeight,
- offset: offset,
+ offset: [ atOffset[ 0 ] + myOffset[ 0 ], atOffset [ 1 ] + myOffset[ 1 ] ],
my: options.my,
at: options.at
});
@@ -212,4 +240,40 @@ $.ui.position = {
}
};
+// DEPRECATED
+if ( $.uiBackCompat !== false ) {
+ // offset option
+ (function( $ ) {
+ var _position = $.fn.position;
+ $.fn.position = function( options ) {
+ if ( !options || !( "offset" in options ) ) {
+ return _position.call( this, options );
+ }
+ var offset = options.offset.split( " " ),
+ at = options.at.split( " " );
+ if ( offset.length === 1 ) {
+ offset[ 1 ] = offset[ 0 ];
+ }
+ if ( /^\d/.test( offset[ 0 ] ) ) {
+ offset[ 0 ] = "+" + offset[ 0 ];
+ }
+ if ( /^\d/.test( offset[ 1 ] ) ) {
+ offset[ 1 ] = "+" + offset[ 1 ];
+ }
+ if ( at.length === 1 ) {
+ if ( /left|center|right/.test( at[ 0 ] ) ) {
+ at[ 1 ] = "center";
+ } else {
+ at[ 1 ] = at[ 0 ];
+ at[ 0 ] = "center";
+ }
+ }
+ return _position.call( this, $.extend( options, {
+ at: at[ 0 ] + offset[ 0 ] + " " + at[ 1 ] + offset[ 1 ],
+ offset: undefined
+ } ) );
+ }
+ }( jQuery ));
+}
+
}( jQuery ));