Simultaneous CSS hover effect on 2 separate menu elements without wrapper? - css

The navigation menu of a fictitious company is as follows:
The company specialises in the made-up, "Crab Sitting", but offers two other services that are targeted at people's anthropod pets.
It has been decided that the link to "Services" in the navigation should lead to "Pet Crab Sitting" right away — without a general page about their services.
That is easy to do with HTML:
<ul>
<li>Home</li>
<li>About</li>
<li>Services
<ul>
<li>Crab Sitting</li>
<li>Polishing Crustacean Shells</li>
<li>Massages for Anthropods</li>
</ul>
</li>
<li>Contact</li>
</ul>
But from a UX standpoint, a rollover effect that will change both is necessary to clarify that the two lead to one place.
In other words, making it appear that the two list elements are one link.
How can a :hover effect be achieved on "Services" and "Crab Sitting" at the same time with CSS, but without sacrificing HTML semantics?

else, you may as well filter from href :
This way, it doesn't matter much where similar href link stands, as long as it's being a child within adjacent ul .
http://jsfiddle.net/GCyrillus/b5Lzn/
[href*="crab-sitting"]:hover, [href*="crab-sitting"]:hover + ul [href*="crab-sitting"] {
background:green;
}
and if in second link, you forget last slash on href, it still works;
http://jsfiddle.net/GCyrillus/b5Lzn/1/
<li>Services
<ul>
<li>Crab Sitting</li>

the best you can do is:
http://jsfiddle.net/ZVUu2/2/
a.blah:hover
{color: red;}
a.blah:hover + ul > li > a.blah
{color:red;}
<ul>
<li>Home</li>
<li><a class="blah" href="/services/crab-sitting/">Services</a>
<ul>
<li><a class="blah" href="/services/crab-sitting/">Crab Sitting</a></li>
<li>Massages for Anthropods</li>
</ul>
</li>
</ul>

li:hover{
This is for the event on the main li
}
li:hover ul li:first-child{
here you have selected the first element of the nested ul when the main li is hovered
}
Happy coding

Related

Change the style of a tag that is only in wanted elements

So i have a page like this :
<body>
<ul>
<li><span class="first">First</span></li>
<li><span class="second">Second</span></li>
<li><span class="third">Third</span></li>
<li><span class="fourth">Fourth</span></li>
</ul>
</body>
I want to change the style of the "li" tags that are only in the first and the second span.
I tried this .first,.second li{margin-left:10px;}, but it didn't work.
The comma needs to separate COMPLETE element paths:
.first li, .second li
{margin-left:10px;}
I've wasted enough time explaining why I didn't mention your improper formatting that I might as well correct you on it at this point;
<body>
<ul>
<li class="first">First</li>
<li class="second">Second</li>
<li class="third">Third</li>
<li class="fourth">Fourth</li>
</ul>
</body>
CSS:
li.first, li.second {
margin-left:10px;
}
If we're really going to travel down this rabbit hole and teach code, might as well mention this can be done entirely without classes:
ul li:nth-child(1), ul li:nth-child(2)
{
margin-left:10px;
}
The li has to follow each parent element, you can't group the parents together and then expect the child to apply to each of them. What you were asking for is for the style to apply to all li that are children of elements with class=second, and to all elements with class=first, not to all li that are children of elements with class=first
.first li, .second li { margin-left:10px }
https://jsfiddle.net/udnjqqkh/
.first li {margin-left:10px;}
.second li {margin-left:10px;}

CSS Style Select Active Menu Item Differently Than Others on Hover

