Pourquoi cet élément inline-block est-il poussé vers le bas?

Voici mon code et je veux comprendre que pourquoi #firstDiv est poussé vers le bas par tous les navigateurs. Je veux vraiment comprendre les rouages intérieurs du fait que pourquoi il est poussé vers le bas plutôt que de le tirer vers le haut d'une manière ou d'une autre. (et je sais comment aligner leurs tops :))

et je sais que son débordement:caché qui est la cause mais pas sûr que la raison pour laquelle il pousse que div vers le bas.

<div id="container">
<div id="firstDiv">FIRST</div>
<div id="secondDiv">SECOND</div>
<div id="thirdDiv">THIRD
<br>some more content<br> some more content
</div>
</div>

body{
    width: 350px;
    margin: 0px auto;
}
#container {
    border: 15px solid orange;   
}
#firstDiv{
    border: 10px solid brown;     
    display:inline-block;
    width: 70px;      
    overflow:hidden;  
}
#secondDiv{
    border: 10px solid skyblue;         
    float:left;
    width: 70px;     
}
#thirdDiv{
    display:inline-block;
    border: 5px solid yellowgreen;    
}

http://jsfiddle.net/WGCyu / .

205
demandé sur Josef K 2012-02-14 11:09:18

8 réponses

fondamentalement, vous avez ajouté plus d'encombrement dans votre code qui crée plus de confusion donc d'abord j'essaie d'éliminer l'encombrement qui empêche de comprendre la vraie question.

tout d'abord, nous devons établir que quelle est la vraie question? c'est pourquoi " inline-block " élément est poussé vers le bas.

maintenant nous commençons à le comprendre et d'abord enlever le désordre.

1 - Pourquoi ne pas donner aux trois divs la même largeur de bordure? donnons-la.

2 - l'élément flottant a-t-il un lien quelconque avec l'élément en ligne-bloc poussé vers le bas? Non, il n'a rien à faire avec elle.

donc, nous avons supprimé ce div tout à fait . Et vous êtes témoins du même comportement de l'élément inline-bloc poussé vers le bas.

voici le tour de certains littérature pour saisir l'idée de boîtes de lignes et comment ils sont alignés dans la même ligne esp lire le dernier paragraphe attentivement parce qu'il y a la réponse de votre question.

la ligne de base d'un' bloc en ligne 'est la ligne de base de sa dernière boîte de ligne dans le flux normal, sauf s'il n'y a pas de boîte de ligne en flux ou si sa propriété' overflow 'a une valeur calculée autre que' visible', auquel cas la ligne de base est la ligne de base marge bord.

si vous n'êtes pas sûr de ligne de base alors voici une brève explication en mots simples.

tous les caractères sauf 'gjpqy' sont écrits sur la ligne de base vous pouvez penser à la ligne de base comme si vous dessiniez une ligne horizontale simple comme souligner juste au-dessous de ces "caractères aléatoires" alors ce sera la ligne de base mais maintenant si vous écrivez un des caractères 'gjpqy' sur la même ligne alors partie inférieure de ces les caractères tomberaient sous la ligne.

ainsi, nous pouvons dire que tous les caractères sauf 'gjpqy' sont écrits complètement au-dessus de la ligne de base alors qu'une partie de ces caractères sont écrits au-dessous de la ligne de base.

3 - pourquoi ne pas vérifier où est la ligne de base de notre ligne? J'ai ajouté quelques caractères qui montrent la ligne de base de notre ligne.

4 - pourquoi ne pas ajouter certains personnages dans nos divs aussi pour trouver leurs bases dans la div? Ici, certains caractères ajoutés dans divs pour clarifier la ligne de base .

maintenant que vous comprenez à propos de baseline, lisez la version simplifiée suivante à propos de baseline des blocs en ligne.

i) Si inline-bloc en question a sa propriété overflow définie à visible (qui est par défaut donc pas besoin de définir si). Alors sa ligne de base serait le référence du bloc contenant de la ligne.

ii) si le bloc en ligne en question a sa propriété overflow réglée à autrement que visible. Alors sa marge inférieure serait sur la ligne de base de la boîte contenant.

  • premier point en détail

