Loki
Loki

Reputation: 4130

Div positioning is changing with and without border

I'm testing some css styles on a blog-like div layout. I used div{border: 1px solid black;} to see the divs and look at its positions.

When this line is in my style, it looks right, but I don't want to have the borders (just had it for development).

As soon as I comment it out everything changes it's positions. Why is this so?

JSFiddle Link

div{border: 1px solid black;} /* Comment this to see the problem */

body{ text-align:center; }

.postTabs{
    float:left;
    background-color: #c8c8c8;
    width: 60px;
    height: 38px;
    padding: 27px 5px 5px 5px;
    border-radius: 50%;
}

.postContent{
    padding: 15px 15px 15px 50px;
    margin-left: 35px;  
    margin-top: 36px;
    text-align: left;
    background-color: #a7a7a7;
}
<div class="postContainer">
  <div class="postTabs">asdf</div>
    <div class="postContent">
      <div class="postBody">adf</div>
  </div>
</div>

Upvotes: 0

Views: 58

Answers (3)

Hashem Qolami
Hashem Qolami

Reputation: 99464

This is because of collapsing margins:

8.3.1 Collapsing margins

In CSS, the adjoining margins of two or more boxes (which might or might not be siblings) can combine to form a single margin. Margins that combine this way are said to collapse, and the resulting combined margin is called a collapsed margin.

Also the spec states:

Two margins are adjoining if and only if:

  • both belong to in-flow block-level boxes that participate in the same block formatting context
  • no line boxes, no clearance, no padding and no border separate them (Note that certain zero-height line boxes (see 9.4.2) are ignored for this purpose.)
  • both belong to vertically-adjacent box edges, i.e. form one of the following pairs:
    • top margin of a box and top margin of its first in-flow child
    • bottom margin of box and top margin of its next in-flow following sibling
    • bottom margin of a last in-flow child and bottom margin of its parent if the parent has 'auto' computed height
    • top and bottom margins of a box that does not establish a new block formatting context and that has zero computed 'min-height', zero or 'auto' computed 'height', and no in-flow children

In this case, the first child is floated to a side and it is removed from normal flow. Hence the first in-flow child of the .postContainer container is .postContent element which has a margin-top of 36px.

Since the container doesn't establish a block formatting context, and there's no border, padding between them, the margins would be collapsed into one.

You could prevent that by giving the container:

  • A padding-top of 1px - for instance - Example here.
  • A border-top of 1px solid transparent Example here.
  • An overflow of anything other than visible which creates a new block formatting context - Example Here.

For further info you could refer to the spec.

Upvotes: 1

Fenton
Fenton

Reputation: 250842

This is because of the default box model in CSS. The element is as wide as the width, plus any padding, plus any border.

You may have expected the border to sit inside of the element, but it actually makes it wider (by 2px in your case) and taller (again by 2px).

You can adjust your width and height accordingly, or you can change the box-model being used with the CSS box-sizing: border-box;

In your case, though, you are only applying the border for development purposes, so changing your CSS to support the border will mean changing it all back again later.

Rather than do all that work, use your browser tools. The screenshot below shows the browser tools in Firefox (all browser have similar tools to this). When you highlight the element in the HTML shown in the tools, it shows the outline of the element on the actual page.

This gives you your development view whenever you need it without having to change the code.

Firefox Tools

Upvotes: 0

Vitorino fernandes
Vitorino fernandes

Reputation: 15951

Check the fiddle here

JS Fiddle

it was happening because of float:left for .postTabs class

.postContainer{
    clear: both;
    float: left;
    width: 100%;
}

Upvotes: 1

Related Questions