Responsive design with CSS3 - html

I used to work with responsive design. Now I have a feeling, but not sure, that it is possible to manage the position of each div by its id or class. For example:
<div id='first'></div>
<div id='second'></div>
<div id='third'></div>
In CSS you might be able to say:
#media (max-width: 600px) {
// pseudo code
#second: after #third
}
#media (max-width: 300px) {
// pseudo code
#first: after #third
}
Is it possible to manage the element that way without giving the position a value, left or right a value?

You can do this with flexbox using the order property.
FIDDLE (Resize browser window)
.container {
display: flex;
}
.container div {
display: inline-block;
margin: 40px;
width: 100px;
height: 100px;
}
.first {
background: gold;
}
.second {
background: tomato;
}
.third {
background: aqua;
}
#media (max-width: 900px) {
.second {
order: 3;
}
}
#media (max-width: 600px) {
.second {
order: 1;
}
}
.first {
order: 3;
}
}
<div class="container">
<div class="first">first</div>
<div class="second">second</div>
<div class="third">third</div>
</div>
Check out this css-tricks article for an overview of flexbox.

Related

Any Flexbox Better dynamic Solution : for Responsive layout design

I have to achieve below three layout - in a responsive way.
1st layout - default layout
2nd Layout - with "min-width:600px"
3rd Layout - with "min-width:700px"
Above three layout I have already achieved.
I have mentioned height "200px" for dark-blue and red colored divs, which is actually somewhat fixed. If at a later stage, content in it increases (hypothetically) - the design layout will fail I think.
Is there any better way of doing it dynamically and my design doesn't fail if content increases.
I tried to think of it but couldn't get any.
Just Asked this question for better learning.
I wanted to achieve it by using flexbox. Any other way is also appreciated.
Can someone point in right direction?
I have added my HTML and css code.
/* default color of background */
.red {
background: red;
}
.dark-blue {
background: darkblue;
}
.light-blue {
background: lightblue;
}
.green {
background: green;
}
/* Container properties */
.container {
/* mentioned 100% so that element inside takes full width i.e with id = container2 */
width: 100%;
display: flex;
flex-wrap: wrap;
}
.box {
width: 100%;
height: 100px;
}
/* Responsive design proprties */
#media screen and (min-width: 600px) {
.dark-blue {
width: 50%;
height: 200px;
}
#container2 {
width: 50%;
height: 50%;
}
}
#media screen and (min-width: 700px) {
.dark-blue,
.red {
height: 200px;
}
.dark-blue {
width: 25%;
order: 2;
}
#container2 {
width: 50%;
flex-wrap: wrap;
}
.red {
width: 25%;
order: -1;
}
}
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Layout shifter</title>
<link rel="stylesheet" href="./style.css">
</head>
<body>
<div class="container">
<div class="box dark-blue"></div>
<div class="container" id="container2">
<div class="box light-blue"></div>
<div class="box green"></div>
</div>
<div class="box red"></div>
</div>
</body>
</html>
Flexbox has some advanatges and some downsides. one of the downsides is, that it is only good in controlling either height or width. Not both.
If you need to control both, CSS-Grid is the way to go.
Use grid-template-areas to place the divs. Its the equivalent to flex order.
body {
margin: 0;
width: 100vw;
min-height: 100vh;
box-sizing: border-box;
display: grid;
}
.dark-blue {
grid-area: dark-blue;
background-color: darkblue;
}
.light-blue {
grid-area: light-blue;
background-color: lightblue;
}
.green {
grid-area: green;
background-color: green;
}
.red {
grid-area: red;
background-color: red;
}
#media only screen
and (max-width: 600px) {
body {
grid-template-areas:
"dark-blue"
"light-blue"
"green"
"red"
}
}
#media only screen
and (max-width: 600px) {
body {
grid-template-areas:
"dark-blue"
"light-blue"
"green"
"red";
}
}
#media only screen
and (min-width: 601px)
and (max-width: 700px) {
body {
grid-template-areas:
"dark-blue light-blue"
"dark-blue green"
"red red";
}
}
#media only screen
and (min-width: 701px) {
body {
grid-template-areas:
"red light-blue light-blue dark-blue"
"red green green dark-blue"
}
}
<div class="dark-blue"></div>
<div class="light-blue"></div>
<div class="green"></div>
<div class="red"></div>

Change order of floated elements

