hydra12’s blog

Tech Stuff, TCEA, PHP, etc.

CakePHP, EXTJS DataGrid, and Paging

Filed under: Cake, ExtJS — admin at 11:28 am on Tuesday, January 15, 2008

I was asked earlier if it was possible to use the datagrid with cake 1.2’s paginator. I did some checking, and I don’t think it is. The paginate function is closely tied to the paginate helper. When you call paginate in the controller, all I ever got back was the same results as findAll.

Fear not, however, because pagination with the datagrid is fairly painless. If you don’t have a working datagrid already, please work through my earlier tutorial first.

Ok, to add pagination, we first have to change our getAllUsers controller function. Change the definition to this:

function getAllUsers($limit=10, $page=0)

Page and Limit are how the model knows which chunk of data to pull from the database. We are just setting some defaults.

Now add the following lines inside the controller (I put mine right after the Configure::write line):

if(!empty($_POST['limit']))
	$limit = $_POST['limit'];
 
if(!empty($_POST['start']))
	$page = ($_POST['start']/$limit)+1;

ExtJS uses posts to send the paging params to cake. The problem is, it sends limit and start, while we need limit and page. The first part just checks to see if $_POST[’limit’] is empty, and if it isn’t, it assigns it to $limit. The second part is similar, but more complicated. For ExtJS, start is which record to start with. If we divide start by limit, we should get the page we are on. However, it didn’t work quite right. By adding 1 to the total, things now work.

Now, change the definition of $userA to read like this:

$userA = $this->User->findAll(null,'*','id ASC', $limit, $page); //gets all the User records and sorts them by username alphabetically.

Note - I left this out the first time. Thanks, Yoris, for catching this.

OK, that takes care of the controller, now we just need to modify myScript.js a little bit. Modify your grid code to look like this:

grid = new Ext.grid.GridPanel({
	ds: ds,
	columns: [
		{id:'id',header: "ID", width: 50, sortable: true, dataIndex: 'id'},
		{header: "Username", width: 125, sortable: true, dataIndex: 'username'},
		{header: "Full name", width: 125, sortable: true, dataIndex: 'fullname'}
	],
	cm: cm,
	stripeRows: true,
	height: 350,
	width: 350,
	title: 'Data Grid',
	bbar: new Ext.PagingToolbar({
		pageSize: 10,
		store: ds,
		displayInfo: true,
		displayMsg: 'Displaying users {0} - {1} of {2}',
		emptyMsg: 'No users to display'		
	})
});

bbar is what we are adding (I think it means bottom bar). Page size is the same as limit (I think). The rest is just configuration. Now change your ds.load command to look like this:

ds.load({params:{start:0, limit:10}}); //This loads data from the database into the datastore.

That’s it! You should now have a paging bar at the bottom.

17 Comments »

551

Comment by aamir

January 16, 2008 @ 3:21 am

Thank you so much for such a great tutorial. Please let me know if you have some tutorial to edit the values of grid.
God bless you

561

Comment by Inma

January 18, 2008 @ 4:29 am

Thanks for this tutorial!!

I’m trying to run this example. But, for the moment, it doesn’t work in my test.

I think that I do something wrong in my controller.

Could you show your full controller code?

Thanks a lot!

Kind regards,
Inma.

562

Comment by Inma

January 18, 2008 @ 6:33 am

Another question:
I know that debugging info breaks the XMLHttpRequest.
So, how can I view SQL querys from CakePHP debugging when I use it together with ExtJS?

If I set Configure::write(’debug’, ‘2′); on getAllUsers function, it doesn’t show anything in the view, no datagrid and no SQL querys from CakePHP debug.

Thanks again!
Inma.

570

Comment by admin

January 21, 2008 @ 8:24 am

@inma - this is indeed a problem. I don’t know the best way to do it, but here’s what I do. I set debug to ‘2′ and call getAllUsers directly. Once I have getAllUsers working, I set debug to 0 and focus on getting index to work. If getAllUsers is returning the correct data in the proper json format, then any problems are on the index side.

Another option is to use cake’s logging functions. The logs are in /tmp/logs. You have two - debug.log and error.log. You can log using one of these forms in your controller:

$this->log($variable); //logs to error.log
$this->log($variable, LOG_DEBUG); //logs to debug.log

