JS:SortedTable

SortedTable is a script that takes a valid table and makes it sortable and also allows you to move rows around. It’s mission is to be the foundation for widgets that do interesting stuff in the new wave of Web 2.0 applications.

Concept

SortedTable is trying to solve a very specific problem – sorting a table automatically (sort functions) or manually (move functions). Anything else is out of the scope and will not make it into the code. The idea of the evolution is to make the code leaner (smaller) but more useful. Any suggestions and contributions are welcome as long as they follow these simple rules. I’m not trying to create a widget. If I ever do it will not change the code of the SortedTable object.

History

0.8

  • first version that actually works on windows and has most of the needed features

0.8a

  • changed the behaviour of sorting:
    • axis=”string” now defaults to case insensitive smartcompare that puts 10 after 9, not after 1
    • no axis does normal compare (broken in 0.8)
    • axis=”sstring” added – does smartcompare case sensitively

0.8b

  • corrected a weird error that broke some sorts in ie6
  • added the possibility for a nonsortable column via class=”nosort” on the th cell
  • added the possibility to ‘regroup’ tbody elements if there’s more than one (for whatever reason)
  • added additional hook to put your custom javascript on (onsort)

0.8c

  • added additional hook to put your custom javascript on (onmove)

0.8d

  • added the option to allow only single line selects
  • corrected compare so that only strings enter compareSmart (error when trying to do split on a DOMElement)
  • changed parseInt to parseFloat for axis=number when sorting
  • changed compare – title now always overrides the value
  • added onselect that happens after onbodyclick

0.8e

  • corrected a bunch of small issues noticed while writing the documentation
    • added return true to selectRange (when it’s actually a range)
    • corrected prepHeader (callbacks on hover were broken)
    • removed redundant s_table variable from prepBody
    • moved onselect to the select method
    • added ondeselect
    • changed parameters to onsort and onmove
  • corrected a few sorting bugs
    • on axis=number NaN is now changed to Infinity to place nonnumeric values at the end
    • in smartcompare numbers go before text
  • corrected an error in the removeBeforeSort code (no nextSibling broke it)
  • added checking in prep so it cannot be done twice
  • added the option to disallow deselect

Future development

The next version will implement a Quicksort algorithm for sorting that will hopefully work a lot faster. It will allow the absence of header and axis properties for each cell that should make the html somewhat smaller.

Download

Check the SortedTable page here or just download the javascript.

Also worth reading