I have the following code of divs
div {
float: left;
width: 33.33%;
height: 50px;
}
#container {
width: 100%;
}
#title,
#image,
#descr {
display: inline-block;
}
#title,
#descr {
float: right;
}
#media only screen and (max-width: 480px) {
div {
width: 100%;
}
}
<div id="title">This is a title</div>
<div id="image">This is an image</div>
<div id="descr">This is a description</div>
What I want to do is, arrange the divs so that, on desktop, the image comes first, followed by the title and the description. Like so:
[This is an image] [This is a title] [This is a description]
However, when I float the title and description to right, the result I get is:
[This is an image] [This is a description] [This is a title]
Also, please not that while I can change the order of the divs in HTML to get the order I want, I want title to come first on mobile followed by image and description, hence, the order.
Edit: please note that the layout is made responsive by floating the divs. I'm looking for a workaround without removing the floats entirely.
jsfiddle
I would use flex to do this as it would be easier:
.container {
display: flex;
/* make things line up in a column */
flex-direction: column;
}
.container>div {
width: 100%;
height: 50px;
}
/* do mobile first and media query for larger */
#media only screen and (min-width: 481px) {
.container {
/* make things line up in a row */
flex-direction: row;
}
.container>div {
width: 33.33%;
}
#title {
order: 2;
}
#image {
order: 1;
}
#descr {
order: 3;
}
}
<div class="container">
<div id="title">This is a title</div>
<div id="image">This is an image</div>
<div id="descr">This is a description</div>
</div>
Float only the image and keep the other float:none.
Pay attention to whitespace between inline-block when removing the float
div {
width: 33.33%;
height: 50px;
}
#container {
width: 100%;
}
#title,
#image,
#descr {
display: inline-block;
}
#image {
float: left;
}
#media only screen and (max-width: 480px) {
div {
width: 100%;
}
}
<div id="title">This is a title</div><div id="image">This is an image</div><div id="descr">This is a description</div>
Use flexbox to change order of elements. Also floats not needed.
.container {
display: flex;
justify-content: space-between;
}
#title {
order: 2;
}
#image {
order: 1;
}
#descr {
order: 3;
}
#media only screen and (max-width: 480px) {
div {
width: 100%;
}
}
<div class="container">
<div id="title">This is a title</div>
<div id="image">This is an image</div>
<div id="descr">This is a description</div>
</div>
You have to change the order in the HTML code accordingly. If you float: right two elements, the first one will be far right, the next one left of it (if there is enough space)
div {
float: left;
width: 33.33%;
height: 50px;
}
#container {
width: 100%;
}
#title,
#image,
#descr {
display: inline-block;
}
#title,
#descr {
float: right;
}
#media only screen and (max-width: 480px) {
div {
width: 100%;
}
}
<div id="image">This is an image</div>
<div id="descr">This is a description</div>
<div id="title">This is a title</div>

Combining min-width and max-width

I want div1 to appear only when the window width is less than 800px, and I want div2 to appear only when the window width is greater than 800px. My solution is to use the following CSS which works. However, is there a way to do this using only one #media command? It seems clumsy to have to write two conditions, one for a max-width, and one for a min-width.
#media screen and (max-width: 800px) {
#div1 {
display: block;
}
#div2 {
display: none;
}
}
#media screen and (min-width: 800px) {
#div1 {
display: none;
}
#div2 {
display: block;
}
}
<div id="div1">
DIV1
</div>
<div id="div2">
DIV2
</div>
Take one of the set out of media queries.
#div1 {
display: none;
}
#div2 {
display: block;
}
#media screen and (max-width: 800px) {
#div1 {
display: block;
}
#div2 {
display: none;
}
}
<div id="div1">
DIV1
</div>
<div id="div2">
DIV2
</div>
Or
#div1 {
display: block;
}
#div2 {
display: none;
}
#media screen and (min-width: 800px) {
#div1 {
display: none;
}
#div2 {
display: block;
}
}
<div id="div1">
DIV1
</div>
<div id="div2">
DIV2
</div>
There is a way to combine media queries try:
#media only screen and (max-width: 600px) and (min-width: 400px) {
The query above will trigger only for screens that are 600-400px wide. This can be used to target specific devices with known widths.
Or if you only want to target screen sizes that are 800px or less use:
#media screen and (max-width: 800px) {
replace #media screen and (max-width: 800px) { #div1 {
display: block;
}
#div2 {
display: none;
} }
with #div1 {
display: block;
}
#div2 {
display: none;
}

