Опубликован: 04.11.2006 | Уровень: специалист | Доступ: платный
Урок 14:

Динамическое управление фильмами-символами

Построение кнопок с непрерывной обратной связью

Порой возникает необходимость в том, чтобы некие действия выполнялись непрерывно, пока нажата кнопка. Кнопки, запрограммированные таким образом, называют кнопками с непрерывной обратной связью; прекрасным примером будут кнопки прокрутки (тема данного упражнения).

Примечание В большинстве случаев реализовать прокрутку гораздо проще с помощью компонента Scrollbar (полоса прокрутки). Это упражнение имеет целью разъяснить вам, как вообще программируется и работает прокрутка – тогда вы сможете, при желании, внедрить собственные идеи вместо стандартных решений.

Если информации в окне при каждом нажатии на соответствующую кнопку будет прокручиваться на одну строку, пользователь быстро устанет. Гораздо удобнее, если прокрутка при нажатой кнопке происходит непрерывно, и прекращается, когда кнопка отпущена. Во Flash это можно реализовать (вскоре мы это продемонстрируем) с помощью событий клипа enterFrame или mouseMove.

В этом упражнении мы с вами добавим кнопки прокрутки к списку, построенному нами в предыдущем упражнении.

  1. Откройте файл scrollingList2.fla из папки Lesson14/Assets.

Этот файл должен быть вам хорошо знаком – в таком виде мы оставили его по завершении предыдущего упражнения. В этом упражнении мы добавим действия ActionScript в кадр 1 слоя Actions главного монтажного стола, к самим кнопкам прокрутки, а также к клипам, содержащим эти кнопки. Первым делом мы создадим функцию, выполняющую собственно прокрутку, а затем поместим в нужные места команды вызова этой функции.

Напомним, что здесь имеется экземпляр клипа list, расположенный внутри клипа display. Все вновь создаваемые экземпляры (клипа infoBar ) помещаются в экземпляр list. Таким образом, нашей функции достаточно будет перемещать по вертикали экземпляр клипа list, чтобы создать эффект прокрутки списка.

Примечание В этом упражнении, используя термин "прокрутка", мы будем подразумевать перемещение по экрану вверх и вниз фильма-символа list путем изменения значения его свойства _y.

  1. Откройте панель Действия, выделите кадр 1 слоя Actions и добавьте сразу после строки, создающей массив list, следующую строку скрипта:
startingY = display.list._y;

Для правильной работы прокрутки мы должны установить максимальное и минимальное положения ( Y ), списка – задать границы прокрутки списка (вертикального перемещения). В любом приложении, где используется прокрутка, необходимо предотвращать возможность прокрутку за пределы документа. Добавленная нами строка скрипта будет использоваться для установления одной из этих вертикальных границ: прокрутка экземпляра клипа list (содержащий присоединенные экземпляры) должна прекращаться, если его Y-координата достигла стартовой Y-координаты ( startingY ). C этой целью мы и используем сейчас значение переменной startingY.


  1. Вставьте в кадр 1, сразу после предыдущей строки, строку bottom=120; – это будет второй ограничитель прокрутки.

Как было сказано на предыдущем шаге, наибольшая возможная Y-координата прокрутки экземпляра клипа list – это его стартовая позиция. Переменная bottom, которую мы определяем на этом шаге, будет содержать значение координаты такое, чтобы самый нижний элемент списка не мог выйти за пределы окна. Каким образом это будет достигаться, вы поймете из следующих шагов.

  1. Начнем описание функции, осуществляющей прокрутку экземпляра клипа. Для этого в кадр 1, сразу после описания функции buildList(), вставьте следующие строки:
function scroll (direction) {
  speed = 10;
}

