Cleaning House after Internet Explorer

Share this article

The new year started great for front-end development. On January 12th, Microsoft ended support for old versions of Internet Explorer. Millions of developers worldwide rejoiced at the news. The last vestiges of the Browser Wars that defined the beginning of the new millenium were finally put to rest.

For at least the last decade, the various versions of Internet Explorer have been the bane of web designers and front-end developers everywhere. The rise of Firefox, Opera and later Chrome showed the world that the web can be so much greater, faster and more secure. Yet, in fear of breaking the web for those who didn’t (or couldn’t) move away from Internet Explorer, we were forced to jump through hoops and bend over backwards to cater to the quirks of these legacy browsers. There is a well known pie chart image (the oldest appearance I could find was in 2007 on that showcases the feelings of the community:

Time Breakdown of Modern Web Design

Fortunately things are a lot better now. We only have to deal with the last incarnation of the Trident engine, namely Internet Explorer 11, which is already a solid modern browser on par with its competition. It is thus the time to clean house and throw away the deprecated tools, processes and techniques. Out with the old…

No More Browser Hacks

The first weapon we had in our arsenal was the browser hacks. A hack is a seemingly incorrect declaration that exploits some parsing errors in the rendering engine. It is used to overwrite the standard declaration with a value that will make the layout look and function properly on that specific browser. There were hacks that targeted single versions of Internet Explorer, while others covered multiple versions. A further classification can be made depending on the format of the hack:

  • Selector hacks: These hacks usually are used to exclude old versions of IE that don’t understand the new syntax.
  • Property/value or attribute hacks: These are the original hacks — exploiting holes in the parsing engine to target specific old versions.
  • Media query hacks: They are used to target/filter various versions of browsers (not only Internet Explorer) based on the support of the syntax for @media declarations.
  • JavaScript hacks: They are used for “browser sniffing”, detecting specific versions of Internet Explorer based on various features supported by the JavaScript engine.

The use of hacks was both complicated and frustrating. Sometimes you had to cascade several hacks one after another, as some parsing errors (that allowed the existence of the hack) were fixed in following versions without removing the rendering problem that required the hack in the first place. Let’s see a few examples of such hacks, restricted to the three versions recently retired:

/*========== Selector Hacks ==========*/

/* Internet Explorer 10+ */
_:-ms-input-placeholder, :root .selector {}

/* Everything except Internet Explorer 9 and lower */
en'] .selector 

/*========== Property/Value Hacks ==========*/

/* Internet Explorer 6-8 */
.selector { property: value\9; }
.selector { property/*\**/: value\9; }

/*========== Media Query Hacks ==========*/

/* Internet Explorer 8 */
@media \0screen {}

/* Internet Explorer 10+ */
@media screen and (-ms-high-contrast: active), (-ms-high-contrast: none) {}

/*========== JavaScript Hacks ==========*/

/* Internet Explorer 6-10 */
var isIE = !!window.ActiveXObject;

/* Internet Explorer 8-10 */
var isIE = document.all && document.querySelector;

For a more comprehensive list of hacks to remove from your code, visit Browserhacks.

Bye Bye Conditional Comments

As we have seen above, the use of CSS hacks is messy, prone to malfunction and (for those of you who are obsessive about their code) making the stylesheet fail validation. Things had escalated to the point where, in November 2005, the guys at Microsoft stepped in and made a call to action for the demise of CSS hacks, urging developers to use conditional comments instead.

Initially conditional comments were used to load extra stylesheets for certain versions of Internet Explorer. At that time the code differences between standard-compliant browsers and Internet Explorer were large enough to make the practice a valid one. When HTML5 became a reality, this was also used to load polyfills that provided the missing support for the new features (we’ll touch this topic later in the article). While this practice was mainly used to target code for IE6–7, you might still encounter it in some legacy code. Let’s have a look at some code samples:

Conditional Comments Used to Load Extra Stylesheets

<!--[if lte IE 8]><link rel="stylesheet" href="lte-ie-8.css"><![endif]-->
<!--[if lte IE 7]><link rel="stylesheet" href="lte-ie-7.css"><![endif]-->
<!--[if lte IE 6]><link rel="stylesheet" href="lte-ie-6.css"><![endif]-->

Conditional Comments Used to Load JavaScript Polyfills

(code excerpt from the default Bootstrap starting template)

<!--[if lt IE 9]>
  <script src=""></script>
  <script src=""></script>

The main issue with this approach was that each version of Internet Explorer targeted this way made extra HTTP requests. The developers were forced to search for approaches that offered higher performance. The result was to deploy conditional comments to add extra classes to the <html> tag. This practice was a lot more popular, being used, among others, by the HTML5 Boilerplate framework. By that time Internet Explorer 6 could either be ignored or treated using graceful degradation, while the differences between the more modern versions (IE7–9) and their competition (Firefox, Chrome, Safari and Opera) were small enough not to warrant entire extra stylesheets. The few minor tweaks could be achieved due to the extra specificity provided by classes added to the <html> tag. This is the example most likely to be encountered today, as illustrated in the examples below:

Conditional Comments Used to Add Extra Classes to The <html> Tag

<!--[if IE 7]>   <html class="ie7"><![endif]-->
<!--[if IE 8]>   <html class="ie8"><![endif]-->
<!--[if IE 9]>   <html class="ie9"><![endif]-->
<!--[if gt IE 9]><!--><html><!--<![endif]-->

CSS Code Using the Extra Classes

.foo { color: black; }
.ie7 .foo { color: blue; } /* IE7 */
.ie8 .foo { color: green; } /* IE8 */
.ie9 .foo { color: red; } /* IE9 */

The launch of Internet Explorer 10 brought the end of conditional comments, as they were not supported anymore in this version. Feature detection (using Modernizr) was the new standard for progressive enhancement or graceful degradation. Only websites or frameworks that needed backward compatibility still used them, mostly to load polyfills, as we could see in the examples above.

Slim Down Your JavaScript Libraries

We have seen above how the lack of support for modern features was often plugged with polyfills using conditional comments. If your application or website is using such scripts, you can safely get rid of them now. But not every situation is as clear as this one. Let’s expand this topic a bit further, with a few relevant examples.

It is a known fact that jQuery is the most used JavaScript library on the web, with more than 53 million websites on the record (according to jQuery was born from the need to level the playing field between browsers by covering the differences in feature support. Over time, the legacy support had reached such a level that in 2013 jQuery was split in two branches: 1.x.x maintained support for old versions of Internet Explorer, while 2.x.x dropped all the features related to Internet Explorer 6–8. The latest update on January 8, 2016, has been announced as the last one before the move to 3.x.x. Therefore you could either stay with the 1.x.x branch and jump directly to 3.x.x, or switch now to 2.x.x and get as much efficiency as possible at the moment.

There is one more thing to consider. Internet Explorer 11 and Edge have better integration of native methods (especially for DOM navigation and manipulation) that in the past required jQuery to function properly across browsers. In some cases, when the scripts can be refactored properly, it might be even possible to remove jQuery completely and make use only of plain JavaScript.

Another example is Modernizr – which we already mentioned earlier. The way this library works is to perform a set of tests for supported features and mark the result as a class attached to the <html> element. With a little bit of research (mainly on we can disable the tests designed to isolate features not supported in older Internet Explorer versions. If your page is making use only of mainstream features, with broad browser support, you might not need to load Modernizr at all.

The same approach is valid for any other polyfill script you might use. Check if the features it patches are supported in the modern browsers and get rid of it if it’s not needed anymore.

Remove Proprietary CSS Values

Once upon a time, Internet Explorer was the only browser capable of doing amazing effects in the page, due to a proprietary piece of technology called ActiveX Filters. Developers were able to do static effects (e.g. opacity), create gradient backgrounds, rotate and transform elements or do transition effects when loading a new page. While CSS3 offered standard alternatives to most these effects, ActiveX filters remained for a long time the only option available for Internet Explorer. It is not uncommon to still encounter these declarations, especially in hand-coded stylesheets. Therefore, be on the lookout for statements like the ones below, you do not need these anymore:

.foo {
  /* Internet Explorer 4.0 syntax */

  /* Internet Explorer 5.5 syntax */
  filter: progid:DXImageTransform.Microsoft.filtername(sProperties)";

  /* Internet Explorer 8 syntax */
  -ms-filter: 'progid:DXImageTransform.Microsoft.filtername(sProperties)'";

If your process of writing CSS includes the use of an auto-prefixer, then you need not worry about this topic. A good plugin will stay up to date to the level of support present in the modern browsers.

Get Rid of Obsolete Meta Tags

Internet Explorer 8 introduced a new software mechanism, called “Compatibility View”, designed to alter the rendering mode in such a way that older websites will still render properly. This was achieved with the help of a X-UA-Compatible declaration, either as a <meta /> element or through the HTTP headers. At one point this approach was even recommended inside the Google Web Toolkit. Today, now that only Internet Explorer 11 and Microsoft Edge are supported, these tags became obsolete. We can see here an example of what you have to look for:

<meta http-equiv="X-UA-Compatible" content="IE=9">
<meta http-equiv="X-UA-Compatible" content="IE=Edge" />

Clean Up Your Custom Web Fonts

For a long time web designers were limited in their font choice. People put together numerous “web safe” font lists from the system fonts available on various operating systems (e.g. CSS Font Stack). With the introduction of the @font-face rule, everyone is now able to load custom fonts, either directly or from services like Google Web Fonts and TypeKit. Let’s not forget the plethora of icon fonts that gathered great popularity. Chris Coyier has a comprehensive entry on using @font-face in case you need to refresh your memory.

With the end of support for Internet Explorer 9 we can now safely ditch the .eot (and even .ttf) font files, together with their related CSS entries. This is especially useful if you need to manage an icon font, as the update process is greatly simplified (although more and more people recommend using SVG icons instead of an icon font).

Simplify Your Cross-Browser Testing Process

Cross-browser testing and debugging has always been a tedious process, especially when Internet Explorer compatibility was required. Over the time various solutions were found: from applications like IETester or Multiple IE. Some people used virtual machines but the main problem was that you still needed a valid OS license for each instance. Then the guys at Microsoft stepped in and offered “time-bombed” virtual machines with specific combinations of Windows and Internet Explorer. All one had to do was to choose their favorite virtualization system from the available list (currently containing Virtual Box, VMWare, Vagrant and HyperV), download the desired virtual machine image, fire it up and start working.

All these options are still available today, if you feel nostalgic and want to explain to the new kids how you had to debug your code on Internet Explorer 6 without Web Developer tools. There should be no more reason though to make them part of the normal development process.


Debugging code for legacy Internet Explorer versions used to be a complicated (and sometimes frustrating) process. We memorized the most common browser bugs and their counters. Position is Everything and Quirks Mode used to be at the top of our bookmark list. Fortunately, as the web continues its evolution, we are able to leave those days behind us and discard the obsolete tools and practices. Now it’s the time for a thorough house cleaning.

Adrian SanduAdrian Sandu
View Author

Adrian is a UX Developer, creator, and speaker living in Iasi, Romania. He believes happiness is the true measure of success and he wants to help other developers achieve their dreams. In the off time, he loves playing video games and tinker with custom PC builds.

browser compatibilitybrowser optimizationbrowser supportie6ie7ie8internet exploreroldiepatrickc
Share this article
Read Next
Get the freshest news and resources for developers, designers and digital creators in your inbox each week
Loading form