Data widgets
Data widgets display database records without hand-written table markup. GridView draws a table with sorting and pages, ListView a list in your own markup, DetailView the fields of one record. The first two receive data from the ActiveDataProvider from the lesson on pagination.
GridView
The action passes a data provider to the view:
// controllers/PostController.php
public function actionIndex(): string
{
$dataProvider = new ActiveDataProvider([
'query' => Post::find(),
'pagination' => ['pageSize' => 20],
]);
return $this->render('index', ['dataProvider' => $dataProvider]);
}The view views/post/index.php calls the widget:
<?php
// views/post/index.php
use yii\grid\GridView;
?>
<?= GridView::widget([
'dataProvider' => $dataProvider,
'columns' => ['id', 'title', 'status'],
]) ?>The page /posts shows a table of three columns. The headers come from attributeLabels(), a click on them sorts the rows, and page links are under the table.
Configuring columns
<?= GridView::widget([
'dataProvider' => $dataProvider,
'columns' => [
['class' => 'yii\grid\SerialColumn'],
'title',
'created_at:datetime',
[
'attribute' => 'status',
'value' => fn ($post) => $post->status ? 'Published' : 'Draft',
],
['class' => 'yii\grid\ActionColumn'],
],
]) ?>| Notation | What it does |
|---|---|
'title' | Prints the column as text |
'created_at:datetime' | Formats the value as a date and time |
An array with value | Calculates the cell content with a function |
SerialColumn | The row number in order |
ActionColumn | Buttons for viewing, updating and deleting |
The ActionColumn buttons lead to the view, update and delete actions of the same controller.
ListView
ListView prints each record through a separate view, which is how a feed of posts is made:
<?php
// views/post/index.php
use yii\widgets\ListView;
?>
<?= ListView::widget([
'dataProvider' => $dataProvider,
'itemView' => '_card',
]) ?>The file views/post/_card.php receives the record in the $model variable. Replace $post['title'] with $model->title in it, and the page shows post cards with page links under them.
DetailView
DetailView shows one record as a "name and value" table. In views/post/view.php:
<?php
// views/post/view.php
use yii\widgets\DetailView;
?>
<?= DetailView::widget([
'model' => $post,
'attributes' => ['id', 'title', 'body:ntext', 'created_at:datetime'],
]) ?>The page /posts/1 shows four rows with the post fields. The ntext format keeps line breaks in the text.
Common mistake
Cells and fields are escaped by default, so HTML markup is printed as text. The raw or html format turns this off: 'body:raw'. Do not apply it to visitor data: together with the markup, someone else's scripts get onto the page.