I hope that helps.

572

Comment by hal

January 21, 2008 @ 9:20 am

Great, pagination now works,
I also did sorting, somehow i had hard time getting the post values from extjs grid, end up using the following, dontknow if this is the way to get post params. but it works

function getAllUarcusers()
{
Configure::write(’debug’, ‘0′);
$this->layout = “ajax”;

if (!empty($this->params[’form’][’limit’]))
$limit = $this->params[’form’][’limit’];
else $limit = 0;

if (!empty($this->params[’form’][’start’]))
$start = $this->params[’form’][’start’];
else $start = 1;

if (!empty($this->params[’form’][’dir’]))
$dir = $this->params[’form’][’dir’];
else $dir = ‘ASC’;

if (!empty($this->params[’form’][’sort’]))
$col = $this->params[’form’][’sort’];
else $col = ‘username’;

573

Comment by Inma

January 22, 2008 @ 2:48 am

OK. Finally it works, and turns on remote sorting.

Thanks to both!

589

Comment by inma

January 28, 2008 @ 3:05 am

Like said AAMIR, could you show how to edit the grid values from a form?

Meanwhile, I will try to do it by myself…

Thanks!

594

Comment by tiago.bar

February 3, 2008 @ 7:04 pm

Is there a way that a caller form can pass params to filter the data grid?

Example: A search action contains the grid (search.ctp with a search.js that load the grid) and a index action call it submiting a form with the field “name” to filter.

Thanks for the greats tutorials!

596

Comment by Arungopan

February 19, 2008 @ 1:14 am

Thank you for such a great tutorial.
Can you please give me some tutorial to delete and add the records of extjs grid using cake php.

600

Comment by admin

February 19, 2008 @ 7:52 pm

@arungopan - I’ll try to get to that sometime soon. I’m still working out some bugs in my form submits with extjs, and I want to get that fixed before I add extra complexity to things.

601

Comment by Yoris

February 22, 2008 @ 4:20 pm

Hydra, you defined :
{
if(!empty($_POST[’limit’]))
$limit = $_POST[’limit’];

if(!empty($_POST[’start’]))
$page = ($_POST[’start’]/$limit)+1;
}

but then in the controller you don´t use them … the controller keeps asking for the total amount of the users… here
{
$userA = $this->User->findAll(null,’*',’username ASC’);
}
you omitted sth in the controller didnt ya?
hope you to get around this… thx in advance

602

Comment by admin

February 25, 2008 @ 2:50 pm

@Yoris - you’re right! Thanks for catching that for me. I updated the tutorial.

611

Comment by wiewior

March 19, 2008 @ 1:48 pm

BIG Thanks for this tutorial!!
You’re great!!

633

Comment by Ianemv

December 17, 2008 @ 9:11 pm

I believe the find should be

$userA = $this->User->find(’all’, array(’limit’ => $limit,’page’=>$page));

Your previous find function is already deprecated on cake 1.2 version.

I enjoy this tutorial.Works fine.

636

Comment by Tom

March 7, 2009 @ 4:14 am

Thx for this tutorial.
But how can i get a additional parameter in data.php

I will make:
”SELECT * FROM table where url = $resquest[’url’]”

is this the right way ?

var store = new Ext.data.JsonStore({
url: ‘data.php?url=Ext.get(’url’).dom.value’,

637

Comment by Brett

April 15, 2009 @ 8:54 pm

You can use cakes pagination, just add something like this to the controller:

$this->paginate[’limit’] = isset($this->params[’form’][’limit’]) ? $this->params[’form’][’limit’] : ‘10′;
$this->paginate[’page’] = isset($this->params[’form’][’start’]) ? (($this->params[’form’][’start’]/$this->params[’form’][’limit’])+1) : ‘1′;
$users = $this->paginate();

638

Pingback by DuncanBrown » Blog Archive » Paginating Data with CakePHP and Yahoo! User Interface DataTable

May 7, 2009 @ 1:44 pm

[…] should go to this post http://www.ntatd.org/mark/?p=32 by Mark Buckner (aka hydra12) describing how to use cakePHP with ExtJS DataGrid, for the […]

RSS feed for comments on this post. TrackBack URI

Leave a comment

XHTML: You can use these tags: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <code> <em> <i> <strike> <strong>