Compatibility problem when resizing an image inside css grid layout - html

Here my page layout, the image should vertically fit into the first row:
<div id="main">
<div id="header" class="vcenter">
<img src="https://source.unsplash.com/random/200x200" id="logo">
</div>
<div id="e1"></div>
</div>
css:
* {
margin: 0px;
padding: 0px;
}
body {
background-color: #001018;
}
#main {
display: grid;
grid-template-columns: 200px;
grid-template-rows: 100px auto;
grid-template-areas:
"header"
"e1";
gap: 20px;
}
#header { grid-area: header; }
#e1 { grid-area: e1; }
#main > div {
background-color: #334455;
padding: 5px;
}
#logo {
max-width: auto;
max-height: 80%;
border: 1px solid red;
}
.vcenter {
display: grid;
align-items: center;
}
Firefox successfully centers the image after resizing but Chrome shifts the image down, like so:
Is there a simple way to make this compatible in both browsers with minimal changes to the css/html, keeping the current grid layout?
Thank you!
https://jsfiddle.net/tfoller/pnmjvq58/32/

There is not enough height. Add height: 100% to #logo. Like that:
#logo {
...
height: 100%;
}
This will work in both browsers.

Related

How can I get my grid column to stay the same size (height and width) when resizing viewports?

I have a container that will have a picture of the day. When changing viewport sizes (mobile screen size) the container gets squashed so much that the image is not readable.. How can I get the containers in my grid system to stay the exact same size relative to the viewport? Thank you!!
html,
body,
form,
main {
height: 100%;
}
body {
background-color: #232A35;
padding: 10px;
}
.content {
height: 100%;
margin-left: auto;
margin-right: auto;
}
.mainheader {
border: 1px red solid;
width: 100%;
}
.iotd {
grid-area: iotd;
}
.banner {
grid-area: banner;
}
.solutions {
grid-area: solutions;
}
.services {
grid-area: services;
}
.tud {
grid-area: tud;
}
.resources {
grid-area: resources;
}
.grid-container {
display: grid;
grid-template-areas: 'iotd banner banner banner banner banner' 'iotd solutions services resources tud tud';
gap: 10px;
background-color: #2196F3;
padding: 10px;
height: 100%;
}
.grid-container>div {
background-color: rgba(255, 255, 255, 0.8);
text-align: center;
padding: 20px 0;
font-size: 30px;
}
#media screen and (max-width: 900px) {
.grid-container>div {
font-size: 10px;
}
}
<div class="content">
<div class="container-fluid mainheader">
<div class="grid-container">
<div class="iotd col">IOTD</div>
<div class="banner col">Banner</div>
<div class="solutions col">Solutions</div>
<div class="services col">Services</div>
<div class="tud col">The Unrecovery Difference</div>
<div class="resources col">Resources</div>
</div>
</div>
</div>
The container that will hold the image is labeled as "IOTD"
Any help is appreciated
resolved the issue by changing the image size rather than the container size when the viewport reaches 900px. I also change the font size to a smaller size which in turn makes all of the containers smaller
One approach might be to include a grid-template-columns rule to specify how you want the horizontal space apportioned, this can include a minimum absolute (px) width for the first column with the option of allowing it to grow when more space is available using minmax.
For example, I've added the following rule to your css:
grid-template-columns: minmax(150px, 1fr) repeat(5, 1fr);
This divides the grid into 6 columns to be consistent with your area template (which remains in operation) but makes the first column at least 150px wide with the option of expanding with the other columns when extra width is available. The remaining five columns are allocated 1/5 of the available space by specifying 5 1fr fractions.
Here's the rule added to your example:
html,
body,
form,
main {
height: 100%;
}
body {
background-color: #232A35;
padding: 10px;
}
.content {
height: 100%;
margin-left: auto;
margin-right: auto;
}
.mainheader {
border: 1px red solid;
width: 100%;
}
.iotd {
grid-area: iotd;
}
.banner {
grid-area: banner;
}
.solutions {
grid-area: solutions;
}
.services {
grid-area: services;
}
.tud {
grid-area: tud;
}
.resources {
grid-area: resources;
}
.grid-container {
display: grid;
grid-template-areas: 'iotd banner banner banner banner banner' 'iotd solutions services resources tud tud';
grid-template-columns: minmax(150px, 1fr) repeat(5, 1fr);
gap: 10px;
background-color: #2196F3;
padding: 10px;
height: 100%;
}
.grid-container>div {
background-color: rgba(255, 255, 255, 0.8);
text-align: center;
padding: 20px 0;
font-size: 30px;
}
#media screen and (max-width: 900px) {
.grid-container>div {
font-size: 10px;
}
}
<div class="content">
<div class="container-fluid mainheader">
<div class="grid-container">
<div class="iotd col">IOTD</div>
<div class="banner col">Banner</div>
<div class="solutions col">Solutions</div>
<div class="services col">Services</div>
<div class="tud col">The Unrecovery Difference</div>
<div class="resources col">Resources</div>
</div>
</div>
</div>
This page https://developer.mozilla.org/en-US/docs/Web/CSS/CSS_Grid_Layout/Grid_Template_Areas has examples where grid-template-areas are combined with grid-template-columns (it also has some ideas on using media queries to suit different view ports).

