How to order list items using flexbox? - html

I have a simple section which display list items and image, here is how it should look :
I know its simple using framework like bootstrap etc but I want to use only flex.
Here is html:
<section class="info-section">
<div class="main-info">
<div class="main-info_left">
<h2>Nature from air</h2>
<p>Mauris consequat libero metus, nec ultricies sem efficitur quis. Integer bibendum eget metus ac accumsan. Integer sit amet lacus egestas, semper est quis, viverra ex.</p>
<ol class="info-list">
<li>CPellentesque eget nunc sit amet urna ullamcorper fermentum et eu leo. Nunc vel nibh tempor, pharetra lectus congue, luctus orci.
</li>
<li>CPellentesque eget nunc sit amet urna ullamcorper fermentum et eu leo. Nunc vel nibh tempor, pharetra lectus congue, luctus orci.
</li>
<li>CPellentesque eget nunc sit amet urna ullamcorper fermentum et eu leo. Nunc vel nibh tempor, pharetra lectus congue, luctus orci.
</li>
<li>CPellentesque eget nunc sit amet urna ullamcorper fermentum et eu leo. Nunc vel nibh tempor, pharetra lectus congue, luctus orci.
</li>
<li>CPellentesque eget nunc sit amet urna ullamcorper fermentum et eu leo. Nunc vel nibh tempor, pharetra lectus congue, luctus orci.
</li>
</ol>
</div>
<div class="main-info_right">
<span><img src="images/drone.png"></span>
</div>
</div>
</section>
Here is css I have tried:
.main-info{
display: flex;
justify-content: center;
flex-direction: row;
align-items: center;
}
ol {
counter-reset:li; /* Initiate a counter */
margin-left:0; /* Remove the default left margin */
padding-left:0; /* Remove the default left padding */
}
ol > li {
position: relative;
margin: 21px 0 57px 2em;
padding: 22px 41px;
list-style: none;
background: #fff;
}
ol > li:before {
content:counter(li); /* Use the counter as content */
counter-increment:li; /* Increment the counter by 1 */
/* Position and style the number */
position:absolute;
top:-2px;
left:-2em;
-moz-box-sizing:border-box;
-webkit-box-sizing:border-box;
box-sizing:border-box;
width: 54px;
height: 54px;
border-radius: 50%;
/* Some space between the number and the content in browsers that support
generated content but not positioning it (Camino 2 is one example) */
margin-right:8px;
padding: 17px;
border: 1px solid rgb(63, 78, 118);;
background:#fff;
font-weight:bold;
font-family: proximaNova;
text-align:center;
}
li ol,
li ul {margin-top:6px;}
ol ol li:last-child {margin-bottom:0;}
here is Jsfiddle : http://jsfiddle.net/bmL7jogu/1/
Unfortunately I dont get the result I want , what do I need to change to get what I want? newbie to flex though

I suppose you want to achieve a vertically counting list items that wraps to rightside. You have already managed to customise incrementing numbers, which seems to be working great.
The actual element in which you want to apply display: flex; is <ol>, which is the parent of <li> creating the columns. Also, by default flexbox will pile up horizontally rather than vertically, and thus you need to apply flex-direction: column; to achieve vertical direction. Finally, adding flex-wrap: wrap; will let flexbox children to 'wrap' to next line, in our case to rightside of the first columns. By configuring e.g. max-width: 50%; to <li> you can adjust how many columns will be displayed when wrapped.
To summarise, below code will achieve desired list items:
ol {
display: flex;
flex-direction: column; /* Make flex children pile up 'vertically'. */
flex-wrap: wrap; /* Wrap children to next 'column'. */
max-width: 60%; /* To prevent covering the drone image. */
max-height: 600px; /* Set maximum height so columns will wrap. */
margin-left: 0; /* Remove the default left margin */
padding-left: 0; /* Remove the default left padding */
counter-reset: li; /* Initiate a counter */
}
ol > li {
position: relative;
margin: 21px 0 57px 2em;
padding: 22px 41px;
max-width: 50%;
list-style: none;
}
In addition, I would recommend you to set your drone image as background-image to .main-info as it seems to be behaving more as a background. By this way, you can avoid struggling with nested flexbox to achieve your design.
Final code:
https://jsfiddle.net/dorapen/7rdb096t/
I hope this answers your question.

