State Saving

State Saving

kenblmarkenblmar Posts: 5Questions: 0Answers: 0

I really like what I can do with DataTables and I am trying to incorportate it in a new project. but having one issue.

I am trying to save the state of the filtered select boxes after page refresh. I have it working for the filter input boxes but not for the select box. The table is filtered correctly after page reload and the input filter box keeps its value but not the select boxes.

My search filters are on the second row and my initial load is

        initComplete: function () {
            this.api().columns().every( function () {
            var column = this;
            var columnIndex = this.index();
            switch ($(".filter th:eq("+columnIndex+")").attr('class')) { 
                case 'theadselect': 
                    var select = $('<select style="width: 90px;"><option value="">filter</option></select>')
                    .appendTo( $(".filter th:eq("+columnIndex+")").empty() )
                    .on( 'change', function () {
                        var val = $.fn.dataTable.util.escapeRegex(
                        $(this).val()
                        );
                        column
                        .search( val ? '^'+val+'$' : '', true, false )
                        .draw();
                    });


                    column.data().unique().sort().each( function ( d, j ) {
                    if(d != ""){                                            
                        select.append( '<option value="'+d+'">'+d+'</option>' );
                    }

                    });

                    break;
                case 'theadsearch': 
                    $(".filter th:eq("+columnIndex+")").html( '<input type="text" placeholder="filter"/>' );

                    $( 'input', $(".filter th:eq("+columnIndex+")") ).on( 'keyup change', function () {
                    if ( column.search() !== this.value ) {
                        column
                        .search( this.value )
                        .draw();
                    }
                    });
                    break;
            }
            } );
        }       

and the state reload is:

    // Restore state - keep filter options if page is refreshed
    var state = table.state.loaded();
    if ( state ) {
        table.columns().eq( 0 ).each( function ( index, colIdx ) {
          var colSearch = state.columns[colIdx].search;

            if ( colSearch.search ) {
                //works for input boxes but not for select boxes
                $('#myTable thead tr:eq(1) th:eq(' + index + ') input', $('.filters th')[colIdx]).val( colSearch.search );

                //Also tried doing it by index statement for each index but still only works for input boxes not select boxes
                 // select box
                 //if ( index == 0) {
                 //   $('#myTable thead tr:eq(1) th:eq(' + index + ') input', $('.filters th')[colIdx]).val( colSearch.search );
                 //}
                                //input box
                 //if ( index == 1) {
                 //   $('#myTable thead tr:eq(1) th:eq(' + index + ') input', $('.filters th')[colIdx]).val( colSearch.search );
                 }
                                 //input box
                 //if ( index == 4) {
                 //   $('#myTable thead tr:eq(1) th:eq(' + index + ') input', $('.filters th')[colIdx]).val( colSearch.search );
                 //}
            }
          //if ( colSearch.search ) {
              // $('#myTable thead tr:eq(1) th:eq(' + index + ') select', $('.filters th')[colIdx]).val( colSearch.search );
          //}           
        } );


    }

I would appreciate any help as this is the last thing I have to resolve. I have already worked out putting the search boxes on the second row, using both search and select boxes, keeping the current page after edits etc.

Thank you

