Responsive design with CSS Grids - css

I'd like to have responsive version to this code.
body {
display: grid;
grid-template-columns: repeat(4, 1fr);
grid-template-areas:
"navigation-bar content content content";
margin: 0; padding: 0;
}
.navigation-bar {
grid-area: navigation-bar;
height: 100vh;
background-color: #1a1b20;
}
.content {
grid-area: content;
background-color: #202127;
}
<body>
<div class="navigation-bar"></div>
<div class="content"></div>
</body>
What I have:
#media only screen and (max-width: 600px) {
body {
}
.navigation-bar {
}
.content {
}
}
I'd like to have navigation-bar on the top of the website and content below it.
It means:
grid-template-columns should be 1fr
height of navigation-bar should be about 25vh
But I don't know, what grid-template-rows should be.
It depends on content, but if there is no content in content, it should fill whole screen (navigation-bar and content is a rest).
May you help me with responsive desige, please?
EDIT:
On mobile phone:

I would write the base styles using columnar flex and then a use grid when the screen is larger than 600px. Note that in mobile, .content uses flex-grow: 1, which means it will fill all the remaining vertical space.
.navigation-bar {
height: 15vh;
background-color: #1a1b20;
}
.content {
flex-grow: 1;
background-color: #202127;
}
body {
margin: 0;
padding: 0;
display: flex;
flex-direction: column;
min-height: 100vh;
color: white;
}
#media only screen and (min-width: 600px) {
body {
display: grid;
grid-template-columns: repeat(4, 1fr);
grid-template-areas:
"navigation-bar content content content";
}
.navigation-bar {
grid-area: navigation-bar;
height: 100vh;
}
.content {
grid-area: content;
}
}
<div class="navigation-bar">navbar</div>
<div class="content">content</div>
jsFiddle

Related

CSS Grid layout with dynamic height

I need to create layout 2x2 blocks with min-width 500px and min-height 300px. (first img).
I can collapse blue block (by click on it) to height 100px and the block which is below must fill the gap and become bigger. The same behaviour if lower block collapsed, the upper will stretch. (second img)
if screen width > 1200, turn it into 4 columns with width:300px, height:600px (third img) enter image description here
I tried to do add for parent
width: 100%;
height: 100%;
display: grid;
grid-template-rows: minmax(300px, 1fr) minmax(300px, 1fr);
grid-template-columns: minmax(500px, 1fr) minmax(500px, 1fr);
grid-column-gap: 25px;
grid-row-gap: 25px;
}
and also added
#media (min-width: 1200px) {
.parent {
grid-template-rows: minmax(600px, 1fr);
grid-template-columns: repeat(4, minmax(300px, 1fr));
}
}
but I don't know how to implement collapsing
Try this. I use the columns property on the parent to make a 2 column layout with the children to be flex containers. This means that when the flex children are clicked, we can use flex-grow, flex-shrink and flex-basis to make the clicked one smaller and the unclicked one automatically grow.
For screen sizes greater than 1200px, I've used a media query to flip the flex container to flex-direction: row which makes your four columns. The only bit that's annoying is that the column layout, the middle section is wider than the other parts. You might be able to fix this with a bit of tweaking
window.onload = () => {
document.querySelector('.container').addEventListener('click', (e) => {
e.target.classList.toggle('shrink');
});
}
.container {
columns: 2;
padding: 0.5rem;
border: 3px solid black;
height: 600px;
}
.column {
display: flex;
flex-direction: column;
height: 100%;
}
[id^="b"] {
background-color: #00A8F3;
border: 3px solid black;
margin-bottom: 0.5rem;
display: grid;
place-items: center;
padding: 1rem;
flex-grow: 1;
flex-shrink: 1;
}
.shrink {
flex-basis: 100px;
flex-grow: 0;
}
#media screen and (min-width: 1200px) {
.column {
flex: 1;
flex-direction: row;
justify-content: space-evenly;
}
.container {
display: flex;
}
[id^="b"] {
flex-basis: 300px;
flex-grow: 0;
flex-shrink: 0;
}
}
<div class='container'>
<div class='column'>
<div id='b1'>1</div>
<div id='b2'>2</div>
</div>
<div class='column'>
<div id='b3'>3</div>
<div id='b4'>4</div>
</div>
</div>
You can try like below. I added a checkbox to simulate the switch between (1) and (2)
.container {
display: grid;
grid-template-columns: 1fr 1fr; /* 2 columns */
grid-auto-flow: dense;
gap: 20px;
border:1px solid;
height: 300px;
}
.container > div {
display: flex;
flex-direction: column;
gap: 20px;
}
.container > div > div {
flex-grow: 1; /* fill remaining height */
height: 100%; /* we start with equal div */
background: lightblue;
font-size: 20px;
}
#media (max-width: 1200px) {
/* update the height on toggle */
input:checked ~ .container > div:first-child > div:last-child,
input:checked ~ .container > div:last-child > div:first-child {
height: 80px;
}
}
#media (min-width: 1200px) {
.container {
grid-template-columns: 1fr 1fr 1fr 1fr; /* 4 columns */
}
.container > div {
display: contents; /* remove inner divs */
}
/* rectify the order */
.container > div:first-child > div:last-child {
grid-column: 3;
}
}
<input type="checkbox">
<div class="container">
<div>
<div> 1 </div>
<div> 3 </div>
</div>
<div>
<div> 2 </div>
<div> 4 </div>
</div>
</div>

