How do I divide blocks in my page with flexbox? - html

I'm facing this problem where I want to have a header, sidebar and content with flexbox. I can't get to a solution to divide these 3 childs. I've been trying to use flex-grow and flex-direction:row but I'm having a problem.
Image of the website
How I want it to be
<style>
.parent {
* {
box-sizing: border-box;
margin: 0;
padding: 0;
}
height: 100vh;
border: 20px solid black;
display: flex;
flex-direction: column;
}
.header {
width: 200px;
height: 200px;
background: cornflowerblue;
}
.side {
width: 200px;
height: 200px;
background: rgb(219, 133, 133);
}
.content {
width: 200px;
height: 200px;
background: rgb(115, 202, 180);
}
.text {
display: flex;
flex-direction: row;
justify-content: center;
align-items: center;
height: 190px;
color: #fff;
}
</style>
<div class="parent">
<div class="header">
<h2 class="text">Header</h2>
</div>
<div class="side">
<h2 class="text">Side</h2>
</div>
<div class="content">
<h2 class="text">Content</h2>
</div>
</div>

You need to create two containers, one for all your elements and one for your header and content.
<div class="parent"> <!-- Container 1 -->
<div class="side">
<h2 class="text">Side</h2>
</div>
<div class="container"> <!-- Container 2 -->
<div class="header">
<h2 class="text">Header</h2>
</div>
<div class="content">
<h2 class="text">Content</h2>
</div>
</div>
</div>
Then, you can treat each container as a separate flex-box. the parent will have a flex-direction: row; and the container will have flex-direction: column;.
You also want to set values in percentages, not absolute values as you have right now (200px, 20rem..).
.parent {
box-sizing: border-box;
margin: 0;
padding: 0;
height: 100vh;
border: 20px solid black;
display: flex;
flex-direction: row;
}
.header {
height: 30%;
background: cornflowerblue;
}
.side {
width: 30%;
height: 100%;
background: rgb(219, 133, 133);
}
.content {
height: 70%;
background: rgb(115, 202, 180);
}
.text {
display: flex;
flex-direction: row;
justify-content: center;
align-items: center;
height: 190px;
color: #fff;
}
.container {
display: flex;
flex-direction: column;
width: 70%;
height: 100%;
}
JSFiddle
Images to illustrate the separation:

You have to wrap your header & content section inside another div. Something like this below example. However, The best way to achieve this layout is using a CSS grid. Here is the complete CSS grid guide
.parent {
display: flex;
height: 100vh;
background: #000;
padding: 5px;
margin: 0;
}
.side {
border: 1px solid #000;
width: 30vw;
display: flex;
justify-content: center;
align-items: center;
background: #fff;
margin-right: 5px;
}
.main-body {
border: 1px solid #000;
width: 70vw;
}
.header,
.content {
display: flex;
justify-content: center;
background: #fff;
}
.header {
height: 25vh;
margin-bottom: 5px;
}
.content {
align-items:center;
height: 70vh;
}
<div class="parent">
<div class="side">
<h2 class="text">Side</h2>
</div>
<div class="main-body">
<div class="header">
<h2 class="text">Header</h2>
</div>
<div class="content">
<h2 class="text">Content</h2>
</div>
</div>
</div>

I don't think that you deeply understand how flexbox work. You should read more about it. I advice you to read a book called CSS-in Depth. You can download it online from a website called Z-lib. Try to understand the code that I posted for you.
<style>
* {
box-sizing: border-box;
margin: 0;
padding: 0;
}
.parent {
height: 100vh;
border: 20px solid black;
display: flex;
background: pink;
}
.main {
display: flex;
backgound-color: green;
flex-direction: column;
flex: 2
}
.header {
background: cornflowerblue;
}
.side {
flex: 1;
background: rgb(219, 133, 133);
}
.content {
background: rgb(115, 202, 180);
flex: 1
}
.text {
display: flex;
flex-direction: row;
justify-content: center;
align-items: center;
height: 190px;
color: #fff;
}
</style>
<div class="parent">
<div class="side">
<h2 class="text">Side</h2>
</div>
<div class="main">
<div class="header">
<h2 class="text">Header</h2>
</div>
<div class="content">
<h2 class="text">Content</h2>
</div>
</div>
</div>

Related

How to align a div to top left on flexed div

