Одной из наиболее мощных DHTML_технологий, которую можно реализовать с помощью JavaScript и CSS, является анимация. В DHTML_анимации нет ниче_ го особенного – надо лишь периодически изменять одно или несколько свойств стиля одного или нескольких элементов. Чтобы, например, передвинуть изобра_ жение влево, надо постепенно увеличивать значение свойства style.left этого изображения, пока последнее не займет требуемое положение. Можно также по_ степенно изменять свойство style.clip для «открытия» изображения пиксел за пикселом.
Пример 16.5 содержит простой HTML_файл, определяющий анимируемый эле_ мент div, и короткий сценарий, изменяющий цвет фона элемента каждые 500 мил_ лисекунд. Примечательно, что изменение цвета выполняется присваиванием зна_ чения свойства CSS_стиля. Анимация возникает за счет того, что изменение цве_ та выполняется периодически с помощью функции setInterval() объекта Window.
392 Глава 16. CSS и DHTML
(Никакая DHTML_анимация не обходится без метода setInterval() или setTime_ out(); возможно, перед изучением примера вы захотите почитать об этих мето_ дах объекта Window в четвертой части книги.) И наконец, обратите внимание на использование оператора деления по модулю (получение остатка) % для перебора цветов. Тот, кто забыл, как работает этот оператор, может обратиться к главе 5.
Пример 16.5 реализует очень простую анимацию. На практике анимация с ис_ пользованием CSS_стилей обычно подразумевает одновременную модификацию нескольких свойств стилей (таких как top, left и clip). Сложную анимацию с по_ мощью технологии, показанной в примере 16.5, создать трудно. Кроме того, что_ бы не надоедать пользователю, анимация должна выполняться в течение корот_ кого периода времени и затем останавливаться, чего нельзя сказать об анимации из примера 16.5.
В примере 16.6 показан JavaScript_файл, определяющий функцию анимации на базе CSS, намного облегчающей эту задачу даже при создании сложной анимации.
Пример 16.6. Основа для создания анимации на базе CSS
/**
* AnimateCSS.js:
* Этот файл определяет функцию с именем animateCSS(), служащую основой
* для создания анимации на базе CSS. Аргументы функции:
*
* element: Анимируемый HTML_элемент.
* numFrames: Общее число кадров в анимации.
* timePerFrame: Количество миллисекунд отображения каждого кадра.
time += timePerFrame; // Увеличить прошедшее время
}
}
Функции animateCSS(), определенной в этом примере, передается пять аргумен_ тов. Первый аргумент задает анимируемый объект HTMLElement. Второй и третий аргументы задают количество кадров анимации и продолжительность времени, в течение которого должен отображаться каждый кадр. Четвертый аргумент – это JavaScript_объект, описывающий выполняемую анимацию. Пятый аргумент – это необязательная функция, которая должна быть вызвана один раз по заверше_ нии анимации.
394 Глава 16. CSS и DHTML
Ключевым является четвертый аргумент функции animateCSS(). Каждое свойст_ во JavaScript_объекта должно иметь то же имя, что и свойство CSS_стиля, а зна_ чением каждого свойства должна быть функция, возвращающая допустимое значение для стиля с этим именем. При отображении нового кадра вызывается каждая из этих функций, чтобы сгенерировать новые значения для каждого ат_ рибута стиля. Каждой функции передается номер кадра и общее время, прошед_ шее с начала анимации, и функция может использовать эти аргументы для вы_ числения нужного значения.
Код примера 16.6 достаточно прост; как мы скоро увидим, вся сложность заклю_ чена в свойствах объекта анимации, которые передаются функции animateCSS(). Функция animateCSS() определяет вложенную функцию с именем displayNext_ Frame() и почти ничего не делает, разве что с помощью setInterval() настраивает периодический вызов displayNextFrame().Функция displayNextFrame() выполняет цикл по свойствам объекта анимации и вызывает различные функции для вы_ числения новых значений свойств стиля.
Обратите внимание: поскольку функция displayNextFrame() определена внутри animateCSS(), она имеет доступ к аргументам и локальным переменным ani_ mateCSS(), несмотря даже на то, что displayNextFrame() вызывается уже после за_ вершения работы функции animateCSS()! (Если вы не понимаете, почему, верни_ тесь к разделу 8.8.)
Следующий пример должен в значительной мере прояснить применение функ_ ции animateCSS(). Данный код перемещает элемент вверх по экрану, при этом по_ степенно открывая его путем увеличения области отсечения.
// Анимируем элемент с идентификатором "title", используя 40 кадров
// по 50 миллисекунд каждый animateCSS(document.getElementById("title"), 40, 50,
{ // Так устанавливаются свойства top и clip для каждого кадра: top: function(f,t) { return 300f*5 + "px"; }
clip: function(f,t) {return "rect(auto "+f*10+"px auto auto)";}, });
Следующий фрагмент кода с помощью функции animateCSS() перемещает объект Button по кругу. Необязательный пятый аргумент передается функции для изме_ нения текста кнопки на «Готово», когда анимация завершается. Функции, ука_ занной пятым аргументом, в качестве аргумента передается анимируемый эле_ мент:
// Перемещаем кнопку по кругу, а затем изменяем выводимый на ней текст animateCSS(document.forms[0].elements[0], 40, 50, // Кнопка, 40 кадров, 50 мс
{ // Эта тригонометрия определяет круг радиусом 100 и с центром // в точке (200,200):
В JavaScript_библиотеке Scriptaculos представляет собой достаточно сложную платформу для создания анимации с множеством предопределенных интерес_ ных анимационных эффектов. Чтобы узнать об этой библиотеке, посетите сайт с остроумным названием http://script.aculo.us/.