arrow_back
Back

Yii2 ActiveField: field options, templates, and client validation

Andrew Dorokhov Andrew Dorokhov schedule 3 min read
menu_book Table of Contents

There’s a widget in Yii2 framework, that is used for displaying form fields. The class of this widget called ActiveField (yii\widgets\ActiveField).

ActiveField используется исключительно в связке с виджетом ActiveForm, так как некоторые его свойства должны ссылаться на объект ActiveForm.

Создание экземпляров ActiveField происходит через вызов функции field() у объекта ActiveForm.

По умолчанию создается экземпляр класса yii\widgets\ActiveField. Но класс можно переопределить через опцию $fieldClass формы ActiveForm.

Метод field() для создания экземпляра поля требует двух обязательных параметров:

public function field($model, $attribute, $options = [])
  • $model - модель с интересующим нас свойством, которые мы будем ассоциировать с этим полем.
  • $attribute - имя самого свойства.

Example 1

Code:

<?= $form->field($model, 'first_name'); ?>

Result:

<div class="form-group field-signupform-first_name required">
    <label class="control-label" for="signupform-first_name">First Name</label>
    <input type="text" id="signupform-first_name" class="form-control" name="SignUpForm[first_name]" aria-required="true">
    <div class="help-block"></div>
</div>

Class ActiveField has a template property, которое отвечает за структуру HTML-блока. По умолчанию это свойство хранит следующее значение:

public $template = "{label}\n{input}\n{hint}\n{error}";

Как видно из шаблона, структура блока состоит из четырех последовательных тегов, разделённых символом переноса. И всё это обрамляется родительским контейнером.

Как происходит рендеринг

Отрисовкой самого HTML-блока занимается метод render() - он возвращает готовую строку с HTML-разметкой. Кроме того, класс ActiveField имеет магический метод __toString(), который тоже вызывает тот же самый render(), а это значит, что можно выводить результат, используя echo $active_form_object.

Рендеринг представляет собой замену шорткодов из $template на HTML-элементы, которые хранится в массиве $parts[] с соответствующими ключами.

$parts['{label}']
$parts['{input}']
$parts['{hint}']
$parts['{error}']

Если эти элементы массива отсутствуют в массиве $parts[], то они будут сформированы с помощью определенных методов:

Element Method
{label} label($label = null, $options = [])
{input} input($type, $options = []),
textInput($options = []),
hiddenInput($options = []),
passwordInput($options = []),
fileInput($options = []),
textarea($options = []),
radio($options = [], $enclosedByLabel = true),
checkbox($options = [], $enclosedByLabel = true),
dropDownList($items, $options = []),
listBox($items, $options = []),
checkboxList($items, $options = []),
radioList($items, $options = [])
{hint} hint($content, $options = [])
{error} error($options = [])

Мы можем как сами заранее поместить нужные элементы в массив, так и вызвать перечисленные методы вручную, чтобы эти элементы сформировались. Второй вариант интересный тем, что мы можем передать специальные параметры (такие как CSS-классы, либо атрибуты для тегов).

Если элемент {input} не был вручную установлен с помощью любого из перечисленных методов, то перед рендерингом будет вызван метод textInput().

Всё, что будет передано в массив $options, станет атрибутами и значениями в конкретном теге. Кроме того, для каждого из этих элементов будет использоваться стандартный набор атрибутов.

Element Property Default value
{label} $labelOptions ['class' => 'control-label']
{input} $inputOptions ['class' => 'form-control']
{hint} $hintOptions ['class' => 'hint-block']
{error} $errorOptions ['class' => 'help-block']

Эти свойства можно использовать тогда, когда мы, например, хотим переопределить все CSS-классы для контейнера, где будут выводиться ошибки и т.п.

Parent container

Все элементы шаблона блока:

public $template = "{label}\n{input}\n{hint}\n{error}";

обрамляются в родительский тег. По умолчанию это <div>.

ActiveField имеет свойство options, которое представляет собой массив с атрибутами и значениями для родительского тега контейнера. По умолчанию там хранится: ['class' => 'form-group'].

For example, here’s how we can change a class value for the parent container of the field block:

$form->field($model, 'name', [
    'options' => ['class' => 'hello'],
]);

Чтобы избавиться от некоторых атрибутов по умолчанию, можно воспользоваться таким кодом:

'options' => [
    'class' => null,
]

Кроме того, здесь есть один трюк, если мы передадим в него параметр "tag" => false, то этим мы избавимся от родительского контейнера вовсе.

code

Need Help with Development?

Happy to help — reach out via the contacts or go straight to my Upwork profile.

work View Upwork Profile arrow_forward
Next Article

Yii2 ActiveForm: models, validation, and form rendering

arrow_forward