Tuesday, February 16, 2010

The Margin Properties

The margin is a blank area between elements in which only the background color or image of the parent element (or the nearest ancestor element that has a background color or image) is visible.

The margin property can take up to four length or percentage values, the keyword auto repeated up to four times or the keyword inherit once. Multiple values are separated by spaces.

Example 1: margin:4px 8em auto 10px;

Example 2: margin:inherit;

When a margin declaration has one value, all the four margins — top, right, bottom and left, are set to that value.

When a margin declaration has four values, the first value refers to the top margin, the second refers to the right margin, the third refers to the bottom margin and the fourth refers to the left margin.

When a margin declaration has two values, the first value refers to the top and bottom margins and the second value refers to the right and left margins.

When a margin declaration has three values, the first value refers to the top margin, the second value refers to the right and left margins, and the third value refers to the bottom margin.

Percentage values refer to the width of the containing block element. margin is not an inherited property. It does not have an initial value. The default margins of an element depends on browsers' internal stylesheets.

Margin sizes can also be specified individually using the margin-top, margin-right, margin-bottom and margin-left properties.

Note: Margins of the html element have the same background color or image as the html element. Firefox 3.5, Internet Explorer 7 and Internet Explorer 8 do not render the bottom margin of the the html element. Internet Explorer 6 does not render the borders and margins of the html element correctly. Internet Explorer 7 renders all margins of the html element as solid margins.

margin with px values

In block-level element that does not have padding or borders, having a block-level child element, the height of the parent element will be just enough to contain the borders, padding and content area of the child element. Therefore, the top and bottom margins of the child element will spill out of the parent's content area. This happens because the margin of the child element is in contact with the margin of the parent element. Therefore, the two margins collapse.
However, if the child element's top or bottom margin has the parent element's padding or border adjacent to it, then the margin will be within the content area of the containing block. This is because the two margins are separated by the padding or border.

Example 3: <div style="margin:0;padding:0"><p style="font-size:35px;font-family:'Times New Roman';margin:20px;padding:0">the quick brown fox jumps over the lazy dog. the five boxing wizards jump quickly</p></div>

In the above example, the top and bottom margins of the <p> are outside the content area div. If the div had top and bottom margins, then the top and bottom margins of the <p> would collapse with the top and bottom margins of the div.

Example 4: <div style="margin:0;padding:0;border-style:solid;border-width:1px"><p style="font-size:35px;font-family:'Times New Roman';margin:20px;padding:0">the quick brown fox jumps over the lazy dog. the five boxing wizards jump quickly</p></div>

Since the div has a border, the top and bottom margins are within the content area of the div.

Example 5: <div style="margin:0;padding:1px"><p style="font-size:35px;font-family:'Times New Roman';margin:20px;padding:0">the quick brown fox jumps over the lazy dog. the five boxing wizards jump quickly</p></div>

Since the div has a padding, the top and bottom margins are within the content area of the div.

Over-constrained Margins

Margins are said to be over-constrained when there is not enough space for them in the containing block.

Example 6: <div style="height:200px;border-width:10px;border-style:solid"><p style="font-size:35px;font-family:'Times New Roman';height: 200px;margin:20px">the quick brown fox jumps over the lazy dog. the five boxing wizards jump quickly</p></div>

In the above example, there is insufficient space for the top and bottom margins. In this situation, the browser renders the top margin within the containing div, and, the content area of the <p> overflows out of the bottom of the div. The bottom margin of  the <p> has no effect on subsequent content. Subsequent elements are rendered on top of the overflowed parts of the <p>.

Example 7: <div style="width:200px;border-width:10px;border-style:solid"><p style="font-size:35px;font-family:'Times New Roman';width:200px;margin:20px">the quick brown fox jumps over the lazy dog. the five boxing wizards jump quickly</p></div>

In the above example, there is insufficient space for the left and right margins. In this situation, the browser renders the left margin within the containing div, the content area of the <p> and the right margin overflow out of the right of the div.

