2010-04-21 12 views
105

Ho un header div come il primo elemento nel mio div wrapper, ma quando aggiungo un margine superiore a un h1 all'interno dell'head div divinge l'intero header div verso il basso. Mi rendo conto che ciò accade ogni volta che applico un margine superiore al primo elemento visibile su una pagina.Margin-Top push esterno div down

Ecco uno snippet di codice di esempio. Grazie!

div#header{ 
 
\t width: 100%; 
 
\t background-color: #eee; 
 
\t position: relative; 
 
} 
 

 
div#header h1{ 
 
\t text-align: center; 
 
\t width: 375px; 
 
\t height: 50px; 
 
\t margin: 50px auto; 
 
\t font-size: 220%; 
 
\t background: url('../../images/name_logo.png') no-repeat; 
 
}
<div id="header"> 
 
\t <h1>Title</h1> 
 
\t <ul id="navbar"></ul> 
 
</div>

risposta

159

messo overflow:auto nel genitore div
see more in this link

+26

'overflow: hidden' è migliore per il 90% dei casi. – vsync

+1

Perché esagerare: nascosto essere migliore? – peterchon

+5

@peterchon - perché auto può causare overflow scrollbars – vsync

27

Non ho una spiegazione solida sul motivo per cui questo accade, ma ho riparato questo cambiando la top-margin-top-padding, o l'aggiunta di display: inline-block allo stile elemento.

EDIT: Questa è la mia teoria

Ho la sensazione che abbia qualcosa a che fare con il modo in margini sono crollati (combinato).

da W3C Collapsing Margins:

In questa descrizione, l'espressione margini collasso significa che margini adiacenti (nessun non vuoti aree contenuto, cuscinetto o di frontiera o pallone li separano) di due o più i riquadri (che possono essere accanto a uno un altro o nidificati) si combinano per formare un margine singolo .

La mia teoria è che, poiché il vostro primo elemento è accanto al corpo i due margini si combinano e vengono applicati al corpo: questo costringe il contenuto del corpo per iniziare al di sotto del margine applicato è crollato nel rispetto della box model.

ci sono situazioni in cui i margini non collassano che potrebbe valere la pena di giocare con (da Collapsing Margins):

* floated elements 
* absolutely positioned elements 
* inline-block elements 
* elements with overflow set to anything other than visible (They do not collapse margins with their children.) 
* cleared elements (They do not collapse their top margins with their parent block’s bottom margin.) 
* the root element 
+3

Inoltre, il riempimento o il bordo sull'elemento con margine collassato (quello interno) lo annullerà. – Anonymous

+0

@Anonimo: grazie! Tutte le soluzioni sopra menzionate erano inaccettabili o non funzionanti per me. – mik01aj

+0

Questo ha funzionato per me: avevo elementi assoluti (un menu a discesa) nel mio contenitore, quindi overflow: l'auto non funzionava. – mwilcox

13

Questo sono alcune delle modi per evitare il collasso dei margini tra elementi padre-figlio. Utilizzare quello che si adatta meglio con il resto del tuo stile:

  • Set display ad altri che block.
  • Impostare float su un valore diverso da none.
  • Rimuovere il margine e utilizzare invece padding. Ad esempio se si dispone di margin-top: 10px, sostituire con padding-top: 10px;.
  • Rimuovere il margine, e utilizzare invece position (absolute o relative) con gli attributi top, bottom, ecc Per esempio, se si ha margin-top: 10px, sostituirlo con position: relative; top: 10px;.
  • Aggiungi un padding o un border nel lato in cui i margini stanno crollando, all'elemento genitore. Il bordo può essere 1px e trasparente.
  • Impostare overflow su un valore diverso da visible sull'elemento genitore.
0

Correte oggi in questo numero.

overflow: hidden non ha funzionato come previsto quando ho avuto più elementi seguiti.

Così ho provato a cambiare la proprietà di visualizzazione del div genitore e display: flex funzionato !!!

Spero che questo possa aiutare qualcuno. :)

0

L'aggiunta di un po 'di padding all'elemento superiore principale può risolvere questo problema.

.parent{ 
 
    padding-top: 0.01em; 
 
}

Questo è utile se avete bisogno di un elemento all'interno del genitore per essere visibile all'esterno l'elemento padre, come se si sta creando un effetto di sovrapposizione.

2

display: flex funzionerà in questo caso. Fornisci l'elemento parent display: flex; e poi dai margine secondo il tuo requisito al tag h1.

0

So che questo è un vecchio problema, l'ho incontrato molte volte. Il problema è che tutte le correzioni qui sono hack che potrebbero avere conseguenze non intenzionali.

Prima di tutto, c'è una spiegazione semplice per il problema di root. A causa del modo in cui funziona il collasso dei margini, se il primo elemento all'interno di un contenitore ha un margine superiore, tale margine superiore viene effettivamente applicato al contenitore principale stesso. È possibile verificare ciò da soli effettuando quanto segue:

<div> 
    <h1>Test</h1> 
</div> 

In un debugger, aprire questo e passare il div. Noterai che il div stesso è posizionato in realtà dove il margine superiore dell'elemento H1 si ferma. Questo comportamento è inteso dal browser.

Quindi c'è una soluzione semplice a questo senza dover ricorrere a strani hack, come la maggior parte dei post qui (senza insulti destinati, è solo la verità) - semplicemente tornare alla spiegazione originale - ...if the first element inside a container has a top margin... - In seguito, avresti quindi bisogno del primo elemento in un contenitore per NON avere un margine superiore. Ok, ma come si fa senza aggiungere elementi che non interferiscano semanticamente con il tuo documento?

Facile! Gli pseudo-elementi! Puoi farlo attraverso una lezione o un mixin predefinito.Aggiungi un :before pseudo-elemento:

CSS tramite una classe:

.top-margin-fix:before { 
    content: ' '; 
    display: block; 
    width: 100%; 
    height: .0000001em; 
} 

Con questo, seguendo l'esempio di marcatura sopra si dovrebbe modificare la div come tale:

<div class="top-margin-fix"> 
    <h1>Test</h1> 
</div> 

Perché funziona?

Il primo elemento in un contenitore, se non ha margine superiore, imposta la posizione dell'inizio del margine superiore dell'elemento successivo. Aggiungendo uno pseudo-elemento :before, il browser aggiunge effettivamente un elemento non semantico (in altre parole, buono per SEO) nel contenitore genitore prima del il tuo primo elemento.

Q. Perché l'altezza: .0000001em?

A. È necessaria un'altezza per il browser per spingere verso il basso l'elemento margine. Questa altezza è effettivamente zero, ma ti permetterà comunque di aggiungere padding al contenitore genitore stesso. Poiché è effettivamente zero, non avrà alcun effetto sul layout del contenitore. Bellissimo.

Ora puoi aggiungere una classe (o meglio, in SASS/LESS, un mixin!) Per risolvere questo problema invece di aggiungere strani stili di visualizzazione che causeranno conseguenze inattese quando vuoi fare altre cose con i tuoi elementi, volutamente eliminare i margini sugli elementi e/o sostituirli con padding, o strani stili di posizione/float che non sono pensati per risolvere questo problema.

Problemi correlati