From d4dd548acaf049d8e4dca9e4b879a51f26bb3d27 Mon Sep 17 00:00:00 2001 From: Arthur Stolyar Date: Tue, 5 May 2015 08:16:29 -0700 Subject: [PATCH] Offset: Fix .offset() to correctly work with ShadowDOM Fixes gh-1784 Close gh-2043 --- src/offset.js | 28 ++++++++++++++-------------- test/unit/offset.js | 28 +++++++++++++++++++++++----- 2 files changed, 37 insertions(+), 19 deletions(-) diff --git a/src/offset.js b/src/offset.js index c6ced41be..0cc26d7d9 100644 --- a/src/offset.js +++ b/src/offset.js @@ -39,7 +39,7 @@ jQuery.offset = { elem.style.position = "relative"; } - curOffset = curElem.offset(); + curOffset = curElem.offset() || { top: 0, left: 0 }; curCSSTop = jQuery.css( elem, "top" ); curCSSLeft = jQuery.css( elem, "left" ); calculatePosition = ( position === "absolute" || position === "fixed" ) && @@ -87,8 +87,7 @@ jQuery.fn.extend({ }); } - var docElem, win, - box = { top: 0, left: 0 }, + var docElem, win, rect, elem = this[ 0 ], doc = elem && elem.ownerDocument; @@ -96,19 +95,20 @@ jQuery.fn.extend({ return; } - docElem = doc.documentElement; + rect = elem.getBoundingClientRect(); - // Make sure it's not a disconnected DOM node - if ( !jQuery.contains( docElem, elem ) ) { - return box; + // Make sure element is not hidden (display: none) or disconnected + if ( rect.width || rect.height || elem.getClientRects().length ) { + win = getWindow( doc ); + docElem = doc.documentElement; + + return { + top: rect.top + ( win.pageYOffset || docElem.scrollTop ) - + ( docElem.clientTop || 0 ), + left: rect.left + ( win.pageXOffset || docElem.scrollLeft ) - + ( docElem.clientLeft || 0 ) + }; } - - box = elem.getBoundingClientRect(); - win = getWindow( doc ); - return { - top: box.top + ( win.pageYOffset || docElem.scrollTop ) - ( docElem.clientTop || 0 ), - left: box.left + ( win.pageXOffset || docElem.scrollLeft ) - ( docElem.clientLeft || 0 ) - }; }, position: function() { diff --git a/test/unit/offset.js b/test/unit/offset.js index 13789c2e9..c0eacb65c 100644 --- a/test/unit/offset.js +++ b/test/unit/offset.js @@ -57,13 +57,31 @@ test("object without getBoundingClientRect", function() { equal( result.left, 0, "Check left" ); }); -test("disconnected node", function() { - expect(2); +test("disconnected element", function() { + expect(1); - var result = jQuery( document.createElement("div") ).offset(); + var result; - equal( result.top, 0, "Check top" ); - equal( result.left, 0, "Check left" ); + try { + result = jQuery( document.createElement("div") ).offset(); + } catch ( e ) {} + + ok( !result, "no position for disconnected element" ); +}); + +test("hidden (display: none) element", function() { + expect(1); + + var result, + node = jQuery("
").appendTo("#qunit-fixture"); + + try { + result = node.offset(); + } catch ( e ) {} + + node.remove(); + + ok( !result, "no position for hidden (display: none) element" ); }); testIframe("offset/absolute", "absolute", function($, iframe) {