overflow-x children element width - css

I have a div with overflow-x auto.
This div has children which are wider than the parent div, causing a scroll.
The inner children are given a border and background color which I would like to stretch across the entire width of them - including the scrolled overflow.
The actual content of the inner children is dynamic - so I can't give them a set width.
.outer {
border: 1px solid black;
width: 100px;
overflow-x: auto;
white-space: nowrap;
}
.inner {
border-bottom: 1px solid blue;
background-color: red;
}
<div class="outer">
<div class="inner">This is is row number 1</div>
<div class="inner">This is is row number 2</div>
<div class="inner">This is is row number 3</div>
</div>
The problem is that it doesn't - as can be seen in this fiddle, the background and border only stretch to the defined width of the parent.
How can I make the width of the children stretch to the entire scrolled area?

The <div> element is a block element and its width will be 100% of its parent. Making it an inline element will force the width of the div to stretch with its text content, but sadly it will need extra markup to make it break into rows (<br/> tags).
The way I manage to do it for your case is by making the inner container display: table; that way the element will behave as table and it'll stretch its width to match its inner text.
.outer {
border: 1px solid black;
width: 100px;
overflow-x: auto;
white-space: nowrap;
}
.inner {
display: table;
border-bottom: 1px solid blue;
background-color: red;
}
Here's a demo: jsFiddle

If you give width bigger than the outer to the inner, you'll have the result.
Try to give width: 200px; or 150%; and let me know...
.outer {
border: 1px solid black;
width: 100px;
overflow-x: auto;
white-space: nowrap;
display:flex;
flex-wrap:wrap;
justify-content:strech;
}
.inner {
border-bottom: 1px solid blue;
background-color: blue;
}
<div class="outer">
<div class="container-inner">
<div class="inner">This is is row number 1</div>
<div class="inner">This is is row number 2</div>
<div class="inner">This is is rowfddfssdfdfs number 3</div>
</div>
</div>
This is ok ?