Grid area with responsive not works as expect

:root {
--min-screen-height:100px;
}
.App {
display: grid;
grid-template-columns: 0.7fr 0.9fr 1.5fr 0.9fr;
grid-template-rows: 2.75rem 3fr;
grid-template-areas:
'nav nav nav nav'
'sidebar leftmenu content rightmenu';
gap: 0.75rem 0.4rem;
}
.navigation {
grid-area: nav;
background-color: yellow;
}
.sidebar {
min-height: var(--min-screen-height);
grid-area: sidebar;
background-color: aliceblue;
}
.leftmenu {
grid-area: leftmenu;
background-color: skyblue;
}
.content {
min-height: var(--min-screen-height);
grid-area: content;
background-color: blanchedalmond;
padding: 0.5em 0.75em 0.5em 0.75em;
}
.rightmenu {
grid-area: rightmenu;
background-color: coral;
}
#media screen and (max-width: 768px) {
.App {
grid-template-columns: 1fr;
grid-template-areas:
'nav'
'content';
}
}
<div class="App">
<div class="navigation">Nav</div>
<div class="sidebar">Side bar</div>
<div class="leftmenu">Left Menu</div>
<main class="content">Main</main>
<div class="rightmenu">Right Menu</div>
</div>
In responsive until 768px I am only showing the nav and container. But still in the 768 I could see the rightmenu.
what is wrong here? or how to fix this? Please check in full page with by resizing it.
https://www.w3.org/TR/css-grid-2/#explicit-grids
The three properties grid-template-rows, grid-template-columns, and grid-template-areas together define the explicit grid of a grid container by specifying its explicit grid tracks. The final grid may end up larger due to grid items placed outside the explicit grid; in this case implicit tracks will be created, these implicit tracks will be sized by the grid-auto-rows and grid-auto-columns properties.
The grid-auto-flow property controls auto-placement of grid items without an explicit position. Once the explicit grid is filled (or if there is no explicit grid) auto-placement will also cause the generation of implicit grid tracks.
So grid-template-areas defines explicit grid. Remaining areas are put in implicit grid.
To get rid of those elements you may use:
#media screen and (max-width: 768px) {
.App {
grid-template-columns: 1fr;
grid-template-areas: "nav" "content";
}
.App :not(.navigation, .content) {
display: none;
}
}
All the divs are still there so the grid does its best to accommodate them although they say they are in grid-areas which are not defined.
To completely get rid of them you will need to set them to display none in the media query.
:root {
--min-screen-height: 100px;
}
.App {
display: grid;
grid-template-columns: 0.7fr 0.9fr 1.5fr 0.9fr;
grid-template-rows: 2.75rem 3fr;
grid-template-areas: 'nav nav nav nav' 'sidebar leftmenu content rightmenu';
gap: 0.75rem 0.4rem;
}
.navigation {
grid-area: nav;
background-color: yellow;
}
.sidebar {
min-height: var(--min-screen-height);
grid-area: sidebar;
background-color: aliceblue;
}
.leftmenu {
grid-area: leftmenu;
background-color: skyblue;
}
.content {
min-height: var(--min-screen-height);
grid-area: content;
background-color: blanchedalmond;
padding: 0.5em 0.75em 0.5em 0.75em;
}
.rightmenu {
grid-area: rightmenu;
background-color: coral;
}
#media screen and (max-width: 768px) {
.App {
grid-template-columns: 1fr;
grid-template-areas: 'nav' 'content';
}
.sidebar,
.rightmenu,
.leftmenu {
display: none;
}
}
<div class="App">
<div class="navigation">Nav</div>
<div class="sidebar">Side bar</div>
<div class="leftmenu">Left Menu</div>
<main class="content">Main</main>
<div class="rightmenu">Right Menu</div>
</div>

How could i use css to make my Grid template fit to column

