There are many times when I am writing an application I need to display data in a table. Most of the time a simple HTML table styled with CSS is all that I need but occasionally I want a bit more. Today we’ll look at designing a plugin for jQuery that will add some advanced features such as row selection and sorting.
Design Goals
Starting out we are going to keep this pretty simple and as it progresses we’ll add more features.
For now we are going to start with a hand coded HTML table and CSS. In a later post we’ll look at populating the grid from a data source.
In this post today we’ll apply the CSS to the table but will expand this to a skinning system later on.
We’ll also be applying the row selection feature today.
Starting Point
Let’s use a simple table as out starting point.
<table cellpadding="0" cellspacing="0" class="easygrid">
<tr>
<th>Name</th>
<th>Title</th>
<th>Age</th>
</tr>
<tr>
<td>Bill</td>
<td>CEO</td>
<td>53</td>
</tr>
<tr>
<td>Jason</td>
<td>Developer</td>
<td>29</td>
</tr>
<tr>
<td>Sue</td>
<td>Accountant</td>
<td>37</td>
</tr>
<tr>
<td>Frank</td>
<td>HR Manager</td>
<td>42</td>
</tr>
<tr>
<td>Jill</td>
<td>Graphic Artist</td>
<td>31</td>
</tr>
</table>
Basic Style
Next we will apply some basic CSS to make our grid look nice.
body, table {
font-family: verdana, arial, sans-serif;
}
table.easygrid {
font-size: 11px;
width: 600px;
border-top: 1px solid #b8b8b8;
border-left: 1px solid #b8b8b8;
}
table.easygrid th {
text-align: left;
padding: 5px;
background: #424242;
color: white;
border-bottom: 1px solid #b8b8b8;
border-right: 1px solid #b8b8b8;
}
table.easygrid td {
padding: 5px;
border-bottom: 1px solid #b8b8b8;
border-right: 1px solid #b8b8b8;
}
table.easygrid td.alt {
background: #f6f3f6;
}
table.easygrid td.selected {
background: navy;
color: white;
font-weight: bold;
}
Building The Plugin
Here is the basic layout of our plugin. We’ll look at implementing those functions in a minute.
This is pretty simple so far. We have our default values, we merge the user passed options with the defaults, and then call two methods on each jQuery instance.
(function($) {
$.fn.easygrid = function(options) {
var defaults = {
alternateBackground: true,
allowRowSelect: true
};
options = $.extend(defaults, options);
return this.each(function(index, table) {
setAlternateBackground($('tr:odd td', table), options.alternateBackground);
rowSelection(table, options.allowRowSelect, options.alternateBackground);
});
};
})(jQuery)
Here is our setAlternateBackground method. Note we are passing all the odd rows found in the current table.
function setAlternateBackground(rows, alt) {
if(alt == true) {
rows.attr('class', this.className + ' alt');
}
}
This function appends the alt CSS class to each row if alternate row backgrounds is enabled.
The next function adds a click handler to each row to implement the row selection functionality.
function rowSelection(table, allowSelect, alt) {
if(allowSelect == true) {
$('tr', table).click(function() {
//reset all rows
$('tr', table).each(function() {
$('td', this).each(function(index, cell) {
$(cell).attr('class', cell.className.replace(' selected'));
});
});
//restore alt backgrounds
setAlternateBackground($('tr:odd td', table), alt);
//select this row
$('td', this).attr('class', this.className + ' selected');
});
}
}
There is a little more involved with this function. If this feature is enabled we are adding a click handler to all the rows in the table.
First the click handler will clear any selected rows and reapply the alternate background colors. I am not sure why this gets lost.
Then, finally, the row that was clicked is selected by applying the selected CSS class to each cell of the row.