It is easy with jquery. Using jquery scrollWidth you will the scroll width you can simply set that as width to inner div. So this will give you scroll width $('.outer')[0].scrollWidth) simply set this as width of inner div.
$(".inner").css('width', $('.outer')[0].scrollWidth);
.outer {
border: 1px solid black;
width: 100px;
overflow-x: auto;
white-space: nowrap;
}
.inner {
border-bottom: 1px solid blue;
background-color: red;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div class="outer">
<div class="inner">This is is row number 1</div>
<div class="inner">This is is row number 2This is is row number 3 </div>
<div class="inner">This is is row number 3 This is is row number 3 This is is row number 3 </div>
</div>

html: introducing an inner wrapper div
<div class="outer">
<div class="innerwrapper">
<div class="inner">This is is row number 1</div>
<div class="inner">This is is row number 2</div>
<div class="inner">This is is row number 3 This is is row number 3 This is is row number 3</div>
</div>
</div>
css:
.outer {
border: 1px solid black;
width: 100px;
overflow-x: auto;
white-space: nowrap;
display:flex;
flex-wrap:wrap;
justify-content:stretch;
}
.innerwrapper {
/* silence is golden */
}
.inner {
border-bottom: 1px solid blue;
background-color: red;
}
linky: https://jsfiddle.net/sL0rkjgm/29/

Related

Making columns the same height while contatining object taking all available space

Here is CSS playground: https://www.bootply.com/HHeQ3n0EbT
<div class="container">
<div class="row">
<div class="col ltg-column-parent">
Column
<div class="ltg-column-inside">
<div class="task-box">
content
</div>
<div class="task-box">
content
</div>
<div class="task-box">
content
</div>
</div>
<div class="task-table-bottom-buttons">
<button>+</button>
</div>
</div>
<div class="col ltg-column-parent">
Column
<div class="ltg-column-inside">
<div class="task-box">
content
</div>
</div>
<div class="task-table-bottom-buttons">
<button>+</button>
</div>
</div>
<div class="col ltg-column-parent">
Column
<div class="ltg-column-inside">
<div class="task-box">
content
</div>
</div>
<div class="task-table-bottom-buttons">
<button>+</button>
</div>
</div>
</div>
</div>
CSS:
.ltg-column-parent {
margin: 1px;
padding: 0;
background-color: lightgray;
padding-bottom: 1rem;
}
.ltg-column-inside {
background-color: rgb(151, 151, 151);
height: 100%;
/* border: white solid 1px; */
}
.task-box {
width: 10rem;
height: 6rem;
color: black;
background-color: white;
border: 1px solid lightgray;
border-left: 7px solid yellow;
padding-left: 1rem;
padding-top: 1rem;
display: inline-block;
}
.task-table-bottom-buttons {
position: relative;
bottom: 0px;
}
I'm making some kind of kanban table, where you can create tasks (white boxes with yellow border) and drag&drop them between columns.
Column is a box with lightgray background.
Darkgray div is where I can put/drag task boxes
Now, there are a few problems here. Darkgray box with "+" button are moving outside its parent lightgray div. This is because darkgray div is set to height: 100% as I want it to take all available space in column. If I delete that, darkgray div shrinks and columns have less space that tasks can be placed.
I want to accomplish a few things:
columns have to have the same height if they lay next to each other (if screen is smaller and columns are placed below, then the same height is not necessary)
"+" button have to be sticked to the bottom of the last task (or entire column if it will be easier)
darkgray div should be as big as possible without artificially chaging height of column (as user have to have place to drop tasks).
What should I do to make it look correctly?
This solution works for me:
.ltg-column-inside {
background-color: rgb(151, 151, 151);
border: white solid 1px;
display: flex;
overflow: auto;
height: auto;
}
use dispaly:flex to .ltg-column-inside
.ltg-column-inside{
dispaly:flex
}
if you don't want the grey section remove this:
.task-box{
height: 6rem;
}

About float in CSS

I'm having some troubles with the 'float' in css.
I have a wrapper div with a width of 960px.I want to add 5 child-div in it with the width of 960 / 5 = 192px. And this is what I've got:
https://i.stack.imgur.com/R6bsw.png
This is my lines of code. Can anyone tell me what's wrong with them?
HTML
#overall-info h1 {
text-align: center;
padding: 1em;
}
.box {
width: 192px;
height: 192px;
border: 1px solid green;
background-color: aquamarine;
float: left;
}
<section id="overall-info">
<div class="container">
<h1>Info</h1>
<div class="box">
</div>
<div class="box">
</div>
<div class="box">
</div>
<div class="box">
</div>
<div class="box">
</div>
</div>
</section>
For each sub-boxes you have 1px of border which successively adds up to the total width.
So the container should have a width of (192+1+1)*5 = 970 and not 960 if you want all your sub-boxes to be contained on one line. You can also suppress the border or use a sub-box width of 190 (190+1+1=192)
Furthermore keeping 1px of free width space for the container can also help
About box-sizing:border-box:
The width and height properties (and min/max properties) includes content, padding and border, but not the margin.
For Fix it:
So, you must use box-sizing:border-box; because width of .box(192px) includes .box border width (1px for border-left and 1px for border-right).
if you don't add box-sizing:border-box,it will be added 2px(1px for border-left and 1px for border-right) to each .box,in the other words width .box gets width (192px + 2px = 194px).
* {
box-sizing:border-box;
}
* {
box-sizing: border-box;
}
.container {
width: 960px;
}
#overall-info h1 {
text-align: center;
padding: 1em;
}
.box {
width: 192px;
height: 192px;
border: 1px solid green;
background-color: aquamarine;
float: left;
}
<section id="overall-info">
<div class="container">
<h1>Info</h1>
<div class="box"></div>
<div class="box"></div>
<div class="box"></div>
<div class="box"></div>
<div class="box"></div>
</div>
</section>
Your 1px borders are adding-up to the width space of your boxes.
set in your css:
* {box-sizing: border-box; }
you can also use percentages widths btw to welcome yourself into the responsive era ;)
.box {
float: left;
box-sizing: border-box;
background: aquamarine;
border: 1px solid green;
width: 20%;
height: 100px;
}
https://developer.mozilla.org/en-US/docs/Web/CSS/box-sizing
in which box-sizing set to border-box is used to account borders, paddings and width into the inner box model width of the targeted element.
If you plan to support IE7 (which is not needed today) than you'll have to manually subtract the border-width from the element width.

Aligning DIVs vertically