You have to set display: flex to the parent and then add order:1 to the first item and then order the others.
.parent{
display: flex;
flex-wrap: wrap;
}
.parent .order1{
order: 1;
}
.parent .order2{
order: 2;
}
.parent .order3{
order: 3;
}
<div class="parent">
<p class="order3"></p>
<p class="order1"></p>
<p class="order2"></p>
</div>
You can also do it with property column-count: 2;
Hope it helps!

Related

Shrink a flexbox containing images inside a nested flexbox container

I try to ajust some dynamic content so it fit onto label to be printed.
The label has a row (.symbolContainer) that can contain 0 or more images. The objective is to shrink that .symbolContainer and those images if the content of .text box need more spaces.
EDIT: The row of images should not wrap, but shrink from 75px to a minimum of 25px.
Seem to me that flexbox is the way to go, and it ended up with 3 levels of nested flexbox, but the images inside the .symbolContainer won't shrink.
Content of .text div can overflow the .body div, but I will adjust the font-size with javascript after.
It is possible to acheive this with flexbox or other tricks?
Here is what I have done so far. Comment in CSS is what I wanted to do.
.container {
width: 3.5in;
height: 5in;
border: 1px solid black;
border-radius: 6px;
display: flex;
flex-direction: column;
}
.title {
font-weight: bolder;
font-size: 24px;
text-align: center;
}
.body {
background-color: #aad9fa;
flex: 1;
overflow: hidden;
display: flex;
flex-direction: column;
}
.symbolContainer {
display: flex;
justify-content: center;
background-color: #c1f1bf;
flex: 0 1 75px;
/* Height is 75px but shrink if need to */
/* No minimum height because can be empty */
}
.symbolContainer>img {
flex: 0 1 75px;
/* Size start at 75 px then shrink */
min-width: 25px;
/* but don't shrink pass 25px */
align-self: flex-start;
}
.text {
font-size: 22px;
flex: 1;
/* Take maximum possible space */
}
.footer {
text-align: center;
height: 30px;
background-color: green;
}
<div class='container'>
<div class='title'>
A title that can be multiline because of his variable length
</div>
<div class='body'>
<div class='symbolContainer'>
<img src="https://simdut.claurendeau.qc.ca/public/img/vector/flamme.svg">
<img src="https://simdut.claurendeau.qc.ca/public/img/vector/nocif.svg">
</div>
<div class="text">
<p>Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nam bibendum risus ex, nec gravida augue iaculis vel. Nam malesuada vitae libero ac tempus. Aenean et ipsum ac justo malesuada venenatis. Proin consequat tellus et varius mattis. Vestibulum
cursus dui in tincidunt pellentesque. Nullam feugiat lacus sem, et dapibus sapien maximus eu.
</p>
<p>Vivamus ullamcorper odio ex, sed rhoncus tellus sagittis eu. Proin egestas erat metus, sed congue dolor efficitur ac. Fusce ultrices quis urna vel tristique. Ut fermentum ipsum tellus, vel accumsan dui malesuada nec. Vivamus aliquam justo vel tortor
luctus, non venenatis lectus sagittis. Morbi feugiat sem nec elit varius ultricies.</p>
</div>
</div>
<div class='footer'>
This is the footer. Can be fixed height
</div>
</div>
You don't need those layers for the Flex Containers in order to do the images responsive.
Symbol Container should be:
.symbolContainer{
min-width: 0; /* resize as what you want */
margin: 5px; /* resize as what you want */
}
img {
width: 450px; /* resize as what you want */
max-width: 100%; /* resize as what you want */
max-height: 450px; /* resize as what you want */
}
.imgContainer{
display: flex;
justify-content: center;
flex-wrap: wrap;
}
Now the html should change to:
<div class='body'>
<div class='imgContainer'>
<div class='symbolContainer'>
<img src="https://simdut.claurendeau.qc.ca/public/img/vector/flamme.svg">
<img src="https://simdut.claurendeau.qc.ca/public/img/vector/nocif.svg">
</div>
</div>
...
That should do what you want. Be aware to resize to what you want.
Hope it helps!
pd. It's based on this post:
https://medium.com/#sashatran/check-out-the-page-here-7d71a2c43a10

div with min-width growing with it's content

