Flexbox, boxes inside boxes [duplicate] - html

This question already has answers here:
In CSS Flexbox, why are there no "justify-items" and "justify-self" properties?
(6 answers)
Closed 2 years ago.
I am busy with a very simple thing of CSS. Let´s say I have four squares and inside each another square. I want my layout to look something like this:
But it looks like this:
But I can't get it right. The four squares are grouped in one element and display is set to inline-block. I want to move the small boxes inside their parents and I think I should do it with "display: flex" and "justify-content: flex-end" for example as in the code below. My code in HTML and CSS look like this.
{
box-sizing: border-box;
margin: 0;
padding: 0;
}
body {
background-color: honeydew;
margin: 15px;
width: 100%;
}
.big {
height: 200px;
width: 200px;
display: flex;
}
.small {
height: 100px;
width: 100px;
}
.block {
display: inline-block;
}
#small-1 {
display: flex;
justify-content: flex-end;
align-items: flex-end;
}
#small-2 {
display: flex;
justify-content: flex-end;
align-items: flex-end;
}
#small-3 {
display: flex;
justify-content: flex-end;
align-items: flex-start;
}
#small-4 {
display: flex;
justify-content: flex-start;
align-items: flex-start;
}
<!doctype html>
<html>
<head>
<link rel="stylesheet" href="stylesheet.css">
<title>Boxes</title>
</head>
<body>
<div class="block" id="block">
<div class="big" style="background-color: grey">
<div class="small" id="small-1" style="background-color:orange"></div>
</div>
</div>
<div class="block" id="block">
<div class="big" style="background-color: black">
<div class="small" id="small-2" style="background-color: yellow"></div>
</div>
</div>
<div class="block" id="block">
<div class="big" style="background-color: blue">
<div class="small" id="small-3" style="background-color: green"></div>
</div>
</div>
<div class="block" id="block">
<div class="big" style="background-color: purple">
<div class="small" id="small-4" style="background-color: pink"></div>
</div>
</div>
</body>
</html>
Can anybody help me with this? It seems pretty obvious and basic, but somehow doesn't work.

Edits:
div.block:nth-child(1) > div:nth-child(1) {
align-items: start; // to vertically align to start
}
div.block:nth-child(4) > div:nth-child(1) {
justify-content: start;// to horizontally align to start
align-items: start; // to vertically align to start
}
div.block:nth-child(3) > div:nth-child(1) {
justify-content: start; // to horizontally align to start
}
body{
display:flex;
}
justify-content:
start: items are packed toward the start of the writing-mode direction.end: items are packed toward the end of the writing-mode direction.
align-items:
flex-start / start / self-start: items are placed at the start of the cross axis. The difference between these is subtle, and is about respecting the flex-direction rules or the writing-mode rules.
flex-end / end / self-end: items are placed at the end of the cross axis. The difference again is subtle and is about respecting flex-direction rules vs. writing-mode rules.
A Complete Guide to Flexbox
CodePen Demo
* {
box-sizing: border-box;
margin: 0;
padding: 0;
}
body {
background-color: honeydew;
margin: 15px;
width: 100%;
display: flex;
}
.big {
height: 200px;
width: 200px;
display: flex;
justify-content: flex-end;
align-items: flex-end;
}
.small {
height: 100px;
width: 100px;
}
.block {
display: inline-block;
}
div.block:nth-child(1) > div:nth-child(1) {
align-items: start;
}
div.block:nth-child(4) > div:nth-child(1) {
justify-content: start;
align-items: start;
}
div.block:nth-child(3) > div:nth-child(1) {
justify-content: start;
}
<!doctype html>
<html>
<body>
<div class="block" id="block">
<div class="big" style="background-color: grey">
<div class="small" id="small-1" style="background-color:orange"></div>
</div>
</div>
<div class="block" id="block">
<div class="big" style="background-color: black">
<div class="small" id="small-2" style="background-color: yellow"></div>
</div>
</div>
<div class="block" id="block">
<div class="big" style="background-color: blue">
<div class="small" id="small-3" style="background-color: green"></div>
</div>
</div>
<div class="block" id="block">
<div class="big" style="background-color: purple">
<div class="small" id="small-4" style="background-color: pink"></div>
</div>
</div>
</body>
</html>