maintenant regardez à nouveau pour clarifier votre concept que ce qui est qui se passe avec le vert div . Si encore n'importe quelle confusion alors ici est ajouté plus de caractères près de Green div pour établir la ligne de base du bloc contenant et la ligne de base de Green div est alignée.

Eh bien, je déclare maintenant qu'ils ont la même base de référence? DROIT?

5 - alors pourquoi ne pas les chevaucher et voir si elles sont en bon état l'une sur l'autre? Ainsi, j'amène la troisième div-gauche: 35px; à vérifier s'ils ont la même ligne de base maintenant ?

maintenant, nous avons notre premier point prouvé.

  • Second point en détail

Eh bien, après explication du premier point le second point est facilement digestible et vous voyez que le premier div qui a la propriété overflow réglée à autre que visible (caché) a sa marge inférieure sur la ligne de base de la ligne.

Maintenant, vous pouvez faire quelques des expériences pour l'illustrer davantage.

  1. Set première div en overflow:visible (ou l'enlever complètement) .
  2. Set deuxième div en overflow: autres que visible .
  3. Set les deux divs overflow: autres que visible .

maintenant, ramenez votre bazar et voyez si tout va bien pour vous.

  1. Apporter retour de votre div flottant (bien sûr, il est nécessaire de

    augmenter la largeur de corps) Vous voyez, il n'a pas d'effet.
  2. Ramener même bizarre marges .
  3. mettre div vert à débordement: visible comme vous mettez dans votre question (que le désalignement est dû à l'augmentation de la largeur de la frontière de 1px à 5px donc si ajustement négatif gauche vous verrez qu'il n'y a pas de problème)
  4. maintenant supprimer les caractères supplémentaires que j'ai ajoutés pour aider dans la compréhension de . (et bien sûr supprimer négatif à gauche)
  5. enfin réduire la largeur du corps parce que nous n'avons plus besoin d'un plus large.

et maintenant nous sommes de retour à notre point de départ.

j'espère avoir répondu à votre question.

322
répondu Gary Lindahl 2014-03-05 11:34:18

la valeur par défaut pour vertical-align dans CSS est baseline et cette règle s'applique aussi avec inline-block lire http://www.brunildo.org/test/inline-block.html

Écrire vertical-align:top dans votre inline-block DIV.

Cochez cette http://jsfiddle.net/WGCyu/1/

296
répondu sandeep 2013-07-10 06:18:17

il suffit d'utiliser vertical-align:top;

Démo

28
répondu Elyor 2015-07-10 09:42:07

Vue ce autre exemple. La raison de ce comportement est décrite dans module CSS3: ligne: 3.2. Zone de ligne d'emballage [1] :

en général, le bord de départ d'une boîte de ligne touche le bord de départ de son bloc contenant et le bord d'extrémité touche le bord d'extrémité de son bloc contenant. Toutefois, les boîtes flottantes peuvent se trouver entre le bord du bloc contenant et le bord de la boîte linéaire. Ainsi, bien que la ligne de les boîtes dans le même contexte de formatage en ligne ont généralement la même avance de progression en ligne (celle du bloc contenant), elles peuvent varier si disponible l'espace de progression en ligne est réduite en raison de flotteurs[...]

comme vous pouvez le voir, le troisième élément est poussé vers le bas, bien qu'il n'ait pas de propriété overflow . La raison doit être quelque part d'autre à trouver. Le second comportement que vous remarquez est décrit dans feuilles de Style en Cascade Niveau 2 Révision 1 (CSS 2.1) Spécification: 9.5 flotteurs [2] :

étant donné qu'un flotteur n'est pas dans le flotteur, des boîtiers Non positionnés créés avant et après le flotteur coulent verticalement comme si le flotteur n'existait pas. Toutefois, les boîtes de lignes actuelles et subséquentes créées à côté du flotteur sont raccourcies au besoin pour laisser place à la boîte de marge du flotteur.

toutes vos display:inline-block; divs utilisent un type de baseline dans ce cas 10.8 calcul de la hauteur de la ligne: les propriétés' line-height 'et' vertical-align ' (très fin) [3] :

la ligne de base d'un "bloc en ligne" est la ligne de base de sa dernière boîte dans le flux normal, sauf s'il n'y a pas de boîtes dans le flux ou si sa propriété "overflow" a une valeur calculée autre que "visible", auquel cas la ligne de base est le bord inférieur de la marge.

Ainsi, lorsque vous utilisez des éléments flottants et des éléments inline-block , l'élément flottant sera poussé sur le côté et le formatage en ligne sera recalculé selon 1 . D'un autre côté, les éléments suivants sont raccourcis s'ils ne conviennent pas. Puisque vous travaillez déjà avec un minimum d'espace, il n'y a pas d'autre moyen de modifier vos éléments que de les pousser 2 . Dans ce cas, l'élément le plus élevé définira la taille de votre div d'emballage, définissant ainsi baseline 3 , en revanche, la modification de la position et de la largeur indiquée dans 2 ne peut pas être appliquée à ces éléments de hauteur maximale espacés. Dans ce cas, un comportement que dans ma toute première démo du résultat.

enfin, la raison pour laquelle votre overflow:hidden empêchera #firstDiv d'être poussé au bord inférieur de votre #container , bien que je n'ai pas pu trouver une raison en section 11 . Sans overflow:hidden il fonctionne comme excepté et défini par 2 et 3 . Démo

TL;DR: Ont un regard très attentif sur le W3 recommandations et la mise en œuvre dans le navigateur. À mon humble avis, les éléments flottants sont décidés à montrer un comportement inattendu si vous ne connaissez pas tous les changements qu'ils font à votre environnement élément. Voici un autre Démo qui montre un problème commun avec les flotteurs.

8
répondu Zeta 2012-02-14 08:01:51

j'ai d'abord commencé à répondre à cette question , mais elle était verrouillée comme dupe avant que je puisse terminer, donc je poste la réponse ici à la place.

tout d'abord, nous devons comprendre ce qu'est inline-block .

La définition dans MDN dit:

l'élément génère une boîte d'éléments de bloc qui sera débitée avec environnant contenu comme s'il s'agissait d'une seule boîte en ligne (se comporter beaucoup comme un élément remplacé voudrait)

pour comprendre ce qui se passe ici, nous devons regarder vertical-align , et c'est la valeur par défaut baseline .

vertical position visualizations

Dans cette illustration vous avez cette carte de couleur:

Bleu: la ligne de base

Rouge: le haut et Le bas de la ligne-hauteur

Vert: le haut et le bas de la boîte de contenu en ligne.

dans l'élément #left, vous avez du contenu textuel qui contrôle Quelle est la ligne de base. Cela signifie que le texte à l'intérieur définit la ligne de base pour la #gauche.

Dans le #droit, il n'y a pas de contenu, de sorte que le navigateur n'a pas d'autre choix que d'utiliser le fond de la boîte comme référence.

Se cette visualisation où I ont dessiné la ligne de base sur un exemple où le premier conteneur inline a du texte, et le suivant est vide:

Baseline drawn

Si vous alignez un élément vers le haut, vous dire que vous alignez le haut de cet élément vers le haut de la boîte de ligne.

Cela pourrait être plus facile à comprendre par un exemple.

div {
    display: inline-block;
    width: 100px;
    height: 150px;
    background: gray;
    vertical-align: baseline;
}
div#middle {
    vertical-align: top;
    height: 50px
}
   
div#right {
    font-size: 30px;
    height: 100px
}
<div id="left">
  <span>groovy</span>
