I've been trying - and failing - to get the following grid layout in CSS flexbox (no grid, I need to support older browsers):
As you can see, I need a
Menu bar (dark grey), always on top, always full width and fixed height
a 2x2 grid (blue and white) that's full width on portrait mode and same aspect ratio on landscape
the purple container using the rest of the available space. Stacked below on portrait and to the side on landscape.
I know about media queries, and I guess I need one to limit the .grid width, but I don't know how to get the landscape layout with that.
Looks simple enough but I guess I need your help! :(
html {
height: 100%;
}
body {
margin: 0;
padding: 0;
min-height: 100%;
display: flex;
flex-direction: column;
}
.container {
display: flex;
flex: 1 0 auto;
flex-direction: column;
}
.row {
display: flex;
flex: 1 0 auto;
flex-direction: row;
flex-wrap: wrap;
}
.col {
flex: 1 0 auto;
}
.grid {
width: 50vw;
}
.topbar {
background-color: #1f1f1f;
max-height: 50px;
}
.purple {
background-color: #663353;
}
.purple p {
padding: 2em;
}
.grid:nth-child(3n+1) {
background-color: #6798cc;
}
<div class="container">
<div class="row topbar"></div>
<div class="row wrap">
<div class="col grid"></div>
<div class="col grid"></div>
<div class="col grid"></div>
<div class="col grid"></div>
</div>
<div class="row">
<div class="col purple">
<p>Lorem ipsum dolor sit amet, consectetur adipisicing elit. Id ipsam rerum laborum velit obcaecati, eveniet reiciendis, veritatis ipsa ducimus recusandae quidem nesciunt dolor facilis sed neque quod.</p>
</div>
</div>
</div>
Related
I'm a bit confused with how Chrome's browser/dev tools inspector is highlighting the width of a div:
In the following code, .siteFooter_upperFooterFlex__Ut3VI (yellow) visually displays as 100% width of .siteFooter_upperFooterContent__Jt8SZ (light-blue) with the inspector closed, however, when I inspect .siteFooter_upperFooterFlex__Ut3VI (yellow), I see:
Why doesn't the inspector show the yellow background color reaching the full width, which is 100%?
.siteFooter_upperFooterContent__Jt8SZ {
position: relative;
z-index: 20;
padding-top: 3rem;
padding-bottom: 3rem;
background-color: lightblue;
}
.siteFooter_upperFooterFlex__Ut3VI {
display: flex;
align-items: stretch;
justify-content: center;
background-color: yellow;
}
.siteFooter_separatorWrap___XQCE {
display: flex;
align-items: center;
justify-content: center;
}
#media (min-width: 768px) {
.siteFooter_upperFooterLeft__0MGuC {
width: 35%;
padding-left: 4rem;
padding-right: 4rem;
}
.siteFooter_upperFooterRight__FGTWq {
display: flex;
width: 35%;
flex-direction: column;
padding-left: 4rem;
padding-right: 4rem;
}
}
<div class="siteFooter_upperFooterContent__Jt8SZ">
<div class="siteFooter_upperFooterFlex__Ut3VI">
<div class="siteFooter_upperFooterLeft__0MGuC">
<div class="siteFooter_upperFooterTextWrap__Pn_No">
<p class="siteFooter_upperFooterText__ofee9">Quisque varius libero sit amet nisl blandit dictum.</p>
</div>
<div class="siteFooter_upperFooterButton__1p9RV"><a class="buttonLink_black__TlKdt"
href="/contact/sales/">Talk to Us</a></div>
</div>
<div class="siteFooter_separatorWrap___XQCE">
<div class="siteFooter_separator__NRxtG"></div>
</div>
<div class="siteFooter_upperFooterRight__FGTWq">
<div class="siteFooter_upperFooterTextWrap__Pn_No">
<p class="siteFooter_upperFooterText__ofee9">Quisque varius libero sit amet nisl blandit dictum.</p>
</div>
<div class="siteFooter_upperFooterButton__1p9RV"><a class="buttonLink_white__zKdgU"
href="https://sandbox.mandoemedia.com/sandbox-wizard">Quisque varius libero sit amet nisl blandit dictum.</a></div>
</div>
</div>
</div>
This appears to be a quirk of Chromium's dev tools implementation; I suppose it is Chromium trying to be helpful. The dev tools are showing you how much of the flex item's width is taken up by the child elements vs how much is 'padded' by the flex layout (the blueish purple boxes on the left and right edges). Note that I've specified Chromium here, not just Chrome; other Chromium browsers like Edge appear to have this "feature", too.
When you hover, note that the width amount shown (for your screenshot, that's 1157px) is more than the width of each child container added together.
The dev tools in Firefox do not make such a distinction and just show you how much space the flex item effectively takes up (which is the full width).
So here is the link to my project repository
https://github.com/iamlovingawareness/EdgeLedger/tree/main
In the following code snippet I am not able to implement this change:
in the solutions and cases section when the max-width is 768px it should stack one on top of the other but when I make the necessary changes in my styles.css file it shows as an error.
This is what I implemented as follows:
#media (max-width: 768px) {
.navbar {
flex-direction: column;
height: 120px;
padding: 20px;
}
.navbar a {
padding: 10px 10px;
margin: 0 3px;
}
.flex-items {
flex-direction: column;
}
.flex-columns .column,
.flex-grid .column {
flex-direction: column;
flex: 100%;
max-width: 100%;
}
.team img {
width: 70%;
}
}
Supporting HTML snippet
<section class="solutions flex-columns">
<div class="row">
<div class="column">
<div class="column-1">
<img src="./image_resources/home/people.jpg" alt="" />
</div>
</div>
<div class="column">
<div class="column-2 bg-primary">
<h4>What you are loooking for</h4>
<h2>We provide bespoke solutions</h2>
<p>
Lorem ipsum dolor sit amet consectetur adipisicing elit. Est,
aut!
</p>
<a href="#" class="btn btn-outline"
><i class="fas fa-chevron-right"></i> Read More</a
>
</div>
</div>
</div>
</section>
Where .flex-columns . columns is what is supposed to do the thing but is not.
Kindly help me out thank you
Update: Went to chrome dev tools to see what was going on and saw this in the element property section:
Here as you can see there is a slash on the property that is supposed to be acting when the max-width is 768px. My question now is how do I find out where it has been overridden and make the necessary changes.
Thanks !
I'm trying to create a 3X3 image (these are image mocks of videos) gallery in a react app. I'm using sass and flexbox grid, and I'm having some trouble with css and responsiveness issues across multiple screen sizes:
here's how it looks like(as it should) on a huge iMac screen(5120 x 2880)
And on a normal sized Laptop screen, it gets messy and even the background image is breaking for some reason:
My goal is to have a responsive 3x3 grid on most common screen sizes, going down to 2x3 or 1x2 on very small screens. the size of every image must be in same ratio for all screens(if the image must resize itself to fit, so is the rest of the page).
I used create-react-app and Sass. I also have access to react-bootstrap but I haven't used any of it yet, trying to make this screen with pure flexbox. I tried wrapping every image with a wrapper div and make special rules on it but it didn't help.
Thanks for the help in advance, for the record, I'm not very experienced with advanced css, previously used basic bootstrap and helper libraries, trying to make this on my own mostly for learning purposes.
Dashboard.jsx
<div className="dashboard-page-wrapper">
<div className="page-content-wrapper">
<Gallery videosAmount = {6} videoUrl = {video}/>
</div>
</div>
Dashboard.scss
.dashboard-page-wrapper {
background-image: url("../../assets/map_bg.png");
height: 100vh;
background-size: cover;
.page-content-wrapper {
width: calc(100% - 290px);
}
}
Gallery.jsx
<div className="video-gallery-wrapper">
<ImageGallery videosAmount={videosAmount} videoUrl= {videoUrl} />
</div>
Gallery.scss
.video-gallery-wrapper {
min-height: 400px;
display: flex;
display: -webkit-flex;
flex-wrap: wrap;
flex-direction: row;
justify-content: flex-start;
align-items: auto;
align-content: center;
padding: 50px;
&:after {
display: block;
flex: 999 999 auto;
}
.image-wrapper {
img {
flex: 0 0 auto;
margin: 20px 10px 20px 20px;
height: 305px;
width: 479px;
}
}
}
Flexbox layout requires your HTML markup to have a certain structure. Because you provided prebuilt code I whipped up a comparable example that I hope helps.
The only place you need any flexbox rules is on the flex container and the flex children, that must be direct child elements of the flex container.
.wrapper {
display: flex;
flex-wrap: wrap;
justify-content: space-between;
}
Here, I am applying flexbox layout to the container with display: flex. The flex-wrap rule allows the items to flow into multiple lines. And justify-content: space-between makes the items sit up against the left and right edges of the container. This provides a vertical gutter between items as long as they do not take up all the available horizontal space.
.video-item {
flex: 0 0 31%;
}
The flex child elements get this flex rule, the value is shorthand for flex-grow: 0, flex-shrink: 0, and flex-basis: 31%. The flex basis of flex items establishes a starting width, and since I have "turned off" grow and shrink the basis serves as the width from here on.
The images you put into the document will try and fight with the sizing of these divs so you need to instruct the images to obey the size of their wrapper div:
.video-wrap img {
width: 100%;
height: auto;
}
Lastly, I just change the flex-basis of the items at various screen sizes, using media queries, to control the number of items across. Check out the full example in full page mode and play with the screen size.
body {
background: #ccc;
margin: 0;
padding: 20px;
}
.wrapper {
display: flex;
flex-wrap: wrap;
justify-content: space-between;
}
.video-item {
flex: 0 0 31%; /* tweak the thrid value to adjust the vertical gutters */
background: #fff;
margin-bottom: 20px;
}
.video-wrap img {
width: 100%;
height: auto;
}
.text-wrap {
text-align: center;
padding: 10px;
}
#media (max-width: 640px) {
.video-item {
flex: 0 0 48%; /* 2 across */
}
}
#media (max-width: 480px) {
.video-item {
flex: 0 0 100%; /* 1 accross */
}
}
<div class="wrapper">
<div class="video-item">
<div class="video-wrap">
<img src="https://picsum.photos/270/180" />
</div>
<div class="text-wrap">
Lorem ipsum dolor sit amet, consectetur adipiscing elit.
</div>
</div>
<div class="video-item">
<div class="video-wrap">
<img src="https://picsum.photos/270/180" />
</div>
<div class="text-wrap">
Lorem ipsum dolor sit amet, consectetur adipiscing elit.
</div>
</div>
<div class="video-item">
<div class="video-wrap">
<img src="https://picsum.photos/270/180" />
</div>
<div class="text-wrap">
Lorem ipsum dolor sit amet, consectetur adipiscing elit.
</div>
</div>
<div class="video-item">
<div class="video-wrap">
<img src="https://picsum.photos/270/180" />
</div>
<div class="text-wrap">
Lorem ipsum dolor sit amet, consectetur adipiscing elit.
</div>
</div>
<div class="video-item">
<div class="video-wrap">
<img src="https://picsum.photos/270/180" />
</div>
<div class="text-wrap">
Lorem ipsum dolor sit amet, consectetur adipiscing elit.
</div>
</div>
<div class="video-item">
<div class="video-wrap">
<img src="https://picsum.photos/270/180" />
</div>
<div class="text-wrap">
Lorem ipsum dolor sit amet, consectetur adipiscing elit.
</div>
</div>
</div>
I have some h2 text that is currently aligned to the left in the mobile view, above a centered div. How can I instead align it flush left relative to the div in the mobile view (with media query provided in the CSS below applied)?
CodePen
Relevant HTML:
<section class="container-projects">
<h2 class="portfolio-header">Featured Work</h2>
<div class="project">
Relevant CSS:
.portfolio-header {
/* Puts header in its own row without removing from container with row flex direction (setting parent container to wrap also required) */
width: 100%;
text-align: left;
color: #7d97ad;
}
.container-projects {
display: flex;
/* Parent container needs this for flex-item to take full width in row */
flex-wrap: wrap;
flex-direction: row;
justify-content: space-between;
margin: 2em 0;
}
/* Special styling for screens up to 767px wide, inclusive (applies to landscape phones) */
#media screen and (max-width: 767px) {
header, .container, footer {
max-width: 100%;
}
/* Must specify max-width for img even though parent .container has the same declaration because max-width isn't inherited */
.container img {
max-width: 100%;
}
.project {
/* Centers projects (aligned left otherwise) */
margin: 0 auto;
}
}
https://codepen.io/anon/pen/OZjWwJ?editors=1100
Slightly modified HTML
<section class="portfolio">
<h2 class="portfolio-header">Featured Work</h2>
<div class="container-projects">
<div class="project">
<img class="project-image" src="https://image.ibb.co/hv4c8n/santorini_small.jpg" alt="View from island of Santorini on a sunny day">
<h3>Project No. 1</h3>
<p>Lorem ipsum dolor sit amet, consectetur adipiscing elit.</p>
</div>
<div class="project">
<img class="project-image" src="https://image.ibb.co/c9sKM7/coast_small.jpg" alt="Distant view of a rugged island with a sailboat nearby">
<h3>Project No. 2</h3>
<p>Lorem ipsum dolor sit amet, consectetur adipiscing elit.</p>
</div>
<div class="project">
<img class="project-image" src="https://image.ibb.co/eO9oES/mediterranean_small.jpg" alt="Bird's eye view of a rocky beach with clear turquoise waters">
<h3>Project No. 3</h3>
<p>Lorem ipsum dolor sit amet, consectetur adipiscing elit.</p>
</div>
</div>
</section>
and CSS
.portfolio {
margin: 0 auto;
width: 100%;
}
#media screen and (max-width: 992px) {
.portfolio {
width: 90%;
}
}
This way, you are wrapping both your h2 and your project images in one container, which makes it a little more logical to manage their margin on screen. margin: 0 auto aligns the container at the center of the screen, which is desirable on all screen widths.
The 992px media query comes from Bootstrap 4's standardized grid system: https://getbootstrap.com/docs/4.0/layout/grid/#grid-options
You can add media query for mobile
#media screen and (max-width: 600px) {
.portfolio-header {
width: 300px;
margin: 10px auto;
}
}
I would like to achieve a result similar to balancing text lines in print but for block elements. Say a collection of 50/50px boxes in a 300/100px container. Floating the boxes within the container will make them fill up one "row", then wrap onto the next one like this:
[1][2][3][4][5][6]
[7]
I would like them to "wrap" in a more balanced way:
[1][2][3][4]
[5][6][7]
or even better, have them "wrap" at every column filling up space as they go:
[1][3][5][7]
[2][4][6]
I figured you can do this with CSS columns but it feels like a hack because the container element need to be float:left or display:inline-block to force columns to stick together, it needs a constrained height etc. I have added a snippet for reference.
Is there a more genuine CSS way to achieve this?
.wrap {
display: inline-block; /*Needs this so make colums stick together*/
columns: 100px;
column-gap: 0;
height: 200px;
}
.wrap>div {
width: 98px;
height: 98px;
background: red;
/* styling only */
overflow: hidden;
text-overflow: ellipsis;
white-space: nowrap;
border: 1px solid blue;
}
<div class="wrap">
<div>1Lorem ipsum dolor sit amet, consectetuer adipiscing elit.</div>
<div>2Mauris eu risus.</div>
<div>3Vestibulum auctor dapibus neque.</div>
<div>4Consectetuer adipiscing elit.</div>
<div>5Eu risus.</div>
<div>6Vestibulum auctor dapibus neque.</div>
<div>7Lorem ipsum dolor sit amet</div>
<div>8Aliquam tincidunt mauris eu risus. Lorem ipsum dolor sit amet, consectetur adipisicing elit.</div>
<div>9Vestibulum auctor dapibus neque.</div>
</div>
Here's a flexbox solution: Using flex-direction: column and flex-wrap: wrap on the parent element you can make the items wrap from top to bottom and fill another column once the column is filled.
This is the code to get flexbox working:
display: flex;
flex-direction: column;
flex-wrap: wrap;
align-content: flex-start;
And here's a demo:
.wrap {
background-color: silver;
height: 100px;
width: 400px;
display: flex;
flex-direction: column;
flex-wrap: wrap;
align-content: flex-start;
}
.box {
height: 50px;
width: 50px;
background-color: red;
box-sizing: border-box;
border: 1px solid white;
}
<div class="wrap">
<div class="box">1</div>
<div class="box">2</div>
<div class="box">3</div>
<div class="box">4</div>
<div class="box">5</div>
<div class="box">6</div>
<div class="box">7</div>
<div class="box">8</div>
<div class="box">9</div>
<div class="box">10</div>
</div>