Problem with FixedHeader when header has multiple rows

Problem with FixedHeader when header has multiple rows

rcwalshrcwalsh Posts: 12Questions: 0Answers: 0
edited September 2010 in General
Hi Allan,

Your DataTables tool is incredible; I've been studying it and using it for weeks and also must say that you run a very nice forum here, which most developers don't bother to do. So thank you for your hard work and for enabling others to help themselves!

I've run into a few problems that I haven't been able to solve, neither by hours of tweaking nor by searching the documentation/forum.

What I'd like to have is a table with the following:
1) FixedHeader (I think I just need the top, not bottom or sides)
2) Various filter controls are embedded within each header cell underneath the label. I don’t care if the controls only work for the “original” header (before getting “caught” by the top of the page by the scrolling), though it would be great if the controls always worked.
3) User can click/use the filter without triggering a sort on that column
4) Columns automatically adjust their widths (onload and on window resize) so that all columns are visible within the window without horizontal scroll and also that certain columns are wide while others are narrow
5) Works in all browsers
6) Server-side processing

I am using your most recent release of DataTables and the FixedHeader plugin.

I don't think #3 was a problem at all until this release of DataTables (I'm not sure why attempting to click/use the inputs within the header cells now cause the sort to happen). The inputs (embedded within thead th) are unusable since attempting to use them triggers a sort.

I’ve come up with a workaround for #3 (although it’s not preferable): I have a TR with THs in the Thead and then a TR with TDs below that row in the Thead, and the TDs contain the filtering controls. This works decently, as the THs remain clickable for sorting, and the TDs have dropdowns and checkboxes and text inputs that are usable for filtering (without triggering a sort). However, even though I’ve used CSS to make the column headers look like single cells (which is better than them being so obviously split across multiple rows), this workaround is still subpar since any empty bottom rows (TR TD) are not clickable even though the user might assume that clicking there would sort the row. I might be able to address this with other jquery code.

My other issue is that FixedHeader doesn’t seem to work with this setup. FixedHeader works for me unless I have multiple TRs in Thead. With my setup, I first get my Processing indicator going endlessly, and then if I try to sort or anything, I get a sZeroRecords message in the table (“No matching records found”).

Am I missing something? Any chance you can help me out with these couple things, Allan?

Thanks so much for your time!
Ryan

P.S. Another possible bug (but doesn’t matter to me) is that adding a table footer seems to break the column autowidth feature, at least with my server-side processing setup.


[code]



Category
Title
Images
Distance
Location
Time Posted
Times Viewed









(All)
Last 30 m
Last 1hr
Last 2hrs
Last 3hrs
Last 6hrs
Last 12hrs
Last 24hrs
Last 48hrs






Just a moment...


[/code]

CSS:

[code]
#listings
{
width:100%;
/*width:1000px;*/
margin:0;
padding:0;
}
#listings th
{
width:100%;
padding-right:1em;
cursor:pointer;
background-color:#E8E8E8;
vertical-align:top;
/*border-left:1px solid gray;
border-right:1px solid gray;*/
}

#listings thead
{
/*border:1px solid gray;*/
background-color:#E8E8E8;
}
#listings tbody td,#listings thead th, #listings thead td
{
/*border:1px solid #ccc;*/
border-left:1px solid #ccc;
border-right:1px solid #ccc;
text-align:left;
}
#listings thead th
{
border-top:1px solid #ccc;

}
#listings thead td, #listings
{
border-bottom:1px solid #ccc;

}
[/code]

