How to get controller name inside CGridView? - php

In views controller name can be achieved by $this->id, but in CGridView $this->id evaluation results in another name (may be gridview widget name). (1) How can I get controller name in cgridview?
Also I tried to define a variable ($thisCtl = $this->id) before calling CGridview. Although $thisCtl has the controller name, in CGridview evaluation process it is not defined. (2) Is there any way to pass a parameter to CGridView?
<?php
$thisCtl = $this->id;
$data = $model->search();
$this->widget('bootstrap.widgets.TbExtendedGridView', array(
'id'=>'insurance-grid',
'dataProvider'=>$model->search(),
//'filter'=>$model,
'columns'=>array(
'id',
'registeration_date',
'modification_date',
array(
'htmlOptions' => array('nowrap'=>'nowrap'),
'class'=>'bootstrap.widgets.TbButtonColumn',
'viewButtonUrl'=>'Yii::app()->createUrl("$thisCtl/view", array("id"=>$data["id"]))',
'updateButtonUrl'=>'Yii::app()->createUrl("$this->id/update", array("id"=>$data["id"]))',
),
),
));
?>

Since it appears you wish to use the controller value within the column values, you can do the following to get the controller name:
$this->grid->controller->id
As you are within a TbButtonColumn, you can access the grid property (since TbButtonColumn extends from CButtonColumn which in turn extends from CGridColumn) to access the TbExtendsGridView (which ultimately extends from CGridView) where you in turn access the controller property of the grid (which is defined by the widget parent), and finally the get id of the controller.
Then, assuming all your other code is correct, you would specify your gridview like so:
<?php
$data = $model->search();
$this->widget('bootstrap.widgets.TbExtendedGridView', array(
'id'=>'insurance-grid',
'dataProvider'=>$model->search(),
//'filter'=>$model,
'columns'=>array(
'id',
'registeration_date',
'modification_date',
array(
'htmlOptions' => array('nowrap'=>'nowrap'),
'class'=>'bootstrap.widgets.TbButtonColumn',
'viewButtonUrl'=>'Yii::app()->createUrl($this->grid->controller->id."/view", array("id"=>$data["id"]))',
'updateButtonUrl'=>'Yii::app()->createUrl($this->grid->controller->id."/update", array("id"=>$data["id"]))',
),
),
));
I haven't used any of the Tb extensions myself, by so long as they did not alter the built in behavior of the objects they extended, the above should work as desired.

the problem is that $this in CGridView refers to it's widget. So we should use a global function to get current controller name:
Yii::app()->getController()->getId();
the code should look like:
<?php
$thisCtl = $this->id;
$data = $model->search();
$this->widget('bootstrap.widgets.TbExtendedGridView', array(
'id'=>'insurance-grid',
'dataProvider'=>$model->search(),
//'filter'=>$model,
'columns'=>array(
'id',
'registeration_date',
'modification_date',
array(
'htmlOptions' => array('nowrap'=>'nowrap'),
'class'=>'bootstrap.widgets.TbButtonColumn',
'viewButtonUrl'=>'Yii::app()->createUrl("'.Yii::app()->getController()->getId().'/view", array("id"=>$data["id"]))',
'updateButtonUrl'=>'Yii::app()->createUrl("'.Yii::app()->getController()->getId().'/update", array("id"=>$data["id"]))',
),
),
));
?>
Thanks to this post Getting Current Controller ID in Yii

Related

yii CButtonColumn in gride view gives error