98 Responses to “JS:SortedTable”

  1. package this says:

    You need to package this better.

    Basically I have to find Events.js, and I really don’t know if I have the correct one, most like not, cause your code ain’t working in my setup yet.

    Thus you should make available whatever files I really need to run this.

  2. My apologees – you need to download the Event.js that is included in the example page. There is a reference in the header to a few versions that should do the trick though…

  3. Love the script, check it out in action in my weather script…

    http://www.kevincornwell.com/weather/index.php

    Keep up the good work!

    -kc

  4. Aaron says:

    Is it just me, or is the example code now broken?

    Here’s what i’m seeing in FF 1.5.0.2 and IE 6.0.2900.blahblah

    In the top (first) table example, selections no longer highlight the way they once did. the highlight seems to be in effect though, because i can click move selected row(s) up after selecting the 2nd or 3rd record, and they will go up.

    After that, when i select say.. the second record and click move selected row(s) down, they do not move.

    In fact, as far as i can tell.. move selected row(s) down is entirely broken. I can only get records to go up.

    I really like this method, and would like to impliment such a thing for manually setting the order of database records.

  5. Thank you for the bug report. The code wasn’t broken, the example was.

    As you can see from the code of the sample links the first two use different code – they access the SortedTable object directly (mySorted) while the second two rely on finding it through a row in the table. Unfortunately when updating the example I forgot to add the id to one of the rows in the table which caused the problem.

    The highlighting issue was a CSS order problem – the odd/even styles were defined lower that the hover/selrow styles…

  6. Georges Bilodeau says:

    Nice job on the script, it works well. I noticed in your example that alternating rows have a different background color, but this functionality is implemented in the page’s JavaScript and not in SortedTable.js. I added a couple simple methods (based on the example) to the ‘helpers’ section of SortedTables.js to make it easier to set up these alternating row background colors:

    setRowClasses:function(r0, r1) {
    this.evenRow = r0;
    this.oddRow = r1;
    },
    colorize:function() {
    for (var i=0;i

  7. Georges I left the code outside of the object intentionally. Row coloring has nothing to do with sorting a table…

  8. Chris says:

    I really love the work you’ve done here – it’s very impressive and I’d be intereste d in using it myself, but unfortunately I’m a novice with Javascript. I’m sure you don’t want to walk a beginner through the use of your code, but I’d appreciate it if you could provide a link to a website that might have information available to use this kind of script, I’d be very grateful!

    Thanks!

    ~Chris

  9. Georges Bilodeau says:

    Yeah, good point on the row coloring ego. I did find one other thing. In the compareSmart function, a JavaScript error was popping up for me when comparing a cell with axis=string and innerHTML of length 0 (my table had some blank fields). Not a dealbreaker at all, but I changed the first two lines of compareSmart to fix it:

    v1 = (v1 && v1.length) ? v1.split(‘ ‘) : [];
    v2 = (v2 && v2.length) ? v2.split(‘ ‘) : [];

    That hopefully won’t break the code for anything else. Thanks for this handy script!

    Georges

  10. cynric says:

    Looks like a great replacement for my old js table sorter!
    i it possible if the to-be-sorted-column countains equal elements to keep the table “subsorted” after a main column? (described my prob here: http://tinyurl.com/jy8om )

  11. cynric this is actually an improvement I will think about when implementing a quicksort – you will be programatically able to sort as in excel – select columns and directions.

  12. Kilorf says:

    Hi superego,

    First i would like to thank you for this excellent script!

    Second i have had a couple of small issues when implementing it, nothing major so heres the fixes:

    – When sorting you use parseInt, instead of parseFloat, which makes it sort wrong in a commonly used situation.

    – using title param for dates are great, but i also need it for other types, for example currency columns where you might have prefixes ($) and different decimal, thousand seperators. This is also easily done, ive only hacked my own implementation for my own purposes, but a clean implementation should be quite obvious.

    Thanks again.

  13. I will change parseInt into parseFloat, good point. For the other thing – the title param always overrides the content of the cell when sorting so it can be used with no changes on any type of field. You can see this in the fourth line of the compare method. I will also add it to the examples…

  14. Kilorf says:

    Yes the title param overwrites the innerHTML value, but it doesnt seem to use the string, sstring, number logic, because the overwrite is part of the if-else.

    In my case it doesnt parse to float and js thinks its a string.

    My ugly hack:
    if (v1.title && v2.title) {
    if(axis==’number’) {
    v1 = parseFloat(v1.title);
    v2 = parseFloat(v2.title);
    } else {
    v1 = v1.title;
    v2 = v2.title;
    }
    }

    Or am i missing something?

  15. You are correct. I will change this in version 0.8d and release it in the next few days…

  16. Shayne says:

    Any news on the 0.8d release? not to be a pain in the ass, i just got a website project thats about to ship out the door and would like to do the small update.

    Thanks.

  17. Shayne says:

    I agree with Kilorf though, we need a money sorter :)

  18. Kashif says:

    A bit of documentation would certainly help :)

  19. links for 2006-05-16…

    SortedTable is a script that takes a valid table and makes it sortable and also allows you to move rows around. (tags: javascript ajax database webdev) SQLyog MySQL GUI is the most popular MySQL Manager and MySQL Admin Tool (tags: mysql database softw…

  20. İshak says:

    I want to sort a column which has numeric values,
    if a cell has non-numeric value (i.e, “” or “-“, which means data empty), sorting does not work properly.

  21. Pete says:

    Any odds on implementing support for multi-column sorting? That would make this even more awesome!

  22. Steve says:

    I’m rather new to javascript and am fumbling my way through this (great work by the way), what I would really like is the order # to dynamically change as it is moved up or down the list.

    If someone could provide me with the code to do this it would be appreciated

  23. Jeremy says:

    I can’t seem to make it sort a date/time column. I display the date and time a record was created and I use the title tag so the date properly sorts. Trouble is it sorts by time as a string instead of numeric. 10:00 pm comes before 7:00 pm and so forth. Any fix for this?

  24. Jeremy – you should put a iso date and time in the title. You’d get something like title=”2005-01-01T10:00:00″ and title=”2005-01-01T07:00:00″ that will sort as it should…

    Others – some errors are being corrected for the next release, money sorting can always be solved via correct title and axis (check examples), quicksort and multicolumn sorting is coming in version 0.9, the documentation and example for static row numbers (for Steve) is coming with 0.8e.

  25. Jeremy says:

    Thanks for the tip, ego. I realized my error shortly after I posted here. I have a new issue now. I have a column that contains numeric and alphanumeric values. I’ve tried sorting as string, sstring and number and it won’t put the numeric values ahead of the alpha ones. I also have a date column which either has a date or it is blank. It will sort the blank dates on top but won’t reverse and put the latest date at the top. I tried some logic to fill the title attribute with ‘1111-11-11’ if the date is blank but that’s not helping. Suggestions?

  26. Jeremy says:

    Thanks for the update. I have one more question and I think my problems will be solved. Going into my page, my results are defaulty sorted. If I click the column that it is already sorted by it looks as though nothing happens. I have to click twice to swap the sort. How can I tell/fool the script into knowing what the table is already sorted by? Can I call the sort function after the table is drawn? How would I go about that? Thanks!

  27. Tiger Baiter says:

    I very much enjoy the script. I am trying to integrate it into an ajax page, and what I’d like to do is use it to update a database in realtime when a row is moved. What I’d like to do is a before and after snapshot of the table order so that I can pass that back to a function, or even just the old row number and the new. You get the picture. Is there any way of accessing these values?

  28. Tiger Baiter says:

    Update – have managed to get it to talk to the AJAX library. What I did was to use the nextSibling and previousSibling properties to extract an id value that match the database keys, then pass that back to the server.

    Will send you code when done.

  29. Joe says:

    Any idea when you’ll be releasing a version with multi column sort? I could really use that functionality.

    Thanks for a great tool!

  30. Ricard says:

    Hello, I’m not expert en javascript, and I don`t know how to do the submit of one kind of Array with the order of ‘s after reordering the rows of my table with up/down buttons. I’m working with Struts and I need submit the new order as a parameter (in the request scope) or as a property of my ActionForm.
    Could anybody help me?

    Thanks in advance!!

  31. Eric Floehr says:

    Thanks for the awesome javascript!

    We are now using this sort Javascript for weather forecast accuracy detail tables at ForecastAdvisor.com. It works great!

    Just go to the site, enter in a U.S. city/state or zipcode, then click “Further analysis >>” at the bottom of the forecast page. This will bring up two tables showing weather forecast accuracy details of Accuweather, The Weather Channel, MyForecast, National Weather Service, etc. that are sortable by high temperature accuracy, low temperature accuracy, icon precipitation forecast accuracy, and text precipitation forecast accuracy, etc.

    Thanks again!

  32. Samn says:

    A great product – Thank you for publishing this.

    I am running into a challenge with table cells that contain hyperlinks. The cells are logically being sorted on the HTML preceeding the linked text, when it is obviously the linked text I want to be sorted.

    I would suggest a mode of the string axis type for hyperlinked strings, that sorted on the value between a pair of anchor tags.

    Thanks again!

  33. Samn says:

    A follow-up on my previous comment – While this may not be practical for very large blocks of text or HTML in a cell, you can still sort cells containing hyperlinked text by including the text in either the title of the link itself, or a bogus attribute. Using [a title=”text” href=”url”]text[/a] will allow you to sort by “data.” If you don’t want the text to appear redundantly as the title, you can make up a property like [a sortdata=”text” href=”url”]text[/a] . The rendering engine will ignore the property “sortdata”.

  34. Jon says:

    I love your script!

    However, I’m having a problem that’s really holding me back. I have a column of checkboxes (which is not sortable) and a column of strings. When I sort the table by the column of strings, the checked=”checked” status of the checkbox column resets in IE. The state is maintained properly in Firefox, however. Any ideas?

  35. Georges says:

    thank you for this beautiful script.
    I also have a question which i can’t answered. I was looking for sorting table rows but to order a menu so I’d like to know if it was possible to but dynamic vas in array.

    More explications.
    I have a menu which contains title and subtitles. They are all written in a table on my page. What i would like is to move rows to put a dynamicaly position that i’m writing in my DB MySQL later. (select * FROM titles ORDER BY ‘position’)

    The position is given by a value in my input field (as I have no input in my table in will be an hidden field in my td)

    2 would become
    2

    4 = number of the title id number and 3 which is the line number. If I move it up 4 should stay and 3 should become 2.

    I hope someone would understand me and if we can do this, I hope it would be useful for someonesle.

  36. Dallas says:

    Any fix for the issue Jeremy was having? I’m having the same problem:

    —————————————-
    Jeremy said,

    on May 22nd, 2006 at 07:36

    Thanks for the update. I have one more question and I think my problems will be solved. Going into my page, my results are defaulty sorted. If I click the column that it is already sorted by it looks as though nothing happens. I have to click twice to swap the sort. How can I tell/fool the script into knowing what the table is already sorted by? Can I call the sort function after the table is drawn? How would I go about that? Thanks!

  37. You should check the first table on the examples page. You can achieve this by setting a class name of ‘sortedplus’ or ‘sortedminus’ on the header cell.

  38. Brady says:

    I noticed that when I put links in the cells the script does not sort correctly. Is there a way to have links?

    Great work by the way.

  39. Josiah says:

    There seems to be a bug in sorting decimal values. See example: http://www.climate.washington.edu/precipranking/table.php?location=qulPcpMO

  40. Yes, I am also having problems in sorting the required table properly. It would be so nice if you can help me.

    Don Lapre Fan
    [email protected]
    http://www.j-ams.org

  41. It’s really easy – the axis parameter defines what kind of compare will run on the data in the cell. If you want the compare function to use something else than the value in the cell you can specify that in the title attribute to the cell and it will use that instead.

    For all the possible values check the examples page. I will expand the home page to include some instructions…

  42. garry says:

    i’m pretty much new to javascript so you’ll forgive me if this seems like an obvious problem.

    i’m tring to add new rows to a table which will ‘inherit’ the same behaviour as other rows in the table which were added without javascript. unfortunateley, when i do this, the rows which are added donot move up and down as the other rows. is there a quick fix for this?

    here’s the extra code that i’ve added to SortTables.js:

    insRow2:function(elm){
    this.cleansort();
    var tbl = elm.parentNode;
    var lastRow = tbl.rows.length;
    var newRow = tbl.insertRow(lastRow);
    var td0 = newRow.insertCell(0);
    var td1 = newRow.insertCell(1);
    var td2 = newRow.insertCell(2);
    td0.innerHTML=”NEW CELL1″;
    td1.innerHTML=”NEW CELL2″;
    td2.innerHTML=”NEW CELL3″;
    },

    SortedTable.insRow = function(elm)
    {
    var st = SortedTable.getSortedTable(elm);
    if (st) st.insRow2(elm);
    }

    which is called like so:

    thanks for the help.

    garry

  43. Josiah says:

    The axis parameter did the trick. Though a couple of columns that have the same type of numbers work without the axis parameter and do not work when the proper axis parameter is included.

  44. Martin says:

    I think there is a bug in the “move specific row down” function on the demo site. It always moves row 1, no matter what row is selected.

    /mac

  45. Martin – ‘move specific row down’ means you specify the row element you want to move. To move the selected row(s) you omit the secont argument to the move function (check the javascript link as you hover over it).

  46. REW says:

    There seems to be a bug in sorting values when an xslt format-number with a thousands separator is added. If some values are in the hundreds and some values are in the thousands, the sort does not work correctly. When the values are all in the thousands, the sort works fine. When I remove the comma in the format statement it works fine.

    TIA

  47. When using different formated numbers the idea is to add the sortable value to the title attribute of the table. Check the examples page for this (the second table solves this issue) – 1,222,345

    – the script will automatically use the title value to sort the element. You can also use the title element for sorting prefixed numbers (eg. $12).

  48. randy says:

    When using large numbers such as the following, it does not seem to sort properly:

    58,896,341.0405
    58,896,341.0405
    158,891,355.078
    68,276,005.7803
    68,276,005.7803
    41,125,489.678

    I downloaded the events and sorttable.js files and updated the HTML like the examples mentioned but when using simple numbers it was fine.

    Is it possible, something that I am missing will correct this? It is a very good script otherwise.

  49. randy, if you’re using delimiters with numbers you should add a title to the cell:

    58,896,341.0405

    This will tell the script to use the title instead of the content when sorting.

Leave a Reply