Replies

  • allanallan Posts: 63,516Questions: 1Answers: 10,472 Site admin
    Hi Ryan,

    Thanks for your kind words! Good to know that DataTables is proving to be useful!

    1. FixedHeader first - I've just tried my examples with an extra TR element in the header, and it appears to work okay. If you've got the 'infinite processing indicator' that would suggest a Javascript error has occurred somewhere - is there any indication of this on the Firebug console (or whatever debugger you use)?

    2. Column header clicks - the issue here is the bubbling of the events going back up the DOM to cause the sort to trigger as well. You might be able to get around tis by simply cancelling the bubble with a click handler on the input elements ( http://api.jquery.com/event.stopPropagation/ ). If this doesn't work (I expect it should, although I've not tried it), an alternative would be to detach the sort listener DataTables puts on the column headers, and then attach your own using fnSortListener ( http://datatables.net/api#fnSortListener ) and a bit of logic based on which element was clicked on.

    3. Footer breaking auto width - that's very odd indeed! I use a footer in most of my demo tables, and I've not seen this behaviour before. Do you have an example you can put up showing the problem?

    Thanks,
    Allan
  • rcwalshrcwalsh Posts: 12Questions: 0Answers: 0
    For FixedHeader, this is the error I get in Firefox Error Console (when I try to have multiple header rows):

    Error: jQuery("thead:eq(0)>tr th:eq(" + e + ")", a)[0].style.width is not a function
    Source File: http://localhost/js/jquery.dataTables.FixedHeader.min.js
    Line: 87

    However, I won't need multiple header rows if I can figure out what you mentioned in #2. I've tried a bit of event.stopPropagation and haven't had luck yet but will keep trying.

    I no longer have an example of the footer problem since I'm no longer using footers anywhere, but I'll let you know if I get to that again.

    Thanks!
  • rcwalshrcwalsh Posts: 12Questions: 0Answers: 0
    I got rid of my second header row, put the dropdown filter into the th of the header row, and added a stopPropagation command as you suggested. Now everything (including my FixedHeader) works in Firefox and IE, but Chrome doesn't seem to let me use the dropdown at all. I'll keep exploring. Thanks for your help.

    [code]
    $('#timePosted').click( function(event)
    {
    event.stopPropagation();
    });
    [/code]
  • rcwalshrcwalsh Posts: 12Questions: 0Answers: 0
    I made the filterable column unsortable by using
    "bSortable": false
    and Chrome still wouldn't let me use the dropdown, so then I removed the FixedHeader plugin entirely, and Chrome STILL wouldn't let me use the dropdown, though it's not showing me any errors, so I'm now wondering if for some reason Chrome+DataTables doesn't allow a dropdown in a TH?

    Thanks!
  • allanallan Posts: 63,516Questions: 1Answers: 10,472 Site admin
    Urm - this is a bit of a tricky one!

    This is basically what the above event handlers should be doing:

    [code]
    document.addEventListener("DOMContentLoaded", function () {
    document.getElementById('test').addEventListener('click', function (e) {
    e.stopPropagation();
    }, false );
    }, false)
    [/code]
    which on a super simple page works absolutely fine in Webkit.... however, (sudden thought process while typing) DataTables is adding the following code to each TH element:

    [code]
    $('th', oSettings.nTHead).mousedown( function (e) {
    this.onselectstart = function() { return false; };
    return false;
    } );
    [/code]
    Can be seen with visual event ( http://www.sprymedia.co.uk/article/Visual+Event ) and that is what is causing this effect. Funny that Firefox behaves differently - I think that would be the return false effect.

    Comment out those lines in _fnDrawHead and it works absolutely fine... So now we come to how to do this with default DataTables - just unbind the event:

    [code]
    $('#example thead th').unbind('mousedown');
    [/code]

    I've just tried this and it seems to work well for me:

    [code]
    var oTable = $('#example').dataTable();
    new FixedHeader( oTable );

    $('#example thead th').unbind('mousedown');

    $('select[name="timePosted"]').click( function (e) {
    e.stopPropagation();
    } );

    $('input[name="allan"]').click( function (e) {
    e.stopPropagation();
    } );
    [/code]
    Phew!

    Good luck,
    Allan
  • rcwalshrcwalsh Posts: 12Questions: 0Answers: 0
    Brilliant! You are so awesome. I'm so excited that this is all working. =-) Thanks so much for your help! -Ryan
This discussion has been closed.