i have a admin page with CGrideView , but when i want to change my button column to add some other buttons gives this error : CButtonColumn and its behaviors do not have a method or closure named "getId".
admin action :
public function actionAdmin()
{
$model=new Block('search');
$model->unsetAttributes(); // clear any default values
if (isset($_GET['Block'])) {
$model->attributes=$_GET['Block'];
}
$this->render('admin',array(
'model'=>$model,
));
}
admin view :
$this->widget('zii.widgets.grid.CGridView', array(
'id'=>'block-grid',
'dataProvider'=>$model->search(),
'filter'=>$model,
'columns'=>array(
'name',
'content',
'type',
'enable',
array(
'class'=>'CButtonColumn',
'template' => '{view}{update}',
'buttons' => array(
'update' => array(
'url' => 'Yii::app()->controller->createUrl("update", array("name"=>$data->name))'
),
'view' => array(
'url'=>'CController::createUrl("view", array("name"=>$data->name))'
),
),
),
)));
solved! the reason is in the :
'view'=>array(
'url'=>'CController::createUrl("view",array("name"=>$data->name))'
),
it should be :
'view'=>array(
'url'=>'Yii::app()->controller->createUrl("view", array("name"=>$data->name))'
),
and why ?
because ():
Because Yii::app()->controller it is instance Controller of current application. Controller have property private $_id. CController::createUrl it is just static method. In method createUrl() calls method $this->getId(), but when you call static method instance is not created-#DanilaGanchar .
so in CController::createUrl it can't find the id of controller and for use that i should give it argument like this CController::createUrl("/page/view",array("name"=>$data->name)) i try that now and worked
The order of elements in template must be equal to the order of element in buttons. You have {view}{update} as the template, but you have defined update button first! So I think changing 'template'=>'{view}{update}' into 'template'=>'{update}{view}' probably can solve your problem.

Yii TbGridView set filter dropdown html attributes

I am unable to figure out how to set the filter dropdown's id attribute.
Here is the view code that defines the widget.
$this->widget('bootstrap.widgets.TbGridView',array(
'id'=>'view-grid',
'enableHistory'=>true,
'dataProvider'=>$model->search(),
'summaryText'=>"",
'filter'=>$model,
'columns'=>array(
array('name'=>'v_id','htmlOptions'=>array('style'=>'width: 60px')),
array('name'=>'v_parent_view','htmlOptions'=>array('style'=>'width: 20%'),'value'=>'$data->vParent->v_name'),
array('name'=>'v_name','type'=>'raw','value'=>function($data,$row) {
if(isset($data->vLatestVersion[0]->vv_id) && $data->vLatestVersion[0]->vv_id) {
return CHtml::link($data->v_name,array("viewVersion/update","id"=>$data->vLatestVersion[0]->vv_id));
} else {
return CHtml::link($data->v_name,array("viewVersion/create","vid"=>$data->v_id));
}
}),
array('name'=>'v_date_modified', 'type'=>'raw', 'htmlOptions'=>array('style'=>'width: 110px'), 'value'=>function($data, $row) {
return $data->modified_since . '<br/><span class="timeago">'.$data->vUserModified->username.'</span>';
}),
array(
'name'=>'v_status',
'value'=>'$data->getStatusName()',
'filter'=>Yii::app()->params['globalDmpLookups']['generalStatus'],
'filterHtmlOptions'=>array('id'=>'sel_status'),
'htmlOptions'=>array('style'=>'width: 60px'),
)
),
));
The line of code near the end that has 'filterHtmlOptions' is what I tried, but it is not working. Any help would be greatly appreciated.
The rendered html of my dropdown should look like this:
<select id="sel_status" name="View[v_status]">...</select>
But sadly it looks like this:
<select name="View[v_status]">...</select>
I found that I was trying to use a dropdown list incorrectly in my list filter for status = Active/Disabled. Doing this the Yii way is a simple matter of setting up the model like this...
public function search()
{
// Warning: Please modify the following code to remove attributes that
// should not be searched.
$criteria=new CDbCriteria;
$criteria->with = array('ggUserModified'); // specify relationship
$criteria->compare('gg_id',$this->gg_id);
$criteria->compare('gg_class',$this->gg_class,true);
$criteria->compare('gg_name',$this->gg_name,true);
$criteria->compare('gg_title',$this->gg_title,true);
$criteria->compare('gg_description',$this->gg_description,true);
$criteria->compare('gg_date_modified',$this->gg_date_modified,true);
$criteria->compare('gg_status',$this->gg_status);
$criteria->compare('User.username',$this->gg_user_modified_rel,true); // use table alias name and specify relationship field property
return new CActiveDataProvider($this, array(
'criteria'=>$criteria,
'sort'=>array(
'attributes'=>array(
'gg_user_modified_rel' => array( // specify relationship field property
'asc'=>'User.username', // specify table alias name
'desc'=>'User.username DESC', // specify table alias name
),
'*',
),
),
));
}
... and setting up the view like this...
<?php $this->widget('bootstrap.widgets.TbGridView',array(
'id'=>'gallery-group-grid',
'dataProvider'=>$model->search(),
'filter'=>$model,
'columns'=>array(
'gg_id',
'gg_name',
array(
'name'=>'gg_user_modified_rel', // specify relationship field property
'value'=>'$data->ggUserModified->username' // specify relationship name
),
'gg_date_modified',
array(
'name'=>'gg_status',
'value'=>'$data->getStatusName()',
'filter'=>Yii::app()->params['globalDmpLookups']['generalStatus'],
'htmlOptions'=>array('style'=>'width: 120px'),
),
array('header'=>'Item Count','value'=>'$data->ggChildCount'),
array(
'class'=>'bootstrap.widgets.TbButtonColumn',
),
),)); ?>
filterHtmlOptions is the HTML options for the table row element, not for the input.
what is the value of Yii::app()->params['globalDmpLookups']['generalStatus']?
if you want to set the filter dropdown's id attribute, set the HTML attributes on the dropdown.
for example :
// ..
'columns'=>array(
array(
'name' => 'majorId',
'filter' => CHtml::activeDropDownList($model, 'majorId', CHtml::listData(
Major::model()->findAll(), "id", "name"),
array(
'empty' => '=== Pilih Jurusan ===',
'id' => 'YOUR_ID'
)
),
),
),
// ..

