Rush ThaMan
Rush ThaMan

Reputation: 111

CSS float left issue

OK so here is my code

<html>
<head>
<style>
.div1{
	height:40px;
	width:40px;
	background-color:red;
	display:block;
	float:left;
}	
.div2{
	height:40px;
	width:40px;
	background-color:green;
	display:block;
	
}
.div3{
	height:40px;
	width:40px;
	background-color:yellow;
	display:block;
}
</style>
</head>

<body>
<div class="div1"></div>
<div class="div2"></div>
<div class="div3"></div>

</body>

</html>

I want my website to look like this: first square is red, next to is green, and below red is yellow square. I thought that float left on first element should make next one jump right next to him. Why doesn't it work?

Upvotes: 1

Views: 4874

Answers (3)

Oriol
Oriol

Reputation: 287960

The problem is that floating elements are out-of-flow:

An element is called out of flow if it is floated, absolutely positioned, or is the root element.

Therefore, they don't impact surrounding elements as an in-flow element would.

This is explained in 9.5 Floats:

Since a float is not in the flow, non-positioned block boxes created before and after the float box flow vertically as if the float did not exist. However, the current and subsequent line boxes created next to the float are shortened as necessary to make room for the margin box of the float.

enter image description here

html {
  width: 550px;
  border: 1px solid;
}
body {
  font-family: sans-serif;
  color: rgba(0,0,0,.15);
}
body:after {
  content: '';
  display: block;
  clear: both;
}
div {
  position: relative;
}
div:after {
  font-size: 200%;
  position: absolute;
  left: 0;
  right: 0;
  top: 0;
  text-align: center;
}
.block-sibling {
  border: 3px solid green;
}
.block-sibling:after {
  content: 'Block sibling';
  color: green;
}
.float {
  float: left;
  border: 3px solid red;
  height: 90px;
  width: 150px;
  z-index: 1;
}
.float:after {
  content: 'Float';
  color: red;
}
<div class="float"></div>
<div class="block-sibling">
  Lorem ipsum dolor sit amet, consectetur adipiscing elit. Donec a diam lectus. Sed sit amet ipsum mauris. Maecenas congue ligula ac quam viverra nec consectetur ante hendrerit. Donec et mollis dolor. Praesent et diam eget libero egestas mattis sit amet vitae augue. Nam tincidunt congue enim, ut porta lorem lacinia consectetur. Donec ut libero sed arcu vehicula ultricies a non tortor.
</div>

There is an exception to that problematic behavior: if a block element establishes a Block Formatting Context (is a BFC root), then it won't overlap the float:

The border box of a table, a block-level replaced element, or an element in the normal flow that establishes a new block formatting context […] must not overlap the margin box of any floats in the same block formatting context as the element itself.

enter image description here

html {
  width: 550px;
  border: 1px solid;
}
body {
  font-family: sans-serif;
  color: rgba(0,0,0,.15);
}
body:after {
  content: '';
  display: block;
  clear: both;
}
div {
  position: relative;
}
div:after {
  font-size: 200%;
  position: absolute;
  left: 0;
  right: 0;
  top: 0;
  text-align: center;
}
.block-sibling {
  border: 3px solid green;
}
.block-sibling.bfc-root:after {
  content: 'BFC sibling';
  color: green;
}
.float {
  float: left;
  border: 3px solid red;
  height: 90px;
  width: 150px;
  z-index: 1;
}
.float:after {
  content: 'Float';
  color: red;
}
.bfc-root {
  overflow: hidden;
}
<div class="float"></div>
<div class="block-sibling bfc-root">
  Lorem ipsum dolor sit amet, consectetur adipiscing elit. Donec a diam lectus. Sed sit amet ipsum mauris. Maecenas congue ligula ac quam viverra nec consectetur ante hendrerit. Donec et mollis dolor. Praesent et diam eget libero egestas mattis sit amet vitae augue. Nam tincidunt congue enim, ut porta lorem lacinia consectetur.
</div>

For example, you can establish a BFC with overflow different than visible, e.g. hidden

.div2 {
  overflow: hidden;
}

.div1 {
  height: 40px;
  width: 40px;
  background-color: red;
  display: block;
  float: left;
}
.div2 {
  height: 40px;
  width: 40px;
  background-color: green;
  display: block;
  overflow: hidden;
}
.div3 {
  height: 40px;
  width: 40px;
  background-color: yellow;
  display: block;
}
<div class="div1"></div>
<div class="div2"></div>
<div class="div3"></div>

Upvotes: 4

Jakub Rożek
Jakub Rożek

Reputation: 2130

Add float: left; to .div2 and clear:left to .div3

<html>
<head>
<style>
.div1{
	height:40px;
	width:40px;
	background-color:red;
	display:block;
	float:left;
}	
.div2{
	height:40px;
	width:40px;
	background-color:green;
	display:block;
	float: left;
}
.div3{
	height:40px;
	width:40px;
	background-color:yellow;
	display:block;
    clear: left;
}
</style>
</head>

<body>
<div class="div1"></div>
<div class="div2"></div>
<div class="div3"></div>

</body>

</html>

You need to add float:left to the green box in order to make the element stand next to red. If you added the float:left to the yellow square, it would stand next to green. We added clear: left to "clear" the left floats.

Read more about floats.

Upvotes: 4

Damian Cardozo
Damian Cardozo

Reputation: 122

<html>
<head>
<style>
.div1{
    height:40px;
    width:40px;
    background-color:red;
    display:block;
    float:left;
}   
.div2{
    height:40px;
    width:40px;
    background-color:green;
    display:block;
    float:left;

}
.div3{
    height:40px;
    width:40px;
    background-color:yellow;
    display:block;
    float:left;
    clear: both; 
}
</style>
</head>

<body>
<div class="div1"></div>
<div class="div2"></div>
<div class="div3"></div>

</body>

</html>

This will do what you want, but, there is much to improve in that code to make it more simple and more DRY, this will be a short answer, if you want to see a better and smaller style to do the same just ask, and gladly will help.

Upvotes: 0

Related Questions