Select tag overlap in IE, Part III

Update 15 Sep 2006: Added check to see if target element is contained in the li before removing the sfhover class to avoid flickering over select elements with a size greater then one.

I've modified iehover-fix.js to use DOM methods to create the iframe shim instead of innerHTML. When using innerHTML the iframe, menus and sub menus were added, which in cases with a large menu tree could take some time. I usually use innerHTML to add a number of elements to the DOM because it is faster. In this case using DOM methods should improve performance since we are only adding one element for each dropdown or flyout menu and not recreating the menu list. I've also added code suggested by Alistair Potts that should work with https pages.

Previously I used:

// IE script to cover <select> elements with <iframe>s
for (j=0; j<ieULs.length; j++) {
	ieULs[j].innerHTML = ('<iframe src="about:blank" scrolling="no" frameborder="0" style="filter: progid:DXImageTransform.Microsoft.Alpha(style=0,opacity=0);"></iframe>' + ieULs[j].innerHTML);
	var ieMat = ieULs[j].firstChild;
	ieMat.style.width=ieULs[j].offsetWidth+"px";
	ieMat.style.height=ieULs[j].offsetHeight+"px";
	ieMat.style.zIndex="-1";
	ieULs[j].style.zIndex="101";
}

Now, I use:

// IE script to cover <select> elements with <iframe>s
for (j=0; j<ieULs.length; j++) {
	var ieMat=document.createElement('iframe');
	if(document.location.protocol == "https:")
		ieMat.src="//0";
	else
		ieMat.src="javascript:false";
	ieMat.scrolling="no";
	ieMat.frameBorder="0";
	ieMat.style.width=ieULs[j].offsetWidth+"px";
	ieMat.style.height=ieULs[j].offsetHeight+"px";
	ieMat.style.zIndex="-1";
	ieULs[j].insertBefore(ieMat, ieULs[j].childNodes[0]);
	ieULs[j].style.zIndex="101";
}

Hopefully this will improve performance and work with https protocol pages.

While I was at it I worked on a version of the menu that uses opacity. In the past I just added opacity to the ul rule which worked with most browsers and IE. This time it worked in Firefox, but with the iframe inside the ul. it didn't work very well with IE.

sfopacity1.gif

Not exactly what I expected. It worked when I added opacity to the li rule and removed the background color from the ul rule.

/* This is to make opacity work in IE. */
* html #nav li ul {
	background-color: transparent;
}
* html #nav li li {
	background: #fff;
	filter: progid:DXImageTransform.Microsoft.Alpha(style=0,opacity=90);
}

sfopacity2.gif

Use your own judgement for the opacity value. Here, I'm using 90. To much opacity (a smaller number) and the menus will be unreadable.

As before, go to the Son of Suckerfish Dropdowns article to learn how to create the CSS for a dropdown menu. Then to use iehover-fix.js, add "nav" as a class name to each top level unordered list.

<ul class="nav">

Include the script element for iehover-fix.js with your directory structure to iehover-fix.js using an IE conditional comment so that it only applies to IE versions less than 7.

<!--[if lt IE 7]><script type="text/javascript" src="js/iehover-fix.js"></script><![endif]-->

And finally add a little bit of CSS to make it work.

/* Support for the "iehover-fix.js" */

* html ul#nav iframe, * html ul.nav iframe {
	position: absolute;
	/* account for the border */
	left: -0.25em;
	top: -0.25em;
	z-index: 0;
	filter: progid:DXImageTransform.Microsoft.Alpha(style=0,opacity=0);
}

/* this is for IE 5.0
select.hide { visibility: hidden; }

/* End Support for the "iehover-fix.js" */

I took the time to copy the Son of Suckerfish Dropdowns example with select elements added so that you can see the problem. You will only see the error in IE. You can see that the iehover fix example in which the dropdowns to go over the select elements in IE.

Samples and Download

Related Articles

80 Comments

Gravatar Image2. Posted at 8/13/2006 6:37:01 PM by Tanny O'Haley

I like what Mathew has done with the onfocus and onblur events with the addition of the "sffocus" class. Works nicely though you might want to add an onkeyup event to catch the arrow key so that users can go between menus without having to tab through each item in a menu to go to the next menu. Just add Mathew's mcAccessible code to your page, modify the CSS and it should work. My code is specific to the problem of menus to not going over select tags in IE versions less than 7. Since not all browsers support the focus pseudo class, his code should be added to include browsers other than IE.

Either way, if the user is using a screen reader the menus should still be available since the CSS hides the drop downs and flyouts by offsetting the menu to the left of the page.

Gravatar Image3. Posted at 8/21/2006 12:01:02 PM by ileadu

Hi,

{ Link }

This example have some problems in Opera 9

Can you help me fix it?

Gravatar Image4. Posted at 8/21/2006 6:06:06 PM by Tanny O'Haley

Hi ileadu,

Please try again. I had set the src of the iframe to javascript:false which was returning false to the window. I have changed that code for Opera and tested it in Opera 9.

Gravatar Image5. Posted at 8/22/2006 11:52:45 PM by ileadu

I have tested it tody.

There is a little problem in Opera9.01 . My mouse cursor move from Percoidei(Top of menu) to Remoras then Remoras often is gone. Anybody can help test it? I'm not good at English.

Gravatar Image6. Posted at 8/23/2006 3:48:46 AM by ileadu

Addition function: use key to navigate

See this link

{ Link }

Ctrl+F2 - enter/switch menu | Arrow keys - navigate | Esc - exit menu

This is useful for browsering web page without the mouse.

Gravatar Image7. Posted at 8/25/2006 9:55:48 AM by greg

I think these DOM methods can be found at webreference.com. They are useful, indeed.

Gravatar Image8. Posted at 9/22/2006 7:48:16 AM by Greg Stout

Tanny,

