If you have come across the problem when you apply margins to some element, it doesn't work? If the answer is yes, then you have already encountered the problem of margin collapsing. We can't call it a problem, it's the behavior of margin property to collapse when two margins in the same or different direction collapse.
What is margin collapsing?
When we apply top or bottom margins to multiple elements their margins sometimes get combined into a single margin. This behavior is called margin collapsing. There are certain rules to understand and use margins properly. If not used properly, margin collapsing can give you unexpected results.
When does margin collapsing happen?
There are three cases to consider before creating a structure that collapses.
Case 1. When children are adjacent siblings:
Only margins of adjacent siblings collapse. This means, If we have two elements with top and bottom margin, the Bottom margin of the first element will collapse with a top margin of the second element. This will happen for all the adjacent elements except the first and last elements.
In the below example, grab planks with the mouse or move sliders to add vertical margins to the plank. Observer the borders of the parent. Rotate the planks to reveal the overlapping margins. margins of the first and last element go outside the parent bounds. This shows margins will work outside its parent.
Case 2. When there is no content separating parent and descendants:
Margin is the most outer border of the DOM element. When there is no border or padding defined, margin-top or margin-bottom of parents descendants will collapse. The collapsed margin ends up outside the parent. If there is an element that creates BFC, the margins won't collapse, instead, they will add up. The elements which creates BFC are border,padding,height,min-height,max-height or any inline content. Margins of floated element and absolutely positioned element never collapse.
In this example below, There is one <hr/> after the second plank. This breaks the margin collapsing of the second and last plank. Observe a small line between those planks. Rotating planks will reveal the backside which shows non-overlapping elements due to this <hr/> block.
Case 3. When an element is empty:
When an element is empty, there is the point of showing only margins between them. So when using empty elements, when there is no physical separation between the top edge and bottom edge, the element will act as it isn't even there. If the empty element has anything that separates the top and bottom edges like padding or border, the element will have some height and its margins will collapse with their adjacent siblings.
In the below example, there's an empty element shown with a red outline. Since it's empty, it doesn't affect the margins of its adjacent elements. By clicking checkbox, min-height:1px is added to the empty element. Observe the margins from the backside. When the checkbox is off, the element's margins behave like there is no element. When checked, because of a separation between the element's top and bottom edge, margins appear.
Collapsing Rules:
1. Elements Collapse Margins Only In Vertical Direction:
As shown in the below example, paragraphs 1 to 7 have top and bottom margins set to 30px.
p{margin:30px;}
So when there are two adjacent siblings having margins, their margins overlap each other - known as collapsing. The element itself is indicated in rainbow colors. If you hover over elements, you'll see margins on the element collapses with its top and bottom element's margins.
2. Horizontal Margin Collapsing Does Not Happen:
Collapsing happens only on the top and bottom edge of the box model or sibling elements. The rule of thumb here is even we have margins on the left and right sides of the element, They won't only on flow layouts, layout modes that create BFC will always display the element as a block so they can't be placed side by side. Display modes like inline-block or inline-flex will stop margin collapsing.
p{margin:20px;}
You can see in the below paragraph, there are 2 small inline elements with horizontal margins. the margins in the horizontal direction add up instead of collapsing making in 40px space in-between inline paragraphs.
3.Elements That Are Adjacent Will Collapse Margins:
Elements with no separator in between will collapse. A separator could be any self-closing element like <br/> or <hr/>, which creates a dom element in-between. It will break the collapsing behavior of the adjacent element. Any container tags will follow the first 3 cases and behave as per their defined properties.
p{margin:30px;}
hr {
margin: 0;
padding: 0;
height: 1px;
background: #000;
position: relative;
}
We're using paragraphs with margin:30px in the example. The first two paragraphs have collapsed between the bottom and top margins. <hr/> element breaks the collapsing so the bottom margin of the second paragraph and top margin of the third paragraph does not collapse.
4. Bigger Margin Value Will Win Over Smaller Ones:
When two or more margins collapse in one direction, The margin with a bigger value will be the collapsed value.
For example below, each section has a margin of 20px. The heading element has a margin-top value of 70px.
section {
margin: 20px auto;
}
h3 {
margin: 70px auto 0px auto;
}
So margin-top of heading and section will collide, margin-top of heading wins. Overall the sections to understand how to section's margin and margins of the section with heading collapses. Hover on the sections to see collapsed margins.
5. Margin Collapsing Will Happen Even On Nested Elements:
In the same example above, we're using the nesting of elements inside sections. Sections have some margin, the child inside parent has some margin, so the total margin still is the maximum of all collapsed margin among their nested child. Nesting does not prevent collapsing rules from applying to adjacent elements. The collapsing happens even outside the parent container element without box-model properties. Over on the section to see margin extending outside of the section element.
section {
margin: 20px auto;
}
section h3 {
margin: 70px auto 0px auto;
}
6.Direction Of The Margins Decides Final Margins:
In the example below, we can have multiple margins in the same direction. Here, margin-top is collapsing both on section, div, and heading in the top direction. All three elements have different margins collapsing in the same direction.
section {
margin: 20px auto;
}
section > div{
margin: 40px 0 0 0;
}
section div h3 {
margin: 70px auto 0px auto;
}
So the final margin will be in the top direction which is the biggest one - Heading that is.
7.Margins Collapsing Can Happen on Group Of Elements:
In the same example above, another thing to notice is we are using nested children and nested margins. More than two margins can collapse if they fall in any of the three cases defined earlier.
section {
margin: 20px auto;
}
section > div{
margin: 40px 0 0 0;
}
section div h3 {
margin: 70px auto 0px auto;
}
8.Negative Margins Overlaps:
Unlike positive margins, negative margins will create overlays of adjacent elements on top of each other. When we use negative margins, the Element defined last in the source code will hide its underlying element because of the natural stacking context. Negative margins follow the same rules as normal margins defined in points 1-7.
9.Multiple Positive and Negative Margins Cancels Margins:
When multiple positive and negative margins collapse, there's simple math. Add winners of each to get the resultant margin. Real-life cases of this type will create chaos as there could be layers of positive and negative margins collapsing with each other canceling out values of other margins.
For example, If we are using a nested structure with both positive and negative margins, the Final result may or may not be what is expected. There is no demo because I don't encourage using negative and positive margins together.
10.Collapsing Happens On Flow Layout Only:
Margin collapsing will occur for the layouts using the flow model. Anything that creates a new BFC will move elements out of flow and margins of such eminent won't collapse. Floats, Inline-blocks, absolute position, flex, or grid will stop margin collapsing.
Final words:
You have come across the entire article, it's a good thing. If you have read all the rules, you know how to use margins in your layouts. The easiest way is to use margins in only one direction so there are no two-directional or negative collapsing. Having knowledge of margin collapsing and why it happens, you can solve many common problems in the layout, in probability avoids making those mistakes.