The following HTML is created by Joomla 1.7 for the menu of a site I'm working on:
<ul class="menu-tabbed-horiz">
<li class="item-435 current active parent">
<a class="firstmenuitem" href="/joomla/" >Home</a>
</li>
<li class="item-467">
<a href="/joomla/index.php/menu2" >Menu 2</a>
</li>
<li class="item-468">
<a href="/joomla/index.php/memu3" >Menu 3</a>
</li>
</ul>
Via CSS, I'm styling this menu. For example, I style the menu item that the mouse is hovering over like this: .menu-tabbed-horiz a:hover. The active one can be styled like so: .menu-tabbed-horiz .current a.
This works without problem, but now I would like to style a menu item differently when it is the current one and hovered on than when it is just hovered on. Something like .menu-tabbed-horiz a:hover && !.current, but that obviously does not work.
Any suggestions would be appreciated, Fabian
If I've understood your question correctly, then you're looking for something like this:
.menu-tabbed-horiz .current a:hover { /*Hovered and current*/ }
.menu-tabbed-horiz a:hover { /*Hovered (all)*/ }
This should work because the first selector is more specific than the second and will therefore be applied to elements with .current instead of the second selector.
Here's a working example of the above code.
You can't do this kind of thing directly. The solution is to define the "non-current" style for .menu-tabbed-horiz li, and the "current" style for .menu-tabbed-horiz li.active.
The second style is more specific than the first, so it will take precedence whenever both styles are present. The first style will be applied for all .menu-tabbed-horiz elements that don't have the .current class.

Weird child selector behavior

Well, I finally decided to totally drop IE6. It's great. First big benefit which comes with this decision is child selectors. So I started to use them for my nested drop-down menus for the first time and expected it to be a breeze. But... here's the code:
<style>
body {
color:#000;
}
ul.top > li {
color:red;
}
<ul class="top">
<li>top li</li>
<li>
<ul class="sub">
<li>sub li</li>
<li>sub li</li>
</ul>
</li>
</ul>
What I expected here, that only immediate children of .top unordered list are colored red and all the rest are black. Isn't it a logical thing to expect? But they all actually get red...
try
ul.top > li {
color:red;
}
ul.sub > li {
color:black;
}
??
Tim gave you the solution. The explanation for this behaviour is that though color: red; is only applied to the top-level lis, the color is inherited by their descendants. Check CSS Inheritance at Dorward Online for an in-depth explanation.
Well you see the red color is applied to both the first and the second element in the list .top, now the second element does not have any style information for color applied, so therefore it uses the style of the parent witch has the color red.
Unfortunately the child selector causing all the li to inherit the class. So you'll need to define another child ul.sub > li{

How to apply different CSS style to child elements as they occur inside one another?

For example my HTML is this
<ul>
<li>Sample 1</li>
<li>Sample 2
<ul>
<li>Sub 1</li>
<li>Sub 2</li>
<li>Sub 3
<ul>
<li>Grandsub 1</li>
<li>Grandsub 2</li>
<li>Grandsub 3
<ul>
<li>verySub 1</li>
<li>verySub 2</li>
</ul>
</li>
</ul>
</li>
</ul>
</li>
<li>Sample 3</li>
</ul>
I want to use different styles on every child <UL> without defining any class or id on them.
I dont know how many child <ul> might occur inside one another so inline css will not to the job
Is this possible?
All you need is to specify each level like so:
<style type="text/css">
ul li { color: red; }
ul li ul li { color: blue; }
ul li ul li ul li { color: black; }
ul li ul li ul li ul li { color: green; }
</style>
No inline style attributes, no classes required.
Works perfectly on the HTML snippet you provided. Keep in mind, that each successive level will inherit from the one before it. That's the whole idea of the "cascading" part of CSS, but I've burned myself forgetting margins at a lower level and having things go haywire.
You can use the "Inline Styling" for each element to have different styles.
Here it is:
<ul style="property:value;">
<li>..</li>
</ul>
If you don't know how many child UL/LI's there may be inside each other, then this won't be possible in CSS.
CSS doesn't support "fuzzy logic" such as: if there are over 5 <li>'s then do something.
Javascript Is the way forward me-thinks!
It looks like you want some way of programmatically defining your style. This is not possible using CSS alone. It does not support you defining your own symbolic names, let alone attempts to do something more 'programmery'. If you were able to generate your CSS dynamically then you could use this to work out the number of levels and algorithmically define the style each time
Otherwise the alternative is to put a maximum on the level of nesting (say 20 levels) and define a style for each one like artlung suggests. Most of the time the lower level definintions won't get used, but they will be there if you need them. This isn't perfect but it's the best you can do with writing directly in CSS.
This uses jQuery, and cycles through a list of three background colours:
function nestedcolour(elements, level) {
if (elements.length > 0) {
var colour = ["#fafafa", "#fbf9ea", "#eeeeee"][level % 3];
elements.css('background-color', colour);
nestedcolour(elements.children("ul").children("li"), level + 1);
}
}
$(document).ready(function() {
nestedcolour($(".classofparentelement"), 0);
});
The .classofparentelement is not really necessary, you can use any method to find the parent element(s).