I read your article with great intrest. I am experincing a issue with select boxes as well.

{ Link }

Based on what you see here where I have

onmouseover="this.style.filter ='alpha(opacity=100)'

onmouseout="this.style.filter ='alpha(opacity=20)'"

on a div.

You can see that everything responds to the transaparency except the selects.

In your mind is this the same z-index issue and if so how could I resolve it?

I would apprecite your help

Gravatar Image9. Posted at 9/22/2006 9:03:51 AM by Tanny O'Haley

Hi Gregg,

I'm sure that someone out there has implemented this technique with divs. However, the work is already done for you with the Suckerfish dropdowns (which can also flyout at the side). What you get with iehover-fix.js is a solution that works with the Suckerfish dropdowns. Give it a try.

Tanny...

Gravatar Image10. Posted at 9/25/2006 11:59:10 AM by Kristin

Tanny,

The problem I am having is using your latest examples and is based on suckerfish drop downs but in IE the menu goes blank when it goes over a drop down. This is on a https: site. ANy suggestions? It works fine using firefox.

Thanks so much for your help!

Gravatar Image11. Posted at 9/25/2006 12:59:03 PM by Tanny O'Haley

Hi Kristin,

Do you have a test link that I can try?

Tanny...

Gravatar Image12. Posted at 9/25/2006 5:59:36 PM by Kristin

Tanny,

Check your email. Thanks so much for your help.

Kristin

Gravatar Image13. Posted at 10/6/2006 10:54:51 AM by Jonathan

I'm not sure why, but when I try to implement your fix to the suckerfish drop menu, nothing drops.

Will your fix fly over a flash element?

Thanks.

Gravatar Image14. Posted at 10/17/2006 7:16:11 AM by Rob

I was using a son of suckerfish varient and select boxes were driving me crazy. After finding your article, I switched to son of suckerfish, updated the CSS and used your code. Now everything's fine. Thank you for sharing your work! It saved the day.

Gravatar Image15. Posted at 10/23/2006 2:39:21 PM by Ricardo Carrasco

this works if you only have one page to hide a select;

working example at

{ Link }

var navHover,rooter;

navHover=function(){

navRoot=document.getElementById("navmenu").getElementsByTagName("li");

for (var i=0;i<navRoot.length;i++){

navRoot[ i ].onmouseover=function(){

this.className+="iehover";

rooter=document.getElementById("form1").style;

rooter.visibility="hidden";

};

navRoot[ i ].onmouseout=function(){

this.className=this.className.replace("iehover","");

rooter=document.getElementById("form1").style;

rooter.visibility="visible";

}}};

if(window.attachEvent) window.attachEvent("onload",navHover);

Gravatar Image16. Posted at 10/23/2006 6:21:34 PM by Tanny O'Haley

Hi Ricardo,

Yes your code does work, just not the way a user would expect. The code completely hides the form! You will not see any of the fields! In your example the only place your code is used for a menu, is the Libraries Menu, which completely covers the form so the user doesn't see that the code is hiding the form. If you change the location of the Libraries menu you will see that the select elements disappear.

The purpose of iehover-fix.js is not to hide the form, but to make the menus go over the select elements instead of under. This is what a user expects of menu behavior.

Gravatar Image17. Posted at 10/23/2006 9:05:23 PM by Ricardo Carrasco

I would have to say that your answer makes no sense, if I put the form or menu someplace else, why would your script or my script be necessary? "The code completely hides the form!" You know that and I know that, I doubt most users would notice unless it was a larger form. You can't use the menu and the form at the same time anyways. I would like to point out that I only was saying for maybe one or two to three pages of this problem, my script(which works with your current css btw) is sufficient, however I realize that your script is lots more sensible for a large site.

Gravatar Image18. Posted at 10/23/2006 9:57:38 PM by Ricardo Carrasco

Sorry for posting again, I would think that a span over the suspect select elements would work also, without hiding the entire form. Also, why would you put IE filters in the css if it is for IE only, as the script is? Which is where the IE opacity should be.

Gravatar Image19. Posted at 10/23/2006 10:30:09 PM by Tanny O'Haley

Hi Ricardo,

Actually for IE 5.0 the code hides select elements without needing additional markup. It uses the iframe shim for IE 5.5 through IE 6.0 as IE 7 and other browsers don't need the iframe shim. This is because in IE prior to 7 select elements are a windowed control which is why they "bleed" through elements like menus or dropdown calendars that are supposed to go over the select elements.

One of the first uses this method was because of user complaints on a login form in the right column of a site. The user's complained that it was confusing to them when the select element disappeared when the menu was supposed to partially obscure the select element. The form had two input fields a select element and a submit button.

My first version of this fixed the problem but only supported a single level dropdown menu. This version supports many levels of nested menus.

Gravatar Image20. Posted at 10/24/2006 11:57:13 AM by Ricardo Carrasco

yea I know all about the selects after IE5.0. You do great work, a lot better than I can ever hope to achieve, just hope you don't bite the chitika stuff like cssplay did(Stu Nicholls). take it easy.

Gravatar Image21. Posted at 11/9/2006 1:29:28 PM by Brent

I was having the same problem that Kristin was having error pages loading in the iframe and blanking out the menu. However I found a fix for that here

and changed \\0 to blank.html and made that blank.html file.

Now I just have to fix my menus being offset to the right in ie6.

Gravatar Image22. Posted at 11/9/2006 2:09:37 PM by Tanny O'Haley

Hi Brent,

That was the solution I gave to Kirstin only the file she used is blank.htm instead of blank.html. I'm also having this problem with my DOMContentLoaded event. I fixed the link in your comment to the article.

Gravatar Image23. Posted at 11/15/2006 11:00:31 AM by Mike Robinson

Thanks so much for your hard work on this fix. I had been pulling my hair out trying to figure out a workaround until I came across your solution.

