web-dev-qa-db-fra.com

Rembourrage-bas / haut dans flexbox layout

J'ai une mise en page flexbox contenant deux éléments. L'un d'eux utilise padding-bottom :

#flexBox {
  border: 1px solid red;
  width: 50%;
  margin: 0 auto;
  padding: 1em;
  display: flex;
  flex-direction: column;
}
#text {
  border: 1px solid green;
  padding: .5em;
}
#padding {
  margin: 1em 0;
  border: 1px solid blue;
  padding-bottom: 56.25%; /* intrinsic aspect ratio */
  height: 0;
}
<div id='flexBox'>
  <div id='padding'></div>
  <div id='text'>Some text</div>
</div>

L'élément bleu conserve son rapport d'aspect en fonction de sa largeur lorsque la page est redimensionnée. Ceci fonctionne avec Chrome et IE et ressemble à:

padding-bottom in chrome and IE on flexbox layout

Cependant, dans Firefox et Edge , je reçois ce qui suit (c'est ignorer le rembourrage sur la boîte bleue, qui maintient le rapport hauteur/largeur):

padding-bottom in Firefox on flexbox layout

Je suis trop nouveau pour flexbox pour vraiment comprendre si cela devrait ou non fonctionner. L'intérêt de flexbox est de redimensionner les choses, mais je ' Je ne sais pas pourquoi il ignore le remplissage intrinsèque et met des tailles absolues sur l’élément bleu.

Je suppose que finalement je ne suis même pas sûr si Firefox ou Chrome fait la bonne chose! Un expert de Firefox flexbox) peut-il aider?)?

73
Simon_Weaver

Mise à jour de février 2018

Firefox et Edge ont convenu de modifier leur comportement pour les éléments flex (et grid) du haut, de la marge inférieure et du remplissage:

[...] par exemple. Les pourcentages gauche/droite/haut/bas sont tous résolus par rapport à la largeur de leur bloc conteneur en mode d’écriture horizontale. [ source ]

Ceci n'est pas encore implémenté (testé sur FF 58.0.2).

Mise à jour avril 2016

( toujours valable en mai 2017 )

Les spécifications ont été mis à jour à:

Le pourcentage de marges et de rembourrages sur les articles flexibles peut être résolu en utilisant:

  • leur propre axe (pourcentages gauche/droite résolus par rapport à la largeur, résolus haut/bas par rapport à la hauteur), ou
  • l'axe en ligne (les pourcentages gauche/droite/haut/bas sont tous résolus par rapport à la largeur)

source: module 1 de CSS Flexible Box Layout Module

Cela signifie que chrome IE FF et Edge (même s'ils n'ont pas le même comportement)) respectent les recommandations de la spécification.

Les spécifications disent aussi:

Les auteurs doivent éviter d'utiliser des pourcentages dans les marges ou les marges des éléments flexibles, car ils auront un comportement différent selon les navigateurs. [ source ]


Solution de contournement :

Vous pouvez envelopper le premier enfant du conteneur Flex dans un autre élément et placer le padding-bottom sur le deuxième enfant:

#flexBox {
  border: 1px solid red;
  width: 50%;
  margin: 0 auto;
  padding: 1em;
  display: flex;
  flex-direction: column;
}
#text {
  border: 1px solid green;
  padding: .5em;
}
#padding {
  margin: 1em 0;
  border: 1px solid blue;
}
#padding > div {
  padding-bottom: 56.25%; /* intrinsic aspect ratio */
}
<div id='flexBox'>
  <div id='padding'><div></div></div>
  <div id='text'>Some text</div>
</div>

J'ai testé cela dans les navigateurs modernes (IE, Chrome, FF et Edge) et ils ont tous le même comportement. Comme la configuration du deuxième enfant est "la même chose que d'habitude", je suppose que les navigateurs plus anciens (également support flexbox) ) afficheront la même présentation.


Réponse précédente:

Selon le specs , Firefox a le bon comportement

Explanantion:

Contrairement aux éléments de bloc qui calculent leur% de marge/remplissage en fonction de la largeur du conteneur, les éléments flexibles:

Les marges et les marges de pourcentage sur les articles flexibles sont toujours résolues par rapport à leurs dimensions respectives; contrairement aux blocs, ils ne résolvent pas toujours la dimension en ligne de leur bloc conteneur.

source dev.w3.org

Cela signifie que padding-bottom/top et margin-bottom/top sont calculés en fonction de la hauteur du conteneur et non de la largeur comme dans une non-flexbox mises en page.

Comme vous n'avez spécifié aucune hauteur pour l'élément flex parent, le remplissage inférieur de l'enfant est censé être de 0px.
Voici un violon avec une hauteur fixe sur le parent qui montre que le remplissage du bas est calculé en fonction de la hauteur du display:flex; récipient.


100
web-tiki

La réponse acceptée est correcte, mais j'ai amélioré la solution en utilisant un pseudo-élément au lieu d'ajouter un nouvel élément au code HTML.

Exemple: http://jsfiddle.net/4q5c4ept/

HTML:

<div id='mainFlexbox'>
  <div id='videoPlaceholder'>
    <iframe id='catsVideo' src="//www.youtube.com/embed/tntOCGkgt98?showinfo=0" frameborder="0" allowfullscreen></iframe>
  </div>
  <div id='pnlText'>That's cool! This text is underneath the video in the HTML but above the video because of 'column-reverse' flex-direction.    </div>
</div>

CSS:

#mainFlexbox {
  border: 1px solid red;
  width: 50%;
  margin: 0 auto;
  padding: 1em;
  display: flex;
  flex-direction: column-reverse;
}
#pnlText {
  border: 1px solid green;
  padding: .5em;
}
#videoPlaceholder {
  position: relative;
  margin: 1em 0;
  border: 1px solid blue;
}
#videoPlaceholder::after {
  content: '';
  display: block;
  /* intrinsic aspect ratio */
  padding-bottom: 56.25%;
  height: 0;
}
#catsVideo {
  position: absolute;
  top: 0;
  left: 0;
  width: 100%;
  height: 100%;
}
34
OrganicPanda