Coldfusion 8's CFGRID

One of the tags to receive an upgrade in CF8 is the CFGRID tag. I can honestly say that I have never had a need to use this tag in the past although for some I can see that it 'could' have been useful.

The added support comes in the form of: type="html",bind,bindOnLoad,pageSize,prefesrbPageOnSort,stripeRows,stripeRowColor.

Lets focus for a minute on the new bind attribute. This attribute allows you to specify an expression to fill the grids contents. This expression can come in three flavors: You can bind directly to a CFC, a javascript function, or additionaly a URL.

The old restriction on the cfgrid is still in place, that being that it has to live within the bounds of a CFFORM tag, that's a small price to pay for ajax functionality right?

So here is a code snippet of the cfgrid in action:

<cfform name="tableform">
   <cfgrid format="html" name="grid_Tables" pagesize="7" selectmode="row"
bind="cfc:components.artgallery.artist.getArtists({cfgridpage},{cfgridpagesize},{cfgridsortcolumn},{cfgridsortdirection})">

                  <cfgridcolumn name="ARTISTID" display="No"/>
                  <cfgridcolumn name="FIRSTNAME" header="FIRSTNAME" >
                  <cfgridcolumn name="LASTNAME" header="LASTNAME" >
                  <cfgridcolumn name="CITY" header="CITY" >
                  <cfgridcolumn name="STATE" header="STATE" >
   </cfgrid>
</cfform>
</cfoutput>

Nothing too fancy other than the bind right? lets look at that a little closer.

bind="cfc:components.artgallery.artist.getArtists({cfgridpage},{cfgridpagesize},{cfgridsortcolumn},{cfgridsortdirection})"
In the bind expression we specify that we are going to be calling a CFC directly, followed by the dot notation down to the component and finishing off with the method (getArtists). Following the method call are the arguments, the grid requires all of the arguments you see here, and the curly braces indicate that they are bound to the grid itself. This way when someone clicks on a row header it will automatically refresh the grid by calling the CFC again with the gridsortcolumn and gridsortdirection arguments, nifty huh?

Here is what it looks like using the default styling:

You should immediately notice the bar at the bottom. This additional little functionality provides automatic paging of your data and you set that by specifiying the pageSize attribute. This value is automatically passed onto your cfc as well.

Lets take a quick look at the code for the Artist cfc:

<cffunction name="getArtists" access="remote">
      <cfargument name="page" required="yes">
      <cfargument name="pageSize" required="yes">
      <cfargument name="gridsortcolumn" required="yes">
      <cfargument name="gridsortdirection" required="yes">

   <cfquery name="members" datasource="cfartgallery">
      SELECT ARTISTID, FIRSTNAME, LASTNAME, CITY, STATE
      FROM ARTISTS
      <cfif gridsortcolumn neq ''>
      order by #gridsortcolumn# #gridsortdirection#
      </cfif>
   </cfquery>
   <cfreturn queryconvertforgrid(members,page,pagesize)/>
   </cffunction>

Nothing new here, or is there? Well if you spotted the queryconvertforgrid function as new you are right, its nothing I built, its a new function desiged specifically for converting a query into something that the cfgrid can use, it also takes the page, and pagesize attributes as arguments so it only passes back the specific page needed.

Another thing, if you have firebug installed you will be able to see how the call is made to your cfc. For my example I left out the argument collection: http://localhost/mycf/components/artgallery/artist.cfc?method=getArtists&returnFormat=json&argumentCollection=

for binding to CFC's coldfusion automatically appends the argument pair "returnFormat=json" this ensures that what you get back is a valid json dataset.

There is a lot more you can do with the cfgrid and a bit of javascript coding, you could use the and tags which allow you to interact with your grid by attaching events handlers to specific events in the grid and then performing actions.

You could quite easily set up master/deatail pages using ajax calls to get the data and update a detail form on the same page. And then update the data asynchronously and then at the same time automatically refresh the grid, pretty darn cool!

In future posts I will explore setting up a master detail form and creating editable grids, and exploring some of the other new features of Coldfusion 8

