Je voulais faire simple : Une page dont premier bloc doit occuper l’intégralité de l’écran.
html, body { padding: 0; margin: 0; }
#first { width: 100vw; height: 100vh; }
<div id="first">Hello</div>
<div>World</div>
Ça n’est *jamais* simple.
Barres de défilement
Alors déjà vw
et vh
prennent en compte les barres de défilement. J’ai perdu l’habitude sous mac mais elles prennent encore de la place à l’affichage sous windows.
Du coup, comme ma page est plus longue que l’écran, j’ai une barre de défilement verticale sur le côté. 100vw
+ la barre de défilement, c’est plus que l’écran. Mon bloc dépasse donc sur le côté.
J’ai deux solutions : 100%
, qui regarde la taille d’affichage disponible (donc sans les barres de défilement) ou window.innerWidth
en javascript qui fait la même chose.
Dans les deux cas je ne veux pas que la taille de mon contenu « saute » en fonction de la longueur de ma page. Le plus simple est de forcer l’affichage de la barre de défilement verticale même dans les très rares cas où je n’en aurai pas besoin.
html, body { padding: 0; margin: 0; overflow-y: scroll; }
#first { width: 100%; height: 100vh; }
<div id="first">Hello</div>
<div>World</div>
Je ne me préoccupe pas de la barre de défilement horizontale. Normalement je ne devrais jamais en avoir sur une page web.
La barre de navigation
Sur les smartphones les navigateurs proposent désormais une barre de navigation escamotable. Elle est visible quand on arrive sur la page, disparait quand on défile vers le bas, réapparait quand on défile vers le haut.
C’est un bon compromis entre le besoin d’un écran sans rien au milieu et le besoin d’avoir accès à la barre de navigation. Reste que « tout l’écran » peut vouloir dire trois choses :
- Tout l’écran de départ, quand il y a la barre, quitte à ce que ça ne prenne plus tout l’écran quand la barre disparait.
- Tout l’écran possible, quitte à ce que ça dépasse de l’écran quand la barre est visible.
- Tout l’écran disponible, et donc une taille qui change suivant que la barre est visible ou non.
Mon bloc doit prendre tout l’écran au démarrage de la page, et je ne veux pas que quoi que ce soit bouge dans la page simplement parce qu’on défile verticalement. Je cherche donc dans la solution 1.
J’ai deux outils pour ça :
100vh
en CSS, qui correspond à la taille n° 2 (sans la barre)window.innerHeight
en Javascript, qui correspond à la taille n°3 (adaptatif) avec un événement « resize » quand la barre apparait ou disparait
Idéalement ma solution c’est « 100vh moins la taille de la barre ».
Malheureusement la taille de la barre ne fait pas partie des variables d’environnement CSS. On a la taille des encoches des écrans iPhone mais pas la taille de la barre qui concerne pourtant quasiment tout le monde.
La seule solution que j’ai trouvée c’est au démarrage faire un <div> de 100vh
, regarder la taille qu’il a, retrancher window.innerHeight
, et stocker ça dans une variable CSS.
<script>
const div=document.createElement('div');
div.setAttribute('style', 'height:100vh;width:0;position.absolute;top:0');
const barSize = div.scrollHeight - window.innerHeight;
document.documentElement.style.setProperty('--bar-height', barSize+'px');
</script>
html, body { padding: 0; margin: 0; overflow-y: scroll; }
#first {
width: 100%;
height: calc(100vh - var(--barSize, 0px);
}
<div id="first">Hello</div>
<div>World</div>
Si vous trouvez mieux, je suis preneur.
Laisser un commentaire