Why do I need to do $(document.body) to extend doc

2019-07-06 21:32发布

问题:

So after attempting to get my app working on the latest IE, it turns out IE doesn't like the following code:

document.body.getElement('.className');

Firefox and Chrome responded okay, but document.body on IE had none of the Mootools Element methods.

After looking at the documentation, some of the examples wrapped document.body in $() to expose it to the Mootools methods.

Just wanted to know the reason why it works fine in FireFox/Chrome, but not automatically in IE?

回答1:

This is because of the way IE exposes (or, er, does not) the Element prototype for extending. In proper browsers, document.body - and everything else that is a part of the DOM and is derived from Element - inherits methods attached to the Element.prototype

In old IE, this does not happen (it inherits from the built-in proto but it's read only-ish). See any topic on why - eg. Is there really no way to expose the prototype of a html element in IE (<8)?

In short, it's DOM. it's not ECMA spec. they did not do it. they do so now (fully since IE9)

MooTools - being prototypical - gets around that by extending elements that it accesses manually. It does so via the $ or the element constructor or Slick (when it first encounters an element).

In IE, the extend will not only setup element storage/uid, it will copy a reference to expando properties from the Element.prototype onto the element object itself.

so, if you did:

$(document.body);
document.body.addClass('bar').adopt(new Element('div')); 

this will work. You only need to extend it once, then all methods are copied onto the actual object.

in the future, mootools will not be prototypical but wrapped (like jquery) so any element access will be through a $ type function.

see https://github.com/mootools/mootools-core/blob/master/Source/Element/Element.js#L268-275