В чем разница между open() и window.open() в Firefox?
В ответе мой вопрос Pumbaa80 нашел разницу между вызовами open()
и window.open()
, попробуйте следующие примеры в Firefox (проверено на 11.0):
Но почему же существует разница? Если я попробую следующий пример:
<script>
var a = 2;
function hello() { alert(this.a); }
hello();
window.hello();
</script>
Оба варианта вызывающей функции hello
работают точно так же, включая те же this
!!!
Ответы
Ответ 1
Один из ваших скриптов вызывает window.open
, а другой вызывает document.open
, потому что цепочка областей видимости в обработчиках событий inline-атрибутов является странной. Итак, вы попадаете в http://www.whatwg.org/specs/web-apps/current-work/multipage/elements.html#dom-document-open
Тем не менее, поскольку вы передаете 3 аргумента, это должно вызывать window.open
. Разница в поведении кажется ошибкой в Firefox. Я зарегистрировал https://bugzilla.mozilla.org/show_bug.cgi?id=741266.
Ответ 2
Внутри обработчика событий open
сам по себе решит document.open
. Как отметил Борис Збарский в комментарии и в его ответе, это ожидаемое поведение, указанное HTML5. В разделе раздел о обработчиках событий, шаг 6 указывает:
6. Используя среду выполнения script, созданную выше, создайте функциональный объект (как определено в ECMAScript edition 5, раздел 13.2 Создание объектов функций), с помощью:
(...)
Лексическая область окружения
- Пусть Scope будет результатом NewObjectEnvironment (элемент Document, глобальная среда).
- Если элемент имеет владельца формы, пусть Scope будет результатом NewObjectEnvironment (владелец формы элемента, область действия).
- Пусть Scope будет результатом NewObjectEnvironment (объект элемента, область действия).
(...)
Другими словами, ссылки переменных внутри обработчика событий будут разрешены в следующем порядке:
- локальная область
- свойства элемента
- свойства формы владельца (если применимо)
-
document
свойства
- глобальная область
Ответ 3
Ваши две скрипки работают одинаково для меня в Chrome.
Однако две строки кода
window.open(...);
и
open(...);
НЕ эквивалентны. Единственный раз, когда они будут эквивалентны, если ваша текущая область выполнения не предоставляет новое определение для open
, заставляя интерпретатор искать в более высоких областях, пока не достигнет глобальной области, и найдет window.open
.
Вы можете увидеть это в действии в этой скрипке:
var test = function () {
var open = function () {
alert('uh oh');
};
window.open('www.google.com');
open('www.google.com');
};
test();
Ответ 4
В браузере контекст по умолчанию - window
. Поэтому вы можете вызвать open()
, alert()
и даже escape()
, например. Вызов window.open()
в точности эквивалентен open()
.
Как открывается новое окно вызовом функции open()
, полностью зависит от вашего браузера.
Ответ 5
Это действительно очень странно. Похоже, что обработчик onclick
при добавлении в качестве атрибута имеет некоторый контекст с обернутой функцией open
, которая отличается от window.open
:
http://jsfiddle.net/aFujb/
Это происходит в последних версиях Firefox, Safari и Chrome. Я не могу найти никакого объяснения или отчета об ошибке для любого браузера.
Я попытался выяснить, что происходит в исходном коде Firefox, но, честно говоря, это слишком много для меня. Выглядит там две разные версии window.open под названием nsGlobalWindow::Open
и nsGlobalWindow::OpenJS
, но я не уверен, что это имеет какое-то отношение к вопрос.
Ответ 6
На самом деле это то же самое. Попробуйте window.open === open
или window["open"] === open
.
Если это дает вам ложь, вы должны быть в закрытии, а somecode - открытым.
И, конечно, это означает все объекты, которые являются членами глобального (окна) объекта.