Transpose table CSS grid - html

I have tabular data that is many columns wide and a couple of rows short, which works great on a desktop screen, but is too wide for mobile screens. How do I make this "table" responsive - transpose it - so that it is narrow and tall on mobile screens? I can't find clear explanation on the Internet. It is made of divs.

Like this with CSS grid:
.container {
display: grid;
grid-template-columns: repeat(5, 1fr);
}
.container div {
border: 1px solid black;
font-size: 18px;
text-align: center;
}
/* make table 'portait' instead of 'landscape' */
#media only screen and (max-width: 820px) {
.container {
grid-template-columns: repeat(3, 100px);
grid-template-rows: repeat(5, 30px);
grid-auto-flow: column;
}
}
<div class="container">
<div>PRODUCT</div>
<div>APPLE</div>
<div>MANGO</div>
<div>ORANGE</div>
<div>BANANA</div>
<div>Price</div>
<div>$50</div>
<div>$25</div>
<div>$30</div>
<div>$15</div>
<div>Quantity</div>
<div>1</div>
<div>11</div>
<div>8</div>
<div>20</div>
</div>

Related

Is it possible to build this header layout using Flexbox CSS?

I've been trying to figure out how to make this layout possible in CSS Flexbox, so far cannot figure out a way to make it work that doesn't involve hiding a duplicate to show only on desktop. Is this possible to do using Flexbox?
Image example of what I'm trying to achieve:
A solution in grid would be a lot nicer and this is a working example the breakpoint for mobile version happens in 800px,
I suggest you read the Grid Area Template system it make these kind of layouts in very modern and nice way
.parent{
width: 100%;
height:100vh;
display: grid;
grid-template-columns: 200px 1fr;
grid-template-rows: 1fr 1fr 1fr;
grid-template-areas: "blue red""blue red""green green";
gap: 10px;
}
.blue{
grid-area: blue;
width: 200px;
background: blue;
}
.red{
grid-area: red;
width: 100%;
background: red;
}
.green{
grid-area: green;
width: 100%;
height: 100%;
background: green;
}
#media screen and (max-width: 800px){
.parent{
grid-template-areas: "blue red"
"blue green";
grid-template-rows: 1fr 1fr;
}
}
<div class="parent">
<div class="red"></div>
<div class="green"></div>
<div class="blue"></div>
</div>

How to set gap size constant in between the cards in CSS?

In the first screenshot this is the full screen so the gap between the cards are fine:-
In the second screenshot when I decrease my window size then the gap automatically changes so its not constant:-
My css code is :
.cards {
padding-top: 10px;
margin: 0 auto;
/*max-width: 1000px;*/
display: grid;
/*grid-template-columns: repeat(5, 1fr); Recorrected below*/
grid-template-columns: repeat(auto-fill, minmax(262px, 1fr));
gap: 10px;
row-gap: 30px;
font-family: sans-serif;
}
how can I make the gap constant so that whether i reduce the window size or not the gap should remain constant and not reduce then nd then.
kindly pls help me with this i have just started to program.
You don't need the row-gap property. The gap set with a fixed value is enough to achieve what you are looking for.
Your items will flow taking a minimum of 262px and fitting as much per row as possible, separated 10px horizontally and vertically.
And maybe that margin: 0 auto is not needed.
remove row-gap and just use gap: 10px (or whatever value you prefer)
EDIT
Here's an example of using grid-gap.
.cards {
display: grid;
grid-gap: 30px;
grid-template-columns: repeat(3, 1fr);
grid-template-rows: repeat(auto-fill, 100px);
width: 100%;
}
.cards div {
background: coral;
width: 100%;
height: 100px;
}
<div class="cards">
<div>1</div>
<div>2</div>
<div>3</div>
<div>4</div>
<div>5</div>
<div>6</div>
<div>7</div>
<div>8</div>
<div>9</div>
<div>10</div>
</div>

How to display two divs next to each other on a smartphone?

