` rows
57 | that contain a `` element using jQuery's `.has()` method (ie, the header row,
58 | containing ` | ` elements, will remain at the top where it belongs).
59 |
60 | ```html
61 |
62 |
63 |
64 | |
65 | ...
66 |
67 |
68 |
69 |
70 | |
71 | ...
72 |
73 |
74 |
75 | ```
76 |
77 | If you want some imageless arrows to indicate the sort, just add this to your CSS:
78 |
79 | ```css
80 | th.sorted.ascending:after {
81 | content: " \2191";
82 | }
83 |
84 | th.sorted.descending:after {
85 | content: " \2193";
86 | }
87 | ```
88 |
89 | How cells are sorted
90 | ---
91 |
92 | At the moment cells are naively sorted using string comparison. By default, the ` | `'s text is used, but you can easily override that by adding a `data-sort-value` attribute to the cell. For example to sort by a date while keeping the cell contents human-friendly, just add the timestamp as the `data-sort-value`:
93 |
94 | ```html
95 | | March 7, 2012 |
96 | ```
97 |
98 | This allows you to sort your cells using your own criteria without having to write a custom sort function. It also keeps the plugin lightweight by not having to guess & parse dates.
99 |
100 | Defining custom sort functions
101 | ---
102 |
103 | If you have special requirements (or don't want to clutter your markup like the above example) you can easily hook in your own function that determines the sort value for a given cell.
104 |
105 | Custom sort functions are attached to `` elements using `data()` and are used to determine the sort value for all cells in that column:
106 |
107 | ```javascript
108 | // Sort by dates in YYYY-MM-DD format
109 | $('thead th.date').data('sortBy', function(th, td, tablesort) {
110 | return new Date(td.text());
111 | });
112 |
113 | // Sort hex values, ie: "FF0066":
114 | $('thead th.hex').data('sortBy', function(th, td, tablesort) {
115 | return parseInt(td.text(), 16);
116 | });
117 |
118 | // Sort by an arbitrary object, ie: a Backbone model:
119 | $('thead th.personID').data('sortBy', function(th, td, tablesort) {
120 | return App.People.get(td.text());
121 | });
122 | ```
123 |
124 | Sort functions are passed three parameters:
125 |
126 | * the ` | ` being sorted on
127 | * the ` | ` for which the current sort value is required
128 | * the `tablesort` instance
129 |
130 | Custom comparison functions
131 | ---
132 |
133 | If you need to implement more advanced sorting logic, you can specify a comparison function with the `compare` setting. The function works the same way as the `compareFunction` accepted by [`Array.prototype.sort()`](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/sort):
134 |
135 | ```javascript
136 | function compare(a, b) {
137 | if (a < b) {
138 | return -1; // `a` is less than `b` by some ordering criterion
139 | }
140 | if (a > b) {
141 | return 1; // `a` is greater than `b` by the ordering criterion
142 | }
143 |
144 | return 0; // `a` is equal to `b`
145 | }
146 | ```
147 |
148 | Events
149 | ---
150 |
151 | The following events are triggered on the `` element being sorted, `'tablesort:start'` and `'tablesort:complete'`. The `event` and `tablesort` instance are passed as parameters:
152 |
153 | ```javascript
154 | $('table').on('tablesort:start', function(event, tablesort) {
155 | console.log("Starting the sort...");
156 | });
157 |
158 | $('table').on('tablesort:complete', function(event, tablesort) {
159 | console.log("Sort finished!");
160 | });
161 | ```
162 |
163 | tablesort instances
164 | ---
165 |
166 | A table's tablesort instance can be retrieved by querying the data object:
167 |
168 | ```javascript
169 | $('table').tablesort(); // Make the table sortable.
170 | var tablesort = $('table').data('tablesort'); // Get a reference to it's tablesort instance
171 | ```
172 |
173 | Properties:
174 |
175 | ```javascript
176 | tablesort.$table // The being sorted.
177 | tablesort.$th // The currently sorted by (null if unsorted).
178 | tablesort.index // The column index of tablesort.$th (or null).
179 | tablesort.direction // The direction of the current sort, either 'asc' or 'desc' (or null if unsorted).
180 | tablesort.settings // Settings for this instance (see below).
181 | ```
182 |
183 | Methods:
184 |
185 | ```javascript
186 | // Sorts by the specified column and, optionally, direction ('asc' or 'desc').
187 | // If direction is omitted, the reverse of the current direction is used.
188 | tablesort.sort(th, direction);
189 |
190 | tablesort.destroy();
191 | ```
192 |
193 | Default Sorting
194 | ---
195 |
196 | It's possible to apply a default sort on page load using the `.sort()` method described above. Simply grab the tablesort instance and call `.sort()`, padding in the ` | ` element you want to sort by.
197 |
198 | Assuming your markup is `` and the column to sort by default is `` you would write:
199 |
200 | ```javascript
201 | $(function() {
202 | $('table.sortable').tablesort().data('tablesort').sort($("th.default-sort"));
203 | });
204 | ```
205 |
206 | Settings
207 | ---
208 |
209 | Here are the supported options and their default values:
210 |
211 | ```javascript
212 | $.tablesort.defaults = {
213 | debug: $.tablesort.DEBUG, // Outputs some basic debug info when true.
214 | asc: 'sorted ascending', // CSS classes added to ` | ` elements on sort.
215 | desc: 'sorted descending',
216 | compare: function(a, b) { // Function used to compare values when sorting.
217 | if (a > b) {
218 | return 1;
219 | } else if (a < b) {
220 | return -1;
221 | } else {
222 | return 0;
223 | }
224 | }
225 | };
226 | ```
227 |
228 | You can also change the global debug value which overrides the instance's settings:
229 |
230 | ```javascript
231 | $.tablesort.DEBUG = false;
232 | ```
233 |
234 | Alternatives
235 | ---
236 |
237 | I don't use this plugin much any more — most of the fixes & improvements are provided by contributors.
238 |
239 | If this plugin isn't meeting your needs and you don't want to submit a pull-request, here are some alternative table-sorting plugins.
240 |
241 | * [Stupid jQuery Table Sort](https://github.com/joequery/Stupid-Table-Plugin)
242 |
243 | _(Feel free to suggest more by [opening a new issue](https://github.com/kylefox/jquery-tablesort/issues/new))_
244 |
245 | Contributing
246 | ---
247 |
248 | As always, all suggestions, bug reports/fixes, and improvements are welcome.
249 |
250 | Minify JavaScript with [Closure Compiler](http://closure-compiler.appspot.com/home) (default options)
251 |
252 | Help with any of the following is particularly appreciated:
253 |
254 | * Performance improvements
255 | * Making the code as concise/efficient as possible
256 | * Browser compatibility
257 |
258 | Please fork and send pull requests, or [report an issue.](https://github.com/kylefox/jquery-tablesort/issues)
259 |
260 | # License
261 |
262 | jQuery tablesort is distributed under the MIT License.
263 | Learn more at http://opensource.org/licenses/mit-license.php
264 |
265 | Copyright (c) 2012 Kyle Fox
266 |
267 | Permission is hereby granted, free of charge, to any person obtaining
268 | a copy of this software and associated documentation files (the
269 | "Software"), to deal in the Software without restriction, including
270 | without limitation the rights to use, copy, modify, merge, publish,
271 | distribute, sublicense, and/or sell copies of the Software, and to
272 | permit persons to whom the Software is furnished to do so, subject to
273 | the following conditions:
274 |
275 | The above copyright notice and this permission notice shall be
276 | included in all copies or substantial portions of the Software.
277 |
278 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
279 | EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
280 | MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
281 | NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
282 | LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
283 | OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
284 | WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
285 |
--------------------------------------------------------------------------------
/bower.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "jquery-tablesort",
3 | "version": "0.0.11",
4 | "homepage": "https://github.com/kylefox/jquery-tablesort",
5 | "authors": [
6 | "Kyle Fox "
7 | ],
8 | "description": "A simple, lightweight jQuery plugin for creating sortable tables.",
9 | "main": "jquery.tablesort.js",
10 | "moduleType": [],
11 | "license": "MIT",
12 | "ignore": [
13 | "**/.*",
14 | "node_modules",
15 | "bower_components",
16 | "test",
17 | "tests"
18 | ],
19 | "dependencies": {
20 | "jquery": "1.8.0 - 2.2.x"
21 | }
22 | }
23 |
--------------------------------------------------------------------------------
/gulpfile.js:
--------------------------------------------------------------------------------
1 | var gulp = require('gulp');
2 | var uglify = require("gulp-uglify");
3 | var rename = require('gulp-rename');
4 |
5 |
6 | gulp.task('min', function() {
7 | gulp.src('jquery.tablesort.js')
8 | .pipe(uglify({preserveComments: 'license'}))
9 | .pipe(rename('jquery.tablesort.min.js'))
10 | .pipe(gulp.dest('.'));
11 | });
12 |
--------------------------------------------------------------------------------
/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
54 |
55 |
56 |
57 |
100 |
101 |
104 |
105 |
106 |
107 |
141 |
142 |
143 |
144 |
--------------------------------------------------------------------------------
/jquery.tablesort.js:
--------------------------------------------------------------------------------
1 | /*
2 | A simple, lightweight jQuery plugin for creating sortable tables.
3 | https://github.com/kylefox/jquery-tablesort
4 | Version 0.0.11
5 | */
6 |
7 | (function($) {
8 | $.tablesort = function ($table, settings) {
9 | var self = this;
10 | this.$table = $table;
11 | this.$thead = this.$table.find('thead');
12 | this.settings = $.extend({}, $.tablesort.defaults, settings);
13 | this.$sortCells = this.$thead.length > 0 ? this.$thead.find('th:not(.no-sort)') : this.$table.find('th:not(.no-sort)');
14 | this.$sortCells.on('click.tablesort', function() {
15 | self.sort($(this));
16 | });
17 | this.index = null;
18 | this.$th = null;
19 | this.direction = null;
20 | };
21 |
22 | $.tablesort.prototype = {
23 |
24 | sort: function(th, direction) {
25 | var start = new Date(),
26 | self = this,
27 | table = this.$table,
28 | rowsContainer = table.find('tbody').length > 0 ? table.find('tbody') : table,
29 | rows = rowsContainer.find('tr').has('td, th'),
30 | cells = rows.find(':nth-child(' + (th.index() + 1) + ')').filter('td, th'),
31 | sortBy = th.data().sortBy,
32 | sortedMap = [];
33 |
34 | var unsortedValues = cells.map(function(idx, cell) {
35 | if (sortBy)
36 | return (typeof sortBy === 'function') ? sortBy($(th), $(cell), self) : sortBy;
37 | return ($(this).data().sortValue != null ? $(this).data().sortValue : $(this).text());
38 | });
39 | if (unsortedValues.length === 0) return;
40 |
41 | //click on a different column
42 | if (this.index !== th.index()) {
43 | this.direction = 'asc';
44 | this.index = th.index();
45 | }
46 | else if (direction !== 'asc' && direction !== 'desc')
47 | this.direction = this.direction === 'asc' ? 'desc' : 'asc';
48 | else
49 | this.direction = direction;
50 |
51 | direction = this.direction == 'asc' ? 1 : -1;
52 |
53 | self.$table.trigger('tablesort:start', [self]);
54 | self.log("Sorting by " + this.index + ' ' + this.direction);
55 |
56 | // Try to force a browser redraw
57 | self.$table.css("display");
58 | // Run sorting asynchronously on a timeout to force browser redraw after
59 | // `tablesort:start` callback. Also avoids locking up the browser too much.
60 | setTimeout(function() {
61 | self.$sortCells.removeClass(self.settings.asc + ' ' + self.settings.desc);
62 | for (var i = 0, length = unsortedValues.length; i < length; i++)
63 | {
64 | sortedMap.push({
65 | index: i,
66 | cell: cells[i],
67 | row: rows[i],
68 | value: unsortedValues[i]
69 | });
70 | }
71 |
72 | sortedMap.sort(function(a, b) {
73 | return self.settings.compare(a.value, b.value) * direction;
74 | });
75 |
76 | $.each(sortedMap, function(i, entry) {
77 | rowsContainer.append(entry.row);
78 | });
79 |
80 | th.addClass(self.settings[self.direction]);
81 |
82 | self.log('Sort finished in ' + ((new Date()).getTime() - start.getTime()) + 'ms');
83 | self.$table.trigger('tablesort:complete', [self]);
84 | //Try to force a browser redraw
85 | self.$table.css("display");
86 | }, unsortedValues.length > 2000 ? 200 : 10);
87 | },
88 |
89 | log: function(msg) {
90 | if(($.tablesort.DEBUG || this.settings.debug) && console && console.log) {
91 | console.log('[tablesort] ' + msg);
92 | }
93 | },
94 |
95 | destroy: function() {
96 | this.$sortCells.off('click.tablesort');
97 | this.$table.data('tablesort', null);
98 | return null;
99 | }
100 |
101 | };
102 |
103 | $.tablesort.DEBUG = false;
104 |
105 | $.tablesort.defaults = {
106 | debug: $.tablesort.DEBUG,
107 | asc: 'sorted ascending',
108 | desc: 'sorted descending',
109 | compare: function(a, b) {
110 | if (a > b) {
111 | return 1;
112 | } else if (a < b) {
113 | return -1;
114 | } else {
115 | return 0;
116 | }
117 | }
118 | };
119 |
120 | $.fn.tablesort = function(settings) {
121 | var table, sortable, previous;
122 | return this.each(function() {
123 | table = $(this);
124 | previous = table.data('tablesort');
125 | if(previous) {
126 | previous.destroy();
127 | }
128 | table.data('tablesort', new $.tablesort(table, settings));
129 | });
130 | };
131 |
132 | })(window.Zepto || window.jQuery);
133 |
--------------------------------------------------------------------------------
/jquery.tablesort.min.js:
--------------------------------------------------------------------------------
1 | /*
2 | A simple, lightweight jQuery plugin for creating sortable tables.
3 | https://github.com/kylefox/jquery-tablesort
4 | Version 0.0.11
5 | */
6 | !function(t){t.tablesort=function(e,s){var i=this;this.$table=e,this.$thead=this.$table.find("thead"),this.settings=t.extend({},t.tablesort.defaults,s),this.$sortCells=this.$thead.length>0?this.$thead.find("th:not(.no-sort)"):this.$table.find("th:not(.no-sort)"),this.$sortCells.on("click.tablesort",function(){i.sort(t(this))}),this.index=null,this.$th=null,this.direction=null},t.tablesort.prototype={sort:function(e,s){var i=new Date,n=this,o=this.$table,l=o.find("tbody").length>0?o.find("tbody"):o,a=l.find("tr").has("td, th"),r=a.find(":nth-child("+(e.index()+1)+")").filter("td, th"),d=e.data().sortBy,h=[],c=r.map(function(s,i){return d?"function"==typeof d?d(t(e),t(i),n):d:null!=t(this).data().sortValue?t(this).data().sortValue:t(this).text()});0!==c.length&&(this.index!==e.index()?(this.direction="asc",this.index=e.index()):"asc"!==s&&"desc"!==s?this.direction="asc"===this.direction?"desc":"asc":this.direction=s,s="asc"==this.direction?1:-1,n.$table.trigger("tablesort:start",[n]),n.log("Sorting by "+this.index+" "+this.direction),n.$table.css("display"),setTimeout(function(){n.$sortCells.removeClass(n.settings.asc+" "+n.settings.desc);for(var o=0,d=c.length;o2e3?200:10))},log:function(e){(t.tablesort.DEBUG||this.settings.debug)&&console&&console.log&&console.log("[tablesort] "+e)},destroy:function(){return this.$sortCells.off("click.tablesort"),this.$table.data("tablesort",null),null}},t.tablesort.DEBUG=!1,t.tablesort.defaults={debug:t.tablesort.DEBUG,asc:"sorted ascending",desc:"sorted descending",compare:function(t,e){return t>e?1:t",
14 | "license": "MIT",
15 | "bugs": {
16 | "url": "https://github.com/kylefox/jquery-tablesort/issues"
17 | },
18 | "homepage": "https://github.com/kylefox/jquery-tablesort#readme",
19 | "devDependencies": {
20 | "gulp": "^3.9.0",
21 | "gulp-rename": "^1.2.2",
22 | "gulp-uglify": "^1.4.1"
23 | }
24 | }
25 |
--------------------------------------------------------------------------------
/zepto.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
41 |
42 |
43 |
44 |
45 |
46 |
47 |
48 | Name |
49 | Band |
50 | Date of Birth |
51 | Age |
52 |
53 |
54 |
55 |
56 | Thom Yorke |
57 | Radiohead |
58 | October 7, 1968 |
59 | 43 |
60 |
61 |
62 | Justin Vernon |
63 | Bon Iver |
64 | April 30, 1981 |
65 | 30 |
66 |
67 |
68 | Paul McCartney |
69 | The Beatles |
70 | June 18, 1942 |
71 | 69 |
72 |
73 |
74 | Sam Beam |
75 | Iron & Wine |
76 | July 26, 1974 |
77 | 37 |
78 |
79 |
80 |
81 |
82 | No thead or tbody ; just tr s
83 |
84 |
85 | Name |
86 | Band |
87 | Date of Birth |
88 | Age |
89 |
90 |
91 | Thom Yorke |
92 | Radiohead |
93 | October 7, 1968 |
94 | 43 |
95 |
96 |
97 | Justin Vernon |
98 | Bon Iver |
99 | April 30, 1981 |
100 | 30 |
101 |
102 |
103 | Paul McCartney |
104 | The Beatles |
105 | June 18, 1942 |
106 | 69 |
107 |
108 |
109 | Sam Beam |
110 | Iron & Wine |
111 | July 26, 1974 |
112 | 37 |
113 |
114 |
115 |
116 |
117 |
118 |
119 |
120 |
121 |
122 |
143 |
144 |
145 |
146 |
--------------------------------------------------------------------------------
| | |