0

I'm trying to fix margins in existing HTML/CSS (fixing with CSS overrides), and I'm having trouble understanding the case I'm working with (boiled down to the code below).

What I want: no padding above the first 'div.floating' (the padding that comes from 'p.par' for some reason - why?). What confuses me: the padding is gone if I remove div#extra (or if '.floating-column' isn't floating). Why? Are there rules for collapsing margins involved that are beyond my understanding?

(Also, changing the HTML is not an option.)

Thanks for help, Manuela

ps: the code:

<!DOCTYPE html>
<html>
<head>
  <style>
html, body, div, p {
  border:0;
  margin:0;
  padding:0;
}

.container {
  width:960px;
  margin:0 auto;
  background-color: #ddd;
}
.container:after {
  content:"";
  display:block;
  height:0;
  clear:both;
  visibility:hidden;
}
.floating-column {
    float:left;
    border: 1px dashed green;
}

.floating {
  width: 100%;
  float: left;
  border: 1px dotted black;
}

.par {
  margin: 10px;
  border: 1px solid red;
}
  </style>
</head>
<body>
  <div class="container">
    <div class="floating-column">
      <div id="extra">
        <div class="floating">first float</div>
        <div class="floating">another float</div>

        <p class="par">Cras nibh erat, tempor non sagittis ac, vulputate ac lectus. Praesent sed fermentum eros. Mauris sodales suscipit diam, a congue dui commodo ac. Sed convallis rutrum ligula, vitae sollicitudin nisl porttitor nec. Mauris tempor fringilla imperdiet. Pellentesque interdum, tellus nec venenatis venenatis, nisi nulla ultricies leo, tincidunt venenatis risus nisl ac dolor. Donec ante leo, elementum et faucibus tincidunt, dignissim lacinia libero. Suspendisse pharetra in augue in sodales. Etiam luctus dui blandit nisi dictum pretium.</p>
      </div>
    </div>
  </div>
</body>
</html>
Manuela Hutter
  • 823
  • 9
  • 16
  • :The browser also has its own specific css.So, whenever you write a style sheet ,try to use at the beginning `*{padding:0px;margin:0px}`, wherever possible. – Naveen Feb 05 '14 at 13:13
  • 1
    why? I already reset padding for all elements that I use (html, body, div, p). – Manuela Hutter Feb 07 '14 at 10:16

5 Answers5

1

Add clear:both css property to p.par, like:

.par {
  margin: 10px;
  border: 1px solid red;
  clear: both;
  display: inline-block;
}

It will clear the float of div.floating, otherwise it'll take its margin from the top of the container.

Check here the DEMO.

osmanz
  • 481
  • 5
  • 15
  • This will not useful because if you put clear:both in this class '.par' then margin of 10px will not be applied please check in your fiddle. – Bhavesh Parekh Feb 05 '14 at 13:26
  • Yes now its working. Good one. and we can just put one div before p tag with clear both then also same thing happens. But this alternative is also works.. – Bhavesh Parekh Feb 05 '14 at 13:31
  • one more thing just add float left to .par class and remove clear both and display inline block. – Bhavesh Parekh Feb 05 '14 at 13:42
0

i know you don't want to change your html, but with a simple clear div between your floating divs the problem will be solved

here's the fiddle with fix (i don't changed anything else) :

http://jsfiddle.net/9bS5a/

<div class="floating">first float</div>
<div style="clear:both"></div>
<div class="floating">another float</div>

edit : if you want the padding to be correct, there must be another clear div under the 2nd float div :

 <div class="floating">first float</div>
 <div style="clear:both"></div>
 <div class="floating">another float</div>
 <div style="clear:both"></div>

fiddle : http://jsfiddle.net/9bS5a/1/

this thread may help and explain you how clear works What does the CSS rule clear: both do?

Community
  • 1
  • 1
alex
  • 31
  • 3
  • Thanks. I do understand how clear works. I just don't seem to understand how paddings work with floats, and when paddings collapse, and when they don't. And yes, I don't want to change my html ;-) – Manuela Hutter Feb 05 '14 at 20:33
0

You get just what you want by not floating those first two divs. There's no gain in floating an element that's width is set to 100% anyhow.

A floated element is removed from the document flow, although other elements still avoid it to some extent. (That's non technical language!)

When the first two divs are floated, the unfloated paragraph after them slides up underneath them and its margin sticks up above them, although its text makes room for them.

ralph.m
  • 13,468
  • 3
  • 23
  • 30
  • I'm all for technical language! Yes, I understand that the floats are nonsensical in this particular case. I think they are there because they are part of a theme that tries to cater for various column layouts. – Manuela Hutter Feb 05 '14 at 20:28
  • You say "the margin sticks up above them". Why only the top margin, but not the left margin? Also, why is this behavior gone if I remove div#extra from the html? There must be something with collapsing margins that I don't get. – Manuela Hutter Feb 05 '14 at 20:30
  • Collapsing margins only applies to top and bottom margins. With #extra there, the collapsing margin of the p sticks out of #extra and pushes the floats down by that amount of margin. Without it, the p still sills under the floats, but can't push the floats down in the same way. – ralph.m Feb 05 '14 at 22:40
  • Yes, I see that behavior, but why is that so? Why can it push down in one case, but not in the other? Do you know of any documentation that I could read to help me understand this? – Manuela Hutter Feb 07 '14 at 08:28
  • Ok, I think I get it now: if margins of parent and first non-floating element collapse, the floats need to push down. In my case, they collapse, if I remove div#extra they don't since .floating-column has a border. Same if I gave div#extra a border :-) – Manuela Hutter Feb 07 '14 at 10:06
  • edit: don't collapse since .floating-column is a float, border or not. (floats don't collapse margins in any case) – Manuela Hutter Feb 07 '14 at 10:13
0

you need to put clear:both above

tag. like:

<div class="container">
<div class="floating-column">
  <div id="extra">
    <div class="floating">first float</div>
    <div class="floating">another float</div>
    <div style="clear:both"></div>
        <p class="par">Cras nibh erat, tempor non sagittis ac, vulputate ac lectus. Praesent sed fermentum eros. Mauris sodales suscipit diam, a congue dui commodo ac. Sed convallis rutrum ligula, vitae sollicitudin nisl porttitor nec. Mauris tempor fringilla imperdiet. Pellentesque interdum, tellus nec venenatis venenatis, nisi nulla ultricies leo, tincidunt venenatis risus nisl ac dolor. Donec ante leo, elementum et faucibus tincidunt, dignissim lacinia libero. Suspendisse pharetra in augue in sodales. Etiam luctus dui blandit nisi dictum pretium.</p>
  </div>
</div>

you can find this http://jsfiddle.net/6U4UU/

Or you can add fload:left to .par class like:

.par {
    margin: 10px;
    border: 1px solid red;
    float:left;
}

this way also solve your problem. Check here http://jsfiddle.net/6U4UU/1/

Bhavesh Parekh
  • 212
  • 2
  • 11
0

The top-margins of 'div#extra' (0px) and 'p.par' (10px) collapse, making it 10px at the top. So the floats have to come below that.

Margins don't collapse if one of the two elements is a float (or if one of the elements has a border), which is why the behavior changes if you remove 'div#extra' and a float becomes the new parent (or add a border to 'div#extra').

If the margins don't collapse, the parent keeps its 0px top-margins, and the floats come right after. The 'p.par' keeps its 10px top-margin, and in this case renders below the floats.

Manuela Hutter
  • 823
  • 9
  • 16