Чтение онлайн

ЖАНРЫ

JavaScript. Подробное руководство, 6-е издание
Шрифт:

Однако важно отметить, что этого не происходит, если объект

Window
уже имеет свойство с таким именем. Элементы с атрибутами
id
, имеющими значение
«history», «location»
или
«navigator»,
например, не будут доступны через глобальные переменные, потому что эти имена уже используются. Аналогично, если HTML-документ включает элемент с атрибутом
id
, имеющим значение «х» и в сценарии объявляется и используется глобальная переменная х, явно объявленная переменная скроет неявную переменную, ссылающуюся на элемент. Если переменная объявляется в сценарии, который в документе находится выше именованного элемента, наличие переменной будет препятствовать появлению
нового свойства окна. А если переменная объявляется в сценарии, который находится ниже именованного элемента, первая же инструкция присваивания значения этой переменной затрет значение неявно созданного свойства.

В разделе 15.2 вы узнаете, что с помощью метода

document.getElementByld
можно отыскивать элементы документа по значениям их HTML-атрибутов
id
. Взгляните на следующий пример:

var ui = ["input","prompt","heading"]; // Массив идентификаторов элементов

ui.forEach(function(id) { // Отыскать элемент для каждого id

ui[id] = document.getElementById(id); // и сохранить его в свойстве

});

После выполнения этого фрагмента свойства

ui.input, ui.prompt
и
ui.heading
будут ссылаться на элементы документа. Вместо
ui.input
и
ui.heading
сценарий мог бы использовать глобальные переменные input и heading. Но, как вы помните из 14.5, объект
Window
имеет метод с именем
prompt,
поэтому сценарий не сможет использовать глобальную переменную
prompt
вместо свойства
ui.prompt
.

Неявное использование идентификаторов элементов в качестве глобальных переменных - это пережиток истории развития веб-броузеров. Эта особенность необходима для сохранения обратной совместимости с существующими веб-страницами, но использовать ее сейчас не рекомендуется - в любой момент производители броузеров могут определить новое свойство в объекте

Window
, что нарушит работу любого программного кода, использующего неявно определяемое свойство с этим именем. Поиск элементов лучше выполнять явно, с помощью метода
document.getElementById.
А его использование будет менее трудоемким, если дать ему более короткое имя:

var $ = function(id) { return document.getElementByld(id); };

ui.prompt = $("prompt");

Многие клиентские библиотеки определяют функцию

$
, которая отыскивает элементы по их идентификаторам, как в примере выше. (В главе 19 мы узнаем, что функция
$
в библиотеке jQuery является универсальным методом выбора элементов, который может возвращать один или более элементов, опираясь на их идентификаторы, имена тегов, атрибут
class
или исходя из других критериев.)

Любой HTML-элемент с атрибутом

id
становится значением глобальной переменной, если значение атрибута
id
еще не используется объектом
Window
. Следующие HTML-элементы ведут себя подобным образом, если в них определен атрибут
name
:

<а> <applet> <area> <embed> <form> <frame> <frameset> <iframe> <img> <object>

Атрибут

id
элемента необходим для придания ему уникальности внутри документа: два элемента не могут иметь одинаковые значения атрибута
id
. Однако это не относится к атрибуту
name
.
Если сразу несколько элементов, из перечисленных выше, будут иметь одно и то же значение атрибута
name
(или, если один элемент имеет атрибут
name
, а другой - атрибут
id
с тем же значением), неявно созданная глобальная переменная с этим именем будет ссылаться на объект, подобный массиву, хранящий все элементы с этим именем.

Элементы

<iframe>
с атрибутом
name
или
id
обрабатываются иначе. Переменная, неявно созданная для таких элементов, будет ссылаться не на объект
Element
, представляющий сам элемент, а наобъект
Window
, представляющий вложенный фрейм созданный элементом
<iframe>.
К этой теме мы еще вернемся в разделе 14.8.2.

14.8. Работа с несколькими окнами и фреймами

Единственное окно веб-броузера может содержать несколько вкладок. Каждая вкладка является независимым контекстом просмотра. Каждая имеет собственный объект

Window
, и каждая изолирована от всех остальных. Сценарий, выполняющийся в одной вкладке, обычно даже не имеет возможности узнать о существовании других вкладок, и тем более не имеет возможности взаимодействовать с их объектами
Window
или манипулировать содержащимися в них документами. Если вы пользуетесь броузером, который не поддерживает вкладки, или поддержка вкладок отключена, вы можете открыть сразу несколько окон веб-броузера. Как и в случае с вкладками, каждое окно имеет свой собственный объект
Window
, и каждое окно обычно изолировано и не зависит от всех остальных окон.

Но окна не всегда изолированы друг от друга. Сценарий в одном окне или вкладке может открывать новые окна или вкладки, и в этом случае окна могут взаимодействовать друг с другом и с находящимися в них документами (с учетом ограничений, накладываемых политикой общего происхождения, описываемой в разделе 13.6.2). Подробнее тема открытия и закрытия окон рассматривается в разделе 14.8.1.

HTML-документы могут содержать вложенные документы, используя для этого элементы

<iframe>.
Элемент
<iframe>
создает вложенный контекст просмотра, представленный отдельным объектом
Window
. Устаревшие и не рекомендуемые к использованию элементы
<frameset>
и
<frame>
также создают вложенные контексты просмотра, и каждый элемент
<frame>
представлен собственным объектом
Window
. Различия между окнами, вкладками, плавающими фреймами (элемент
<iframe>
) и фреймами в клиентском JavaScript весьма несущественны: все они являются отдельными контекстами просмотра и в сценариях все они представлены объектами
Window
. Вложенные контексты просмотра не изолированы друг от друга, как обычно бывают изолированы независимые вкладки. Сценарий, выполняющийся в одном фрейме, всегда имеет доступ к вмещающим и вложенным фреймам, и только политика общего происхождения может не позволять сценарию просматривать документы в этих фреймах. Вложенные фреймы рассматриваются в разделе 14.8.2.

Поскольку в клиентском JavaScript объект Window является глобальным объектом, каждое окно или фрейм имеет отдельный контекст выполнения сценариев на языке JavaScript. Однако сценарий JavaScript, выполняющийся в одном окне, может, с учетом ограничений политики общего происхождения, использовать объекты, свойства и методы, объявленные в другом окне. Более подробно эта тема обсуждается в разделе 14.8.3. На тот случай, когда политика общего происхождения не позволяет сценариям в двух отдельных окнах взаимодействовать друг с другом напрямую, стандарт HTML5 предусматривает прикладной интерфейс передачи сообщений, основанный на механизме событий, который обеспечивает возможность косвенного взаимодействия. Подробнее эта возможность рассматривается в разделе 22.3.

Поделиться с друзьями: