Yii Framework Forum: Solved with custom pagination: Cpagination Only Works On First Page. - Yii Framework Forum

Jump to content

Page 1 of 1
  • You cannot start a new topic
  • You cannot reply to this topic

Solved with custom pagination: Cpagination Only Works On First Page. Recieving POST variables from a form makes CPaginator losing the data Rate Topic: -----

#1 User is offline   benelli 

  • Junior Member
  • Pip
  • Yii
  • Group: Members
  • Posts: 21
  • Joined: 29-May 14
  • Location:Spain

Posted 29 May 2014 - 10:04 AM

Hello all, i am new to Yii and this forum. I am starting a new project and after some researchs i have decided to learning this framework and use it.

Now i am stuck with the pagination. I have a form, sending by POST only 2 variables to an action. This action generates the pagination, and the first page is shown well, but if i try to navigate through the CLinkPager there is no data shown, even the CLinkpager itself has disappeared.

I have 3 days lost yet with this problem. I have read almost every pagination related post without finding a solution, and i have changed my code almost 100 times. First i tried to paginate from a model function directly (that returned a CActiveDataProvider) but i was unable to even show the first page. I have seen all the pagination examples triggered from the controller, i mean always the querys are executed from the actions in the controller (in order to paginate the data).

There is no way to paginate a CActiveDataProvider object directly, for example returned from a model function?

Now the code is this, works for only first page:

Controller:

public function actionIndexSearch() {

        //here some trivial validations and a debug echo 
        if ($_POST['city'] != null && isset($_POST['type'])) {
            //I tried also defining constants for ensure the data is not lost by pagination (maybe recalling this action again without POST data...)
            //define(_CITY, $_POST['city']);
            //define(_TYPE, $_POST['type']);
            $cityId = $_POST['city'];
            $type = $_POST['type'];
            echo "dentro";
        }
        //Another echo for watching the behavior.
        echo "fuera";
        //Creating the data to paginate and its pagination:
        $c = new CDbCriteria();
        $location = Location::model()->tableName();
        $c->compare('t.event_type_id', $type, false);
        $c->join = 'inner join ' . $location . ' l on l.city_id = "' . $cityId . '"';
        $itemcount = LiveEvent::model()->count($c);
        $pages = new CPagination($itemcount);
        $pages->setPageSize(2);
        $pages->applyLimit($c);

        Yii::app()->setTheme('urbandow');
        $this->layout = 'main';
        $this->render('eventsResults', array(
            'data' => LiveEvent::model()->findAll($c),
            'pages' => $pages,
            //'cityId' => $cityId,
            //'type' => $type,
        ));
    }



In my view, for example:


 <?php
                                $this->widget('CLinkPager', array(
                                'pages' => $pages,
                                    ));
?> 

<?php
                    
                    
                    foreach ($data as $data1){
                          echo $data1->title;
                    }
                    
?>  



Ok, and in my model i had this (now it is not used, but i think if we want put all the logic in the models there should be a way to paginate it...):

public static function listByCity($cityId, $type) {

        $c = new CDbCriteria();

        $location = Location::model()->tableName();
        $c->compare('t.event_type_id', $type, false);
        $c->join = 'inner join ' . $location . ' l on l.city_id = "' . $cityId .'"';
        return new CActiveDataProvider($this, array(
            'criteria' => $c,
            'pagination' => 2,
        ));
    }


Thank you very much!
0

#2 User is offline   Ankit Modi 

  • Master Member
  • PipPipPipPip
  • Yii
  • Group: Members
  • Posts: 893
  • Joined: 19-February 13
  • Location:India

Posted 31 May 2014 - 12:21 PM

just past the proceeOutput when page is render...

for ex..
$this->render('index',array(),false,true);

Thanks,
Ankit Modi
Skype : amodi06
0

#3 User is offline   benelli 

  • Junior Member
  • Pip
  • Yii
  • Group: Members
  • Posts: 21
  • Joined: 29-May 14
  • Location:Spain

Posted 02 June 2014 - 04:32 AM

Hello again.

I have tried it Ankit, if i use TRUE the page is not rendered. If i use FALSE the behavior doesn't change.

http://www.yiiframew...r#render-detail

If i declare the variables $cityId=1 and $type=1 inside the action method instead of retrieving the values from the post data, the pagination works well in all pages. I mean the data is lost when the pagination buttons are used, because probably the method actionIndexSearch() is called again, and its called without recieving any post data, so the new page have no data and is shown empty (and without paginator).

How is this solved in Yii? How can i use a form to get some data and then paginate it?
0

