I have a weird bug that started showing up when I made the body be a relative positioned element with a 39px margin (I'm making room for a toolbar at the top of a page).
Anyway - if you look at how most sites tell you to compute a page element position, you'll see code like this:
function getPos(elt) {
var pt = [0, 0];
while (elt.offsetParent !== null) {
pt[0] += elt.offsetLeft;
pt[1] += elt.offsetTop;
elt = elt.offsetParent;
}
return pt;
}
This works fine, even if your <body> tag has a a margin. BUT, if your body is also position:relative, then this returns a value with is too small - it does not include the margins of the body element.
How do I 1) detect if the body is relative positioned, and 2) find our what the margins are so I can add them back in?
Note that I need Page coordinates so I can compare them to MouseEvent PageX, PageY.
We can also use the jQuery position() method. The position() method is an inbuilt method in jQuery which is used to find the position of the first matched element relative to its parent element in the DOM tree.
Use the Element. getBoundingClientRect() Function to Get the Position of an Element in JavaScript. The getBoundingClientRect() function produces a DOMRect object containing information about an element's size and position in the viewport.
We can use the getBoundingClientRect method to get an element's position relative to its viewport. We get the div with querySelector . Then we call getBoundingClientRect on it to get an object with the top and left properties. top has the position relative to the top of the viewport.
position: relative; Setting the top, right, bottom, and left properties of a relatively-positioned element will cause it to be adjusted away from its normal position. Other content will not be adjusted to fit into any gap left by the element.
If you restrict yourself to only working in "modern" browsers, as the zepto.js implementation does, you can get a much smaller implementation of the .offset() function:
offset: function(){
var obj = this[0].getBoundingClientRect();
return {
left: obj.left + document.body.scrollLeft,
top: obj.top + document.body.scrollTop,
width: obj.width,
height: obj.height
};
}
https://github.com/madrobby/zepto/blob/master/src/zepto.js
Which is more or less what jQuery does if getBoundingClientRect is available.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With