I want to make a image (inside a div) to the most left of the bottom div and I don't how to do this.
For example I have this image
.container {
display: flex;
flex-direction: column;
align-items: center;
}
.applicationimage {
width: 60px;
height: 60px;
border-radius: 100%;
}
.settings {
display: flex;
width: 80%;
height: 40rem;
background-color: white;
align-self: center;
}
<main>
<div class="container">
<div class="applicationinfo">
<img src="https://wallup.net/wp-content/uploads/2019/09/1667-beautiful-gray-cat-748x468.jpg" class="applicationimage">
</div>
<div class="settings">
<span>hi</span>
</div>
</div>
</main>
I'm new to html & css so I will appreciate your help making this image to the most left of his bottom div.
If you know the width of the div, it's easy. You can give the .applicationinfo element align-self: flex-start; and margin-left: 10%; (10% is calculated by this formula: (100% - widthOfDiv) / 2)
body {
background: black;
}
.container {
display: flex;
flex-direction: column;
align-items: center;
}
.applicationinfo {
align-self: flex-start;
margin-left: 10%;
}
.applicationimage {
width: 60px;
height: 60px;
border-radius: 100%;
}
.settings {
display: flex;
width: 80%;
height: 40rem;
background-color: white;
align-self: center;
}
<main>
<div class="container">
<div class="applicationinfo">
<img src="https://wallup.net/wp-content/uploads/2019/09/1667-beautiful-gray-cat-748x468.jpg" class="applicationimage">
</div>
<div class="settings">
<span>hi</span>
</div>
</div>
</main>
remove the flex direction, here's it
display: flex;
justify-items: flex-end;
align-items: flex-end;}
You can do it by positioning applicationinfo since you haven't styled it.
you can add parent position: relative; then child to absolute; then give child top: 0; left: 0;
.container {
display: flex;
height: 80vh;
flex-direction: column;
align-items: center;
justify-content: center;
align-items: center;
position: relative;
background: #222;
border: 1px solid yellow;
}
.applicationinfo {
width: 80%;
top: 0;
left: 0;
border: 1px solid green;
}
.applicationimage {
width: 60px;
height: 60px;
border-radius: 100%;
border: 1px solid blue;
}
.settings {
display: flex;
width: 80%;
height: 80%;
background-color: white;
align-self: center;
}
<div class="container">
<div class="applicationinfo">
<img src="https://wallup.net/wp-content/uploads/2019/09/1667-beautiful-gray-cat-748x468.jpg" class="applicationimage">
</div>
<div class="settings">
<span>hi</span>
</div>
</div>

How to expand a flexbox container to the end of the page? [duplicate]