#4 User is offline   Ankit Modi 

  • Master Member
  • PipPipPipPip
  • Yii
  • Group: Members
  • Posts: 893
  • Joined: 19-February 13
  • Location:India

Posted 02 June 2014 - 11:03 PM

View Postbenelli, on 02 June 2014 - 04:32 AM, said:

Hello again.

I have tried it Ankit, if i use TRUE the page is not rendered. If i use FALSE the behavior doesn't change.

http://www.yiiframew...r#render-detail

If i declare the variables $cityId=1 and $type=1 inside the action method instead of retrieving the values from the post data, the pagination works well in all pages. I mean the data is lost when the pagination buttons are used, because probably the method actionIndexSearch() is called again, and its called without recieving any post data, so the new page have no data and is shown empty (and without paginator).

How is this solved in Yii? How can i use a form to get some data and then paginate it?


Try this jquery.js fals when action was called



$cs = Yii::app()->clientScript;

$cs->reset();

$cs->scriptMap = array(

'jquery.js' => false, // prevent produce jquery.js in additional javascript data

);
Thanks,
Ankit Modi
Skype : amodi06
0

#5 User is offline   benelli 

  • Junior Member
  • Pip
  • Yii
  • Group: Members
  • Posts: 21
  • Joined: 29-May 14
  • Location:Spain

Posted 03 June 2014 - 08:14 AM

View PostAnkit Modi, on 02 June 2014 - 11:03 PM, said:

Try this jquery.js fals when action was called



$cs = Yii::app()->clientScript;

$cs->reset();

$cs->scriptMap = array(

'jquery.js' => false, // prevent produce jquery.js in additional javascript data

);


Hello again, thanks for the reply! But it hasn't solved my problem :(

I tried also disable al jquery in the page without success.