How can I get my grid layout to scale properly?

I am trying to build a grid layout at the top of my page that will have a navigation bar and a picture that changes every day. I have this done.. But when I try to scale my webpage to a mobile layout, everything breaks.. The grid shrinks down so much that the columns start to go outside of the grid. I followed the bootstrap docs, and took this grid layout from the website and configured it to my own liking.
html, body, form, main {
height: 100%;
}
body{
background-color: #232A35;
}
.content{
width:90%;
height:100%;
margin-left:auto;
margin-right:auto;
}
.mainheader{
border:1px red solid;
width:100%;
}
.iotd { grid-area: iotd; }
.banner { grid-area: banner; }
.solutions { grid-area: solutions; }
.services { grid-area: services; }
.tud { grid-area: tud; }
.resources { grid-area: resources; }
.grid-container {
display: grid;
grid-template-areas:
'iotd banner banner banner banner banner'
'iotd solutions services resources tud tud';
grid-template-columns: auto auto auto auto;
grid-template-rows: auto auto;
gap: 10px;
background-color: #2196F3;
padding: 10px;
height:100%;
}
.grid-container > div {
background-color: rgba(255, 255, 255, 0.8);
text-align: center;
padding: 20px 0;
font-size: 30px;
}
<div class="content">
<div class="container-fluid mainheader">
<div class="grid-container">
<div class="iotd">IOTD</div>
<div class="banner">Banner</div>
<div class="solutions">Solutions</div>
<div class="services">Services</div>
<div class="tud">The Unrecovery Difference</div>
<div class="resources">Resources</div>
</div>
</div>
</div>

Images not adjusting inside the grid