This question already has answers here:
Fill remaining vertical space with CSS using display:flex
(6 answers)
Closed 9 months ago.
I'm trying to expand the content in the middle (main-box) to fit the whole page until it reaches the footer.
I've tried adding flex: 1 to it, making the height: 100% or even use flex-grow: 1 as it is a child of a flex item.
body {
display: flex;
flex: 1;
flex-direction: column;
border: solid black 10px;
}
.page {
display: flex;
flex-direction: column;
flex: 1;
}
header {
background-color: #2D3047;
color: #E0CA3C;
}
.container {
flex-grow: 1;
}
.buttons {
text-align: center;
}
.points {
display: flex;
justify-content: center;
gap: 10px;
}
.computer,
.player {
border: solid black 2px;
padding: 10px;
margin: 20px;
}
.result {
text-align: center;
border: solid black 2px;
margin: 0;
padding: 0;
width: auto;
}
footer {
background-color: #2D3047;
color: #E0CA3C;
justify-self: flex-end;
}
<div class="page">
<header>
<h1>Rock, Paper, Scissors</h1>
</header>
<div class="main-box">
<div class="buttons">
<button class="rock">Rock</button>
<button class="paper">Paper</button>
<button class="scissors">Scissors</button>
</div>
<div class="container">
<div class="points">
<div class="player-score">0</div>
<div class="computer-score">0</div>
</div>
<div class="result"></div>
</div>
</div>
<div class="footer">Copyright CAIFRA</div>
</div>
Codepen
I see you are using position absolute on footer class , in my opinion take a look i change it into a position relative. using position relative with bottom 0 , then it will work,
<div class="page">
<header>
<h1>Rock, Paper, Scissors</h1>
</header>
<div class="main-box">
<div class="buttons">
<button class="rock">Rock</button>
<button class="paper">Paper</button>
<button class="scissors">Scissors</button>
</div>
<div class="container">
<div class="points">
<div class="player-score">0</div>
<div class="computer-score">0</div>
</div>
<div class="result"></div>
</div>
</div>
<div class="footer">
Copyright CAIFRA
</div>
</div>
CSS CODE
body {
margin: 0;
padding: 0;
}
header {
text-align: center;
background-color: #2D3047;
color: #E0CA3C;
padding: 20px;
}
.page {
display: flex;
flex-direction: column;
flex: 1;
}
.main-box {
background-color: #93B7BE;
display: flex;
flex-direction: column;
justify-content: center;
flex-grow: 1;
}
.computer-score, .player-score {
border: 2px black solid;
width: 50px;
height: 50px;
display: flex;
justify-content: center;
align-items: center;
margin: 20px;
}
.points {
display: flex;
flex-direction: row;
align-items: center;
justify-content: center;
}
.result {
border: 2px black solid;
height: 50px;
width: 300px;
margin-left: auto;
margin-bottom: 20px;
margin-right: auto;
display: flex;
align-items: center;
justify-content: center;
}
.buttons {
display: flex;
align-items: center;
justify-content: center;
gap: 20px;
padding-top: 30px;
}
.footer {
text-align: center;
background-color: #2D3047;
color: #E0CA3C;
padding: 10px;
position: relative;
bottom: 0;
left: 0;
width: 100%;
}
Maybe you can add 100vh on your container and see if this is what you want. Let me know
html {height: 99.1%;}
body {
flex-direction: column;
border: 10px solid black ;
height:99.1%;
margin: 0;
padding: 0;
}
.page {
display: flex;
flex-direction: column;
}
header {
background-color: #2D3047;
color: #E0CA3C;
}
.container {
height: 99.1% ;
bottom: 10px;
overflow: hidden;
}
.buttons {
text-align: center;
}
.points {
display: flex;
justify-content: center;
gap: 10px;
}
.computer,
.player {
border: solid black 2px;
padding: 10px;
margin: 20px;
}
.result {
text-align: center;
border: solid black 2px;
margin: 0;
padding: 0;
width: auto;
}
.footer {
background-color: #2D3047;
color: #E0CA3C;
bottom: 10px;
position: fixed;
width: 100%;
}
<body>
<div class="page">
<header>
<h1>Rock, Paper, Scissors</h1>
</header>
<div class="main-box">
<div class="buttons">
<button class="rock">Rock</button>
<button class="paper">Paper</button>
<button class="scissors">Scissors</button>
</div>
<div class="container">
<div class="points">
<div class="player-score">0</div>
<div class="computer-score">0</div>
</div>
<div class="result"></div>
</div>
</div>
<div class="footer">Copyright CAIFRA</div>
</div>
</body>
body {
margin: 0;
padding: 0;
}
header {
text-align: center;
background-color: #2D3047;
color: #E0CA3C;
padding: 20px;
}
.page {
display: flex;
flex-direction: column;
height: 90vh;
}
.main-box {
background-color: #93B7BE;
display: flex;
flex-direction: column;
justify-content: center;
flex-grow: 1;
height: 100vh;
}
.computer-score,
.player-score {
border: 2px black solid;
width: 50px;
height: 50px;
display: flex;
justify-content: center;
align-items: center;
margin: 20px;
}
.points {
display: flex;
flex-direction: row;
align-items: center;
justify-content: center;
}
.result {
border: 2px black solid;
height: 50px;
width: 300px;
margin-left: auto;
margin-bottom: 20px;
margin-right: auto;
display: flex;
align-items: center;
justify-content: center;
}
.buttons {
display: flex;
align-items: center;
justify-content: center;
gap: 20px;
padding-top: 30px;
}
.footer {
text-align: center;
background-color: #2D3047;
color: #E0CA3C;
padding: 10px;
position: absolute;
bottom: 0;
left: 0;
width: 100%;
}
<div class="page">
<header>
<h1>Rock, Paper, Scissors</h1>
</header>
<div class="main-box">
<div class="buttons">
<button class="rock">Rock</button>
<button class="paper">Paper</button>
<button class="scissors">Scissors</button>
</div>
<div class="container">
<div class="points">
<div class="player-score">0</div>
<div class="computer-score">0</div>
</div>
<div class="result"></div>
</div>
<div class="footer">
Copyright CAIFRA
</div>
</div>
</div>
Simply add body { min-height: 100vh; }, so it actually ahs the size of at least the viewport size. By default it will only have the height of the content.
body {
margin: 0;
box-sizing: border-box;
min-height: 100vh;
}
/* original CSS */
body {
display: flex;
flex-direction: column;
border: solid black 10px;
}
.page {
display: flex;
flex-direction: column;
}
header {
background-color: #2D3047;
color: #E0CA3C;
}
.container {
flex-grow: 1;
}
.buttons {
text-align: center;
}
.points {
display: flex;
justify-content: center;
gap: 10px;
}
.computer,
.player {
border: solid black 2px;
padding: 10px;
margin: 20px;
}
.result {
text-align: center;
border: solid black 2px;
margin: 0;
padding: 0;
width: auto;
}
footer {
background-color: #2D3047;
color: #E0CA3C;
}
<div class="page">
<header>
<h1>Rock, Paper, Scissors</h1>
</header>
<div class="main-box">
<div class="buttons">
<button class="rock">Rock</button>
<button class="paper">Paper</button>
<button class="scissors">Scissors</button>
</div>
<div class="container">
<div class="points">
<div class="player-score">0</div>
<div class="computer-score">0</div>
</div>
<div class="result"></div>
</div>
</div>
<div class="footer">Copyright CAIFRA</div>
</div>

