Drupal Ajax framework

Drupal's Ajax Framework используется для динамического обновления частей HTML страницы на основе данных полученных с сервера. Во время определенного события, например нажатия кнопки, срабатывает callback функция которая исполняет код на сервере и возвращает обновленную разметку, которая будет заменять старую на лету без перезагрузки страницы.

Этот фреймворк создает PHP макро язык который позволяет серверу объяснить JavaScript какие действия необходимо выполнить на клиентской части. При работе с формами фреймворк можно использовать с помощью свойства #ajax. Свойство #ajax используется для привязки событий к Ajax framework. По умолчанию, #ajax использует "system/ajax" как путь для отправки который вызывает ajax_form_callback() и определенную в #ajax["callback"] функцию. Тем не менее, вы можете задать другой путь для вызова или другую callback функцию, которая может возвращать обновленный HTML или новый набор команд типа Ajax framework commands.

Стандартная последовательность работы фреймворка:

  • Элемент формы имеет свойство #ajax которое включает параметр #ajax["callback"] без указания #ajax["path"]. Параметр #ajax["path"] который позволяет создавать расширенный функционал будет описан ниже.
  • Во время изменения элемента запускаетсяAjax обработка.
  • Браузер отправляет HTTP POST запрос по пути "system/ajax" .
  • Меню callback для "system/ajax", ajax_form_callback(), вызывает drupal_process_form() для обработки и изменения отправленной формы если это необходимо. Форма обрабатывается таким же образом как если бы она была отправлена без использования Ajax, теми же #process функциями, функциями валидации и обработчиками формы, это облегчает процесс разработки форм с использованием Ajax которые будет работать корректно в случае если JavaScript у клиента отключен.
  • Когда обработка завершена, ajax_form_callback() вызывает функцию определенную в #ajax["callback"], которая возвращает обновленный элемент формы или массив с набором Ajax команд.
  • Page delivery callback для "system/ajax", ajax_deliver (), обрабатывает элементы возвращенные функцией объявленной в #ajax["callback"], и возвращает JSON строку созданную функцией ajax_render () браузеру.
  • Браузер преобразует JSON строку в массив объектов с командами и выполняет каждую команду, в результате старое содержимое страницы заключенное в #ajax["wrapper"] замещается новым содержимым возвращенным функцией объявленной в #ajax["callback"] используя анимационный эффект объявленный в #ajax["effect"].

Простой пример использования Ajax из модуля Examples.

function main_page() {
  return drupal_get_form("ajax_example_simplest");
}
 
function ajax_example_simplest($form, &$form_state) {
  $form = array();
  $form["changethis"] = array(
    "#type" => "select",
    "#options" => array(
      "one" => "one",
      "two" => "two",
      "three" => "three",
    ),
    "#ajax" => array(
      "callback" => "ajax_example_simplest_callback",
      "wrapper" => "replace_textfield_div",
     ),
  );
 
  // Этот элемент формы будет заменен обновленным после изменения элемента $form["changethis"]
  $form["replace_textfield"] = array(
    "#type" => "textfield",
    "#title" => t("Значение по умолчанию будет изменено"),
    "#description" => t("Скажите почему вы выбрали ") . """ .
      (!empty($form_state["values"]["changethis"])
      ? $form_state["values"]["changethis"] : t("Еще не выбрано")) . """,
    "#prefix" => "<div id="replace_textfield_div">",
    "#suffix" => "</div>",
  );
  return $form;
}
 
function ajax_example_simplest_callback($form, $form_state) {
  // Форма была изменена и элемент $form["replace_textfield"]
  // будет изменен на обновленный  
  return $form["replace_textfield"];
} 

В этом примере элемент "changethis" имеет Ajax обработчик. Значение по умолчанию для #ajax["event"] - "change", таким образом при изменении элемената "changethis" выполняется Ajax запрос. Форма отправляется и обрабатывается, после чего вызывается callback функция. Затем форма автоматически создает измененный $form["replace_textfield"]["#description"], то есть callback просто возвращает измененную часть формы.