I got 2 columns grid with following layout:
My issue is that when I use images inside the right column (1 image inside each box)..Images overflow and whole grid kind of acts weird.
It looks something like this:
Codepen Link: https://codepen.io/kazmi066/pen/MWXGgaL?editors=1100
* {
margin: 0;
padding: 0;
box-sizing: border-box;
}
.grid {
background: green;
width: 100%;
max-height: 70vh;
display: grid;
gap: 20px;
grid-template-columns: repeat(auto-fit, minmax(340px, 1fr));
}
.col1 {
height: 100%;
background: red;
}
.col2 {
height: 100%;
background: orange;
}
.box1 {
width: 100%;
height: 50%;
border: 1px solid black;
}
.box2 {
width: 100%;
height: 50%;
border: 1px solid blue;
}
img {
width: 100%;
height: 100%;
object-fit: cover;
}
<div class="grid">
<div class="col1"></div>
<div class="col2">
<div class="box1"><img src="https://images.unsplash.com/photo-1600585154340-be6161a56a0c?ixlib=rb-4.0.3&ixid=MnwxMjA3fDB8MHxleHBsb3JlLWZlZWR8N3x8fGVufDB8fHx8&w=1000&q=80" alt="property"/></div>
<div class="box2"><img src="https://images.unsplash.com/photo-1600585154340-be6161a56a0c?ixlib=rb-4.0.3&ixid=MnwxMjA3fDB8MHxleHBsb3JlLWZlZWR8N3x8fGVufDB8fHx8&w=1000&q=80" alt="property" /></div>
</div>
</div>
I want the images to adjust inside the boxes perfectly without the need of custom height and width so that any size of image can work in this scenario.
fit would be object-fit: contain; for the image not cover.
but if the ratio of the image is not the ratio of the box, you'll have blank
you can put the image in background of box1, box2... with a background size cover. It will cover entirely and clipped the overflow. If box ratio "totally" different of the image, lot of image can be clipped, but it's not so often.
I've found a way, only CSS, nothing is changed in your HTML
2 points:
1- it's using clip-path
2- image fill box space, but are clipped otherwise blank space
* {
margin: 0;
padding: 0;
box-sizing: border-box;
}
.grid {
background: green;
width: 100%;
max-height: 70vh;
display: grid;
gap: 2vh;
grid-template-columns: repeat(auto-fit, minmax(340px, 1fr));
grid-template-rows: 100%;
}
.col1 {
background: red;
}
.col2 {
display: grid;
grid-template-columns: 1fr;
grid-template-rows: 34vh 34vh;
background: orange;
justify-content: center;
}
.box1 {
width: 100%;
border: 1px solid black;
clip-path: inset(0);
}
.box2 {
width: 100%;
border: 1px solid blue;
clip-path: inset(0);
}
img {
width: 100%;
object-fit: contain;
}
<div class="grid">
<div class="col1"></div>
<div class="col2">
<div class="box1"><img src="https://images.unsplash.com/photo-1600585154340-be6161a56a0c?ixlib=rb-4.0.3&ixid=MnwxMjA3fDB8MHxleHBsb3JlLWZlZWR8N3x8fGVufDB8fHx8&w=1000&q=80" alt="property" /></div>
<div class="box2"><img src="https://images.unsplash.com/photo-1600585154340-be6161a56a0c?ixlib=rb-4.0.3&ixid=MnwxMjA3fDB8MHxleHBsb3JlLWZlZWR8N3x8fGVufDB8fHx8&w=1000&q=80" alt="property" /></div>
</div>
</div>
based on your grid max-height in vh, I defined all others same kind of values in vh. Lot more consistent and avoid some little strange pixels or lines here or there depending of window size.
I put a nested grid inside col2 where box1 box2 go. box have a clip-path with inset 0, meaning clipping everything out.
The solution that worked for me:
I used grid-auto-rows to create 2 rows with specific height.
Then added span to adjust the column accordingly to cover both rows.
.grid {
width: 100%;
border: 1px solid red;
display: grid;
gap: 14px;
grid-template-columns: repeat(12, 1fr);
grid-auto-rows: 280px 280px;
}
.col1 {
height: 100%;
grid-column: 1/8;
grid-row: span 2;
background: red;
}
.col2 {
grid-column: 8/13;
height: 100%;
background: orange;
}
.col2 img:first-child {
margin-bottom: 11px;
}
img {
width: 100%;
height: 100%;
object-fit: cover;
}
#media (max-width: 768px) {
.grid {
grid-auto-rows: 220px 120px;
}
.col1 {
grid-column: 1/13;
}
.col2 {
grid-column: 1/13;
grid-row: span 2;
}
}
<div class="grid">
<div class="col1">
<img src="https://images.unsplash.com/photo-1600585154340-be6161a56a0c?ixlib=rb-4.0.3&ixid=MnwxMjA3fDB8MHxleHBsb3JlLWZlZWR8N3x8fGVufDB8fHx8&w=1000&q=80" alt="property"/>
</div>
<div class="col2">
<img src="https://images.unsplash.com/photo-1564013799919-ab600027ffc6?ixlib=rb-4.0.3&ixid=MnwxMjA3fDB8MHxzZWFyY2h8Mnx8YmVhdXRpZnVsJTIwaG91c2V8ZW58MHx8MHx8&w=1000&q=80" alt="property"/>
<img src="https://images.pexels.com/photos/186077/pexels-photo-186077.jpeg?cs=srgb&dl=pexels-binyamin-mellish-186077.jpg&fm=jpg" alt="property" />
</div>
</div>
Final output now:
Solution-2: Found Another better solution with Grid-template-areas I guess which looks more cleaner:
.grid {
width: 100%;
border: 1px solid red;
display: grid;
gap: 14px;
grid-template-areas:
"mainImage mainImage otherImage1"
"mainImage mainImage otherImage1"
"mainImage mainImage otherImage2"
"mainImage mainImage otherImage2"
}
.mainImage {
grid-area: mainImage;
}
.otherImage1 {
grid-area: otherImage1;
}
.otherImage2 {
grid-area: otherImage2;
}
img {
width: 100%;
height: 100%;
object-fit: cover;
}
<div class="grid">
<img src="https://images.unsplash.com/photo-1600585154340-be6161a56a0c?ixlib=rb-4.0.3&ixid=MnwxMjA3fDB8MHxleHBsb3JlLWZlZWR8N3x8fGVufDB8fHx8&w=1000&q=80" alt="property" class="mainImage" />
<img src="https://images.unsplash.com/photo-1564013799919-ab600027ffc6?ixlib=rb-4.0.3&ixid=MnwxMjA3fDB8MHxzZWFyY2h8Mnx8YmVhdXRpZnVsJTIwaG91c2V8ZW58MHx8MHx8&w=1000&q=80" alt="property" class="otherImage1" /> <img src="https://images.pexels.com/photos/186077/pexels-photo-186077.jpeg?cs=srgb&dl=pexels-binyamin-mellish-186077.jpg&fm=jpg" alt="property" class="otherImage2" />
</div>
<h1>something else here</h1>