I have 4 divs and on a normal computer screen, they come next to each other with the following code.
.parent {
display: grid;
grid-template-columns: repeat(4, 1fr);
grid-template-rows: 1fr;
grid-column-gap: 0px;
grid-row-gap: 0px;
}
.div1 {
grid-area: 1 / 1 / 2 / 2;
}
.div2 {
grid-area: 1 / 2 / 2 / 3;
}
.div3 {
grid-area: 1 / 3 / 2 / 4;
}
.div4 {
grid-area: 1 / 4 / 2 / 5;
}
<div class="parent">
<div class="div1">1</div>
<div class="div2">2</div>
<div class="div3">3</div>
<div class="div4">4</div>
</div>
When I view this on my smartphone, all 4 divs will display in 1 row.
How can I display 2 divs in 1 row? So the final result will be 2 rows with 2 divs each on a smartphone.
change this line: grid-template-columns: repeat(4, 1fr); to: grid-template-columns: repeat(2, 1fr); then you only have 2 columns per row.
then change this line: grid-template-rows: 1fr; to: grid-auto-rows: auto; to automatically insert as many rows as needed at size them to the highest content.
last but not least: delete css for all div-boxes as they are useless in this case anyway. Also its not the way it is or should be used.
use media queries to adjust design for different screen sizes as used in the sample below:
#media start the media query. with only screen you define that only the screen size should be used as rule. and (max-width: 480px) defines the rule to be applied for mobile screens (largest is 480px width for portrait mode).
.parent {
display: grid;
grid-auto-rows: auto;
grid-gap: 0px;
}
#media only screen
and (max-width: 480px) {
.parent {
grid-template-columns: repeat(2, 1fr);
}
}
#media only screen
and (min-width: 481px) {
.parent {
grid-template-columns: repeat(4, 1fr);
}
}
<div class="parent">
<div class="div1">1</div>
<div class="div2">2</div>
<div class="div3">3</div>
<div class="div4">4</div>
</div>
You can use #media screen to make custom Css for different screen sizes.
#media screen is used to specify different layout for various screen sizes.
You can find the guide here:
https://www.w3schools.com/cssref/css3_pr_mediaquery.asp
This guide also includes examples where you would get an idea how to unitize #media screen thing.

How can I collapse a row (remove a row) which doesn't have content in an explicitly declared CSS grid layout?

The question is similar to How do you collapse unused row in a CSS grid? but my rows are explicitly declared.
I have a CSS grid similar to below design:
But whenever I have no content/limited content, I'm getting some unwanted rows there. How can I remove those rows as it's adding unwanted space in my design?
I think I can't use grid-auto-rows or anything because I wanted that layout, for which I need to define the rows as in my CSS.
ref: how my layout looks when there's not enough content.
Please check the codepen:
With content: https://codepen.io/asim-coder/pen/JwJzWx
Without content: https://codepen.io/asim-coder/pen/mawomJ
.card {
display: grid;
grid-template-columns: 1fr 1fr 1fr;
grid-template-rows: 2fr 1fr 1fr 2fr;
grid-gap: 5px;
}
.card * {
/* styles for demonstational purposes */
background: #02750b;
color: #fff;
display: flex;
justify-content: center;
align-items: center;
padding: 5px;
}
.card :nth-child(2) {
grid-area: 1 / 2 / 3 / 3;
}
.card :nth-child(5) {
grid-area: 3 / 2 / 5 / 3;
}
.card :nth-child(4) {
grid-area: 2/ 1 / 4/ 2;
}
.card :nth-child(6) {
grid-area: 2/ 3 / 4/ 4;
}
p {
padding: 5px;
background: #b5b53f;
}
<div class="card">
<div>1</div>
<div>2</div>
<div>3</div>
<div>4</div>
<div>5</div>
<div>6</div>
<div>7</div>
<div>8</div>
</div>
<p>Some thing after the content</p>
You're defining the rows at the container level.
.card {
display: grid;
grid-template-columns: 1fr 1fr 1fr;
grid-template-rows: 2fr 1fr 1fr 2fr;
grid-gap: 5px;
}
But content is handled at the grid item level.
Therefore, when the container is asked to layout explicit tracks, it does the job without regard for the existence of content.
In your case, when content appears or disappears, there is no change to the container rules, so there is no reason for rows to disappear.
But I don't see any reason for explicit rows to make this layout work. Just take them out.
Note that fr units distribute free space in the container. But you haven't set a height on the container, which means there is no free space to distribute. This may lead to unexpected behavior across major browsers (depending on how they chose to render such a scenario). Try setting a height on the container for more proper and stable behavior.
.card {
display: grid;
grid-template-columns: 1fr 1fr 1fr;
/* grid-template-rows: 2fr 1fr 1fr 2fr; */
grid-gap: 5px;
}
.card * {
/* styles for demonstational purposes */
background: #02750b;
color: #fff;
display: flex;
justify-content: center;
align-items: center;
padding: 5px;
}
.card :nth-child(2) {
grid-area: 1 / 2 / 3 / 3;
}
.card :nth-child(5) {
grid-area: 3 / 2 / 5 / 3;
}
.card :nth-child(4) {
grid-area: 2/ 1 / 4/ 2;
}
.card :nth-child(6) {
grid-area: 2/ 3 / 4/ 4;
}
p {
padding: 5px;
background: #b5b53f;
}
<div class="card">
<div>1</div>
<div>2</div>
<div>3</div>
<div>4</div>
<div>5</div>
<div>6</div>
<div>7</div>
<div>8</div>
</div>
<p>Keep in mind you're using <i>fr</i> units in a container with no defined height. So expect free space to be distributed unevenly across examples.</p>
<div class="card">
<div>1</div>
<div>2</div>
<div>3</div>
</div>
<p>less space = smaller <i>fr</i> units = potentially shorter grid areas (browser behavior may vary)</p>

