IE Bug (window === top) === false

In IE.

window === top; // false
window === window.window // false
window == top; // true
window == window.window // true

In FF3.6 & Chrome stable this doesn't happen.

In IE typeof, .toString, Object.prototype.toString.call all return the same for both top & window

This is related to this.

Can anyone tell me why IE can't do strict equivelance?

Note that circular reference doesn't cause issues in both IE & Chrome.

o = {};
o.o = o;
o === o.o; // true

Turns out

window.window === window.top; // true
window.window === window.self; // true

So it's an issue with getting window on it's own.

for (var i in window) {
    if (window.window[i] !== window[i]) {
        console.log(i); // external, frames, clipboardData
    }
}

[Edit]

This is just getting stupid now:

 window.frames === window.frames; // false
 window.frames == window.frames; // false
 window.external == window.external; // true
 window.external === window.external; // false
 window.clipboardData === window.clipboardData; // false
 window.clipboardData == window.clipboardData; // false

[Further edit]

turns out that window.frames holds a pointer to the ie debugger. So having the debugger open changes the window object. I have to do some more testing.

window.frames.location === window.frames.location; // false
window.frames.location == window.frames.location; // true
window.frames.event.boundElements == window.frames.event.boundElements; // false

Not to mention that window.external just does not play nicely

>>for (var i in window.external) alert(i);
"Object doesn't support this action"

Answers:

Answer

This isn't exactly a bug: host objects can do whatever they like, and the window object is a particularly complicated beast, serving the dual purposes of being the object that represents the browser window and also being an alias for the global object. I'd chalk this one up as a weirdness and avoid using the strict === operator when comparing Window objects.

Note that this isn't a "JavaScript is weird" shrugpost. As well as serving as the global object, window is a host object and pre-HTML5 could legitimately (according to spec, at least) behave however it liked. Older versions of IE take advantage of this freedom and exhibit much quirky behaviour for which there is no specification whatsoever. Trying to understand it all without access to the source code is a pointless exercise.

Answer

For anyone who encounters this problem and needs a solution:

I ran into this problem while developing a Facebook app. I wanted to make sure the app had been loaded into the Canvas Page iframe, but in Internet Explorer window === top always returns false.

This:

window.top === window.self

should work in all versions of IE (and other browsers). It's great for determining if you've been framed, and it's happy, well-formed JS that won't make you feel dirty. It works inside an iframe without throwing any security warnings, too.

Answer

wtfjs is one of my favourite sites for the really wacky oddities you can find in Javascript.

Unsurprisingly, this little IE feature has got a mention, along with an attempt at an explanation: http://wtfjs.com/2010/02/25/ie-scope

Whether that explanation is accurate or not, I can't say, but the effect has been noted before.

So yes, there may be a quirk in IE's DOM here.

But it wouldn't be the only quirk in IE, and it strikes me as being one of the less important ones. In fact, to be honest, why do this even matter? Other than having a laugh at IE's expense, what is the use-case for ever wanting to compare window === top in a real-world script?

Answer

window tends to be the global object, rather than the page. window.window would be a property of that global object called "window" so in theory they should never be identical (===) but may be similar (==) since that global object is in the global scope.

I haven't tested this, but as a guess, you may have better luck comparing self (the current page) and parent

Tags

Recent Questions

Top Questions

Home Tags Terms of Service Privacy Policy DMCA Contact Us

©2020 All rights reserved.