CSS values for DIV structure setup

I need to setup the following DIV structure (See image below. It tells more than a 1000 words)
The structure consists of 2 colums. The main column (left) has a variable width and 100% height.
The right colums has a FIXED width of 380px and 100% height.
Then inside the right column I need 3 DIVS.
The top DIV has a fixed height of 200px and must be aligned to the top.
The bottom DIV has a fixed height of 150px and must be aligned to the bottom.
The middle DIV has a variable height and must fill up the space vertically.
This is the DIV setup And the CSS I have:
.main-content {
width: 100%;
padding: 0px;
}
.col-1 {
width: calc(100% - 380px);
min-height: calc(var(--vh, 1vh)*100);
background-color: #2693FF;
float: left;
}
.col-2 {
width: 380px;
min-height: calc(var(--vh, 1vh)*100);
float: right;
}
.col-2-top {
height: 200px;
background-color: #00B200;
}
.col-2-middle {
height: 100%;
background-color: #FF8000;
}
.col-2-bottom {
height: 100px;
background-color: #B25900;
}
<div class="main-content">
<div class="col-1"></div>
<div class="col-2">
<div class="col-2-top"></div>
<div class="col-2-middle"></div>
<div class="col-2-bottom"></div>
</div>
</div>
Then... Column 1 and 2 should stack when the viewport width becomes less than 768px.
Column 1 on top and Column 2 below it.
Like this:
I think I'm almost there, but I'm having problems with the height of the Main DIV and the heights and aligning of the DIV col-2 middle DIV. I also need a bit helpt to get these divs stack nicely above each each other.
I would suggest that you use grid layout instead of floating around your <div>s, grid layout allows you to structure your layout and separate them in columns and rows, and areas using grid-template-areas.
for max-width:748 just add media query, here is how it might be implemented:
body {
padding: 0;
margin: 0;
}
.main-content {
display: grid;
background-color: #2196F3;
grid-template-areas:
'main fixed-top'
'main variable-mid-area'
'main fixed-bottom';
background-color: #2196F3;
height: 100vh;
grid-template-columns: 1fr 380px;
grid-template-rows: 200px 1fr 150px;
}
.main-content > div {
color: #fff;
font-size: 30px;
vertical-align: middle;
display: flex;
justify-content: center;
align-items: center;
}
.main {
grid-area: main;
background-color: #2693FC;
}
.variable-mid-area {
grid-area: variable-mid-area;
background-color: #FF8015;
}
.fixed-top {
grid-area: fixed-top;
background-color:#00B21F;
}
.fixed-bottom {
grid-area: fixed-bottom;
background-color: #B2590B;
}
#media only screen and (max-width: 768px) {
.main-content {
grid-template-areas:
'main'
'fixed-top'
'variable-mid-area'
'fixed-bottom';
grid-template-rows: 300px 200px 1fr 150px;
grid-template-columns: 100%;
height: auto;
}
}
<div class="main-content">
<div class="main"> main </div>
<div class="fixed-top"> 200 </div>
<div class="variable-mid-area"> auto </div>
<div class="fixed-bottom"> 150 </div>
</div>
If you have any questions how the css works, feel free to ask them in the comments.
I know the background-colors are irrelevant but they help to visualize it.
.container {
min-width: 768px;
width: 100%;
display: grid;
grid-template-columns: calc(100% - 380px) 1fr;
min-height: 100vh;
}
.col1 {
background-color: dodgerblue;
}
.col2 {
display: flex;
flex-direction: column;
}
.col2-row1 {
height: 200px;
background-color: orange;
}
.col2-row2 {
background-color: forestgreen;
height: 100%;
}
.col2-row3 {
height: 150px;
background-color: red;
}
#media (max-width: 768px) {
.container {
grid-template-columns: 1fr;
}
}
<div class="container">
<div class="col1">1</div>
<div class="col2">
<div class="col2-row1">2</div>
<div class="col2-row2">3</div>
<div class="col2-row3">4</div>
</div>
</div>