I am a CSS/HTML auto learner, apologies if my question is stupid.
I want a div which is 40% wide minimum with its content justified but when more items will be added in this div its width grows accordingly.
This is what I have so far:
.hcontainerbutton {
display: flex;
width: 40%;
background-color: blue;
align-items: center;
justify-content: space-around;
right: 30%;
left: 30%;
position: absolute;
bottom: 0!important;
}
both with width:40% or min-width:40% the div doesn't grow if I add more items into it
Wrap .hcontainerbutton in a container and apply flexbox and height properties to it. This can be used to position .hcontainerbutton instead of position: absolute.
Add min-width value to .hcontainerbutton
You can test this layout by adding and remove .content divs and viewing in full screen.
body {
margin: 0;
}
.container {
display: flex;
justify-content: center;
height: 100vh;
}
.hcontainerbutton {
min-width: 40%;
background-color: blue;
display: flex;
justify-content: space-around;
margin-top: auto;
}
.content {
background: pink;
width: 100px;
height: 100px;
}
<div class="container">
<div class="hcontainerbutton">
<div class="content"></div>
<div class="content"></div>
<div class="content"></div>
<div class="content"></div>
<div class="content"></div>
</div>
</div>
Based on your requirements, this can be done with normal CSS itself, you need not go for flex, Here is an explanation on what is done.
First we set the width and height of html and body tag, then using margin:0px remove the margins set by the browser.
html,
body {
width: 100% height: auto;
margin: 0px;
}
Now the parent that will wrap the centered div will have to have the CSS property text-align:center, basically what this does is, it will center align elements with display property inline-block.
.parent {
text-align: center;
}
Then coming to the main div, which has the class hcontainerbutton, we can set the max-width(in the example I use 40%) and min-width(in the example I use 80%) to whatever is needed. The CSS property display:inline-block ensures it takes the width of the content alone. The CSS property word-wrap:break-word ensures the text is broken and maintains the widht of the div.
Below is a working snippet of the code.
html,
body {
width: 100% height: auto;
margin: 0px;
}
.parent {
text-align: center;
}
.hcontainerbutton {
word-wrap: break-word;
min-width: 40%;
max-width: 80%;
display: inline-block;
}
<div class="parent">
<div class="hcontainerbutton"> asdf
</div>
<div class="hcontainerbutton"> Lorem ipsum dolor sit amet, consectetur adipiscing elit. Proin eleifend magna augue. Morbi sagittis eu urna et facilisis. Nam finibus erat justo, vel porta magna aliquam a. Pellentesque faucibus molestie libero vitae condimentum. Nunc condimentum tincidunt
nulla, id suscipit magna dignissim id. Nulla dapibus suscipit velit et viverra. Mauris non gravida justo. Sed efficitur eleifend elementum. Integer non mattis mi. Etiam vestibulum viverra erat, eget dapibus tellus iaculis ut. Mauris ullamcorper magna
sapien, ac gravida odio blandit varius. Fusce eu placerat enim. Etiam nec elementum dui. In fermentum massa sed augue interdum aliquam. Nunc lacinia blandit elit a iaculis.
</div>
</div>

aligning text to top of webpage in html code using css

