我有一个gridview,其中包含一个复选框列,并且还使用了分页。当我检查第一页中的一些复选框并导航到第二页并在第二页中检查另一页时,我在第一页中检查的选项不会保留在那里。是否可以在分页期间保留复选框值?
Gridview代码
$widget = $this->widget('zii.widgets.grid.CGridView', array(
'dataProvider' => $model->search(),
'cssFile' => Yii::app()->baseUrl . '/media/js/admin/css/admingridview.css',
//'filter' => $model,
'ajaxUpdate' => true,
'enablePagination' => true,
'columns' => array(
array(
'name' => 'id',
'header' => '#',
'value' => '$this->grid->dataProvider->pagination->currentPage * $this->grid->dataProvider->pagination->pageSize + ($row+1)',
),
array(
'class' => 'CCheckBoxColumn',
'selectableRows' => '2',
'header' => 'Selected',
),
array(
'name' => 'fb_user_id',
'header' => 'FaceBook Id',
'value' => 'CHtml::encode($data->fb_user_id)',
),
array(
'name' => 'first_name',
'header' => 'Name',
'value' => 'CHtml::encode($data->first_name)',
),
array(
'name' => 'email_id',
'header' => 'Email',
'value' => 'CHtml::encode($data->email_id)',
),
array(
'name' => 'demo',
'type' => 'raw',
'header' => "Select",
'value' => 'CHtml::checkBox("email[]","",array("class"=>"check","value"=>$data->email_id))',
),
),
));
修改
记住网格视图中所选选项的扩展程序,请检查此链接Selgridview
感谢 bool.dev
答案 0 :(得分:7)
您可以使用会话/ cookie来存储选中的值。我不太确定如何使cookie工作,所以我会告诉你如何使用会话。特别是yii创建的用户会话。
现在使用会话我们需要将已检查(和未经检查)的id传递给控制器,因此我们将修改每次ajax更新(即分页之间)发送到控制器的数据,为此我们利用CGridView的beforeAjaxUpdate
选项。
我还在您的代码中使用以下CCheckBoxColumn 代替(当然您可以根据自己的需要修改解决方案):
array(
'name' => 'demo',
'type'=>'raw',
'header' => "Select",
'value' => 'CHtml::checkBox("email[]","",array("class"=>"check","value"=>$data->email_id))',
),
<?php $this->widget('zii.widgets.grid.CGridView', array(
// added id of grid-view for use with $.fn.yiiGridView.getChecked(containerID,columnID)
'id'=>'first-grid',
'dataProvider'=>$model->search(),
'cssFile' => Yii::app()->baseUrl . '/media/js/admin/css/admingridview.css',
// added this piece of code
'beforeAjaxUpdate'=>'function(id,options){options.data={checkedIds:$.fn.yiiGridView.getChecked("first-grid","someChecks").toString(),
uncheckedIds:getUncheckeds()};
return true;}',
'ajaxUpdate'=>true,
'enablePagination' => true,
'columns' => array(
array(
'name' => 'id',
'header' => '#',
'value' => '$this->grid->dataProvider->pagination->currentPage * $this->grid->dataProvider->pagination->pageSize + ($row+1)',
),
array(
'name' => 'fb_user_id',
'header' => 'FaceBook Id',
'value' => 'CHtml::encode($data->fb_user_id)',
),
array(
'name' => 'first_name',
'header' => 'Name',
'value' => 'CHtml::encode($data->first_name)',
),
array(
'name' => 'email_id',
'header' => 'Email',
'value' => 'CHtml::encode($data->email_id)',
),
/* replaced the following with CCheckBoxColumn
array(
'name' => 'demo',
'type'=>'raw',
'header' => "Select",
'value' =>'CHtml::checkBox("email[]","",array("class"=>"check","value"=>$data->email_id))',
),
*/
array(
'class' => 'CCheckBoxColumn',
'selectableRows' => '2',
'header'=>'Selected',
'id'=>'someChecks', // need this id for use with $.fn.yiiGridView.getChecked(containerID,columnID)
'checked'=>'Yii::app()->user->getState($data->email_id)', // we are using the user session variable to store the checked row values, also considering here that email_ids are unique for your app, it would be best to use any field that is unique in the table
),
),
));
?>
特别注意beforeAjaxUpdate
和CCheckBoxColumn的代码,在beforeAjaxUpdate中,我们传递checkedIds
作为已经检查过的所有id(在本例中为email_ids)的csv字符串,{{1作为所有未经检查的ID的csv字符串,我们通过调用函数uncheckedIds
来获取未选中的框,紧接着就是这样。请注意,当我测试时,我使用了一个整数id字段(我的表)作为唯一字段,而不是电子邮件字段。
getUncheckeds()
函数可以在gridview的视图文件中的任何位置注册:
getUncheckeds()
在上面的功能中,请注意选择器以及Yii::app()->clientScript->registerScript('getUnchecked', "
function getUncheckeds(){
var unch = [];
/*corrected typo: $('[name^=someChec]') => $('[name^=someChecks]') */
$('[name^=someChecks]').not(':checked,[name$=all]').each(function(){unch.push($(this).val());});
return unch.toString();
}
"
);
和each
功能。
完成后,我们需要修改此视图的控制器/操作。
push
就是这样,它现在应该有效。
答案 1 :(得分:1)
为了开发该计划,您需要知道在导航时会发生什么。
当您导航到分页页面时,会进行ajax调用并接收新数据,并从CActive Record或任何数据源获取。新数据符合数据库记录或源记录。当你再次回到上一页时,会进行Ajax调用并更新内容,这与数据库中的相同。
我觉得你应该暂时保存已检查项目的数据,并在行动时将其永久化。
你可以做这样的事情
<script type="text/javascript">
$("input:checkbox").click(function () {
var thisCheck = $(this);
if (thisCheck.is (':checked')){
// do what you want here, the way to access the text is using the
// $(this) selector. The following code would output pop up message with
// the selected checkbox text
$(this).val());
}
});
</script>
您可以在某处保存临时存储空间
答案 2 :(得分:0)
也可以在普通表单上提交:
我想将此添加为对bool.dev的回答的评论,但我还没有足够的声誉来做到这一点。所以我不得不单独回答。
bool.dev,你的答案很棒,而且效果很好,比x。
但是,按照预期,它仅在ajax调用更新gridview时有效。我有一个gridview构成表单的一部分,所以我希望它也可以正常提交表单,否则当表单上有其他验证错误时,复选框不会再次加载。
所以,除了你所做的,我在表格上添加了隐藏字段,例如:
<input type="hidden" name='checkedBox1' id='checkedBox1' value=''>
<input type="hidden" name='uncheckedBox1' id='uncheckedBox1' value=''>
然后,在提交表单之前,我的sumbit按钮运行你的getChecked()和getUncheckeds()函数,并将结果存储在隐藏字段中:
if ($('#checkedBox1').length >0) {$('[name=checkedBox1]').val(getChecked());}
if ($('#uncheckedBox1').length >0) {$('[name=uncheckedBox1]').val(getUncheckeds());}
在控制器中,除了检查$ _GET ['checkedIds']之外,还检查$ _POST ['checkedBox1']并将其值存储到会话中,方法与$ _GET ['checkedIds']相同,使用相同的会话变量。
使用$ _POST ['uncheckedBox1']执行相同操作。
这应该有效。