Left and Right Margins and Viewport Width

Example 8: <body><p style="font-size:35px;font-family:'Times New Roman';width:700px;margin:50px">the quick brown fox jumps over the lazy dog. the five boxing wizards jump quickly</p></body>

In the above example, the width of the left and right margins are 50px each and the width of the content area of the <p> is 700px. Therefore the minimum width of the viewport required to display the <p> and its margins is 800px. No matter what the width of the viewport, the left margin is always rendered. The right margin, however, behaves as if it has been set to auto. Therefore, if the viewport's width is less than 750px, the browser will put a horizontal scroll bar so that both the left margin and the <p>'s content area can be viewed and the content area of the <p> will overflow the content area of its parent; there will be no right margin. If the viewport's width is greater than 750px but less than 800px, then the left margin and content area will have the specified width, and the remaining space will be taken up by the right margin. If the viewport's width is greater than 800px, the right margin's width will be greater than 50px.

Due to various bugs, the above example renders differently in Internet Explorer 6 — like other browsers, the left margin is always 50px, but unlike other browsers, the right margin is always present and has a minimum width of 50px. If the viewport's width is less than 800px, the browser puts a horizontal scroll bar. Also, the width of the body element is automatically increased by the browser so that the margins and content area of the <p> never overflow.

Due to a rendering bug, Internet Explorer 7, like Internet Explorer 6, always renders the left and right margins along with the <p>'s content area. The difference is, it does not automatically increase the width of the containing element. Therefore, when the width of the viewport is less than 800px, the right margin and, if necessary, the content area of the <p> overflow the body element. The right margins is always 50px or more.

Firefox 3, Firefox 3.5 and Internet Explorer 8 render the above example correctly.

Unconstrained Margins

When the sum of the widths of the left and right margins and the width of the content area is less than the width of the content area of the containing block, the right margin expands to take up the extra space available.

When the sum of the heights of the top and bottom margins and the height of the content area is less than the height of the content area of the containing block, the bottom margin expands to take up the extra space available.

Example 9: <div style="width:600px;height:400px;border-width:1px;border-style:solid"><p style="font-size:35px;font-family:'Times New Roman';height:200px;margin:20px">the quick brown fox jumps over the lazy dog. the five boxing wizards jump quickly</p></div>

In the above example, the left and top margins are 20px while the right and bottom margins are 180px.

Vertical Collapsing of Margins

When the top or bottom margins of two elements come into contact with each other, the two margins vertically collapse. Therefore, the resulting margin will be the size of the larger margin. If the two margins are equal, then the margins will collapse to the size of a single margin.

Example 10: <p style="font-size:35px;font-family:'Times New Roman';margin:15px">the quick brown fox jumps over the lazy dog.</p>
<p style="font-size:35px;font-family:'Times New Roman';margin:25px">the quick brown fox jumps over the lazy dog.</p>

Left and right margins never collapse — a left and a right margin that are adjacent to each other remain the same size, therefore the total horizontal distance between the elements will be the sum of the margins.

Example 11: <p style="font-size:35px;font-family:'Times New Roman'">the quick brown fox j<span style="margin:20px">u</span><span style="margin:20px">m</span>ps over the lazy dog</p>

In the above example, the distance between the "u" and the "m" will be 40px.

Example 12: <div style="margin:10px;padding:0;background-color:purple"><p style="font-size:35px;font-family:'Times New Roman';margin:20px;padding:0">the quick brown fox jumps over the lazy dog. the five boxing wizards jump quickly</p></div>

In the above example, the top and bottom margins of the <p> (20px) collapse with the top and bottom margins of the <div>, resulting in a margin of 20px. This is because the top and bottom margins of the <p> are outside the <div> since the <div> has no top and bottom border or padding.

When an element that has no padding or border has a child element that has top or bottom margins, the margins of the child element collapses with the margins of the parent element. However, if there is a border or padding separating two margins, then they do not collapse.

