Reputation: 524
I am using basic column visibility and individual column searching (text inputs).
The problem is that when the user adds a previously-hidden column to the table, the text field box for that column does not appear. Thus, the user cannot filter that column.
Does anyone know how to enable filters for hidden columns as well? Ideally, this would not cause a byproduct of clearing the text in the other filters (if the user did enter text in the other filters).
Here is my filtering code:
<script type="text/javascript">
$(document).ready(function() {
// Setup - add a text input to each footer cell
$('#tableID tfoot th').each( function () {
var title = $(this).text();
if ((title != '') && !(title.includes("$"))) {
// Then the current column is *not* the Action column.
$(this).html( '<span style="color: #515151; font-size:15px;"><i>Filter</i></span> <br> <input type="text" style="margin-top:10px;" placeholder="'+title+'" /> ' );
}
} );
var table = $('#tableID').DataTable();
// Apply the search
table.columns().every( function () {
var that = this;
$( 'input', this.footer() ).on( 'keyup change', function () {
if ( that.search() !== this.value ) {
that
.search( this.value )
.draw();
}
});
} );
} );
</script>
I am using this line to hide the columns that I want to be hidden from view by default:
(table.column('.hideCol')).visible(false);
Upvotes: 0
Views: 2053
Reputation: 1177
I have worked with this small snippet to hide/Unhide the Individual Column Search, Integrated with Column Visibility Event of Datatables.
$('#table').on( 'column-visibility.dt', function ( e, settings, column, state ) {
columnv = settings.aoColumns[column].bVisible;
if(columnv === false){
$('#table').find("tr.filters th:eq('"+column+"')").hide();
}else{
$('#table').find("tr.filters th:eq('"+column+"')").show();
}
});
Upvotes: 0
Reputation: 15540
There's a custom column-visibility
event in DataTables. So, you may revise your <input>
elements visibility based on current status of the column.
E.g. you have <input>
rendering function, like that:
//function to render input elements
const renderTfootInputs = () => {
//grab previous inputs into array
const prevInputs = [];
dataTable.columns().every(function(){
prevInputs.splice(this.index(), 1, $(`#example tfoot [colindex="${this.index()}"]`).val());
});
//purge <tfoot> row contents
$('#example tfoot tr').empty()
//iterate through table columns
dataTable.columns().every(function(){
//if the column is visible
this.visible() ?
//append corresponding footer <input>
$('#example tfoot tr').append(`<th><input colindex="${this.index()}" placeholder="${$(this.header()).text()}" value="${prevInputs[this.index()] || ''}"></input></th>`) :
true;
});
};
Than, you may call it upon column visibility changes:
$('#example').on('column-visibility.dt', renderTfootInputs);
Complete demo of this approach might look as follows:
//sample data source
const dataSrc = [
{id: 1, title: 'apple', cat: 'fruit'},
{id: 2, title: 'pear', cat: 'fruit'},
{id: 3, title: 'banana', cat: 'fruit'},
{id: 4, title: 'carrot', cat: 'vegie'},
{id: 5, title: 'eggplant', cat: 'vegie'}
];
//datatables initialization
const dataTable = $('#example').DataTable({
data: dataSrc,
dom: 'Bfrtip',
buttons: ['colvis'],
columns: ['id','title','cat'].map(header => ({title: header, data: header})),
columnDefs: [
{targets: 0, visible: false}
]
});
//append blank footer to the table
$('#example').append('<tfoot><tr></tr></tfoot>');
//function to render input elements
const renderTfootInputs = () => {
//grab previous inputs into array
const prevInputs = [];
dataTable.columns().every(function(){
prevInputs.splice(this.index(), 1, $(`#example tfoot [colindex="${this.index()}"]`).val());
});
//purge <tfoot> row contents
$('#example tfoot tr').empty()
//iterate through table columns
dataTable.columns().every(function(){
//if the column is visible
this.visible() ?
//append corresponding footer <input>
$('#example tfoot tr').append(`<th><input colindex="${this.index()}" placeholder="${$(this.header()).text()}" value="${prevInputs[this.index()] || ''}"></input></th>`) :
true;
});
};
//initial call of above function
renderTfootInputs();
//call that function each time upon column visibility changes
$('#example').on('column-visibility.dt', renderTfootInputs);
//individual search
$('#example').on('keyup', 'tfoot input', function(event){
dataTable.column($(event.target).attr('colindex')).search($(event.target).val()).draw();
});
tfoot input {
display: block;
}
tfoot th {
padding-left: 10px !important;
}
<!doctype html>
<html>
<head>
<script type="application/javascript" src="https://code.jquery.com/jquery-3.3.1.min.js"></script>
<script type="application/javascript" src="https://cdn.datatables.net/1.10.19/js/jquery.dataTables.min.js"></script>
<script type="application/javascript" src="https://cdn.datatables.net/buttons/1.5.6/js/dataTables.buttons.min.js"></script>
<script type="application/javascript" src="https://cdn.datatables.net/buttons/1.5.6/js/buttons.colVis.min.js"></script>
<script type="application/javascript" src="test.js"></script>
<link rel="stylesheet" type="text/css" href="https://cdn.datatables.net/1.10.19/css/jquery.dataTables.min.css">
<link rel="stylesheet" type="text/css" href="https://cdn.datatables.net/buttons/1.5.6/css/buttons.dataTables.min.css">
</head>
<body>
<table id="example"></table>
</body>
</html>
Upvotes: 2