Gravatar Image24. Posted at 11/15/2006 1:50:09 PM by Mike Robinson

Perhaps I spoke too soon with that last comment. :) I'm pulling out my hair again! I have implemented this solution in an environment that uses both http and https connections (for internal and external access respectively). Internally, there are no problems. Externally, however, there is a pop-up in IE for every top level menu item (i.e. every transparent iframe created) saying "This page displays both secure and non-secure items. Do you wish to continue displaying the non-secure items? Yes/No". My hunch here is to set the iframe src to another https url (such as a blank html file on the server prefixed by https) and it seems to me that this should avert the pop-ups. But, I don't have a testing/development server running on https, so I would have to test this on a production server which is not an option I'm willing to exercise yet. Do you think or can you verify that this solution would work?

Thanks in advance for any input, and again for your hard work on this fix.

Gravatar Image25. Posted at 11/15/2006 5:52:42 PM by Tanny O'Haley

Hi Mike,

This is an easy one to fix. Go into the code and change the src attribute of the iframe from about:blank to blank.htm.

ieULs[j].innerHTML = ('<iframe src="about:blank" scrolling="no" frameborder="0" style="filter: progid:DXImageTransform.Microsoft.Alpha(style=0,opacity=0);"></iframe>' + ieULs[j].innerHTML);

Should be changed to:

ieULs[j].innerHTML = ('<iframe src="blank.htm" scrolling="no" frameborder="0" style="filter: progid:DXImageTransform.Microsoft.Alpha(style=0,opacity=0);"></iframe>' + ieULs[j].innerHTML);

Then create a blank.htm page that will be accessible to the iframe. Brent in comment 21 used this and I helped Kristin in comment 10 use the same method.

Gravatar Image26. Posted at 11/20/2006 5:25:26 AM by Edson Correa

Hi Tanny, I'm having the same problem that Kristin reported. In HTTPS pages the drop-down menus goes blank, but in normal HTTP works fine. I cannot give you a link for test because the test site requires login with a valid digital certificate. But since I see that Kristin was the same problem but as the solution was not been posted, maybe you have the solution for this. I'm getting crazy with this since the site must go to the production as soon as possible. I'll appreciate any help.

Gravatar Image27. Posted at 11/20/2006 6:24:47 PM by Tanny O'Haley

Hi Edson,

Please see comment 25 for a solution to the https problem.

Gravatar Image28. Posted at 12/4/2006 10:21:24 PM by Rommel

Hi Tanny, you code works great but somehow the dropdown menus does not show up in IE/Mac. Any idea how this to be fix?

--Rommel

Gravatar Image29. Posted at 12/5/2006 4:34:53 PM by Tanny O'Haley

Hi Rommel,

The problem is that Mac IE5 doesn't support attachEvent which is used by the code to add the event. What you might want to do is use an IE conditional comment to include the iehover-fix.js file and change the code to use window.onload=sfHover; instead, if you absolutely need to support IE Mac. However, the iframe code is specific to the Windows operating system. So you will probably need to add code to check to see if it is IE Mac to not add the iframe code. Personally, I no longer support IE Mac because it is so buggy.

Gravatar Image30. Posted at 12/5/2006 5:40:40 PM by Rommel

Thanks man!

Gravatar Image31. Posted at 12/12/2006 8:17:06 AM by Russell Keppner

Hi Tanny,

I just wanted to chime in and say thanks! Your post here saved me hours of hair pulling; it answered my question exactly. It's amazing a Google search can lead you to.

Gravatar Image32. Posted at 12/13/2006 2:48:53 AM by nagi reddy

Its good . But for me in my application we r creating one dialog box if that dialog box is dragged onto the select list then overlapping is come into the picture. Will u plz help me in this regard.

Gravatar Image33. Posted at 12/13/2006 2:49:59 AM by nagi reddy

Hi Tanny,

will plz help.As early as possible.

Gravatar Image34. Posted at 12/13/2006 1:34:33 PM by Tanny O'Haley

Hi Nagi

Look at the code for the Calendar Dropdown. It uses an iframe as a shim behind the calendar so that it goes over select elements in IE 5.5 and 6. IE 7 doesn't use a windowed control for select elements and IE 5 does not support iframes. For IE 5 you will have to run code to set the visibility of all select elements to hidden.

Another option is to use an actual popup window.

Gravatar Image35. Posted at 1/9/2007 9:07:35 AM by Daniel Marlow

I had some trouble with this line in the setHover function:

ieMat.src="//0";

and IE6, which in some cases popped up a "secure/non-secure items" warning or displayed the iframe on top of the menu, rather than behind it. By changing that line to this:

ieMat.src="javascript:'<html></html>';

the secure/non-secure items warning went away and the iframe is always behind the menu.

I found the empty javascript document trick from the Microsoft AJAX guys and a similar problem I was having with some of the new AJAX controls. Check out the end of this thread:

{ Link }

The empty javascript document trick seems to work more universally than 'about:blank' or 'blank.html'. We tried 'em all with varying degrees of success (or lack thereof, actually.)

I suspect I might be able to always set the iframe's source to that empty javascript document but I have not been able to fully test it in your script yet.

Anyway, many thanks for the script. It has helped immensely!

Gravatar Image36. Posted at 1/30/2007 9:16:50 AM by john

I found that for IE 7 you need to apply a background to the hover list elements for the drop down to work. This code is essential on your example.

#nav li:hover, #nav li.sfhover {

background: #eda;

}

Wanted to pass that along as it is not required in the Son of Suckerfish drop-downs. Maybe it should be as their example page has a background so it works in IE7

John

Gravatar Image37. Posted at 1/30/2007 3:53:16 PM by Kris

Back in December, I successfully implemented the blank.html solution referenced in comment #21. All was well with Suckerfish on https...

