Quiero obtener la posición de un elemento en relación con la ventana gráfica del navegador (la ventana gráfica en la que se muestra la página, no toda la página). ¿Cómo se puede hacer esto en JavaScript?
Muchas gracias
Quiero obtener la posición de un elemento en relación con la ventana gráfica del navegador (la ventana gráfica en la que se muestra la página, no toda la página). ¿Cómo se puede hacer esto en JavaScript?
Muchas gracias
Respuestas:
Las respuestas existentes ahora están desactualizadas. El getBoundingClientRect()método nativo ha existido desde hace bastante tiempo y hace exactamente lo que pide la pregunta. Además, es compatible con todos los navegadores (¡al parecer, IE 5!)
Desde la página de MDN :
El valor devuelto es un objeto TextRectangle, que contiene propiedades de solo lectura izquierda, superior, derecha e inferior que describen el cuadro de borde, en píxeles, con la parte superior izquierda relativa a la parte superior izquierda de la ventana gráfica .
Lo usas así:
var viewportOffset = el.getBoundingClientRect();
// these are relative to the viewport, i.e. the window
var top = viewportOffset.top;
var left = viewportOffset.left;
getBoundingClientRect().topno está en mi IE11, devuelve 0. ¿Tiene alguna solución?
En mi caso, solo para estar seguro con respecto al desplazamiento, agregué el window.scroll a la ecuación:
var element = document.getElementById('myElement');
var topPos = element.getBoundingClientRect().top + window.scrollY;
var leftPos = element.getBoundingClientRect().left + window.scrollX;
Eso me permite obtener la posición relativa real del elemento en el documento, incluso si se ha desplazado.
getBoundingClientRect().topno está en mi IE11, devuelve 0. ¿Tiene alguna solución?
window.scrollY || window.pageYOffsetpuede mejorar el soporte
Editar: agregue un código para tener en cuenta el desplazamiento de la página.
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);
}
}
El argumento id es el id del elemento cuyo desplazamiento desea. Adaptado de una publicación peculiar .
var element = document.querySelector('selector');
var bodyRect = document.body.getBoundingClientRect(),
elemRect = element.getBoundingClientRect(),
offset = elemRect.top - bodyRect.top;
Puedes probar:
node.offsetTop - window.scrollY
Funciona en Opera con la metaetiqueta viewport definida.
offsetTopes relativa al elemento posicionado más cercano. Que, dependiendo de la estructura de la página, puede ser o no un elemento raíz.
jQuery implementa esto con bastante elegancia. Si nos fijamos en la fuente de jQuery offset, encontrará que esto es básicamente cómo se implementa:
var rect = elem.getBoundingClientRect();
var win = elem.ownerDocument.defaultView;
return {
top: rect.top + win.pageYOffset,
left: rect.left + win.pageXOffset
};
La función en esta página devolverá un rectángulo con las coordenadas superior, izquierda, altura y anchura de un elemento pasado en relación con el puerto de visualización del navegador.
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;
}
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;
}
Gracias por todas las respuestas. Parece que Prototype ya tiene una función que hace esto (la función page ()). Al ver el código fuente de la función, descubrí que primero calcula la posición de desplazamiento del elemento en relación con la página (es decir, la parte superior del documento), luego resta el scrollTop de eso. Vea el código fuente del prototipo para más detalles.
Supongo que un elemento que tiene una identificación de btn1existe en la página web, y también que jQuery está incluido. Esto ha funcionado en todos los navegadores modernos de Chrome, Firefox, IE> = 9 y Edge. jQuery solo se usa para determinar la posición relativa al documento.
var screenRelativeTop = $("#btn1").offset().top - (window.scrollY ||
window.pageYOffset || document.body.scrollTop);
var screenRelativeLeft = $("#btn1").offset().left - (window.scrollX ||
window.pageXOffset || document.body.scrollLeft);
A veces, getBoundingClientRect()el valor de la propiedad del objeto muestra 0 para IE. En ese caso, debe configurar display = 'block'el elemento. Puede usar el siguiente código para que todos los navegadores se compensen.
Extienda la funcionalidad de jQuery:
(function($) {
jQuery.fn.weOffset = function () {
var de = document.documentElement;
$(this).css("display", "block");
var box = $(this).get(0).getBoundingClientRect();
var top = box.top + window.pageYOffset - de.clientTop;
var left = box.left + window.pageXOffset - de.clientLeft;
return { top: top, left: left };
};
}(jQuery));
Utilizar :
var elementOffset = $("#" + elementId).weOffset();