This is my css code and this is how my images show up
This is my html code and it shows all of the but theres also a Car component that has more code in it
<section className="Carslist">
<div className="Carslist-center">
{cars.map(item => {
return <Car key={item.id} car={item} />;
})}
</div>
</section>
.Carslist {
padding: 5rem 0;
}
.Carslist-center {
width: 100vw;
margin: 0 auto;
display: grid;
grid-template-columns: repeat(auto-fill, minmax(250px, 1fr));
grid-row-gap: 2rem;
grid-column-gap: 30px;
}
#media screen and (min-width: 776px) {
.Carslist-center {
width: 90vw;
}
}
#media screen and (min-width: 992px) {
.Carslist-center {
width: 95vw;
max-width: 1170px;
}
}
I would like to make each picture fit fully to the grid
Please show us your HTML code, but this CSS code should work
img {
object-fit: cover;
width: 100%;
height: 100%;
}

CSS grid template columns - how does it work?

I'm new to CSS Grid and trying to learn how it works. I've found a layout that I've been playing around with but I can't seem to figure out how to get the article to span the entire width of the footer/header. I've tried changing the grid-template-columns but and get pretty close to spanning it but not all the way.
Any tips would be greatly appreciated!
.grid {
display: grid;
grid-template-columns: 150px auto 0px;
grid-gap: 1em;
}
header,
footer {
grid-column: 1 / 4;
}
#media all and (max-width: 800px) {
aside,
article {
grid-column: 1 / 4;
}
}
/* Demo Specific Styles */
body {
margin: 0 auto;
max-width: 56em;
padding: 1em 0;
}
header,
aside,
article,
footer {
background: #eaeaea;
display: flex;
align-items: center;
justify-content: center;
height: 25vh;
}
header {
height: 250px;
}
<div class="grid">
<header>
Header
</header>
<aside class="sidebar-left">
Left Sidebar
</aside>
<article>
Article
</article>
<footer>
Footer
</footer>
</div>
I can't seem to figure out how to get the article to span the entire width of the footer/header.
You have created a 3-column grid:
grid-template-columns: 150px auto 0px
You've set the header and footer to span across all three columns:
header, footer {
grid-column: 1 / 4;
}
However, the article has no such instruction. It simply expands across column two, because that's the default setting (i.e., grid-column { 2 / auto }).
Therefore, you need to tell the article to expand across the third column. Add this to your code:
article {
grid-column: 2 / 4;
}
.grid {
display: grid;
grid-template-columns: 150px auto 0px;
grid-gap: 1em;
}
header,
footer {
grid-column: 1 / 4;
}
/* new */
article {
grid-column: 2 / 4;
}
#media all and (max-width: 800px) {
aside,
article {
grid-column: 1 / 4;
}
}
/* Demo Specific Styles */
body {
margin: 0 auto;
max-width: 56em;
padding: 1em 0;
}
header,
aside,
article,
footer {
background: #eaeaea;
display: flex;
align-items: center;
justify-content: center;
height: 25vh;
}
header {
height: 250px;
}
<div class="grid">
<header>Header</header>
<aside class="sidebar-left">Left Sidebar</aside>
<article>Article</article>
<footer>Footer</footer>
</div>

Images in CSS Grid

I can't figure out how to go about resizing images within CSS Grid.
I don't mind if the image is clipped at all but I would like my aside item to resize the image so that it shrinks/grows to fill the item as best as possible as the webpage is resized.
The grid layout is adjusting with #media (min-width: 600px) { /* tablet */ and #media (min-width: 1600px) { /* desktop */.
HTML:
<body>
<div class="container">
<header>
Home
Getting Started
Tracks
Contact Us
</header>
<main>Content</main>
<advert>Advert</advert>
<aside>
<img src="https://jagrotax.co.uk/wp-content/uploads/2013/01/mojo-tyres-rotax-max.jpg" alt="Mojo Kart Tyre list">
</aside>
<footer>Maximilian Crosby ©</footer>
</div>
</body>
CSS:
.container {
display: grid;
grid-template-columns: 1fr;
grid-template-rows: 8% 10% 70% 10% 2%;
grid-gap: 10px;
grid-template-areas: /* mobile */
"header"
"advert"
"main"
"aside"
"footer";
font-family: 'Comfortaa', cursive;
min-height: 1000px;
background: #BCF9FF;
text-align: center;
}
header {
background: #A6CFFF;
grid-area: header;
display: flex;
flex-wrap: wrap;
font-size: 26px;
justify-content: space-evenly;
align-items: center;
padding: 0px 40px 0px;
}
main {
background: #A6CFFF;
grid-area: main;
}
advert {
background: #A6CFFF;
grid-area: advert;
}
aside {
background: #A6CFFF;
grid-area: aside;
}
footer {
grid-area: footer;
}
you only need to add this to your css:
aside img {
width: 100%;
height: 100%;
-o-object-fit: cover;
object-fit: cover;
}
The Img inside your aside need to use 100% of the space (inside the aside area) that's why you need the width and the height to be 100%. Also by using the object-fit: cover, the img will preserve the aspect ratio.
Here is a fiddle:
https://jsfiddle.net/cisco336/n5dzte8m/

Resources