Top of scrollable div not visible

I need to add a vertically scrollable div in my project. The div is a list of items with fixed height. I can't figure out why the top area of the div is not visible. Below is some sample code. As you can see, the first element of the list is not entirely visible.
html,
body {
height: 100%;
}
* {
box-sizing: border-box;
}
.main-container {
display: flex;
flex-direction: column;
align-items: center;
justify-content: center;
height: 100%;
background-image: linear-gradient(45deg, #85ffbd 0%, #fffb7d 100%);
}
.content {
width: 75%;
max-height: 500px;
background-color: white;
display: flex;
flex-direction: column;
align-items: center;
justify-content: center;
}
.post-list {
display: flex;
flex-direction: column;
align-items: center;
justify-content: center;
background-color: rgba(0, 0, 0, 0.03);
width: 95%;
border-radius: 5px;
overflow-y: scroll;
overflow-x: hidden;
position: relative;
}
.post-item {
border: 1px solid black;
width: 100%;
margin: 0.5rem;
}
.test {
height: 8rem;
background-color: rgba(255, 0, 0, 0.1);
width: 100%;
text-align: center;
}
<div class="main-container">
<div class="content">
<h1>Some list</h1>
<div class="post-list">
<div class="post-item"> <div class="test"> 1. some content </div> </div>
<div class="post-item"> <div class="test"> 2. some content </div> </div>
<div class="post-item"> <div class="test"> 3. some content </div> </div>
<div class="post-item"> <div class="test"> 4. some content </div> </div>
</div>
</div>
</div>
https://jsfiddle.net/1dphx94s/8/
Just remove justify-content: center in post-list it places all the content in the center of div and makes huge struggling which is not necessary in our case, you just need to center elements on X-axis, flex and align-items are enough
html,
body {
height: 100%;
}
* {
box-sizing: border-box;
}
.main-container {
display: flex;
flex-direction: column;
align-items: center;
justify-content: center;
height: 100%;
background-image: linear-gradient(45deg, #85ffbd 0%, #fffb7d 100%);
}
.content {
width: 75%;
max-height: 500px;
background-color: white;
display: flex;
flex-direction: column;
align-items: center;
justify-content: center;
}
.post-list {
display: flex;
flex-direction: column;
align-items: center;
/*justify-content: center;*/
background-color: rgba(0, 0, 0, 0.03);
width: 95%;
border-radius: 5px;
overflow-y: scroll;
overflow-x: hidden;
position: relative;
}
.post-item {
border: 1px solid black;
width: 100%;
margin: 0.5rem;
}
.test {
height: 8rem;
background-color: rgba(255, 0, 0, 0.1);
width: 100%;
text-align: center;
}
<div class="main-container">
<div class="content">
<h1>Some list</h1>
<div class="post-list">
<div class="post-item"> <div class="test"> 1. some content </div> </div>
<div class="post-item"> <div class="test"> 2. some content </div> </div>
<div class="post-item"> <div class="test"> 3. some content </div> </div>
<div class="post-item"> <div class="test"> 4. some content </div> </div>
</div>
</div>
</div>

How to make nested flex child scrollable

I have a list of messages (which is a flex child) in a container with unknown height and want to make them scrollable. But I cannot find a proper combination of flex-grow: 1, min-height: 0 and other flex tricks to make it working - message list is still bigger than its parent.
When I add overflow-y: auto to its parent - it works but this parent besides messages list includes some content which should not scroll.
Here's my example for this case: https://jsfiddle.net/ecbtrn58/2/
<div class="page">
<div class="messages-section">
<div class="header">Your messages</div>
<div class="content">
<img src="https://http.cat/100" width="70" height="50"/>
<div class="messages-list">
<div class="message">Hi.</div>
<div class="message">Hello.</div>
<div class="message">Good morning.</div>
<div class="message">Yo!</div>
</div>
</div>
</div>
</div>
.page {
background-color: #ddd;
width: 300px;
height: 300px;
.messages-section {
display: flex;
flex-direction: column;
width: 50%;
height: 100%;
background-color: #ccc;
.header {
background: #bbb;
padding: 5px;
}
.content {
display: flex;
flex-direction: column;
align-items: center;
padding: 5px;
.messages-list {
display: flex;
flex-direction: column;
overflow-y: auto;
/* What to add here to make it scrollable? */
.message {
height: 50px;
margin: 10px;
padding: 10px;
background: #1dc497;
}
}
}
}
}
How can I make messages list to scroll?
You have to set the height of .content to 100% and make it scrollable:
.page {
background-color: #ddd;
width: 300px;
height: 300px;
}
.page .messages-section {
display: flex;
flex-direction: column;
width: 50%;
height: 100%;
background-color: #ccc;
}
.page .messages-section .header {
background: #bbb;
padding: 5px;
}
.page .messages-section .content {
display: flex;
flex-direction: column;
align-items: center;
padding: 5px;
height: 100%;
overflow-x: scroll;
}
.page .messages-section .content .messages-list {
display: flex;
flex-direction: column;
overflow-y: auto;
/* What to add here to make it scrollable? */
}
.page .messages-section .content .messages-list .message {
height: 50px;
margin: 10px;
padding: 10px;
background: #1dc497;
}
<div class="page">
<div class="messages-section">
<div class="header">Your messages</div>
<div class="content">
<img src="https://http.cat/100" width="70" height="50" />
<div class="messages-list">
<div class="message">Hi.</div>
<div class="message">Hello.</div>
<div class="message">Good morning.</div>
<div class="message">Yo!</div>
</div>
</div>
</div>
</div>

Flexbox: scrollable content with sticky footer

I want to make a box (flex-item in this case) which always stays in the middle of it's container. In that box, there is a header, footer and content section. If the size of the content grows too big in height, I want the content section to be scrollable. The header and footer should always be visible and the box should always stay in it's container.
Here is what I have been able to write:
HTML
<div class="flex-container">
<div class="flex-item">
<header>Header</header>
<div class="content">
A
<br>B
<br>C
<br>D
<br>E
<br>F
<br>G
<br>H
<br>I
<br>J
<br>K
</div>
<footer>Footer</footer>
</div>
</div>
CSS
body {
margin: 120px;
}
.flex-container {
display: flex;
width: 200px;
height: 200px; /* We can assume that the container's height is hardcoded in this example, but the end solution should work even if this value is changed*/
border: 1px solid black;
justify-content: center;
}
.flex-item {
box-sizing: border-box;
width: 150px;
border: 5px solid blue;
align-self: center;
background-color: red;
display: flex;
flex-flow: column;
max-height: 100%;
}
.content {
/* It should be possible to scroll this element when it get too big in height*/
background-color: grey;
flex: 1;
}
The code is hosted on JSFiddle: https://jsfiddle.net/9fduhpev/3/
To explain the same thing visually, here is the current situation:
Here is what I want:
Use overflow-y: auto;.
Read this: http://www.w3schools.com/cssref/css3_pr_overflow-y.asp
body {
margin: 120px;
}
.flex-container {
display: flex;
width: 200px;
height: 200px;
border: 1px solid black;
justify-content: center;
}
.flex-item {
box-sizing: border-box;
width: 150px;
border: 5px solid blue;
align-self: center;
background-color: red;
display: flex;
flex-flow: column;
max-height: 100%;
}
.content {
background-color: grey;
flex: 1;
overflow-y: auto;
}
<div class="flex-container">
<div class="flex-item">
<header>Header</header>
<div class="content">
A
<br>B
<br>C
<br>D
<br>E
<br>F
<br>G
<br>H
<br>I
<br>J
<br>K
<br>L
</div>
<footer>Footer</footer>
</div>
</div>
I suggest you give it overflow: auto. With that it will be scrollable when needed.
body {
margin: 20px;
}
.flex-container {
display: flex;
width: 200px;
height: 200px;
border: 1px solid black;
justify-content: center;
}
.flex-item {
box-sizing: border-box;
width: 150px;
border: 5px solid blue;
align-self: center;
background-color: red;
display: flex;
flex-flow: column;
max-height: 100%;
}
.content {
background-color: grey;
flex: 1;
overflow: auto;
}
<div class="flex-container">
<div class="flex-item">
<header>Header</header>
<div class="content">
A
<br>B
<br>C
<br>D
<br>E
<br>F
<br>G
<br>H
<br>I
<br>J
<br>K
<br>L
</div>
<footer>Footer</footer>
</div>
</div>
I would do something like this:
.content {
height: 100%;
overflow:auto;
background-color: grey;
flex: 1;
}
https://jsfiddle.net/9fduhpev/4/