Why does grid-gap not work on mobile?

I've been playing around with CSS Grid recently and have noticed something that I can't see to find the answer to. Let's say I split my page out to have 2 columns, and then a row below it, with another column (which spans both columns). On mobile, I'd like them to stack one on top of the other and then go back to layout described above after a certain breakpoint. Here is the markup:
HTML
<div class="grid">
<div class="upper">
<div class="a">A</div>
<div class="b">B</div>
</div>
<div class="lower">
<div class="c">C</div>
</div>
</div>
SCSS
.upper, .lower {
display: grid;
}
.upper {
grid-template-columns: 1fr 1fr;
grid-template-rows: auto auto;
background-color:grey;
grid-gap:10px;
#media only screen and (max-width:800px) {
grid-template-columns: 1fr;
grid-template-rows: auto;
}
}
.lower {
grid-template-columns: 1fr;
grid-template-rows:auto;
background-color: green;
grid-gap:10px;
}
I've noticed that on mobile, even though I've defined grid-gap for both of my grid sections, on mobile when the columns stack, the grid-gap is not maintained. So in the fiddle below, when you make the window smaller, you can see that when the columns, stack one on top of the other, the gap between B and C is non existent. Here is the fiddle:
Fiddle
Hope I'm making sense!
EDIT: Bear in mind I'm only testing this in Firefox and Chrome (which support grid).
The grid-gap rule doesn't work between B and C because it doesn't apply.
This rule creates gutters between rows and columns inside a grid container.
But you are declaring grid-gap on .upper and .lower, two siblings in a block container. Their parent (.grid) is not a grid container because it doesn't have display: grid or inline-grid.
Therefore, grid-gap: 10px on .upper is creating a 10px gutter between A and B...
and grid-gap: 10px on .lower is creating a 10px gutter between.... nothing (.lower has only one grid item. grid-gap creates gutters between multiple grid items).
fiddle demo 1
For grid-gap to work among the .upper and .lower siblings you need to apply it to their parent, which must be a grid container.
fiddle demo 2
.grid {
display: grid; /* NEW */
grid-gap: 25px; /* NEW */
}
.upper, .lower {
display: grid;
}
.upper {
grid-template-columns: 1fr 1fr;
grid-gap: 25px;
}
.lower {
grid-template-columns: 1fr;
grid-template-rows: auto;
grid-gap: 10px; /* does nothing unless there are multiple grid items */
}
#media ( max-width:800px ) {
.upper {
grid-template-columns: 1fr;
grid-template-rows: auto;
}
}
.upper > * { border: 1px dashed red; }
.lower > * { border: 1px dashed blue; }
<div class="grid">
<div class="upper">
<div class="a">A</div>
<div class="b">B</div>
</div>
<div class="lower">
<div class="c">C</div>
</div>
</div>