Comment obtenez-vous la hauteur rendue d'un élément?


406

Comment obtenez-vous la hauteur rendue d'un élément?

Disons que vous avez un <div>élément avec du contenu à l'intérieur. Ce contenu à l'intérieur va étirer la hauteur du <div>. Comment obtenir la hauteur "rendue" lorsque vous n'avez pas explicitement défini la hauteur. Évidemment, j'ai essayé:

var h = document.getElementById('someDiv').style.height;

Y a-t-il une astuce pour le faire? J'utilise jQuery si cela aide.


Réponses:


183

Ça devrait être

$('#someDiv').height();

avec jQuery. Cela récupère la hauteur du premier élément de l'ensemble encapsulé sous forme de nombre.

Essayer d'utiliser

.style.height

ne fonctionne que si vous avez défini la propriété en premier lieu. Pas très utile!


1
Un mot - génial! Merci pour la participation de tous. Beaucoup de bonnes informations sur ce fil. Cela me permettra de centrer les pages en utilisant CSS mais en utilisant jQuery pour rendre la hauteur globale du div "container" correcte sans s'aventurer dans CSS hackville. Merci encore.
BuddyJoe

3
même si vous n'utilisez PAS jQuery ou ne pouvez pas ou je ne veux pas, je suggère fortement à quiconque de l'implémenter en utilisant simplement offsetHeight d'aller de l'avant et de télécharger la source jQuery et de rechercher "height" pour trouver le code qu'ils utilisent. plein de trucs fous là-dedans!
Simon_Weaver

1
@matejkramny - Cette question et réponse remonte à plus de 5 ans . L'OP utilisait déjà jQuery sur son site, plutôt que de réimplémenter lui-même la même logique / similaire, pourquoi ne pas utiliser la fonction jQuery d'une ligne qui le fait déjà? Je suis d'accord que jQuery est exagéré pour beaucoup de choses et je n'ai pas peur de vanilla JS, mais quand il y a une fonction dans une bibliothèque qui fait exactement ce dont vous avez besoin, il semble idiot de ne pas l'utiliser, en particulier pour des raisons de "Pas inventé ici"
Russ Cam

3
@matejkramny L'intention du PO lors de la question était d'obtenir la hauteur de rendu de l'élément, pas de comprendre ce qui se passe dans le DOM et dans les coulisses; si telle était leur intention, ils ont posé la mauvaise question. Je suis d'accord que les gens devraient être enclins à comprendre les bibliothèques et les cadres qu'ils utilisent, la connaissance est le pouvoir et tout cela, mais parfois, on veut juste une réponse à une question spécifique. En effet, les commentaires ci-dessus suggèrent déjà de parcourir le code jQuery pour comprendre ce qui se passe dans les coulisses.
Russ Cam

22
Pour l'OP, l'utilisation de jQuery est une réponse valide. Pour le reste du monde voyant cela depuis lors, la réponse non jQuery est la meilleure. Peut-être que SO doit s'adapter à cette réalité.
Dimitris

1220

Essayez l'un des:

var h = document.getElementById('someDiv').clientHeight;
var h = document.getElementById('someDiv').offsetHeight;
var h = document.getElementById('someDiv').scrollHeight;

clientHeight comprend la hauteur et le rembourrage vertical.

offsetHeight inclut la hauteur, le rembourrage vertical et les bordures verticales.

scrollHeight inclut la hauteur du document contenu (serait supérieure à la hauteur en cas de défilement), le remplissage vertical et les bordures verticales.


3
Merci, je ne connaissais pas cette propriété. Il est également compatible avec IE8 +.
lyubeto

Je suis perplexe quant à la signification de clientHeight. J'ai un élément div qui contient un tas d'éléments p et le contenu va bien au-delà de la zone visible du navigateur vers le bas. Et je m'attendais à ce que clientHeight donne la hauteur rendue et scrollHeight pour donner toute la longueur. Mais ils sont presque égaux (ne diffèrent que par la marge, le rembourrage, etc.).
bahti

10
@bahti sauf s'il a lui-même une hauteur limitée et un débordement: caché ou une certaine forme de débordement: défilement, l'élément se développera (que ce soit dans votre vue ou non) pour afficher tout le contenu et scrollHeight et clientHeight seront égaux.
Ulad Kasach

