My JavaScript book is out! Don't miss the opportunity to upgrade your beginner or average dev skills.

Friday, March 20, 2015

Bringing Custom Elements to IE8

Update
The video of the event that brought Custom Elements down to IE8 and explain the Custom Elements role on the Web is online!


While preparing my talk, slides, and demos for last Wednesday Frontend.fi event I've decided to rethink what was truly needed in order to make my Custom Elements polyfill compatible with IE8 too.

Brief history about my polyfill

When I've first written document.registerElement polyfill I had different targets in mind: everything on mobile that was not covered by Polymer and X-Tag webcomponents.js polyfill should have worked as well.
I was working some R&D project at Twitter by that time and the idea of having Custom Elements for Android 2, Blackberry, Windows Phone 7, and all other OSs ignored by the Google library, which targets mostly modern Desktop browsers and it aims to cover the the whole WebComponents family instead of just Custom Elements, was truly tempting.
The challenge was to find the minimum amount of hacks needed to make it work, and the result was a 2.5 KB minzipped output VS around 30 KB minzipped for the library used in the core of both Polymer and X-Tag.
To be honest, those 17+ KB via CDN aren't a big deal, but the incompatibility with not so old platforms is ... so I'd call it win/win in size and portability.

Why IE8 now

Once I've developed and tested Custom Elements for all these platforms, the shadow of IE8 kept bugging me. I was sure nobody cared, I strongly believed it was somehow impossible or it would have required a huge effort for zero profit.
Truth is, same way I've found the minimum amount of hacks needed to make it work in all those platforms, and please bear in mind that even if disappearing Android 2 phones are still selling, I could have simply ignored Mutation Events and Mutation Observer. I had this little monolithic piece of crap that was simply working everywhere, and I could have hooked IE8 in there with ease.
When you have a test suite to develop against, when you do TDD for real, things are way easier to implement and it took "only one extra day of work" to actually see the green light and also create a working demo that integrates the most common thing ever on the web: a map that points at your business.

The untold story of that map is that it will never show a white space instead of a map as <google-map> custom tag would: it works even in browsers that have no JavaScript support at all! ... however, this is another story that I've also better explained in Helsinki.

I put that extra day of work in quotes because I've been hearing the "cool story bro" on how much effort would take to implement something here or there, and I believe most of the time developers didn't even try. I am an old dev with a lot of IE4+ background so maybe it was easier for me ... but trust me, I had to find out few new and undocumented IE8 specific hacks in order to make it work and even if not perfect, it just bloody works!
There are inevitably caveats for IE8, but if you are targeting this platform you are already taking extra precautions so nothing new for you.
Finally, whenever my Frontend.fi talk will be live I'll update this post so you can see the presentation that brought this little "miracle" to life.

What kind of sorcery is this?

The exact sequence of polyfills needed to make this work, a sequence absolutely unobtrusive for all browsers but IE8, is represented in this file: change the order and it won't work so stick with that in any major template you have and you'll be good to go!

4 comments:

Marcus said...

Great post! I'm starting a new project and wanted to use Web Components, but when I found out IE8 was not supported I thought I was going to have to scrap that idea. So I'm ecstatic to find your polyfill! One question I do have is can your polyfill be used with Polymer? I prefer Polymer's declarative style over X-Tags, plus I think Polymer would be easier for other members of my team learn.

Andrea Giammarchi said...

I don't use Polymer so I don't know the answer. You should probably ask them how hooked to webcomponents.js is their abstraction on top.

That said, I don't think it's difficult to replicate similar abstraction on top of Custom Elements only.

Unknown said...

Is this available on NPM?

Andrea Giammarchi said...

if you don't care about IE8, since the order of things matters and not everything should be loaded everywhere, you can load both `dom4` and `document-register-element` via npm too.