justify-content and align-items should be placed on the container level, so the #small's don't have to be that props, but .big.
I create a pen as example:
https://codepen.io/alecell-the-lessful/pen/qBZeBEx
[EDIT]
I just realise that I don't answer your question, and maybe that link helps you: In CSS Flexbox, why are there no "justify-items" and "justify-self" properties?
The point is that you should use item level selectors such as align-self and margin to reach the desired behavior.
As above I provide a pen to example: https://codepen.io/alecell-the-lessful/pen/zYqgYvd

Related

Align problem when I try to center and align items with flex

I just came across this problem. Everything seems ok, but I don't understand where is the problem. Centering and aligning items at the same time are not good?
Only I wanted to write down 3 div in the column direction. I can not change the structure because I will try something with this structure.
This is how does it look like. https://codepen.io/vortovor/pen/ExXZMzR
.col {
display: flex;
flex-direction: column;
justify-content: center;
align-items: center;
background: pink;
}
.col>div {
background: #ddd;
<div class="row">
<div class="col">
<div class="top">
<div>Hello</div>
<div>I'm</div>
</div>
<div class="bottom">
<div>Here</div>
</div>
</div>
</div>
You are missing the height property in your .col add to your code
.col{
height: 500px;
border: 1px black solid;
}
so can see that is working fine:
.col {
height: 500px;
border: 1px black solid;
}
/* orginal CSS */
.col {
display: flex;
flex-direction: column;
justify-content: center;
align-items: center;
}
<div class="row">
<div class="col">
<div class="top">
<div>Hello</div>
<div>I'm</div>
</div>
<div class="bottom">
<div>Here</div>
</div>
</div>
</div>
the code is fine, what happens is the size of the content of your divs.
if you add a class to all your word divs
.a {
text-align: center;
border: 1px red solid;
width: 100px;
}
at the moment you have the width of each word which are different and you alignment is centre, therefore it looks like:
one
onelong
oneme

Align button to the right of sibling using flex

I am really struggling to understand how flex works, my aim in this pen
https://codepen.io/Esperteyu/pen/WMExEj
is to align the "Click Me Outside of the IFrame" button to the right limit of the iframe but in the "next line".
I can align it to it but just when I don't center the iframe container, if that makes sense. And ideally I would like the iframe centered and the button aligned to its right.
The html is:
<div class="container">
<div class="container-center ">
<div class="center ">
<iframe srcdoc="<html><body><h2 style='text-align:center'>This is the iframe</h2><input type='button' value='Click Me Inside the iframe' style='float: right;'></body></html>">
</iframe>
</div>
</div>
<div class="container-right">
<div class="right">
<div>
<input type="button" value="Click Me Outside of the iframe">
</div>
</div>
</div>
</div>
The css is:
.container {
background:red;
}
.container-center {
display:flex;
justify-content: center;
flex-direction: row;
width:100%;
}
.container-right {
display:flex;
justify-content: flex-end;
flex-direction: row;
}
.center {
display: flex;
background: lightblue;
}
.center iframe{
width: 100%;
}
Any help?
Thanks
To have the container-center centered in its parent, and as Flexbox doesn't have a property of its own to accomplish that, you could to take some help of e.g. a pseudo, to match the right element, combined with making the container a flex container.
.container {
background:red;
display:flex;
justify-content: center;
}
.container-right,
.container::before {
content: '';
flex: 1;
}
With the flex: 1, the pseudo and the container-right will take equal of the space left, and push the container-center to the middle, and with the align-items on the container-right you control the vertical alignment of its children.
If you check this codepen, where I added a border on the pseudo/right element, you'll see what is going on more clear.
Updated codepen
Stack snippet
.container {
background:red;
display:flex;
justify-content: center;
}
.container-right,
.container::before {
content: '';
flex: 1;
}
.container-center {
}
.container-right {
display:flex;
align-items: flex-end; /* align children vertically */
overflow: hidden;
}
.center {
display: flex;
background: lightblue;
}
.center iframe{
width: 100%;
}
<div class="container">
<div class="container-center ">
<div class="center ">
<iframe srcdoc="<html><body><h2 style='text-align:center'>This is the iframe</h2><input type='button' value='Click Me Inside the iframe' style='float: right;'></body></html>">
</iframe>
</div>
</div>
<div class="container-right">
<div class="right">
<div>
<input type="button" value="Click Me Outside of the iframe">
</div>
</div>
</div>
</div>
Updated based on a comment.
If you mean that the button outside the frame should right align on a row of its own, you need an extra wrapper to accomplish that.
Updated codepen
Stack snippet
.container {
background:red;
display:flex;
justify-content: center;
}
.container-right {
display:flex;
justify-content: flex-end;
}
.center {
display: flex;
background: lightblue;
}
.center iframe{
width: 100%;
}
<div class="container">
<div class="wrapper">
<div class="container-center ">
<div class="center ">
<iframe srcdoc="<html><body><h2 style='text-align:center'>This is the iframe</h2><input type='button' value='Click Me Inside the iframe' style='float: right;'></body></html>">
</iframe>
</div>
</div>
<div class="container-right">
<div class="right">
<div>
<input type="button" value="Click Me Outside of the iframe">
</div>
</div>
</div>
</div>
</div>
As a note, the last sample's code could be simplified, to this:
https://codepen.io/anon/pen/ddzNgy

Create a section at bottom of a Bootstrap container

.force-to-bottom {
background: grey;
align-self: flex-end;
width: 100%;
margin: 0;
text-align: center;
height:200px;
}
#story {
text-align: center;
display: flex;
flex-direction: column;
padding:0;
justify-content: space-between;
}
.row {
display: flex;
}
html, body, .row, .container {
height: 100%;
}
.container {
background: pink;
}
<div class="container fill-height">
<div class="row">
<div id="story" class="col-lg-12">
<h1 style="text-align:center;">Demo</h1>
<div class="row force-to-bottom text-center">
<p>It's supposed to stay at the bottom of this section n goes across the whole screen</p>
</div>
</div>
</div>
</div>
I have a single page with multiple containers. I'm trying to create a section like a footer at the bottom of one of those containers. That footer should stay at the bottom of that section, but not at the bottom of the entire page. I've tried to add a force-to-bottom div but that did not work. How should I achieve this? Many thanks!
<div id="containerOne" class="container fill-height">
<div class="row force-to-bottom text-center">
<p>this is the footer of that one div</p>
</div>
</div>
<div id="containerTwo" class="container fill-height">
</div>
You can use flexbox to achieve this easily.
Make the #story flex by giving it display: flex property along with flex-direction: column to align its children below each other vertically.
Next to the .force-to-bottom children simply give the property align-self: flex-end to float to the bottom of its respective containers.
html, body, .row, #story, .container {
height: 100%;
}
.row {
display: flex;
}
.container {
background: pink;
}
.force-to-bottom {
background: grey;
align-self: flex-end;
width: 100%;
height: 50px;
margin: 0;
justify-content: center;
align-items: center;
}
#story {
display: flex;
flex-direction: column;
justify-content: space-between;
padding: 0;
}
<div id="payContainer" class="container fill-height">
<div class="row">
<div id="story" class="col-lg-12">
<h1 style="text-align:center;">Demo</h1>
<div class="row force-to-bottom text-center">
<p>It's supposed to stay at the bottom of this section n goes across the whole screen</p>
</div>
</div>
</div>
</div>
Update after OP updated code:
Like I mentioned, for the above updated HTML structure you have. You need to apply display: flex to the #story div instead(not the .container). Also add another property flex-direction: column to make its children elements align below each other. .force-to-bottom styles remain the same.