4
Excellente réponse, mais logiquement, les bordures qui affectent la hauteur d'un élément sont les bordures supérieure et inférieure, qui sont horizontales. Cette réponse les désigne comme des «bordures verticales». Je pensais juste laisser tomber mes 2 cents
Kehlan Krumme

1
D'après ce que je sais, .clientWidth/.clientHeight n'incluez PAS la largeur du défilement si le défilement est affiché. Si vous souhaitez inclure la largeur du défilement, vous pouvez utiliser à la element.getBoundingClientRect().width place
Dmitry Gonchar

151

NON JQUERY car il y avait un tas de liens utilisant elem.style.heighten haut de ces réponses ...

HAUTEUR INTÉRIEURE:
https://developer.mozilla.org/en-US/docs/Web/API/Element.clientHeight

document.getElementById(id_attribute_value).clientHeight;

HAUTEUR EXTÉRIEURE:
https://developer.mozilla.org/en-US/docs/Web/API/HTMLElement.offsetHeight

document.getElementById(id_attribute_value).offsetHeight; 

Ou l'une de mes références préférées: http://youmightnotneedjquery.com/


49

Vous pouvez utiliser .outerHeight() à cette fin.

Il vous donnera la hauteur de rendu totale de l'élément. De plus, vous n'avez besoin de définir aucun css-heightélément. Par mesure de précaution, vous pouvez conserver sa hauteur automatiquement afin qu'elle puisse être rendue selon la hauteur du contenu.

//if you need height of div excluding margin/padding/border
$('#someDiv').height();

//if you need height of div with padding but without border + margin
$('#someDiv').innerHeight();

// if you need height of div including padding and border
$('#someDiv').outerHeight();

//and at last for including border + margin + padding, can use
$('#someDiv').outerHeight(true);

Pour une vue claire de ces fonctions, vous pouvez aller sur le site de jQuery ou un article détaillé ici .

cela effacera la différence entre .height()/ innerHeight()/outerHeight()


1
Merci. En travaillant avec des flotteurs, j'ai eu beaucoup de problèmes avec la hauteur auto, mais je n'avais alors aucune expérience. En règle générale, je n'ai pas défini la hauteur, sauf dans un script de mise en page complexe où j'efface initialement le champ, mais le configure pour qu'il soit égal pour chaque bloc (Div) qui se retrouve avec le même sommet. Même une différence d'un pixel entre les blocs peut visser la disposition lors du redimensionnement des fenêtres.
DHorse

1
BTW, je pense que l'offset a des utilisations dépendantes de la version du navigateur concernant les marges que cela élimine.
DHorse

2
La question n'appelle pas jQuery. Pouah.
dthree

1
@dthree Je pense qu'il a clairement mentionné qu'il utilise jQuery. (également inclus dans les balises) :)
ouvert et gratuit

45

J'utilise ceci pour obtenir la hauteur d'un élément (retourne float) :

document.getElementById('someDiv').getBoundingClientRect().height

Cela fonctionne également lorsque vous utilisez le DOM virtuel . Je l'utilise dans Vue comme ceci:

this.$refs['some-ref'].getBoundingClientRect().height

1
getBoundingClientRect (). height renvoie un nombre à virgule flottante (tandis que les autres renvoient un entier), sympa :)
Ari

31
style = window.getComputedStyle(your_element);

puis simplement: style.height


14

Certainement utiliser

$('#someDiv').height()   // to read it

ou

$('#someDiv').height(newHeight)  // to set it

Je poste ceci comme une réponse supplémentaire car il y a quelques choses importantes que je viens d'apprendre.

Je suis presque tombé dans le piège en ce moment d'utiliser offsetHeight. C'est ce qui s'est passé :

  • J'ai utilisé la bonne vieille astuce consistant à utiliser un débogueur pour «surveiller» les propriétés de mon élément
  • J'ai vu lequel a une valeur proche de la valeur que j'attendais
  • C'était offsetHeight - donc je l'ai utilisé.
  • Ensuite, j'ai réalisé que cela ne fonctionnait pas avec une DIV cachée
  • J'ai essayé de me cacher après avoir calculé maxHeight mais cela avait l'air maladroit - je me suis trompé.
  • J'ai fait une recherche - découvert jQuery.height () - et l'ai utilisé
  • découvert que height () fonctionne même sur les éléments cachés
  • juste pour le plaisir j'ai vérifié l'implémentation jQuery de hauteur / largeur

