HTML5 block-level link bug in IE7+

Warning This article was written over six months ago, and may contain outdated information.

HTML5 allows the use of block elements inside the a tag, which was not permitted in HTML4. This means that you can wrap a link around whole sections of markup, making all of the child elements of the a become the link. You use it like so:

<a href="http://example.com">
  <div>
    <h3>I'm an example</h3>
  </div>
</a>

You can begin to use this straight away, as every browser supports it — although you must be wary of one rather glaring bug in Internet Explorer.

The bug occurs if you try to nest other a elements inside the block-level one, as shown in this example markup:

<a href="http://example.com">
  <div>
    <h3><a href="http://example.com">I'm an example</a></h3>
  </div>
</a>

With this markup IE7 fails to render some elements, and IE8 and IE9 create an empty, ‘phantom’ element. I’ll show you what I mean, starting with the way this markup should render; on the left is the HTML markup as it displays in your browser, and on the right I’ve placed a screenshot from Firefox to act as a comparison.

And now see how they appear in IE7 (left) and IE8 & IE9 (right):

As you can see, in IE7 the h3 element loses its background color and margin, and in IE8 & IE9 there’s an empty box above my markup; this is the ‘phantom’ element, which is inheriting the border from the div element, and the margin-bottom from the h3. Were I to add margin-top (or further properties that affect the box model) to my markup, they would also show up here.

Strangely, this bug doesn’t seem to occur in IE6.

The fix is quite simple: don’t nest a elements. I only did it as I needed an element to create a particular style effect, but it can be done just as easily with a span. I tried a number of other approaches but this seemed to be the only one that worked.

Update: As has been pointed out in the comments, nesting a elements is in fact prohibited by the HTML5 specification. I’ll leave this post here for the other people like me who weren’t aware of that.

8 comments on
“HTML5 block-level link bug in IE7+”

  1. Nice article, but the problem is bigger than just IE. All browsers seem to crash on nested links. And of course, they all seem to crash differently :)

    Wrote something about it a couple of weeks ago, with images of dom results: http://www.onderhond.com/blog/work/nesting-links-how-to-make-your-browser-v

  2. Thanks Niels. You’re right, the DOM is a bit mangled; it renders the elements fine visually, but the link isn’t block-level. My advice concurs with yours: don’t nest links.

  3. Just because HTML5 now grants us the ‘ok” to include block-level elements within an inline element like the a tag, it doesn’t necessarily mean one should do so. It seems that it was more of a move to satisfy the current blogging trend of ‘everyone’s putting a’s around h1-h6’s, so let’s keep in line with our backwards-compatibility approach’. Curious if displaying the outside link as block or inline-block via CSS would help… (?)

  4. Hi Justin,

    I actually like these block-level links, I can think of many occasions where they’re useful, and I think that it was a good move of the HTML5WG to formalise this convention.

    As to your question, I tried setting the outside link to inline-block, block, even inline, but nothing had any effect.

  5. Hi Peter, Perhaps I was/am too caught up with dreams of XHTML 2. Ha!, but, in all seriousness, I agree, block-level links do come in handy from time to time. Thank-you for all your exceptional write-ups, I visit month to month, as you always address some of the most relevant and useful topics in web design/development. Cheers! /Justin

  6. Thanks Justin, that’s really kind of you to say so.

  7. Nice to hear, that all browsers support it.

    But I don’t understand why you try to nest <a>. It’s also not allowed by the HTML5 spec:
    The a element may be wrapped around entire paragraphs, lists, tables, and so forth, even entire sections, so long as there is no interactive content within (e.g. buttons or other links). This example shows how this can be used to make an entire advertising block into a link:

  8. You’re absolutely right, Fabian, I hadn’t seen that. I’ve updated the post accordingly.