Впоследствии мы организуем вызов этой функции в нашем проекте посредством события enterFrame, присоединенного к экземплярам клипов, содержащих кнопки прокрутки. Одна из кнопок будет предназначена для прокрутки вверх, другая – вниз. Параметр direction, передаваемый этой функции, будет содержать строковое значение: "up" или "down". Условный оператор (который мы сейчас добавим), в зависимости от значения этого параметра будет выполнять действия, предназначенные для прокрутки экземпляра list вверх или вниз. Переменная speed – скорость прокрутки. Пока одна из кнопок удерживается в нажатом положении, экземпляр list будет перемещаться (либо вверх, либо вниз). Скорость его перемещения и определяется значением переменной speed. Кстати, число 10 взято вовсе не из каких-то "высших соображений"; если хотите, можете взять другое значение.

  1. В описание функции, сразу после строки speed = 10;, добавьте оператор if/else if:
if (direction == "up") {
} else if (direction == "down") {
}

Как мы уже сказали, direction передается функции в качестве параметра и может принимать строковые значения "up" либо "down". Данный условный оператор будет определять действия, выполняемые функцией, в зависимости от значения этого параметра. На следующих шагах мы вставим в каждую секцию этого условного оператора свой набор действий, осуществляющий прокрутку в том или ином направлении.

  1. В секцию оператора if для значения "up" поместите следующий набор действий:
if (display.list._y – speed + display.list._height > (startingY + bottom)) {
  display.list._y -= speed;
} else {
  display.list._y = (startingY + bottom) – display.list._height;
}

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

В условии оператора проверяется, где окажется нижняя грань экземпляра list при перемещении его на 10 пикселей вверх. Вычисляется это так: берется текущая Y-координата экземпляра list, из нее вычитается значение speed, затем прибавляется общая высота экземпляра. Полученная координата нижней грани экземпляра сравнивается с одним из ограничителей прокрутки (который получается путем сложения значений bottom и startingY ). Если в результате перемещения экземпляра list он не достиг ограничителя, то все в порядке – выполняется действие из первой секции оператора, движение экземпляра продолжается. Если же экземпляр дошел до ограничителя, выполняется секция else, и экземпляр попросту устанавливается в максимальную разрешенную координату по вертикали.


Если все это вам не совсем понятно, не расстраивайтесь: сейчас мы рассмотрим на примере, как все это работает. Для этого предположим, что элементы нашего скрипта имеют следующие значения:

speed = 10
startingX = 100
bottom = 120
display.list._height = 400 //высота (размер по вертикали) экземпляра list
display.list._y = -165 //текущая координата экземпляра list по вертикали

С этими значениями условное выражение в операторе if будет выглядеть следующим образом:

if (-165 – 10 + 400 > (100 + 120))

В итоге получим:

if (225 > 220)

Поскольку 225 больше 220, выполняется следующее действие:

display.list._y -= speed;

Тем самым экземпляр list переместится на 10 пикселей вверх, и его Y-координата станет равна -175. Теперь, при следующем выполнении условного оператора, мы получим:

if (-175 – 10 + 400 > (100 + 120))

И, в итоге:

if (215 > 220)

Утверждение ложно, ведь 215 меньше 220, поэтому выполняется действие из секции else:

display.list._y = (startingY + bottom) – display.list._height;

Экземпляр list помещается в Y-координату, значение которой вычисляется в правой части этого выражения:

(startingY + bottom) – display.list._height

Подставляя наши значения, получим:

(100 + 120) – 400

Это даст

220 - 400

И в итоге

-180

Тем самым экземпляр list будет привязан к вертикальной координате -180 – нижняя грань экземпляра будет совмещена к верхнему ограничителю прокрутки – дальнейшая прокрутка экземпляра list невозможна.

Теперь давайте настроим обработку прокрутки вниз.

  1. В секцию оператора if/else для значения "down" поместите вложенный оператор if/else if:
if (display.list._y + speed < startingY) {
  display.list._y += speed;
} else {
  display.list._y = startingY;
}

Эта часть условного оператора будет обслуживать прокрутку экземпляра клипа вниз. Похоже на то, что было на предыдущем шаге, только здесь условный оператор следит, чтобы экземпляр list при перемещении вниз на значение speed (display.list._y += speed) не вышел за нижний ограничитель прокрутки ( startingY ). Если этого не произошло, выполняется действие из первой секции оператора, перемещающее экземпляр клипа вниз. В противном случае ( else ) нижняя грань экземпляра совмещается с нижним ограничителем прокрутки.

