CGridView Assign table row an id

Does anyone know how to assign a table row in the CGridView an id?

I have searched every where and have not been able to find the answer.

Any help would be greatly appreciated.

Very probably this isn’t implemented…

I just took a look at the source code and it’s looking like this:




	public function renderTableRow($row)

	{

		if($this->rowCssClassExpression!==null)

		{

			$data=$this->dataProvider->data[$row];

			echo '<tr class="'.$this->evaluateExpression($this->rowCssClassExpression,array('row'=>$row,'data'=>$data)).'">';

		}

		else if(is_array($this->rowCssClass) && ($n=count($this->rowCssClass))>0)

			echo '<tr class="'.$this->rowCssClass[$row%$n].'">';

		else

			echo '<tr>';

		foreach($this->columns as $column)

			$column->renderDataCell($row);

		echo "</tr>\n";

	}




I would extend the CGridView class and overwrite the renderTableRow function as follows:

  • copy/paste the original code and change each 3 <tr to: '<tr ‘.$this->getRowId($row).’ [original code …]

  • implement the getRowId($row) function. This must return an empty string by default or the string ‘id="[your id-evaluation code here]"’.

Thanks szfjozsef for your help.

Where should I implement the getRowId($row) function? Should this it be in the model, view or controller?

This will look like this:

You need to create a new file, named, let’s say MyGridView. This file should be (where it’s visible by the framework,) for example in protected/components. Inside this file, create the MyGridView class.

class MyGridView extends CGridView {

}

Inside this class, creating a function renderTableRow($row) will override the original one.

Creating the getRowId($row) function will be yours since it doesn’t exists in the original class.

Hmm… There is too much to write… You need to be sure to fully understand the object-oriented part of php or of the programming languages in general…

When everything is put together, in a view you should use:

$this->widget(‘application.components.MyGridView’, array(…the same initialization stuff goes here as in the case of CGridView

This may sound a little bit complicated, but believe me, it isn’t.

Thanks again, so here is what I ended up doing. Not sure if it is 100% correct, but it is working for now:

Created new component named MyGridView.php:


Yii::import('zii.widgets.grid.CGridView');


class MyGridView extends CGridView

{  

	public $rowIdExpression;

	

	public function renderTableRow($row)

	{

			if($this->rowCssClassExpression!==null)

			{

					$data=$this->dataProvider->data[$row];

					echo '<tr '.$this->getRowId($row).' class="'.$this->evaluateExpression($this->rowCssClassExpression,array('row'=>$row,'data'=>$data)).'">';

			}

			else if(is_array($this->rowCssClass) && ($n=count($this->rowCssClass))>0)

					echo '<tr '.$this->getRowId($row).' class="'.$this->rowCssClass[$row%$n].'">';

			else

					echo '<tr '.$this->getRowId($row).'>';

			foreach($this->columns as $column)

					$column->renderDataCell($row);

			echo "</tr>\n";

	}

	

	public function getRowId($row)

	{

		if($this->rowIdExpression!==null)

		{	

			$data=$this->dataProvider->data[$row];

			return 'id='.$this->evaluateExpression($this->rowIdExpression,array('data'=>$data));

		}

		else

		{

			return '';

		}

	}

}

In my view file, called the my newly created class:


$this->widget('application.components.MyGridView' , array(

	'id'=>'lines-wln-grid-all',

	'dataProvider'=>$dataProvider,

	'filter'=>$model_all,

	'cssFile'=>Yii::app()->baseUrl . '/css/gridview.css',

	'rowIdExpression'=>'$data->id', // Notice the call to my newly created function

	'columns' => $dialog->columns(),	

));

so now the questions is: is it worth overriding the core class instead of assigning a class to the row? what is it that an id can achieve that a class cannot

Nice work!

ID’s are unique.

Generating unique id’s it’s more simple than defining lots of classes

Thanks for this post. It helped me so much!! Congratulations for the Yii Community!!

Wow, thanks alot for the post! :)

Works with the Bootstrap Plugin YiiBooster like this:

components/MyGridWiew.php


<?php

// src: http://www.yiiframework.com/forum/index.php/topic/32823-cgridview-assign-table-row-an-id/

Yii::import('bootstrap.widgets.TbExtendedGridView');


class MyGridView extends TbExtendedGridView

{

	public $rowIdExpression;


	public function renderTableRow($row)

	{

		if ($this->rowCssClassExpression !== null)

		{

			$data = $this->dataProvider->data[$row];

			echo '<tr '.$this->getRowId($row).' class="' . $this->evaluateExpression($this->rowCssClassExpression, array('row' => $row, 'data' => $data)) . '">';

		} else if (is_array($this->rowCssClass) && ($n = count($this->rowCssClass)) > 0)

			echo '<tr '.$this->getRowId($row).' class="' . $this->rowCssClass[$row % $n] . '">';

		else

			echo '<tr '.$this->getRowId($row).'>';

		foreach ($this->columns as $column)

		{

			echo $this->displayExtendedSummary && !empty($this->extendedSummary['columns']) ? $this->parseColumnValue($column, $row) : $column->renderDataCell($row);

		}

		echo "</tr>\n";

	}


	public function getRowId($row)

	{

		if($this->rowIdExpression!==null)

		{

			$data=$this->dataProvider->data[$row];

			return 'id='.$this->evaluateExpression($this->rowIdExpression,array('data'=>$data));

		}

		else

		{

			return '';

		}

	}

}



In my view:


$this->widget('application.components.MyGridView' , array(

        'rowIdExpression'=>'$data->id', // Notice the call to my newly created function


        /* content as usual */

        'id'=>'lines-wln-grid-all',

        'dataProvider'=>$dataProvider,

        'filter'=>$model_all,

        'cssFile'=>Yii::app()->baseUrl . '/css/gridview.css',

        'columns' => $dialog->columns(),       

 

));



Just write in grid options




'rowHtmlOptionsExpression'=>'array("id"=>$data->id)',



http://www.yiiframew…pression-detail