Making hovor state of hidden list visible when page is active

One day I hope to not be such a newbie on this stuff, but some of this feels so insurmountable sometimes!
OK. I have a nav bar with hidden li items that are visible when hovered over.
Here's the live site:
http://www.rattletree.com
Here's the code for the nav:
<ul id="navbar">
<li id="iex">About Rattletree</li>
<li id="upcomgshows">Calendar</li>
<li id="sods">Sights & Sounds
<ul class="innerlist">
<li class="innerlist"><img class="arrowAdjust" src="images/curved_arrow.png" alt="" /></li>
<li class="innerlist">Listen</li>
<li class="innerlist">Photos</li>
<li class="innerlist">Video</li>
<li class="innerlist">Press</li>
</ul>
</li>
<li id="bookin">Contact
<ul class="innerlist">
<li class="innerlist"><img class="arrowAdjust" src="images/curved_arrow.png" alt="" /></li>
<li class="innerlist">Booking Info</li>
<li class="innerlist">Media Inquiries</li>
</ul>
</li>
<li id="ste"> Store</li>
<li id="instrumes">The Instruments</li>
<li id="classe">Workshops</li>
</ul>
css:
div#navbar2 {
background-color:#546F8B;
border-bottom:1px solid #546F8B;
border-top:1px solid #000000;
display:inline-block;
position:relative;
width:100%;
}
div#navbar2 ul#navbar {
color:#FFFFFF;
font-family:Arial,Helvetica,sans-serif;
font-size:16px;
letter-spacing:1px;
margin:10px 0;
padding:0;
white-space:nowrap;
}
div#navbar2 ul#navbar li ul.innerlist {
color:#000000;
display:none;
position:relative;
z-index:20;
}
div#navbar2 ul#navbar li {
display:inline;
list-style-type:none;
margin:0;
padding:0;
position:relative;
}
Now it's a bit tricky what I want to do:
If a user navigates to one of the innerlist pages, I'd like that innerlist ul to remain visible (with the specific li displaying the hovered state).
Now I think I could figure that out on my own, but you can see on the live page that if the user is on a page from the innerlist and that list was visible, then if they hovered over the other nav tab, then those innerlists would overlap. This is a problem.
Hopefully that last sentence makes sense!
In short:
I need to keep the inner list of the active page displaying, BUT if the user hovers over another nav button WITH it's own inner list, then the live innerlist needs to disappear.
Clear as mud?
I would suggest jQuery as it gives you a complete tool set for this sort of thing. But basically let us assume that you have the css you declared above.
$("ul#navbar li ul.innerlist").show()
or
$("ul#navbar li ul.innerlist").hide()
these are going to allow you to control your visibility state. You bind these to the parents:
$("div#navbar2 ul#navbar li").hover(function() {
$("ul", this).show();
});
With some input from How to get the children of the $(this) selector?
You will need to use Javascript to handle this. You won't be able to do this entirely with CSS.
What you will want to do is create a Javascript function that will be triggered on the "mouseover" event of any of the elements of ul#navbar. This function will make any inner lists that are showing be hidden, and show the proper inner list for that menu element.
I suggest the following. On the page that you are showing, give the li a class of active.
Then with jQuery, do the following:
$('li.active > ul').show();
Also, you'd want to cancel the hovering possibility for that li, since if you don't, whenever someone hovers on it, the submenu will hide after the user hovers off.
So,
$('li.active').hover(function() {
$('li.active > ul').show();
});
That should take care of it, me thinks.
Good luck.
Could also be done with CSS only, see: http://aext.net/2009/12/incredible-drop-down-menu-solution-with-css-only/
Be careful, you can run into performance problems on big sites with :hover on elements, which are noch anchors in IE -.-
Avoid the :hover pseudo-selector for
non-link elements for IE clients. If
you use :hover on non-anchor elements,
test the page in IE7 and IE8 to be
sure your page is usable. If you
find that :hover is causing
performance issues, consider
conditionally using a JavaScript
onmouseover event handler for IE
clients.
-> http://code.google.com/intl/de-DE/speed/page-speed/docs/rendering.html

Resources