How to solve :first-child CSS bug in IE 7

Yesterday, IE 7, once again, pushed me to the brink of going postal. Refusing to give up, I finally managed to find the problem.

Background

I was creating a top menu for a web site I was working on, and it needed some special styling for each first item, i.e. the first LI, and other styling for all others. Since it’s a controlled environment, IE 6 doesn’t need to be supported (Yay!); hence I thought I’d be using some cool CSS to solve it, as opposed to riddling the HTML code with classes.

Let’s look at my (somewhat :-) ) simplified example:

HTML code

<ul>
    <!-- First item is special -->
    <li>
        <a href="/">Start page</a>
    </li>
    <li>
        <a href="/">News</a>
    </li>
    <li>
        <a href="/">Contact</a>
    </li>
</ul>

CSS code

li {
    background: red;
}
li:first-child {
    background: blue;
}

The problem

No matter how I tweaked and changed my code, the :first-child CSS pseudo selector would not work in IE 7. Naturally, Microsoft claims it does support it, and, while going mental, I was trying to figure out whether it was just another crappy implementation that doesn’t work at all, or if there was something weird with my code.

The solution!

After pulling my last beard hair from my face, it dawned upon me! The key was the HTML comment preceding the first LI item, incorrectly interpreted by IE to be the first child element of the UL. In my defense, the HTML comment wasn’t written by me and yes, it could be in another place… :-)

Still, it’s a horrendous bug, and therefore I wanted to warn you! Be very careful about where you put your HTML comments, because the possible results will mess with your mind.

