why doesn't the div spread the entire div container? - css

i want the background of a div to change on hover. However on hover, the doesn't change the entire div background color (reason the div width doesnt cover the entire width of the div it is contained in). Could you please let me know how to fix it. Below is the code snippet,
.list_container {
height: 100%;
display: flex;
flex-direction: column;
overflow: auto;
ul {
height: 100%;
width: 100%;
display: flex;
flex-direction: column;
li {
.list {
margin: 0;
display: flex;
align-items: center;
&:hover {
background-color: green;
}
}
}
}
}
}
<div className="list_container">
<header>
<h4>Listitems</h4>
</header>
<ul>
<li>
<div className="list"><span>hello</span></div>
<ul>
<li>
<div className="list"><span>hello</span></div>
</li>
</ul>
</div>
</li>
</div>
</ul>
</div>
The div with classname list doesnt spread the width of entire div it is contained in (that is lists). The list items are added dynamically. So as the list items grow...the div with class list doesnt cover the entire div list_container. How can i fix this. Thanks.

Related

Image dissapears when I use flexbox

I am trying to build this nav bar and make it responsive as well, the thing is that when I apply display: flex; the logo just dissapears. For some reason, when I use a fixed width the image stays, but when I use percentages the image just goes away. I would like to use percentages to mantain the responsiveness of the nav bar.
Here is what I have so far.
* {
margin: 0;
padding: 0;
box-sizing: border-box;
}
header {
display: flex;
border: 10px solid orange;
justify-content: space-around;
width: 100%;
}
header div#company-logo img#header-img {
width: 50%;
}
<header id="header">
<div id="company-logo">
<img src="https://via.placeholder.com/100x50.jpg" alt="hamburguer logo" id="header-img">
</div>
<nav id="nav-bar">
<ul>
<li class="nav-link">Home</li>
<li class="nav-link">Info</li>
<li class="nav-link">Contact Us</li>
</ul>
</nav>
</header>
Like I said before, I have tried with fixed percentages, such as px or vw. I just want to understand why the image dissapears when I use percentages.
#company-logo {
flex: 0 0 auto;
}
...should do it. It means:
flex-grow: 0;
flex-shrink: 0;
flex-basis: auto;
The important bits are flex-shrink: 0; flex-basis: auto;.

CSS : background-clipping regarding to above elements?

I have this layout on my HTML-page :
page layout
It's a form with checkboxes (which are hidden) and the labels are styled to look like buttons (white border and transparent background to show the gradient below). The gradient part is the container.
Now what I would like to achieve is to show the gradient background only below the buttons so that the parts between the buttons remains white.
See the example here : example (and worship my Photoshop skills)
I tried to figure out a solution but I ended up with nothing. If some of you guys could help me out, I would really appreciate it :)
Thank you in advance !
Create multiple small round boxes with no background and large box-shadow values.
Excess shadow on these boxes will be clipped by overflow: hidden on their respective parents.
Apply gradient background on the outermost parent.
Here is a working demo:
*,
*:before,
*:after {box-sizing: border-box;}
body {
background: linear-gradient(orange, yellow) no-repeat;
margin: 0;
}
.list {
justify-content: center;
list-style: none;
flex-wrap: wrap;
display: flex;
padding: 0;
margin: 0;
}
.list li {
justify-content: center;
padding: 30px;
overflow: hidden;
display: flex;
flex-grow: 1;
flex-basis: 50%;
}
.list .box {
box-shadow: 0 0 0 1000px #fff;
justify-content: center;
align-items: center;
border-radius: 100%;
display: flex;
height: 120px;
width: 120px;
}
<ul class="list">
<li>
<div class="box">Immobilier</div>
</li>
<li>
<div class="box">Travaux</div>
</li>
<li>
<div class="box">Finance</div>
</li>
<li>
<div class="box">Evenementiel</div>
</li>
<li>
<div class="box">Juridique</div>
</li>
<li>
<div class="box">Communication</div>
</li>
<li>
<div class="box">Recrutement</div>
</li>
</ul>

Vertical align on full height page using flexbox

I am trying to create simple page that has header with navbar that is separated by content area. I am unable to force div #cover to be aligned in center vertically. I want my design to be responsive so I do not want to specify width on the parent div content.
I know I can use flex: 1 to fill the rest of the area but I tried that and it does not work for me.
Please see here: Codepen
.site-content {
display: flex;
flex-direction: column;
}
.navbar {
display: flex;
justify-content: space-between;
}
nav ul {
display: flex;
list-style-type: none;
}
li {
margin: 0 10px;
}
.content {
display: flex;
flex: 1;
}
<div class="site-content">
<div class="navbar">
<div class="title">TitLe</div>
<nav>
<ul>
<li>link1</li>
<li>link2</li>
<li>link3</li>
</ul>
</nav>
</div>
<div class="content">
<div id="cover">
Lorem ipsum
</div>
</div>
</div>
You need to define the height for .site-content.
.site-content {
display: flex;
flex-direction: column;
height: 100vh; /*new*/
}
Or set the percentage height on html, body and .site-content tags.
html, body, .site-content {
height: 100%;
}
Also reset the default margin on body as needed.
body {
margin: 0;
}
To vertically center #cover, use align-items on the container.
.content {
display: flex;
flex: 1;
align-items: center; /*new*/
}
Updated Codepen

