Reputation: 43
I have 7 components of a fixed width (256px) and margin: 20px
and I want them to be aligned in a grid, but I'm trying to get the last item in the last row to always be justified right so it lines up with the column furthest right. I also want the column grid to be centered on the page. I've tried a few things but I've gotten stuck.
I tried doing this with a flex box, and while it's entirely possible I'm missing something about flex boxes that could get this to work, I didn't have any luck. The closest I got was something like:
.grid {
display: flex;
flex-flow: row wrap;
justify-content: center;
}
.grid div {
margin: 20px;
width: 256px;
height: 48px;
}
.grid div:last-child {
margin-left: auto
}
But the justify-content, while it gets the components centered on the page, also, if the last row has less components than the other rows, centers those components and ruins the grid effect.
I also tried this without a flex box and kind of got close with just:
.grid div {
margin: 20px;
width: 256px;
height: 48px;
float: left;
}
.grid div:last-child {
float: right;
}
This is pretty close I'd just need a way to set the width of the grid to be a multiple of 256px (well, 296px because of the margins) and then center the grid in the parent. Totally doable with media-queries but I feel like there should be a more straightforward solution.
(Pictures in case I'm not explaining it well)
Behavior I'm looking for: https://i.sstatic.net/y5ySx.jpg
Behavior that's not right: https://i.sstatic.net/xakgw.jpg
HTML for reference:
<div class="grid">
<div></div>
<div></div>
<div></div>
<div></div>
<div></div>
<div></div>
<div></div>
</div>
Upvotes: 2
Views: 65
Reputation: 87191
With a couple of media queries you should be able to do this, where you use the pseudo elements as ghost elements, and fill the gap between the last and second last item.
Here I also gave the grid
a max width, so there can't be 5 in a row, and I did that because if you need that, you'll need an extra element as the second last to act as a ghost because it will take 3 ghost elements (2 pseudo + 1) to solve that.
If you need to fit 5 in a row, one simply double the size on one of the pseudo elements, 256px + 256px + 40px ( 40px for the margin ), for 6 in a row, 3 times the width etc.
html, body {
margin: 0;
}
.grid {
display: flex;
flex-flow: row wrap;
justify-content: center;
}
.grid div {
margin: 20px;
width: 256px;
height: 48px;
background: lightgray;
}
.grid div:last-of-type {
order: 2
}
@media screen and (min-width: 592px) {
.grid::after {
content: '';
margin: 20px;
width: 256px;
height: 0;
order: 1;
}
}
@media screen and (min-width: 888px) {
.grid::before {
content: '';
margin: 20px;
width: 256px;
height: 0;
order: 1;
}
}
@media screen and (min-width: 1184px) {
.grid::before {
display: none;
}
}
@media screen and (min-width: 1480px) {
.grid::before {
display: inline;
width: 552px;
}
}
<div class="grid">
<div></div>
<div></div>
<div></div>
<div></div>
<div></div>
<div></div>
<div></div>
</div>
Upvotes: 1
Reputation: 64174
As a proof of how stubborn I am, here is my solution.
The trick is to have a number of elements that is divisible by 2..3..4..5 so add as much extra elements as needed.
Of course, this is so ugly that I have choosen to hide the source code :-(
.grid {
display: flex;
flex-flow: row wrap;
justify-content: center;
border: solid 1px red;
}
.grid div {
margin: 20px;
width: 256px;
height: 48px;
background-color: tomato;
}
.grid div:last-of-type {
background-color: fuchsia;
order: 3;
margin-top: -68px;
}
.grid span {
margin: 0px 20px;
width: 256px;
height: 0px;
order: 2;
}
.grid span:first-of-type {
margin-top: 40px;
height: 48px;
}
<div class="grid">
<div></div>
<div></div>
<div></div>
<div></div>
<div></div>
<div></div>
<div></div>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
</div>
Upvotes: 1