Создание приложений с базами данных для Интернета и интрасетей: практическое руководство (С) Александр Вячеславович Фролов, Григорий Вячеславович Фролов, 2000 2. Сценарии в страницах HTML и DHTML 2. Сценарии в страницах HTML и DHTML Объектная модель браузера Microsoft Internet Explorer Применение сценариев для создания интерфейса пользователя Начальная регистрация пользователя Загрузка новой страницы в окно браузера Перекодирование содержимого полей форм Отключение кэширования страниц Модальные и немодальные диалоговые панели Вывод информационных сообщений Сообщение с выбором одной из двух возможностей Диалоговая панель на базе документа HTML Десятично-шестнадцатеричный преобразователь Одновременная замена нескольких документов HTML в окнах разных фреймов Использование растровых изображений Растровое изображение как объект Динамическая замена растровых изображений Изменение внешнего вида графических ссылок Создание анимационных изображений Ожидание загрузки всех изображений Наложение фильтра на графическое изображение Применение Cookie в клиентских сценариях Выполнение основных операций с Cookie Создание Cookie расширением сервера Web Создание Cookie в клиентском сценарии Изменение значения параметра Cookie Ограничения на использование Cookie Фиксация повторных посещений страницы Записная книжка Cookie Notepad Настройка параметров документа HTML Настройка браузера для работы с Cookie Прежде чем Вы начнете использовать страницы ASP и непосредственно работать с базой данных, Вам необходимо освоить основные приемы создания документов HTML и DHTML с клиентскими сценариями на языках JavaScript и VB Script. Мы предполагаем, что Вы уже владеете этими языками программирования, поэтому не стали подробно излагать их в книге. Однако краткую справочную информацию по JavaScript и VB Script мы поместили в приложение к книге. При необходимости Вы можете к ней обратиться. Объектная модель браузера Microsoft Internet Explorer Для выполнения каких-либо действий над страницами HTML, загруженными в окно браузера, клиентский сценарий должен обращаться к интерфейсам объектов сценария, доступных в браузере. Схематически объектная модель браузера Microsoft Internet Explorer представлена на рис. 2-1. Вы можете обращаться к этому рисунку при составлении клиентских сценариев для указанного браузера. Рис. 2-1. Объектная модель браузера Microsoft Internet Explorer Объект window соответствует окну браузера Microsoft Internet Explorer. Он содержит такие объекты, как document, navigator, frames, history, location, screen и event. В свою очередь, объект document может содержать объекты links, anchor, forms и другие, а объект forms — объект elements. Когда пользователь загружает в окно браузера страницу HTML, перечисленные выше объекты создаются и становятся доступными для сценариев. Их состав и количество зависит от содержимого загруженной страницы. В таблице 2-1 Вы найдете описание некоторых объектов браузера Microsoft Internet Explorer. Таблица 2-1. Объекты браузера Microsoft Internet Explorer
В зависимости от содержимого страницы HTML, загруженной в окно браузера, сценариям становятся доступными и другие объекты, например images и applets. Заметим, что браузер Netscape Navigator имеет другой набор объектов и другие связи между ними. Окно браузера Netscape Navigator соответствует объекту window, содержащему такие объекты как Frame, document, Location и History. Объект document, представляющий собой документ HTML, загруженный в окно браузера, содержит в свою очередь объекты Form, Layer, Link, Image, Area, Anchor, Applet и Plugin. Если документ HTML, загруженный в браузер Netscape Navigator, содержит формы, то соответствующие объекты Form могут включать в себя объекты, созданные для элементов форм, таких, как переключатели, поля ввода текстовой информации, списки и т. д. Это объекты Text, Textarea, Password, Hidden, Submit, Reset, Radio, Checkbox, Button, Select и FileUpload. Объект Select, представляющий собой список, содержит объекты Option, создаваемые для строк списка. Более подробную информацию об объектах браузера Netscape Navigator Вы найдете в Интернете по адресу http://developer.netscape.com/doc/manuals, а также в литературе, список которой приведен в конце нашей книги. В качестве простого примера обращения сценариев JavaScript к объекту Navigator мы приведем листинг небольшого документа HTML, расположенного в файле BrowserInfo.html (листинг 2-1). Листинг 2-1. Файл ch01/BrowserInfo.html Обращаясь к свойству браузера navigator.appName мы можем определить название браузера: document.writeln("<TR><TD>Название
браузера:</TD><TD>" Аналогичным образом мы можем определить другие параметры браузера и системы, такие как версия, тип процессора, язык и т. д.: document.writeln("<TR><TD>Кодовое имя
браузера:</TD><TD>" При загрузке этого документа в окно браузера Вы увидите сведения о версии браузера. На рис. 2-2 и 2-3 мы показали, что получится при загрузке документа BrowserInfo.html в браузер Microsoft Internet Explorer 5.0 и в браузер Netscape 4.51. Рис. 2-2. Информация о браузере Microsoft Internet Explorer Обратите внимание, что браузер Netscape не показал нескольких свойств, с которыми легко справился Microsoft Internet Explorer. Это свойства navigator.cpuClass, navigator.systemLanguage, navigator.userLanguage и navigator.appMinorVersion, появившиеся в последних версиях браузера Microsoft Internet Explorer. Даже на таком простейшем примере видно, что сценарии JavaScript могут работать по-разному в разных браузерах. Рис. 2-3. Информация о браузере Netscape Далее мы расскажем о применении различных объектов описанной выше модели браузера. Применение сценариев для создания интерфейса пользователя При создании Интернет-магазина мы используем диалоговый интерфейс, основанный на применении форм и фреймов. Если Вы знакомы с языком HTML, то должны знать, что формы создаются с помощью тегов <FORM>. Внутри формы могут располагаться текстовые поля ввода, списки, переключатели, кнопки и другие объекты. Как выполняется обработка данных, введенных пользователем в форме? Тут возможны два варианта. Первый таков: данные, введенные пользователем при помощи формы, сразу переправляются на сервер для проверки и обработки. Во втором случае эти данные предварительно проверяются клиентским сценарием. У каждого из этих двух способов есть свои преимущества и недостатки. В первом случае преимущества заключаются в том, что форма не содержит никакого сценария и, следовательно, нет причин для возникновения проблем совместимости сценариев и браузера пользователя. Однако, если в форме много полей, которые должны быть заполнены определенным образом, велика вероятность того, что пользователь где-то ошибется. Тогда сервер отправит пользователю сообщение об ошибке, и ему придется проверить форму, а затем отправить ее на сервер повторно. Известно, что в целом Интернет не обладает высокой пропускной способностью. Поэтому повторные передачи данных раздражают пользователей и могут вызвать увеличение нагрузки на каналы связи и сервер. При применении второго способа введенные пользователем данные проверяются локально. Это улучшает время ответа системы, но иногда приводит к возникновению проблемы совместимости использованного Вами сценария и браузера пользователя. В том случае, когда Вы ставите перед собой задачу обеспечить максимальную доступность магазина для посетителей с любыми браузерами, постарайтесь полностью исключить применение клиентских сценариев. Однако при разработке административных приложений, предназначенных для управления работой магазина (или любого другого приложения Web) использование клиентских сценариев для проверки форм вполне допустимо. Начальная регистрация пользователя Как правило, прежде чем пользователь попадет к виртуальным прилавкам Вашего магазина, ему необходимо выполнить регистрацию. В процессе регистрации он сообщит Вам свое полное имя, почтовый и электронный адреса и, возможно, другую информацию. Все эти сведения Вам необходимо сохранить в базе данных. В этом разделе мы расскажем о том, как выполнить предварительную проверку регистрационных данных, введенных пользователем, перед их отправкой на сервер. Сам процесс отправки мы рассмотрим позже, в разделе, посвященном страницам ASP. В качестве примера мы подготовили небольшую форму, предназначенную для регистрации посетителей магазина (рис. 2-4). Рис. 2-4. Форма регистрации посетителей магазина В полях этой формы посетитель должен указать сведения о себе, необходимые для оформления покупки. Заметьте, что здесь пользователю не предлагается ввести номер своей кредитной карточки. Такая информация должна передаваться напрямую на сервер компании, занимающейся обслуживанием кредитных карточек минуя сервер Интернет-магазина. Некоторые поля в этой форме отмечены как обязательные для заполнения. Перед тем как отправлять введенные данные на сервер для записи в базу данных покупателей, было бы неплохо проверить правильность заполнения полей формы. Для этой цели мы используем сценарий JavaScript, который: · проверяет, заполнил ли посетитель обязательные поля, отмеченные в форме символом «*»; · сравнивает пароль с подтверждением пароля — они должны совпадать; · проверяет e-mail, который должен содержать по крайней мере один символ «@» и одну точку. В качестве тренировки Вы можете добавить строку для проверки номера телефона — в нем допустимы пробелы, символы «-» и цифры. Чтобы отличить цифры от других символов, используйте функцию isDigit. Исходный текст документа HTML с формой и сценарием JavaScript показан в листинге 2-2. Этот документ был создан при помощи Microsoft FrontPage. Клиентские сценарии редактировались в среде Microsoft InterDev 6.0. Листинг 2-2. Файл ch01/RegisterForm.html В документе имеется форма с полями ввода регистрационной информации: <form name="RegForm"
action="http://www.YourServer.YourDomain/YourCGI.cgi"
metod="post"> Обращаем Ваше внимание на следующий фрагмент этого документа: <input type="button"
onClick="checkForm();" Когда посетитель щелкнет мышью кнопку Регистрация, будет вызвана функция checkForm, выполняющая проверку полей формы: function checkForm() Если при вводе допущены ошибки, функция отобразит на экране пользователя сообщение об ошибке, а если все правильно — отправит данные на сервер Web для обработки программой CGI. Доступ к полям формы выполняется при помощи объекта document, например: document.RegForm.name.value Здесь мы ссылаемся на имя формы (RegForm), на имя поля (name), а также на свойство value, содержащее значение этого поля. Для проверки правильности ввода почтового адреса мы применили функцию mailAddressIsValid: function mailAddressIsValid(mailAddress) Если все данные введены правильно, мы отображаем их на экране функцией alert и затем отправляем на сервер Web. Для отправки данных формы применяется метод submit, как это показано ниже: document.RegForm.submit(); Для удобства эта строка выделена в листинге 2-2 жирным шрифтом. Такое действие эквивалентно щелчку кнопки типа Submit, применяемой в обычных формах для отправки данных. Еще одна задача, часто возникающая при разработке приложений Web, это ввод календарных дат и диапазонов календарных дат. Например, Вам может потребоваться список клиентов, зарегистрировавшихся в определенный период времени или список платежных транзакций, выполненных за определенный период времени. При кажущейся простоте этой задачи ее реализация тем не менее может быть затруднена рядом «подводных камней». Во-первых, если разрешить пользователю вводить даты в свободном формате, Вашему приложению придется иметь дело не только с ошибочно введенными датами, но и со множеством правильных форматов дат. В зависимости от страны проживания пользователи будут указывать дату по-своему, и это сильно затрудняет Вашу задачу. Во-вторых, необходимо, чтобы при проверке дат учитывалось количество дней в указанном месяце, а также високосные годы. И, наконец, при записи даты в базу данных или при использовании дат в запросах SQL Вам придется преобразовать ее в фиксированный формат, с которым сможет работать программа SQL. С учетом сказанного выше, на наш взгляд, лучше всего применять для ввода дат такие органы управления, как списки. Предварительно в них следует указать возможные значения дат. Нам понравилось, как решена проблема ввода диапазона дат Максимом Синевым из компании Spektrum Web Development (http://www.spektrum.org.ru). На рис. 2-5 мы показали форму с календарями, предназначенную для просмотра списка покупателей по дате регистрации. В этой форме мы применили (в немного измененном виде) разработанное им решение для ввода диапазона дат, основанное на применение средств DHTML и сценариев JavaScript. Заметим, что в силу использования объектной модели браузера Microsoft Internet Explorer, этот метод не пригоден для работы с другими браузерами. Однако данное обстоятельство не имеет решающего значения при создании приложений Web для интрасетей и административных приложений Web в Интернете. Как пользоваться формой, показанной на рис. 2-5? Все операции выполняются мышью. Щелкая ссылки вида <<< и >>>, Вы можете изменять год в начальной и конечной дате. В данном случае выполняется поиск пользователей, зарегистрировавшихся в период с 1998 до 2000 года. Щелкая название месяца и календарной даты в левом и правом календаре, Вы установите период времени с точностью до одного дня. В нашем случае начальная дата — 3 марта 1998 года, а конечная — 29 февраля 2000 года. Для наглядности названия месяцев и календарные даты выделены в окне формы желтым цветом. Для того чтобы запустить поиск, достаточно щелкнуть мышью ссылку Поиск. Рис. 2-5. Форма для просмотра списка покупателей по дате регистрации Если снять флажок у переключателя искать по дате регистрации:, календари в форме исчезнут, причем это произойдет мгновенно, без повторной загрузки формы с сервера Web (рис. 2-6). После его повторного включения календарь также быстро появится на экране вновь. Операции рисования календаря, его сокрытия и повторного отображения выполняются с применением сценариев JavaScript и объектной модели DHTML. Форма, предназначенная для определения параметров просмотра, определена следующим образом: <form method="POST" id="SearchForm"> Полный и Листинг 2-3. Файл ch01/CustomerSearch.html Рис. 2-6. Теперь дата регистрации не учитывается Изучая этот листинг, прежде всего обратите внимание на то, что он ссылается на файл calendar.js: <html> В нем хранится большинство функций сценария JavaScript, обеспечивающих работу календарей. Полный текст файла calendar.js Вы найдете в листинге 2-4. Листинг 2-4. Файл ch01/calendar.js Теперь мы расскажем о том, как устроен документ HTML CustomerSearch.html (листинг 2-3). При внимательном изучении видно, что помимо всего прочего он содержит две пустые таблицы для календарей: <table border="0"
cellpadding="0" cellspacing="0" id="calendarTable"> Заполнение этих таблиц осуществляется при помощи сценария JavaScript. Как это происходит? В теле тега <BODY> мы определили обработчик события onLoad, вызывающий функцию buildmap: <body onload="buildmap()"> Вот исходный текст функции buildmap: function buildmap() Данная функция вызывается при завершении загрузки документа HTML в окно браузера. В ее задачу входит определение текущей даты и ее составляющих — номера года, месяца и числа. Для этой цели вызываются функции getFullYear, getMonth и getDate. Далее для заполнения полей таблицы начальной даты функция buildmap последовательно вызывает функции refby, fillfmonths и fillfdays: function refby() Для заполнения полей таблицы конечной даты вызываются функции refey, filltmonths и filltdays. Эти функции интенсивно используют свойство innerText различных объектов таблиц календарей, заданных в тексте HTML их идентификаторами ID: function refby() Присваивая новое значение свойству innerText, сценарий JavaScript способен динамически изменять содержимое тегов страницы, отображаемой в окне браузера. На этой возможности DHTML и строится вся работа данного сценария. Последнее действие, выполняемое функцией buildmap, это активизация переключателя искать по дате регистрации:. Именно этот режим используется в форме по умолчанию: document.all.UseDataCheckBox.checked=true; В файле calendar.js содержится определение функции buildmapEx — она позволяет выполнить предварительную установку календарей для заданного диапазона дат: function buildmapEx(FY, FM, FD, TY,
TM, TD, DateCheck) Еще одна функция, представляющая интерес, определена в файле CustomerSearch.html (листинг 2-3). Это функция hidecalendar, предназначенная для того, чтобы отображать и убирать с экрана календари при изменении состояния переключателя искать по дате регистрации:. Вот ее исходный текст: var
sCalendarPreserve; Функция hidecalendar вызывается по событию onClick, когда пользователь щелкает этот переключатель. Если флажок снят, функция hidecalendar сохраняет в переменной sCalendarPreserve содержимое кода HTML таблицы календарей с идентификатором calendarTable: var sCalendarPreserve; Далее функция hidecalendar создает новую пустую таблицу, сохраняя ссылку на соответствующий объект в переменной oNewNode, и замещает таблицу с календарями этой пустой таблицей: oNewNode =
document.createElement("<table>"); На следующем этапе мы замещаем содержимое таблицы, изменяя свойство outerHTML, и выключаем переключатель: oNewNode.outerHTML = Новое содержимое таблицы представляет собой одну строку ссылки в виде слова Поиск. При выборе этой или аналогичной ссылки в исходной таблице с календарями управление передается функции go, выполняющей переход к странице поиска покупателей. Когда пользователь вновь активизирует переключатель искать по дате регистрации:, функция hidecalendar возвращает таблицу календарей в исходное состояние: oCurrentNode=document.getElementById("TableReplaced"); Что же касается функции go, то мы рассмотрим ее в следующем разделе. Загрузка новой страницы в окно браузера Сценарий JavaScript способен загрузить в окно браузера (или в окно фрейма, если документ содержит фреймы) новый документ HTML, заданный адресом URL. В частности, если текущий документ содержит форму запроса к базе данных, сценарий JavaScript может загрузить в текущее окно браузера документ HTML (или ASP) с результатами обработки этого запроса. Именно так и работает функция go из примера, приведенного в листинге 2-3: function go() Здесь в свойство href объекта window.location записывается адрес страницы ASP, с названием GetSearchResults.asp. Эта страница расположена в том же каталоге, что и вызывающий ее документ HTML, поэтому вместо полного пути мы указали только имя файла. После имени файла проставлен разделяющий символ «?» и достаточно длинная строка параметров, передаваемая странице ASP. Эта строка содержит начальную и конечную дату, имя пользователя, адрес его электронной почты и еще один параметр с именем FRCE, о котором мы пока умолчим. Строка параметров будет прочитана и обработана серверным сценарием, встроенным в страницу GetSearchResults.asp. Подробнее об этом мы расскажем в следующей главе. Если Вы не собираетесь выполнять предварительную обработку формы при помощи клиентского сценария, адрес данной страницы ASP нужно указать в параметре ACTION тега <FORM>, как это делается при вызове расширений CGI и ISAPI. Перекодирование содержимого полей форм Чтобы данные из полей формы были корректно переданы программам CGI, ISAPI или странице ASP, они должны иметь так называемую кодировку URL. В этой кодировке символы пробелов заменяются знаком «+», а для представления кодов управляющих и некоторых других символов применяется последовательность вида «%xx», где символы «xx» представляют собой шестнадцатеричный код исходного символа в виде двух символов ASCII. Если Вы передаете программам CGI, ISAPI или странице ASP параметры из клиентского сценария, преобразование текстовых строк в кодировку URL придется выполнить явным образом. В сценариях JavaScript это легко осуществить при помощи функции escape. Вот, например, как это делается в функции go из только что рассмотренного примера: var
sLogName=escape(document.all.SearchForm.LogName.value); Если же вызов программ расширения сервера Web или страниц ASP выполняется через параметр ACTION тега <FORM>, преобразование происходит автоматически. Отключение кэширования страниц Когда пользователь путешествует по сети Интернет с помощью браузера, посещенные им страницы кэшируются либо самим браузером, либо промежуточным прокси-сервером. Механизм кэширования заметно ускоряет повторный просмотр страниц, так как одни и те же данные не передаются по несколько раз через медленные каналы Интернета. К сожалению, механизм кэширования страниц иногда вызывает проблемы в приложениях Web, создающих страницы динамически при помощи программ CGI, ISAPI или средств ASP. Проблемы проявляются, когда пользователь пытается просмотреть несколько раз одну и ту же страницу, созданную динамически. Даже если каждый раз эти страницы имеют различное содержимое, браузер будет показывать только первый вариант, который он загрузил в свой кэш при первом обращении к странице. В результате пользователю кажется, что страница не обновляется. Как отменить кэширование страниц? Едва ли стоит просить пользователя отключить кэширование страниц в его браузере — это отрицательно скажется на скорости просмотра информации. Кроме того, информация в некоторых случаях кэшируется не локально, а в прокси-сервере, настроить который пользователь не может. Первый достаточно известный способ заключается в применении тега <META> с параметром HTTP-EQUIV=Expires, расположенного внутри заголовка документа <HEAD>. Этот параметр указывает дату, начиная с которой содержимое документа считается устаревшим и он подлежит перезагрузке. Например, Вы можете использовать тег <META> следующего вида: <META HTTP-EQUIV=Expires CONTENT=Tue, 02 Jan 1996 01:00:00 GMT> К сожалению, этот простой способ работает не всегда. Более надежный способ, который можно применить при загрузке динамически создаваемых страниц с помощью клиентских сценариев, заключается в добавлении фиктивного параметра со случайным значением. Мы применили этот способ в функции go, полный текст которой приведен в листинге 2-3: window.location.href =
"GetSearchResults.asp?DATECHECK=" + Параметр с именем FRCE представляет собой случайное число, полученное от функции Math.random и преобразованное в текстовую строку функцией toString. Другие способы отключения кэширования страниц будут описаны в главе, посвященной серверным сценариям ASP. Модальные и немодальные диалоговые панели При создании любых интерактивных приложений всегда возникает задача отображения различных сообщений или получения от пользователя дополнительной информации. В этом разделе мы расскажем об использовании для этой цели модальных и немодальных окон, создаваемых средствами клиентских сценариев. Заметим, что описанные здесь средства лучше применять для создания административных приложений, доступ к которым осуществляется не всеми пользователями Интернета, а только сотрудниками Вашей фирмы. Это связано с тем, что посетители могут отключить в их браузере возможность работы клиентских сценариев. Модальными называются такие диалоговые панели, которые должны быть закрыты для продолжения работы приложения. Например, если приложение выводит на экран модальную диалоговую панель с сообщением об ошибке, работа приложения будет приостановлена до тех пор, пока пользователь не прочитает сообщение и не щелкнет кнопку OK. Для создания окон модальных диалоговых панелей серверный сценарий использует методы, перечисленные в таблице 2-2. Таблица 2-2. Методы для создания окон модальных диалоговых панелей
Теперь мы рассмотрим несколько практических примеров применения перечисленных выше методов. Вывод информационных сообщений В первом примере мы покажем, как выводить на экран обычные текстовые сообщения. На рис. 2-7 изображено окно с двумя кнопками — Вход и Выход. Если щелкнуть кнопку Вход, на экране появится приветственное сообщение, показанное на рис. 2-8, а если щелкнуть кнопку Выход — сообщение, показанное на рис. 2-9. Рис. 2-7. Панель для демонстрации способа выдачи сообщений Исходный текст соответствующего документа HTML представлен в листинге 2-5. Листинг 2-5. Файл ch02/MessageBox.html Как видно из этого исходного текста, в документе имеется таблица с двумя кнопками: <table border="0" width="27%"
cellpadding="2"> Для каждой из этих кнопок мы определили обработчик события onClick, задача которого заключается в вызове функции msgBox. Эта функция просто обращается к методу alert, передавая ему в качестве параметра строку сообщения: function msgBox(sMessage) Рис. 2-8. Сообщение, появляющееся в результате щелчка кнопки Вход Рис. 2-9. Сообщение, появляющееся в результате щелчка кнопки Выход В данном случае мы воспользовались для выдачи сообщения простейшим методом alert, так как в ответ на это сообщение пользователю не нужно принимать решение и выбирать одно из нескольких действий. В следующем примере пользователю предоставлен выбор — он может отреагировать на сообщение различным образом. Сообщение с выбором одной из двух возможностей Иногда для выполнения какого-либо действия необходимо запросить подтверждение. Например, если администратор базы данных с помощью Вашего приложения редактирует список пользователей, то перед удалением пользователя было бы неплохо запросить у него дополнительное разрешение. Кроме того, приложению может потребоваться дополнительная информация, например имя пользователя. Все эти задачи решают с помощью методов confirm и prompt. Покажем, как это сделать на конкретном примере. Предположим, нужно удалить пользователя из базы данных. На рис. 2-10 показано окно браузера, в которое загружен документ HTML, выполняющий данную операцию. Рис. 2-10. Документ HTML, предназначенный для удаления пользователей Если Вы щелкнете кнопку Удалить пользователя, клиентский сценарий запросит имя «жертвы» (рис. 2-11). При этом он вызовет метод prompt. Рис. 2-11. Ввод имени удаляемого пользователя Чтобы удалить пользователя, Вам надо ввести его имя и нажать кнопку OK. В реальных приложениях имена пользователей хранятся в базе данных. О том, как удалять пользователей из базы данных, Вы узнаете позже. Перед удалением пользователя наш сценарий выводит на экран сообщение, показанное на рис. 2-12. Оно отображается с применением метода confirm. Рис. 2-12. Запрос подтверждения на удаление пользователя Здесь отображается имя удаляемого пользователя и предлагается подтвердить выполнение этой операции. Если щелкнуть кнопку OK, на экране появится сообщение об успешном удалении пользователя с заданным именем (рис. 2-13). Оно отображается методом alert. Рис. 2-13. Сообщение об успешном удалении пользователя Исходный текст документа HTML со сценарием, выполняющим описанные выше действия, Вы найдете в листинге 2-6. Листинг 2-6. Файл ch02/OtherModalMessageBox.html Когда пользователь щелкает кнопку Удалить пользователя, управление получает функция deleteUser: function deleteUser() Она вызывает метод prompt и указывает ему в качестве имени удаляемого пользователя значение по умолчанию — «<temp user>». Если пользователь завершает работу диалоговой панели кнопкой OK, метод prompt возвращает строку имени пользователя. После щелчка кнопки Cancel метод prompt возвращает значение null. Есть и еще один способ — пользователь вводит кнопкой OK пустую строку. При этом метод prompt также возвращает пустую строку. После вызова метода prompt функция deleteUser проверяет возвращенное этим методом значение. Если это не пустая строка и не значение null, сценарий выполняет действия по удалению пользователя. В нашем случае эти действия фактически не реализуются, но Вы можете добавить свой код в то место сценария, которое выделено строкой комментария. Когда удаление пользователя завершается удачей, функция deleteUser выводит на экран сообщение об этом, вызывая функцию msgBox: function msgBox(sMessage) Диалоговая панель на базе документа HTML Описанные выше средства создания модальных диалоговых панелей помогут Вам только в простейших случаях, когда требуется лишь показать пользователю сообщение, предложить ему выбор из двух возможностей или запросить одну текстовую строку. Однако иногда надо получить от пользователя обширную информацию. Например, если Вы создаете электронный книжный магазин, то при регистрации новых поступлений Вы должны ввести в базу данных такие сведения, как название книги, имя автора, аннотация на книгу, название издательства и выходные данные книги, сведения о поставщике и т. д. В этом случае не обойтись без форм ввода, созданных на основе документов HTML. Средствами метода showModalDialog Ваш клиентский сценарий может организовать вывод документов HTML с формой ввода на экран, получение и предварительную обработку введенной информации. Например, в документе HTML на рис. 2-14 имеется кнопка, предназначенная для регистрации новых книг (наряду с кнопками регистрации других новых товаров). Рис. 2-14. Документ HTML для регистрации новых товаров Если Вы щелкнете эту кнопку, на экране появится модальная диалоговая панель регистрации новых книг, содержащая форму ввода с полями различных типов (рис. 2-15). Рис. 2-15. Документ HTML с формой регистрации новых книг Заполнив поля в этой форме, Вы можете зарегистрировать книгу в базе данных, щелкнув кнопку Добавить в базу данных, либо отказаться от регистрации при помощи кнопки Отменить регистрацию. После этого окно с формой исчезнет с экрана. В случае успешной регистрации на экране появится сообщение, содержащее текст из всех полей формы (рис. 2-16). Рис. 2-16. Просмотр информации о зарегистрированной книге Если же регистрация отменена, Вы вновь вернетесь к документу HTML, показанному на рис. 2-14. Теперь обратимся к исходному тексту клиентского сценария, выполняющего все перечисленные выше действия (листинги 2-7 и 2-8). Листинг 2-7. Файл ch02/ModalRegisterDialog.html В листинге 2-7 приведен исходный текст документа HTML с кнопкой запуска регистрации. Данная кнопка расположена в ячейке таблицы: <table border="0" width="27%"
cellpadding="2"> Щелчок этой кнопки вызывает функцию registerNewBook, выполняющую отображение модельной диалоговой панели регистрации, прием из полей этой панели введенной информации и отображение ее на экране: function registerNewBook() Как работает эта функция? Прежде всего, она создает массив regFields для сохранения значений из полей формы регистрации: var regFields = new Array(); В этот массив будет записано значение, возвращенное методом showModalDialog, после того как пользователь завершит работу с модальной диалоговой панелью: regFields =
window.showModalDialog("ModalRegisterForm.html", В качестве первого параметра мы передаем методу showModalDialog адрес URL документа с формой ModalRegisterForm.html. В нашем случае этот документ лежит в том же каталоге, что и вызывающий его документ ModalRegisterDialog.html, поэтому вместо полного или относительного адреса URL мы ограничимся именем файла. Через второй параметр мы передаем текстовую строку, которая будет использована в диалоговой панели как заголовок формы. Заметим, что Вы можете передать панели не только одно значение, а целый массив. Это полезно, например, для начальной инициализации полей формы значениями по умолчанию. И, наконец, третий параметр формы определяет ширину и высоту окна, в котором будет отображена панель, а также диапазоны изменения размеров этого окна пользователем (эта возможность доступна только при использовании браузера Microsoft Internet Explorer 5.0 или более новой версии). Один из элементов возвращаемого массива — Return определяет, добавил ли пользователь новую книгу в базу данных кнопкой Добавить в базу данных или отказался от выполнения это операции, щелкнув кнопку Отменить регистрацию. Следующий фрагмент кода позволяет определить, какой кнопкой была завершена работа с диалоговой панелью: if(regFields["Return"] == "OK") Если панель закрыта кнопкой Добавить в базу данных, соответствующий сценарий (размещенный в файле ModalRegisterForm.html) записывает в элемент массива Return строку «OK», а если Отменить регистрацию — строку «Cancel». После успешной регистрации функция registerNewBook получает содержимое всех полей формы регистрации, обращаясь к соответствующим элементам массива по именам, и формирует итоговую строку для отображения на экране методом alert: var sBookInfo = "Название: " +
regFields["Title"] + Теперь мы рассмотрим исходный текст документа HTML с формой регистрации, который находится в листинге 2-8. Листинг 2-8. Файл ch02/ModalRegisterForm.html Помимо полей для ввода сведений о книге, в форме регистрации имеется таблица с кнопками: <table width="497"> Когда пользователь щелкает кнопку Добавить в базу данных, управление передается функции addBook, а когда кнопку Отменить регистрацию — функции addCancel. Сначала мы рассмотрим функцию addBook: function addBook() Ее задача заключается в заполнении массива formFields, определенном в документе ModalRegisterForm.html следующим образом: var formFields = new Array; Обращаясь последовательно ко всем полям формы, функция addBook формирует содержимое массива formFields: formFields["Title"]=document.RegForm("Title").value; Дополнительно в элемент массива Return функция addBook записывает строку «OK», которая срабатывает при завершении работы диалоговой панели кнопкой Добавить в базу данных: formFields["Return"]="OK"; Дальнейшие действия функции addBook показаны ниже: window.returnValue = formFields; Здесь мы сохраняем заполненный массив в свойстве window.returnValue, записываем значение false в свойство event.returnValue и закрываем окно диалоговой панели, вызывая метод window.close. Изменение значения event.returnValue позволяет не возвращать объект event (это происходит по умолчанию). Что же касается функции addCancel, вызываемой щелчком кнопки Отменить регистрацию, то она записывает в массив formFields только одно значение с именем Return и возвращает это значение аналогично функции addBook: function addCancel() Таким образом, с помощью элемента массива formFields с именем Return мы передаем код кнопки, использованной для завершения работы диалоговой панели. Остальные элементы — Title, Author, Annotation и Publisher — передают значения из полей формы, введенные пользователем при регистрации книги. Немодальные диалоговые панели представляют собой дополнительные окна браузера, существующие автономно от других окон. Клиентский сценарий может открыть новое немодальное окно методом open и загрузить в него для просмотра любой документ HTML. Пример вызова метода open показан ниже: open(sURLAddress [, sWindowName [, sFeatures [, replace]]]]); Метод возвращает имя нового окна, которое можно использовать для ссылки на свойства и методы окна, а также на свойства и методы объектов, расположенных в этом окне. Рассмотрим параметры метода open. Первый обязательный параметр sURLAddress задает адрес URL документа HTML, предназначенного для загрузки в новое окно. Второй необязательный параметр sWindowName определяет имя окна для использования в параметре target тега <A> или в теге <FORM>. Он может быть пустой строкой. Третий, тоже необязательный параметр features, задает различные параметры, определяющие внешний вид создаваемого окна браузера. Он представляет собой текстовую строку, где через запятую перечислены значения отдельных параметров, например: var wndNewWindow; Параметр определяет действия с указанным адресом URL в списке истории просмотренных страниц. Если он равен true, данный адрес замещает текущий в указанном списке, а если false — этот адрес будет добавлен в конец списка. В таблице 2-3 мы перечислили все возможные параметры окна. Таблица 2-3. Параметры окна
В качестве примера, иллюстрирующего применение немодальных окон, рассмотрим страницу HTML, предназначенную для просмотра других страниц с заданным адресом URL. Такая страница показана на рис. 2-17. Рис. 2-17. Выбор адреса URL страницы для просмотра в немодальном окне Здесь в поле Адрес URL Вы можете задать адрес любой страницы, расположенной как на локальном диске, так и в сети Интернет. Мы указали имя документа BrowserInfo.html, исходный текст которого уже рассматривал ранее в нашей книге. После того как пользователь щелкнет кнопку GO!, на экране появится новое окно, и в него будет загружена указанная Вами страница (рис. 2-18). Конечно, копирование выполняется только в том случае, если при вводе адреса URL Вы не допустили ошибку. Рис. 2-18. Страница загружена в немодальное окно Обращаем Ваше внимание на то, что окно браузера, показанное на этом рисунке, не совсем стандартное. В нем нет ни меню, ни инструментальных линеек, ни строки состояния. Мы это сделали намеренно, указав соответствующие параметры при вызове метода window.open. При необходимости Вы можете изменить вид этого окна по своему усмотрению. Исходный текст документа HTML с клиентским сценарием, создающим новое окно браузера, представлен в листинге 2-9. Листинг 2-9. Файл ch02/ShowURL.html В форме, предназначенной для ввода адреса URL имеется поле ввода адреса и кнопка, предназначенная для выполнения перехода по заданному адресу: <form name="GoForm"> Когда пользователь щелкнет кнопку GO!, управление будет передано функции go: function go() Эта функция вызывает метод window.open, передавая ему в качестве первого параметра значение, извлеченное из поля формы с именем URLAddress. Именно там находится указанный пользователем адрес URL. Второй параметр определяет имя окна, а третий задает параметры его отображения. В нашем случае мы указываем, что в окне не должно быть инструментальной линейки (параметр toolbar=no) и меню (параметр menubar=no). Кроме того, пользователь получит возможность изменять размеры окна после его отображения по своему усмотрению (параметр resizable=yes). Использование фреймов для создания приложений Web для Интернета имеет свои положительные и отрицательные стороны. С одной стороны, фреймы значительно облегчают процесс разработки и сопровождения крупных серверов Web, так как ссылки на разделы сервера располагаются не на всех страницах, а только не некоторых, специально предназначенных для этой цели. С другой стороны, не все браузеры в состоянии корректно просматривать страницы с фреймами. Принимая решение о применении фреймов или об отказе от них, учитывайте, что такие приложения как Интернет-магазин содержат помимо страниц, предназначенных для широкого круга посетителей, страницы администрирования. На них записаны процедуры администрирования работой магазина, поэтому доступ к ним, как правило, имеет небольшое число сотрудников Вашей фирмы. Вы можете установить на компьютерах этих сотрудников браузер Microsoft Internet Explorer самой новой версии и забыть о проблемах несовместимости с фреймами. В этом случае применение фреймов значительно упростит административную часть Вашего проекта. Не вдаваясь в детали использования фреймов (которые Вы легко найдете в других книгах), мы приведем только необходимые сведения о них. Для того чтобы объединить несколько страниц HTML при помощи фреймов, Вам нужно подготовить специальный документ HTML, в котором описаны такие параметры фреймов, как их размер и расположение. Особенность такого документа — отсутствие на своем обычном месте области тела документа, выделенного тегами <BODY> и </BODY>. Вместо этого в файле описания фреймов присутствуют теги <FRAMESET>, </FRAMESET>, <NOFRAME> и </NOFRAME>: <html> Параметры rows и cols тега <FRAMESET> определяют размеры фреймов и задаются в виде списка значений, разделенных запятой. Вы можете определить обработчики событий onLoad и onUnload, получающие управление, соответственно, при загрузке содержимого в главное окно фрейма и при замене текущего документа HTML в этом окне на другой документ. Фактически эти обработчики относятся не к фреймам, а к окну, где эти фреймы отображаются. Для тех браузеров, которые не могут работать с фреймами, необходимо подготовить документ HTML, расположив его тело между операторами <NOFRAME> и </NOFRAME>. В этот документ стоит поместить сообщение о том, что для просмотра данной страницы Web необходимо применять более современный браузер. Рассмотрим подробнее параметры оператора <FRAMESET>, предназначенного для определения набора фреймов. Эти параметры описаны в таблице 2-4. Таблица 2-4. Параметры тега <FRAMESET>
Параметры COLS и ROWS нужны в том случае, когда фреймы, определенные в наборе, располагаются в виде таблицы. Первый из этих параметров указывает ширину колонки, а второй — высоту строки. Если фреймы располагаются в одном столбце, параметр COLS указывать не надо. Аналогично, если фреймы занимают только одну строку, не нужно указывать параметр ROWS. Вы можете задать значения для параметров COLS и ROWS либо в процентном отношении соответственно к ширине и высоте окна браузера, либо в пикселах. Если вместо значения указан символ «*», колонка или строка занимают всю оставшуюся часть окна. Например, в следующей строке задана высота первого фрейма, равная 90 пикселам, а второй фрейм занимает всю нижнюю часть окна браузера: <FRAMESET ROWS="90,*"> В следующем примере два фрейма, расположенные рядом, занимают соответственно 20% и 80% ширины окна браузера. <FRAMESET COLS="20%,80%"> Параметры оператора <FRAME> Между тегами <FRAMESET> и </FRAMESET> располагаются теги <FRAME>, определяющие параметры отдельных фреймов. Это параметры SRC и NAME. Первый задает адрес URL документа HTML, который будет загружен в данный фрейм, а второй — имя фрейма, которое можно использовать в клиентском сценарии для адресации объектов, расположенных во фрейме. Заметим, что адрес URL не должен содержать анкеры (anchor). Параметры тега <FRAME> приведены в таблице 2-5. Таблица 2-5. Параметры тега <FRAME>
Средства клиентских сценариев, составленных на языках JavaScript или VBScript, позволят Вам наделить фреймы возможностями, недостижимыми при использовании одного лишь языка разметки гипертекста HTML. Например, один из фреймов может содержать ссылки на документы, которые при активизации этих ссылок загружаются в окно другого фрейма. Клиентский сценарий позволит таким образом загружать не один документ, а одновременно несколько документов в разные фреймы. В следующем разделе мы на конкретном примере расскажем о том, как передавать данные между объектами форм, расположенных в разных фреймах. Десятично-шестнадцатеричный преобразователь В качестве примера применения клиентских сценариев для передачи данных между окнами различных фреймов мы рассмотрим десятично-шестнадцатеричный преобразователь. Внешний вид этого преобразователя показан на рис. 2-19. Рис. 2-19. Десятично-шестнадцатеричный преобразователь, выполненный с использованием фреймов На этом рисунке видно, что окно преобразователя состоит из трех фреймов. В верхнем размещен заголовок. Клавиатура преобразователя, предназначенная для ввода десятичных чисел и запуска процесса преобразования, находится в левом фрейме. Правый фрейм используется для отображения исходного десятичного числа и результата преобразования. Вы можете вводить исходное число не только с клавиатуры, но и непосредственно в поле Dec, расположенное в правом фрейме. Поле Hex заблокировано для ввода при помощи обработчика события onFocus. Исходный текст файла описания фреймов показан в листинге 2-10. Листинг 2-10. Файл ch02/Converter/index.html В нем определены фреймы нашего калькулятора: <frameset ROWS="85,*" frameborder=1> Наш сценарий будет работать с фреймами toc и mainpage, хранящимися соответственно в файлах с именами toc.html и main.html. В файле title.html содержится заголовок (листинг 2-11). Листинг 2-11. Файл ch02/Converter/title.html Исходный текст документа, содержащего форму с полями Dec и Hex, представлен в листинге 2-12. Листинг 2-12. Файл ch02/Converter/main.html Форма определена следующим образом: <form name="Sel"> Для поля исходного десятичного числа при помощи параметра NAME мы задали имя decValue. Поле результата называется hexValue. Эти имена используются сценарием JavaScript для адресации наших полей. Документ toc.html (листинг 2-13) содержит форму с кнопками и функции сценария. Листинг 2-13. Файл ch02/Converter/toc.html Рассмотрим работу сценария в нашем десятично-шестнадцатеричном преобразователе. Главная особенность этого приложения — то, что поля для ввода и отображения преобразуемых чисел располагаются в разных документах HTML, загруженных в отдельные фреймы. Для того чтобы проинициализировать поля hexValue и decValue, мы ссылаемся на форму, расположенную внутри фрейма mainpage: parent.mainpage.document.forms[0].hexValue.value =
""; Здесь parent ссылается на объект, который является родительским по отношению к документу HTML, содержащему сценарий. В данном случае это окно, в котором отображаются все наши фреймы. Для чтения содержимого поля decValue применяется аналогичная техника: szOld = parent.mainpage.document.forms[0].decValue.value; Обратите внимание, что для текстового поля hexValue мы предусмотрели обработчик событий onFocus. Он получает управление, когда пользователь передает полю фокус ввода. Задача обработчика заключается в том, чтобы снова отобрать фокус ввода, предотвратив непосредственное редактирование числа пользователем. Теперь о том, как выполняется ввод преобразуемых десятичных чисел. С каждой из кнопок, связанной с вводом десятичного числа, связан обработчик события onClick, вызывающий функцию putNumber, например: INPUT TYPE="button" NAME="3" VALUE=" 3 " onClick="putNumber(this,this.form);"> Этой функции передаются два параметра — нажатая кнопка (как объект класса button) и форма, в которой эта кнопка находится: function putNumber(btn,form) Задача функции putNumber — ввод числа и его отображение в двух текстовых полях, расположенных в верхней части калькулятора: function putNumber(btn,form) В самом начале своей работы функция putNumber проверяет двоичную переменную newnumber. Если ее значение равно true, пользователь может ввести первую цифру нового числа. В этом случае функция putNumber обнуляет содержимое текстовых полей hexValue и decValue, а также устанавливает значение newnumber, равное false. Далее функция проставляет введенную пользователем цифру перед переменной szOld, равной текущему значению из поля decValue. При этом она вызывает метод concat из класса String, предназначенный для слияния (конкатенации) строк. На следующем этапе текущее значение вычисляется функцией eval. Эта функция пытается интерпретировать текстовую строку, переданную ей в качестве параметра, как арифметическое выражение, возвращая результат интерпретации в виде численного значения. Результат сохраняется в переменной nCurrent и отображается в текстовом поле decValue. Функция getResult, выполняющая десятично-шестнадцатеричное преобразование, получает исходное число из поля decValue и передает его функции dec2hex . Результат преобразования записывается затем в поле hexValue: function getResult(form) Рассмотрим функцию dec2hex, преобразующую десятичное число в шестнадцатеричное. Результат преобразования эта функция возвращает в виде текстовой строки: function dec2hex(nDec) В начале своей работы функция dec2hex проверяет знак исходного числа. Отрицательные числа преобразуются в положительные. При этом в переменную bNegative записывается значение true. Алгоритм преобразования десятичного числа в шестнадцатеричное основан на делении исходного числа на 16 в цикле. Если целая часть результата деления, вычисляемая методом Math.floor, оказывается меньше 16, цикл завершается. В противном случае остаток от деления рассматривается как значение текущего шестнадцатеричного разряда. Для того чтобы получить символическое представление шестнадцатеричного числа по его значению, мы извлекаем нужный символ из строки szHexTable, вызывая для этого метод charAt: szBuf=szHexTable.charAt(nRem); По завершении цикла функция вычисляет старшие разряды результата, а также корректирует знак этого результата в соответствии с состоянием переменной bNegative. Одновременная замена нескольких документов HTML в окнах разных фреймов Еще одна задача, для решения которой можно с успехом применять клиентские сценарии, связана с одновременным отображением нескольких документов HTML в окнах разных фреймов. Рассмотрим следующую ситуацию. Предположим, мы готовим страницу с тремя фреймами. Верхний фрейм содержит заголовок, левый — некоторое подобие оглавления и, наконец, правый — показывает содержимое. Щелкая кнопки, расположенные в левом фрейме, Вы можете просматривать в правой части окна различные документы HTML (рис. 2-20). Рис. 2-20. Главная страница с тремя фреймами С помощью клиентского сценария мы отобразим аннотацию на материал, представленный в правом фрейме, во фрейме заголовка, расположенного в верхней части окна. Если Вы щелкнете кнопку Добро пожаловать, в заголовке появится наш логотип. Если же щелкнете кнопку Книги или Статьи, заголовок будет выглядеть так, как это показано на рис. 2-21 и 2-22 соответственно. Рис. 2-21. В результате щелчка кнопки Книги изменилось содержимое правого и верхнего фрейма Рис. 2-22. Теперь мы просматриваем информацию о статьях В листинге 2-14 мы показали исходный текст файла описания фреймов index.html. Листинг 2-14. Файл ch02/ourCD/index.html Так же как и в предыдущем примере, здесь определены три фрейма: <FRAMESET ROWS="85,*" FRAMEBORDER=1> Документ HTML, загружаемый в окно фрейма заголовка и отображающийся сразу после загрузки фрейма (а также после того, как пользователь щелкнет кнопку Добро пожаловать), показан в листинге 2-15. Листинг 2-15. Файл ch02/ourCD/title.html Файл main.html представлен в листинге 2-16. Он не имеет никаких интересных особенностей. Листинг 2-16. Файл ch02/ourCD/main.html Гораздо важней для нас файл toc.html. В этом файле находятся функции сценария JavaScript и ссылки на другие документы HTML. Этот файл показан в листинге 2-17. Листинг 2-17. Файл ch02/ourCD/toc.html Функция loadPage загружает в фреймы mainpage и title документы HTML, адреса URL которых передаются ей через параметры: function loadPage(szNewURL,szTitle) Чтобы загрузить документ мы устанавливаем свойство location.href окна соответствующего фрейма: parent.mainpage.window.location.href=szNewURL; Для вызова функции loadPage мы используем следующую конструкцию: <A HREF="javascript:loadPage('main.html',
'title.html');"> Здесь в параметре HREF тега ссылки <A> после ключевого слова javascript мы расположили строку вызова функции. Обратите внимание на применение одинарных и двойных кавычек. Так как в сценариях JavaScript вложение одинаковых кавычек недопустимо, для строк, передаваемых функции в качестве параметров, мы применяем одинарные кавычки. Значение же параметра HREF выделено при этом двойными кавычками. Использование растровых изображений Растровые изображения в виде файлов формата GIF и JPEG широко применяются в документах HTML, так как они позволяют значительно улучшить внешний вид страниц серверов Web. К сожалению, возможности HTML не позволяют добиться достаточно сложных видеоэффектов без применения дополнительных средств — аплетов Java, элементов управления ActiveX и клиентских сценариев. Фактически, кроме статической графики Вы можете использовать только анимационные изображения, построенные с применением многосекционных файлов GIF, и сегментированные графические изображения, нужные для создания ссылок. В этом разделе мы рассмотрим некоторые возможности графического оформления страниц серверов Web, которые станут Вам доступны при использовании клиентских сценариев. Снова заметим, что применять описанные здесь приемы нужно осмотрительно, так как пользователь может запретить работу сценариев при настройке своего браузера. Растровое изображение как объект Для того чтобы встроить растровое изображение в документ HTML, необходимо использовать тег <IMG>. Общий вид этого тега показан ниже: <IMG SRC="Адрес_файла_изображения" Здесь мы указали только три параметра. Полный список параметров тега <IMG> с кратким их описанием Вы найдете в таблице 2-6. Таблица 2-6. Параметры тега <IMG>
Параметры тега <IMG> определяют адрес файла с изображением, выравнивание текста, расположенного возле изображения и т. д. С помощью параметров HEIGHT и WIDTH выполняется масштабирование графических изображений. Значение этих параметров указано в процентах от ширины окна просмотра. Масштабирование позволяет подготовить графический файл весьма небольшого размера: он занимает значительную площадь в окне браузера, но быстро передается через Интернет. Вы, однако, не вправе масштабировать сегментированные графические изображения и фоновые изображения. Если в документе HTML размещено несколько растровых изображений, то Вы можете адресовать соответствующие объекты как элементы массива document.images. Например, первое изображение адресуется следующим образом: document.images[0]. Однако в некоторых случаях удобнее пользоваться именами изображений, определенными параметром NAME оператора <IMG>. Объект-изображение имеет свойство src, соответствующее параметру SRC оператора <IMG>. Адресуясь к этому свойству, Вы можете не только определять текущий адрес URL изображения, но и задавать новый. Этим мы и воспользуемся далее. Динамическая замена растровых изображений Одна из наиболее интересных возможностей, доступных при использовании клиентских сценариев, заключается в динамической замене графических изображений, указанных в параметре SRC оператора <IMG>. Например, в следующей строке сценария мы указываем, что изображение с именем btn1 должно иметь адрес «pic/aurap.gif»: document.btn1.src="pic/aurap.gif" Здесь мы указали неполный адрес URL, однако, можно указывать и полный адрес. Что произойдет при выполнении этой строки сценария? Область, выделенная в окне браузера для растрового изображения btn1, будет заполнена изображением pic/aurap.gif. Если до этого там было другое изображение, оно будет заменено новым. Какие возможности предоставляет динамическая замена растровых изображений? Во-первых, Вы можете создавать графические ссылки, которые изменяют свой вид, когда над ними установлен курсор мыши. Во-вторых, заменой растровых изображений в клиентском сценарии Вы сможете создавать анимационные изображения. Рассмотрим примеры сценариев, иллюстрирующих эти возможности. Изменение внешнего вида графических ссылок В документе HTML, изображенном на рис. 2-23, находятся две кнопки, созданные как растровые графические изображения. Они используются для активизации ссылок, соответствующих двум другим документам HTML. Рис. 2-23. Кнопка с надписью АУРАМЕДИА изменила свой цвет Если установить курсор над одной из кнопок, надпись на соответствующей кнопке изменит свой цвет. Это достигается динамической заменой графического изображения кнопки при помощи клиентского сценария. Обратите внимание на исходный текст документа HTML, Листинг 2-17. Файл ch02/grbutton/grbutton.html Для создания ссылок мы воспользовались тегом <A>. Он применяется здесь совместно с тегом <IMG>, поэтому ссылка отображается как графическое изображение. Для тега ссылки <A> мы определили обработчики событий onMouseOver и onMouseOut: onMouseOver="document.btn1.src='pic/aurap.gif'"
Когда курсор мыши оказывается над ссылкой (то есть над графическим изображением ссылки), управление получает обработчик события onMouseOver. Этот обработчик загружает изображение pic/aurap.gif, где слово АУРАМЕДИА написано черным цветом (для второй кнопки в аналогичной ситуации загружается изображение pic/softcatp.gif). После того как пользователь убирает курсор мыши от кнопки, в дело включается обработчик события onMouseOut. Он восстанавливает исходное изображение, указанное в параметре SRC тега <IMG>. Создание анимационных изображений В следующем примере мы покажем, как, используя динамическую смену растровых графических изображений в клиентском сценарии, можно получить эффект анимации. На рис. 2-24 мы показали документ HTML именно с такой анимацией. Рис. 2-24. Анимация с помощью клиентского сценария В окне браузера последовательно отображаются кадры анимационного изображения (рис. 2-25), причем сначала в прямой, а затем — в обратной последовательности. Это выглядит так, как будто слово «Noise» периодически тонет в цветном «шуме» и затем проявляется вновь. Рис. 2-25. Изображения отдельных кадров анимационной последовательности Также обратите внимание вот на что: чтобы получить подобный эффект при помощи многосекционного файла GIF, размер этого файла надо удвоить. Причина заключается в том, что Вам придется включить в файл кадры вначале в прямой, а затем в обратной последовательности. Клиентский сценарий позволяет более тонко управлять процессом отображения кадров, причем относительно простыми средствами, в результате этого Вам станут доступны достаточно сложные визуальные эффекты. Исходный текст документа HTML, в котором имеется сценарий, выполняющий анимацию, показан в листинге 2-18. Листинг 2-18. Файл ch02/noise/noise.html В теле документа с помощью тега <IMG> мы разместили первый кадр анимационной последовательности: <IMG SRC="img01.gif" NAME="Img"> С помощью параметра NAME мы задали имя Img. Его использует сценарий для ссылки на объект. Кроме того, в теле нашего документа находится вызов функции showNextImage: <body BGCOLOR=white> Она предназначена для отображения очередного кадра анимационной последовательности в окне бразуера. Вот исходный текст функции showNextImage: function showNextImage() В области заголовка документа HTML находится определение функции showNextImage и двух глобальных переменных: var i=1; Переменная i хранит номер текущего кадра, отображаемого в окне браузера. Этот номер вначале увеличивается функцией showNextImage от 1 до 16, а затем снова уменьшается до 1. Изменение номера происходит на 1 (в ту или иную сторону) при каждом вызове функции showNextImage. В переменной bForward хранится направление изменения номера кадра. Значение true соответствует прямому направлению, а значение false — обратному. Когда функция showNextImage получает управление, она анализирует содержимое переменной bForward. Если в этой переменной находится значение true, функция showNextImage увеличивает значение переменной i, а затем сравнивает результат с числом 17. Когда отображение всех кадров в прямой последовательности завершено, в переменную bForward записывается false, после чего при следующем вызове функции showNextImage номер текущего кадра не увеличится, а уменьшится. Для отображения очередного кадра функция showNextImage изменяет значение свойства src изображения document.Img, как это показано ниже: document.Img.src= "img0" + i + ".gif"; Имя файла, в котором хранится изображение кадра, конструируется из строки «img0», номера кадра, и строки «.gif». Последнее, что делает функция showNextImage, перед тем как возвратить управление, — вызывает функцию setTimeout: setTimeout("showNextImage()", 100); Напомним, что функция setTimeout устанавливает таймер. Задержка срабатывания таймера определяется вторым параметром и в нашем случае равна 100 миллисекундам. Когда таймер включится, начнется выполнение строки сценария, которая была передана функции setTimeout в качестве первого параметра. Мы вызываем после окончания задержки функцию showNextImage и, таким образом, обеспечиваем вызов этой функции в бесконечном цикле. Ожидание загрузки всех изображений Если Вы собираетесь размещать в своем документе HTML анимационное изображение, состоящее из отдельных кадров, которые, в свою очередь, расположены в отдельных файлах, возникает одна проблема. Она связана с трудностью определения времени загрузки всех изображений анимационной последовательности через медленные и нестабильные каналы Интернета. Чтобы анимационное изображение отобразилось без искажений, необходимо вначале дождаться завершения процесса загрузки файлов отдельных кадров и лишь затем запускать анимацию. В листинге 2-19 мы привели исходный текст документа HTML со сценарием, который работает подобным образом. Листинг 2-19. Файл ch02/noise/noise2.html В теле документа HTML расположен сценарий, вызывающий последовательно функции loadAllImages и showNextImage: loadAllImages(nNumberOfImages); Функции loadAllImages в качестве параметра передается общее количество изображений в анимационной последовательности. В нашем случае оно равно 18. Задача функции loadAllImages — заполнить массив объектов класса Image: function loadAllImages(nNumberOfImages) Этот массив определен в области заголовка нашего документа HTML: var imgArray = new Array(18); Заполнение массива выполняется в цикле: var i; Для каждого элемента массива вначале с помощью ключевого слова new создается объект класса Image, а затем устанавливается значение свойства src этого объекта. Последняя операция и приводит к инициированию загрузки файла изображения, выполняемой асинхронно. После того как массив заполнен, можно вызывать функцию showNextImage: var nNumberOfImages = 18; Она идентична описанной в предыдущем примере, за исключением того, что для установки свойства src изображения Img используются элементы заранее подготовленного массива imgArray: document.Img.src = imgArray[i-1].src; Наложение фильтра на графическое изображение Способ подмены графического изображения, описанный ранее в разделе «Изменение внешнего вида графических ссылок», имеет один существенный, на наш взгляд, недостаток. Для каждого изображения Вам придется подготовить два файла, первый из которых будет соответствовать невыделенному состоянию графической ссылки, а второй — выделенному. Если таких ссылок много, это увеличит время загрузки страницы, а также объем файлов, хранящихся в каталоге Вашего сервера Web. Между тем средствами DHTML Вы можете подсветить выделенные мышью графические ссылки без удвоения объема файлов с графикой. Этого достигают, изменяя одно из свойств стиля ячейки таблицы, содержащей графическую ссылку. На рис. 2-26 показана основная страница нашего сервера Web, расположенного в Интернете по адресу http://www.glasnet.ru/~frolov. Рис. 2-26. Подсвечивание элементов графического меню средствами DHTML В левой части этой страницы расположено достаточно длинное графическое меню. Оно представляет собой набор зеленых кнопок с текстом белого цвета. Когда пользователь помещает курсор мыши над такой кнопкой, она изменяет свой цвет на серый. Как достигается такой эффект? В листинге 2-20 мы привели исходный текст файла toc.html, образующего левый фрейм главной страницы нашего сервера Web. Листинг 2-20. Файл ch02/ColorFilter/toc.html Вот фрагмент этого файла: <table border="0" width="130"
cellspacing="0" cellpadding="0"> Обратите внимание, что в теге <td> ячейки таблицы, содержащей графическую ссылку на файл main.html мы определили обработчики событий onMouseOver и onMouseOut (выделено в листинге 2-20 жирным шрифтом). Первое из них возникает, когда курсор мыши располагается над областью окна браузера, занимаемой этой ячейкой, а второе — когда курсор покидает данную область. В ответ на эти события вызываются функции GON и GOFF, исходные тексты которых приведены в листинге 2-20. Обращаясь к объекту события event.srcElement, эти функции вначале проверяют свойство tagName, которое содержит имя тега объекта, возбудившего событие. В случае изображения имя тега будет представлять собой текстовую строку «IMG». Далее функция определяет фильтр event.srcElement.style.filter, который используется при рисовании графического объекта. Функция GON устанавливает фильтр «Gray», действие которого заключается в преобразовании цветного изображения в черно-белое с градациями серого: function GON() Функция GOFF отменяет действие фильтра, записывая в соответствующее свойство пустую строку. function GOFF() Помимо «Gray», Вы можете использовать и другие фильтры, описанные в документации по DHTML, например фильтр «Invert», инвертирующий цветное изображение. Заметим, что описанный в этом разделе способ подсветки работает только в браузере Microsoft Internet Explorer. Что же касается Netscape Navigator, то он имеет другую объектную модель. Если загрузить страницу toc.html в этот браузер, подсветка перестанет работать (тем не менее ссылки будут функционировать нормально). Применение Cookie в клиентских сценариях В этом разделе мы расскажем Вам о таком важном элементе, как Cookie. Возможно, Вы слышали о нем и даже знаете, что с его помощью недобросовестные администраторы серверов Web получают несанкционированный доступ к файлам пользователей. Что такое Cookie? Скажем сразу, что с кулинарным искусством это связано мало, хотя переводится с английского языка как «печенье» или «булочка». Говоря кратко, Cookie представляет собой свойство документа HTML. Данные Cookie физически хранятся локально на компьютере пользователя, загрузившего этот документ, в виде специальных файлов. Средствами Cookie пользователь может настроить, или «приготовить», по собственному вкусу документ HTML, если для него предусмотрена такая настройка. Проще всего представить себе Cookie как набор строковых параметров, каждый из которых имеет имя и значение. Клиентский сценарий может создавать Cookie для документа HTML, определяя в нем произвольное количество параметров и задавая для них произвольные значения. Далее такой набор параметров становится принадлежностью данного конкретного документа HTML и может быть проанализирован, изменен или удален сценарием. Как мы уже говорили, основное, для чего нужен Cookie, — так это для того, чтобы предоставить пользователю возможность настроить «под себя» интерфейс активных документов HTML. Эти параметры могут анализироваться или не анализироваться сервером Web, но в любом случае они хранятся у пользователя. И, разумеется, пропадут, если пользователь, скажем, отформатирует свой жесткий диск. После этого для документа HTML их придется задавать заново. Конечно, задачу индивидуальной настройки параметров страниц можно решить и другими способами, например при помощи активных серверных страниц ASP или расширений сервера Web — типа программ CGI и приложений ISAPI. Для этого на сервере Web надо установить базу данных, хранящую параметры для всех зарегистрированных в ней пользователей. В этом случае расширение сервера Web способно динамически создавать настраиваемые документы HTML, используя для определения внешнего вида страниц параметры, хранящиеся в базе данных. Возлагая задачу хранения параметров отдельных документов HTML на пользовательский браузер, Вы сильно упрощаете задачу организации настройки диалогового интерфейса. А для этого как раз нужны Cookie и клиентские сценарии. Еще одно практическое применение Cookie — хранение товара, выбранного посетителем Вашего виртуального электронного магазина. Покупатель отмечает разный товар на разных страницах сервера. При этом полный заказ вначале сформирован и сохранен в Cookie, а затем по явному запросу пользователя переправляется на сервер. Среди других применений Cookie можно отметить сетевые игры. В Cookie хранится , например, текущее состояние игры или другие параметры. При разработке приложений Web помните, что приложения ни при каких условиях не должны хранить в Cookie такую информацию, как идентификаторы пользователей и пароли, а также номера кредитных карточек. Дело в том, что эта информация может оказаться доступной администраторам серверов Web и попасть в третьи руки. Обнаружив, что Ваше приложение пытается записывать в Cookie конфиденциальную информацию, предусмотрительные пользователи, скорее всего, откажутся от работы с ним. Выполнение основных операций с Cookie Рассмотрим основные операции с Cookie, например создание Cookie, получение и изменение значений параметров Cookie, а также удаление Cookie. Существуют два способа создания Cookie, первый из которых используется расширениями сервера Web, а второй — клиентскими сценариями. Мы рассмотрим их оба. Создание Cookie расширением сервера Web Для того чтобы создать Cookie первым способом, расширение сервера Web обычно добавляет в заголовок HTTP динамически создаваемого документа HTML поле с именем Set-Cookie. В нем определяются имена и значения параметров Cookie. Когда расширение сервера Web вызывается из документа HTML, имеющего Cookie, параметры Cookie предаются этому расширению через поле Cookie заголовка HTTP и могут быть проанализированы. Заголовок HTTP, предназначенный для создания Cookie, выглядит следующим образом: Set-Cookie: Имя=Значение; expires=Дата_GMT; Описание отдельных полей заголовка Set-Cookie приведено в таблице 2-7. Таблица 2-7. Поля заголовка Set-Cookie
Все поля, кроме первых двух (Имя и Значение), не обязательны. Дата должна быть записана в формате День_недели, ДД-Мес-ГГ ЧЧ:ММ:СС GMT, где: · День_недели — английское трехбуквенное сокращение названия дня недели (например, Mon); · ДД — номер дня недели; · Мес — английское трехбуквенное сокращение названия месяца (например, Jun); · ГГ — две последние цифры года; · ЧЧ — часы; · ММ — минуты; · СС — секунды Например, дату можно указать так: Mon, 07-Jun-93 14:45:00 GMT Сделаем небольшое замечание относительно полей domain и path, определяющих условие, при котором выполняется установка Cookie. Когда браузер загружает документ HTML с сервера Web и среди заголовков HTTP этого документа присутствует заголовок Set-Cookie, он проверяет возможность установки Cookie. В процессе проверки анализируется адрес URL, откуда был загружен этот документ, а также содержимое полей domain и path. Если эти поля не указаны, то по умолчанию считаются, что они соответствуют адресу URL, по которому находится загруженный документ HTML. В этом случае выполняется установка Cookie. Когда же указано поле domain, установка Cookie выполняется, только если документ загружен с сервера Web, принадлежащего данному домену. Средствами параметра path можно установить ограничение на адреса URL в рамках домена, для которых выполняется установка Cookie. При этом значение «/» соответствует всем адресам данного домена. Одновременно сервер Web способен создать несколько параметров Cookie, включив в заголовок документа HTML несколько заголовков Set-Cookie. Создание Cookie в клиентском сценарии Второй способ предполагает использование свойства document.cookie. Это свойство мы упомянули, рассказывая о свойствах и методах объекта document, создаваемого для документа HTML, загруженного в окно браузера. В общем виде сценарий создает Cookie следующим образом: document.cookie = "Имя=Значение"; Здесь мы просто записываем в свойство cookie объекта document текстовую строку, определяющую Cookie. Для пересчета текущей даты в формат GMT в клиентских сценариях можно использовать встроенные функции, о чем мы расскажем чуть попозже. В качестве примера ниже показан исходный текст функции addCookie, которую мы используем в своих сценариях для создания Cookie. function addCookie(szName,szValue,dtDaysExpires) Функция addCookie получает три параметра. Через параметр szName передается имя параметра, хранящегося в Cookie. Параметр szValue определяет значение этого параметра Cookie. Что же касается последнего параметра — dtDaysExpires, то он задает интервал времени по отношению к моменту создания Cookie, когда этот Cookie необходимо удалить. Самое сложное в функции addCookie — это определение даты удаления Cookie и преобразование этой даты в формат GMT. Данная задача решается следующим образом. Прежде всего, функция addCookie создает объект класса Date с помощью ключевого слова new: var dtExpires = new Date(); Записанная таким образом в переменную dtExpires дата соответствует моменту вызова функции addCookie. Далее с помощью метода getTime функция addCookie определяет текущую дату в миллисекундах и прибавляет к результату значение параметра dtDaysExpires, полученное функцией, умноженное на константу (24*60*60*1000): dtExpires.getTime() + dtDaysExpires * 24 * 60 * 60 * 1000 Константа — это количество часов в сутках, умноженное на количество минут в часе, затем на количество секунд в минуте и, наконец, на количество миллисекунд в секунде. Результат вычислений записывается при помощи метода setTime в переменную даты dtExpires. Теперь здесь хранится дата автоматического уничтожения Cookie браузером. Осталось лишь преобразовать эту дату в формат GMT. Такое преобразование нетрудно сделать с помощью специально предназначенного для этого метода toGMTString, возвращающего текстовую строку в нужном нам формате: dtExpiryDate = dtExpires.toGMTString(); Теперь нам остается только сформировать текстовую строку определения Cookie и записать ее в свойство document.cookie: document.cookie = На этом создание Cookie завершено. Теперь, когда в Вашем распоряжении есть функция addCookie, создание Cookie представляет собой очень простую задачу. Например, в следующей строке мы создаем Cookie с именем Count и значением 0, причем через 10 дней браузер автоматически удалит этот Cookie: addCookie("Count","0",10); При необходимости использования других параметров Cookie, например path или domain, Вы можете немного дополнить текст функции addCookie. С этой задачей Вы легко справитесь самостоятельно. Итак, Вы научились создавать Cookie в клиентских сценариях. Теперь попробуем решить другую задачу — определение значения параметров Cookie. Она сводится к простому сканированию текстовой строки, полученной следующим образом: var szCookieString = document.cookie; В этой строке Вам нужно найти подстроку «Имя=Значение;», а затем извлечь полученное значение. Для облегчения этой работы Вы можете воспользоваться функцией findCookie. Исходный текст этой функции приведен ниже: function findCookie(szName) После извлечения строки из свойства document.cookie и записи этой строки в переменную szCookieString функция findCookie организует циклический просмотр всех символов этой строки. Условием завершения цикла является просмотр всех символов szCookieString.length. Сравнивая имя параметра с подстрокой, извлеченной из строки szCookieString при помощи метода substring, функция findCookie пытается найти нужный параметр. Если попытка оказывается успешной, функция findCookie пропускает символ присваивания, извлекая значение параметра, ограниченное точкой с запятой. Это значение возвращается функцией findCookie. Если же поиск неудачен, функция findCookie возвращает пустую строку. Какие возможности предоставляет функция findCookie? Во-первых, она позволит Вам проверить, установлен ли для данного документа Cookie с заданным именем: if(findCookie("Visit") == "") Для того чтобы записать в текстовую переменную значение параметра Cookie с заданным именем, Вы должны сделать следующее: var szVisitValue = findCookie("Visit"); Как видите, пользоваться функцией findCookie достаточно просто. Изменение значения параметра Cookie Для изменения значения параметра Cookie с заданным именем Вы можете просто вызвать функцию addCookie еще раз: addCookie("Count","0",10); Здесь мы вначале установили для параметра Count значение 0, а затем изменили это значение на 5. Самый простой способ удалить Cookie — установить для него такое время автоматического удаления, которое уже прошло. Для этого нужно получить текущую дату, уменьшить ее, например, на одну микросекунду, а затем изменить значение document.cookie. Все это делает функция removeCookie: function removeCookie(szName) В последней строке этой функции мы указали такое значение параметра expires, при котором Cookie будет немедленно удален браузером. Ограничения на использование Cookie На использование Cookie накладываются определенные ограничения, перечисленные ниже: · всего можно создать не более 300 Cookie; · необходимо, чтобы размер каждого Cookie не превышал 4 кб; · для каждого домена может быть создано не более 20 Cookie Если указанные ограничения будут нарушены, браузер может удалить самые старые Cookie или обрезать значения параметров Cookie. В этом разделе на примере конкретных клиентских сценариев мы покажем, как можно использовать Cookie для решения различных практических задач. Фиксация повторных посещений страницы В нашем первом примере документ HTML содержит форму с двумя кнопками (рис. 2-27). Рис. 2-27. Кнопки для перехода к динамически создаваемому документу HTML и для удаления Cookie Если нажать на кнопку GO!, сценарий создаст новый документ HTML. Внешний вид его зависит от того, сколько раз пользователь нажимал на эту кнопку. Кнопка Удалить cookie предназначена для удаления Cookie, созданного в нашем документе HTML. Когда Вы нажимаете на кнопку GO! в первый раз, Cookie еще не создан. При этом генерируется документ HTML, изображенный на рис. 2-28. Рис. 2-28. Такой документ HTML создается динамически при первом посещении Во второе и последующие посещения внешний вид документа изменяется (рис. 2-29). Рис. 2-29. Такой документ HTML создается динамически при втором посещении Теперь здесь виден новый заголовок, а также содержимое параметров Cookie с именами Visit, Count, info, MidiUsed и JavaUsed. При каждом новом посещении значение параметра Count будет увеличиваться на единицу. Если же в документе, показанном на рис. 2-27, Вы нажмете кнопку Удалить cookie, подсчет посещений начнется заново. Исходный текст документа HTML показан в листинге 2-21. Листинг 2-21. Файл ch02/Again.html Функции addCookie, findCookie и removeCookie, определенные в этом документе, Вам уже знакомы. Они предназначены для создания Cookie, извлечения значения заданного параметра Cookie и удаления Cookie соответственно. Функция btnClick вызывается, когда пользователь нажимает в форме кнопку GO!: function btnClick() Прежде всего, эта функция ищет параметр Cookie с именем Visit. Если такой параметр не найден, считается, что страница посещается в первый раз. В этом случае функция btnClick создает параметры Cookie с именами Visit и Count, а затем формирует текст документа HTML с приглашением: addCookie("Visit","Alexandr_Frolov",10); Когда пользователь посещает страницу повторно, параметр Cookie с именем Visit уже существует. В этом случае функция btnClick пытается найти параметр с именем Count и получить его значение: var szCnt = findCookie("Count"); Это значение затем увеличивается на единицу и записывается обратно в параметр Cookie с именем Count: i = szCnt; Завершая свою работу, функция btnClick записывает приглашение для повторно посетивших страницу пользователей и отображает содержимое свойства document.cookie: document.write("<H2>You are welcome
AGAIN!</H2>"); Обработчик события onClick кнопки Удалить cookie вызывает функцию removeCookie для параметров Cookie с именами Count и Visit, удаляя их: <INPUT TYPE="button" VALUE="Remove
All Cookies" Записная книжка Cookie Notepad В следующем примере мы применили Cookie для хранения произвольного текста, набранного пользователем в многострочном окне редактирования (рис. 2-30). Рис. 2-30. Документ с записной книжкой Cookie Notepad При первой загрузке документа HTML с записной книжкой окно редактирования остается пустым. Вы можете набрать здесь любой текст и записать его в Cookie, щелкнув кнопку Сохранить текст. Если теперь Вы закроете документ HTML и откроете его вновь, набранный Вами ранее текст появится в окне редактирования. Для того чтобы удалить текст и Cookie, достаточно щелкнуть кнопку Удалить текст. Исходный текст документа HTML с записной книжкой Cookie Notepad показан в листинге 2-22. Листинг 2-22. Файл ch02/Notebook.html Функция addCookie, использованная нами здесь, имеет одну особенность: перед записью текстовой строки в параметр Cookie она выполняет ее кодировку в формате URL, вызывая для этого функцию escape: document.cookie = szName + "=" + escape(szValue) + "; expires=" + dtExpiryDate; Это необходимо по той причине, что введенный в окне редактирования текст может содержать пробелы и любые другие символы. Аналогичные изменения мы внесли и в функцию findCookie. Она возвращает значение, перекодированное в обычный текст функцией unescape, выполняющей действия противоположные действиям функции escape: szTemp = document.cookie.substring( Когда пользователь нажимает кнопку Сохранить текст, вызывается функция btnClick: function btnClick() Эта функция просто записывает в параметр Cookie с именем MyText текстовую строку, извлеченную из многострочного поля редактирования TestForm.Comment.value. При удалении текста кнопкой Удалить текст вызывается функция removeCookie, удаляющая параметр Cookie с именем MyText, а также записывается пустая строка в окно многострочного редактирования: <INPUT TYPE="button" VALUE="Clear
text" В самом конце тела документа HTML находится небольшой фрагмент сценария, запускающийся сразу после загрузки этого документа: var szMyText=""; Этот фрагмент пытается получить значение параметра Cookie с именем MyText. Если это ему удается и функция findCookie возвращает непустую строку, полученная строка записывается в окно многострочного поля редактирования TestForm.Comment.value. В результате сразу после загрузки документа это окно оказывается заполненным текстом, сохраненным в Cookie. Вы можете посмотреть системный файл, хранящий данные Cookie. Для этого откройте каталог Temporary Internet Files, расположенный в системном каталоге Microsoft Windows 95 или в каталоге %systemroot%\Profiles\<имя_пользователя>\Cookies операционной системы Microsoft Windows NT (здесь %systemroot% — системный каталог Microsoft Windows NT). Вы можете скопировать файлы Cookie, например, на поверхность рабочего стола и открыть для просмотра любым текстовым редактором. То, что Вы увидите, показано ниже (содержимое файлов Cookie меняется в зависимости от операционной системы и версии браузера): Visit В самом начале файла видно имя Visit параметра Cookie. На следующих строках находятся значения других параметров, отделенные друг от друга строкой ~~local~~/E:\!Russian Edition\InternetDB\Src\ch02\. Для записи символов кириллицы здесь использована кодировка URL. Если удалить этот файл и затем открыть документ HTML, многострочное окно редактирования будет пустым. Удалив этот файл, мы удалим и расположенный в нем Cookie. Настройка параметров документа HTML Следующий пример демонстрирует, как можно использовать Cookie для настройки пользователем параметров документа HTML. На рис. 2-31 показан документ HTML с двумя кнопками и переключателем, имеющим зависимую фиксацию. Рис. 2-31. Главный документ HTML, позволяющий выполнить настройку Если Вы нажмете верхнюю кнопку, то в окне браузера появится документ HTML, созданный динамически клиентским сценарием. В первый раз этот документ будет таким, как показано на рис. 2-32. Рис. 2-32. Внешний вид документа при первом посещении Переключатели позволят Вам выбрать один из четырех цветов фона документа. Это значение будет храниться в Cookie. Для того чтобы вернуться к цвету, принятому по умолчанию, в документе HTML, показанному на рис. 2-31, нужно нажать кнопку Параметры по умолчанию. При последующих посещениях внешний вид документа изменится (рис. 2-33). Рис. 2.33. Внешний вид документа при третьем посещении Его фон будет иметь такой цвет, какой был задан при помощи переключателей. Исходный текст документа HTML показан в листинге 2-23. Листинг 2-23. Файл ch02/CustomPage.html Помимо функций addCookie, findCookie и removeCookie, предназначенных для работы с Cookie, в сценарии определена переменная szColor, предназначенная для хранения выбранного пользователем цвета фона, а также функции btnGo, chkRadio и setDefault. Функция btnGo прежде всего проверяет наличие параметра Cookie с именем Count: function btnGo() Если такого параметра нет, сценарий считает, что пользователь просматривает этот документ в первый раз. В этом случае функция btnGo добавляет два параметра Cookie с именами Count и bgColor: addCookie("Count","0",10); Первый из них предназначен для хранения счетчика посещений, а второй — для хранения цвета фона. Далее функция btnGo формирует документ HTML с приглашением для пользователя, просматривающего документ в первый раз, и завершает свою работу. В том случае, когда сразу после вызова функция btnGo нашла параметр Cookie с именем Count и получила его значение, это значение увеличивается на единицу и записывается обратно. Кроме того, оно отображается в тексте документа: document.write("<H2>Рады видеть Вас
снова!</H2>"); Затем функция btnGo устанавливает цвет фона сформированного документа HTML в соответствии со значением, извлеченным из параметра Cookie с именем bgColor: document.bgColor=findCookie("bgColor"); Функция chkRadio вызывается, когда пользователь отмечает один из переключателей выбора цвета: function chkRadio(form,value) Эта функция записывает значение выбранного цвета в переменную szColor, а также в параметр Cookie с именем bgColor. И, наконец, функция setDefault удаляет параметр Cookie с именем Count и устанавливает в переменной szColor белый цвет фона, принятый по умолчанию: function setDefault(form) Эта функция вызывается, когда пользователь нажимает кнопку с надписью Параметры по умолчанию: <INPUT TYPE="reset" VALUE="Параметры
по умолчанию" Обратите внимание, что данная кнопка имеет тип reset. Когда пользователь ее щелкает, в форме отмечается переключатель, задающий белый цвет фона. Это происходит потому, что указанный переключатель определен с параметром CHECKED, а кнопка типа reset устанавливает все органы управления формы в исходное состояние. Настройка браузера для работы с Cookie Хотя Cookie не представляют особой опасности для пользователей, не каждый захочет, чтобы хранящаяся в них информация передавалась на сервер Web. В сочетании с другими полями заголовка HTTP данные Cookie позволяют собирать определенную статистику о пользователях, а это нравится далеко не всем. Настраивая браузер соответствующим образом, пользователи могут ограничить или вовсе отключить взаимодействие с Cookie. Вы должны это учитывать, если при создании активных документов HTML надеетесь на использование Cookie. Браузер Microsoft Internet Explorer версии 5.0 допускает установку различных режимов работы с Cookie. Эти режимы указываются в панели Security Settings на вкладке Security блокнота Internet Options (рис. 2-34), доступного из меню Tools. Рис. 2-34. Установка режимов работы с Cookie По умолчанию активизирован переключатель Enable, разрешающий применение Cookie. Переключатель Disable полностью запрещает использование Cookie. Если Вы пометите переключатель Prompt, при попытке установить Cookie на экране появится предупреждающее сообщение. Если Вы установили Microsoft InterDev 6.0, отладка клиентских сценариев не вызовет у Вас особых сложностей. Запустите браузер Microsoft Internet Explorer и выберите из меню View строку Script Debugger. Далее в меню второго уровня укажите строку Break at Next Statement. Теперь браузер подготовлен к запуску сценария под отладкой. Загрузите в окно браузера документ HTML с отлаживаемым сценарием. Это можно сделать, перетаскивая мышью пиктограмму документа в окно браузера или средствами меню File браузера. Как только будет выполнена любая строка клиентского сценария, запустится отладчик сценариев, встроенный в Microsoft InterDev 6.0. Вы увидите диалоговую панель Microsoft Development Environment, в которой Вам придется подтвердить необходимость запуска сценария под отладкой, щелкнув кнопку Yes. Когда Вы увидите вторую панель с запросом на открытие файла проекта, откажитесь от этой операции, щелкнув кнопку No. В результате отобразится окно отладчика Microsoft InterDev 6.0, в которое будет загружен исходный текст документа со сценарием. Строка, на которой произошел останов, выделена цветом. Используя кнопки инструментальной панели, Вы сможете поэтапно выполнять сценарий, устанавливать дополнительные точки останова, просматривать содержимое локальных переменных и т. д. Подробное описание приемов работы с отладчиком выходит за рамки нашей книги. При необходимости воспользуйтесь электронной справочной системой, встроенной в Microsoft InterDev 6.0. |