Now we've noticed the mixed content messages coming up again in IE6 and IE7. Today I revisited this board and tried the latest solution from comment #35, but it has no effect. I'm still getting mixed content popups. Anyone else noticed this problem reappearing? Any ideas?

PS

Thanks to everyone for their contributions!

Gravatar Image38. Posted at 2/19/2007 2:13:12 PM by Nicholas Engelking

I've noticed that the iframe shims are set using px withds and heights:

ieMat.style.width=ieULs[j].offsetWidth+"px";

ieMat.style.height=ieULs[j].offsetHeight+"px";

while the menus themselves are set using ems. Ems are of course more desierable as they let the user change their font size. The menus scale perfectly in i.e. with font size, but the shims don't, and are too large or too small with non-normal font sizes. I believe the fix is to set the width and height of ieMat in ems, but as far as I know there is no way to get the offset height and widths in ems. Is there another place to get the size information in ems to make the solution scale with font size?

Gravatar Image39. Posted at 2/19/2007 5:32:28 PM by Tanny O'Haley

Nicholas,

Making the size of the shims is something I've thought about for a long time. Right now I don't know of any reliable way to get the height and width in the same unit as defined by the developer's CSS.

I was thinking of taking the width out and letting the CSS define the width, the problem is with the height, though I haven't tried it yet. You may be able to define the width of the iframe in ems and the height as 100%.

If anyone gives that a try please post back the results.

Thank you.

Gravatar Image40. Posted at 4/29/2007 4:49:12 AM by Rafael

Tanny, I think you could use IE's currentStyle method to access the menu dimensions in ems. It returns the values the author has put in the CSS along with the units.

Gravatar Image41. Posted at 4/30/2007 7:14:38 AM by Kevin

Great work! I sucessfully used your menu to replace a static, fixed width menu. But, once I replaced the link's href with real ones, I had the following unusual behavior. On fast loading screens, no problem. On screens that took longer, the request stopped. Then I realized I got bored waiting and moved my mouse, which I guess cause the onmouseout to fire and cancel the pending request. I retested making sur enot to move teh nouse after I clicked the link. No problem. So I deduced that onmouseout is cancelling the navigation. I tried to add: return true; to the end of the onmouse function handler, but there was no effect. Any ideas?

Gravatar Image42. Posted at 5/1/2007 1:20:14 PM by Leif Jason

Thanks Tanny - this proved quite useful.

Gravatar Image43. Posted at 6/1/2007 8:55:58 AM by Gregory Becker

Your workarround / fix triggers errors on IE 6 when the page is secured with SSL (the famous 'the page contains unsecured elements...' errors).

That's because when SSL is activated you're trying the load '//0'. I had to change your code a bit to make it working properly :

Instead of having

.src = '//0'

You could have

.src = 'javascript:false'

And finally, I have this :

var ieMat=document.createElement('iframe');

ieMat.src="javascript:false";

... rest of the code ...

ieULs[j].insertBefore(ieMat, ieULs[j].childNodes[0]);

Gravatar Image44. Posted at 6/1/2007 10:09:44 AM by Tanny O'Haley

Hi Gregory,

The javascript:false solution, while it does get rid of the SSL error also displays the word "false" in the iframe. This is why I recommend replacing the source with an actual blank.htm page on your site if you are using SSL.

Gravatar Image45. Posted at 6/4/2007 11:20:57 AM by Ruslan Ulanov

Hi Tanny,

In your post #19 you say that iframe shim is required ONLY for IE 5.5 through 6.0. Yes, it is true for a SELECT element - IE 7 now correctly renders the dropdowns, but apparently IE 7 inroduces a new issue with OBJECT elements (specifically ActiveX objects). They do "bleed" through the menus just like SELECTs did before. The iehover fix resolves this issue, so it applies to IE7 as well.

Thanks, Ruslan

Gravatar Image46. Posted at 6/4/2007 8:20:46 PM by Tanny O'Haley

Hi Ruslan,

Good to know this. Oh well, one step forward, two steps back.

Gravatar Image47. Posted at 6/21/2007 9:00:48 AM by MikeB

Hi Tanny,

I noticed this issue:

When you choose the select the dropdown list (i.e: <select>) below the nav and leave it open and then mouseover the nav to trigger the suckerfish dropdown, the select list appears above the dropdown. Any ideas how to fix this?

Thanks,

Mike

Gravatar Image48. Posted at 8/3/2007 6:42:27 AM by Robert

I'd like to see the script modified to use getElementsByClassName instead of getElementById so that you can have multiple menus on the same page, since you can't repeat an ID name.

My J'script skills aren't the best and I couldn't get the menus to close in IE 7.

Has anyone don't this yet?

Gravatar Image49. Posted at 8/3/2007 4:08:45 PM by Tanny O'Haley

Hi Robert,

The script already works with an id of nav or class of nav. It looks for both of them. First the id, then it looks at all UL elements and processes each that has nav in the className. Is it not working on your site?

Gravatar Image50. Posted at 8/7/2007 1:49:34 PM by Kris

I'm trying to debug my code for the https mixed content issue in IE7:

If anyone wants to view my source and point out the problem, I could use another set of trained eyes.

Alternatively, I would like to see your solution. Does anyone have a publicly accessible example of an https site with suckerfish menus that do not generate mixed content popups in IE7? If you send the link I can view the browser source and compare it to mine. Thanks!

Gravatar Image51. Posted at 8/7/2007 1:55:01 PM by Kris

Sorry, but the URL in my previous post was omitted. You can see the mixed content popups at:

{ Link }

Gravatar Image52. Posted at 8/29/2007 3:05:48 PM by Kris

It turns out the mixed content errors in IE7 were due not to Son of Suckerfish, but to the Google CSE search box we are using. The script was calling a non-secure .js file. I corrected the problem by conditionally pointing to the https version. Ahhh.