How do I align the red box with the gray box vertically?
http://jsfiddle.net/sLZzK/1/
I need several box combinations like that on my page, which is why I cannot simply push the red box up manually. A negative margin won't work either, since I do not know in advance how much content will be in the gray box. And the red box must overlap other page content, hence the absolute positioning. (http://jsfiddle.net/xMm82/)
CSS:
body {
padding: 0;
margin: 10px;
}
.left_div {
margin-bottom: 10px;
width: 300px;
height: 70px;
border: 1px solid gray;
}
.right_div {
position: absolute;
border: 1px solid red;
left: 311px;
width: 200px;
height: 200px;
}
HTML:
<div class="left_div">gray box
<div class="right_div">red box</div>
</div>
Why are you using absolute positioning for such structure? In the case the better solution is to use float: left for each div. If you want to have two divs aligned vertically use display: table-cell rule. Here it is:
FIDDLE
UPDATE: Try to use this:
FIDDLE
what I've understood is you want gray box on top of Red box:
first of all wrap them in a parent div.
set the width of wrapper to desirable width.
set width to 100%(both red and gray) and you are done !! (fiddle)
If you want to arrange them horizontally:
left_div will be wrapper
it will contain 2 child div's
left one will have content and right one will be red box.(fiddle)
I would do it this way:
HTML:
<div class="container">
<div class="left_div">gray box</div>
<div class="right_div yellow">red box</div>
<div class="clr"></div>
</div>
CSS:
.container:not(:last-child){margin-bottom: 10px;}
.left_div,.right_div{float:left;}
.clr{clear:both;}
Fiddle here.
use float to arrange vertically and clear:both to prevent any errors
here's the corrected one
.left{
float:left;
width: 300px;
}
.right{
float:left;
width: 200px;
}
.left_div {
width: 300px;
height: 70px;
border: 1px solid gray;
}
.right_div {
border: 1px solid red;
width: 200px;
height: 200px;
}
<div class="left">
<div class="left_div">
</div>
</div>
<div class="right">
<div class="right_div">
</div>
</div>
<div style="clear:both"></div>
http://jsfiddle.net/sLZzK/8/
There you go: http://jsfiddle.net/sLZzK/14/
HTML:
<div class="wrapper">
<div class="left_div">gray box</div>
<div class="right_div">red box</div>
</div>
CSS:
.wrapper {
border: 1px solid #369;
padding: 10px;
}
.wrapper > div {
display: inline-block;
vertical-align: middle;
}
You might also want to read about flexbox which will give you a similar and more consistent result, however it's not fully supported on various browsers yet.

Css: overflow: auto + specified width

Example: http://jsfiddle.net/5VCfm/2/embedded/result/
.container {
position: absolute;
border: 1px solid red;
max-width: 90%;
margin-bottom: 20px
}
.container + .container {
top: 260px;
}
.content-container {
border: 1px solid green;
max-height: 200px;
overflow: auto;
padding: 15px;
}
.content-wrap {
border: 1px solid navy;
}
.content {
border: 1px solid red;
padding: 10px;
}
html
<div class="container">
<div class="content-container">
<div class="content-wrap">
<div class="content">
<h2>No width</h2>
large content see http://jsfiddle.net/5VCfm/2/embedded/result/
</div>
</div>
</div>
</div>
<div class="container">
<div class="content-container">
<div class="content-wrap">
<div class="content" style="width:300px">
<h2>Width 300px</h2>
large content see http://jsfiddle.net/5VCfm/2/embedded/result/
</div>
</div>
</div>
</div>
If width of element inside container is specified, he takes off the edge of the parent creating a horizontal scrolling. What is most characteristic behaves in Mozilla and Chrome. But Opera and IE show all right.
How to solve the problem? Is a bug?
The parent container has a max-width:90%, means it will become smaller as much as it can but it will never surpass 90% of the viewport width.
When this 90% is smaller than 300px (child), the horizontal scroll bar is being created, this process is completely normal, you just have to realize that the child has a fixed width, it will not get smaller.
Use max-width:300px; on the .content, this will allow it to have a 300px width IF IT CAN, but when the parent (90%) is less, it will become tighter.
DEMO

Two Divs on the same row and center align both of them

