Tengo un div de encabezado como primer elemento en mi div de contenedor, pero cuando agrego un margen superior a un h1 dentro del div de encabezado, empuja hacia abajo todo el div de encabezado. Me doy cuenta de que esto sucede cada vez que aplico un margen superior al primer elemento visible en una página.
Aquí hay un fragmento de código de muestra. ¡Gracias!
div#header{
width: 100%;
background-color: #eee;
position: relative;
}
div#header h1{
text-align: center;
width: 375px;
height: 50px;
margin: 50px auto;
font-size: 220%;
background: url('../../images/name_logo.png') no-repeat;
}
<div id="header">
<h1>Title</h1>
<ul id="navbar"></ul>
</div>
overflow:hidden
es mejor para el 90% de los casos.overflow: hidden
ooverflow: auto
puede causar efectos secundarios no deseados, algunos de los cuales puede que no vea a primera vista. Descubrí que cambiarmargin
apadding
hace el truco, como sugiere la respuesta a continuación. Sin embargo, todavía no entiendo por qué ocurre todo el problema.No tengo una explicación sólida de por qué sucede esto, pero lo arreglé cambiando el
top-margin
atop-padding
o agregandodisplay: inline-block
al estilo del elemento.EDITAR: Esta es mi teoría
Tengo la sensación de que tiene algo que ver con cómo se colapsan (combinan) los márgenes.
de los márgenes de colapso del W3C :
Mi teoría es que dado que su primer elemento está al lado del cuerpo, los dos márgenes se combinan y se aplican al cuerpo: esto obliga al contenido del cuerpo a comenzar por debajo del margen colapsado aplicado de acuerdo con el modelo de caja .
Hay situaciones en las que los márgenes no colapsan con los que podría valer la pena jugar (desde Márgenes contraídos ):
fuente
Estas son algunas de las formas de evitar el colapso del margen entre los elementos padre-hijo. Use el que mejor se adapte al resto de su estilo:
display
en otro queblock
.float
en otro quenone
.padding
. Por ejemplo, si tuvieramargin-top: 10px
, reemplace conpadding-top: 10px;
.position
(absolute
orelative
) con los atributostop
,bottom
etc. Por ejemplo, si tienemargin-top: 10px
, reemplazar conposition: relative; top: 10px;
.padding
o aborder
en el lado donde se contraen los márgenes, al elemento padre . El borde puede ser 1px y transparente.overflow
en otro que no seavisible
el elemento padre .fuente
Sé que este es un problema antiguo, lo he encontrado muchas veces. El problema es que todas las soluciones aquí son hacks que podrían tener consecuencias no deseadas.
En primer lugar, hay una explicación fácil para el problema raíz. Debido a la forma en que funciona el colapso del margen, si el primer elemento dentro de un contenedor tiene un margen superior, ese margen superior se aplica efectivamente al contenedor principal. Puede probar esto por su cuenta haciendo lo siguiente:
En un depurador, abra esto y desplace el div. Notarás que el div en sí se coloca donde se detiene el margen superior del elemento H1 . Este comportamiento está previsto por el navegador.
Entonces, hay una solución fácil para esto sin tener que recurrir a hacks extraños, como lo hacen la mayoría de las publicaciones aquí (sin insultos, es solo la verdad) - simplemente regrese a la explicación original -
...if the first element inside a container has a top margin...
- Después de eso, necesitaría El primer elemento en un contenedor que NO tiene un margen superior. De acuerdo, pero ¿cómo lo haces sin agregar elementos que no interfieran semánticamente con tu documento?¡Fácil! Pseudo-elementos! Puede hacerlo a través de una clase o un mixin predefinido. Añadir un
:before
pseudo-elemento:CSS a través de una clase:
Con esto, siguiendo el ejemplo de marcado anterior, modificaría su div como tal:
¿Por qué funciona esto?
El primer elemento en un contenedor, si no tiene margen superior, establece la posición del inicio del margen superior del siguiente elemento. Al agregar un
:before
pseudo-elemento, el navegador agrega un elemento no semántico (en otras palabras, bueno para SEO) en el contenedor principal antes de su primer elemento.P. ¿Por qué la altura: .0000001em?
A. Se requiere una altura para que el navegador empuje el elemento de margen hacia abajo. Esta altura es efectivamente cero, pero aún le permitirá agregar relleno al contenedor principal. Como es efectivamente cero, tampoco tendrá un efecto en el diseño del contenedor. Hermoso.
Ahora puede agregar una clase (¡o mejor, en SASS / LESS, un mixin!) Para solucionar este problema en lugar de agregar estilos de visualización extraños que causarán consecuencias inesperadas cuando desee hacer otras cosas con sus elementos, eliminando deliberadamente los márgenes en los elementos y / o reemplazarlo con relleno, o estilos extraños de posición / flotación que realmente no están destinados a resolver este problema.
fuente
display: flex
Funcionará en este caso. Proporcione el elemento principaldisplay: flex;
y luego otorgue margen según su requisito para lah1
etiqueta.fuente
Se encuentra con este problema hoy.
overflow: hidden
no funcionó como se esperaba cuando me siguieron más elementos.¡Así que intenté cambiar la propiedad de visualización del div padre y
display: flex
funcioné!Espero que esto pueda ayudar a alguien. :)
fuente
Agregar un poco de relleno al elemento principal superior puede solucionar este problema.
Esto es útil si necesita que un elemento dentro del elemento primario sea visible fuera del elemento primario, como si está creando un efecto superpuesto.
fuente
Esto sucede debido al colapso del margen. Cuando el elemento hijo toca el límite del elemento padre y cualquiera de ellos se aplica con márgenes, entonces:
El margen que sea más grande ganará (aplicado).
si alguno de ellos tiene margen, ambos compartirán lo mismo.
Soluciones
fuente