</div>
<div id="middle">groovy</div>

<div id="right">groovy</div>

le résultat est celui - ci-et j'ai ajouté la ligne de base bleue, et la boîte rouge: Explained vertical-align

Ce qui se passe ici, c'est que la hauteur de la boîte de ligne dépend de la façon dont le contenu de la ligne entière est disposé. Cela signifie que pour calculer l'alignement supérieur, les alignements de base doivent être calculés en premier. L'élément #middle a vertical-align:top , il n'est donc pas utilisé pour le positionnement de base. mais les #left et #right sont positionnés verticalement de sorte que leurs lignes de base sont alignées. Lorsque cela est fait, la hauteur de la boîte de ligne a augmenté, parce que l'élément #right a été poussé un peu plus haut en raison de la taille de police plus grande. Ensuite, la position supérieure de l'élément #middle peut être calculée, et c'est le long de la boîte du haut de la ligne.

2
répondu awe 2018-08-15 11:25:10

le problème, c'est parce que vous avez appliqué float:left sur le deuxième div. ce qui fait que la deuxième div vient sur le côté gauche et votre première div tombe et vient après votre deuxième div. Si vous appliquez float: gauche sur la première div aussi, votre problème sera disparu.

overflow: hidden ne cause aucun problème à votre mise en page, overflow:hidden affecte uniquement les éléments internes d'un div, il n'a rien à voir avec les autres éléments qui sont à l'extérieur.

