Tamanhos de Janela e Rolagem em JavaScript
Aprenda a medir o viewport, ler o tamanho do documento, verificar a posição de rolagem e rolar programaticamente com JavaScript.
Compreender as dimensões da janela e o comportamento de rolagem é essencial para construir interfaces web responsivas. Este artigo aborda como medir o viewport (a área visível da página), como ler o tamanho total do documento, como descobrir o quanto a página foi rolada e como rolar programaticamente — incluindo rolagem suave e rolagem de um elemento para a área visível. Cada conceito vem acompanhado de um exemplo executável.
A distinção fundamental a ter em mente: o viewport é o que o utilizador consegue ver no momento, enquanto o documento é a página inteira, grande parte da qual pode estar fora da área visível.
Medindo o Viewport (Janela Visível)
O viewport é o retângulo da página que o utilizador vê agora. Há duas formas de ler o seu tamanho, e a diferença é importante.
document.documentElement.clientWidth/clientHeight— a largura e a altura do viewport excluindo a barra de rolagem. Esta é a escolha correta quando se precisa da área real disponível para o conteúdo.window.innerWidth/innerHeight— o interior completo da janela incluindo a largura da barra de rolagem. Útil para verificações rápidas, mas pode ser alguns pixels maior queclientWidthquando uma barra de rolagem está presente.
Use clientWidth/clientHeight para cálculos de layout (por exemplo, centralizar um elemento); use innerWidth/innerHeight para verificações de breakpoint onde alguns pixels não importam.
// Viewport size excluding the scrollbar (recommended for layout)
console.log(document.documentElement.clientWidth);
console.log(document.documentElement.clientHeight);
// Window interior including the scrollbar
console.log(window.innerWidth);
console.log(window.innerHeight);O exemplo a seguir exibe o tamanho do viewport em tempo real e é atualizado sempre que a janela é redimensionada.
<!DOCTYPE html>
<html lang="en">
<head>
<title>Window Size Display</title>
</head>
<body>
<div id="window-info"></div>
<script>
function displayWindowSize() {
const w = document.documentElement.clientWidth;
const h = document.documentElement.clientHeight;
document.getElementById('window-info').innerHTML =
'Viewport width: ' + w + 'px<br>' +
'Viewport height: ' + h + 'px';
}
window.addEventListener('resize', displayWindowSize);
window.addEventListener('load', displayWindowSize);
</script>
</body>
</html>Medindo o Tamanho Total do Documento
Para obter a altura de toda a página — incluindo a parte que foi rolada para fora da área visível — leia as propriedades scroll* do elemento do documento. Devido a inconsistências históricas entre navegadores, a forma confiável é obter o máximo de várias medições:
const scrollHeight = Math.max(
document.body.scrollHeight, document.documentElement.scrollHeight,
document.body.offsetHeight, document.documentElement.offsetHeight,
document.body.clientHeight, document.documentElement.clientHeight
);
console.log('Full document height: ' + scrollHeight);Este é exatamente o valor necessário para construir uma barra de progresso, um gatilho de scroll infinito ("estou perto do final?") ou um botão "rolar até o fim". scrollWidth funciona da mesma forma para overflow horizontal.
Lendo a Posição de Rolagem Atual
Para descobrir o quanto a página foi rolada, use:
window.scrollX— deslocamento de rolagem horizontal em pixels (também chamado dewindow.pageXOffset, um alias mais antigo).window.scrollY— deslocamento de rolagem vertical em pixels (aliaswindow.pageYOffset).
scrollX/scrollY são os nomes modernos; pageXOffset/pageYOffset são idênticos e ainda suportados para compatibilidade retroativa.
console.log(window.scrollX); // same as window.pageXOffset
console.log(window.scrollY); // same as window.pageYOffsetRolando Programaticamente
A janela expõe três métodos para mover a página por conta própria.
window.scrollTo(x, y)— rola para uma posição absoluta.scrollTo(0, 0)retorna ao topo.window.scrollBy(dx, dy)— rola relativamente à posição atual.scrollBy(0, 100)move 100px para baixo a partir de onde você está.element.scrollIntoView()— rola para que um elemento específico fique visível.
Os três aceitam um objeto de opções com behavior: 'smooth' para uma rolagem animada em vez de um salto instantâneo:
// Smoothly scroll back to the top of the page
window.scrollTo({ top: 0, left: 0, behavior: 'smooth' });
// Nudge the page down by one viewport height
window.scrollBy({ top: window.innerHeight, behavior: 'smooth' });Rolagem Suave até um Elemento
scrollIntoView é a forma mais simples de saltar para uma seção — por exemplo, um botão "voltar ao topo" ou "ir para os comentários". Passar { behavior: 'smooth' } anima o movimento:
<!DOCTYPE html>
<html lang="en">
<head>
<title>Smooth Scrolling</title>
</head>
<body>
<button onclick="document.getElementById('target').scrollIntoView({ behavior: 'smooth' });">Go to Target</button>
<div style="height: 2000px;">
<div id="target" style="margin-top: 1800px;">Target Element</div>
</div>
</body>
</html>Rastreando a Posição de Rolagem
Crie efeitos dinâmicos com base na posição de rolagem do utilizador. O exemplo abaixo atualiza um elemento fixo para exibir o deslocamento vertical atual a cada evento scroll.
<!DOCTYPE html>
<html lang="en">
<head>
<title>Scroll Position Detector</title>
</head>
<body>
<div style="height: 3000px;">
<div style="position: fixed;">Scroll position: <span id="position">0</span>px</div>
</div>
<script>
const positionSpan = document.getElementById('position');
window.addEventListener('scroll', function() {
positionSpan.innerHTML = window.scrollY;
});
</script>
</body>
</html>Nota: Para maior compatibilidade com navegadores, document.documentElement.scrollTop pode ser usado como alternativa para window.scrollY.
Encontrando a Posição de um Elemento com getBoundingClientRect
element.getBoundingClientRect() retorna o tamanho do elemento e sua posição relativa ao viewport (não ao documento). O objeto retornado possui top, bottom, left, right, width e height.
Como os valores são relativos ao viewport, eles mudam conforme você rola. Para converter a posição de um elemento em coordenadas do documento, adicione o deslocamento de rolagem atual:
const box = element.getBoundingClientRect();
// Distance from the top of the viewport (changes while scrolling)
console.log(box.top);
// Distance from the top of the whole document (stable)
const documentTop = box.top + window.scrollY;
console.log(documentTop);Um uso comum é verificar se um elemento está visível atualmente na tela:
function isInViewport(el) {
const r = el.getBoundingClientRect();
return r.top >= 0 &&
r.bottom <= document.documentElement.clientHeight;
}Para uma análise mais profunda da diferença entre coordenadas do viewport e do documento, consulte Coordenadas em JavaScript.
Personalizando Barras de Rolagem para Melhor Estética
Barras de rolagem personalizadas podem elevar o apelo visual do seu site:
<!DOCTYPE html>
<html lang="en">
<head>
<title>Custom Scrollbars</title>
<style>
body {
height: 2000px; /* For demonstration */
}
/* Custom scrollbar styling */
::-webkit-scrollbar {
width: 12px;
}
::-webkit-scrollbar-track {
background: darkblue;
}
::-webkit-scrollbar-thumb {
background-color: lightgreen;
border-radius: 10px;
border: 3px solid darkcyan;
}
</style>
</head>
<body>
Scroll to see the custom scrollbar!
</body>
</html>Neste exemplo, usamos pseudo-elementos para selecionar e estilizar diferentes partes da barra de rolagem. Veja a explicação de cada propriedade CSS utilizada:
::-webkit-scrollbar: Este pseudo-elemento seleciona a própria barra de rolagem. Definimos sua largura em 12 pixels, o que determina a espessura da barra de rolagem.::-webkit-scrollbar-track: Este pseudo-elemento representa a trilha (ou ranhura) pela qual o cursor da barra de rolagem se move. Estilizamos com um fundo azul escuro. As cores utilizadas aqui foram escolhidas para mostrar a diferença em cada parte da barra de rolagem. Cores mais sutis são sugeridas para uma aplicação real.::-webkit-scrollbar-thumb: Este pseudo-elemento seleciona a parte arrastável da barra de rolagem, conhecida como cursor. Escolhemos verde claro para o cursor, tornando-o destacado em relação à trilha para melhor visibilidade. Oborder-radius: 10pxaplica cantos arredondados ao cursor, dando-lhe um visual moderno e elegante. A borda de 3 pixels sólida em ciano escuro também é utilizada.
Nota: Os pseudo-elementos ::-webkit-scrollbar são específicos para navegadores baseados em Chromium. Para Firefox e padrões modernos, considere usar as propriedades CSS scrollbar-width e scrollbar-color. Exemplo: scrollbar-width: thin; scrollbar-color: lightgreen darkblue;
Conclusão
Ao dominar as técnicas de dimensionamento de janela e rolagem em JavaScript, você pode melhorar significativamente a experiência do utilizador e a responsividade dos seus projetos web. Lembre-se da distinção fundamental — clientWidth/clientHeight medem o viewport visível, as propriedades scroll* medem o documento completo, e scrollX/scrollY (também conhecido como pageXOffset/pageYOffset) indicam o quanto você rolou. Use scrollTo, scrollBy e scrollIntoView com behavior: 'smooth' para mover a página por conta própria.
Para continuar, explore:
- Rolagem em JavaScript — eventos e padrões para reagir à rolagem.
- Coordenadas em JavaScript — sistemas de coordenadas do viewport versus do documento em profundidade.
- Trabalhando com Estilos no DOM — leia e altere estilos de elementos, incluindo as dimensões discutidas aqui.