I have got a menu list:
<ul>
<li class="marked">First item</li>
<li>Second much longer than first item</li>
</ul>
I would like to have an image marker on top of item.marked which width will be 100% of text width. The image must stretch so it will be completely visible. Height is constant.
Can this be done with CSS and IE compatibility?
<style type="text/css">
.selected {
background:url("example.png") no-repeat 0 100%;
}
</style>
Solutions for changing background of list item (can be adapted to change an image):
1. CSS-only, persistent, works for current versions of browsers (doesn't work for IE8 and older) - DEMO.
HTML:
<ul>
<li>
<input type="radio" name="s" id="o1" checked>
<label for="o1">First item</label>
</li>
<li>
<input type="radio" name="s" id="o2">
<label for="o2">Second much longer than first item</label>
</li>
</ul>
Relevant CSS:
ul input[type=radio] {
display: none;
}
input[type=radio]:checked + label {
background: lightblue;
}
If you want to have an image (with img tag) above the selected items, then you can adapt it like in this demo.
HTML:
<ul>
<li>
<input type="radio" name="s" id="o1" checked>
<label for="o1">First item
<img src="http://upload.wikimedia.org/wikipedia/commons/5/5b/Supernumerary_rainbow_03_contrast.jpg">
</label>
</li>
<li>
<input type="radio" name="s" id="o2">
<label for="o2">Second much longer than first item
<img src="http://upload.wikimedia.org/wikipedia/commons/5/5b/Supernumerary_rainbow_03_contrast.jpg">
</label>
</li>
</ul>
And add the following CSS:
label img {
top: 0;
width: 100%;
height: 100%;
display: none;
position: absolute;
}
input[type=radio]:checked + label img {
display: block;
}
If you don't want to do it with an img tag, then you can use a background-image on a pseudo-element and set the background-size to 100% 100%, like in this demo. The HTML is the same as in the first demo and you need to also have this in the CSS:
label {
position: relative;
}
input[type=radio]:checked + label:after {
top: 0;
right: 0;
bottom: 0;
left: 0;
position: absolute;
background: url(http://upload.wikimedia.org/wikipedia/commons/5/5b/Supernumerary_rainbow_03_contrast.jpg);
background-size: 100% 100%;
content: '';
}
2. CSS-only, not persistent (list item does not stay selected when you click somewhere else on the page), works for IE8 (and also IE7, but you have to hover off the text to see the change) - DEMO.
HTML:
<ul>
<li>First item</li>
<li>Second much longer than first item</li>
</ul>
Relevant CSS:
a:active, a:focus {
outline: none;
background: lightblue;
}
Related
I put together a treeview control with HTML and CSS, that can display the nodes as an Org chart or a classic treeview list.
In the CodePen, each node has a set width: 100px.
How can I fit the content of the div (using display: inline-block for example), but keep the layout of the chart as it is?
The layout of the tree as you see it is exactly as I want it, apart from the set width. When I tried to replace width: 100px with display: inline-block, the layout changes completely and whatever I tried only made it worse.
As for the layout:
org-view: If a node is directly within a red rectangle box, is children should
be displayed horizontally (eg: A, F, M and N are horizontally
displayed under Root Node). The parent node is centered in the middle of its first and last child (Root Node is centered in the middle of A and N)
list-view: If a node is directly within a green rectangle box, its children will appear below, vertically.
HTML:
<head>
<meta charset="UTF-8" />
<title>Hierarchy Chart</title>
</head>
<link rel="stylesheet" href="hierarchy-chart.css">
<body>
<div class="wbs">
<ol class="org-view">
<li>
<div class="node" for="node-1">1. Root node</div>
<input type="checkbox" checked id="node-1" />
<ol class="list-view">
<li>
<div class="node" for="node-1-1">AAAA</div>
<input type="checkbox" checked id="node-1-1" />
<ol class="list-view">
<li>
<div class="node">BBBB</div>
</li>
</ol>
<ol class="org-view">
<li>
<div class="node" for="node-1-1-2">CCCC</div>
<input type="checkbox" checked id="node-1-1-2" />
<ol class="list-view">
<li>
<div class="node">DDDD</div>
</li>
</ol>
<ol class="list-view">
<li>
<div class="node">EEEE</div>
</li>
</ol>
</li>
</ol>
</li>
</ol>
<ol class="org-view">
<li>
<div class="node" for="node-1-2">FFFF</div>
<input type="checkbox" checked id="node-1-2" />
<ol class="list-view">
<li>
<div class="node" for="node-1-2-1">GGGG</div>
<input type="checkbox" checked id="node-1-2-1" />
<ol>
<li>
<div class="node">HHHH</div>
</li>
<li>
<div class="node">IIII</div>
</li>
</ol>
</li>
</ol>
<ol class="list-view">
<li>
<div class="node" for="node-1-2-2">JJJJ</div>
<input type="checkbox" checked id="node-1-2-2" />
<ol>
<li>
<div class="node">KKKK</div>
</li>
<li>
<div class="node">LLLL</div>
</li>
</ol>
</li>
</ol>
</li>
</ol>
<ol class="list-view">
<li>
<div class="node">MMMM</div>
</li>
</ol>
<ol class="list-view">
<li>
<div class="node">NNNN</div>
</li>
</ol>
</li>
</ol>
</div>
</body>
</html>
CSS
body {background-color: white;}
.wbs {
display: grid;
border: 4px solid #eee;
position: relative;
}
.wbs ol {
list-style-type: none;
padding-left: 10px;
}
.org-view {
border: 1px dashed red;
margin: auto;
}
.org-view >li > .node:first-child {
margin-left: auto;
margin-right: auto;
}
.list-view {
border: 1px dashed lightgreen;
vertical-align: top;
}
/* Tree view collapsible functionalities */
.wbs input {
//display: none;
}
.wbs input ~ ol {
display: none;
}
.org-view >li > .node:first-child {
margin-left: auto;
margin-right: auto;
}
.org-view > li > input:checked ~ ol {
display: inline-block;
}
.org-view .list-view input:checked ~ ol {
display: block;
}
.org-view .org-view input:checked ~ ol {
display: inline-block;
}
.node {
margin-top: 10px;
}
.node {
color: blue;
position: relative;
background-color: white;
border-radius: 3px;
border: 2px solid #4285F4;
//display: inline-block;
width: 100px;
padding: 4px;
vertical-align: top;
}
To me it seems fine.
If you want the nodes to cause a line break, you could wrap them within a <div> element, so they would have a block element breaking the lines.
Also, you might wanna center them.
Here's a fork of your CodePen: https://codepen.io/anon/pen/jYdEro?editors=1100#
Had only the first nodes. I'm too lazy to actually do the entire thing - but you'll get the point :)
Some explanation:
Added a new wrapper element for each node element named node-wrapper. The default display for <div> elements is block so that takes care of the line breaks. The styles for that element:
.node-wrapper {
text-align: center;
}
Since the node element is inline-block, we can center it by using text-align on the parent element.
I am trying to create a responsive navbar, so when you click a hidden checkbox the content unhides.
The problem is, I can't get the "checked" css to actually pick up and do anything.
Example to run here: http://codepen.io/anon/pen/KNvvZy
CSS:
#nav-hidden{background: red; display: none;}
#navigation-mobile{display:none;}
/* DESKTOP */
#media only screen and (max-width: 1200px) {
#navigation-mobile {display: block;}
#menu-toggle:checked ~ #nav-hidden {
opacity: 1;
height: 100vh;
visibility: visible;
}
.label-toggle {
cursor: pointer;
display: block;
float: right;
}
}
HTML:
<div id="navigation-mobile">
<input type="checkbox" id="menu-toggle">
<label for="menu-toggle" class="label-toggle"></label>
</input>
<div id="nav-hidden">
<ul>
<li>test</li>
<li>test</li>
</ul>
</div>
</div>
In your example, on the original state you have:
#nav-hidden{display:none;}
So, you'll need to reset it on :checked state:
#menu-toggle:checked ~ #nav-hidden {display:block;}
Also want to point out that, you can animate height, opacity, visibility etc., but you can't animate display property.
The <input> element is a self-closing tag, you can do <input> or <input />, but you can't do <input></input>.
#nav-hidden {
display: none;
}
#menu-toggle:checked ~ #nav-hidden {
display: block;
}
<div id="navigation-mobile">
<input type="checkbox" id="menu-toggle">
<label for="menu-toggle" class="label-toggle"></label>
<div id="nav-hidden">
<ul>
<li>test</li>
<li>test</li>
</ul>
</div>
</div>
I have a checkbox and label in my header im using for a side menu.
However, its not working and the selector of being checked isn't working.
See here: https://jsfiddle.net/jpjL3hhp/
That should when clicked show a side bar.
However, it works here when my header isn't involved in the code: https://jsfiddle.net/jpjL3hhp/1/
What is causing the problem?
Working code:
<input type="checkbox" id="menu_collapse_icon">
<label for="menu_collapse_icon" class="menu_collapse_icon_label">Show Menu</label>
<div class="side-navigation">
<ul>
<li>
Login
</li>
</ul>
</div>
Not working:
<header>
<input type="checkbox" id="menu_collapse_icon">
<label for="menu_collapse_icon" class="menu_collapse_icon_label">Show Menu</label>
<div class="side-navigation">
<ul>
<li>
Login
</li>
</ul>
</div>
</header>
This is used for the check:
#menu_collapse_icon:checked ~ .side-navigation {
margin-right: 0;
}
The problem is your HTML structure.
You are using #menu_collapse_icon:checked ~ .side-navigation as the selector.
In the non-working example where you integrated with all the header it doesn't work because your .side-navigation isn't being selected since its not in the same level as #menu_collapse_icon.
So if you place the .side-navigation in the same level as #menu_collapse_icon it will work.
Like this:
.side-navigation {
right: 0;
height: 100%;
background-color: white;
width: 200px;
margin-top: 106px;
margin-right: -200px;
transition: margin-right 0.5s ease;
position: fixed;
}
#menu_collapse_icon:checked ~ .side-navigation {
margin-right: 0;
}
header {
position: fixed;
height: 100px;
background-color: blue;
width: 100%;
}
header nav ul li {
float: left;
}
<header>
<div class="max-container">
<input type="checkbox" id="menu_collapse_icon">
<label for="menu_collapse_icon" class="menu_collapse_icon_label">
Show Menu
</label>
<div class="side-navigation">
<ul>
<li> Login
</li>
<li> Jobs
</li>
<li> Employers
</li>
</ul>
</div>
</div>
</header>
The layout I want to achieve is the following, one large image with a gallery of four thumbnails below it:
I'm using a Javascript gallery to actually display a full screen gallery, activated when clicking on this element.
The problem is that the gallery script expects the images as direct children in an unordered list, all of them including the one that is the big image in my layout:
<ul>
<li data-src="img1.jpg">
<img src="thumb1.jpg" />
</li>
<li data-src="img2.jpg">
<img src="thumb2.jpg" />
</li>
</ul>
The first <li> is the big image, all the others are small thumbnails.
Is there a way to achive my desired layout while still having all the images in the unordered list? If I could break up the list this would be easy, but that wouldn't be recognized by the gallery script anymore.
Is it possible to achive this layout without changing the underlying structure of the list?
I suggest using float: left and display: block on li, and float: none on li:first-child:
ul
{
margin: 0;
padding: 0;
list-style-type: none;
}
li
{
margin: 2px 5px;
display: block;
float: left;
}
li:first-child
{
float: none;
}
<ul>
<li>
<img src="http://lorempixel.com/g/430/430/" />
</li>
<li>
<img src="http://lorempixel.com/g/100/100/" />
</li>
<li>
<img src="http://lorempixel.com/g/100/100/" />
</li>
<li>
<img src="http://lorempixel.com/g/100/100/" />
</li>
<li>
<img src="http://lorempixel.com/g/100/100/" />
</li>
</ul>
Simple and clean, no JS involved.
This is my attempt based on flexbox. The skewed images are a side effect of taking random cat images from the web, and constraining them to a certain width and height (fiddle).
The CSS:
ul {
padding: 0;
margin: 0;
}
ul {
display: flex;
flex-wrap: wrap;
list-style: none;
}
li {
/** add box-sizing: border-box; if you include padding or borders **/
}
li:first-child {
width: 100%;
height: 500px;
}
li:not(:first-child) {
/** add box-sizing: border-box; if you include padding or borders **/
width: 25%; /** use calc if you include margins **/
height: 100px; /** whatever height you want **/
}
li > img { /** demo only - because of image sizes **/
width: 100%;
height: 100%;
}
The HTML:
<ul>
<li data-src="whatever">
<img src="http://www.gordonrigg.com/the-hub/wp-content/uploads/2015/06/little_cute_cat_1920x1080.jpg" />
</li>
<li data-src="whatever">
<img src="http://rufflifechicago.com/wp-content/uploads/cat-treats.jpg" />
</li>
<li data-src="whatever">
<img src="http://www.vetprofessionals.com/catprofessional/images/home-cat.jpg" />
</li>
<li data-src="whatever">
<img src="http://animalia-life.com/data_images/cat/cat8.jpg" />
</li>
<li data-src="whatever">
<img src="http://www.catprotection.com.au/wp-content/uploads/2014/11/5507692-cat-m.jpg" />
</li>
</ul>
You are looking for some simple CSS, there are multiple ways to approach this, the easiest is likely:
<style type="text/css">
ul.thumbs li{
float:right;
}
</style>
<ul class="thumbs">
<li data-src="img1.jpg">
<img src="thumb1.jpg" />
</li>
<li data-src="img2.jpg">
<img src="thumb2.jpg" />
</li>
</ul>
you could also set the ul to display:table-row and the lis to display:table-cell which would allow them to evenly spread and fill the space allowed in the ul
Based on your edit you will need something a little more complicated, without knowing which plugin you are using, or how it works, you can try this approach (uses a little jQuery):
$(document).ready(function(){
$('li').click(function(){
$(this).parent().find('.selected').removeClass('selected');
$(this).addClass('selected');
});
});
ul{
padding-top:405px;
position:relative;
}
li{
height:100px;
width:100px;
float:left;
background:blue;
}
li.selected{
background: red;
position: absolute;
top: 0;
height: 400px;
width: 400px;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.10.0/jquery.min.js"></script>
<ul>
<li class="selected">test 1</li>
<li>test 2</li>
<li>test 3</li>
<li>test 4</li>
<li>test 5</li>
</ul>
What I'm trying to accomplish:
Removing the bottom border on the nested list-item element, but keeping the bottom border of its parent list-item element.
I'm trying to figure out if I can use a "universal selector", like ">*" to say: "For everything element that lives in this parent, make the border 0".
Question:
Is this possible?
See the fiddle: http://jsfiddle.net/VnLZH/
HTML:
<aside>
<b>What I'm trying to accomplish: </b><br>
1.) Removing the bottom border on the nested list-item element, but keeping the bottom border of its parent list-item element. <br>
2.) I'm trying to figure out if I can use a "universal selector", like ">*" to say: "For everything element that lives in this parent, make the border 0". <br><br>
<b>Question</b><br>
Is this possible?
</aside>
<h1>This works</h1>
<div class="option1">
<ul>
<li>Category</li>
<li>Category</li>
<li>Category</li>
<li>Category
<div>
<ul>
<li><input type="radio" name="radio" /> Option 1</li>
<li><input type="radio" name="radio" /> Option 2</li>
<li><input type="radio" name="radio" /> Option 3</li>
</ul>
</div>
</li>
<li>Category</li>
<li>Category</li>
</ul>
</div>
<h1>What I want to work</h1>
<div class="option2">
<ul>
<li>Category</li>
<li>Category</li>
<li>Category</li>
<li>Category
<div>
<ul>
<li><input type="radio" name="radio" /> Option 1</li>
<li><input type="radio" name="radio" /> Option 2</li>
<li><input type="radio" name="radio" /> Option 3</li>
</ul>
</div>
</li>
<li>Category</li>
<li>Category</li>
</ul>
</div>
CSS:
aside { background: #f2f2f2; margin: 1em 0; padding: .5em; }
h1 { margin: 1em 0 0; }
/* This works */
.option1 { }
.option1 ul { }
.option1 ul li { border-bottom: 1px solid black; }
.option1 ul li div ul li { border: none; }
/* What I want to work */
.option2 { }
.option2 ul { }
.option2 ul li { border-bottom: 1px solid black; }
.option2 ul li div >* { border: none; }
Your code (.option2 ul li div > *) doesn't work because the lists themselves have no borders, but the list items do. Thus, .option2 ul li div ul > * would work, but moreover, even specifying .option2 ul li * would target any element nested within a list item of the option2 list.
.option2 ul li { border-bottom: 1px solid black; }
.option2 ul li * { border: none; } //removes border on nested elements of any kind
I misunderstood
Just remove the ">" and you should be fine
http://jsfiddle.net/VnLZH/9/
.option2 ul li div * { border: none; }