I have two divs like this
<div style="border:1px solid #000; float:left">Div 1</div>
<div style="border:1px solid red; float:left">Div 2</div>
I want them to display on the same row, so I used float:left.
I want both of them to be at center of the page as well, so I tried to wrap them with another div like this
<div style="width:100%; margin:0px auto;">
<div style="border:1px solid #000; float:left">Div 1</div>
<div style="border:1px solid red; float:left">Div 2</div>
</div>
But it doesn't work. If I change the code to this
<div style="width:100%; margin-left:50%; margin-right:50%">
<div style="border:1px solid #000; float:left">Div 1</div>
<div style="border:1px solid red; float:left">Div 2</div>
</div>
then it's going to the center, but the horizontal scrollbar is there and it seems like it's not really centered as well.
Can you please kindly suggest to me how can I achieve this? Thanks.
Edit: I want the inner div (Div 1 and Div 2) to be center align as well.
You could do this
<div style="text-align:center;">
<div style="border:1px solid #000; display:inline-block;">Div 1</div>
<div style="border:1px solid red; display:inline-block;">Div 2</div>
</div>
http://jsfiddle.net/jasongennaro/MZrym/
wrap it in a div with text-align:center;
give the innder divs a display:inline-block; instead of a float
Best also to put that css in a stylesheet.
Could this do for you? Check my JSFiddle
And the code:
HTML
<div class="container">
<div class="div1">Div 1</div>
<div class="div2">Div 2</div>
</div>
CSS
div.container {
background-color: #FF0000;
margin: auto;
width: 304px;
}
div.div1 {
border: 1px solid #000;
float: left;
width: 150px;
}
div.div2 {
border: 1px solid red;
float: left;
width: 150px;
}
both floated divs need to have a width!
set 50% of width to both and it works.
BTW, the outer div, with its margin: 0 auto will only center itself not the ones inside.
Align to the center, using display: inline-block and text-align: center.
.outerdiv
{
height:100px;
width:500px;
background: red;
margin: 0 auto;
text-align: center;
}
.innerdiv
{
height:40px;
width: 100px;
margin: 2px;
box-sizing: border-box;
background: green;
display: inline-block;
}
<div class="outerdiv">
<div class="innerdiv"></div>
<div class="innerdiv"></div>
</div>
Align to the center using display: flex and justify-content: center
.outerdiv
{
height:100px;
width:500px;
background: red;
display: flex;
flex-direction: row;
justify-content: center;
}
.innerdiv
{
height:40px;
width: 100px;
margin: 2px;
box-sizing: border-box;
background: green;
}
<div class="outerdiv">
<div class="innerdiv"></div>
<div class="innerdiv"></div>
</div>
Align to the center vertically and horizontally using display: flex, justify-content: center and align-items:center.
.outerdiv
{
height:100px;
width:500px;
background: red;
display: flex;
flex-direction: row;
justify-content: center;
align-items:center;
}
.innerdiv
{
height:40px;
width: 100px;
margin: 2px;
box-sizing: border-box;
background: green;
}
<div class="outerdiv">
<div class="innerdiv"></div>
<div class="innerdiv"></div>
</div>
I would vote against display: inline-block since its not supported across browsers, IE < 8 specifically.
.wrapper {
width:500px; /* Adjust to a total width of both .left and .right */
margin: 0 auto;
}
.left {
float: left;
width: 49%; /* Not 50% because of 1px border. */
border: 1px solid #000;
}
.right {
float: right;
width: 49%; /* Not 50% because of 1px border. */
border: 1px solid #F00;
}
<div class="wrapper">
<div class="left">Div 1</div>
<div class="right">Div 2</div>
</div>
EDIT: If no spacing between the cells is desired just change both .left and .right to use float: left;
Better way till now:
If you give display:inline-block; to inner divs then child elements of inner divs will also get this property and disturb alignment of inner divs.
Better way is to use two different classes for inner divs with width, margin and float.
Best way till now:
Use flexbox.
http://css-tricks.com/snippets/css/a-guide-to-flexbox/
Please take a look on flex it will help you make things right,
on the main div set css display :flex
the div's that inside set css: flex:1 1 auto;
attached jsfiddle link as example enjoy :)
https://jsfiddle.net/hodca/v1uLsxbg/

Resources