DIV with float right over DIV with float left

Hi I have a navigation div, which has a div on the bottom of it. This div has two other divs "DIV 1" and "DIV 2" (see on picture). Now I the navigation is closed on a tablet device, so I would show the second div which contains float: right over the first div which contains float: left, like in the picture. How can I do this? Now the first div is over the second. Thanks.
You can do this with Flexbox and media queries just change order of second element to order: -1 , here is Fiddle
.nav {
height: 200px;
display: flex;
align-items: flex-end;
border: 1px solid black;
}
.one {
background: #5B9BD5;
}
.two {
background: #FF0000;
}
.div {
flex: 1;
padding: 10px 0;
border: 1px solid black;
margin: 5px;
box-sizing: border-box;
}
#media(max-width: 480px) {
.nav {
flex-direction: column;
align-items: normal;
justify-content: flex-end;
}
.div {
flex: 0 0 50px;
}
.two {
order: -1;
}
}
<div class="nav">
<div class="div one">1</div>
<div class="div two">2</div>
</div>
You can use media queries for that purpose.
You can just manipulate your divs at some point to change their style.
#media (max-width: 600px) {
#someElement {
float: left;
}
}
You can try the following, along with media queries to remove the float at 800px:
JSFiddle: https://jsfiddle.net/7ws3m9Lx/
CSS:
.div1,.div2 { width: 50%; }
.div1 { float: left; }
.div2 { float: right; }
#media screen and (min-width: 0) and (max-width: 800px){
.div1,.div2 { float: none; width: 100%; }
}
HTML:
<div class="parent">
<div class="div2">DIV2</div>
<div class="div1">DIV1</div>
</div>

How to wrap items in flexbox for smaller screens?

I'm trying to create a layout for different resize. I need to reach the result in these images here:
I have this code:
.container {
position: relative;
display: flex;
align-items: stretch;
}
.item {
background-color: black;
box-sizing: border-box;
padding: 20px;
flex: 2;
color: #fff;
}
.item:nth-child(2) {
background-color: grey;
flex: 1
}
.item:nth-child(3) {
background-color: green;
flex: 0.5;
}
#media screen and (max-width: 990px) {
.container {
height: auto;
display: table;
}
.item:nth-child(2) {
float: left;
}
.item:nth-child(3) {
float: right;
}
}
<section class="container">
<div class="item">
<h2>title1</h2>
<hr>You'll notice that even though this column has far more content in it, instead of the other columns ending early, they size themselves to meet the end of this column vertically.</div>
<div class="item">
<h2>title2</h2>
<hr>Normally, the only way to achieve this would be either a hack, or to set all boxes to min-height.
</div>
<div class="item">
<h2>title3</h2>
<hr>This is a column with not much content.
</div>
</section>
Here there's a codepen https://codepen.io/darudev/pen/pyBrzL
Problem is in 990px resize view, I don't find solution to create the same view as "mockup".
Is there someone that can help me or give me some suggestions?
Thank you.
You don't need the table and float properties in your code.
#media screen and (max-width: 990px) {
.container {
height: auto;
display: table;
}
.item:nth-child(2) {
float: left;
}
.item:nth-child(3) {
float: right;
}
}
The entire layout can be made with flexbox.
Here's the solution: When the screen resizes smaller than 990px, allow flex items to wrap and give the first item a 100% width, which forces the following items to the next line.
.container {
display: flex;
}
.item {
background-color: black;
box-sizing: border-box;
padding: 20px;
flex: 2;
color: #fff;
}
.item:nth-child(2) {
background-color: grey;
flex: 1;
}
.item:nth-child(3) {
background-color: green;
flex: 0.5;
}
#media screen and (max-width:990px) {
.container { flex-wrap: wrap; }
.item:first-child { flex-basis: 100%; }
}
<section class="container">
<div class="item">
<h2>title1</h2>
<hr>You'll notice that even though this column has far more content in it,
instead of the other columns ending early, they size themselves to meet the end
of this column vertically.</div>
<div class="item">
<h2>title2</h2>
<hr>Normally, the only way to achieve this would be either a hack, or to set
all boxes to min-height.</div>
<div class="item">
<h2>title3</h2>
<hr>This is a column with not much content.
</div>
</section>
revised codepen