Наверх

Обрабатываем поля форм, добавляемые динамически


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

<div class="control-group">
  <label class="control-label" for="contractor_phone">Телефон</label>
  <div class="controls">
    <div class="input-append">
      <input type="text" id="contractor_phone" name="contractor_phone[]">
      <span class="btn" id="add_phone"><i class="icon icon-plus"></i></span>
      <div id="addPhones"></div>
    </div>
  </div>
</div>

<script type="text/javascript">
$("#add_phone").click(function() {
    $("#addPhones").append('<input type="text" name="contractor_phone[]">');
});
</script>
В итоге в $_POST['contractor_phone'] приходит массив телефонов.

Здесь проблем нет. Проблемы начинаются, если пользователь не заполнил какое-то обязательное поле. В этом случае FormIt возвращает пользователя на ту же страницу, выводит сообщения об ошибках и значения, которые пользователь уже ввел, в плейсхолдеры.

К нашему массиву доступ есть, но если вывести плейсхолдер [[!+fi.contractor_phone]], мы получим все значения из массива через запятую. Можно получить каждое конкретное значение так: [[!+fi.contractor_phone.0]], [[!+fi.contractor_phone.1]]… Но нам-то нужно каждое значение вывести в своем поле. Если бы у нас было поле radio, то этого нам хватило бы, но мы ко всему прочему не знаем, сколько у нас будет полей — у каждого пользователя по-своему.

Выхода два:
  1. С помощью JavaScript разбираем строку [[!+fi.contractor_phone]] на отдельные значения и создаем поля;
  2. Самостоятельно анализируем $_POST['contractor_phone'] и создаваем поля.

Я пошел по второму пути.

В форме есть div, в который добавляются поля. Туда же и прописываем вызов нашего сниппета:

...
<div id="addPhones">[[!contractorPhonesAdd]]</div>
...
Код сниппета:

if (!$_POST['contractor_phone']) return;
$phones = $_POST['contractor_phone'];

foreach ($phones as $phone) {
  $output .= $modx->getChunk('tpl.contractorPhonesAdd',
                              array('phone' => $phone));
}
return $output;

Чанк tpl.contractorPhonesAdd
<input type="text" name="contractor_phone[]" value="[[+phone]]">

Теперь пользователь оценит бережное отношение к данным, которые он вводит. И мы не будем заставлять пользователя несколько раз подряд вводить одно и то же. G+

Оригинал статьи community.modx-cms.ru/blog/tips_and_tricks/9069.html


11 комментариев

  1. Darklelik Darklelik 16 октября 2014, 16:17 # 0
    Отлично написано! Спасибо. Илья может подскажешь, как добавлять плейсхолдеры для динамических полей в чанк письма для formit?
    1. Илья Уткин 17 октября 2014, 10:31 # 0
      Вот в этом плейсхолдере: [[!+fi.contractor_phone]] и находятся все введенные пользователем данные.
      1. Darklelik Darklelik 18 октября 2014, 10:08(Комментарий был изменён) # 0
        Блин хоть убей выводит
        в письме [[!+fi.contractor_phone]] и не в какую не подставляет данные
        Если ставить [[contractor_phone]] выводит список телефонов но без разделителей…
        [[contractor_phone.0]] тоже не работает (((
        1. Илья Уткин 20 октября 2014, 06:27 # 0
          А [[+contractor_phone]]?
          1. Darklelik Darklelik 20 октября 2014, 06:30 # 0
            Да именно так, опечатался тут, значит будем писать хук. Спасибо
          2. Илья Уткин 20 октября 2014, 06:28 # 0
      2. Михаил 17 октября 2014, 09:29 # 0
        Илья, и еще такой вопросик, а как быть с полями, которые идут datefield (ExtJs). Как их выводить в метки времени. А то пишет в базу как 12/10/12 к примеру
        1. Илья Уткин 17 октября 2014, 10:34 # +1
          Ну тут какой тип данных в базе написан, тот и будет сохраняться. Если в типе поля указать int, то xPDO его переведет в метку времени.
          1. Михаил 17 октября 2014, 10:46 # 0
            Кланяюсь! Помогло. Блин а где вот это написанно то, я реально не допер
        2. Константин 29 января 2018, 15:53 # 0
          Илья, подскажите как динамически менять emailTo

          Я сделал селект с емайлами, пробовал подставлять в скрытые поля, но все равно использует emailTo указанный в вызове
          <input type="hidden" name="emailTo" value="email@email.ru">
          ...
          <input type="hidden" name="addressTo" value="email@email.ru">
          
          связка AjaxForm и FormIt
          1. Илья Уткин 01 февраля 2018, 11:56 # 0
            Вам нужно использовать хук FormItAutoResponder

          Авторизация

          через сервис Loginza:


          Шаблоны MODX

          1 2 Дальше »

          Объектная
          модель
          MODX