I have this css code:
.post {
margin-top: 0.5em;
margin-left: 2em;
margin-right: 2em;
text-align: center;
}
.post p{
max-width: 1200px;
padding: .5em;
text-align: justify;
margin: 0;
top: 1.25em;
}
.post h1{
text-align: center;
}
and have this in html:
<div class="post">
<h1>Title of Sample Work 2</h1>
<p>Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nullam dapibus id nisl ut suscipit. Nullam vel justo tellus. Suspendisse vehicula rhoncus nunc sed accumsan. In hac habitasse platea dictumst. Mauris vel dolor velit. Phasellus finibus massa mauris, at interdum nisl luctus at. Etiam porttitor, metus non dapibus pretium, orci arcu pretium nulla, eget congue augue libero at lectus. Mauris pretium urna tristique, laoreet enim rhoncus, euismod tortor.</p>
</div>
And this is what I see:
Why there is so much margin at the top and the text title is so down?
You can see an example of the actual page on the web here:
http://www.nanogomo.com/sample1.html
It is interesting that if I add more content to it, it pushes the text up.
Because the #wrapper has display:flex and has a before. You should you remove the following:
#wrapper::before {
content: '';
display: block;
}
The flex container contained 3 elements home-back, post and before. Before is absolutely positioned so it is removed from the normal flow (doesn't take space). Before (with no width) and post are positioned on the main ax (vertical because direction is flex column) with justify-items: space-between (main ax is vertical).
use margin top and give value according to the need.
.post h1{
text-align: center;
margin-top: -7px;
}
Try setting a value to margin and padding:
.post h1{
text-align: center;
margin: 0px;
padding: 0px;
}

How to put text in the center of box while using border-box in CSS?

I've got the following code:
* {
box-sizing: border-box;
}
.container {
width: 100%;
max-width: 60rem;
/* 960 */
margin: 0 auto;
}
.item {
width: 100%;
overflow: hidden;
margin-bottom: 5rem;
/* 80 */
}
.item__img,
.item__info {
width: 50%;
float: right;
}
.item__img {} .item__img .img-map {
width: 95%;
height: 18.750rem;
/* 300 */
}
.item__img img {
width: 95%;
height: 18.750rem;
/* 300 */
}
<div class="container" role="main">
<article class="item">
<div class="item__info">
<p>Lorem ipsum dolor sit amet, consectetur adipiscing elit. Aliquam ac sodales orci. Praesent sit amet consequat purus. Praesent lobortis mi quis rutrum fringilla. Phasellus velit arcu, ultricies vestibulum varius sed, convallis ut eros. Vestibulum
vel congue felis, ut lacinia tellus. Integer ullamcorper gravida ligula non convallis. Ut suscipit vulputate erat eu porttitor. Morbi sagittis vulputate bibendum. Aliquam ultricies finibus tortor, a elementum nisl aliquet at. In sed dui id mauris
rutrum ornare.</p>
</div>
<div class="item__img">
<div class="img-map">
<img src="http://biologypop.com/wp-content/uploads/2014/11/dog1.jpg" />
</div>
</div>
</article>
</div>
sorry for bad style, I've just started to learn CSS...
Now, after seeing that in the browser, I see the picture of a dog and next to it there's some text. I would like to have this text aligned in the center (vertically). Basically, currently it looks like this, and I would like to set it up like this. How should I modify my CSS code to display it as it is? Thanks!
EDIT My other question is - why the text is not lined up on the top to the top layer of the picture? I don't see any constraint for that in my css code, does anybody know how it works?
My suggestion is to ignore anyone that suggests using display:flex, because it doesn't have the browser support it needs for public domain. (currently as of 14/04/15. This will get better as time goes on and will probably be a more serious consideration once Windows 10 comes out later this year)
What you are wanting can be achieved with display:table; on the parent and display:table-cell; on the children. In the code below I have rearranged the HTML so the image is first and removed the float:right; (my experience leads me to not use float anymore as it causes so many headaches that can be avoided, but that's a much bigger discussion).
Adding vertical-align:middle; to the children will make them vertically align in their "cell".
The reason you were previously seeing space above your text is because each browser has a default style-sheet that is applied. For example Firefox has this:
p, dl, multicol {
display: block;
margin: 1em 0;
}
To aid your understanding of such things I suggest to use Mozilla Firefox and download the Firebug add-on.
Here's the full code:
* {
box-sizing: border-box;
}
.container {
width: 100%;
max-width: 60rem;
/* 960 */
margin: 0 auto;
}
.item {
width: 100%;
overflow: hidden;
margin-bottom: 5rem;
display:table;
/* 80 */
}
.item__img,
.item__info {
width: 50%;
display:table-cell;
vertical-align:middle;
}
.item__img {} .item__img .img-map {
width: 95%;
height: 18.750rem;
/* 300 */
}
.item__img img {
width: 95%;
height: 18.750rem;
/* 300 */
}
<div class="container" role="main">
<article class="item">
<div class="item__img">
<div class="img-map">
<img src="http://biologypop.com/wp-content/uploads/2014/11/dog1.jpg" />
</div>
</div>
<div class="item__info">
<p>Lorem ipsum dolor sit amet, consectetur adipiscing elit. Aliquam ac sodales orci. Praesent sit amet consequat purus. Praesent lobortis mi quis rutrum fringilla. Phasellus velit arcu, ultricies vestibulum varius sed, convallis ut eros. Vestibulum
vel congue felis, ut lacinia tellus. Integer ullamcorper gravida ligula non convallis. Ut suscipit vulputate erat eu porttitor. Morbi sagittis vulputate bibendum. Aliquam ultricies finibus tortor, a elementum nisl aliquet at. In sed dui id mauris
rutrum ornare.</p>
</div>
</article>
</div>
This link might help you, I use this trick very often when it comes to vertically aligning:
http://zerosixthree.se/vertical-align-anything-with-just-3-lines-of-css/
Add this code:
position: relative;
top: 50%;
-webkit-transform: translateY(-50%);
-ms-transform: translateY(-50%);
transform: translateY(-50%);
to a container around the text (in your case the 'p'), and make sure to set the height of the container (article.item) that wraps around both the image and the text.
You want to set a height of your div and line-height aswell.
Like:
.div{ height: 100px;
line-height: 100px;}
See an example here: http://jsfiddle.net/BRxKX/
Use flexbox if you can, it allows you to do this without any odd rules or hacks.
For example:
HTML
<div class="container">
<div class="image">200 x 200</div>
<p>Lots of text here...</p>
</div>
CSS
* {
box-sizing: border-box;
}
.container {
display: flex;
align-items: center;
}
.image {
height: 200px;
width: 200px;
min-width: 200px;
}
See it here in action. Try editing the text within the p tag to see how it works.

Unable to set width of flexbox child to 100%

I am learning CSS flexbox and was doing a simple layout where I wanted the first flex child to displayed with 100% width of the parent and rest flex items wrapping below. Also, the wrapped flex items should occupy width in a specific ratio (easy to set with 'flex' property).
To do this I set "flex-basis" property of first flex item to 100% and set flex property of next 2 to the ratio I want. Here is what the pertinent CSS looks like (link to complete fiddle is below):
.main{
max-width: 1000px;
margin: 100px auto;
display: flex;
flex-flow: row wrap;
}
/*using ususal shorthand notation*/
.flex-item:nth-child(1) {
flex:1 100%;
}
.flex-item:nth-child(2) {
flex:2;
}
.flex-item:nth-child(3) {
flex:3;
}
This should set the first item's width to 1000px and for the next two as 400px and 600px respectively; wrapped and displayed below the first child.
But for some reason the CSS breaks, and the 2nd and 3rd items are pushed outside main container.
What more strange is that adding margin to the flex items fixes the whole thing and I don't understand how this is happening (I must be doing something stupid). Even addding some border or padding to the '.flex-item' rule works.
.flex-item{
margin: 5px;
}
Here is the JS Fiddle. You can try un-commenting the '.flex-item' rule in CSS to see what is going on.
I was lazy not to add the any prefixes (since almost every new browser supports it) ,but the problem is same across latest FF, IE and chrome.
The second and third elements have 0 width, so they can fit in any place ..
That's way they stay in the first line.
just set 1px for basis, and they will be in the second row
*{
box-sizing: border-box;
padding: 0;
margin: 0;
}
body{
font-family: 'Raleway', Helvetica, sans-serif;
font-size: 14px;
font-weight: 300;
color: #555;
}
.main{
max-width: 1000px;
margin: 20px auto;
border: 1px dotted #999;
padding: 20px;
display: flex;
flex-flow: row wrap;
}
/* adding any border, margin, padding rules here fixes it */
.flex-item:nth-child(2) {
flex:2 1px;
background-color: lightyellow;
}
.flex-item:nth-child(3) {
flex:3 1px;
}
.flex-item:nth-child(1) {
flex:1 100%;
}
<div class="main">
<p class="flex-item">
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Proin non consequat lorem. In dignissim mauris eu est commodo, ac ullamcorper dui facilisis. Sed feugiat eros quis facilisis feugiat. Pellentesque eu quam egestas, facilisis augue eu, aliquam mi. Nunc nunc metus, eleifend id finibus sit amet, imperdiet eget mi.
</p>
<p class="flex-item">
In dignissim mauris eu est commodo, ac ullamcorper dui facilisis. Sed feugiat eros quis facilisis feugiat. Pellentesque eu quam egestas, facilisis augue eu, aliquam mi. Nunc nunc metus, eleifend id finibus sit amet, imperdiet eget mi.
</p>
<p class="flex-item">
In dignissim mauris eu est commodo, ac ullamcorper dui facilisis. Sed feugiat eros quis facilisis feugiat. Pellentesque eu quam egestas, facilisis augue eu, aliquam mi. Nunc nunc metus, eleifend id finibus sit
.flex-item:nth-child(2) {
flex:2 1px;
}
.flex-item:nth-child(3) {
flex:3 1px;
}