I am trying to build a layout with a menubar and a main container that includes a searchbar, left sidebar, and a results table.
I want the main container to always be as tall as possible for the window and the left sidebar and results table to also be as tall as possible within the main container.
This is how this would look with fixed heights on everything:
https://jsfiddle.net/m45cakne/1/
<div class="menubar"></div>
<div class="main-section">
<div class="searchbar">
</div>
<div class="section-content">
<div class="sidebar"></div>
<div class="results-table"></div>
</div>
</div>
* {
box-sizing: border-box;
}
html, body {
height: 100%;
}
.menubar {
height: 50px;
border: 1px solid black;
}
.main-section {
border: 1px solid black;
margin-top: 20px;
height: 600px;
}
.searchbar {
border: 1px solid black;
margin: 20px;
height: 50px;
}
.section-content {
display: -webkit-box;
display: -ms-flexbox;
display: flex;
-ms-flex-wrap: wrap;
flex-wrap: wrap;
padding-right: 25px;
padding-left: 25px;
flex: 1;
}
.sidebar {
-webkit-box-flex: 0;
-ms-flex: 0 0 25%;
flex: 0 0 25%;
max-width: 25%;
border: 1px solid black;
position: relative;
width: 100%;
min-height: 1px;
padding-right: 15px;
padding-left: 15px;
height: 490px;
}
.results-table {
-webkit-box-flex: 0;
-ms-flex: 0 0 75%;
flex: 0 0 75%;
max-width: 75%;
position: relative;
width: 100%;
min-height: 1px;
border: 1px solid black;
height: 490px;
padding: 0px;
}
The menubar height can change as the page is viewed on different devices, and the searchbar height can also change as it is filled with search terms.
What would be the right method to build this responsive layout with CSS?
Just use flex properties all the way through:
body {
display: flex;
flex-direction: column;
height: 100vh;
margin: 0;
}
.menubar {
flex: 0 0 50px;
border: 1px solid black;
}
.main-section {
flex: 1;
display: flex;
flex-direction: column;
border: 1px solid black;
margin-top: 20px;
padding: 25px;
}
.searchbar {
flex: 0 0 50px;
margin-bottom: 20px;
border: 1px solid black;
}
.section-content {
flex: 1;
display: flex;
flex-wrap: wrap;
}
.sidebar {
flex: 0 0 25%;
border: 1px solid black;
}
.results-table {
flex: 1;
border: 1px solid black;
}
* {
box-sizing: border-box;
}
<div class="menubar">menu bar</div>
<div class="main-section">main container
<div class="searchbar">search bar</div>
<div class="section-content">
<div class="sidebar">side bar</div>
<div class="results-table">results table</div>
</div>
</div>
jsFiddle demo
Related
I struggle with an responsive attempt. I got two columns, where the width is based on VW. The bigger column contains am div element to close. This element should have always the same top and left margin, in relatives to the parent column. No matter if I resize the window.
Currently if I resize the distance between changes, either increase or shrinks to a point, where my close div get out of position c
body {
background: grey;
overflow: hidden;
}
.container-fluid {
width: 100%;
margin: auto;
display: flex;
flex-wrap: inherit;
align-items: center;
justify-content: space-between;
}
.col-lg-8 {
flex: 0 0 auto;
width: 66.666667%;
}
.col-lg-4 {
flex: 0 0 auto;
width: 33.333333%;
}
.card {
position: relative;
display: flex;
flex-direction: column;
height: 50vh;
background-color: #fff;
background-clip: border-box;
border: 0 solid rgba(0, 0, 0, 0.125);
border-radius: 1rem;
margin: 0.5em;
padding: 0.5em;
}
.title {
margin: 0.5em;
font-size: 3em;
float: left;
}
.close-btn {
position: absolute;
float: left;
cursor: pointer;
font-size: 2em;
left: 57vw;
top: 2vh;
}
<!DOCTYPE html>
<html lang="en">
<head>
<meta http-equiv="Content-Type" content="text/html;charset=utf-8" />
<title>Fixed Close Position</title>
<!-- fontawesome stylesheet https://fontawesome.com/ -->
<script src="https://kit.fontawesome.com/98a5e27706.js" crossorigin="anonymous"></script>
</head>
<body>
<div class="container-fluid">
<div class="col-lg-8">
<div class="card">
<div class="title">Headline</div>
<div class="close-btn"><i class="fa-solid fa-circle-xmark"></i></div>
</div>
</div>
<div class="col-lg-4">
<div class="card">
<div class="title">News</div>
</div>
</div>
</div>
</body>
</html>
ompletely. I am stuck.
Try this,
body {
background: grey;
overflow: hidden;
}
.container-fluid {
width: 100%;
margin: auto;
display: flex;
flex-wrap: inherit;
align-items: center;
justify-content: space-between;
}
.col-lg-8 {
flex: 0 0 auto;
width: 66.666667%;
}
.col-lg-4 {
flex: 0 0 auto;
width: 33.333333%;
}
.card {
position: relative;
display: flex;
flex-direction: column;
height: 50vh;
background-color: #fff;
background-clip: border-box;
border: 0 solid rgba(0, 0, 0, 0.125);
border-radius: 1rem;
margin: 0.5em;
padding: 0.5em;
}
.title {
margin: 0.5em;
font-size: 3em;
float: left;
}
.close-btn {
position: absolute;
cursor: pointer;
font-size: 2em;
left: auto;
top: 2vh;
right: 2vh;
}
I have an HTML structure where I can't seem to get the CSS position sticky working.
I think it because it's within the aside container. If I make aside stick it works.
I want the .product-info div to be sticky and when it hits the div .content-other it unsticks.
Unless with flex I could move out .personal-info and .product-info from within the aside and have them sit to the right on top of each other? Like
content | Personal info
| Product info
Then not bother having the wrapping aside? Not sure how to stack these like this though with flex.
body {
padding: 20px;
}
.container {
margin-left: auto;
margin-right: auto;
position: relative;
padding-bottom: 16px;
padding-top: 16px;
width: 100%;
display: flex;
}
.content {
position: relative;
max-width: 100%;
flex-basis: 74%;
border: 1px solid black;
width: 300px;
margin-right: 20px;
height: 540px;
}
.right-side {
align-self: flex-start;
background-color: #ffffff;
border: 2px solid #e8e8e3;
border-radius: 0 4px 4px 4px;
flex: 1 1;
flex-basis: 40%;
min-width: 338px;
padding: 16px 16px 0;
display: block;
width: 400px;
}
.personal-info {
height: 250px;
}
.product-info {
position: sticky;
position: -webkit-sticky;
top: 24px;
border: 1px solid red;
}
.content-other {
width: 100%;
background: #f5f5f5;
height: 400px;
}
<div class="container">
<div class="content">content area here</div>
<aside class="right-side">
<div class="personal-info">some info</div>
<div class="product-info">sticky info</div>
</aside>
</div>
<div class="content-other">.product-info unsticks when it hits here</div>
Cheers
Simply remove align-self: flex-start;
body {
padding: 20px;
}
.container {
margin-left: auto;
margin-right: auto;
position: relative;
padding-bottom: 16px;
padding-top: 16px;
width: 100%;
display: flex;
}
.content {
position: relative;
max-width: 100%;
flex-basis: 74%;
border: 1px solid black;
width: 300px;
margin-right: 20px;
height: 540px;
}
.right-side {
/*align-self: flex-start;*/
background-color: #ffffff;
border: 2px solid #e8e8e3;
border-radius: 0 4px 4px 4px;
flex: 1 1;
flex-basis: 40%;
min-width: 338px;
padding: 16px 16px 0;
display: block;
width: 400px;
}
.personal-info {
height: 250px;
}
.product-info {
position: sticky;
position: -webkit-sticky;
top: 24px;
border: 1px solid red;
}
.content-other {
width: 100%;
background: #f5f5f5;
height: 400px;
}
<div class="container">
<div class="content">content area here</div>
<aside class="right-side">
<div class="personal-info">some info</div>
<div class="product-info">sticky info</div>
</aside>
</div>
<div class="content-other">.product-info unsticks when it hits here</div>
I have an HTML structure where I can't seem to get the CSS position sticky working.
I think it because it's within the aside container. If I make aside stick it works.
I want the .product-info div to be sticky and when it hits the div .content-other it unsticks.
Unless with flex I could move out .personal-info and .product-info from within the aside and have them sit to the right on top of each other? Like
content | Personal info
| Product info
Then not bother having the wrapping aside? Not sure how to stack these like this though with flex.
body {
padding: 20px;
}
.container {
margin-left: auto;
margin-right: auto;
position: relative;
padding-bottom: 16px;
padding-top: 16px;
width: 100%;
display: flex;
}
.content {
position: relative;
max-width: 100%;
flex-basis: 74%;
border: 1px solid black;
width: 300px;
margin-right: 20px;
height: 540px;
}
.right-side {
align-self: flex-start;
background-color: #ffffff;
border: 2px solid #e8e8e3;
border-radius: 0 4px 4px 4px;
flex: 1 1;
flex-basis: 40%;
min-width: 338px;
padding: 16px 16px 0;
display: block;
width: 400px;
}
.personal-info {
height: 250px;
}
.product-info {
position: sticky;
position: -webkit-sticky;
top: 24px;
border: 1px solid red;
}
.content-other {
width: 100%;
background: #f5f5f5;
height: 400px;
}
<div class="container">
<div class="content">content area here</div>
<aside class="right-side">
<div class="personal-info">some info</div>
<div class="product-info">sticky info</div>
</aside>
</div>
<div class="content-other">.product-info unsticks when it hits here</div>
Cheers
Simply remove align-self: flex-start;
body {
padding: 20px;
}
.container {
margin-left: auto;
margin-right: auto;
position: relative;
padding-bottom: 16px;
padding-top: 16px;
width: 100%;
display: flex;
}
.content {
position: relative;
max-width: 100%;
flex-basis: 74%;
border: 1px solid black;
width: 300px;
margin-right: 20px;
height: 540px;
}
.right-side {
/*align-self: flex-start;*/
background-color: #ffffff;
border: 2px solid #e8e8e3;
border-radius: 0 4px 4px 4px;
flex: 1 1;
flex-basis: 40%;
min-width: 338px;
padding: 16px 16px 0;
display: block;
width: 400px;
}
.personal-info {
height: 250px;
}
.product-info {
position: sticky;
position: -webkit-sticky;
top: 24px;
border: 1px solid red;
}
.content-other {
width: 100%;
background: #f5f5f5;
height: 400px;
}
<div class="container">
<div class="content">content area here</div>
<aside class="right-side">
<div class="personal-info">some info</div>
<div class="product-info">sticky info</div>
</aside>
</div>
<div class="content-other">.product-info unsticks when it hits here</div>
I applied display: block to my other divs but my image is displayed in front. I thought display: block would force a line break. Why is my image in front?
https://codepen.io/El_Escandalo/pen/PoPzXPZ?editors=1100
That's because your .container div is limited to height: 200px;. Erase that to allow its height to adjust to the contents, and your image container will be below it.
You've got an extra closed after container C.
* {
padding: 0;
margin: 0;
}
.container {
height: 200px;
text-align: center;
padding: none;
}
.a {
height: 100px;
width: 33%;
background: red;
display: block;
padding: none;
border: 10px solid purple;
box-sizing: border-box;
}
.b {
height: 100px;
width: 33%;
background: green;
display: block;
padding: none;
border: 10px solid purple;
box-sizing: border-box;
}
.c {
height: 100px;
width: 33%;
background: blue;
display: block;
padding: none;
border: 10px solid purple;
box-sizing: border-box;
}
.d {
border: 25px solid pink;
margin: 0 auto;
width: 75vw;
height: auto;
text-align: center;
}
.d img {
width: 100%;
}
<div class="container">
<div class="a"></div>
<div class="b"></div>
<div class="c"></div>
<div class="img-cont">
<div class="d">
<img src="https://cdn.pixabay.com/photo/2020/03/26/10/51/norway-4970019_1280.jpg" alt="view">
</div>
</div>
Chrome is normal,Safari failure。How can that be compatible? height:100%;
I need to keep Chrome and use Safari. My Safari version 10.1.2 (12603.3.8)
* {
margin: 0;
padding: 0;
box-sizing: border-box;
outline: none;
}
* ::-webkit-scrollbar {
width: 0;
}
html, body {
height: 100%;
width: 100%;
display: -webkit-box;
display: -ms-flexbox;
display: flex;
flex-direction: column;
}
body {
border: 5px solid red;
}
.d {
height: 100%;
border: 5px solid green;
}
<div class="d"></div>
<div class="d"></div>
Seems like a recent Safari rendering bug involving flex-direction: column. You're putting two height: 100% elements into the same space, and they're both rendering at 100% height and stacking instead of fitting into the same space.
Here are two solutions:
Change height: 100% to height: 50% so both elements are half the height of their parent, or...
Remove the height attribute and add flex: 1 so both children grow as large as they can in the parent's space, and split themselves 50/50 automatically.
* {
margin: 0;
padding: 0;
box-sizing: border-box;
outline: none;
}
*::-webkit-scrollbar {
width: 0;
}
html,
body {
height: 100%;
width: 100%;
display: flex;
flex-direction: column;
}
body {
border: 5px solid red;
}
.d {
height: 50%;
border: 5px solid green;
}
<div class="d"></div>
<div class="d"></div>
* {
margin: 0;
padding: 0;
box-sizing: border-box;
outline: none;
}
*::-webkit-scrollbar {
width: 0;
}
html,
body {
height: 100%;
width: 100%;
display: flex;
flex-direction: column;
}
body {
border: 5px solid red;
}
.d {
flex: 1;
border: 5px solid green;
}
<div class="d"></div>
<div class="d"></div>