En voici juste une partie:

Math.max(
Math.max(document.body["scroll" + name], document.documentElement["scroll" + name]),
Math.max(document.body["offset" + name], document.documentElement["offset" + name])
) 

Oui, il regarde les deux défilement et décalage. Si cela échoue, il regarde encore plus loin, en tenant compte des problèmes de compatibilité du navigateur et du CSS. En d'autres termes STUFF I DONT CARE ABOUT - or want to.

Mais je n'ai pas à le faire. Merci jQuery!

Morale de l'histoire: si jQuery a une méthode pour quelque chose, c'est probablement pour une bonne raison, probablement liée à la compatibilité.

Si vous n'avez pas lu la liste des méthodes jQuery récemment, je vous suggère de jeter un œil.


Vu votre autre commentaire au niveau de la question. Je suis vendu sur jQuery. Cela fait un petit moment. Mais cela a scellé l'accord. Je suis amoureux du fait que cette chose simple va résoudre des centaines de problèmes de mise en page pour moi (principalement sur les sites Intranet où je sais que JavaScript est en cours d'exécution).
BuddyJoe

13
document.querySelector('.project_list_div').offsetHeight;

4
ajouter une explication à votre solution
Freelancer

puis offsetHeight
Ritwik

6
Cette propriété arrondira la valeur à un entier . Si vous avez besoin d'une valeur flottante , utilisezelem.getBoundingClientRect().height
Penny Liu

12

J'ai créé un code simple qui n'a même pas besoin de JQuery et qui va probablement aider certaines personnes. Il obtient la hauteur totale de 'ID1' après le chargement et l'utilise sur 'ID2'

function anyName(){
    var varname=document.getElementById('ID1').offsetHeight;
    document.getElementById('ID2').style.height=varname+'px';
}

Il suffit ensuite de régler le corps pour le charger

<body onload='anyName()'>

C'est utile et j'emploie quelque chose de similaire dans un code plus complexe.
DHorse

10

Hm nous pouvons obtenir la géométrie de l'élément ...

var geometry;
geometry={};
var element=document.getElementById(#ibims);
var rect = element.getBoundingClientRect();
this.geometry.top=rect.top;
this.geometry.right=rect.right;
this.geometry.bottom=rect.bottom;
this.geometry.left=rect.left;
this.geometry.height=this.geometry.bottom-this.geometry.top;
this.geometry.width=this.geometry.right-this.geometry.left;
console.log(this.geometry);

Et ce simple JS?


1
var geometry; geometry={};peut simplement êtrevar geometry={};
Mark Schultheiss

10

Je pense que la meilleure façon de le faire en 2020 est d'utiliser des js simples et getBoundingClientRect().height;

Voici un exemple

let div = document.querySelector('div');
let divHeight = div.getBoundingClientRect().height;

console.log(`Div Height: ${divHeight}`);
<div>
  How high am I? 🥴
</div>

En plus de heightcette façon, nous avons également accès à un tas d'autres choses sur le div.

let div = document.querySelector('div');
let divInfo = div.getBoundingClientRect();

console.log(divInfo);
<div>What else am I? 🥴</div>


8

Est-ce donc la réponse?

"Si vous devez calculer quelque chose sans le montrer, définissez l'élément sur visibility:hiddenetposition:absolute ajoutez-le à l'arborescence DOM, récupérez l'offsetHeight et supprimez-le. (C'est ce que fait la bibliothèque de prototypes derrière les lignes la dernière fois que j'ai vérifié)."

J'ai le même problème sur un certain nombre d'éléments. Il n'y a pas de jQuery ou de Prototype à utiliser sur le site mais je suis tout à fait d'accord pour emprunter la technique si ça marche. Comme exemple de certaines choses qui n'ont pas fonctionné, suivies de ce qui a fonctionné, j'ai le code suivant:

// Layout Height Get
function fnElementHeightMaxGet(DoScroll, DoBase, elementPassed, elementHeightDefault)
{
    var DoOffset = true;
    if (!elementPassed) { return 0; }
    if (!elementPassed.style) { return 0; }
    var thisHeight = 0;
    var heightBase = parseInt(elementPassed.style.height);
    var heightOffset = parseInt(elementPassed.offsetHeight);
    var heightScroll = parseInt(elementPassed.scrollHeight);
    var heightClient = parseInt(elementPassed.clientHeight);
    var heightNode = 0;
    var heightRects = 0;
    //
    if (DoBase) {
        if (heightBase > thisHeight) { thisHeight = heightBase; }
    }
    if (DoOffset) {
        if (heightOffset > thisHeight) { thisHeight = heightOffset; }
    }
    if (DoScroll) {
        if (heightScroll > thisHeight) { thisHeight = heightScroll; }
    }
    //
    if (thisHeight == 0) { thisHeight = heightClient; }
    //
    if (thisHeight == 0) { 
        // Dom Add:
        // all else failed so use the protype approach...
        var elBodyTempContainer = document.getElementById('BodyTempContainer');
        elBodyTempContainer.appendChild(elementPassed);
        heightNode = elBodyTempContainer.childNodes[0].offsetHeight;
        elBodyTempContainer.removeChild(elementPassed);
        if (heightNode > thisHeight) { thisHeight = heightNode; }
        //
        // Bounding Rect:
        // Or this approach...
        var clientRects = elementPassed.getClientRects();
        heightRects = clientRects.height;
        if (heightRects > thisHeight) { thisHeight = heightRects; }
    }
    //
    // Default height not appropriate here
    // if (thisHeight == 0) { thisHeight = elementHeightDefault; }
    if (thisHeight > 3000) {
        // ERROR
        thisHeight = 3000;
    }
    return thisHeight;
}

qui essaie tout et n'importe quoi pour obtenir un résultat nul. ClientHeight sans effet. Avec les éléments problématiques, je reçois généralement NaN dans la base et zéro dans les hauteurs de décalage et de défilement. J'ai ensuite essayé la solution Ajouter DOM et clientRects pour voir si cela fonctionne ici.

29 juin 2011, j'ai en effet mis à jour le code pour essayer à la fois d'ajouter à DOM et clientHeight avec de meilleurs résultats que ce à quoi je m'attendais.

1) clientHeight était également égal à 0.

