Fixed columns render out of sync with sliding columns, KeyTables not following sorting when editing

Fixed columns render out of sync with sliding columns, KeyTables not following sorting when editing

bg7bg7 Posts: 44Questions: 6Answers: 0

Link to test case:
http://live.datatables.net/poyaximo/1/edit

Description of problem:
If you have columns set as fixed columns and inline editing enabled the fixed columns don't render in the same manner as the columns that slide.

In the example linked above the first two columns are fixed. If you edit the office column you'll see the row height increase to accommodate the select widget. If you edit the office column in the first row the disconnect between the render for the fixed and sliding columns is most pronounced. If you edit the title column you'll see the same effect only in reverse - the fixed column row heights increase but the sliding columns row heights don't.

A similar effect occurs if you edit the name (a fixed column) and position (a sliding column) fields. Set either of those to be blank and the validation sets an error message below the field. The row heights again get out of sync between the fixed and sliding columns. In addition, if you set the name in the second row to be blank the error actually ends up hidden below (where you're likely to miss it) though you can scroll the field down to see it.

A second issue involves editing and sorting. For example, if you sort by the title and then edit one of the row titles and change it such that that row will appear in a different order in the table, the KeyTable focus (the blue field outline) can end up on the wrong cell. If you tab out of the field after selecting the new value then the focus goes to the next field to the right but stays with the row you edited, as you would expect. But if you press enter instead of tab to save your change then the focus stays where it is while the rows re-sort and then you unexpectedly end up on a different row than the one you were editing.

Replies

  • allanallan Posts: 61,446Questions: 1Answers: 10,054 Site admin

    Thanks for letting me know about this. I don't have an immediate fix other than to suggest using bubble editing on the fixed columns I'm afraid.

    Fixing the layout when editing in the non-fixed part is a matter of calling fixedColumns().update() when the open triggers. But, that doesn't work when editing on the fixed part since it causes a redraw of those elements.

    I'll need to dig further into what the correct fix for this is.

    Regards,
    Allan

  • bg7bg7 Posts: 44Questions: 6Answers: 0

    Allan,

    Sure - we just ran into this and figured you'd want to know. Bubble editing is enabled as well but our users definitely prefer the inline editing as it's a ton quicker.

    Thanks.

    Ben

  • bg7bg7 Posts: 44Questions: 6Answers: 0

    Allan,

    I got around to trying what you suggested with the fixedColumns.update(). I added this (note it helped to have it trigger on open and close to adjust in both cases):

    editor.on('open close', function (e, mode, action) {
      table.fixedColumns().update();
    });
    

    I also added this to the fixed columns config:

    heightMatch: 'auto'
    

    Between those two this seemed to readjust the fixed column cell properly when an inline edit in a sliding column cell was triggered and that cell contained a widget that caused the height and/or width of the cell to increase. These changes also broke inline editing for the fixed column cells. I double-click on that an there's no error and nothing happens. I'm guessing that's what you were referring to when you mentioned the redraw of those elements. And as expected none of this helped with the column headers for the sliding columns still being out of alignment - no surprise there.

    Anyway, I'm sure fixing it in the DataTables code will be a much more solid solution than me trying to work around things from the outside.

    Thanks.

    Ben

  • allanallan Posts: 61,446Questions: 1Answers: 10,054 Site admin

    Hi Ben,

    Thanks for posting back. great to hear you've found an interim solution!

    Allan

  • bg7bg7 Posts: 44Questions: 6Answers: 0

    Allan,

    I ended up separating the open and close event listeners and tweaked them a bit and now the fixed column cells as well as the sliding column header widths are resizing properly when inline editing is triggered. To be clear, the fixed column we're using is actually named 'name' - that's what it's matching with the dataSrc() below. It'd be nice if it were possible to simply match against the name of the column but it didn't seem to be available.

    editor.on('open', function (e, mode, action) {
      if (mode === 'inline') {
        // do *not* invoke this for editable fixed columns
        if (table.column(table.cell({ focused: true }).index().column).dataSrc() !== 'name') {
          table.columns.adjust().fixedColumns().update();
        }
      }
    });
    
    editor.on('close', function (e, mode, action) {
      if (mode === 'inline') {
        table.columns.adjust().draw('full-hold');
      }
    });
    

    It's definitely not perfect and I'm sure whatever you build into DataTables to handle this will be a ton better but for now it gets the job done.

    Thanks.

    Ben

  • bg7bg7 Posts: 44Questions: 6Answers: 0

    Allan,

    I just downloaded the current release which includes FixedColumns 4.0.0. From what I can tell the fixedColumns().update() method that we're using as a workaround for the issues in this ticket is now missing.

    https://datatables.net/reference/api/fixedColumns().update()

    If you go to the main API page and filter on FixedColumns it's missing but on the page linked above it's not marked as deprecated or obsolete and it errors when we call it. I'm hoping this is just an oversight and it can be added back in until the remaining issues in this ticket are resolved - is that possible? We definitely need the workaround until that happens.

    While from what I've been able to tell so far from the 4.0.0 update the fixed and non-fixed fields seem to sync better than before in terms of height/width resizing but the headers are still not staying in sync (they don't widen/narrow as the fields do) and we're using the update() call to work around that issue.

    Thanks.

    Ben

  • allanallan Posts: 61,446Questions: 1Answers: 10,054 Site admin

    Hi Ben,

    With the way FixedColumns works now, there is no need for the fixedColumns().update() method. That it did before was re-clone the original elements to float them above the table. With FixedColumns 4, that is no longer required - we use position: sticky so it is actually the original elements which are floating above the table - no cloning and remeasurements required.

    So based on your fix before:

    table.draw('full-hold');
    

    will hopefully do the job. If it doesn't can you give me a link to your page?

    Allan

  • bg7bg7 Posts: 44Questions: 6Answers: 0

    Allan,

    I tried your suggestion and it works, but it appears to break something else in the process...

    I've got a table with a fixed column and then a bunch of sliding columns. I'm using KeyTable to get around and do inline editing. If I double-click on a field to edit it everything works fine. But if I press enter to edit it the draw() adjusts the column headers appropriately but it blurs the focus from the field I just pressed enter to edit (interestingly this doesn't happen if I double-click the field). I then have to click in that field to get the focus back where it belongs which of course defeats the purpose of navigating/editing with KeyTable. To double-check this I tried setting the draw() in a _.delay() and I can see the focus go to the input and then as soon as the draw executes the cursor vanishes.

    To deal with this I added this line right after the draw():

    $(e.target.s.setFocus.s.opts._input[0]).focus();

    Pretty ugly but it does grab the appropriate input and set the focus back where it belongs. Is there a better reference to the input? That's the only one I saw off the jQuery event object in the open event but I feel like I must be completely missing something much simpler.

    Would it be possible for DataTables to handle the draw() internally and then set the focus to the correct input? That seems like it would be a ton cleaner than a workaround plus a workaround for that workaround's side-effect.

    As for an example, I built one and included it when I created this ticket but it looks like it has expired. I could try to recreate it from scratch if you need me to.

    Thanks.

    Ben

Sign In or Register to comment.