getBoundingClientRect: размеры и позиция
element.getBoundingClientRect()возвращает объектDOMRectс размерами элемента и его позицией относительно viewport (видимой области экрана).
Зачем нужно
Метод необходим всякий раз, когда нужно знать, где именно на экране находится элемент: для позиционирования тултипов, дропдаунов, реализации кастомного drag-and-drop или проверки видимости элемента. Он учитывает трансформации CSS и всегда отдаёт актуальные данные на момент вызова.
Где используется
- Позиционирование всплывающих подсказок и контекстных меню относительно элемента
- Проверка, виден ли элемент в viewport (ленивая загрузка до IntersectionObserver)
- Кастомный drag-and-drop: вычисление смещений
- Анимации с точными координатами
Возвращаемый объект
const rect = element.getBoundingClientRect();
rect.top // расстояние от верха viewport до верха элемента
rect.left // расстояние от левого края viewport до левого края элемента
rect.bottom // расстояние от верха viewport до нижнего края элемента
rect.right // расстояние от левого края viewport до правого края элемента
rect.width // ширина элемента (right - left)
rect.height // высота элемента (bottom - top)
rect.x // псевдоним left
rect.y // псевдоним top
Примеры
Базовое использование
const btn = document.querySelector('.btn');
const rect = btn.getBoundingClientRect();
console.log(`Ширина: ${rect.width}px`);
console.log(`Высота: ${rect.height}px`);
console.log(`Позиция: top=${rect.top}, left=${rect.left}`);
Позиционирование тултипа
function showTooltip(anchor, text) {
const tooltip = document.createElement('div');
tooltip.className = 'tooltip';
tooltip.textContent = text;
document.body.append(tooltip);
const rect = anchor.getBoundingClientRect();
const tooltipRect = tooltip.getBoundingClientRect();
// Разместить над элементом с центрированием
tooltip.style.top = `${rect.top + window.scrollY - tooltipRect.height - 8}px`;
tooltip.style.left = `${rect.left + window.scrollX + rect.width / 2 - tooltipRect.width / 2}px`;
}
Проверка видимости в viewport
function isInViewport(element) {
const rect = element.getBoundingClientRect();
return (
rect.top >= 0 &&
rect.left >= 0 &&
rect.bottom <= window.innerHeight &&
rect.right <= window.innerWidth
);
}
window.addEventListener('scroll', () => {
document.querySelectorAll('.lazy').forEach(el => {
if (isInViewport(el)) {
el.classList.add('visible');
}
});
});
Координаты относительно документа
// getBoundingClientRect даёт координаты относительно viewport,
// для документа нужно добавить прокрутку
function getDocumentRect(element) {
const rect = element.getBoundingClientRect();
return {
top: rect.top + window.scrollY,
left: rect.left + window.scrollX,
width: rect.width,
height: rect.height,
};
}
Частые ошибки
- Вызов до добавления в DOM — элемент должен быть вставлен и виден (не
display: none); иначе все значения будут 0. - Путать viewport и документ —
rect.top— это расстояние от верха экрана, а не страницы; при прокрутке значение меняется. - Кешировать результат —
getBoundingClientRectвозвращает снимок на момент вызова; при прокрутке или изменении layout значения устаревают.