Создание форм
Формы на основе ActiveRecord: ActiveForm
Основной способ использования форм в Yii — через yii\widgets\ActiveForm. Этот подход следует предпочитать, когда форма основана на модели. Кроме того, существуют некоторые полезные методы в yii\helpers\Html, которые обычно используются для добавления кнопок и подсказок к любой форме.
Форма, отображаемая на стороне клиента, в большинстве случаев имеет соответствующую модель, которая используется для проверки ввода на стороне сервера (см. раздел Проверка ввода для получения более подробной информации о проверке).
При создании форм на основе модели первым шагом является определение самой модели. Модель может быть основана на классе Active Record, представляющем некоторые данные из базы данных, или на общем классе модели (расширяющем yii\base\Model) для захвата произвольного ввода, например, форма входа.
Подсказка: Если поля формы отличаются от столбцов базы данных или существуют форматирование и логика, специфичные только для этой формы, лучше создать отдельную модель, расширенную от yii\base\Model.
В следующем примере показано, как общую модель можно использовать для формы входа:
<?php
class LoginForm extends \yii\base\Model
{
public $username;
public $password;
public function rules()
{
return [
// define validation rules here
];
}
}
В контроллере мы передадим экземпляр этой модели в представление, где виджет ActiveForm используется для отображения формы:
<?php
use yii\helpers\Html;
use yii\widgets\ActiveForm;
$form = ActiveForm::begin([
'id' => 'login-form',
'options' => ['class' => 'form-horizontal'],
]) ?>
<?= $form->field($model, 'username') ?>
<?= $form->field($model, 'password')->passwordInput() ?>
<div class="form-group">
<div class="col-lg-offset-1 col-lg-11">
<?= Html::submitButton('Login', ['class' => 'btn btn-primary']) ?>
</div>
</div>
<?php ActiveForm::end() ?>
Оборачивание с begin() и end()
В приведенном выше коде ActiveForm::begin() не только создает экземпляр формы, но также помечает начало формы. Все содержимое, размещенное между ActiveForm::begin() и ActiveForm::end(), будет заключено в HTML-тег <form>. Как и любой виджет, вы можете указать некоторые параметры того, как виджет должен быть настроен, передав массив методу begin. В этом случае дополнительный класс CSS и идентификатор передаются для использования в открывающем теге <form>. Для всех доступных параметров, пожалуйста, обратитесь к документации API yii\widgets\ActiveForm.
ActiveField
Для создания элемента формы вместе с меткой элемента и любой применимой проверкой JavaScript метод ActiveForm::field() вызывается, возвращая экземпляр yii\widgets\ActiveField. Когда результат этого метода выводится непосредственно, результатом является обычное текстовое поле ввода. Для настройки вывода вы можете цеплять дополнительные методы ActiveField к этому вызову:
// a password input
<?= $form->field($model, 'password')->passwordInput() ?>
// adding a hint and a customized label
<?= $form->field($model, 'username')->textInput()->hint('Please enter your name')->label('Name') ?>
// creating a HTML5 email input element
<?= $form->field($model, 'email')->input('email') ?>
Это создаст все <label>, <input> и другие теги в соответствии с шаблоном, определенным полем формы. Название поля ввода определяется автоматически из имени формы модели и имени атрибута. Например, имя поля ввода для атрибута username в приведенном выше примере будет LoginForm[username]. Это правило именования приведет к тому, что массив всех атрибутов для формы входа будет доступен в $_POST['LoginForm'] на стороне сервера.
Подсказка: Если у вас есть только одна модель в форме и вы хотите упростить имена ввода, вы можете пропустить часть массива, переопределив метод formName() модели, чтобы он возвращал пустую строку. Это может быть полезно для моделей фильтров, используемых в GridView для создания более красивых URL.
Указание атрибута модели может быть выполнено более сложными способами. Например, когда атрибут может принимать значение массива при загрузке нескольких файлов или выборе нескольких элементов, вы можете указать его, добавив [] к имени атрибута:
// allow multiple files to be uploaded: echo $form->field($model, 'uploadFile[]')->fileInput(['multiple'=>'multiple']); // allow multiple items to be checked: echo $form->field($model, 'items[]')->checkboxList(['a' => 'Item A', 'b' => 'Item B', 'c' => 'Item C']);
Будьте внимательны при именовании элементов формы, таких как кнопки отправки. Согласно документации jQuery, существуют некоторые зарезервированные имена, которые могут вызвать конфликты:
Формы и их дочерние элементы не должны использовать имена или идентификаторы элементов, которые конфликтуют с свойствами формы, такими как
submit,length, илиmethod. Конфликты имен могут привести к запутанным ошибкам. Полный список правил и проверка вашей разметки на эти проблемы см. в DOMLint.
Дополнительные HTML-теги могут быть добавлены в форму с помощью простого HTML или с использованием методов из класса-помощника Html, как это сделано в приведенном выше примере с Html::submitButton().
Подсказка: Если вы используете CSS Twitter Bootstrap в своем приложении, вы можете использовать yii\bootstrap\ActiveForm вместо yii\widgets\ActiveForm. Первый расширяет последний и использует стили, специфичные для Bootstrap, при генерации полей ввода формы.
Подсказка: Для стилизации обязательных полей звёздочками можно использовать следующий CSS:
div.required label.control-label:after { content: " *"; color: red; }
Создание списков
Существует 3 типа списков:
- Списки выпадающих списков
- Список радиокнопок
- Список флажков
Для создания списка необходимо подготовить элементы. Это можно сделать вручную:
$items = [
1 => 'item 1',
2 => 'item 2'
]
или путем извлечения из БД:
$items = Category::find()
->select(['label'])
->indexBy('id')
->column();
Эти $items должны быть обработаны различными виджетами списка. Значение поля формы (и текущий активный элемент) автоматически устанавливается текущим значением атрибута $model.
Создание списка выпадающего списка
Мы можем использовать метод ActiveField yii\widgets\ActiveField::dropDownList() для создания списка выпадающего списка:
/* @var $form yii\widgets\ActiveForm */
echo $form->field($model, 'category')->dropdownList([
1 => 'item 1',
2 => 'item 2'
],
['prompt'=>'Select Category']
);
Создание списка радиокнопок
Мы можем использовать метод ActiveField yii\widgets\ActiveField::radioList() для создания списка радиокнопок:
/* @var $form yii\widgets\ActiveForm */
echo $form->field($model, 'category')->radioList([
1 => 'radio 1',
2 => 'radio 2'
]);
Создание списка флажков
Мы можем использовать метод ActiveField yii\widgets\ActiveField::checkboxList() для создания списка флажков:
/* @var $form yii\widgets\ActiveForm */
echo $form->field($model, 'category')->checkboxList([
1 => 'checkbox 1',
2 => 'checkbox 2'
]);
Работа с Pjax
Виджет Pjax позволяет обновлять определенный раздел страницы вместо перезагрузки всей страницы. Вы можете использовать его для обновления только формы и замены ее содержимого после отправки.
Вы можете настроить $formSelector для указания, отправка какой формы может инициировать pjax. Если он не установлен, все формы с атрибутом data-pjax внутри заключенного содержимого Pjax будут инициировать запросы pjax.
use yii\widgets\Pjax;
use yii\widgets\ActiveForm;
Pjax::begin([
// Pjax options
]);
$form = ActiveForm::begin([
'options' => ['data' => ['pjax' => true]],
// more ActiveForm options
]);
// ActiveForm content
ActiveForm::end();
Pjax::end();
Подсказка: Будьте осторожны с ссылками внутри виджета Pjax, так как ответ также будет отображен внутри виджета. Чтобы этого избежать, используйте атрибут
data-pjax="0"HTML.
Значения в кнопках отправки и загрузке файлов
Известны проблемы с использованием jQuery.serializeArray() при работе с файлами и значениями кнопок отправки, которые не будут решены и вместо этого устаревают в пользу класса FormData, введенного в HTML5.
Это означает, что единственная официальная поддержка файлов и значений кнопок отправки с ajax или с помощью виджета Pjax зависит от поддержки браузера для класса FormData.
Дополнительное чтение
Следующий раздел Проверка ввода обрабатывает проверку отправленных данных формы на стороне сервера, а также проверку ajax и на стороне клиента.
Для чтения о более сложном использовании форм вы можете ознакомиться со следующими разделами:
- Сбор табличных данных для сбора данных для нескольких моделей одного типа.
- Получение данных для нескольких моделей для обработки нескольких различных моделей в одной форме.
- Загрузка файлов о том, как использовать формы для загрузки файлов.
© 2008–2017 by Yii Software LLC
Licensed under the three clause BSD license.
http://www.yiiframework.com/doc-2.0/guide-input-forms.html