Enumeration and Object Oriented JavaScript

 

*AnimTree
*Tabs
*GlideMenus
*DragLib

Who is this Article For?

This article is intended for JavaScript library authors, language implementors (IE, Mozilla), and language contributors.

Anyone who reads this article thoroughly will gain a deeper understanding of how enumeration works in JavaScript, and how to deal with language complications and cross browser issues.

For the TG1 group (who is writing ES4), my recommended changes from ES3 to are notated as struck out and highlighted. My recommendations reflect what I think should change from ECMAScript rev 3 to ECMAScript rev 4.

Synopsis

This article is about the for in statement, how it is broken in IE, and how to work around the problem.

Prototype Chain

Constructor chaining affects the prototype chain, which affects enumeration.

Borrowing Properties

Borrowing properties is taking properties of a supplier object and using them on a receiver object. This is usually done using a for in loop. Some examples demonsotrate complications with the prototype chain and the problems caused by an IE bug that I call the JScript DontEnum bug.

Borrowing properties is related to constructor chaining. Both can be used as a solution to the problem of adding new behavior to a class. The two are used sometimes interchangeably, and sometimes together.

Examples

I have included some real world code (YUI) and some examples of my own. Most of the examples are abbreviated and to the point. The goal is to explain JavaScript and programming techniques, which can be used to create a real program. The examples display an understanding how the prototype chain and enumeration come into play in real-world code.

This article is quite long. The top level sections should be read all the way through, with the exception of the explanation of Creating a Subclass. This section doesn't have any dependencies.

You can save paper by printing at a smaller scale (60%), and double sided (if your printer supports that). Or, you can just read it on your computer (I bet you knew that).

Tests

There are many live tests that you can and should run. The tests use eval to run the textContent of the pre element in each example.

The tests show three things:

If a test does not have a browser table, it is because the test is known to pass in every browser. If you encounter such a test that does not pass, please email me.

If there are any false statements, or if you get a different result than what is listed in a browser table, please send an email to me.

Browsers tested:

Many of the examples use String.nl

String.nl = /*@cc_on!@*/"\n"||"\r\n";
Internet Explorer Whitespace Hacks

Internet Explorer handles whitespace incorrectly. This caused several problems with the examples in this article that use innerText and innerHTML with the pre element (other elements could not be supported). The odd line of code above is a workaround.

Each test is inside a pre. The test code is run in a closure to keep the global namespace clean.

(function(){ // Closed test scope.
    // Example test code
})();

There is a small templating system that performs evaluation on supplanted code marked by ${/*code*/}. This was necessary to facilitate white box testing This is viewable in the source of this document. The templating system uses a setInnerHTML function to deal with Internet Explorer's whitespace problem.