Replies

  • tangerinetangerine Posts: 3,365Questions: 39Answers: 395
  • kenblmarkenblmar Posts: 5Questions: 0Answers: 0

    Thanks for responding. I have seen that post but I can't figure out how to use it to set the value of the select box

  • allanallan Posts: 63,532Questions: 1Answers: 10,475 Site admin

    Please don't post duplicates.

    You need to load the values that have been saved for the state. I put this example together a while back for a similar question - it also uses FixedColumns and puts the select elements in the header.

    Allan

  • kenblmarkenblmar Posts: 5Questions: 0Answers: 0

    My apologies. I did see your example but just couldn't get it to work correctly. I do have it working now, thanks. I am still wondering if there is any advantage to doing this code in initComplete: function or not. I saw the code in that function in one of the examples.

    Also, Do you have an example of the same code you just referenced but with search input boxes and selects? I am trying to read thru the documentation to learn more on my own as well.

    Thanks again

  • allanallan Posts: 63,532Questions: 1Answers: 10,475 Site admin

    I am still wondering if there is any advantage to doing this code in initComplete: function or not

    If you are Ajax loading the data, then yes, you'd need to do it in initComplete if you want to be able to access the data. Ajax loaded data is async by its nature, so a callback is required.

    Also, Do you have an example of the same code you just referenced but with search input boxes and selects?

    Currently no, but it should be possible to merge that code with the text input search.

    Allan

  • kenblmarkenblmar Posts: 5Questions: 0Answers: 0
    edited October 2017

    Allan, I just wanted to say thanks for responding and putting me in the right direction. I was able to get it working with the code you showed me and the extra piece about the search input boxes. I will put my code here as well as it may help someone else. Now both input and select textboxes are saving the filter options upon refresh. I still have to learn more about the "table.columns()" function.

      /* Plugin API method to determine is a column is sortable */
    $.fn.dataTable.Api.register( 'column().searchable()', function () {
      var ctx = this.context[0];
      return ctx.aoColumns[ this[0] ].bSearchable;
    } );
    
    
    $(document).ready( function () {
      // Create the DataTable
      var table = $('#myTable').DataTable( {
        orderCellsTop: true,
        columnDefs: [
          { searchable: false, targets: [ 7 ] },
          { orderable: false, targets: 7 }  
        ],
        stateSave: true,
           //Save page number state upon refresh
        "bStateSave": true,
            "fnStateSave": function (oSettings, oData) {
               localStorage.setItem( 'DataTables', JSON.stringify(oData) );
            },
            "fnStateLoad": function (oSettings) {
               return JSON.parse( localStorage.getItem('DataTables') );
            },
        //do not display page number if 1 page
        "fnDrawCallback": function() {
            if (Math.ceil((this.fnSettings().fnRecordsDisplay()) / this.fnSettings()._iDisplayLength) > 1) {
                $('.dataTables_paginate').css("display", "block");  
                //$('.dataTables_length').css("display", "block");
                //$('.dataTables_filter').css("display", "block");  
            } else {
                $('.dataTables_paginate').css("display", "none");
                //$('.dataTables_length').css("display", "none");
                //$('.dataTables_filter').css("display", "none");
            }
    
        },
    
        
      } );
      
      // Add filtering
      //table.columns( '.theadselect' ).every( function () {
      table.columns().every( function () {
        if ( this.searchable() ) {
            var columnIndex = this.index();
            switch ($(".filter td:eq("+columnIndex+")").attr('class')) {
            case 'theadselect':     
            
                var that = this;
    
                // Create the `select` element
                var select = $('<select class="form-control" style="width: 120px;"><option value="">filter</option></select>')
                  .appendTo(
                    $('thead tr:eq(1) td').eq( this.index() )
                  )
                  .on( 'change', function() {
                    that
                      .search($(this).val())
                      .draw();
                  } );
              
                // Add data
                this
                  .data()
                  .sort()
                  .unique()
                  .each( function(d) {
                   if (d != "") {
                    select.append($('<option>' + d + '</option>'));
                   }
                } );
                
                // Restore state saved values
                var state = this.state.loaded();
                if ( state ) {
                  var val = state.columns[ this.index() ];
                  select.val( val.search.search );
                  
                }
            break;
                
            case 'theadsearch':
                    var that = this;
                      
                    $(".filter td:eq("+columnIndex+")").html( '<input type="text" class="form-control" placeholder="filter"/>' );
                        
    
                    $( 'input', $(".filter td:eq("+columnIndex+")") ).on( 'keyup change', function () {
                                if ( that.search() !== this.value ) {
                    that
                        .search( this.value )
                        .draw();
                                }
                    });
                        
        
                    // Restore state - keep filter options if page is refreshed
                    var state = this.state.loaded();
                    if ( state ) {
                        table.columns().eq( 0 ).each( function ( index, colIdx ) {
                            var colSearch = state.columns[colIdx].search;
                            
                            if ( colSearch.search ) {
                                     $('#myTable thead tr:eq(1) td:eq(' + index + ') input', $('.filters td')[colIdx]).val( colSearch.search );
                            }
                
                        } );
                        
                    //table.draw("full-hold")
                    } 
                                                                                
                        
            break;          
                
                
                
    
            }
        }
      } );
    
    <table id="myTable" class="table table-striped table-hover">          
           <thead>          
        <tr>
                      <th class="bigger">Date</th>
                      <th class="small">Room</th>
                      <th class="small">Call In</th>
                      <th class="small">Language</th>
                      <th class="small">Interpreter</th>
                      <th class="small">Time In</th>
                      <th class="small">Time Out</th>
                      <!--th>Comments</th>-->
                      <th class="bigger">Action</th>                    
                    </tr>
        <tr class="filter">
                      <td class="theadselect"></td>
                      <td class="theadsearch"></td>
                      <td class="theadselect"></td>
                      <td class="theadselect"></td>
                      <td class="theadsearch"></td>
                      <td class="theadselect"></td>
                      <td class="theadselect"></td>
                      <!--th class="theadsearch">Comments</th>-->
            <td></td>  
                    </tr>               
                  </thead>
                  <tbody>
    
This discussion has been closed.