Gravatar Image53. Posted at 12/4/2007 9:44:30 PM by J

Thanks for sharing this. That's wonderful.

Gravatar Image54. Posted at 12/20/2007 12:31:23 PM by Daniel

Is it possible to use this script with Stu Nicholls CSS Menu? I've got my sctructure already in place and prefer his method, but need a solution to the SELECT issue. Has anyone tried to modify the script according to the menu in the url below?

Drop Down Menu

Gravatar Image55. Posted at 12/20/2007 3:07:00 PM by Tanny O'Haley

Hi Daniel,

It looks like it may be possible to use the technique. You would have to write code that would use the for loop that inserts and sizes the iframe as the first element in the ul. This of course would not work for IE5 and below. It may work, but with the numerous conditional statements to make Stu Nicholls' menu to work in IE, you can only try it out and see if it works.

I personally think that the use of the many conditional statements in the unordered lists that add tables or changes the list in Stu's menu detracts from the ease of use and maintainability of a simple unordered list in the Suckerfish menus.

Gravatar Image56. Posted at 1/10/2008 4:36:56 PM by Paul

Hi- Thanks for all your hard work. I have pdf documents in iframes that I'm trying to get my suckerfish menus to hover over. Your solution seems to work fine in IE but not in Firefox. Any ideas? Thanks!

Gravatar Image57. Posted at 1/10/2008 6:46:08 PM by Tanny O'Haley

Hi Paul,

Sorry I don't have a solution for Firefox and the PDF documents. This solution is for IE only.

Gravatar Image58. Posted at 1/11/2008 9:08:18 AM by Paul

Anyone out there have a solution for DHTML elements hovering over pdf documents within iframes in Firefox? I've scoured the web and can find nothing!

Thanks!

Gravatar Image59. Posted at 1/14/2008 9:07:10 AM by Paul

It looks like there aren't any answers out there for hovering suckerfish dropdowns over iframed pdfs in Firefox. What about hiding the iframe during a dropdown? Anybody know how to do this? Other solutions?

Any help would be greatly appreciated! I've been banging my head against this for days!

Gravatar Image60. Posted at 1/31/2008 7:58:20 PM by Derek

Is there a way with this version to have a delay say 200 miliseconds on the drop down menu??

I know with the original version you could add a Timer function to the js, but I cant seem to figure out how to get it to work with this version.

I really like how well this version runs and the delay is the only thing I think it is missing. Can someone help me get this to work?

Gravatar Image61. Posted at 2/20/2008 1:13:06 AM by chris

How would you rewrite your script if you have two menus on your website? I have a vertical and a horizontal menu. Both menus have submenus 3 layers deep. I have tried out your script but it works only with one menu than the other one does not work and my javascript is not good enough to rewrite it for two menus. Could you please help? My two menu ID's are: "nav" and "leftnav".

Many Thanks

Chris

Gravatar Image62. Posted at 2/20/2008 11:17:35 AM by Tanny O'Haley

Hi Chris,

Instead of an ID equal to "nav", use a "nav" class on each UL you want to use as a menu. The code is setup to automatically look for ULs with a class of "nav".

Gravatar Image63. Posted at 3/14/2008 7:57:26 AM by carlos

first of all thanks- this is good fix with ihover...js file.but i really need urgent help.I have menu.jsp in which im creating my menu and there is main.jsp which is calling menu.jsp on top part and down part 2.jsp which has tab pane....

now the prob: whenever i cliek on menu i can see small menu is flashing at top-right corner and then later it will show the proper rendering of the menu.

please give me sol for this..its very urgent

Gravatar Image64. Posted at 3/14/2008 2:16:31 PM by carlos

Hello Tanny,

post 63 is solved now but im facing wired issue in IE7....

my submenu get overlapped bye my tab control.means my menu is get overlapped by my tab control...

pl.help me

Gravatar Image65. Posted at 4/3/2008 10:06:54 PM by brenton

Thanks for this tanny, I've been looking for a fix like this for a long time and have only just come across yours and it worked straight away. tahnks

Gravatar Image66. Posted at 4/7/2008 2:00:54 PM by carlos

Hello Tanny,

Im facing very wierd issue.the drop-down menu is working fine but on one of the server(Iplanet) on IE6 it is giving me prob.it is showing blank menu. for ref. here is the java script.

<!--[if lte IE 6]>

<script type="text/javascript"><!--//--><![CDATA[//><!--

sfHover = function() {

// Support the standard nav without a class of nav.

var el = document.getElementById("nav");

if(!/\bnav\b/.test(el.className) && el.tagName == "UL")

setHover(el);

// Find all unordered lists.

var ieNavs = document.getElementsByTagName('ul');

for(i=0; i<ieNavs.length; i++) {

var ul = ieNavs;

// If they have a class of nav add the menu hover.

if(/\bnav\b/.test(ul.className))

setHover(ul);

}

}