Описание функции мы закончили, теперь пора поработать с кнопками прокрутки.

  1. Открыв библиотеку, сделайте двойной щелчок на фильме-символе под названием list arrow.

На экране появится кнопка Arrow, находящаяся на монтажном столе этого клипа. Эту кнопку (как и фильм-символ list arrow, частью которого она является) мы будем использовать для прокрутки в обоих направлениях – и вверх, и вниз.

  1. Открыв панель Действия, выделите кнопку и введите такой скрипт:
on (press) {
  buttonPressed = "yes";
}
on (release, releaseOutside, dragOut) {
  buttonPressed = "";
}

Эта кнопка будет попросту присваивать значение переменной buttonPressed – "yes" или "", в зависимости от действий пользователя. Если пользователь нажал эту кнопку, buttonPressed получает значение "yes". Если пользователь отпускает кнопку мыши (неважно, где при этом находится указатель – на кнопке или за ее пределами), переменная buttonPressed получает значение "". На следующем шаге мы используем значение этой переменной.

  1. Открыв библиотеку, сделайте двойной щелчок на фильме-символе под названием scroll.

Монтажный стол этого клипа содержит два экземпляра фильма-символа list arrow, который содержит кнопку Arrow, к которой мы на предыдущем шаге присоединили скрипт. Один из экземпляров развернут на 180 градусов. Верхний экземпляр носит имя down, а нижний экземпляр – up.

Как вы помните, при нажатии кнопки, имеющейся в каждом из этих двух экземпляров, переменная buttonPressed получает значение "yes". Важно понимать, что каждый из экземпляров представляет собой самостоятельный монтажный стол. Нажатие кнопки, находящейся в одном из экземпляров, изменит значение переменной buttonPressed только на этом монтажном столе; на переменную другого экземпляра это событие никак не повлияет.

  1. Открыв панель Действия, выделите экземпляр клипа down и введите такой скрипт:
onClipEvent (enterFrame) {
  if (buttonPressed == "yes") {
    _root.scroll("down");
  }
}

Мы используем событие enterFrame: ActionScript будет непрерывно (24 раза в секунду) проверять значение переменной buttonPressed на монтажном столе этого клипа, и если это значение равно "yes", будет вызывать функцию scroll() с главного монтажного стола. Это – основа принципа действия нашей кнопки с непрерывной обратной связью. Булево значение в выражении условного оператора определяется самой кнопкой. Пока переменная buttonPressed имеет значение "yes" (то бишь, пока кнопка внутри данного экземпляра нажата), происходит прокрутка. Параметр "down", передаваемый функции scroll(), дает ей знать, в каком направлении должна происходить прокрутка.

  1. Выделите экземпляр клипа up и введите в панели Действия, такой скрипт:
onClipEvent (enterFrame) {
  if (buttonPressed == "yes") {
    _root.scroll("up");
  }
}

Скрипт идентичен тому, что был на предыдущем шаге, только функции scroll() передается другое значение параметра – "up".

  1. Командой Управление > Проверить фильм (Control > Test Movie) запустите тест фильма.

Давайте пустим в дело кнопки, чтобы проверить наши скрипты. Нажмите и удерживайте кнопку "вниз", чтобы начать прокрутку, потом попробуйте другую кнопку. Как видите, когда экземпляр list достигает верхнего или нижнего предела, прокрутка останавливается.

  1. Закройте тестовый фильм и сохраните свою работу под именем scrollingList3.fla.

Итак, мы с вами в этом упражнении организовали с помощью ActionScript прокрутку динамически сформированного списка, используя кнопки с непрерывной обратной связью.

Салтанат Бектегенова
Салтанат Бектегенова

Дострочное пересдача экзамена

 

Евгений Стародубцев
Евгений Стародубцев

Вот задание:

7. Открыв панель Действия (Actions) и установив ее в Экспертный режим(Expert Mode), выделите кадр 1 слоя Actions и введите следующий скрипт:

Евгения Дегтяренко
Евгения Дегтяренко
Украина, Запорожье
Анна Елисеева
Анна Елисеева
Россия, Великий Новгород, Ногородский государственный университет имени Ярослава Мудрого, 2003