Make flex items stretch full height and vertically center their content

I have a horizontal flex box (i.e. flex-direction: row, i.e. side-by-side) with a few items. Each item can be a single line of text, or can have multiple lines. I want to vertically-align the contents of each flex item.
If each item had a transparent background, I could easily use align-items: center. However, I want each item to be stretched vertically, because I want to set a background (or maybe borders, or maybe it is a clickable region) to the entire available height.
So far, I know:
Stretching: align-items: stretch
Aligning: align-items: center
Stretching and aligning: ???
Demo available at http://codepen.io/denilsonsa/pen/bVBQNa
ul {
display: flex;
flex-direction: row;
}
ul.first {
align-items: stretch;
}
ul.second {
align-items: center;
}
ul > li {
flex-grow: 1;
flex-shrink: 0;
flex-basis: 5em;
text-align: center;
}
ul > li:nth-child(2) {
background: #CFC;
}
/* Visual styles, just ignore. */
html, body { font-family: sans-serif; font-size: 25px; }
ul, li { list-style: none; margin: 0; padding: 0; }
ul { background: #CCF; width: 25em; }
<ul class="first">
<li>Sample</li>
<li><span>span</span></li>
<li><span>multiple</span> <span>span</span></li>
<li>text <span>span</span></li>
<li>multi<br>line</li>
</ul>
<hr>
<ul class="second">
<li>Sample</li>
<li><span>span</span></li>
<li><span>multiple</span> <span>span</span></li>
<li>text <span>span</span></li>
<li>multi<br>line</li>
</ul>
Similar questions:
Question 14012030 and question 23442692 and question 27729619 and question 25311541 ask essentially the same thing, but they either have a single element or plain text as child of each flex item. As soon as we have mixed content, possibly with multiple elements, those solutions do not work.
Question 19026884 is unrelated, the issue there was the wrong markup.
Unfortunately, it is impossible to achieve the desired effect while using the exact markup posted in the question.
The solution involves:
Setting display: flex; on <li>.
Wrapping the <li> contents into another element.
This is required because <li> is now a flex container, so we need another element to prevent the actual contents from becoming flex items.
In this solution, I introduced a <div> element, but it could have been other element.
Now that <li> is a flex container and it contains only a single child, we can use align-items and/or justify-content to align this new and only child.
The DOM tree looks like this:
<ul> flex-parent, direction=row
├ <li> flex-item && flex-parent && background && JavaScript clickable area
│ └ <div> flex-item as a single transparent element
│ ├ Actual contents
│ └ Actual contents
├ …
Note: The solution in this answer uses 2 nested flex boxes. The solution by Michael_B uses 3 nested flex boxes, because it has the added challenge of expanding the <a> element to fill the entire <li>. Which one is preferred depends on each case. If I could, I would accept both answers.
/* New code: this is the solution. */
ul > li {
display: flex;
flex-direction: column;
justify-content: center;
align-items: center;
}
/* Old code below. */
ul {
display: flex;
flex-direction: row;
align-items: stretch;
}
ul > li {
flex-grow: 1;
flex-shrink: 0;
flex-basis: 5em;
text-align: center;
}
ul > li:nth-child(2) {
background: #CFC;
}
/* Visual styles, just ignore. */
html, body { font-family: sans-serif; font-size: 25px; }
ul, li { list-style: none; margin: 0; padding: 0; }
ul { background: #CCF; width: 25em; }
button:focus + ul {
font-size: 14px;
width: auto;
}
<button>Click here to set <code>width: auto</code> and reduce the font size.</button>
<!-- New code: there is a single <div> between each <li> and their contents. -->
<ul>
<li><div>Sample</div></li>
<li><div><span>span</span></div></li>
<li><div><span>multiple</span> <span>span</span></div></li>
<li><div>text <span>span</span></div></li>
<li><div>multi<br>line</div></li>
</ul>
I want each item to be stretched vertically, because I want to set a
background (or maybe borders, or maybe it is a clickable region) to
the entire available height.
You can achieve this layout without any changes to your HTML structure. There's no need for additional containers.
You already have a primary flex container and a group of flex items. Simply make those flex items into nested flex containers. That will enable you to align the content with flex properties.
(Since you mentioned that you may need clickable regions, I switched from li to a elements.)
nav {
display: flex;
background: #CCF;
width: 25em;
}
nav > a {
flex: auto; /* flex-grow: 1, flex-shrink: 1, flex-basis: auto */
text-align: center;
text-decoration: none;
display: flex;
align-items: center;
justify-content: center;
}
nav > a:nth-child(2) {
background: #CFC;
}
html, body {
font-family: sans-serif;
font-size: 25px;
}
<nav>
Sample
<span>span</span>
<span>multiple</span> <span>span</span>
text <span>span</span>
multi<br>line
</nav>
revised codepen
Note that content placed directly inside a flex container is wrapped in an anonymous flex item:
From the spec:
4. Flex Items
Each in-flow child of a flex container becomes a flex item, and each contiguous run of text that is directly contained inside a flex
container is wrapped in an anonymous flex item.
So, because the text is automatically wrapped in flex items, you can keep the full height of each item (align-items: stretch from the primary container) and vertically center the content (align-items: center from the nested containers).
Make the li flex-containers with flex-direction:column. I think that's what you are after.
html,
body {
font-family: sans-serif;
font-size: 25px;
}
ul,
li {
list-style: none;
margin: 0;
padding: 0;
}
ul {
background: #CCF;
width: 25em;
display: flex;
flex-direction: row;
}
ul.first {
align-items: stretch;
}
ul > li {
flex-grow: 1;
flex-shrink: 0;
flex-basis: 5em;
text-align: center;
display: flex;
flex-direction: column;
justify-content: center;
align-items: center;
/*outline: 1px dotted #444;*/
}
ul > li:nth-child(2) {
background: #CFC;
}
<ul class="first">
<li>Sample</li>
<li><span>span</span>
</li>
<li><span>multiple</span> <span>span</span>
</li>
<li>text <span>span</span>
</li>
<li>multi
<br>line</li>
</ul>
Flex-child items can also be flex-parent items.
*,
*:before,
*:after {
box-sizing: inherit;
}
html {
box-sizing: border-box;
font-family: sans-serif;
font-size: 25px;
}
body {
display: flex;
flex-flow: column nowrap;
background-color: #333;
overflow: hidden;
}
html,
body {
width: 100%;
height: 100%;
padding: 0;
margin: 0;
}
.List {
padding: 0;
margin: 0;
background: #CCF;
width: 25em;
list-style: none;
display: flex;
flex-flow: row nowrap;
justify-content: center;
}
.ListItem {
flex-basis: 5em;
display: flex;
flex-flow: row wrap;
text-align: center;
align-items: center;
}
.ListItem:nth-child(2) {
background: #CFC;
}
.ListItem__content {
width: 100%;
}
<ul class="List">
<li class="ListItem">
<span class="ListItem__content">Sample</span>
</li>
<li class="ListItem">
<span class="ListItem__content">span</span>
</li>
<li class="ListItem">
<span class="ListItem__content">multiple <br> span</span>
</li>
<li class="ListItem">
<span class="ListItem__content">span</span>
</li>
<li class="ListItem">
<span class="ListItem__content">multi<br>line</span></li>
</ul>

multiple divs, some left, some right, all vertically aligned with CSS

What would be the best way, given any number of elements in a container, to align some elements to the left and some to the right while centering both left and right content vertically?
For example, given this markup:
<div class="action">
<div class="message">This is our message</div>
<div class="comment">Comments for the message</div>
<div class="person">John Doe</div>
<div class="date">01/18/2013</div>
<div class="time">12:35 PM</div>
</div>
Can the message and comment be left aligned in the action container while the person, date and time are right aligned with both left and right content vertically centered? Can this be done without new markup and with any content length for each element?
Thanks.
Some CSS would do the trick. Have the containing div position: relative, and float the children div's either left or right. Also center-align the text.
.container{
position: relative;
}
.left{
float: left;
width: 50%;
background-color: Silver;
text-align: center;
}
.right{
float: right;
width: 50%;
background-color: Yellow;
text-align: center;
}
Fiddle Example
With a minimal change to existing markup (introduction of two div tags, one for each column), this becomes rather trivial if you use Munawwar's flex-helper.
HTML:
<div class="hbox flex">
<div class="left vbox main-center">
<div class="message">
<p>This is our message.</p>
<p>It spans many lines.</p>
<p>Or rather, paragraphs.</p>
<p>Additional waffle.</p>
<p>Syrup, bacon, a banana.</p>
<p>Tall glass of milk.</p>
</div>
<div class="comment">Comments for the message.</div>
</div>
<div class="right vbox main-center">
<div class="person">John Doe</div>
<div class="date">01/18/2013</div>
<div class="time">12:35 PM</div>
</div>
</div>
CSS:
/*Example-specific CSS*/
/*left column*/
.left {
width: 80%;
background-color: Silver;
text-align: center;
}
/*right column*/
.right {
width: 20%;
background-color: Yellow;
text-align: center;
}
/*Minimal use of Munawwar's flex-helper*/
/* https://github.com/Munawwar/flex-helper */
/*Stack child items vertically*/
.vbox {
display: flex;
/*Align children vetically*/
flex-direction: column;
align-content: flex-start;
/*Prevent extending beyond boundaries*/
overflow: hidden;
}
/*Stack child items horizontally*/
.hbox {
display: flex;
/*Align children horizontally*/
flex-direction: row;
align-content: flex-start;
/*Wrap items to next line on main-axis*/
flex-wrap: wrap;
/*Prevent extending beyond boundaries*/
overflow: hidden;
}
/*Stretch item along parent's main-axis*/
.flex {
flex: 1;
}
/*Stack child items to the main-axis center*/
.main-center {
justify-content: center;
}
JSFiddle demo
No waffles were harmed in the production of this answer, though some may have been eaten.

Resources