Home > Software engineering >  jQuery Datatables Responsive createdCell issue
jQuery Datatables Responsive createdCell issue

Time:06-13

I am currently working on a datatable which finally seems to work exactly the way I want, however one issue remains, please see my screenshots below:

enter image description here

As you can see, I am adding custom colors in the column STATUS based on the actual status value using the following code:

            'columnDefs': [ {
                'targets': 3,
                'createdCell': function (td, cellData, rowData, row, col) {
                    if ( cellData == 'Pending' ) {
                        $(td).css('color', '#e27522'),
                        $(td).css('font-weight', 'bold')
                    }
                    else if ( cellData == 'Confirmed' ) {
                        $(td).css('color', 'green'),
                        $(td).css('font-weight', 'bold')
                    }
                    else if ( cellData == 'Accepted' ) {
                        $(td).css('color', 'lightgreen'),
                        $(td).css('font-weight', 'bold')
                    }}
                },
                { responsivePriority: 1, targets: 5 }]

This works great, however these properties are getting removed on responsive mode.

Responsive mode:

enter image description here

How can I maintain these color values for status? Here my full Javascript:

<script type="text/javascript">
    $(document).ready(function() {
        $('#jquery-datatable-ajax-php').DataTable({
            'processing': true,
            'responsive': true,
            'serverSide': true,
            'serverMethod': 'post',
            'order': [[5, 'desc']],
            'ajax': {
            'url':'datatable.php'
            },
            'columns': [
                { data: 'client_name' },
                { data: 'quote_number' },
                { data: 'project' },
                { data: 'status' },
                { data: 'quote_total', render: $.fn.dataTable.render.number(',', '.', 2,), className: 'dt-body-right'},
                { data: 'id', 'name': 'id', fnCreatedCell: function (nTd, sData, oData, iRow, iCol) {$(nTd).html("<a class='link' href='/quotes/view/" oData.id "?nocache=<?php echo time()?>'>View</a>");}}
            ],
            'columnDefs': [ {
                'targets': 3,
                'createdCell': function (td, cellData, rowData, row, col) {
                    if ( cellData == 'Pending' ) {
                        $(td).css('color', '#e27522'),
                        $(td).css('font-weight', 'bold')
                    }
                    else if ( cellData == 'Confirmed' ) {
                        $(td).css('color', 'green'),
                        $(td).css('font-weight', 'bold')
                    }
                    else if ( cellData == 'Accepted' ) {
                        $(td).css('color', 'lightgreen'),
                        $(td).css('font-weight', 'bold')
                    }}
                },
                { responsivePriority: 1, targets: 5 }]
       });
    } );
</script>

Some expert help would be greatly appreciated, thank you.

CodePudding user response:

You can create the status labels for "Pending", "Confirmed" and "Accepted" inside a <span> element - and add a class to that element to control its formatting.

When the table is collapsed in responsive mode, the entire span will be transferred to the child record - and the formatting will be preserved.

First add some CSS styles. For simplicity, I have named the CSS classes in my styles to match the status labels. This helps me to avoid writing an if... else... statement for the different class names. But you can call your classes whatever you want:

.Pending {
  color: #e27522;
  font-weight: bold;
}

.Confirmed {
  color: green;
  font-weight: bold;
}

.Accepted {
  color: lightgreen;
  font-weight: bold;
}

Now I can use a column renderer to build the <span> HTML as a text string:

columnDefs: [
  { 
    targets: 5, 
    "render": function ( data, type, row, meta ) {
      if (type === 'display') {
        return '<span >'   data   '</span>';
      } else { 
        return data;
      }
    }
  }
]

Runnable demo:

$(document).ready(function() {

  $('#example').DataTable( {
    responsive: true,
    columnDefs: [
      { 
        targets: 5, 
        "render": function ( data, type, row, meta ) {
          if (type === 'display') {
              return '<span >'   data   '</span>';
          } else {
              return data;
          }
        }
      }
    ]
  } );


} );
<!doctype html>
<html>
<head>
  <meta charset="UTF-8">
  <title>Demo</title>
  <script src="https://code.jquery.com/jquery-3.5.1.js"></script>
  <script src="https://cdn.datatables.net/1.10.22/js/jquery.dataTables.js"></script>
  <link rel="stylesheet" type="text/css" href="https://cdn.datatables.net/1.10.22/css/jquery.dataTables.css">
  <link rel="stylesheet" type="text/css" href="https://datatables.net/media/css/site-examples.css">

  <!-- responsive plug-in -->
  <link rel="stylesheet" type="text/css" href="https://cdn.datatables.net/responsive/2.2.6/css/responsive.dataTables.css"/>
  <script type="text/javascript" src="https://cdn.datatables.net/responsive/2.2.6/js/dataTables.responsive.js"></script>

<style>

.Pending {
  color: #e27522;
  font-weight: bold;
}

.Confirmed {
  color: green;
  font-weight: bold;
}

.Accepted {
  color: lightgreen;
  font-weight: bold;
}

</style>

</head>

<body>

<div style="margin: 20px;">

    <table id="example"  style="width:100%">
        <thead>
            <tr>
                <th>Name</th>
                <th>Position</th>
                <th>Age</th>
                <th>Start date</th>
                <th>Salary</th>
                <th>Status</th>
            </tr>
        </thead>
        <tbody>
            <tr>
                <td>Tiger Nixon</td>
                <td>System Architect</td>
                <td>61</td>
                <td>2011/04/25</td>
                <td>$320,800</td>
                <td>Pending</td>
            </tr>
            <tr>
                <td>Garrett Winters</td>
                <td>Accountant</td>
                <td>63</td>
                <td>2011/07/25</td>
                <td>$170,750</td>
                <td>Confirmed</td>
            </tr>
            <tr>
                <td>Ashton Cox</td>
                <td>Junior Technical Author</td>
                <td>66</td>
                <td>2009/01/12</td>
                <td>$86,000</td>
                <td>Accepted</td>
            </tr>
        </tbody>
    </table>

</div>

</body>
</html>


Additional Note

The type === 'display' logic is how DataTables allows you to create a display value which is different from sorting and filtering values. If you don't do this, you will find that the word "span" (for example) will always find all rows - because of how we built the display data. But if the data type is not display then we just use the underlying data value (without the <span> text). You can read more about this "orthogonal data" here.

  • Related