Для определения Ajax обработчика в форме необходимо добавить свойство "#ajax" при объявлении элемента формы. Это поле будет вызывать Ajax запрос при нажатии на него (или другом событии, в зависимости от типа элемента). Свойство #ajax содержит следующие параметры (из которых "path" или "callback" обязательный параметр).

  • #ajax["callback"]: Callback функция которая вызывается на стороне сервера, она принимает аргументы $form и $form_state и возвращает массив элементов для обработки, HTML разметку или набор Ajax команд. Если возвращен массив для обработки или HTML разметка то это значение заменяет содержимое содержащееся в элементе с id объявленном в параметре #ajax["wrapper"], также сообщения обработанные функцией theme_status_messages() будут размещены перед элементом. (Если сообщения не нужны можно воспользоваться набором Ajax команд). Если возвращен набор Ajax команд, то все они будет выполнены.
  • #ajax["path"]: путь для обработки запроса. В большинстве случаев этот параметр пропускается и используется стандартный путь "system/ajax". Этот путь должен быть объявлен как меню callback которые возвращает данные обработанные функцией ajax_render(). По умолчанию "system/ajax", вызывает функцию ajax_form_callback(), которая в свою очередь вызывает функцию объявленную в свойстве #ajax["callback"]. Если вы используете свой путь, вы должные самостоятельно обрабатывать запросы в вашем коде.
  • #ajax["wrapper"]: CSS идентификатор обертки в которую будет помещаться обновленное значение возвращенное функцией объявленной в свойстве #ajax["callback"]. Содержимое возвращенное этой функцией заменяет содержимое элемента id которого объявлено в свойстве #ajax["wrapper"]. Этот оберточный элемент обычно создают с помощью свойств #prefix и #suffix. Обратите внимание что это именно ID элемента а не CSS селектор. Например если это элемент имеет id #some-selector, то надо использовать запись #ajax["wrapper"] = "some-selector", а не "#some-selector".
  • #ajax["effect"]: jQuery эффект который будет использоваться для замены содержимого. По умолчанию это "none". Возможные варианты: "none", "slide" или "fade".
  • #ajax["speed"]: Скорость эффекта. По умолчанию "slow". Может принимать значения "slow", "fast" или числовое значение обозначающее длительность эффекта в миллисекундах.
  • #ajax["event"]: JavaScript событие при котором будет отсылаться Ajax запрос. В случае если это свойство не указано событие будет выбрано автоматически в зависимости от типа элемента.
  • #ajax["prevent"]: JavaScript события которое необходимо предотвратить. По умолчанию это событие "click" для типов "submit", "button" и "image_button". Можно задать несколько событий перечислив их через пробел. Например, когда #ajax обработчик назначается для кнопки на форме, нажатие кнопки Enter для текстового поля вызывает событие "click" для кнопки Submit. Вызов Ajax в этом случае может привести к проблемам. В таком случае Ajax привязывают к событию "mousedown" вместо "click", а событие "click" передают в свойство "prevent". Таким образом мы предотвращаем отправку формы нажатием кнопки Enter.
  • #ajax["method"]: jQuery метод который будет использован для отображения новой HTML разметки. По умолчанию это "replaceWith". Допустимые значения: "replaceWith", "append", "prepend", "before", "after", или "html". Для дополнительной информации смотрите jQuery manipulators documentation.
  • #ajax["progress"]: Определяет throbber или progress bar будет использоваться для отображения во время ожидания ответа от callback функции и добавления соответствующего сообщения. Допустимые параметры: "type", "message", "url", "interval". Для более подробной информации смотрите Form API Reference.

В дополнение к использованию Form API для создания изменений в формах, Ajax можно использовать посредством добавления классов к кнопкам и ссылкам. Если добавить класс "user-ajax" к ссылке, то при нажатии не нее будет выполняться Ajax запрос. При использовании этого метода, атрибут href может содержать параметр "/nojs/" как часть пути. Когда Ajax Framework создает запрос, эта часть будет превращена в "/ajax/". Таким образом серверный код может легко распознать был ли сделан запрос посредством Ajax или нет.

Таким же образом, Submit кнопке может быть назначен класс "use-ajax-submit". В этом случае форма будет отправлена через Ajax по пути указанном в параметре "#action". В данном случаем параметр "#action" также может содержать часть "/nojs/" которая будет превращена в "/ajax/".

Сервер отвечая на запрос в свою очередь делает необходимые манипуляции с данными, после чего создает массив Ajax команд. Эти команды будут превращены в JSON который возвратиться на машину клиента где все команды будут прочитаны как макро язык и выполнены.

Каждая команда это ассоциативный массив который будет превращен в командный объект на стороне JavaScript. Пример команды $command_item["command"], такой как "alert" или "replace", которая будет отвечать методу в пространстве имен Drupal.ajax[command]. Массив с командами может содержать любые другие данные необходимые для обработки, например "method", "selector", "settings" и т.д.

Команды обычно создаются с помощью вспомогательных функций, как показано на прмере ниже:

  $commands = array();
  // Заменяет содержимое  "#object-1" текстом "some html here".
  $commands[] = ajax_command_replace("#object-1", "some html here");
  // Создает визуальный  маркер "changed" для "#object-1" элемента.
  $commands[] = ajax_command_changed("#object-1");
  return array("#type" => "ajax", "#commands" => $commands);

При возвращении массива Ajax команд бывает полезно вывести сообщение. В этом случае массив может быть построен следующим образом:

$commands = array();
$commands[] = ajax_command_replace(NULL, $output);
$commands[] = ajax_command_prepend(NULL, theme("status_messages"));
return array("#type" => "ajax", "#commands" => $commands);

Полный список команд смотрите здесь Ajax framework commands.

Оригинальаня статья: http://api.drupal.org/api/drupal/includes%21ajax.inc/group/ajax/7

Автор перевода: Денис Захаров

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