Negative Margins

When a margin declaration has a negative value, and after collapsing the margin with adjacent margins the result is still negative, the content area of the element that the negative margin is applied to will be moved up or the content area of the next element will be moved up, or, the content area of the element will be stretched left or right depending on which margin has the negative value.

Internet Explorer 6 and Internet Explorer 7 do not correctly render negative margins that cause elements to overlap each other or overflow their containing elements. Some of Internet Explorer 7's negative margin bugs can be fixed by triggering hasLayout on the element that has the negative margins.

Negative top and bottom margins

When an element has a negative margin and the adjacent element has a margin that collapses on the negative margin, the resulting margin is the algebraic sum of the two margins.

When an element has a negative top or bottom margin that, after collapsing with adjacent margins (if any) is still negative, the element is moved up (in the case of the top margin) or, the next element's content area is moved up (in the case of the bottom margin).

In Internet Explorer 6, the part of the top or bottom of an element's content area that overflows the boundary of its containing block (which could be the edge of the containing block's content area, the outer edge of the padding or the outer edge of the border), is cut-off or truncated. This bug cannot be fixed by triggering hasLayout.

In Internet Explorer 7, when inside a div, a part of the top or bottom of an element's content area that is next to that element's negative margin is cut-off or truncated. This bug occurs even when the padding of the element's content area does not overflow its containing element. This bug can be fixed by triggering hasLayout on the element that has the negative margin.

Example 13: <p style="font-size:35px;font-family:'Times New Roman';margin-bottom:-10px">the quick brown fox jumps over the lazy dog, the five boxing wizards jump quickly</p> <p style="font-size:35px;font-family:'Times New Roman';margin-left:10px;margin-top:0;">the quick brown fox jumps over the lazy dog, the five boxing wizards jump quickly</p>

In the above example, the first <p> has a negative bottom margin and the <p> after it has a top margin set to 0. Therefore, the content area of the second <p> is moved 10 pixels up. This brings the content area of the second <p> on top of the content area of the first <p>. The background image of the second <p> covers 10 pixels of the background of the first <p>. However, the text of the first <p> is not covered.

Note: Internet Explorer 6, due to a bug, does not render the background image of the second <p> correctly. In Internet Explorer 7, the background image of the second <p> covers the text of the first <p>. This bug cannot be fixed by triggering hasLayout.

Negative left and right margins

When an element has a negative margin and the adjacent element has a margin that collapses on the negative margin, the resulting margin is the algebraic sum of the two margins.

When an element has a negative left or right margin that, after collapsing with adjacent margins (if any) is still negative, the element is extended to the left (in the case of the left margin) or, is extended to the right (in the case of the right margin). The extended portion to the left is outside the viewport cannot be viewed and the extended portion to the right can be viewed by horizontal scrolling.

In Internet Explorer 6, the part of the left or right of an element's content area that overflows the boundary of its containing block (which could be the edge of the containing block's content area, the outer edge of the padding or the outer edge of the border), is cut-off or truncated. This bug cannot be fixed by triggering hasLayout.

In Internet Explorer 7, when inside a div, an element that has a negative right margin will have the portion of the content area that overflows the boundary of the containing element on the right truncated. The boundary of the containing element may be the right edge of the content area, the outer edge of the right padding or the outer edge of the right border. This bug can be fixed by triggering hasLayout on the element that has the negative margin. However, this fix does not work if the containing element does not have padding or borders on the side of the negative margin of the child element.

Example 13: <p style="font-size:35px;font-family:'Times New Roman';margin-right:-50px;margin-left;-50px;padding:0">the quick brown fox jumps over the lazy dog, the five boxing wizards jump quickly</p>

