JSFiddle - React, Tailwind, and code Playground

HTML

<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/2.2.0/jquery.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/angular.js/1.5.0/angular.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/datatables/1.10.11/js/jquery.dataTables.min.js"></script>
<script src="https://cdn.datatables.net/keytable/2.1.1/js/dataTables.keyTable.min.js"></script>
<script src="https://cdn.datatables.net/buttons/1.1.2/js/dataTables.buttons.min.js"></script>
<script src="https://cdn.datatables.net/buttons/1.1.2/js/buttons.html5.min.js"></script>
<link rel="stylesheet" href="https://cdn.datatables.net/1.10.11/css/jquery.dataTables.min.css">
<link rel="stylesheet" href="https://cdn.datatables.net/buttons/1.1.2/css/buttons.dataTables.min.css">
<link rel="stylesheet" href="https://cdn.datatables.net/keytable/2.1.1/css/keyTable.dataTables.min.css">
<div ng-controller="applicationController">
  <div id="tableDiv" />
</div>

CSS

.datatableCell {
        height: 25px;
        margin: 0 !important;
        padding: 0 !important;
        width: 100% !important;
            resize: none !important;
    overflow: visible !important;
    padding:0 !important;
    margin:0 !important;
    line-height:25px;
    width: 100%;
    -webkit-box-sizing: border-box; /* <=iOS4, <= Android  2.3 */
       -moz-box-sizing: border-box; /* FF1+ */
            box-sizing: border-box; /* Chrome, IE8, Opera, Safari 5.1*/
    height:100% !important;
       top:0;
    bottom:0;
    left:0;
    right:0;
    position:absolute;
    }

    #displayTable { 
    border-spacing: 0 !important;
    border-collapse: collapse !important;

}

        #displayTable th, #displayTable td { 
            margin: 0 !important;
        padding: 2px 0 0 !important;
        line-height:25px;
            height: 25px !important;
            position:relative;
            vertical-align: top;

}

JavaScript

var app = angular.module('appModule', []);
app.controller('applicationController', ['$scope', function ($scope) {
    $scope.SelectedUser = "";
    $scope.SelectedPage = "";
    $scope.EditingPageId = "";
    $scope.Notes = [];
    $scope.RowTemplate = [];
    $scope.Columns = [];
    $scope.Table = [];
    $scope.CurrentCell = [];

    $scope.GetPageInfo = function () {
          var responseColumns = [{"Name": "", "Type":"String", "Width": 18},{"Name": "Id", "Type":"Int32", "Width": 18},{"Name": "Notes", "Type": "String", "Width":4000}];
          			

          $scope.Notes = [
          	{"" : "", Id: "1", Notes: "some notes"},
            {"" : "", Id: "2", Notes: "some notes"}
          ];

					//if stored columns doesn't equal response columns, then recreate table
          if (!angular.equals($scope.Columns, responseColumns)) {
              $scope.Columns = responseColumns;
              var tableHeadersString = "";
              var tableHeaders = [];

							//foreach column, dynamically create columns
              $.each($scope.Columns, function (i, val) {
              
              		//Set Command column
                  if (val.Name == "") {
                      tableHeaders.push({
                          data: val.Name,
                          width: 20,
                          "render": function (data, type, row) {
                              return "<div class='command ui'></div>";
                          }
                      });
                  }
                  else
                  //Set Id column
                      if (val.Name == "Id") {
                          tableHeaders.push({
                              data: val.Name,
                              visible: false,
                              "render": function (data, type, row) {
                                  return "<textarea  cols='5000'  wrap='hard'  id='#Cell_" + val.Name.replace(" ", "_") + "' class='datatableCell'>" + data + "</textarea>";
    ...