2) Dom m'a en fait donné une hauteur qui était super.

3) ClientRects renvoie un résultat presque identique à la technique DOM.

Étant donné que les éléments ajoutés sont de nature fluide, lorsqu'ils sont ajoutés à un élément DOM Temp autrement vide, ils sont rendus en fonction de la largeur de ce conteneur. Cela devient bizarre, car c'est 30 pixels plus court qu'il ne finit par le faire.

J'ai ajouté quelques instantanés pour illustrer comment la hauteur est calculée différemment. Bloc de menu rendu normalement Bloc de menu ajouté à l'élément DOM Temp

Les différences de hauteur sont évidentes. Je pourrais certainement ajouter un positionnement absolu et caché mais je suis sûr que cela n'aura aucun effet. J'ai continué à être convaincu que cela ne fonctionnerait pas!

(Je m'éloigne davantage) La hauteur sort (rend) plus bas que la vraie hauteur rendue. Cela pourrait être résolu en définissant la largeur de l'élément DOM Temp pour qu'il corresponde au parent existant et pourrait être fait assez précisément en théorie. Je ne sais pas non plus ce qui résulterait de leur suppression et de leur ajout à leur emplacement actuel. Comme ils sont arrivés par une technique innerHTML, je chercherai à utiliser cette approche différente.

* CEPENDANT * Rien de tout cela n'était nécessaire. En fait, cela a fonctionné comme annoncé et a retourné la bonne hauteur !!!

Quand j'ai été en mesure de rendre les menus à nouveau incroyablement visibles, DOM avait renvoyé la bonne hauteur selon la disposition fluide en haut de la page (279 px). Le code ci-dessus utilise également getClientRects qui retourne 280 px.

Ceci est illustré dans l'instantané suivant (extrait de Chrome une fois qu'il a fonctionné.)
entrez la description de l'image ici

Maintenant, je n'ai aucune idée de pourquoi ce truc de prototype fonctionne, mais il semble que ce soit le cas. Alternativement, getClientRects fonctionne également.

Je soupçonne que la cause de tous ces problèmes avec ces éléments particuliers était l'utilisation de innerHTML au lieu d'appendChild, mais c'est de la pure spéculation à ce stade.


6

offsetHeight, d'habitude.

Si vous devez calculer quelque chose mais ne pas l'afficher, définissez l'élément sur visibility:hiddenet position:absolute, ajoutez-le à l'arborescence DOM, récupérez le offsetHeightet supprimez-le. (C'est ce que fait la bibliothèque de prototypes en arrière-plan la dernière fois que j'ai vérifié).