1
répondu Pal Singh 2012-02-14 07:27:03

essayez d'ajouter padding:0; au corps et d'enlever la marge de vos divs.

ajouter background-color:*any couleur de fond * pour vérifier la différence.

0
répondu LOLZ 2017-09-19 16:41:53

essayez de rendre toutes les propriétés CSS de tous les éléments identiques.

j'ai eu un problème similaire et en corrigeant cela j'ai identifié que je laissais tomber un élément avec la propriété Font dans L'élément Div.

après avoir laissé tomber cet élément avec la propriété Font, L'alignement de all DIV a été perturbé. Pour corriger cela, je mets la propriété Font à tous les éléments DIV de la même façon que l'élément qui est tombé dans elle.

Dans l'exemple suivant, la Élément de la classe ".dldCuboidButton " défini avec font-size:30 px.

donc j'ai ajouté la même propriété aux classes restantes i.e. .cuboidRecycle,.liCollect,.dldCollect qui sont utilisés par les éléments DIV. De cette façon, tous les éléments DIV suivent les mêmes mesures avant et après y avoir introduit l'élément.

.cuboidRecycle {
    height:40px; 
    width:'20px; float:right';
    overflow:'none';
    background-color:#cab287;
    color:#ffffff; 
    border-radius:8px; 
    text-align:'center'; 
    vertical-align:'top';
    display: inline-block;
    font-size: 30px; /* Set a font-size */
}


.liCollect {
    height:40px; 
    width:'20px; float:right';
    overflow:'none';
    background-color:#cab287;
    color:#ffffff; 
    border-radius:8px; 
    text-align:'center'; 
    vertical-align:'top';
    display: inline-block;
    font-size: 30px; /* Set a font-size */
}

.dldCollect {
    height:40px; 
    width:'20px; float:right';
    overflow:'none';
    background-color:#009933;
    color:#ffffff; 
    border-radius:8px; 
    text-align:'center'; 
    vertical-align:'top';
    display: inline-block;
    font-size: 30px; /* Set a font-size */
}


.dldCuboidButton {
    background-color:  #7c6436;
    color: white; /* White text */
    font-size: 30px; /* Set a font-size */
    border-radius: 8px;
    margin-top: 1px;
  }

Voici l'exemple de HTML créé dynamiquement en utilisant CSS ci-dessus.

$("div#tabs").append(
  "<div id='" + newTabId + "'>#" + uniqueId + 
  "<input type=hidden id=hdn_tmsource_" + uniqueId + "  value='" + divTmpfest + "'>" + 
  "<input type=hidden id=leCuboidInfo_" + uniqueId + " value=''>" + 
  "<div id='" + divRecycleCuboid + "' class=cuboidRecycle ondrop='removeDraggedCuboids(event, ui)'  ondragover='allowDrop(event)'><font size='1' color='red'> Trash bin </font></div>" +
  "<div id='" + divDropLeCuboid  + "' class=liCollect ondrop='dropForLinkExport(event)'  ondragover='allowDrop(event)'><font size='1' color='red'>Drop Template Manifest Cuboid here</font></div>" +
  "<div id='" + divDropDwldCuboid  + "' class=dldCollect ondrop='dropForTMEntry(event)'  ondragover='allowDrop(event)'><font size='1' color='red'>Drop Template Cuboids here..</font></div>" +
  "</div>" 
);
0
répondu Rahul Varadkar 2018-03-04 13:57:24