Vertically justify content

Hopefully this isn't an unsolved task, but I'm trying to vertically justify an unknown (ish) number of divs inside of a container.
Each div should be equal distances from each other, and, additionally, the same distance from the edges. (Assuming the last part can be accomplished using ghost elements before and after)
The divs will each fill the width of the container, and the container is a set height, but the number of elements inside the container is unknown.
I'm assuming it can be done using Flexbox to some degree, but have been unsuccessful in my attempts thus far.
Yep, flexbox is the simplest way to do it.
On the container element:
.container {
display: flex;
flex-direction: column;
justify-content: space-between;
}
On the child elements:
.container div {
flex: 1;
width: 100%
}
For the spacing between the elements, just add padding to the container and bottom margins to the children.
The style would look like this:
.container {
/* Same as above, and */
padding: 20px;
}
.container div {
/* Same as above, and */
margin-bottom: 20px;
}
.container div:last-of-type{
margin-bottom: 0;
/* So that spacing is even at bottom and top of container */
}
(I was typing this when you posted your answer, so I put it up anyway)
Fiddle
I use justify-content:space-evenly.
HTML:
div.container {
display: flex;
}
div.one_item_container {
display: flex;
flex-direction: column;
justify-content: space-evenly;
}
<div class="container">
<div class="one_item_container">
<img height="30" src="hello.jpeg" style="background-color:lightblue;" />
</div>
<div class="one_item_container">
<img height="50" src="hello2.jpeg" style="background-color:lightblue;" />
</div>
<div class="one_item_container">
<img height="40" src="hello2.jpeg" style="background-color:lightblue;" />
</div>
</div>
As usual, no matter how long I search, I find the answer only immediately after I ask the question. :D
For those curious, or for my own future reference: Flexbox's justify DOES work, you just need a few more options:
HTML:
<div id="outer-container">
<div class="inner-element"></div>
<div class="inner-element"></div>
<div class="inner-element"></div>
<div class="inner-element"></div>
<div class="inner-element"></div>
<div class="inner-element"></div>
<div class="inner-element"></div>
</div>
CSS:
#outer-container {
height: 250px;
width: 200px;
background: red;
display: flex;
justify-content: space-around;
flex-direction: column;
}
.inner-element {
width: 200px;
height: 10px;
background: blue;
}
https://css-tricks.com/almanac/properties/j/justify-content/
https://jsfiddle.net/WW3bh/