Accessing value of indirectly related models

I am displaying a CGridView below CDetailView on view.php page for Company model. I have problem in displaying values in CGridView using company details. The company model has an array of CompanyAddresses which is used as CArrayDataProvider for CGridView.
$config = array();
$dataProvider = new CArrayDataProvider($rawData=$model->companyAddresses,$config);
$this->widget('zii.widgets.grid.CGridView', array(
'dataProvider'=>$dataProvider
, 'columns'=>array(
//'id',
array('header'=>'SN.',
//'value'=>'++$row', // may nt work with pagination but the below does work
'value'=>'$this->grid->dataProvider->pagination->currentPage * $this->grid->dataProvider->pagination->pageSize + ($row+1)',
),
'address',
array(
'name'=>'Tehsil',
//'value'=> Utility::getTehsilName(Tehsil::model()->findByPk('tehsil_id')),
'value'=> Utility::getTehsilName($this->loadModel('tehsil_id')),
//'value'=> Tehsil::model()->findByAttributes( array('id' => 'tehsil_id' ) )->name,
),
array(
'name'=>'address_tag_id',
'value'=>AddressTag::model()->findByPk('address_tag_id'),
),
)
));
I am not able to fetch Tehsil_Name from Tehsil Table which has its ID inside CompanyAddress table.
Your using value attribute is wrong, check this:
'value'=>function($data){
return Utility::getTehsilName($data->tehsil_id);
},
value is a php expression that is evaluated to produce the contents of the gridview cell as below
'value' => 'Utility::getTehsilName($this->grid->controller->loadModel($data->tehsil_id))'
If you had used relation chaining to solve this your expression would have been simplified to say:
'value' => '$data->model1->tehsil->name'
where model1 is the middle relation.

Data isn't displaying from another table in CGridView Widget