Header Sticky Position in CSS Grid Layout

I'm learning CSS Grid layout and i have a problem about positioning.
What i want is to create a page layout composed by a left-side menu, top-bar menu and a main content page like the image below:
I have been able to achieve the goal, but now i want to fix the position of the top bar and sidebar while main content is scrolling.
I set position:sticky to both containers but it does not working.
How can i fix?
Here is my code:
* {
margin: 0 !important;
padding: 0 !important;
box-sizing: border-box !important;
}
.grid-container {
display: grid;
grid-template-columns: auto 1fr;
grid-template-rows: 10% 100vh;
grid-template-areas:
"LeftMenu TopMenu"
"LeftMenu Main";
}
.LeftMenu {
background-color: #a4a4a4;
grid-area: LeftMenu;
width: 200px;
height: 100%;
}
.TopMenu {
background-color: #d49494;
grid-area: TopMenu;
width: 100%;
height: 100%;
display: flex;
}
.Main {
background-color: #8990eb;
grid-area: Main;
width: 100%;
height: 100vh;
}
<div class="xdg-component-appnav-menu">
<div class="grid-container">
<div class="LeftMenu">left menu</div>
<div class="TopMenu">top menu</div>
<div class="Main">
<p style="padding-bottom: 1000px;">Content</p>
</div>
</div>
</div>
You don't need position: sticky. It's extra complication and still isn't fully supported by some browsers.
Just use overflow: auto on the main container.
.grid-container {
display: grid;
height: 100vh;
grid-template-columns: 200px 1fr;
grid-template-rows: 10% 90%;
grid-template-areas:
"LeftMenu TopMenu"
" LeftMenu Main ";
}
.LeftMenu {
grid-area: LeftMenu;
background-color: #a4a4a4;
}
.TopMenu {
grid-area: TopMenu;
background-color: #d49494;
}
.Main {
grid-area: Main;
overflow: auto; /* key adjustment */
background-color: #8990eb;
}
body {
margin: 0;
}
<div class="xdg-component-appnav-menu">
<div class="grid-container">
<div class="LeftMenu">left menu</div>
<div class="TopMenu">top menu</div>
<div class="Main">
<p style="height: 1000px;">Content</p>
</div>
</div>
</div>