My issue is two-fold. First, I'm unable to correctly set the keyField for CArrayDataProvider, all I'm getting back is a string instead of a value. Second, I'm trying to use the keyField inside of CArrayDataProvider to set an id on the button in each row inside of CGridView. The reason I want to do this is so that I can pass the id value onward to an ajax function (if there's a better way to do this in Yii, I'm all ears). Any help would be much appreciated, thanks in advance!
I also posted this question once on Yii's forums. I normally wouldn't repost, but I have had a hard time getting answers there, as opposed to stack overflow, you guys are the best! Here's the link to my original post if anyone is interested.
Here is how I'm building the array that I'm using as my RAW data:
foreach ($items as $item) {
$tableRow = array("id"=>$item["Id"], "Organization"=>$item["Organization"], "Roles"=>$item["Roles"]);
$return_items[] = $tableRow;
}
Here is the CArrayDataProvider setup I'm using. I noticed that 'keyField' is not being given the id value, just the string 'id':
$dataProvider=new CArrayDataProvider($return_items, array(
'keyField'=>'id',
'sort'=>array(
'attributes'=>array(
'Organization',
'Roles',
),
),
'pagination'=>array(
'pageSize'=>10,
),
));
Lastly, here is the CGridView I'm trying to setup in the view. All that appears on the button is the id tag, but no value:
$this->widget('zii.widgets.grid.CGridView', array(
'dataProvider'=>$authItems,
'columns'=>array(
'Organization',
'Roles',
array('name'=>'',
'type'=>'raw',
'htmlOptions'=>array('id'=>'id'),
'value'=>'CHtml::button("Edit Roles", array("data-toggle"=>"modal", "data-target"=>"#roles-modal"))'),
),
));
Try passing it via CHtml::button which you have already applied. E.g.
'value'=>'CHtml::button("Edit Roles", array(
"id"=>$data["id"],
"data-toggle"=>"modal",
"data-target"=>"#roles-modal"
))'),
Related
I have modified my model so that the data displayed in cgridview is unique per user, depending on the account type...
However I need to create a form from another model where I could get the data from the cgridview via dropdown...
I used this code at first...
<?php
$this->widget('ext.select2.ESelect2',array(
'model'=>$model,
'attribute'=>'pr_id',
'data'=>$model->searchPatient(),//function to provide data
// or
//'data'=>CHtml::listData(PatientRecord::model()->findAll(), 'id', 'first_name')
);
?>
but it returns all of the contents of the PatientRecord model, I tried using a condition before planning to retrieve the contents from the cgridview...
$doctor= Yii::app()->user->id;
CHtml::listData(PatientRecord::model()->findAll( array(
'condition'=>'doctor_id=:doctor_id',
'params' => array(':doctor_id' => $doctor)
)
);), 'id', 'first_name')
it didn't have an error but it didn't display anything on the dropdown either...
any suggestions?
I think the problem is with a ; and ) in your model code, try this:
$doctor= Yii::app()->user->id;
CHtml::listData(PatientRecord::model()->findAll( array(
'condition'=>'doctor_id=:doctor_id',
'params' => array(':doctor_id' => $doctor)
)
), 'id', 'first_name');
You should always enable error logging in local environment, this will help you find any errors in your code. Here is a link on how to enable error logging.
Hope that helps :)
I try to create dropdown-list with Yii, using listData and activeDropDownList.
I use the examples found on the web, but it refuses to create the optgroups for me.
$data = CHtml::listData(MyModel::model()->getEntries(0), 'id', 'text', 'group');
Generates an array as expected:
Array([group1] => Array([10]=>FirstEntry, [20]=>SecondEntry),
[group2]=>Array([30]=>firstEntryGroup2, [40]=>firstEntryGroup2))
And so on. So it's an associative array filled with sub-arrays...
But when I use
echo CHtml::activeDropDownList($model, 'dropdownName', $data);
All I get is a flat dropdown without the optgroups. Just the entries from the sub-arrays...
Yii 1.1.6 (I read something about safe-attributes and tried to implement it, but with no success...
The old answer below is incorrect. Sorry. You create optgroups using a 'group' attribute in your drop down data array.
array(
array('id'=>256,'text'=>'TV','group'=>'Electrical'),
array('id'=>257,'text'=>'Radio','group'=>'Electrical'),
);
http://www.yiiframework.com/forum/index.php/topic/6903-how-can-i-generate-a-select-list-with-optgroup/
Old answer:
There is a great gist here that shows how do create what you're after: https://gist.github.com/StandardNerd/2909111
<?php echo CHtml::dropDownList('Cars', 'car_id', array(
'Mazda'=>array(
'mazda-rx7'=>'RX7',
'mazda-rx5'=>'RX5',
),
'Volvo'=>array(
'volvo-b9tl'=>'B9TL',
'volvo-l90e-radlader'=>'L90E Radlader',
),
)); ?>
You're currently using an activeDropDownList which should only be different because you add your $model variable instead of 'Cars' and tweak the function
One of solutions is anonymous function.
$data = CHtml::listData(
MyModel::model()->getEntries(0),
'id',
'text',
function(MyModel $aMyModelInstance){
return $aMyModelInstance->getLocalizedGroupNameForThisInstance();
});
The Zend Form is proving to be a bit tricky for me, even as much as I am working with it lately...
I have this form and I am attempting to dynamically create the several checkboxes for it. It is working out alright, except I cannot seem to get the 'value' attribute to change.
In my Zend form class I have this snippet...
// psychotic symptoms
$this->addElement('checkbox', 'psychoticsymptom', array(
'label' => 'psychoticsymptom',
'name' => 'psychoticsymptom',
));
In my view (phtml) I am calling it like this...
<div class="element">
<?php // Psychotic Symptoms
$Criteria = new Criteria();
$Criteria->add( DictionaryPeer::CATEGORY, 'MAR: Psychotic Symptoms' );
$Criteria->addAscendingOrderByColumn( 'Ordinal' );
$this->PsychoticSymptomsList = DictionaryPeer::doSelect( $Criteria );
foreach( $this->PsychoticSymptomsList as $Symptom ) {
$form->psychoticsymptom->setValue($Symptom->getDictionaryId());
$form->psychoticsymptom->setAttrib('name', $Symptom->getWord());
echo $Symptom->getDictionaryId(); // prove my id is coming through... (it is)
$form->psychoticsymptom->getDecorator('label')->setTag(null);
echo $form->psychoticsymptom->renderViewHelper();
$form->psychoticsymptom->setLabel($Symptom->getWord());
echo $form->psychoticsymptom->renderLabel();
echo '<br />';
}
?>
</div>
Everything seems to be working fine, except the value attribute on each checkbox is rendering a value of '1'. I have tried moving the 'setValue' line to several different positions, as to set the value before the form element renders but I am having no luck getting this to work. It's worth any effort to me because I need to do the same type of operation in many areas of my application. I would have done this a bit different too, but I am re-factoring another application and am trying to keep some things unchanged (like the database for instance).
Any help is much appriciated
Thanks
you can try to overwrite the "checkedValue" and "uncheckedValue". check this reference
$this->addElement('checkbox', 'psychoticsymptom', array(
'label' => 'psychoticsymptom',
'name' => 'psychoticsymptom',
'checkedValue' => 'checked Value',
'uncheckedValue' => 'unchecked Value'
));
You seem to only have one psychoticsymptom element "checkbox" which your adding (changing) the value too for each $this->PsychoticSymptomsList.
Maybe you would be better off using a multicheckbox element instead.
Thanks in advance to anyone who can help. I've been searching for an answer, but haven't found one yet. I've run into "solutions" that haven't worked that run from 1 line, to re-writing an entire class.
I've got the "grid" to show the relation, and am able to use the search feature. What I can't figure out is the sort feature. The column header becomes non-clickable once the below changes have been made.
This is what I have:
The relation name/label is "company," setup in Employee model.
Table: Employee -- Column: idCompany
&
Table: Company -- Column: companyNick
admin.php - VIEW
<?php $this->widget('zii.widgets.grid.CGridView', array(
'id'=>'employee-grid',
'dataProvider'=>$model->search(),
'filter'=>$model,
'columns'=>array(
array(
'name'=>'company',
'value'=>'$data->company->companyNick',
),
'lastName',
'firstName',
ETC...
Employee.php - MODEL
public function search()
{
// Warning: Please modify the following code to remove attributes that
// should not be searched.
$criteria=new CDbCriteria;
//Company Relation Search
$criteria->compare('company.companyNick',$this->company,true);
$criteria->with='company';
//stock
$criteria->compare('idEmployee',$this->idEmployee,true);
$criteria->compare('idAccount',$this->idAccount,true);
ETC...
I've been having the same problems and in the end solved it this way:
Model Search method:
$sort = new CSort();
$sort->attributes = array(
'assignedTo'=>array(
'asc'=>'(SELECT surname from people
WHERE people.person_id = t.assigned_to) ASC',
'desc'=>'(SELECT surname from people
WHERE people.person_id = t.assigned_to) DESC',
),
'*', // add all of the other columns as sortable
);
View file:
$this->widget('zii.widgets.grid.CGridView', array(
'id'=>'tasks-grid',
'dataProvider'=>$model->search(),
//'filter'=>$model,
'columns'=>array(
'task',
array(
'header'=>'Assigned To',
'value'=> '$data->assignedTo->surname.", ".$data->assignedTo->forename',
'name'=> 'assignedTo',
'sortable'=>TRUE,
),
'due_date',
'status',
),
));
This way I'm selecting a single field from the related table into the order by clause and then ordering by that, you create the table join in the expression, in this case it is -people.person_id = t.assigned_to (where t is a table alias provided by yii). This is perhaps not the most efficient way to create the order by clause but it works!
This seems to be a daily question on [yii]. Strip that stuff out of your search function, and add a filter attribute to your CGridView column like so:
array(
'name'=>'company',
'value'=>'$data->company->companyNick',
'filter' => CHtml::listData(Company::model()->findAll(),'id','nick'),
),
There is also good explanation how to do this on Yii web site Wiki page:
http://www.yiiframework.com/wiki/281/searching-and-sorting-by-related-model-in-cgridview/
I like Mike H's answer. I also want to point out that you could, instead of entering the raw SQL, use with() to perform a relational query and then set select to false to prevent actually loading the related models. You can also use the related attribute's attributeLabel in the view by passing the dot-notated string, e.g.,:
// Controller
$gridDataProvider = new CActiveDataProvider('EmrFormPatientTie', array(
'criteria'=>array(
'condition'=>'flag_locked=0',
'with'=>array('patient'=>array(
'select'=>false, // Perform relational query without loading related models
)),
),
'pagination'=>(array('pageSize'=>15)),
'sort'=>array(
'attributes'=>array(
'patient.display_id'=>array(
'asc'=>'patient.display_id',
'desc'=>'patient.display_id DESC',
),
'*', // Make all other columns sortable, too
),
),
));
// View
array(
'name'=>'patient.display_id',
'value'=>'$data->patient->display_id',
),
I recently started to build a custom keyword search using Yii 1.1.x
The search works 100%. But as soon as I sort the columns and use pagination in the admin view the search gets lost and all results are shown. So with otherwords it's not filtering so that only the search results show. Somehow it resets it.
In my controller my code looks as follows
$builder=Messages::model()->getCommandBuilder();
//Table1 Columns
$columns1=array('0'=>'id','1'=>'to','2'=>'from','3'=>'message','4'=>'error_code','5'=>'date_send');
//Table 2 Columns
$columns2=array('0'=>'username');
//building the Keywords
$keywords = explode(' ',$_REQUEST['search']);
$count=0;
foreach($keywords as $key){
$kw[$count]=$key;
++$count;
}
$keywords=$kw;
$condition1=$builder->createSearchCondition(Messages::model()->tableName(),$columns1,$keywords,$prefix='t.');
$condition2=$builder->createSearchCondition(Users::model()->tableName(),$columns2,$keywords);
$condition = substr($condition1,0,-1) . " OR ".substr($condition2,1);
$condition = str_replace('AND','OR',$condition);
$dataProvider=new CActiveDataProvider('Messages', array(
'pagination'=>array(
'pageSize'=>self::PAGE_SIZE,
),
'criteria'=>array(
'with'=>'users',
'together'=>true,
'joinType'=>'LEFT JOIN',
'condition'=>$condition,
),
'sort'=>$sort,
));
$this->render('admin',array(
'dataProvider'=>$dataProvider,'keywords'=>implode(' ',$keywords),'sort'=>$sort
));
and my view looks like this
$this->widget('zii.widgets.grid.CGridView', array(
'dataProvider'=>$dataProvider,
'columns'=>array(
'id',
array(
'name'=>'user_id',
'value'=>'CHtml::encode(Users::model()->getReseller($data->user_id))',
'visible'=>Yii::app()->user->checkAccess('poweradministrator')
),
'to',
'from',
'message',
/*
'date_send',
*/
array(
'name'=>'error_code',
'value'=>'CHtml::encode($data->status($data->error_code))',
),
array(
'class'=>'CButtonColumn',
'template'=>'{view} {delete}',
),
),
));
I really do not know what do do anymore since I'm terribly lost, any help will be hihsly appreciated
You could set a user state for your search criteria and test for the state each time the controller loads your view.
Something along the lines of
if(isset($_REQUEST['search'])){
$keywords = explode(' ',$_REQUEST['search']);
Yii::app()->user->setState('keywords',$keywords);
}
else if(Yii::app()->user->hasState('keywords')){
$keywords=Yii::app()->user->getState('keywords');
}
The drawback here is the keywords state will be maintained for the length of the session.
that's why I dont' like these frameworks. In raw PHP I'd make it with just $link=http_build_query($_GET); and then use this link for both pagination and sorting. But you have to find a way to do the same using your framework ideology. I bet they have some example for such a commonplace task.