Using DetailView and GridView (with filters) to show related at same page

Hi. I was using Yii 1.1 for a couple years, now Im starting with Yii2 for new projects and I cant resolve this

I have two models Course and Student, and 1 controller CourseController. The controller have 2 methods:

class CourseController extends Controller
{
//...

    public function actionView($id)
    {
        return $this->render('view', [
            'model' => $this->findModel($id),
        ]);
    }
    public function actionStudents($id)
    {
        $searchModel = new StudentSearch();
        $searchModel->course = $id;
        $dataProvider = $searchModel->search(Yii::$app->request->queryParams);

        return $this->render('_students', [
            'searchModel' => $searchModel,
            'dataProvider' => $dataProvider,
        ]);
    }
}

I need to show the course details including the students registered in a GridView (using pagers and filters).

Now, my view.php:

<?php

use yii\helpers\Html;
use yii\widgets\DetailView;

$this->title = $model->SIGLA;
$this->params['breadcrumbs'][] = $this->title;
\yii\web\YiiAsset::register($this);
?>
<div class="course-view">

    <?= DetailView::widget([
        'model' => $model,
        'attributes' => [
            'ID',
            'NAME',
        ],
    ]) ?>

</div>
<?php
$url = yii\helpers\Url::to(['students', 'id' => $model->ID]);
$csrf_param = Yii::$app->request->csrfParam;  
$csrf_token = Yii::$app->request->csrfToken;
$id = $model->ID;
$this->registerJs("
$(document).ready(function() {
    var contenedor = 'to1';
    var href= '$url';
    $.ajax({
        'type' : 'GET',
        'url' : '$url',
        'dataType' : 'html',
        'data' : {
            '$csrf_param' : '$csrf_token', // #2
            'id' : $id
        },
        'success' : function(data){ // #5
            $('#to1').html(data);
        }
    });
});",
Yii::$app->view::POS_READY
);
?>
<div id="to1">
</div>

the file _students.php (gridview for students registered):

<?php

use yii\helpers\Html;
use yii\grid\GridView;
use yii\widgets\Pjax;

?>

<div class="student-index">
    <h2>Students</h1>

    <?php Pjax::begin([
        'enablePushState' => false,
    ]); ?>

    <?= GridView::widget([
        'dataProvider' => $dataProvider,
        'filterModel' => $searchModel,
        'columns' => [
            'ID',
            'NAME',
            //....
         ],
    ]); ?>

    <?php Pjax::end(); ?>
</div>

So… i can view detail of course and the students registered , and i can search in the gridview… nos… when i use the pages it works fine… but filtering change the url and the page: i lost the details.

I need to solve this, because i need to add other sections for the same course using more gridviews

Any help will be great

1 Like

Hi @jotafv, welcome to Yii2!

I’m doing it like the following.

controller

    public function actionView($id)
    {
        $model = $this->findModel($id);
        $searchModel = new StudentSearch();
        $searchModel->course = $id;
        $dataProvider = $searchModel->search(Yii::$app->request->queryParams);

        return $this->render('view', [
            'model' => $model,
            'searchModel' => $searchModel,
            'dataProvider' => $dataProvider,
        ]);
    }

view

    <?= DetailView::widget([
        'model' => $model,
        'attributes' => [
            'ID',
            'NAME',
        ],
    ]) ?>
    ...
    <?php Pjax::begin([
        'id' => 'students',
    ]); ?>

    <?= GridView::widget([
        'dataProvider' => $dataProvider,
        'filterModel' => $searchModel,
        'columns' => [
            'ID',
            'NAME',
            //....
         ],
    ]); ?>

    <?php Pjax::end(); ?>

Yes, I simply combine the detail view and the grid view in a single controller and view. This is working fine for me.

I hope it will work with another grid view added to it.

And if you want many grid views, you may want to optimize the controller code a little by using renderPartial.

Thank for your answer.

I tried that solution, but the page is reloading complete when i use the filters or the pagination, and i dont want that. In fact, I need to include many sections with diferent gridviews for related data, in many pages.

Updating:

Finally i solve my problem (page reload when use filter/pager of the gridview): just needed adjust the Pjax widget. Maybe someone find useful this solution.

<?php Pjax::begin([
    'id'=>'pjax-students',
    'enablePushState' => false,
    'clientOptions'=>[
        'container'=>'#pjax-students',
        'push'=>false,
        'skipOuterContainers' =>true,
    ],
]); ?>

also, to prevent Pjax reload the entire page after few seconds of inactivity the view must include:

$this->registerJs('$(document).on("pjax:timeout", function(event) {
    // Prevent default timeout redirection behavior
    event.preventDefault()
  });');

sources: https://github.com/yiisoft/jquery-pjax

1 Like