I have two different divs with various contents, and would like them to be the same height and width. It seems like a bad idea to set their height and width to a fixed pixel size, because their size should probably vary based on browser/screen size. Setting their width to a percentage works, but percentage is not an option for height.
Is there a way to ensure two divs have the same dimensions without setting to fixed pixel sizes? Or are fixed pixel sizes really so bad?
Having an outer div with display: table; and these two divs inside it with display: table-cell; should work for you.
I'd suggest defining a container div which varies according to screen width (using #media screen) and using css3's flex to define your divs like so :
HTML
<div class="container">
<div class="first-div">first div </div>
<div class="second-div">second div </div>
</div>
CSS
.first-div{
-webkit-flex: 1; /* Safari 6.1+ */
flex: 1;
background-color:yellow;
border: 2px solid black;
}
.second-div{
-webkit-flex: 1; /* Safari 6.1+ */
flex: 1;
background-color:blue;
border: 2px solid black;
}
.container{
width:auto;
display: -webkit-flex; /* Safari */
-webkit-align-items: center; /* Safari 7.0+ */
display: flex;
align-items: center;
}
https://jsfiddle.net/sujy3bq4/19/
Hope this helps you.
When using height, you need to make sure that you have a full body to work with. By default, the body height is auto. If you set the height to 100%, you can start to use the height attribute on child elements.
Just remember that height is always set to it's parent:
body,html{height:100%;}
div{width:50%; height:50%;}
.el1{float:left; background:#f00;}
.el2{float:right; background:#0f0;}
<div class="el1"></div>
<div class="el2"></div>
If using CSS3 is an option in your case then you can use the 'ViewPort Percentage Lengths" Details on W3.
Something like below should work. (Refer question here for more details.)
div {
height:100vh;
}
Super easy and intuitive way to make responsive, square containers
Scalable percentage heights with padding-bottom:
See Codepen
Basically, set the height to 0, and set the bottom padding to any percentage you'd like.
.box {
float: left;
width: 23%;
height: 0;
padding-bottom:23%;
margin: 1%;
background-color: #e6e6e6;
box-sizing: border-box;
text-align: center;
}
<section>
<div class="box">
1
</div>
<div class="box">
2
</div>
<div class="box">
3
</div>
<div class="box">
4
</div>
</section>
Related
I am trying to get 2 divs that do not have a common parent div to be the height of the larger div. (using display: flex).
As shown in the above code, I would like <child-div1> and <child-div2> to have the same height. Currently, I have display: flex on the <parent-div> which successfully makes <middle-div1> and <middle-div2> to have the same height. However, I can't seem to figure out how to ensure that <child-div1> and <child-div2> have the same height.
<parent-div style="display: flex">
<middle-div1>
<child-div1></child-div1>
</middle-div1>
<middle-div2>
<child-div2></child-div2>
</middle-div2>
</parent-div>
In order to figure it out you could right click in the page, then select inspect element, and you going to see a window like this:
by clicking the most left icon and hovering over the two divs, you are going to see the exact width x height
Add display: flex to the <middle-div> flex items.
This will automatically apply align-items: stretch to the <child-div> children. (Just note that a height rule will override align-items: stretch.)
With that layout, you can set both children to have height: inherit; it's inheriting the height from the tallest part of the container. So for example, if you have an image on one side that is 400 px tall, that stretches the container, therefore, allowing the other child to grow in height also.
.container {
display: flex;
}
.one, .two {
height: inherit;
width: 50%;
}
.one {
background-color: lightblue;
}
.two {
background-color: darkgreen;
color: white;
}
<div class="container">
<div class="one">1<br><img src="https://dummyimage.com/400x400/000/fff&text=test"></div>
<div class="two">2</div>
</div>
One solution is to add height:100%; to child-div1 and child-div2
<parent-div style = "display: flex">
<middle-div1>
<child-div1 style="height: 100%;"></child-div1>
</middle-div1>
<middle-div2>
<child-div2 style="height: 100%;"></child-div2>
</middle-div2>
</parent-div>
I need an image in nested flex containers to have width 100%, but this doesn´t work in IE11 when the container has flex-direction: column. I tried:
img {
width: 100%;
max-width: calc( 100% - 0.1px );
}
but this also doesn't work. Any ideas?
section, .articles-wrapper, .article-wrapper {
display: flex;
}
.article-wrapper {
flex-direction: column;
}
img {
width: 100%;
}
html:
<section>
<div class="articles-wrapper">
<div class="article-wrapper">
<img src="http://via.placeholder.com/600x150">
</div>
</div>
</section>
Have you inspected the page to see how the elements are laid out?
The image actually is taking up 100% of it's parent's width, because by default flex-items are not allowed to grow to fill the flex container but expand only enough to display their content.
Both the .articles-wrapper and .article-wrapper elements need to be explicitly allowed to grow, either by specifying flex-grow: 1; or using the shorthand property flex with one of several values:
.articles-wrapper, .article-wrapper {
flex: auto; /* shorthand for flex: 1 1 auto; */
}
OR
.articles-wrapper, .article-wrapper {
flex: 1; /* shorthand for flex: 1 1 0%; */
}
As you get deeper into using flexbox, I recommend keeping Philip Walton's Flexbugs repo at hand which lists common bugs for all browsers as well as workarounds for each.
EDIT Michiel: flex: 1 works in IE11, except that the aspect ratio is not maintained when the window is scaled to a smaller size than the image size. This 'feature' is documented in Flexbugs #5, and can be solved by adding a non-flex wrapper:
<section>
<div class="articles-wrapper">
<div class="article-wrapper">
<div> <!-- ADDED NON-FLEX WRAPPER -->
<img src="http://via.placeholder.com/600x150">
</div>
</div>
</div>
</section>
I have a .parent div and within that I have an unknown number of .child divs. I need the child divs to be in a vertical grid and all of them need to be equal height. Unfortunately, I can't use javascript for this.
I have tried different combinations of display: inline-block and float: left, but I can't get the children to be the same height.
I am able to achieve same height using display: table-cell but then I run into another problem that the children don't split onto multiple lines if the total width exceeds the container width.
Is there a way to do this with pure css? I only need to support IE10+ if that helps (flexbox?)
You can use a wrapping flexbox - see how the heights are auto-adjusted (due to the align-items:stretch property which is default) when the child divs wrap as you resize the window.
* {
box-sizing: border-box;
}
body {
margin: 0;
}
.wrapper {
display: flex;
flex-flow: row wrap;
}
.wrapper > div {
border: 1px solid red;
}
<div class="wrapper">
<div>
some text here some text here
</div>
<div>
some text here
<br/>more text here
</div>
<div>
some text here
<br/>more text here and some more and some more
</div>
<div>
some text here
<br/>more text here
<br/>more text here
</div>
</div>
Yes you could use flexbox.
.parent{
display: flex;
}
.child{
flex:1;
}
You could try using viewport units.
Something like this might work:
.child {
height: 1vw;
}
This will make the child elements have 1/100 of the viewport width.
To read more about viewport units
Viewport units support
I have a layout where I have 3 columns.
Therefore, I divide 100% by 3.
The result is obviously 33.333....
My goal is perfect 1/3 of screen.
Question:
How many numbers after dot can CSS handle to specify 1/3 of width ?
e.g. 33.33333 (n=5) ← how many n can css handle
HTML:
<div id="wrapper">
<div id="c1"></div>
<div id="c2"></div>
<div id="c3"></div>
</div>
CSS:
#c1, #c2, #c3 {
width: 33%; // 1/3 of 100%
}
Is there a better way to divide by 3?
As it's 2018, use flexbox - no more inline-block whitespace issues:
body {
margin: 0;
}
#wrapper {
display: flex;
height: 200px;
}
#wrapper > div {
flex-grow: 1;
}
#wrapper > div:first-of-type { background-color: red }
#wrapper > div:nth-of-type(2) { background-color: blue }
#wrapper > div:nth-of-type(3) { background-color: green }
<div id="wrapper">
<div id="c1"></div>
<div id="c2"></div>
<div id="c3"></div>
</div>
Or even CSS grid if you are creating a grid.
body {
margin: 0;
}
#wrapper {
display: grid;
grid-template-columns: repeat(3, 1fr);
grid-auto-rows: minmax(200px, auto);
}
#wrapper>div:first-of-type { background-color: red }
#wrapper>div:nth-of-type(2) { background-color: blue }
#wrapper>div:nth-of-type(3) { background-color: green }
<div id="wrapper">
<div id="c1"></div>
<div id="c2"></div>
<div id="c3"></div>
</div>
Use CSS calc():
body {
margin: 0;
}
div {
height: 200px;
width: 33.33%; /* as #passatgt mentioned in the comment, for the older browsers fallback */
width: calc(100% / 3);
display: inline-block;
}
div:first-of-type { background-color: red }
div:nth-of-type(2) { background-color: blue }
div:nth-of-type(3) { background-color: green }
<div></div><div></div><div></div>
JSFiddle
References:
How to remove the space between inline-block elements?
MDN calc()
Can I Use calc()
A perfect 1/3 cannot exist in CSS with full cross browser support (anything below IE9). I personally would do: (It's not the perfect solution, but it's about as good as you'll get for all browsers)
#c1, #c2 {
width: 33%;
}
#c3 {
width: auto;
}
How about using the CSS3 flex model:
HTML Code:
<div id="wrapper">
<div id="c1">c1</div>
<div id="c2">c2</div>
<div id="c3">c3</div>
</div>
CSS Code:
*{
margin:0;
padding:0;
}
#wrapper{
display:-webkit-flex;
-webkit-justify-content:center;
display:flex;
justify-content:center;
}
#wrapper div{
-webkit-flex:1;
flex:1;
border:thin solid #777;
}
Using this fiddle, you can play around with the width of each div. I've tried in both Chrome and IE and I notice a difference in width between 33% and 33.3%. I also notice a very small difference between 33.3% and 33.33%. I don't notice any difference further than this.
The difference between 33.33% and the theoretical 33.333...% is a mere 0.00333...%.
For arguments sake, say my screen width is 1960px; a fairly high but common resolution. The difference between these two widths is still only 0.065333...px.
So, further than two decimal places, the difference in precision is negligible.
.selector{width:calc(100% / 3);}
In case you wonder, In Bootstrap templating system (which is very accurate), here is how they divide the columns when you apply the class .col-md-4 (1/3 of the 12 column system)
CSS
.col-md-4{
float: left;
width: 33.33333333%;
}
I'm not a fan of float, but if you really want your element to be perfectly 1/3 of your page, then you don't have a choice because sometimes when you use inline-block element, browser can consider space in your HTML as a 1px space which would break your perfect 1/3. Hope it helped !
Just in case someone is still looking for the answer,
let the browser take care of that. Try this:
display: table on the container element.
display: table-cell on the child elements.
The browser will evenly divide it whether you have 3 or 10 columns.
EDIT
the container element should also have: table-layout: fixed otherwise the browser will determine the width of each element (most of the time not that bad).
Just to present an alternative way to fix this problem (if you don't really care about supporting IE):
A soft coded solution would be to use display: table (no support in IE7) along with table-layout: fixed (to ensure equal width columns).
Read more about this here.
I have found that 6 decimal places is sometimes required (at least in Chrome) for the 1/3 to return a perfect result.
E.g., 1140px / 3 = 380px
If you had 3 elements within the 1140 container, they would need to have a width set to 33.333333% before Chrome's inspector tool shows that they are at 380px. Any less amount of decimal places, and Chrome returns a lesser width of 379.XXXpx
2018 Update
This is the method I use width: 33%; width: calc(33.33% - 20px); The first 33% is for browsers that do not support calc() inside the width property, the second would need to be vendor prefixed with -webkit- and -moz- for the best possible cross-browser support.
#c1, #c2, #c3 {
margin: 10px; //not needed, but included to demonstrate the effect of having a margin with calc() widths/heights
width: 33%; //fallback for browsers not supporting calc() in the width property
width: -webkit-calc(33.33% - 20px); //We minus 20px from 100% if we're using the border-box box-sizing to account for our 10px margin on each side.
width: -moz-calc(33.33% - 20px);
width: calc(33.33% - 20px);
}
tl;dr account for your margin
I do not think you can do it in CSS, but you can calculate a pixel perfect width with javascript. Let's say you use jQuery:
HTML code:
<div id="container">
<div id="col1"></div>
<div id="col2"></div>
<div id="col3"></div>
</div>
JS Code:
$(function(){
var total = $("#container").width();
$("#col1").css({width: Math.round(total/3)+"px"});
$("#col2").css({width: Math.round(total/3)+"px"});
$("#col3").css({width: Math.round(total/3)+"px"});
});
I have the page structure as:
<div class="parent">
<div class="child-left floatLeft">
</div>
<div class="child-right floatLeft">
</div>
</div>
Now, the child-left DIV will have more content, so the parent DIV's height increases as per the child DIV.
But the problem is child-right height is not increasing. How can I make its height as equal to it's parent?
For the parent element, add the following properties:
.parent {
overflow: hidden;
position: relative;
width: 100%;
}
then for .child-right these:
.child-right {
background:green;
height: 100%;
width: 50%;
position: absolute;
right: 0;
top: 0;
}
Find more detailed results with CSS examples here and more information about equal height columns here.
A common solution to this problem uses absolute positioning or cropped floats, but these are tricky in that they require extensive tuning if your columns change in number+size, and that you need to make sure your "main" column is always the longest. Instead, I'd suggest you use one of three more robust solutions:
display: flex: by far the simplest & best solution and very flexible - but unsupported by IE9 and older.
table or display: table: very simple, very compatible (pretty much every browser ever), quite flexible.
display: inline-block; width:50% with a negative margin hack: quite simple, but column-bottom borders are a little tricky.
1. display:flex
This is really simple, and it's easy to adapt to more complex or more detailed layouts - but flexbox is only supported by IE10 or later (in addition to other modern browsers).
Example: http://output.jsbin.com/hetunujuma/1
Relevant html:
<div class="parent"><div>column 1</div><div>column 2</div></div>
Relevant css:
.parent { display: -ms-flex; display: -webkit-flex; display: flex; }
.parent>div { flex:1; }
Flexbox has support for a lot more options, but to simply have any number of columns the above suffices!
2.<table> or display: table
A simple & extremely compatible way to do this is to use a table - I'd recommend you try that first if you need old-IE support. You're dealing with columns; divs + floats simply aren't the best way to do that (not to mention the fact that multiple levels of nested divs just to hack around css limitations is hardly more "semantic" than just using a simple table). If you do not wish to use the table element, consider css display: table (unsupported by IE7 and older).
Example: http://jsfiddle.net/emn13/7FFp3/
Relevant html: (but consider using a plain <table> instead)
<div class="parent"><div>column 1</div><div>column 2</div></div>
Relevant css:
.parent { display: table; }
.parent > div {display: table-cell; width:50%; }
/*omit width:50% for auto-scaled column widths*/
This approach is far more robust than using overflow:hidden with floats. You can add pretty much any number of columns; you can have them auto-scale if you want; and you retain compatibility with ancient browsers. Unlike the float solution requires, you also don't need to know beforehand which column is longest; the height scales just fine.
KISS: don't use float hacks unless you specifically need to. If IE7 is an issue, I'd still pick a plain table with semantic columns over a hard-to-maintain, less flexible trick-CSS solution any day.
By the way, if you need your layout to be responsive (e.g. no columns on small mobile phones) you can use a #media query to fall back to plain block layout for small screen widths - this works whether you use <table> or any other display: table element.
3. display:inline block with a negative margin hack.
Another alternative is to use display:inline block.
Example: http://jsbin.com/ovuqes/2/edit
Relevant html: (the absence of spaces between the div tags is significant!)
<div class="parent"><div><div>column 1</div></div><div><div>column 2</div></div></div>
Relevant css:
.parent {
position: relative; width: 100%; white-space: nowrap; overflow: hidden;
}
.parent>div {
display:inline-block; width:50%; white-space:normal; vertical-align:top;
}
.parent>div>div {
padding-bottom: 32768px; margin-bottom: -32768px;
}
This is slightly tricky, and the negative margin means that the "true" bottom of the columns is obscured. This in turn means you can't position anything relative to the bottom of those columns because that's cut off by overflow: hidden. Note that in addition to inline-blocks, you can achieve a similar effect with floats.
TL;DR: use flexbox if you can ignore IE9 and older; otherwise try a (css) table. If neither of those options work for you, there are negative margin hacks, but these can cause weird display issues that are easy to miss during development, and there are layout limitations you need to be aware of.
For the parent:
display: flex;
For children:
align-items: stretch;
You should add some prefixes, check caniuse.
I found a lot of answers, but probably the best solution for me is
.parent {
overflow: hidden;
}
.parent .floatLeft {
# your other styles
float: left;
margin-bottom: -99999px;
padding-bottom: 99999px;
}
You can check other solutions here http://css-tricks.com/fluid-width-equal-height-columns/
Please set parent div to overflow: hidden
then in child divs you can set a large amount for padding-bottom. for example
padding-bottom: 5000px
then margin-bottom: -5000px
and then all child divs will be the height of the parent.
Of course this wont work if you are trying to put content in the parent div (outside of other divs that is)
.parent{
border: 1px solid black;
overflow: hidden;
height: auto;
}
.child{
float: left;
padding-bottom: 1500px;
margin-bottom: -1500px;
}
.child1{
background: red;
padding-right: 10px;
}
.child2{
background: green;
padding-left: 10px;
}
<div class="parent">
<div class="child1 child">
One line text in child1
</div>
<div class="child2 child">
Three line text in child2<br />
Three line text in child2<br />
Three line text in child2
</div>
</div>
Example: http://jsfiddle.net/Tareqdhk/DAFEC/
Does the parent have a height? If you set the parents height like so.
div.parent { height: 300px };
Then you can make the child stretch to the full height like this.
div.child-right { height: 100% };
EDIT
Here is how you would do it using JavaScript.
CSS table display is ideal for this:
.parent {
display: table;
width: 100%;
}
.parent > div {
display: table-cell;
}
.child-left {
background: powderblue;
}
.child-right {
background: papayawhip;
}
<div class="parent">
<div class="child-left">Short</div>
<div class="child-right">Tall<br>Tall</div>
</div>
Original answer (assumed any column could be taller):
You're trying to make the parent's height dependent on the children's height and children's height dependent on parent's height. Won't compute. CSS Faux columns is the best solution. There's more than one way of doing that. I'd rather not use JavaScript.
I used this for a comment section:
.parent {
display: flex;
float: left;
border-top:2px solid black;
width:635px;
margin:10px 0px 0px 0px;
padding:0px 20px 0px 20px;
background-color: rgba(255,255,255,0.5);
}
.child-left {
align-items: stretch;
float: left;
width:135px;
padding:10px 10px 10px 0px;
height:inherit;
border-right:2px solid black;
}
.child-right {
align-items: stretch;
float: left;
width:468px;
padding:10px;
}
<div class="parent">
<div class="child-left">Short</div>
<div class="child-right">Tall<br>Tall</div>
</div>
You could float the child-right to the right, but in this case I've calculated the widths of each div precisely.
I have recently done this on my website using jQuery. The code calculates the height of the tallest div and sets the other divs to the same height. Here's the technique:
http://www.broken-links.com/2009/01/20/very-quick-equal-height-columns-in-jquery/
I don't believe height:100% will work, so if you don't explicitly know the div heights I don't think there is a pure CSS solution.
If you are aware of bootstrap you can do it easily by using 'flex' property.All you need to do is pass below css properties to parent div
.homepageSection {
overflow: hidden;
height: auto;
display: flex;
flex-flow: row;
}
where .homepageSection is my parent div.
Now add child div in your html as
<div class="abc col-md-6">
<div class="abc col-md-6">
where abc is my child div.You can check equality of height in both child div irrespective of border just by giving border to child div
<div class="parent" style="height:500px;">
<div class="child-left floatLeft" style="height:100%">
</div>
<div class="child-right floatLeft" style="height:100%">
</div>
</div>
I used inline style just to give idea.
I can see that the accepted answer uses position: absolute; instead of float: left. In case you want to use float: left with the following structure,
<div class="parent">
<div class="child-left floatLeft"></div>
<div class="child-right floatLeft"></div>
</div>
Give position: auto; to the parent so that it will contain its children height.
.parent {
position: auto;
}
.floatLeft {
float: left
}
I learned of this neat trick in an internship interview. The original question is how do you ensure the height of each top component in three columns have the same height that shows all the content available. Basically create a child component that is invisible that renders the maximum possible height.
<div class="parent">
<div class="assert-height invisible">
<!-- content -->
</div>
<div class="shown">
<!-- content -->
</div>
</div>