function setHover(nav) {

var ieULs = nav.getElementsByTagName('ul');

if (navigator.appVersion.substr(22,3)!="5.0") {

// IE script to cover <select> elements with <iframe>s

for (j=0; j<ieULs.length; j++) {

var ieMat=document.createElement('iframe');

if(document.location.protocol == "https:")

ieMat.src="javascript:false";

else

ieMat.src="javascript:false";

ieMat.scrolling="no";

ieMat.frameBorder="0";

ieMat.style.width=ieULs[j].offsetWidth+"px";

ieMat.style.height=ieULs[j].offsetHeight+"px";

ieMat.style.zIndex="-1";

ieULs[j].insertBefore(ieMat, ieULs[j].childNodes[0]);

ieULs[j].style.zIndex="101";

}

// IE script to change class on mouseover

var ieLIs = nav.getElementsByTagName('li');

for (var i=0; i<ieLIs.length; i++) if (ieLIs) {

// Add a sfhover class to the li.

ieLIs.onmouseover=function() {

if(!/\bsfhover\b/.test(this.className))

this.className+=" sfhover";

}

ieLIs.onmouseout=function() {

if(!this.contains(event.toElement))

this.className=this.className.replace(' sfhover', '');

}

}

} else {

// IE 5.0 doesn't support iframes so hide the select statements on hover and show on mouse out.

// IE script to change class on mouseover

var ieLIs = document.getElementById('nav').getElementsByTagName('li');

for (var i=0; i<ieLIs.length; i++) if (ieLIs) {

ieLIs.onmouseover=function() {this.className+=" sfhover";hideSelects();}

ieLIs.onmouseout=function() {this.className=this.className.replace(' sfhover', '');showSelects()}

}

}

}

// If IE 5.0 hide and show the select statements.

function hideSelects(){

var oSelects=document.getElementsByTagName("select");

for(var i=0;i<oSelects.length;i++)

oSelects.className+=" hide";

}

function showSelects(){

var oSelects=document.getElementsByTagName("select");

for(var i=0;i<oSelects.length;i++)

oSelects.className=oSelects.className.replace(" hide","");

}

// Run this only for IE.

if (window.attachEvent) window.attachEvent('onload', sfHover);

// end

//--><!]]></script>

<![endif]-->

Its really urgent i will appericiate your help on this.

Gravatar Image67. Posted at 4/7/2008 2:38:56 PM by carlos

Sorry but forgot to mentioned...on iplanet it is secured http.

but im sure in the code we already handle https..i just installed iplanet on my local machine and it is working,so mostly it is realated to { Link } http) session.

please guide me for this.

Gravatar Image68. Posted at 4/8/2008 5:31:05 PM by Tanny O'Haley

Hi Carlos,

It looks like you don't have the latest version of iehover-fix.js which does support https. Please download the latest version.

Gravatar Image69. Posted at 5/28/2008 8:19:55 AM by carlos

Hello Tanny,

I need an urgent help.Basic problem is I have menu control based on suckerfish and on my page i have tab conrol.

so when mouse is over menu,menu list is get open but it is behind the tab control and we can not select menu item from that.

BUT IT IS WORKING FINE IN IE-6 BUT NOT IN IE 7.

here for your reference i added the css file and script too.

<!--[if lte IE 6]>
<script type="text/javascript">
sfHover = function() {
// Support the standard nav without a class of nav.
var el = document.getElementById("nav");
if(!/\bnav\b/.test(el.className) && el.tagName == "UL")
setHover(el);
// Find all unordered lists.
var ieNavs = document.getElementsByTagName('ul');
for(i=0; i<ieNavs.length; i++) {
var ul = ieNavs[ i ];
// If they have a class of nav add the menu hover.
if(/\bnav\b/.test(ul.className))
setHover(ul);
}
}
function setHover(nav) {
var ieULs = nav.getElementsByTagName('ul');
if (navigator.appVersion.substr(22,3)!="5.0") {
// IE script to cover <select> elements with <iframe>s
for (j=0; j<ieULs.length; j++) {
var ieMat=document.createElement('iframe');
if(document.location.protocol == "https:")
ieMat.src="javascript:'<HTML></HTML>'";
else
ieMat.src="javascript:false";
ieMat.scrolling="no";
ieMat.frameBorder="0";
ieMat.style.width=ieULs[j].offsetWidth+"px";
ieMat.style.height=ieULs[j].offsetHeight+"px";
ieMat.style.zIndex="-1";
ieULs[j].insertBefore(ieMat, ieULs[j].childNodes[0]);
ieULs[j].style.zIndex="101";
}
// IE script to change class on mouseover
var ieLIs = nav.getElementsByTagName('li');
for (var i=0; i<ieLIs.length; i++) if (ieLIs[ i ]) {
// Add a sfhover class to the li.
ieLIs[ i ].onmouseover=function() {
if(!/\bsfhover\b/.test(this.className))
this.className+=" sfhover";
}
ieLIs[ i ].onmouseout=function() {
if(!this.contains(event.toElement))
this.className=this.className.replace(' sfhover', '');
}
}
} else {
// IE 5.0 doesn't support iframes so hide the select statements on hover and show on mouse out.
// IE script to change class on mouseover
var ieLIs = document.getElementById('nav').getElementsByTagName('li');
for (var i=0; i<ieLIs.length; i++) if (ieLIs[ i ]) {
ieLIs[ i ].onmouseover=function() {this.className+=" sfhover";hideSelects();}
ieLIs[ i ].onmouseout=function() {this.className=this.className.replace(' sfhover', '');showSelects()}
}
}
}
// If IE 5.0 hide and show the select statements.
function hideSelects(){
var oSelects=document.getElementsByTagName("select");
for(var i=0;i<oSelects.length;i++)
oSelects[ i ].className+=" hide";
}
function showSelects(){
var oSelects=document.getElementsByTagName("select");
for(var i=0;i<oSelects.length;i++)
oSelects[ i ].className=oSelects[ i ].className.replace(" hide","");
}
// Run this only for IE.
if (window.attachEvent) window.attachEvent('onload', sfHover);
// end
</script>
<![endif]-->
=======================
// CSS file
body {
margin: 0px; padding: 0px; text-align: left;
background-image: url('../images/bg_repeat.png');
background-position: top left; background-repeat: repeat-x;
background-color: #e4f8ff;
}
form {
margin: 0px;
}
.logo {
position: absolute; top: 15px; left: 20px; z-index: 10;
}
table { border-collapse: collapse; }
th { text-align: right; }
.main { width: 760px; }
.opacity { opacity: .9; filter: alpha(opacity=90); }
img { border: none; }
p { font-family: Arial, Helvetica, sans-serif; }
b { font-family: Arial, Helvetica, sans-serif; }
select {
font-family: Arial, Helvetica, sans-serif;
font-size: 1.1em;
}
input {
font-family: font-family: verdana, sans-serif;
font-size: 1.2em;
}
.closetab {
position: absolute; top: 35px; left: 785px; z-index: 1; border: none;
}
/* Drop-down Menu */
#container {
width: 650px;
/*background: #F4ECD9;*/
text-align: left;
/*border: 1px solid #eda;*/
/*border: 1px solid #559dcb*/
margin: 0 auto;
}
h1 {
height: 60px;
background: url(blank.gif) bottom center no-repeat;
text-indent: -999em;
margin: 1em 0 0 0;
}
#nav, #nav ul {
float: left;
width: 86em; /*Frame Window Width */
list-style: none;
line-height: 1;

