I am aware I can get five image across a page by setting each image as width 20% and using flex-wrap: wrap. But how do I evenly space the images?
I tried justify-content: space-around; but that looks ridiculous. Padding messes up the 20% width calculation. So what's a good tact? I don't want the images to look like they are stitched together. If there are six images, there will be a large gap to right of the 6th image. I think that's fine.
article {
display: flex;
flex-wrap: wrap;
}
img {
width: 20%;
padding: 1em;
/* I want five across with image spacing, how do I achieve this? */
}
<article>
<img src="http://res.cloudinary.com/unee-t-staging/image/upload/c_fill,g_auto,h_500,w_500/Unee-T%20inspection%20report%20-%20placeholder%20images/table_succulent.jpg">
<img src="http://res.cloudinary.com/unee-t-staging/image/upload/c_fill,g_auto,h_500,w_500/Unee-T%20inspection%20report%20-%20placeholder%20images/table_succulent.jpg">
<img src="http://res.cloudinary.com/unee-t-staging/image/upload/c_fill,g_auto,h_500,w_500/Unee-T%20inspection%20report%20-%20placeholder%20images/table_succulent.jpg">
<img src="http://res.cloudinary.com/unee-t-staging/image/upload/c_fill,g_auto,h_500,w_500/Unee-T%20inspection%20report%20-%20placeholder%20images/table_succulent.jpg">
<img src="http://res.cloudinary.com/unee-t-staging/image/upload/c_fill,g_auto,h_500,w_500/Unee-T%20inspection%20report%20-%20placeholder%20images/table_succulent.jpg">
<img src="http://res.cloudinary.com/unee-t-staging/image/upload/c_fill,g_auto,h_500,w_500/Unee-T%20inspection%20report%20-%20placeholder%20images/table_succulent.jpg">
</article>
I would wrap the images in a tag to manage element width and image width separately. Then apply the width and padding onto the containing element. Set the width of img to auto, and max-width to 100% to prevent the images from stacking.
In addition, you can alter the number of images that display at different screen sizes by changing the wrapper class properties.
When it comes to flexbox, I always reach for CSS-tricks!
.flexbox {
display: flex;
flex-flow: row wrap;
}
.flexbox .image {
width: 20%;
padding: 0.5em;
}
.flexbox img {
width: auto;
max-width: 100%;
}
* {
box-sizing: border-box;
}
<div class="flexbox">
<div class="image"><img src="https://qph.fs.quoracdn.net/main-qimg-0e316e1a1e2a600d0b922cddb3a5c6c2"></div>
<div class="image"><img src="https://qph.fs.quoracdn.net/main-qimg-0e316e1a1e2a600d0b922cddb3a5c6c2"></div>
<div class="image"><img src="https://qph.fs.quoracdn.net/main-qimg-0e316e1a1e2a600d0b922cddb3a5c6c2"></div>
<div class="image"><img src="https://qph.fs.quoracdn.net/main-qimg-0e316e1a1e2a600d0b922cddb3a5c6c2"></div>
<div class="image"><img src="https://qph.fs.quoracdn.net/main-qimg-0e316e1a1e2a600d0b922cddb3a5c6c2"></div>
<div class="image"><img src="https://qph.fs.quoracdn.net/main-qimg-0e316e1a1e2a600d0b922cddb3a5c6c2"></div>
<div class="image"><img src="https://qph.fs.quoracdn.net/main-qimg-0e316e1a1e2a600d0b922cddb3a5c6c2"></div>
</div>
If you want the borders of the images to be aligned with the borders of the container and not offset by the padding, I would opt for a solution that relies on one sided margin, but that does not apply to the last item of each row.
Considering a row count of 5 items, and an image to image margin of 1% of the container's width, with the following DOM structure:
<div class="flex-container">
<div>
<img src="http://res.cloudinary.com/unee-t-staging/image/upload/c_fill,g_auto,h_500,w_500/Unee-T%20inspection%20report%20-%20placeholder%20images/table_succulent.jpg">
</div>
<div>
<img src="http://res.cloudinary.com/unee-t-staging/image/upload/c_fill,g_auto,h_500,w_500/Unee-T%20inspection%20report%20-%20placeholder%20images/table_succulent.jpg">
</div>
<div>
<img src="http://res.cloudinary.com/unee-t-staging/image/upload/c_fill,g_auto,h_500,w_500/Unee-T%20inspection%20report%20-%20placeholder%20images/table_succulent.jpg">
</div>
<div>
<img src="http://res.cloudinary.com/unee-t-staging/image/upload/c_fill,g_auto,h_500,w_500/Unee-T%20inspection%20report%20-%20placeholder%20images/table_succulent.jpg">
</div>
<div>
<img src="http://res.cloudinary.com/unee-t-staging/image/upload/c_fill,g_auto,h_500,w_500/Unee-T%20inspection%20report%20-%20placeholder%20images/table_succulent.jpg">
</div>
<div>
<img src="http://res.cloudinary.com/unee-t-staging/image/upload/c_fill,g_auto,h_500,w_500/Unee-T%20inspection%20report%20-%20placeholder%20images/table_succulent.jpg">
</div>
</div>
Apply the following styles:
.flex-container {
display: flex;
flex-wrap: wrap;
}
.flex-container div {
max-width: 19.2%; /* (100 - ((items_per_row - 1) * 1) / (items_per_row)*/
margin-bottom: 15px;
}
.flex-container div img {
width: 100%;
height: 100%;
}
.flex-container div:not(:nth-child(5n)) { /* matches number of items per row */
margin-right: 1%;
}
Example on CodePen: https://codepen.io/anon/pen/wEKmdG
Disclaimer: I'm working with #hendry on the same project...
Related
im trying to create a footer with a few social media icons...however, the method i've tried has resulted in the following problem :
expectation:
reality:
as you can see i'm failing in bringing the social media icons closer together... i tried setting the columns flex % to - however that pulls everything closer together towards the left of the screen...
here is my .row and .column as well as the social media icons..
.row {
display: flex;
}
.column {
flex: 30%;
padding: 00px;
}
.marginauto1 {
margin: 30px auto 20px;
display: block;
horizontal-align; middle;
vertical-align: middle;
}
<footer class= "marginauto1">
<center><div class="row">
<div class="column">
<center><a class= "pointer" href="twitter_url">
first time taking a stab at this on my own and I'm just really stuck here.. any help or tips would be appreciated!
If you want to put all your icons together in the middle:
img{
height:50px;
}
div{
display:flex;
justify-content: center;
background-color:blue;
}
<footer>
<div>
<img src="data:image/png;base64,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">
<img src="https://encrypted-tbn0.gstatic.com/images?q=tbn:ANd9GcRyFcxKQYRAhR9esHvHVZokZGCYFNC1_rMHhw&usqp=CAU">
</div>
</footer>
<center> tag will not applicable if you are using flexbox. Instead flex-box itself has some properties that you can make use of. In your use-case you can go with justify-content: center
.row{
display: flex;
justify-content: center;
}
.item{
color: red;
background: lightblue;
margin-left: 20px;
}
<footer class= "marginauto1">
<div class="row">
<div class="item 1">
<h1>Telegram</h1>
</div>
<div class="item 2">
<h1>Facebook</h1>
</div>
<div class="item 3">
<h1>Twitter</h1>
</div>
</div>
</footer>
If you don't want any space in between of 2 or more items you can remove the margin.
Its working as expected. You have defined .column with flex: 30%; which intrun will split into 3
flex-grow: 1;
flex-shrink: 1;
flex-basis: 30%;
So what have you done is allowing the element to grow till the available width with a minimum of 30% relative to the container. This is because the flex-basis is defined. This will be 33% each.
For your soution to work remove flex: 30%; from .column. This will take the width depending on the content.
If you want some gap between the element, try adding some margin or padding, I have used margin for that. Or you can set the width of column element.
Inorder to align the items center in horizontal axis, use justify-content: center; for the flex element.
Working Fiddle
.row {
display: flex;
justify-content: center;
}
.column {
padding: 0px;
margin-right: 20px;
}
.marginauto1 {
margin: 30px auto 20px;
display: block;
}
.pointer img {
width: 50px;
}
<footer class="marginauto1">
<div class="row">
<div class="column">
<a class="pointer" href="">
<img src="https://cdn1.iconfinder.com/data/icons/logotypes/32/twitter-512.png" alt="">
</a>
</div>
<div class="column">
<a class="pointer" href="">
<img src="https://cdn1.iconfinder.com/data/icons/logotypes/32/twitter-512.png" alt="">
</a>
</div>
<div class="column">
<a class="pointer" href="">
<img src="https://cdn1.iconfinder.com/data/icons/logotypes/32/twitter-512.png" alt="">
</a>
</div>
</div>
</footer>
hello I need to basicaly display a table but with flex (only because I need to adjust the look for mobile)
.container {
display: flex
}
<div class="container">
<div class="row">
<div>1000</div>
<div>mary</div>
</div>
<div class="row">
<div>1</div>
<div>john</div>
</div>
<div class="row">
<div>11</div>
<div>mike</div>
</div>
</div>
how can I make each column have the same width? or at least the width of the largest item.
If you apply flex-grow: 1 to each div in the .row then it will expand accordingly. Note that the .row divs need the display flex (flex only apply to the DIRECT children of the flexed element.
The width can be set by using flex-basis and calc() and dividing the full-width by the number of columns you want (2 in this case). I added a border to demonstrate.
I would be remiss if I didn't suggest that the best tool to display a table structure - is a ... table... then you can work out how to modifiy for responsive layout - but the semantic structure of a table is correct for tabulr content.
.container {
width: 100%;
}
.row {
display: flex;
width: 100%;
}
.row div {
flex-grow: 1;
flex-basis: calc(100% / 2);
padding: 4px 8px;
border: solid 1px red;
}
<div class="container">
<div class="row">
<div>1000</div>
<div>mary</div>
</div>
<div class="row">
<div>1</div>
<div>john</div>
</div>
<div class="row">
<div>11</div>
<div>mike</div>
</div>
</div>
Use flex-basis to set the 'default' width first.
Use flex-grow and/or flex-shrink to allow it to grow /shrink
Use max-width' and min-width` to define by how much it can grow/shrink
.container{ #Stack the div inside the conainer
display:flex;
flex-flow: columns nowrap;
}
.row{ # Set div as cell in the row.
display:flex;
flex-flow: row nowrap;
flex-basis: 33%; # Calculate width from there.
flex-grow:1; #Allow resizing bigger
flex-shrink:1; #Allow resize smaller.
max-width:50%; #Adjust to your liking
min-width:25%; #Adjust o your liking
}
Please consider this ressource https://css-tricks.com/snippets/css/a-guide-to-flexbox/
You can add a flex-basis to the .row items by doing this:
.row {
flex-basis:calc(100% / 3);
}
.container {
width: 100%;
}
.row {
display: flex;
width: 100%;
}
.row div {
flex-grow: 1;
flex-basis: calc(100% / 2);
padding:10px;
margin: 5px;
background: #eee;
}
<div class="container">
<div class="row">
<div>1000</div>
<div>mary</div>
</div>
<div class="row">
<div>1</div>
<div>john</div>
</div>
<div class="row">
<div>11</div>
<div>mike</div>
</div>
</div>
My challenge is:
I want to have a grid with a fixed amount of columns (which can later be adjusted via javascript) and a flexible amount of rows of equal height.
The number of rows are determined by the amount of grid items, which are UI cards.
These cards should fill out the entire height of their respective cell but MUST not increase the height of the row. So basically max-height = row-height assigned by grid
Then inside these cards we have the typical three parts: Header, Body and Footer. The body MUST be scroll-able, if more list items exists than the row-height allows.
I've tried to implement this on stackblitz
https://stackblitz.com/edit/angular-3gkmtm
What i don't understand is
Why the cards "stretches" the row when more items appear
How to achieve the scroll-able card body section without manually using a fixed height (like in the example i use max-height)
Why when there are more then 3 rows, it overflows
Please help!
<article>
<section>
<h2>Fixed Gird with scrollable cards</h2>
</section>
<section>
<button (click)="onAdd()">Add</button>
<button (click)="onRemove()">Remove</button>
</section>
<section class="remaining-height">
<div class="grid-container">
<div class="grid-item" *ngFor="let card of cards">
<div class="card">
<div class="card-header">Card #{{card}}</div>
<div class="card-body card-flexible-scroll">
<div class="list-item" *ngFor="let item of list">{{item}}</div>
</div>
<div class="card-footer">
Some Footer
</div>
</div>
</div>
</div>
</section>
</article>
article{
display: flex;
flex-direction: column;
height: 100%;
}
.remaining-height{
flex:1
}
.grid-container {
display: grid;
grid-gap: 0.5rem;
height: 100%;
grid-auto-rows: auto;
grid-template-columns: repeat(5, auto);
}
.grid-item{
display: flex;
padding:24px;
}
.card{
display: flex;
flex-direction: column;
width: 100%;
height:100%;
background:#ccc;
}
.card-body{
.list-item{
padding: 6px;
background:#fcd3d3;
}
.list-item:nth-child(even){
background:#efefef;
}
}
.card-flexible-scroll{
flex:1;
overflow-y:auto;
max-height: 300px; // <= no max height
}
Angular Controller to generate cards and list items
```js
export class AppComponent {
name = "Angular";
cards = new Array(8).fill(0).map((_,idx)=>idx+1);
list = new Array(30).fill(0).map((_,idx)=>idx+1);
onAdd() {
this.cards.push(this.cards.length + 1);
}
onRemove() {
this.cards.pop();
}
}
global style
html , body{
height: 100vh;
overflow: hidden;
}
If I understand correctly what you are trying to do you want that the card body takes all the available row space between the header and footer and not force the card to be bigger than the row if it contains items.
It is possible to achieve that with adding another div with absolute positioning inside the card body div that is sized to the full body height then the items inside will overflow correctly.
Here is the changed template:
<article>
<section>
<h2>Fixed Gird with scrollable cards</h2>
</section>
<section>
<button (click)="onAdd()">Add</button>
<button (click)="onRemove()">Remove</button>
</section>
<section class="remaining-height">
<div class="grid-container">
<div class="grid-item" *ngFor="let card of cards">
<div class="card">
<div class="card-header">Card #{{card}}</div>
<div class="card-body">
<div class="card-flexible-scroll">
<div class="list-item" *ngFor="let item of list">{{item}}</div>
</div>
</div>
<div class="card-footer">
Some Footer
</div>
</div>
</div>
</div>
</section>
</article>
And the updated CSS:
.card-body{
.list-item{
padding: 6px;
background:#fcd3d3;
}
.list-item:nth-child(even){
background:#efefef;
}
position: relative;
flex:1;
}
.card-flexible-scroll{
position: absolute;
width: 100%;
height: 100%;
max-height: 100%;
overflow-y: auto;
}
I created a fork of your StackBlitz where you can see how it works. If this is not what you look for please explain more.
In this jsfiddle, I want the Author element to be aligned between the various card elements. I can't see how to stretch the element containing the details to match the variably sized elements in the same row.
The goal is to have the Author lines lining up horizontally across the rows.
.container {
display: flex;
flex-flow: row wrap;
margin: 10px;
}
.card {
width: 200px;
margin: 10px;
}
.product_detail {
display: flex;
flex-direction: column;
justify-content: space-between;
border: 1px solid pink;
}
.detail_item {
border: 1px solid blue;
flex: 1;
}
img {
width: 100%;
}
<div class='container'>
<div class="card">
<section>
<img src="https://c.booko.info/covers/34edd12eb5c21388/v/600.jpeg" itemprop="image" size="500x750">
</section>
<section class="product_detail">
<div itemprop="name" class='detail_item'>
A Book Title
</div>
<div class="detail_item">A Subtitle might be here</div>
<div itemprop="author" class='detail_item'>Author</div>
</section>
</div>
<div class="card">
<section>
<img src="https://c.booko.info/covers/34edd12eb5c21388/v/600.jpeg" itemprop="image" size="500x750">
</section>
<section class="product_detail">
<div itemprop="name" class='detail_item'>
A Book Title which is much longer and takes up a few lines
</div>
<div class="detail_item">A Subtitle might be here</div>
<div itemprop="author" class='detail_item'>Author</div>
</section>
</div>
<div class="card">
<section>
<img src="https://c.booko.info/covers/34edd12eb5c21388/v/600.jpeg" itemprop="image" size="500x750">
</section>
<section class="product_detail">
<div itemprop="name" class='detail_item'>
A Book Title
</div>
<div class="detail_item">A Subtitle might be here</div>
<div itemprop="author" class='detail_item'>Author</div>
</section>
</div>
</div>
As I understood it, you are trying to have the Author div anchored to the bottom of each card.
Assuming I understood correctly, you were pretty close. Here's what was missing:
the .card div needed to be a flex container
the .product_detail section needed to stretch to fill its available space
the Author div needed to be anchored to the bottom
Here's the CSS that changed:
.card {
display: flex;
flex-direction: column;
}
.product_detail {
flex: 1;
}
.detail_item[itemprop="author"] {
margin-top: auto;
}
Here's an updated Fiddle
Note: if you don't want the .detail_item divs to be vertically evenly distributed, you can just remove the flex: 1; property from .detail_item which would look like this.
Hope this helps. Good luck!
I am wondering if this is possible: I have a header that can contain a variable amount of text. Below that I have another element which I want to take up the remaining height of the page.
<div class="header row">
<div class="title column large-5">Potentially very long text</div>
<div class="menu column large-7">Menu items</div>
</div>
<div class="content">
</div>
<div class="footer">
</div>
Normally I would do this using calc, eg:
.content {
height: calc(100vh - 75px);
}
Where 75px is the set height of .header.
But in this example, the .header element is dynamic and does not have a set height. Only a padding and font-size are set.
To complicate things, this also uses the Foundation Grid layout, which makes me nervous about using display: table (.title and .menu sit side by side on desktop, but stacked on mobile) .
Is there anyway to get the height of the dynamic header element (without resorting to JQuery)?
You can use flexbox and set .content to flex-grow: 1 so that it will fill to grow the available space.
body {
display: flex;
flex-direction: column;
min-height: 100vh;
margin: 0;
}
.content {
flex-grow: 1;
background: #eee;
}
<div class="header row">
<div class="title column large-5">Potentially very long text</div>
<div class="menu column large-7">Menu items</div>
</div>
<div class="content">
</div>
<div class="footer">
</div>
I made a small pen to show the way to do this using flex box, it involved changing your markup a bit:
css:
.container {
display: flex;
flex-direction: column;
height: 250px; // whatever you want here
}
.header {
width: 100%;
background: red;
padding: 10px;
}
.content {
background: yellow;
width: 100%;
flex-grow: 1;
}
So the content will always take the available space inside the content div.
check the whole pen: http://codepen.io/anshul119/pen/yMYeLa
hope this helps.