CListView group by item

Hi,

I am new to yii and i wanted to know if it is possible to group a CListView result in the view?

For example i have a list with photos some are published some are not how can i group them so i can list them by the group published or not published.

Greetings Arjan

PhotosController.php




	public function actionUploaded()

	{

		$dataProvider=new CActiveDataProvider('Photos', array(

			'criteria'=>array(

				'condition'=>'user_id='.Yii::app()->user->getId().' AND published=0',

			),

			'pagination'=>array(

				'pageSize'=>20,

			),

		));

		$this->render('uploaded',array(

			'dataProvider'=>$dataProvider,

		));

	}



views index.php




<?php

$this->breadcrumbs=array(

	'Photos',

);


$this->menu=array(

	array('label'=>'Upload Photos', 'url'=>array('upload')),

	array('label'=>'Manage Photos', 'url'=>array('admin')),

);

?>


<h1>Photos</h1>


<?php $this->widget('zii.widgets.CListView', array(

	'dataProvider'=>$dataProvider,

	'itemView'=>'_view',

));?>



Views _view.php




<div class="view">


	<?php echo CHtml::link(CHtml::image('images/thumbnails/'.$data->id.'_thumb.jpg', ''), array('view', 'id'=>$data->id)); ?>

    <br />


	<b><?php echo CHtml::encode($data->getAttributeLabel('user_id')); ?>:</b>

	<?php echo CHtml::encode($data->getProfile($data->user_id)->firstname." ".$data->getProfile($data->user_id)->lastname); ?>

	<br />


	<b><?php echo CHtml::encode($data->getAttributeLabel('catid')); ?>:</b>

	<?php echo CHtml::encode($data->catid); ?>

	<br />


	<b><?php echo CHtml::encode($data->getAttributeLabel('title')); ?>:</b>

	<?php echo CHtml::encode($data->title); ?>

	<br />


	<b><?php echo CHtml::encode($data->getAttributeLabel('equipment')); ?>:</b>

	<?php echo CHtml::encode($data->equipment); ?>

	<br />

    

	<b><?php echo CHtml::encode($data->getAttributeLabel('original')); ?>:</b>

	<?php echo CHtml::encode($data->original); ?>

	<br />

        

	<b><?php echo CHtml::encode($data->getAttributeLabel('size')); ?>:</b>

	<?php echo CHtml::encode($data->getReadableFileSize()); ?>

	<br />


	<b><?php echo CHtml::encode($data->getAttributeLabel('created')); ?>:</b>

	<?php echo CHtml::encode($data->created); ?>

	<br />


	<b><?php echo CHtml::encode($data->getAttributeLabel('published')); ?>:</b>

	<?php echo CHtml::encode($data->getReadablePublished()); ?>

	<br />

    

</div>



Did something myself but don’t know if it is a proper way to do it like this.

PhotosController




	/**

	 * Lists all photos by user_id.

	 */

	public function actionIndex()

	{

		$group=new CActiveDataProvider('Photos', array(

			'criteria'=>array(

				'select'=>'DISTINCT published',

			),

			'pagination'=>array(

				'pageSize'=>20,

			),

		));	

		

		$dataProvider=new CActiveDataProvider('Photos', array(

			'criteria'=>array(

				'condition'=>'user_id='.Yii::app()->user->getId(),

			),

			'pagination'=>array(

				'pageSize'=>20,

			),

		));

		//var_dump($dataProvider);

		$this->render('index',array(

			'dataProvider'=>$dataProvider,

			'group'=>$group,

		));		

	}



Views index.php




<?php

$this->breadcrumbs=array(

	'Photos',

);


$this->menu=array(

	array('label'=>'Upload Photos', 'url'=>array('upload')),

	array('label'=>'Manage Photos', 'url'=>array('admin')),

);

?>


<h1>Photos</h1>


<table width="100%" cellspacing="0" cellpadding="2">

   

<?php foreach($group->data as $gd){ ?>


        <tr>

            <td><?php echo CHtml::encode($gd->getReadablePublished()); ?></td>

        </tr>      

		<?php foreach($dataProvider->data as $dpd){ ?>


			<?php if ( $dpd->getReadablePublished() == $gd->published ) { ?>

                    <tr style="width:25%; height:150px; float:left">

                    <td><?php echo CHtml::link(CHtml::image('images/thumbnails/'.$dpd->id.'_thumb.jpg', ''), array('view', 'id'=>$dpd->id)); ?></td>

                    </tr>

            <?php } ?>


		<?php } ?>

		

<?php } ?>


</table>



Welcome to the forum.

The idea is correct, in the inner cicle you should build dataproviders depending on the group.

Thanks for reply, can you give me an example of what you mean by build dataproviders depending on the group and how can i use pagination on each group?

Greetings Arjan

Hello,

This is my first post so thank you for any guide or tip that you could provide me. I am new in yii and this framework is awesome.

I have the same problem, I already sucessfully loop to my categories but i dont know how to send the selected dataprovider to to clistview. In the current example it render the entire provider. any ideas ?


foreach ($category as $c)

{

	echo $c->category;

	echo '</br>';

	


	foreach ($dataProvider->data as $dp)

	{

		if ($c->id_category == $dp->id_category)

			{

			

    		$this->widget('zii.widgets.CListView', array(

			'dataProvider'=>$dataProvider,

			'itemView'=>'_view',

			));

			}

	}


}



Don’t worry, I fix it using this code. Hope that will be usefull to someone else.




foreach ($category as $c)

{

	echo '<div class="categories">';

	echo $c->category;

	

	

	$arrcat=array();

	$i=0;

	

	foreach ($dataProvider->data as $dp)

	{

		if ($c->id_category == $dp->id_category)

			{

			

			$arrcat[$i] = $dp->id_person;

    	$i++;

    	

			}

	}


$catdataProvider = new CActiveDataProvider ('Person', array (  

'criteria' => array ( 

    		        'condition' => 'id_state IN(1,3,4) AND id_person IN ('.implode(",", $arrcat).')'  ,

    			'limit' => 8,

			),

));


			

$this->widget('zii.widgets.CListView', array(

			'dataProvider'=>$catdataProvider,

			'itemView'=>'_view',

			));

		echo '</div>';	

}