/*background: #4a7cb0; */ /*Background for menu and submenu container too*/
background-image: url(../images/backGd.jpg);
font-family: Arial, Helvetica, sans-serif;
font-size: 11px;
padding: 0;
/*border: solid #eda;
border-width: 1px 0;*/
margin: 0.5em -20em 0 10em; /* margin: 0.5 from top,-20 from left 0 bottom 20 is right */
z-index: 10;
}
#nav a {
display: block;
width: 10em;
w\idth: 6em;
color: #7C6240;
text-decoration: none;
padding: 0.25em 2.5em; /*padding: 0.25em 2.0em;*/
}
#nav a.parent {
background: url(../images/arrow.gif) center right no-repeat;
}
#nav li {
float: left;
padding: 0;
width: 10em;
}
#nav li ul {
position: absolute;
left: -999em;
height: auto;
width: 14.4em;
w\idth: 13.9em;
font-weight: normal;
border-width: 0.15em;
border: 1px solid #BBB; /*THEME CHANGE HERE*/
margin: 0;
}
#nav li li {
padding-right: 1em;
width: 13em /* Selector width*/
}
#nav li ul a {
width: 13em;
w\idth: 9em;
}
#nav li ul ul {
margin: -1.75em 0 0 14em;
}
#nav li:hover ul ul, #nav li:hover ul ul ul, #nav li.sfhover ul ul, #nav li.sfhover ul ul ul {
left: -999em;
}
#nav li:hover ul, #nav li li:hover ul, #nav li li li:hover ul, #nav li.sfhover ul, #nav li li.sfhover ul, #nav li li li.sfhover ul {
left: auto;
}
/*
#nav li:hover, #nav li.hover {
position: static;
}*/
#nav li:hover {background-position: 0 0;}
/*
#nav li:hover ul, #nav li.sfhover ul {
left: auto;
background-position: 0 0;
}*/
#nav li:hover, #nav li.sfhover {
background: #c8e3f0; /* #eda; Selector Color */
}
#content {
clear: left;
}
#content a {
color: #7C6240;
}
#content a:hover {
text-decoration: none;
}
#scaffolding {
height: 70px;
background: white url(/images/header_bg.gif) no-repeat;
border: solid #eda;
border-width: 1px 0 0 0;
margin: 1em 0 0 0;
}
#scaffolding a {
text-decoration: none;
text-indent: -999em;
display: block;
height: 70px;
background: url(/images/hdlogo_flip2.gif) no-repeat;
background-position: 181px 0;
}
#scaffolding a:hover {
background-position: 181px -70px;
}
ul.nav iframe {
position: absolute;
/* account for the border */
left: -0.25em;
top: -0.25em;
z-index: -1;
filter: progid:DXImageTransform.Microsoft.Alpha(style=0,opacity=0);
}
html ul.nav li { z-index: 201; }
/* this is for IE 5.0 */
select.hide { visibility: hidden; }
/* End Support for the "iehover-fix.js" */
*:first-child+html #nav {height: 1%;}
*:first-child+html #nav li {height: 1%;}
/* End of Menu */
.tabPane {
height: 21px; /* Height of tabs */
border: none;
}
.aTab {
border: none; font-family: Arial; padding: 20px; font-size: 11px;
}
.aTab th, td {
padding: 2px;
spacing: 2px;
}
.aTab .display {
width: 750px; height: 300px; background-image: url(../images/tablebg.png);
margin-top: 20px;
}
.aTab .display table { width: 750px; }
.aTab .display th {
background-image: url('../images/thbar.png'); background-position: top left;
background-repeat: repeat-x; height: 28px; padding: 0px 5px;
font-weight: bold; color: #fff; vertical-align: middle;
}
.tabPane DIV {
float: left; height: 100%; /* Height of tabs */
padding-left: 10px; vertical-align: middle; background-repeat: no-repeat;
background-position: bottom left; cursor: pointer; position: relative;
bottom: -1px; margin-left: 0px; margin-right: 0px;
}
.tabPane .tabActive {
background-image: url('../images/tab_left_active.gif');
margin-left: 0px; margin-right: 10px; z-index: 10;
}
.tabPane .tabInactive {
background-image: url('../images/tab_left_inactive.gif');
margin-left: 0px; margin-right: 10px; z-index: 1;
}
.tabPane .inactiveTabOver {
background-image: url('../images/tab_left_over.gif');
margin-left: 0px; margin-right: 10px;
}
.tabPane span {
font-family: arial; vertical-align: top

; font-size: 11px;
padding-left: 3px; padding-right: 3px; line-height: 21px;
float: left;
}
.tabPane .tabActive span {
padding-bottom: 1px; line-height: 20px;
}
.tabPane img { float: left; }
/* End of Tabs */
.tabFrame {
overflow: auto;
width: 760px;
border: 1px white solid;
}
.tabFrame table {
border: 0;
}
.tabFrame th {
background-image: url('../images/thbar.png');
background-position: top left;
background-repeat: repeat-x;
height: 28px;
padding: 1px 5px;
font-weight: bold;
color: #fff;
vertical-align: middle;
text-align: left;
}
.tabFrame td {
spacing: 3px;
padding: 3px;
vertical-align: top;
font-size: 12px
}
.upper input {
text-transform: uppercase;
}

