I'm having a bit of a "moment" where I am stumped on an issue I thought should be pretty easy (and probably is, I'm just over complicating I'm sure).
I'm looking to have a div with multiple children div's; the children should automatically expand or contract based on the number there are (the site I'm working on is in a CMS that allows a user to add or remove items).
My issue is having the div's respect the min- and max-width declaration. I have a hunch that it could be something to do with them being float:left, but I've tried a few other variations with no luck.
My main objective is to get these columns to fill their space on one "row", up to 4 columns.
EDIT: I need to have these columns be a minimum width, as well as a maximum width. So if there are 3 child div's, they should all be wider than if there were 4 child div's.
Here is an example of my code: http://codepen.io/joe/full/IJvGp
HTML
<div class="sub cf">
<div class="row">
<div class="col">
Column 1
</div>
<div class="col">
Column 2
</div>
<div class="col">
Column 3
</div>
<div class="col">
Column 4
</div>
</div>
</div>
CSS
.sub {
width: 670px;
background: #fff;
border: 10px solid #414042;
}
.sub .row {
padding: 0;
float: left;
width: 100%;
}
.sub .row .col {
min-width: 166px;
max-width: 222px;
width: 100%;
float: left;
border-right: 1px solid #D0D2D3;
margin: 0;
padding: 0;
}
.cf::before, .cf::after {
content: "";
display: table;
}
.cf::after {
clear: both;
}
With jquery you could dynamically set the column widths as a % based on the number of columns within the row.
var colWidth = (1 / $('.sub.cf .row').children().length * 100) + '%';
$('.sub.cf .col').outerWidth(colWidth);
working fiddle. Insert or remove more columns and rerun it to see how it works.
Removing the width:100%; on the .sub .row .col item made them appear in 4 columns.
Regardless it looks like you should be using a table instead of this approach.
CSS3 Solution
Remove the min and max widths on .col but add the box-sizing: border-box property to that. Then add the following code below the .col definition which yields the result in this fiddle:
.sub .row .col:nth-last-of-type(2),
.sub .row .col:nth-last-of-type(2) ~ .col
{
width: 50%;
}
.sub .row .col:nth-last-of-type(3),
.sub .row .col:nth-last-of-type(3) ~ .col
{
width: 33.3%;
}
.sub .row .col:nth-last-of-type(4),
.sub .row .col:nth-last-of-type(4) ~ .col
{
width: 25%;
}
You could try something like this:
HTML:
<div class="sub">
<div></div>
<div></div>
<div></div>
<div></div>
</div>
CSS:
.sub {
text-align: justify;
width: 670px;
background: #fff;
sborder: 10px solid #414042;
}
.sub div {
display: inline-block;
max-width: 166px;
min-height: 100px;
border-right: 1px solid #D0D2D3;
margin: 0;
padding: 0;
}
.sub:after {
content: '';
width: 100%;
display: inline-block;
}
The main problem here is width: 100% and max-width: 222px. With width: 100% you are making the children divs as big as you can. And because of max-width: 222px they all become 222px width. Your parent div is 670px width, so if you do the math: 222px * 4 = 888px. The children divs' total width is exceeding the parent's width, that's why it's pulling the last div down.
You can try:
Codepen
If you don't care much about supporting IE8- then ScottS solution is the best.
You have the following code.
max-width:222px;
Reduce it to some value so that it can be accomdated!
max-width:166px;
works for me!
Related
I have two divs next to each/side by side..
The LEFT div has a FLUID width.
The RIGHT div has a static wdth.
When I resize the screen/browser... it work great! (and as intended).
However because of the way it was set up:
(Fiddle example: http://jsfiddle.net/VHcPT/384/)
The RIGHT div in physically first in the mark-up..(and floated RIGHT).
However at say 768px breakpoint.. I need this RIGHT (static) DIV to stack UNDER the LEFT div.. how can I achieve this?
If I physically have the RIGHT div AFTER the LEFT div in the markup.. it would stack as expected.. but I need to have it FIRST so the fluid/static behavior in place works as it should.
So to re-cap, its NOT about getting the two divs next to each other one fluid, one static.. its how to handle that at a responsive/breakpoint.. and get the static (RIGHT) div to stack UNDER the fluid (LEFT) div
Using the fiddle example.. the RED DIV would go UNDER (stack) the GREEN lines/div.. (the green would then be full width).. at a certain breakpoint.
and because code is required now:
HTML:
<div id="contentcontainer">
<div class="rightcontainer">mm</div>
<div class="leftcontainer">
<div class="item_1">
some text
</div>
<div class="item_2">
some text
</div>
</div>
</div>
CSS:
#directorycontainer {
padding:10px 10px;
display:table;
box-sizing: border-box;
width: 100%;
font-size: 0.8em;
font-weight: normal;
}
.directory {
background: green;
margin-right: 10px;
overflow: hidden;
padding-right: 10px;
position: relative;
}
.mapcontainer {
background: red;
display:table;
width:240px;
height:480px;
float:right;
position:relative;
overflow: hidden;
}
.providercontainer{
background-color: #f7f9fb;
border: 1px solid #e1dacd;
display: table;
margin-bottom: 0.625em;
padding: 0;
width: 100%;
}
OK well looks like this works and should be an acceptable answer/solution:
Fiddle:
http://jsfiddle.net/VHcPT/389/
HTML/Markup:
<div id="contentcontainer">
<div class="leftcontainer">
<div class="item_1">
some text
</div>
<div class="item_1">
some text
</div>
</div>
<div class="rightcontainer">mm</div>
</div>
CSS:
* {box-sizing: border-box;}
#contentcontainer {
padding:10px 10px;
display:table;
box-sizing: border-box;
width: 100%;
font-size: 0.8em;
font-weight: normal;
}
.leftcontainer {
background: green;
overflow: hidden;
padding: 5px;
float:left;
width:calc(100% - 240px);
}
.rightcontainer {
background: red;
display:table;
width:240px;
height:480px;
float:left;
position:relative;
overflow: hidden;
}
.item_1{
background-color: #f7f9fb;
border: 1px solid #e1dacd;
display: table;
margin-bottom: 0.625em;
padding: 0;
width: 100%;
}
works with whatever breakpoints you set and the elements will stack correctly.
you may like my FLEXBOX alternative to you problem. It may take a bit of practice, but it will eventually give you much more control.
The FIDDLE
Below the basic CSS structure, no other 'display', 'position' or 'overflow' needed. With this structure you can mix-match any number of fixed and/or fluid columns.
.flex--box { display: flex; flex-flow: row wrap }
.flex--fluid { flex: 1 1 auto }
.flex--fixed { flex: 0 0 auto; min-width: 240px }
/* MOBILE MQ */
#media all and (max-width: 360px) {
.flex--fluid, .flex--fixed {
flex: 1 1 auto;
}
}
Let me know if you have problem with it.
And of course, do give credit if you think it is worth it.
( BTW: I changed the colors to something less retina intensive &D )
I'm trying to display two divs side-by-side with inline-block (can't use floats). Currently my CSS fails to do this. I realize this might be a duplicate, but having tried suggestions from related posts I still can't get it to work.
#wrapper {
display: inline-block;
width: 300px;
}
#images {
display: inline-block;
width: 100px;
}
#specs {
display: inline-block;
width: 100px;
}
<div id="wrapper">
<div id="images">
TEST Data
</div>
<div id="specs">
Test Data
</div>
</div>
#wrapper must have +200px of width
Modify css for #wrapper:
#wrapper{
display:inline-table;
width: 200px;
}
Width must be at least 200px, since you want two elements (100px each) to fix within.
example jsfiddle
The issue is that your wrapper div is only 100px wide, so the two sub-items can't fit side by side since they're also 100px wide. I made it much wider and they now appear side by side: jsfiddle
#wrapper{
display:inline-block;
width: 300px;
}
#images {
display: inline-block;
width: 100px;
}
#specs {
display: inline-block;
width: 100px;
}
wrapper is the same size as the contained elements #images and #specs, so make it width: 100% or something larger than 200px and those elements will line up horizontally.
div {outline: 1px dashed red;}
#wrapper{
display:inline-block;
width: 100%;
}
#images {
display:inline-block;
width: 100px;
}
#specs {
display:inline-block;
width: 100px;
}
<div id="wrapper">
<div id="images">
TEST Data
</div>
<div id="specs">
Test Data
</div>
</div>
I would like to achieve a layout that looks like this:
I am interested in a css/html only solution, so no javascript required.
The widths of both divs are dynamic, so I cannot use any static margins.
The spacing between the sides of the divs, and the top, should be the same.
I tried using margin: auto auto 0 auto on the inner div, as you can see in this jsfiddle, but it only works for left and right.
Note, the following attempt doesn't answer the question fully, since the width of the child cannot be dynamic.
The idea is to use a percentage width + percentage margin-top values on the child. It's a responsive layout, see the comments in the code, and try it out on different window sizes.
JSFiddle: http://jsfiddle.net/jkoycs6e/
body {
margin: 0;
}
.outer {
height: 100vh; /*for demo only*/
background: teal;
overflow: auto;
}
.inner {
width: 80%;
background: gold;
margin: auto;
margin-top: 10%; /* 100%-80%/2 */
}
<div class="outer">
<div class="inner">
hello<br/>hello<br/>hello
</div>
</div>
This is not possible. At least not without using javascript. There is no css-only solution.
If you put align="center" in your div you'll get to the middle of the screen every time but it's not going to be supported in HTML5 so I recommend the 50:50 approach.
div
{
text-align:center;
margin-top:50%;
margin-bottom:50%;
}
Hope that helps. ^^
Set the outer parent's overflow to auto and give your margin-top a relative value. Something like this:
.outer {
background: blue;
overflow: auto;
}
.inner {
background:yellow;
width: 100px;
height: 100px;
margin: 1em auto 0 auto;
}
<div class="outer">
<div class="inner">
</div>
</div>
This seems to work:
.outer {
height: 500px;
width: 300px;
background: blue;
position: relative;
}
.inner {
width: 80%;
height: 200px;
background:green;
position: absolute;
margin-left: 10%;
margin-right: 10%;
margin-top: 10%;
margin-bottom: 0;
}
You can change the percentages marked for the margins as per your intended value for k.
Here's the fiddle
EDIT: Note that the width of inner has to be set in terms of percentages for this to work. Also note that when a margin is specified in terms of percentage, the margin's value is computed as a percentage of the width of the container. Even for the vertical margins, the percentage is applied on the width (and NOT the height) of the container.
Here's an SO post that's helpful in understanding how to position elements with respect to their container.
This answer doesn't actually make use of the margin property, nor does it have only two div.
body {
font-size: 26px;
text-align: center;
font-family: monospace;
}
#container {
display: inline-block;
position: relative;
width: 100%;
}
#dummy {
margin-top: 20%;
}
#element {
position: absolute;
top: 0;
bottom: 0;
left: 0;
right: 0;
background-color: silver
/* show me! */
}
#wrapper {
display: table;
width: 100%;
}
#row {
display: table-header-group;
}
#left {
display: table-cell;
background-color: chartreuse;
width: 20%;
}
#incenter {
display: table-cell;
background-color: aqua;
}
#right {
display: table-cell;
background-color: chartreuse;
width: 20%;
}
<div>
<div id="container">
<div id="dummy"></div>
<div id="element">
k (20%)
</div>
</div>
<div id="wrapper">
<div id="row">
<div id="left">width = k (20%)</div>
<div id="incenter">incenter</div>
<div id="right">width = k (20%)</div>
</div>
</div>
</div>
Another example with measurements in pixels is here.
For explanation refer:
https://stackoverflow.com/a/12121309/2534513
https://stackoverflow.com/a/6615994/2534513
I have actually combined techniques mentioned in above two answers to make this one.
Using JavaScript would have been a lot easier.
I am having a bit of a hard time trying to get the 3 column layout sorted.
This is my current HTML and css layout
<div class="row">
<div class="col">C1</div>
<div class="col">C2</div>
<div class="col">C3</div>
</div>
The CSS is as follows:
.row {
width: 964px;
}
.row:last-child {
margin: 0;
}
.row .col {
width: 33.33%
float: left;
margin-bottom: 20px;
margin-right: 10px;
}
The columns are basically of equal width using percentages of 33.33%. Problem I have is that while the columns show up within the the row container, on the last column, there is a gap on the right margin. Increasing the right margin pushes the last column to the next line.
How can I line up the columns so that they keep the same width, but for the first and last columns to not to have any margins (ie. no left margin on the first column and no right margin on the 3rd column).... Any ideas?
Thank you..
.row .col:last-child
{
margin-right:0;
}
this will do. but, don't forget to include it after '.row.col' style
Use % instead of px here margin-right: 10px;
.col{
width: 32%;
margin-right: 2%;
}
.col:last-child{
margin-right: 0%;
}
you should use
.row{
display:table;
}
.col{
display:table-cell;
}
EXAMPLE:
.row{
display:table;
width:100%;
}
.col{
border:1px solid #000;
display:table-cell;
width:33%;
}
FIDDLE DEMO
If your row is a fixed width (964px) then can't you just calculate the column widths that you want and put the margin as a left and right on column two?
Also, 964 doesn't divide by three so it's a bit of an odd choice - you'll always end up with rounding issues - I've changed it to 963px for the example below.
e.g.
<div class="row">
<div class="col">C1</div>
<div class="col middle">C2</div>
<div class="col">C3</div>
</div>
with CSS:
.row .col {
width: 321px;
float: left;
margin-bottom: 20px;
}
.row .middle {
margin-left: 10px;
margin-right: 10px;
}
Thanks for the answers guys, I ended up having to change the padding amount that my main site container was using. Once I had a width of 970px, I just borrowed a bit of css from Bootstrap to get the layout to display correctly.
End result being:
.row {
margin-right: -15px;
margin-left: -15px;
}
.col {
float: left;
width: 33.33333333%;
position: relative;
min-height: 1px;
padding-right: 15px;
padding-left: 15px;
}
That lines everything up perfect for me.
The div elements inside the row are floated left, as described here:
http://www.w3schools.com/html/html_responsive.asp
and percentage sized.
I tried to apply what was suggested in this link below, in a similar question, but without success:
Responsive CSS / Inline divs
The divs keep an inline relation of 50% - 100% - 50% and their contents overlap.
Can anyone help me spot what I missed?
Thank you.
In my CSS and HTML I have:
footer[role="contentinfo"] div {
box-sizing: border-box;
}
.engage-row:after {
content: "";
display: table;
clear: both;
}
.col-1 {
float: left;
width: 25%;
}
.col-2 {
float: left;
width: 50%;
padding: 10px 20px 0px 20px;
}
.col-3 {
float: left;
width: 25%;
}
.footer-wfix {
clear: both;
}
/* for illustrative purposes */
.engage-row {
border: 1px solid red;
}
.engage-row > div {
border: 1px solid blue;
}
<footer id="colophon" role="contentinfo">
<div class="footer-wrap">
<div class="engage-row">
<div class="col-1">
Column 1
</div>
<div class="col-2">
Column 2
</div>
<div class="col-3">
Column 3
</div>
</div>
<div class="footer-wfix">
Footer Menu and Site-generator
</div>
</div>
</footer><!-- #colophon -->
Edited the code and am adding the below for clarity:
- I edited the footer by adding the "engage-row" and it's containing column divs.
- All divs have inherited box-sizing: border-box.
- Column 1, Column 2 and Column 3 don't readjust positioning when I decrease the screen size (width); instead of becoming on top of each others, they are changing their size (keeping percentages but becoming smaller), making the containing text and images overlap (text from column 2 goes in front of the image in column 1). I hope I am using the correct terms for clarity.
- How can I make them readjust the positioning as the screen size changes?
- PrintScreen: 3column divs in footer
(This is an awesome site. Thank you)
You need to take into account the padding in the .col-2 declaration. When you have three columns adding up to a total of "100 % width" and then add padding, the result so to speak is "more than 100 % width", causing the overlapping behavior you observe.
One way around it is to declare the paddings in percent as well. If you don't like the resulting "elastic margins", you need to figure out a equation that works. Or check out Bootstrap or something similar (I mean you can either use it as is, or decipher their responsive solutions).
You need to add the css3 property box-sizing: border-box; This will wrap your padding into your div, so the width will be 50% only.
Please share your feedback if its helpful for your problem.
.col-2{
float: left;
width: 50%;
padding:10px 20px 0px 20px;box-sizing: border-box;
}
you mention 25% 50% 25% and a border of div so overlapped,
in this case use box-sizing: border-box;
.engage-row:after {
content: "";
display: table;
clear: both;
}
.col-1 {
float: left;
width: 25%;
}
.col-2 {
float: left;
width: 50%;
padding: 10px 20px 0px 20px;
}
.col-3 {
float: left;
width: 25%;
}
.footer-wfix {
clear: both;
}
/* for illustrative purposes */
.engage-row {
border: 1px solid red;
}
.engage-row > div {
border: 1px solid blue;
box-sizing: border-box;/*added one*/
}
This is what I needed (I couldn't be clear until I researched enough):
The left and right divs include images and I didn't want those to change size as I decrease the screen resolution. I wanted to input that adjustment in the middle div which contains only text and a subscription form.
The question/answer that drove me there:
How to make element fill remaining width, when sibling has variable width?
My testing fiddle - http://jsfiddle.net/0gvxxpjj/
<!-- In html--->
<div class="row">
<div class="col-1">
<img src="">
</div>
<div class="col-3">
<img src="">
</div>
<div class="col-2">
<h3>Header</h3>
<p>This is a paragraph that, along with the header, needs to wrap as the screen is resized</p>
</div>
</div>
<!-- html ends here-->
/* CSS starts here */
.col-1 {
float: left;
width: 100px;
}
.col-3 {
float: right;
width: 100px;
}
.col-2{
padding: 10px 20px 0px 20px;
overflow: hidden;
}
.row {
border: 1px solid black;
display: inline-block;
}
.col-1, .col-3 {
border: 1px solid blue;
}
.col-2 {
border: 1px dashed red;
}
Hope it becomes useful to someone else.
As I understand it, you want to have the divs be in a 25% - 50% - 25% layout and after the browser shrinks beyond a certain size, they become 100% width and stack on top of each other.
This is done via media queries. What, essentially, happens is that you set some CSS rules inside a media query which adds to any previous CSS rules only when a certain condition has been met (in this case browser width). A rough example can be seen below.
These are the relevant parts:
This sets how the divs will look by default - full width.
.col-1,
.col-2,
.col-3 {
float: left;
width: 100%;
}
This sets the widths of the divs to 25-50-25 once the browser width is larger than 768px.
#media all and (min-width:768px) {
.col-1, .col-3 {
width: 25%;
}
.col-2 {
width: 50%;
}
}
You can extend this example to the layout you desire.
footer[role="contentinfo"] div {
box-sizing: border-box;
}
.engage-row:after {
content: "";
display: table;
clear: both;
}
.col-1,
.col-2,
.col-3 {
float: left;
width: 100%;
}
.col-2 {
padding: 10px 20px 0px 20px;
}
.footer-wfix {
clear: both;
}
/* for illustrative purposes */
.engage-row {
border: 1px solid red;
}
.engage-row > div {
border: 1px solid blue;
}
#media all and (min-width:768px) {
.col-1, .col-3 {
width: 25%;
}
.col-2 {
width: 50%;
}
}
<footer id="colophon" role="contentinfo">
<div class="footer-wrap">
<div class="engage-row">
<div class="col-1">
Column 1
</div>
<div class="col-2">
Column 2
</div>
<div class="col-3">
Column 3
</div>
</div>
<div class="footer-wfix">
Footer Menu and Site-generator
</div>
</div>
</footer><!-- #colophon -->