60 Comments

  • #1 Pete B
    February 4th, 2009 at 12:04

    I guess it’s like IE’s jscript engine, which thinks comment nodes and HTML elements are the same thing :(

  • #2 Ole
    February 4th, 2009 at 12:53

    HTML Comments in IE must be set carefully. They can also produce the weird “Duplicate character bug” which is described here:

    http://www.positioniseverything.net/explorer/dup-characters.html

  • #3 kimblim
    February 4th, 2009 at 12:57

    I'm actually not that surprised to see this bug/feature. My best guess would be that IE has to interpret comments as elements for conditional comments to work? Still, I don't think it's a big bug, and it's relatively simple to work around.

    Did you try IE8 to see if it still works in the same way?

  • #4 Morgan Roderick
    February 4th, 2009 at 14:03

    Wow, that's an amazing oversight!

    But, at least it'll be consistent across many future versions, as it'll also be in IE7 compatability mode for many versions to come, unless they decide not to do bug for bug compatability mode ;-)

  • #5 Anders Ringqvist
    February 4th, 2009 at 15:11

    Would not have used the heading "How to solve…" and neither state that I come up with a solution =P There is no solution. IE7 needs to be patched, that is the solution. Moving the HTML comment aint a solution on the problem. There might be cases where there might be a comment there and you can´t do anything about it. There might be times you need a comment there, white-space suppression anyone?

    Just state that there is a problem with the :first-child pseudo-class in IE7 but please don´t say you found a solution, it´s missleading. It´s "sensationsjournalistik" at it´s best.

  • #6 Robert Nyman - author
    February 4th, 2009 at 15:50

    kimblim,

    Yes, it's probably related to conditional comments in some sort of way. I'd still deem it serious, though, in all kinds of CSS code where relations and placement of HTML elements is deciding applied styles.

    Haven't tried IE 8 with it yet.

    Morgan,

    Yes, wonder if their IE 7 mode in future versions will have bug fixes. Probably not, I presume.

    Pete,

    Yeah, most likely.

    Ole,

    Ah, yes, that one is bad too.

    Anders,

    Since it solves the problem for me, and for a majority of other stumbling upon it, I would definitely say it deserves the epithet "How to solve…". With web development in general, help articles and so on, it is about how you as a developer can solve the problem you're facing, extend the web browser to encompass differences etc.

    Of course the core problems in IE has to be fixed, but that is up to Microsoft. So, if you find "How to solve…" as a headline to be "sensational journalism", at best, you haven't seen much of that… :-)

  • #7 Jesse Rodgers
    February 4th, 2009 at 16:37

    I ran into this yesterday! The swearing fit both before it was figured out and after was pretty fun… It is amazing/scary how you have to think like a browser to figure out odd little things like this. Thanks for posting this!

    I am happily on a "no IE6 supported" project as well… feels good. ;)

  • #8 Christopher Papastef
    February 4th, 2009 at 20:38

    So very typical of MS. To implement a feature almost all the way…

  • #9 Nick Fitzsimons
    February 4th, 2009 at 21:56

    This problem of IE 7 treating comments as elements for the purpose of applying CSS came up on the css-discuss mailing list when the browser was still in beta. As Ingo Chao pointed out, comments can even be made to react to <code>:hover</code> :-)

  • #10 mdmadph
    February 4th, 2009 at 22:51

    @Christopher Papastefanou

    Wouldn't you say that this time they implemented it, but then went too far? They do that just about as often. :(

  • #11 Cerebral
    February 5th, 2009 at 1:07

    I knew it directly when I saw your code :p

    You need to meet this once to be able to avoid it forever: like mentionned before, HTML comments in IE are dangerous. Another place to avoid them is before the doctype, it would jump into Quirks Mode.

  • #12 Robert Nyman - author
    February 5th, 2009 at 10:29

    Jesse,

    Yes, it's all about getting into the mind of IE. :-)

    And congrats for no IE 6 for you!

    Christopher, mdmadph,

    Yeah, not all the way, or too much. Still, jsut plain wrong…

    Nick,

    Great, thanks for the link!

    Cerebral,

    Yeah, me too. I had an enormous file, but when I broke it down to the above, I saw it too. :-)

  • #13 Chris
    February 5th, 2009 at 10:49

    Some versions of IE are also known for being very nitpicking with whitespaces. And having a comment before doctype triggers quirks mode. So the fact that a comment counts as an element is stupid but fits in the scheme…

  • #14 Olly Hodgson
    February 5th, 2009 at 15:33

    Be very careful about where you put your HTML comments, because the possible results will mess with your mind.

    This is good advice when working with IE6, too. Any comment or other hidden element (hidden inputs for example) can trigger the duplicated characters bug.

    Of course, sometimes you don't need any hidden elements to trigger it. You just need IE6 to fail miserably at adding up. None of the usual fixes worked, hence I nearly went postal yesterday. In the end some voodoo magic (involving the magic number 3 and overflow: hidden; on an element several branches up the tree) made the problem go away. GAAAH!

  • #15 chovy
    February 5th, 2009 at 18:52

    The comment IS the first child of UL.

    Coment tags are still part of the DOM, simply because they are invisible in the rendered view of the browser doesn't mean they aren't there.

    I fail to see how this is "incorrectly interpreted by IE".

  • #16 Ingo Chao
    February 5th, 2009 at 19:28
  • #17 Nick Fitzsimons
    February 5th, 2009 at 23:49

    @chovy: Comments might be part of the DOM, but that is a different specification to CSS, and the terms "first child" has different meanings in the two specifications.

    CSS 2.1 states that the adjacent sibling selectors should ignore <q cite="http://www.w3.org/TR/CSS21/selector.html#adjacent-selectors">non-element nodes (such as text nodes and comments)</q>.

    Although :first-child is a pseudo-class rather than an adjacent sibling selector, its definition also refers explicitly to elements and thus also excludes comments.

  • #18 Robert Nyman - author
    February 6th, 2009 at 10:13

    Chris,

    Yes, whitespace can cause enormous problems, and don't even think about preceding the doctype with anything.

    Olly,

    Good to see that we share the potential of going postal. :-)

    chovy,

    Nick's comments explains it. Also, I'd like to add that, opposed to, for instance, hidden form elements, HTML comments have no rendering, no styling, no script access, no values posted.

    Hence, it's rather just page information than page content, in my mind, and should therefore not be treated like a child element.

    Ingo,

    Thanks for sharing!

    Nick,

    You took the words right out of my mouth. :-)

  • #19 :first-child bug no IE7 » Pinceladas da Web – XHTML, CSS, JavaScript e WebStandards
    February 12th, 2009 at 12:00

    [...] dia que passa fico conhecendo mais um bug novo no Internet Explorer. Já ouviram falar do bug de first-child no IE7? O curioso problema que ocorre é o seguinte. Observem a seguinte marcação [...]

  • #20 Richard Hamilton
    February 18th, 2009 at 1:12

    Thank you very much for posting this. I had an exactly similar problem where the class was correctly applied in Firefox but applied one level further down the DOM in IE7. I concluded that it was a bug and searched accordingly. Your article immediately cleared up the problem.

    Thank you.

    Regards

    Richard

  • #21 Robert Nyman - author
    February 18th, 2009 at 1:48

    Richard,

    Glad that it was of help to you!

  • #22 ??????? » [Web] ????
    March 3rd, 2009 at 7:18

    [...] How to solve :first-child CSS bug in IE 7 [...]

  • #23 Martin
    June 17th, 2009 at 22:04

    Funny to read that some people think that it's a bug in IE7 :)

    The only situation when the first-child selector does not work is when you forget to use a doctype. Just use valid (x)HTML-code and there's no problem at all.

  • #24 Robert Nyman - author
    June 17th, 2009 at 23:41

    Martin,

    It is a bug in IE 7. Naturally, this has been tested with strict HTML and XHTML doctypes, and it, in my mind, incorrectly parses the HTML comment as the first-child. Nothing that is invisible should be affected by presentation code, i.e. CSS.

  • #25 Martin
    June 18th, 2009 at 0:23

    I'm sorry, in my hurry I read your post the wrong way. I thought you said that IE7 does not support :first-child, but it was about the HTML-comment that confuses IE7. That's indeed strange behavior, good to know ;) Thanks.

  • #26 Robert Nyman - author
    June 18th, 2009 at 0:36

    Martin,

    No worries. :-)

  • #27 Nikita Sumeiko
    September 23rd, 2009 at 18:30

    I had the same problem in one of my html sliced documents.

    I have spent a lot of time on looking why IE7 gives me this bugs:

    – ignores auto margins;

    – first-class selectors.

    I've checked the document many times, every class and every element, but it was clear and the W3 Validator said the document is valid and he marked it with a green color as usually.

    Than I decided to remove commented text, which was placed in my html document before this line:

    <code><!DOCTYPE html…</code>

    This text just include document information, such as:

    <cite><!– filename: index.html; author: author's name… –></cite>

    When I removed this comment, all the IE7 bugs disappeared!

    My mistake was here: I forgot, that comments marked <– … –> is only html document comments and they should be placed only inside <html> tag.

  • #28 Stefan
    January 28th, 2010 at 18:50

    Robert, you saved my beard. Thank you!!!

  • #29 Robert Nyman - author
    January 28th, 2010 at 18:53

    Stefan,

    Great!

  • #30 Abdullah
    February 21st, 2010 at 13:07

    Man, I wanna kiss you :D :D . I would have probably wasted my whole day to figure out what the hell is happening, but thanks God I found your post. You saved my hours. Thanks a lot :)

  • #31 Robert Nyman - author
    February 21st, 2010 at 20:09

    Abdullah,

    Great to hear that it helped out!

  • #32 Martin
    April 2nd, 2010 at 0:51

    Thanks for this post. Only took me five minutes to figure out what the heck was up. Without the post, I probably would have ended up banging my head against the wall.

  • #33 Robert Nyman - author
    April 5th, 2010 at 10:56

    Martin,

    You're welcome!

  • #34 abcd
    April 27th, 2010 at 8:27

    Untitled Document

    li:first-child{color: green;}

    li:last-child{color: red;}

    li:target{color:green;}

    li:last-child:hover{color: orange;}

    a:hover{color: yellow;}

    First

    Second

    Third

    <!– last item is special –>

    Last

    check this code there is no any comments in this code bur still last child and first child is not working ie 7

  • #35 abcd
    April 27th, 2010 at 8:49

    <html xmlns="http://www.w3.org/1999/xhtml"&gt;

    <head>

    <meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1" />

    <title>Untitled Document</title>

    <style type="text/css">

    li:first-child{color: green;}

    li:last-child{color: red;}

    li:target{color:green;}

    li:last-child:hover{color: orange;}

    a:hover{color: yellow;}

    </style>

    </head>

    <body>

    First

    Second

    Third

    <li title="last">Last

    </body>

    </html>

    check this code there is no any comments in this code bur still last child and first child is not working ie 7

  • #36 Robert Nyman - author
    April 27th, 2010 at 11:55

    abcd,

    The CSS pseudo-properties <code>:last-child</code> and <code>:target</code> aren't supported by IE7, but <code>:first-child</code> really should work for you in that example. Try stripping out all the other CSS and see if it works.

  • #37 abcd
    April 29th, 2010 at 15:39

    yes i checked it's not working in IE7

  • #38 abcd
    April 29th, 2010 at 15:40

    is there any idea other than first child and last child

  • #39 Robert Nyman - author
    April 29th, 2010 at 15:42

    abcd,

    Nope, that is all I can think of.

  • #40 Josh Salverda
    June 29th, 2010 at 8:33

    @abcd

    I know your post is a couple months old but your code probably isn't working because the first child has an <a> tag in there. You have to explicitly set the color on <a> tags so your css would have to be something like: li:first-child a { color: green; }

    :)

  • #41 gexplorer
    July 12th, 2010 at 18:19

    I've tested the code of the example and it doesn't work on IE7. Can you test it again now? The version of the IE7 might be different (7.0.5730.13)

  • #42 Kris
    September 21st, 2010 at 1:23

    How can I target the first paragraph in a div when a different tag precedes the first paragraph? For example:

    <code>

    <div>

    <img src="" />

    I want to target this paragraph.

    Second paragraph

    </div>

    </code>

    If I remove the image tag, div p:first-child works, but with the tag there, it seems to find the image as the first child.

  • #43 Robert Nyman - author
    September 22nd, 2010 at 1:07

    gexplorer,

    Not sure what version it was, but it might have been fixe din a minor update then.

    Kris,

    You could do it with a CSS3 selector, but they are only supported in the latest versions of various web browsers.

  • #44 dravidian7
    October 22nd, 2010 at 17:49

    i can’t believe that would cause that, but it works! thanks. Ie8 has same problem.

  • #45 Robert Nyman - author
    October 26th, 2010 at 10:08

    dravidian7,

    Glad it helped!

  • #46 Angel D.
    December 29th, 2010 at 23:44

    Thanks to IE I now have not one but five imaginary friends. They are all hot elves FYI. Madness isn’t as bad as people make it sound i guess….

    This post saved me (*us –> cant forget the hot elves) today. Thanx!

  • #47 Robert Nyman - author
    December 30th, 2010 at 20:55

    Angel,

    Ha ha! :-)
    Whatever solves the problem right? :-)

  • #48 Web Design Scotland
    July 15th, 2011 at 16:06

    Thanks, solved my problem 2 years later!

  • #49 Robert Nyman - author
    July 15th, 2011 at 19:30

    Web Design Scotland,

    Glad it was of use. :-)

  • #50 alexandria
    October 25th, 2011 at 2:56

    hi,
    I was near to give up, thanks for this very useful post, you saved me !

    regards

  • #51 Robert Nyman - author
    October 25th, 2011 at 10:38

    alexandria,

    Glad it helped!

  • #52 Steven
    November 24th, 2011 at 15:31

    Thanks for that… would never have thought of that…

  • #53 Robert Nyman - author
    November 25th, 2011 at 9:55

    Steven,

    Glad it was of help!

  • #54 MoiKano
    November 28th, 2011 at 16:24

    Hi,

    if needed, it is possible to bypass this bug using conditional comment:

    it isn’t so pretty, but functional :)

  • #55 MoiKano
    November 28th, 2011 at 16:28

    … sorry, I didn’t escape the html :P

    this was the example:
    <!--[if !IE]> this is a comment <![endif]-->

    :)

  • #56 Robert Nyman - author
    November 28th, 2011 at 20:52

    MoiKano,

    Ha, cool idea!

  • #57 ArnaudBan
    April 4th, 2012 at 17:04

    Thank you very mutch ! Perfect !
    I would have never find it myself…

  • #58 Robert Nyman - author
    April 4th, 2012 at 18:34

    ArnaudBan,

    Glad to help!

  • #59 Dave
    May 1st, 2012 at 1:29

    Hi Robert,

    I realize this is an older post, but just wanted to mention that I was working on a project using some of the Twitter Bootstrap framework, and was having an issue with a “first-child” row not lining up with some other content in ie7; Did a search for first-child + ie7 and your article came up.

    The problem was indeed a comment on the proceeding closing div, and removing it solved the issue.

    As a hobbyist coder, I would have never figured it out on my own.

    A big thanks for posting this.

  • #60 Robert Nyman - author
    May 8th, 2012 at 19:20

    Dave,

    Good to hear, and glad it was helpful!

Write a comment

Share your thoughts:

HTML: You can use these tags: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <strike> <strong> . If you want to display code examples, please remember to write &lt; for < and &gt; for >.

Comment preview