Gravatar Image70. Posted at 5/28/2008 7:53:48 PM by Tanny O'Haley

Hi Carlos,

I think your problem may be one of z-index. Make sure that the z-index of your tabs is less than the menu.

If that doesn't work, set the conditional comment from:

<!--[if lte IE 6]>

to:

<!--[if lte IE 7]>

Gravatar Image71. Posted at 6/6/2008 8:13:33 AM by Lee Glasgow

Is there a way to get this to work in FF and Safari, I am having trouble with a java applet and this script helps the menus hover over the java applet in ie6 and ie7 but it isn't getting called in FF and Safari. I will say that this is an awesome fix. Thanks

Gravatar Image72. Posted at 7/18/2008 7:58:21 AM by coolgirl

Tanny,

I am using the solution you provided. But Still no Success in IE6. Can you Please Help me?Thanks

Gravatar Image73. Posted at 7/18/2008 8:42:47 AM by coolgirl

Can anyone provide a complete solution please?

Gravatar Image75. Posted at 9/19/2008 7:17:13 AM by Markus

Question about IE6: I've got a multi-tiered Suckerfish menu using a master UL with id=nav. The menus have anywhere from 9 to 14 tiered UL tags with up to a third level flyout. I've found that when I run your script in IE6 it seems to run rather quickly to loop through all of the UL elements adding the IFRAME, but the browser is unresponsive and my WinXP process meter goes to 100% for another 8-10 seconds and no menus are available. In fact, it locks up the entire browser so nothing can be selected.

I've determined that the script runs quickly and finishes, but IE seems to take a long time to "finish inserting" the IFRAMEs before the user can do anything else. Have you experienced anything like this?

Gravatar Image76. Posted at 12/22/2008 10:10:49 PM by Nirav

H! .

Nice and very useful article.Thanks for saving my day.

I had used this for my webstie.I had few issues still.I am pasting my code below.First thing On hover of menu I need to have diff colors on header and menu.I am nt getting hw 2 do it with ur css.Secondly In opera I am getting White background in menu and submenu,also hover to header of menu didnt work properly.Please help me out this.I hd nt changed js file m using as it is.

#nav, #nav ul { /* Header style*/

float: left;

width: 580px;

list-style: none;

line-height: 2.0;

background: #142942;

font-weight: bold;

padding: 0;

border: solid #FFF;

border-width: 0px 0;

margin: 0 0 0.1em 0;

}

#nav a { /* Text on Header*/

display: block;

width: 14em;

width: 6em;

color: White;

text-decoration: none;

font-weight:bold;

padding: 0.25em 2em;

margin-left:.2em;

}

#nav a.header

{

border-right: 1px solid white; /*right divider between tabs*/

}

#nav a.sub{

background: url(/images/arrow-right.gif) center right no-repeat; /* Image for red-Arrow*/

}

#nav li {

float: left;

padding: 0;

width: 100px;

}

#nav li ul {

position: absolute;

left: -999em;

height: auto;

width: 16.6em;

width: 20.0em;

padding:0;

font-size: 12px;

border: 1px solid #142942;

margin: 0;

background: #b9d1ed;

/* opacity: .95;

*/

}

#nav li li {

padding-right: 0em;

width: 20.0em;

border: 1px solid #000;

}

#nav li ul a {

width: 16em;

width: 13.5em;

color:black;

}

#nav li ul ul {

margin: -30px 0 0 14em;

margin: -30px 0 0 16.95em;

}

#nav li:hover ul ul, #nav li:hover ul ul ul{

left: -999em;

}

#nav li.sfhover ul ul, #nav li.sfhover ul ul ul

{

left:-999em;

}

#nav li:hover ul, #nav li li:hover ul, #nav li li li:hover ul {

left: auto;

}

#nav li.sfhover ul, #nav li li.sfhover ul ,#nav li li li.sfhover ul {

left: auto;

}

#nav li:hover, #nav li.sfhover{

background: #142942;

}

/* Support for the "iehover-fix.js" */

ul.nav iframe {

position: absolute;

/* account for the border */

left: -0.25em;

top: -0.25em;

z-index: -1;

filter: progid:DXImageTransform.Microsoft.Alpha(style=0,opacity=0);

}

* html ul.nav li { z-index: 201; }

Gravatar Image78. Posted at 2/3/2009 11:56:18 AM by Tanny O'Haley

Hi Phil,

I looked at the post about the problem you're having and the problem is in the HTML. The code I've provided works with HTML formatted specifically for Suckerfish drop downs. The code will not work with tables. If you change the code to use nested unordered lists, then I'm sure that the menus will work correctly in IE6 and below with dropdown lists.

What the code does is place an absolutely positioned IFRAME element within the UL element and sizes it so that it is the same size as the UL. The IFRAME element will appear over the windowed SELECT element in IE. IE 7 does not have this problem.

Tanny O'Haley

Gravatar Image79. Posted at 3/30/2009 2:19:14 AM by Lê Trung Thu

Thanks you, this is very usefull. You just get me out of the trouble :)

Gravatar Image80. Posted at 3/10/2010 4:32:52 AM by Rana Bhavna

It works quite well but I'm curious to know if there are other possible solutions...

You see there is another select in the top right hand corner of my page and it flickers on and off whenever I get near the menu (evidently). I find it annoying. Is there a way to prevent that effect (hiding one specific select ONLY on mouseover) to be applied to all selects?

Add a comment

Discussion for this entry is now closed.