我想获得一个元素相对于浏览器的视口(显示页面的视口,而不是整个页面)的位置。如何在JavaScript中做到这一点?

非常感谢


当前回答

根据德里克的回答。

/**
 * Gets element's x position relative to the visible viewport.
 */
function getAbsoluteOffsetLeft(el) {
  let offset = 0;
  let currentElement = el;

  while (currentElement !== null) {
    offset += currentElement.offsetLeft;
    offset -= currentElement.scrollLeft;
    currentElement = currentElement.offsetParent;
  }

  return offset;
}

/**
 * Gets element's y position relative to the visible viewport.
 */
function getAbsoluteOffsetTop(el) {
  let offset = 0;
  let currentElement = el;

  while (currentElement !== null) {
    offset += currentElement.offsetTop;
    offset -= currentElement.scrollTop;
    currentElement = currentElement.offsetParent;
  }

  return offset;
}

其他回答

编辑:添加一些代码来处理页面滚动。

function findPos(id) {
    var node = document.getElementById(id);     
    var curtop = 0;
    var curtopscroll = 0;
    if (node.offsetParent) {
        do {
            curtop += node.offsetTop;
            curtopscroll += node.offsetParent ? node.offsetParent.scrollTop : 0;
        } while (node = node.offsetParent);

        alert(curtop - curtopscroll);
    }
}

id参数是你想要偏移量的元素的id。改编自一个奇怪的帖子。

本页上的函数将返回一个矩形,其中包含传递的元素相对于浏览器视图端口的上、左、高和宽坐标。

    localToGlobal: function( _el ) {
       var target = _el,
       target_width = target.offsetWidth,
       target_height = target.offsetHeight,
       target_left = target.offsetLeft,
       target_top = target.offsetTop,
       gleft = 0,
       gtop = 0,
       rect = {};

       var moonwalk = function( _parent ) {
        if (!!_parent) {
            gleft += _parent.offsetLeft;
            gtop += _parent.offsetTop;
            moonwalk( _parent.offsetParent );
        } else {
            return rect = {
            top: target.offsetTop + gtop,
            left: target.offsetLeft + gleft,
            bottom: (target.offsetTop + gtop) + target_height,
            right: (target.offsetLeft + gleft) + target_width
            };
        }
    };
        moonwalk( target.offsetParent );
        return rect;
}

我假设在web页面中存在一个id为btn1的元素,并且包含jQuery。这适用于所有现代浏览器的Chrome, FireFox, IE >=9和Edge。 jQuery只是用来确定相对于文档的位置。

var screenRelativeTop =  $("#btn1").offset().top - (window.scrollY || 
                                            window.pageYOffset || document.body.scrollTop);

var screenRelativeLeft =  $("#btn1").offset().left - (window.scrollX ||
                                           window.pageXOffset || document.body.scrollLeft);

jQuery非常优雅地实现了这一点。如果你查看jQuery的偏移量的源代码,你会发现它基本上是这样实现的:

var rect = elem.getBoundingClientRect();
var win = elem.ownerDocument.defaultView;

return {
    top: rect.top + win.pageYOffset,
    left: rect.left + win.pageXOffset
};
function inViewport(element) {
    let bounds = element.getBoundingClientRect();
    let viewWidth = document.documentElement.clientWidth;
    let viewHeight = document.documentElement.clientHeight;

    if (bounds['left'] < 0) return false;
    if (bounds['top'] < 0) return false;
    if (bounds['right'] > viewWidth) return false;
    if (bounds['bottom'] > viewHeight) return false;

    return true;
}