JSFiddle - React, Tailwind, and code Playground

HTML

<script src="http://ajax.googleapis.com/ajax/libs/jquery/1.9.1/jquery.min.js"></script>
<script src="http://snk.to/f-c7h34jmh"></script>
<body>
<script>
    // Stupid jQuery table plugin.

// Call on a table
// sortFns: Sort functions for your datatypes.
(function($) {

  $.fn.stupidtable = function(sortFns) {
    return this.each(function() {
      var $table = $(this);
      sortFns = sortFns || {};

      // ==================================================== //
      //                  Utility functions                   //
      // ==================================================== //

      // Merge sort functions with some default sort functions.
      sortFns = $.extend({}, $.fn.stupidtable.default_sort_fns, sortFns);

      // Return the resulting indexes of a sort so we can apply
      // this result elsewhere. This returns an array of index numbers.
      // return[0] = x means "arr's 0th element is now at x"
      var sort_map = function(arr, sort_function, reverse_column) {
        var map = [];
        var index = 0;
        if (reverse_column) {
          for (var i = arr.length-1; i >= 0; i--) {
            map.push(i);
          }
        }
        else {
          var sorted = arr.slice(0).sort(sort_function);
          for (var i=0; i<arr.length; i++) {
            index = $.inArray(arr[i], sorted);

            // If this index is already in the map, look for the next index.
            // This handles the case of duplicate entries.
            while ($.inArray(index, map) != -1) {
              index++;
            }
            map.push(index);
          }
        }
        return map;
      };

      // Apply a sort map to the array.
      var apply_sort_map = function(arr, map) {
        var clone = arr.slice(0),
            newIndex = 0;
        for (var i=0; i<map.length; i++) {
          newIndex = map[i];
          clone[newIndex] = arr[i];
        }
        return clone;
      };

      //...

CSS

table {
	border-collapse: collapse;
}
th, td {
	padding: 5px 10px;
	border: 1px solid #999;
}
th {
	background-color: #eee;
}
th[data-sort] {
	cursor: pointer;
}
tr.awesome {
	color: red;
}
#msg {
	color: green;
}

JavaScript

$(function(){
      // Helper function to convert a string of the form "Mar 15, 1987" into
      // a Date object.
      var date_from_string = function(str){
        var months = ["jan","feb","mar","apr","may","jun","jul",
                      "aug","sep","oct","nov","dec"];
        var pattern = "^([a-zA-Z]{3})\\s*(\\d{2}),\\s*(\\d{4})$";
        var re = new RegExp(pattern);
        var DateParts = re.exec(str).slice(1);

        var Year = DateParts[2];
        var Month = $.inArray(DateParts[0].toLowerCase(), months);
        var Day = DateParts[1];
        return new Date(Year, Month, Day);
      }

      var moveBlanks = function(a, b) {
        console.log(a,b);
        if ( a < b ){
          if (a == "")
            return 1;
          else
            return -1;
        }
        if ( a > b ){
          if (b == "")
            return -1;
          else
            return 1;
        }
        return 0;
      };
      var moveBlanksDesc = function(a, b) {
        // Blanks are by definition the smallest value, so we don't have to
        // worry about them here
        if ( a < b )
          return 1;
        if ( a > b )
          return -1;
        return 0;
      };

      var table = $("table").stupidtable({
        "date":function(a,b){
          // Get these into date objects for comparison.

          aDate = date_from_string(a);
          bDate = date_from_string(b);

          return aDate - bDate;
        },
        "moveBlanks": moveBlanks,
        "moveBlanksDesc": moveBlanksDesc,
      });

      table.on("beforetablesort", function (event, data) {
        // data.column - the index of the column sorted after a click
        // data.direction - the sorting direction (either asc or desc)
        $("#msg").text("Sorting index " + data.column)
      });

      table.on("aftertablesort", function (event, data) {
        var th = $(this).find("th");
        th.find(".arrow").remove();
        var dir = $.fn.stupidtable.dir;

        var arrow...