I still searching the way to paginate with Yii :(
0

#6 User is offline   Ankit Modi 

  • Master Member
  • PipPipPipPip
  • Yii
  • Group: Members
  • Posts: 893
  • Joined: 19-February 13
  • Location:India

Posted 04 June 2014 - 06:27 AM

Hi,

can you please post the admin view?
Just conform you can use the Clink Pager or not?

Thanks,
Ankit Modi
Skype : amodi06
0

#7 User is offline   benelli 

  • Junior Member
  • Pip
  • Yii
  • Group: Members
  • Posts: 21
  • Joined: 29-May 14
  • Location:Spain

Posted 04 June 2014 - 10:37 AM

View PostAnkit Modi, on 04 June 2014 - 06:27 AM, said:

Hi,

can you please post the admin view?
Just conform you can use the Clink Pager or not?


I attach the file, the line 107 is where i implement the pagination, thanks!

Attached File(s)


0

#8 User is offline   Ankit Modi 

  • Master Member
  • PipPipPipPip
  • Yii
  • Group: Members
  • Posts: 893
  • Joined: 19-February 13
  • Location:India

Posted 05 June 2014 - 11:44 PM

Hi Man,

As a friend I think your code is not correct and it's not proper way..

please don't keep in mind..Posted Image

Please use this proper Yii syntax..

http://www.yiiplaygr...taview/gridView


if you have any query please contact me on Skype : amodi06
if I am available I will help you.


Regards,
Ankit Modi
Thanks,
Ankit Modi
Skype : amodi06
0

#9 User is offline   benelli 

  • Junior Member
  • Pip
  • Yii
  • Group: Members
  • Posts: 21
  • Joined: 29-May 14
  • Location:Spain

Posted 03 July 2014 - 06:26 AM

Hello Again.

Finally i didn't understand how to use the Yii pagination alone (without any other helper like gridview), so i have solved the pagination problem creating it by AJAX from scratch by my self.

Thanks anyway!
0

#10 User is offline   Rajith R 

  • Master Member
  • PipPipPipPip
  • Yii
  • Group: Members
  • Posts: 884
  • Joined: 20-April 11
  • Location:India

Posted 03 July 2014 - 07:32 AM

This is easy to implement.

In controller or in the same view

This is Just an example.

                $criteria = new CDbCriteria;
		$criteria->compare('is_deleted',0);  // normal DB field
                $criteria->order = 'first_name ASC';
		
		$total = Students::model()->count($criteria);
		$pages = new CPagination($total);
        $pages->setPageSize(Yii::app()->params['listPerPage']);
        $pages->applyLimit($criteria);  // the trick is here!
		$posts = Students::model()->findAll($criteria);
		
		 
		$this->render('manage',array('model'=>$model,
		'list'=>$posts,
		'pages' => $pages,
		'item_count'=>$total,
		'page_size'=>Yii::app()->params['listPerPage'],)) ;







In view file
<?php 
                              $this->widget('CLinkPager', array(
                              'currentPage'=>$pages->getCurrentPage(),
                              'itemCount'=>$item_count,
                              'pageSize'=>$page_size,
                              'maxButtonCount'=>5,
                              //'nextPageLabel'=>'My text >',
                              'header'=>'',
                            'htmlOptions'=>array('class'=>'pages'),
                            ));?>

Rajith Ramachandran,
Wiwo inc.
| Mobile: 919995504508
0

#11 User is offline   Rajith R 

  • Master Member
  • PipPipPipPip
  • Yii
  • Group: Members
  • Posts: 884
  • Joined: 20-April 11
  • Location:India

Posted 03 July 2014 - 07:34 AM

Avoid POST use GET
Rajith Ramachandran,
Wiwo inc.
| Mobile: 919995504508
0

#12 User is offline   benelli 

  • Junior Member
  • Pip
  • Yii
  • Group: Members
  • Posts: 21
  • Joined: 29-May 14
  • Location:Spain

Posted 29 October 2014 - 04:28 AM

Hi all again. I'm coming to show you how i did it.

I used a jQuery pagination plugin for navigation buttons, making a custom AJAX call to an action in my handmade AjaxController, then the action do the logic part of the pagination and finally it returns to the AJAX a renderpartial of a custom view filled with the paginated data.

The Ajax call trigged:

function realizaProceso(id, level, limit, current){
    
    var parametros = {
            "id" : id,
            "level" : level,
            "current" : current,
            "limit" : limit
    };

    $.ajax({
            data:  parametros,
            url:   "<?php echo Yii::app()->createUrl('ajax/HotelAjaxPagination'); ?>",
            type:  'post',
            beforeSend: function () {
                    //$("#content").html("Procesando, espere por favor...");
            },
            success:  function (response) {
                    $("#content").html(response);
            }
    });


}


The action in the AjaxController. It also has a dynamic tablename selection based on the "level" parameter given.

public function actionHotelAjaxPagination() {

        $id = $_POST['id'];
        $level = $_POST['level'];
        $limit = $_POST['limit'];
        $current = $_POST['current'];
        
        $searchCriteria = new CDbCriteria(); 
        $searchCriteria->select = "t.*";
        $searchCriteria->order = "t.title asc";
        $searchCriteria->offset = ($current*PAGINATION_ITEM_LIMIT);
        $searchCriteria->limit = (PAGINATION_ITEM_LIMIT); // or $limit
        
        $baseTableName = "country";
        
        if ($level > 0){
            for ($i = 0; $i < $level; $i++)
                $baseTableName.="_sub";
            $crossTableName = $baseTableName."_to_hotel";
            $fk = $baseTableName . "_id";
            $searchCriteria->join = "INNER JOIN ". $crossTableName ." ct ON ct.hotel_id = t.id";
            $searchCriteria->addCondition("ct.".$fk." = ".$id);            
            $data = Hotel::model()->findAll($searchCriteria);  
        }else{
            $searchCriteria->join = "INNER JOIN country_sub cs ON t.country_sub_id = cs.id";
            $searchCriteria->addCondition("cs.country_id = ".$id);
            $data = Hotel::model()->findAll($searchCriteria);
        }
         
        $this->renderPartial('hotelSearchPagination', array('data' => $data, 'current' => $current, 'count' => count($data)));

        Yii::app()->end();
    }


And just iterate over results in our hotelSearchPagination view file to show whatever we want.


The jQuery plugin i'm using:


jQuery.fn.pagination = function(maxentries, opts){
    
	opts = jQuery.extend({
		num_display_entries:5,
		num_edge_entries:0,
		link_to:"#",
		prev_text:"First ",
		next_text:" Last",
		ellipse_text:"...",
		prev_show_always:true,
		next_show_always:true,
		callback:function(){return false;}
	},opts||{});
	
	return this.each(function() {
		/**
		 * Calculate the maximum number of pages
		 */
		function numPages() {
			return Math.ceil(maxentries/opts.items_per_page);
		}
		
		/**
		 * Calculate start and end point of pagination links depending on 
		 * current_page and num_display_entries.
		 * @return {Array}
		 */
		function getInterval()  {
			var ne_half = Math.ceil(opts.num_display_entries/2);
			var np = numPages();
			var upper_limit = np-opts.num_display_entries;
			var start = current_page>ne_half?Math.max(Math.min(current_page-ne_half, upper_limit), 0):0;
			var end = current_page>ne_half?Math.min(current_page+ne_half, np):Math.min(opts.num_display_entries, np);
			return [start,end];
		}
		
		/**
		 * This is the event handling function for the pagination links. 
		 * @param {int} page_id The new page number
		 */
		function pageSelected(page_id, evt){
			current_page = page_id;
			drawLinks();
			var continuePropagation = opts.callback(page_id, panel);
			if (!continuePropagation) {
				if (evt.stopPropagation) {
					evt.stopPropagation();
				}
				else {
					evt.cancelBubble = true;
				}
			}

                        ////////////////////// MY ACTION:
                        updateContent(current_page);
                        
			return continuePropagation;
		}
		
		/**
		 * This function inserts the pagination links into the container element
		 */
		function drawLinks() {
			panel.empty();
			var interval = getInterval();
			var np = numPages();
			// This helper function returns a handler function that calls pageSelected with the right page_id
			var getClickHandler = function(page_id) {
				return function(evt){ return pageSelected(page_id,evt); }
			}
			// Helper function for generating a single link (or a span tag if it's the current page)
			var appendItem = function(page_id, appendopts){
                            
                                    page_id = page_id<0?0:(page_id<np?page_id:np-1); // Normalize page id to sane value
                                    appendopts = jQuery.extend({text:page_id+1, classes:""}, appendopts||{});
                                    if(page_id == current_page){
                                            if (isNaN(appendopts.text))
                                                var lnk = jQuery("<a class='enlace_paginacion' href='#'> "+(appendopts.text)+"</span>");
                                            else
                                                var lnk = jQuery("<a class='enlace_paginacion_activo' href='#'> "+(appendopts.text)+"</span>");
                                    }
                                    else
                                    {
                                            var lnk = jQuery("<a class='enlace_paginacion'>"+(appendopts.text)+"</a>")
                                                    .bind("click", getClickHandler(page_id))
                                                    .attr('href', opts.link_to.replace(/__id__/,page_id));
                                    }
				
				if(appendopts.classes){lnk.addClass(appendopts.classes);}
				panel.append(lnk);
			}
			// Generate "Previous"-Link
			if(opts.prev_text && (current_page > 0 || opts.prev_show_always)){
				appendItem(0,{text:opts.prev_text, classes:"prev"});
			}
//			// Generate starting points
			if (interval[0] > 0 && opts.num_edge_entries > 0)
			{
				var end = Math.min(opts.num_edge_entries, interval[0]);
				for(var i=0; i<end; i++) {
					appendItem(i);
				}
				if(opts.num_edge_entries < interval[0] && opts.ellipse_text)
				{
					jQuery("<span>"+opts.ellipse_text+"</span>").appendTo(panel);
				}
			}
			// Generate interval links
			for(var i=interval[0]; i<interval[1]; i++) {
				appendItem(i);
			}
			// Generate ending points
			if (interval[1] < np && opts.num_edge_entries > 0)
			{
				if(np-opts.num_edge_entries > interval[1]&& opts.ellipse_text)
				{
					jQuery("<span>"+opts.ellipse_text+"</span>").appendTo(panel);
				}
				var begin = Math.max(np-opts.num_edge_entries, interval[1]);
				for(var i=begin; i<np; i++) {
					appendItem(i);
				}
				
			}
			// Generate "Next"-Link
			if(opts.next_text && (current_page < np-1 || opts.next_show_always)){
				appendItem(numPages(),{text:opts.next_text, classes:"next"});
			}
		}
		
		// Extract current_page from options
		var current_page = opts.current_page;
		// Create a sane value for maxentries and items_per_page
		maxentries = (!maxentries || maxentries < 0)?1:maxentries;
		opts.items_per_page = (!opts.items_per_page || opts.items_per_page < 0)?1:opts.items_per_page;
		// Store DOM element for easy access from all inner functions
		var panel = jQuery(this);
		// Attach control functions to the DOM element 
		this.selectPage = function(page_id){ pageSelected(page_id);}
		// When all initialisation is done, draw the links
		drawLinks();
        // call callback function
        opts.callback(current_page, this);
	});
}




Thank you all for your answers.
0

#13 User is offline   Rajith R 

  • Master Member
  • PipPipPipPip
  • Yii
  • Group: Members
  • Posts: 884
  • Joined: 20-April 11
  • Location:India

Posted 30 October 2014 - 01:59 AM

:) :)
Rajith Ramachandran,
Wiwo inc.
| Mobile: 919995504508
0

Share this topic:


Page 1 of 1
  • You cannot start a new topic
  • You cannot reply to this topic

1 User(s) are reading this topic
0 members, 1 guests, 0 anonymous users