Flexbox in Firefox: Items are not lined up properly [duplicate]

This question already has answers here:
Absolutely positioned flex item is not removed from the normal flow in IE11
(4 answers)
Closed 6 years ago.
This http://jsfiddle.net/7ra5oL77/ should line up the orange dots horizontally with the text underneath.
The relevant items are:
<div class="draggable ui-widget-content"></div>
and
<div class="item">60°C</div>
This works in Chrome and Edge, but Firefox seem to not use the full width and there is a too big white space on the right side.
Can anyone help me?
The issue that I see is that firefox is recognizing your div.lines as items within the flexbox even though the are position absolute. If you pull them outside of the container or delete them altogether (I don't see their purpose), then you should be fine.
The absolute positioned .lines mess up with the space-around alignment:
#graph-containment-wrapper {
justify-content: space-around;
}
This seems a bug, because the spec says
An absolutely-positioned child of a flex container does not
participate in flex layout.
The justify-content property aligns flex items along the
main axis of the current line of the flex container.
As a workaround, you can use auto margins to achieve the same effect without the interference of absolutely positioned elements:
.draggable {
margin: 0 auto;
}
.lines {
padding: 0px;
margin: 0px;
height: 1px;
background-color: orange;
position: absolute;
}
.draggable {
width: 30px;
height: 30px;
background: orange;
border-radius: 30px;
cursor: n-resize;
top: 200px;
z-index: 1;
border: 0px;
display: flex;
justify-content: center;
align-items: center;
color: white;
margin: 0 auto;
}
.x-axis {
display: flex;
justify-content: space-around;
width: 100%
}
#graph-containment-wrapper {
display: flex;
height: 20rem;
background-color: white;
}
.graph {
-webkit-user-select: none;
}
.draw-area{
width: 100%
}
.hlines{
background-color: lightgray;
width:100%;
height: 1px;
display: flex;
}
.hlines-container{
display:flex;
min-height: 100%;
justify-content: space-between;
flex-direction: column;
padding: 15px;
height: 20rem;
margin-top: -20rem
}
<div class="graph">
<div class="draw-area">
<div id="graph-containment-wrapper">
<div class="draggable ui-widget-content"></div>
<div class="draggable ui-widget-content"> </div>
<div class="draggable ui-widget-content"> </div>
<div class="draggable ui-widget-content"> </div>
<div class="draggable ui-widget-content"> </div>
<div class="lines" id="myline0"></div>
<div class="lines" id="myline1"></div>
<div class="lines" id="myline2"></div>
<div class="lines" id="myline3"></div>
</div>
<div class="hlines-container">
<div class="hlines"></div>
<div class="hlines"></div>
<div class="hlines"></div>
<div class="hlines"></div>
<div class="hlines"></div>
<div class="hlines"></div>
</div>
</div>
<div class="x-axis">
<div class="item">20°C</div>
<div class="item">30°C</div>
<div class="item">40°C</div>
<div class="item">50°C</div>
<div class="item">60°C</div>
</div>
</div>