Related Blog Entries

Comments
Gary's Gravatar Fixed a typo in the gridsortdirection argument, would generate an error when
you clicked on one of the column headers.
# Posted By Gary | 6/20/07 3:12 AM
abul's Gravatar Is it possible to add image in a cfgrid in Ajax.
# Posted By abul | 8/1/07 8:14 AM
Gary Gilbert's Gravatar Abul,

Sorry at the moment it is not possible to create custom renderers for cfgrid. It may be possible if you manipulate the base ext.grid objects column model after Coldfusion writes the code.

Your best choice is to use the ext grid. I have a tutorial on ext grid with custom renderer: http://www.garyrgilbert.com/blog/index.cfm/2007/7/...
# Posted By Gary Gilbert | 8/1/07 8:42 AM
Hal Helms's Gravatar Actually, you can have images in a cfgrid, as well as other HTML, but you'll have to add this to your query itself. Cfgrid will render any HTML (including calls to images) found there. Ray Camden blogged about this recently.
# Posted By Hal Helms | 8/15/07 9:47 AM
Gary Gilbert's Gravatar @Hal,

Thanks for the info Hal. I didn't think to add the img tag directly in the query. I guess as you say you can display just about anything in the grid. I was more thinking in the lines of having a cell renderer not formulating html on the server-side and sending it to the front end.
# Posted By Gary Gilbert | 8/16/07 4:00 AM
Kebab Dylan's Gravatar ok, so I am trying to get this to work and i am getting a "error:http: Error invoking CFC /club.cfc : Not Found"

if i call the method directory from the cfml file, no problem, but once I try to use binding, it cannot find the cfc.

any ideas?
# Posted By Kebab Dylan | 10/10/07 1:06 PM
Gary Gilbert's Gravatar @kebab,

can you get to your cfc using a url? for example I have a cfc in webroot\dev\com\gg called fileExplorer.cfc and to access the getDirectories method in the cfc I can use the URL below

http://www.garyrgilbert.com/dev/com/gg/fileexplore...=

which returns a result to me in a json array.

The bind attribute would therefore look like "cfc:dev.com.gg.fileExplorer.getDirectories({cftreeitempath},{cftreeitemvalue})"

As a side note you can NOT use a cf mapping your cfc MUST be web accessible!
# Posted By Gary Gilbert | 10/10/07 4:34 PM
Ryan's Gravatar I have it all setup, but the problem I am running into is that there is an error stating it cannot execute the query, even though I put the query on another page, and dump it out, it shows up fine.
# Posted By Ryan | 10/19/07 8:26 AM
Kebab Dylan's Gravatar yes. it is accessible and i can call the get method and get back text...
# Posted By Kebab Dylan | 11/2/07 2:55 PM
Tre's Gravatar In past versions of the grid there was not a way to select multiple rows, how about this version?
# Posted By Tre | 11/14/07 11:52 AM
Felipe's Gravatar Hi there guys, one question.. I need to have a dropdown "cfselect" that will trigger some code to refresh the html grid with different queries... I have all figured it out except the function to call the cfgrid from the cfselect onchange using the new html type in cf8.

Any help?

Thanks in advance.
# Posted By Felipe | 11/20/07 1:37 AM
Gary Gilbert's Gravatar If I understand correctly you want the cfgrid to refresh with new information when you select something in the cfselect right?

In order to do that you would bind the grid to the onchange event of the cfselect. To do that you would change the bind expression on your grid.
<cfselect name="myselect" bind="cfc:mycfc.getSelectData()" bindonload="true">
<cfgrid ..... bind="cfc:mycfc.getGridData({cfgridpage},{cfgridpagesize},{cfgridsortcolumn},{cfgridsortdirection},{myselect})"

This will automatically tie your grid to the value field of your select.
# Posted By Gary Gilbert | 11/20/07 4:38 AM
Gary Gilbert's Gravatar I wrote a blog entry on how to bind a grid to a select box

http://www.garyrgilbert.com/blog/index.cfm/2007/11...
# Posted By Gary Gilbert | 11/21/07 9:49 AM