Window.event! == window.event в IE
Код:
<html>
<head>
<script type="text/javascript">
onload = function(){
document.getElementById('btn1').onclick = function(){
if (window === window)
alert('window === window')
else
alert('window !== window');
if (window.event === window.event)
alert('window.event === window.event')
else
alert('window.event !== window.event' );
}
}
</script>
</head>
<body>
<button id="btn1" >click</button>
</body>
</html>
Результат:
IE (я тестировал IE6 - IE8):
window === window
window.event !== window.event
Все остальные браузеры говорят:
window === window
window.event === window.event
Какова причина ответа IE? Спасибо.
Ответы
Ответ 1
Я экспериментировал. Кажется, что каждый раз, когда вы обращаетесь к window.event
в IE, вы получаете новый объект:
document.body.onclick = function() {
var u = window.event, v = window.event;
console.log(window.event == window.event); // false
console.log(u == v); // false
console.log(u == u); // true
console.log(v == v); // true
console.log(u == window.event); // false
console.log(v == window.event); // false
};
Поэтому всякий раз, когда вы извлекаете window.event
, IE создает новый объект. Если вы тестируете этот объект против себя (u == u
или v == v
), он true
. Если вы протестируете его против другого объекта window.event
, это будет false.
(Обратите внимание, что это отличается от NaN
, поскольку var a = NaN; console.log(a == a);
- false
.)
Вспомните window.event
как нечто вроде генератора, более похожее на window.createCopyOfLastEvent()
в IE. window.event
- это геттер, который всегда возвращает новый объект. Ниже приведено следующее:
document.body.onclick = function() {
var v = window.event;
v.a = 1;
console.log(v.a); // 1
console.log(window.event.a); // undefined
};
В приведенном выше примере window.event.a
является undefined
, когда он регистрируется, потому что он относится к другому объекту, чем тот, где a = 1
.
Чтобы проиллюстрировать это поведение, можно было бы воссоздать в чистом JavaScript (в браузере с поддержкой ES5: IE9 или в последних версиях FF, Chrome или Safari):
var weirdObject = Object.create({ }, {
whoa: {
get: function() {
return new Object();
}
}
});
console.log(weirdObject.whoa == weirdObject.whoa); // false
Или, может быть, даже незнакомец смотрит:
Object.defineProperty(window, 'ahh', {
get: function() {
return Math.random();
}
});
console.log(ahh == ahh); // false
Ответ 2
Обновление:
Прочитайте это: IE Bug (окно === top) === false
Короче - IE сломан и не очень хорошо сравнивает объекты хоста.
Не все браузеры поддерживают window.event
. Большинство используют объект event
, переданный функции. (window.event
считалось специфичным для IE, хотя, похоже, Chrome его скопировал.)
Попробуйте следующее:
document.getElementById('btn1').onclick = function(event){
if (!event) {event = window.event;}
alert([typeof event, typeof window.event])
if (window === window)
alert('window === window')
else
alert('window !== window');
if (window.event === window.event)
alert('window.event === window.event')
else
alert('window.event !== window.event' );
}
}
Ответ 3
Поведение сравнения ECMAScript-совместимый Когда код выполняется в браузере, который не поддерживает window.event
, мы эффективно сравнивая два значения undefined, которые возвращают true
. В MSIE window.event
есть только интерфейс MSEventObj
, что означает, что два разных обращения к нему не возвратят тот же объект, и они будут сравнивать ложно.
Это означает, что, ну, window.event
никогда не будет таким же, поэтому сравнение бессмысленно. Если вы пытаетесь сравнить типы событий, вы можете выполнить сравнение типов уток, заставляя сравнение строк:
//false, you're either comparing undefined values or different objects
console.log(window.event == window.event);
//true, you're either comparing two "undefined" or "[object MSEventObj]" strings
console.log((""+window.event) === (""+window.event));
Мне не известно о практическом сценарии, когда вам потребуется выполнить эту конкретную проверку. Определение типа события должно быть выполнено путем проверки его свойства type
:
function doSomething(e) {
if (!e) var e = window.event;
alert(e.type);//or whatever
}
Обратите внимание, что это должно быть выполнено из script той части DOM - не из консоли инструментов разработчика:
![don't]()
Привычки свойств кросс-браузера