I have two table Event and EventCategory. I am using zii.widgets.grid.CGridView widget to display all the events in the admin section.
I have created the following relations between tables.
Relation in EventCategory model:
'event' => array(self::HAS_MANY, 'Event', 'category_id'),
Relation in Event model:
'category' => array(self::BELONGS_TO, 'EventCategory', 'category_id'),
The following code I am using to display the Events:
<?php $this->widget('zii.widgets.grid.CGridView', array(
'id'=>'event-grid',
'dataProvider'=>$model->search(),
'filter'=>$model,
'summaryText'=> '',
'columns'=>array(
array('header'=>'Id','name'=>'event_id','filter'=>''),
'event_code',
'category.evntcatm_name',
'event_name',
array(
'class'=>'CButtonColumn',
'htmlOptions'=>array('class'=>'actions aligncenter'),
'deleteButtonImageUrl'=>false,
'updateButtonImageUrl'=>false,
'viewButtonImageUrl'=>false
),
),
)); ?>
'category.evntcatm_name' doesn't display anything. It is just creating the blank column with NO ERROR. What I am missing here.
Please try something like it
$data->category->evntcatm_name
You should use code like this:
'columns' = array(
/*YOUR DATA*/
array(
'name' => 'category_id',
'value' => function($data) {
return !empty($data->category) ? $data->category->evntcatm_name : null;
}),
)
This way can solve your problem with "Trying to get property of non-object". If you see blank cell in grid that means you miss relation (or it doesnt exist, in this way you should check relation condition or database)
Here is a few wild guesses:
Is category.evntcatm_name correctly spelled?
Is there actually data in the evntcatm_name field to begin with?
I know it might sound too simple to miss, but the error almost has to be on that level.
Try finding a category using the primary key and output it's evntcatm_name.
$cat = EventCategory::model()->findByPk(1);
echo $cat->evntcatm_name;
Maybe if you could share your schema for those two tables?
You can use
array(
'header' => 'Category Title',
'value' => '$data->category->evntcatm_name'
),
instead of 'category.evntcatm_name'
The model instance is not object now in the Cgidview:
Try
$data['category']['evntcatm_name'];

How to convert model data objects array to dataProvider

Suppose I have model User which have many to many relation to itself named as friends.
so $user->friends (or $model->friends in view) gives me an array of User objects. I wanted to display the friends as gridview. But CGridView data as dataProvider object. Googling for it found the way to convert array of model objects to dataProvider object as given below.
$this->widget('zii.widgets.grid.CGridView', array(
'id' => 'gridUser',
'dataProvider' => new CArrayDataProvider($model->friends, array()),
));
Now using this I get an error
Property "User.id" is not defined.
UPDATE
public function relations()
{
return array(
'friends' => array(self::MANY_MANY, 'User', 'friendship(user_id, friend_id)'),
);
}
I use two stage building the provider shown below. But I found that it gives you trouble in terms of Pagination. I have not bothered to resolve that problem since am doing other things
$dataProvider = new CArrayDataProvider('User');
$dataProvider->setData($model->friends);
$this->widget('zii.widgets.grid.CGridView', array(
'id' => 'gridUser',
'dataProvider' =>$dataProvider,
));
That being said, your code should work (see the example below from API docs). I suspect there is wrong attribute in your relations than the provided code. Re-check the relation definition if it is ok
From Yii docs:
$rawData=Yii::app()->db->createCommand('SELECT * FROM tbl_user')->queryAll();
// or using: $rawData=User::model()->findAll(); <--this better represents your question
$dataProvider=new CArrayDataProvider($rawData, array(
'id'=>'user',
'sort'=>array(
'attributes'=>array(
'id', 'username', 'email',
),
),
'pagination'=>array(
'pageSize'=>10,
),
));
Got it :) , i can use CActiveDataProvider instead of CArrayDataProvider as given below
$this->widget('zii.widgets.grid.CGridView', array(
'id' => 'gridUser',
'dataProvider' => new CActiveDataProvider('User', array(
'data'=>$model->friends,
)),
//...... columns display list.....
));
Anyways thanks for the reply #Stefano

Categories