intéressant. je n'ai jamais vérifié le prototype. une idée pourquoi jQuery ne fait pas cela en coulisses?
Simon_Weaver

J'ai vu cela lorsque j'ai eu des difficultés et testé cette technique et cela a très bien fonctionné en JavaScript simple
DHorse

5

Parfois, offsetHeight retournera zéro parce que l'élément que vous avez créé n'a pas encore été rendu dans le Dom. J'ai écrit cette fonction pour de telles circonstances:

function getHeight(element)
{
    var e = element.cloneNode(true);
    e.style.visibility = "hidden";
    document.body.appendChild(e);
    var height = e.offsetHeight + 0;
    document.body.removeChild(e);
    e.style.visibility = "visible";
    return height;
}

vous devez cloner l'élément sinon il sera complètement supprimé du dom. Il semble que c'est ce qui va se passer dans votre code.
punkbit

Ce code n'est pas destiné à conserver l'élément dans le DOM. Il est destiné à le mettre dans le DOM brièvement (assez longtemps pour le rendre et obtenir sa hauteur), puis il le retire. Vous pouvez ensuite placer l'élément dans le dom ailleurs plus tard (en sachant quelle sera sa hauteur avant de le faire). Notez le nom de la fonction "getHeight"; c'est tout ce que le code a l'intention de faire.
Lonnie Best

@punkbit: Je vois ce que tu veux dire. Votre élément est déjà dans le dom. Le code que j'ai écrit est pour un élément qui n'est pas encore dans le DOM. Le clonage serait mieux, comme vous le dites, car peu importe que l'élément soit dans le dom ou non.
Lonnie Best

@punkbit: J'ai modifié le code en utilisant le clonage, mais je ne l'ai pas testé.
Lonnie Best

ouais, c'était mon point. Il me semblait qu'il disait "élément" pour un élément existant dans le DOM. Mais tout va bien! Ne vous méprenez pas.
punkbit

4

Si vous utilisez déjà jQuery, votre meilleur pari est .outerHeight()ou .height(), comme cela a été indiqué.

Sans jQuery, vous pouvez vérifier le dimensionnement de la boîte en cours d'utilisation et ajouter divers rembourrages + bordures + clientHeight, ou vous pouvez utiliser getComputedStyle :

var h = getComputedStyle (document.getElementById ('someDiv')). height;

h sera maintenant une chaîne comme un "53.825px".

Et je ne trouve pas la référence, mais je pense que j'ai entendu dire que cela getComputedStyle()peut coûter cher, donc ce n'est probablement pas quelque chose que vous voulez appeler à chaque window.onscrollévénement (mais alors, jQuery ne l'est pas non plus height()).


Une fois que vous avez la hauteur getComputedStyle, utilisez parseInt(h, 10)pour obtenir un entier pour les calculs.
RhodanV5500


1

Si j'ai bien compris votre question, alors peut-être que quelque chose comme ça aiderait:

function testDistance(node1, node2) {
    /* get top position of node 1 */
    let n1Pos = node1.offsetTop;
    /* get height of node 1 */
    let n1Height = node1.clientHeight;
    /* get top position of node 2 */
    let n2Pos = node2.offsetTop;
    /* get height of node 2 */
    let n2Height = node2.clientHeight;

    /* add height of both nodes */
    let heightTogether = n1Height + n2Height;
    /* calculate distance from top of node 1 to bottom of node 2 */
    let actualDistance = (n2Pos + n2Height) - n1Pos;

    /* if the distance between top of node 1 and bottom of node 2
       is bigger than their heights combined, than there is something between them */
    if (actualDistance > heightTogether) {
        /* do something here if they are not together */
        console.log('they are not together');
    } else {
        /* do something here if they are together */
        console.log('together');
    } 
}

-4

Avez-vous défini la hauteur dans le CSS spécifiquement? Si vous ne l'avez pas, vous devez utiliser offsetHeight;plutôt queheight

var h = document.getElementById('someDiv').style.offsetHeight;

8
offsetHeight est une propriété de l'élément lui-même, pas de son style.
Shog9
En utilisant notre site, vous reconnaissez avoir lu et compris notre politique liée aux cookies et notre politique de confidentialité.
Licensed under cc by-sa 3.0 with attribution required.