In the above example, since the left margin is -50px, 50px from the beginning of the <p> is cut off because it is supposed to be rendered outside the viewport. Note that the cut off portion cannot be viewed — it is not possible to horizontally scroll to that region. The right margin is -50px, therefore, 50px of the <p> overflows the content area of is the containing element (<body>). If the margin of the containing element is not large enought to contain the overflow, the <p> overflows it. The browser puts a horizontal scroll bar which enables one to scroll to the part of the <p> that is outside the visible part of the viewport.

Note: Internet Explorer 6 always expands the width of the containing element to accomodate the width of a child element. This is a bug. Internet Explorer 7, at certain window widths, renders the above example in the same way as Internet Explorer 6 (incorrectly) but at other widths renders it correctly.

margin Declarations with auto

The keyword auto is useful only when applied to left and right margins. On top and bottom margins, auto results in zero margins. However in Internet Explorer 6 and 7, due to a bug, auto on top and bottom margins do not result in zero margins. Therefore, auto on top and bottom margins must be avoided.

When there is no left and right padding or borders on an element, the sum of the widths of the content area, the left margin, and the right margin will be equal to the width of the content area of the containing block.When left or right margins have the value auto, the browser determines the size of the margin, which will be such that the sum of the left and right margins and the content area is equal to the width of the content area of the containing block.

On an element that has no left and right padding or borders, when the sum of the widths of the content area and the left and right margins does not equal to the sum of the content area of the containing block, the right margin is expanded to fill the available space. However, if the left margin is set to auto, then the left margin expands to fill the available space.

margin-right:auto

On an element whose width is auto, margin-right:auto causes the element's right margin to become zero.

On an element that has its width set to a particular size and left margin set to zero or a particular size, margin-right:auto causes the element's right margin to expand to fill all the available space (after allocation of space to the content area and left margin). This is the default appearance of the right margin whether (when width and left-margin are of a particular size) or not there is a CSS declaration that matches the right margin.

Example 14: <div style="height:400px;width:400px"><p style="font-size:35px;font-family:'Times New Roman';margin-right:auto;width:200px">the quick brown fox jumps over the lazy dog, the five boxing wizards jump quickly</p></div>

margin-left:auto

On an element whose width is auto, margin-left:auto causes the element's left margin to become zero.

On an element that has its width to set a particular size and right margin set to zero or a particular size, margin-left:auto causes the element's right margin to expand to fill all the available space (after allocation of space to the content area and left margin).

Example 15: <p style="font-size:35px;font-family:'Times New Roman';margin-left:auto;width:200px">the quick brown fox jumps over the lazy dog, the five boxing wizards jump quickly</p>

margin-left:auto and margin-right:auto

On an element whose width is auto, if both the left and right margins have the value auto,  the element's left and right margins become zero.

On an element that has its width set to a particular size, having both left and right margins set to auto causes the available space (after allocation of the content area space) to be split equally among the left and right margins. Therefore, the element's content area will be horizontally centered in the containing block's content area.

Example 16: <p style="font-size:35px;font-family:'Times New Roman';margin-left:auto;margin-right:auto;width:200px">the quick brown fox jumps over the lazy dog, the five boxing wizards jump quickly</p>

margin-top:auto and margin-bottom:auto

margin-top:auto and margin-bottom:auto causes the top and bottom margins of element to become zero. However, in Internet Explorer 6 and Internet Explorer 7 the margins are greater than zero. This is a bug.

Note that if, after allocating the necessary vertical space to all the components of an element box there is still space left in the containing block, then the bottom margin expands and uses the remaining space, even if the element has the margin-bottom:auto declaration.

Margin Declarations in Percentages

Percentages in margin declarations refer to the width of the containing block element. Internet Explorer 6 frequently calculates percentage margins incorrectly. Note that even top and bottom margins are calculated with respect to the width (not the height) of the containing block element.

Margin Declarations in em

Margin declarations in em refer to the font size of the element to which the declaration applies.

2 comments:

Unknown said...

what a wealth of information! thanks for sharing. hope all's well.

Chetan Crasta said...

Thanks, Arnab. Nice of you to leave a comment!