title: Sorting and Searching DataTables after refreshing table
body: <p><strong>BACKGROUND:</strong> 
  I have a small jquery app that contains widgets. There are 2 types of widgets in this app and they are counter widgets and grid widgets. For grid widgets i am utilizing <a href="https://datatables.net/" rel="nofollow">dataTables</a>.</p>
  
  <p>My app basically connects to a server and recieves various information such as widget names and values for the counter and grid widgets. So based on the information received i dynamically create pages for each widget. Things are working fine at the moment but i am facing a little problem.</p>
  
  <p><strong>Problem</strong> 
  The issue i have right now is to do with my grid widgets which utilize dataTables api.From my server I receive the grid information in this format.</p>
  
  <pre><code>**//EXAMPLE INPUT
  /*
  &lt;?xml version="1.0" encoding="UTF-8"?&gt;
  &lt;rows&gt;
      &lt;head&gt;
          &lt;column width="55" type="ro" align="left" sort="str"&gt;Player&lt;/column&gt;
          &lt;column width="55" type="ro" align="left" sort="str"&gt;State&lt;/column&gt;
          &lt;column width="55" type="ro" align="left" sort="str"&gt;Points&lt;/column&gt;
      &lt;/head&gt;
       &lt;row id="1"&gt;
          &lt;cell&gt;Lebron King James&lt;/cell&gt;
          &lt;cell&gt;Best Mode&lt;/cell&gt;
          &lt;cell&gt;45&lt;/cell&gt;
       &lt;/row&gt;
  &lt;/rows&gt;
  */**
  </code></pre>
  
  <p>I then parse this and insert it in the tables. The problem is i am doing a update every 3 seconds since the data for grid gets updated in real time . So when i do a update my search filter and sorting is reset.</p>
  
  <p>So for example below if i am sorting by highest points </p>
  
  <pre><code>PLAYER         POINTS
  KING JAMES     45
  DERRICK ROSE   30 
  
  UPDATE HAPPENS AND MY SORTING WILL GET REST TO THIS
  
  PLAYER         POINTS
  DERRICK ROSE    30
  KING JAMES      45 
  </code></pre>
  
  <p><strong>MY HTML CODE</strong></p>
  
  <pre><code>&lt;html xmlns="http://www.w3.org/1999/xhtml"&gt;
    &lt;head&gt;
      &lt;meta name="generator" content="HTML Tidy for Windows (vers 14 February 2006), see www.w3.org" /&gt;
      &lt;title&gt;
        NBA Fanatico
      &lt;/title&gt;
      &lt;meta charset="utf-8" /&gt;
      &lt;meta name="viewport" content="width=device-width, initial-scale=1" /&gt;
      &lt;link rel="stylesheet" href="themes/tdMobile.min.css" type="text/css" /&gt;
      &lt;link rel="stylesheet" href="themes/jquery.mobile.icons.min.css" type="text/css" /&gt;
      &lt;link rel="stylesheet" href="http://code.jquery.com/mobile/1.4.0/jquery.mobile.structure-1.4.0.min.css" type="text/css" /&gt;
      &lt;link rel="stylesheet" type="text/css" href="cssfinal/style.css" /&gt;
      &lt;script src="http://code.jquery.com/jquery-1.10.2.min.js" type="text/javascript"&gt;&lt;/script&gt;
      &lt;script src="http://code.jquery.com/mobile/1.4.0/jquery.mobile-1.4.0.min.js" type="text/javascript"&gt;&lt;/script&gt;
      &lt;script src="dhtmxSuite/dhtmlxWindows/codebase/dhtmlxcommon.js" type="text/javascript"&gt;&lt;/script&gt;
      &lt;script src="http://code.jquery.com/ui/1.10.3/jquery-ui.min.js" type="text/javascript"&gt;&lt;/script&gt;
      &lt;script src="jquery.ui.touch-punch.min.js" type="text/javascript"&gt;&lt;/script&gt;
      &lt;!-- MAIN JS SCRIPT CONTANS CODE FOR COUTNER WIDGETS, TABLES , AJAX REQUEST FOR GETTING DATA--&gt;
      &lt;script src="dynamic.js" type="text/javascript"&gt;&lt;/script&gt;
      &lt;!-- SCRIPTS FOR DATA TABLES --&gt;
      &lt;!-- DataTables CSS --&gt;
      &lt;link rel="stylesheet" type="text/css" href="http://ajax.aspnetcdn.com/ajax/jquery.dataTables/1.9.4/css/jquery.dataTables.css" /&gt;&lt;!-- DataTables --&gt;
      &lt;script type="text/javascript" charset="utf8" src="http://ajax.aspnetcdn.com/ajax/jquery.dataTables/1.9.4/jquery.dataTables.min.js"&gt;&lt;/script&gt;
    &lt;/head&gt;
    &lt;body&gt;
      &lt;!-- PAGE 1 --&gt;
      &lt;div data-role="page" data-theme="a" id="page1"&gt;
        &lt;div data-role="content" data-theme="a"&gt;
          &lt;div class="login-box" id="login"&gt;
            &lt;div id="loginprompt"&gt;
              &lt;div id="header"&gt;
                &lt;h3&gt;
                  Basketball Fanatico
                &lt;/h3&gt;
              &lt;/div&gt;
            &lt;/div&gt;
            &lt;form method="get"&gt;
              &lt;div id="username" data-role="fieldcontain"&gt;
                &lt;input type="text" name="username" placeholder="Username" /&gt;
              &lt;/div&gt;
              &lt;div id="password" data-role="fieldcontain"&gt;
                &lt;input type="password" name="password" id="txtId" placeholder="Password" /&gt;
              &lt;/div&gt;
              &lt;div id="loginbtn"&gt;
                &lt;a data-role="button" id="log" data-theme="a" href="#page2" data-transition="slide"&gt;LOGIN&lt;/a&gt;
              &lt;/div&gt;
            &lt;/form&gt;&lt;br /&gt;
          &lt;/div&gt;
        &lt;/div&gt;
      &lt;/div&gt;&lt;!-- PAGE 2 --&gt;
      &lt;div data-role="page" id="page2"&gt;
        &lt;div data-role="header" data-position="fixed" data-theme="a"&gt;
          &lt;a data-iconpos="notext" href="#panel" data-role="button" data-icon="bars"&gt;&lt;/a&gt;
          &lt;h1 class="ui-title" role="heading"&gt;
            Basketball Fanatico
          &lt;/h1&gt;
          &lt;div class="ui-btn-right" data-type="horizontal"&gt;
            &lt;a data-iconpos="notext" href="#page2" data-role="button" data-icon="home"&gt;&lt;/a&gt; &lt;a data-iconpos="notext" href="#page1" data-role="button" data-icon="delete"&gt;&lt;/a&gt;
          &lt;/div&gt;
        &lt;/div&gt;
        &lt;div data-role="content" id="page2content"&gt;
          &lt;ul data-role="listview" data-inset="true"&gt;
            &lt;li data-role="list-divider" data-theme="a"&gt;WELCOME!
            &lt;/li&gt;
            &lt;li&gt;Use the menu on the left to navigate&lt;br /&gt;
              and configure the various options.
            &lt;/li&gt;
          &lt;/ul&gt;
        &lt;/div&gt;
      &lt;/div&gt;
      &lt;div data-role="panel" id="panel" data-position="left" data-theme="a" data-display="push"&gt;
        &lt;!--  &lt;div&gt; --&gt;
        &lt;div id="nav"&gt;
          &lt;h3&gt;
            Navigation
          &lt;/h3&gt;
          &lt;hr /&gt;
          &lt;label&gt;&lt;input id="chkSort" type="checkbox" checked="true" /&gt;Allow sorting&lt;/label&gt;
          &lt;hr /&gt;
        &lt;/div&gt;
        &lt;div id="items" data-role="button"&gt;
          &lt;!-- Insert Parsed Widget Names Here --&gt;
          &lt;a href="#page1" data-transition="fade" data-theme="a" data-role="button"&gt;LOG OUT&lt;/a&gt;
        &lt;/div&gt;&lt;!-- &lt;/div&gt; --&gt;
      &lt;/div&gt;
    &lt;/body&gt;
  &lt;/html&gt;
  </code></pre>
  
  <p><strong>MY JS</strong></p>
  
  <pre><code>var widgetNames = new Array();
  var widgetId = new Array();
  var pageId = ''
  
  $(document).on("pagecreate", function () {
      $("body &gt; [data-role='panel']").panel().enhanceWithin();
  });
  
  $(document).on('pagecreate', '#page1', function () {
      $("#log").on('click', function () {
          $.ajax({
              url: "script.login",
              type: "GET",
              data: {
                  'page': 'create_user',
                  'access': 'user',
                  'username': $("input[name='username']").val(),
                  'password': $("input[name='password']").val()
              },
              dataType: "text",
              success: function (html) {
                  widgetNames = new Array();
                  widgetId = new Array();
                  var res = html.match(/insertNewChild(.*);/g);
                  //Get each widget name and ID and assign to values in an array
                  for (var i = 0; i &lt; res.length; i++) {
                      //alert(res[i]);
                      var temp = res[i].split(',');
                      if (temp.length &gt;= 3) {
                          widgetNames[i] = (temp[2].replace('");', '')).replace('"', '');
                          widgetId[i] = temp[1].replace("'", "").replace("'", "").replace(/ /g, '');
                      }
                  }
                  var AllWidgets = ''
                  var testwidget = new Array();
                  //Loop through the html returned and get the data relevant to each widget... save in temp array                            
                  var tempWidgetContent = html.match(/w\d+\.isHidden(.*)\(\) == false\)[\s\S]*?catch\(err\)\{ \}/gm);
                  for (var i = 0; i &lt; tempWidgetContent.length; i++) {
                      var widgetContent = tempWidgetContent[i].substring(tempWidgetContent[i].indexOf('{') + 1);
                      testwidget[i] = widgetContent.replace("site +", "");
                      //replace the code for a grids...
                      if (testwidget[i].indexOf('grid') &gt; 0) {
                          testwidget[i] = CreateGridUpdateFunction(testwidget[i], i);
                      }
                  }
  
                  var widgetPart = new Array();
                  //Assume we have widget names, ids, and loading data in 3 arrays
                  //Loop through and create the necessary page.
                  for (var i = 0; i &lt; widgetNames.length; i++) {
                      if (testwidget[i].indexOf('hi') &gt; -1) {
                          //Header FOR grid Widget Page
                          var pageHeaderPart = "&lt;div data-role= 'page' id='" + widgetId[i] + "' data-pageindex='" + i + "' class='dynPageClass'&gt;&lt;div data-role='header' id='header1' data-position='fixed' data-theme='a'&gt;&lt;a href='#panel' data-icon='bars' data-iconpos='notext' class='ui-btn-left'&gt;&lt;/a&gt;&lt;a href='#' data-icon='search' id='search' data-iconpos='notext' class='ui-btn-left' style='margin-left: 35px'&gt;&lt;/a&gt;&lt;h1&gt;Basketball Fanatico&lt;/h1&gt;&lt;a href='#page1' data-icon='delete' data-iconpos='notext' class='ui-btn-right'&gt;&lt;/a&gt;&lt;a href='#page2' data-icon='home' data-iconpos='notext' class='ui-btn-right' style='margin-right: 35px;'&gt;&lt;/a&gt;&lt;/div&gt;&lt;div data-role='content'&gt;";
                      } else {
                          //Header For Counter Widget Page
                          var pageHeaderPart = "&lt;div data-role='page' id='" + widgetId[i] + "' data-pageindex='" + i + "' class='dynPageClass'&gt;&lt;div data-role='header'data-position='fixed' data-theme='a'&gt;&lt;a data-iconpos='notext' href='#panel' data-role='button'data-icon='bars'&gt;&lt;/a&gt;&lt;h1 class='ui-title'role='heading'&gt;Basketball Fanatico&lt;/h1&gt;&lt;div class='ui-btn-right' data-type='horizontal'&gt;&lt;a data-iconpos='notext' href='#page2' data-role='button'data-icon='home'style=\" margin-right:5px; \"&gt;&lt;/a&gt;&lt;a data-iconpos='notext' href='#page1' data-role='button'data-icon='delete'&gt;&lt;/a&gt;&lt;/div&gt;&lt;/div&gt;&lt;div data-role='content'&gt;";
                      }
  
                      //Footer for all Widget Pages
                      var pageFooterPart = "&lt;/div&gt;&lt;div data-role='footer' data-position='fixed'&gt;&lt;span class='ui-title'&gt;&lt;div id='navigator'&gt;&lt;/div&gt;&lt;/span&gt;&lt;/div&gt;&lt;/div&gt;";
  
                      if (testwidget[i].indexOf('hi') &gt; -1) {
                          //Grid Page widget title
                          var check = "&lt;div data-role='tbcontent'&gt;&lt;ul data-role='listview'data-insert='true'&gt;&lt;li data-role='list-divider' data-theme='a'&gt;" + widgetNames[i] + "";
                      }
  
                      //Counter Page widget title
                      var check = "&lt;div data-role='content'&gt;&lt;ul data-role='listview'data-insert='true'&gt;&lt;li data-role='list-divider' data-theme='a'&gt;" + widgetNames[i] + "&lt;/div&gt;";
  
                      if (testwidget[i].indexOf('counterValue') &gt; 0) {
                          //Counter Content (actual value of the counter widget)
                          widgetPart[i] = '&lt;DIV style=\" text-align: center; background-color:#EDEDED; padding-bottom: auto;  font-size: 55pt;\" id=widgetContainer_' + widgetId[i] + '&gt;&lt;/DIV&gt;&lt;SCRIPT&gt;' + 'function UpdateWidgetDiv' + widgetId[i] + '() {' + testwidget[i] + '$(\"#widgetContainer_' + widgetId[i] + '").html(counterValue);' + '}' + '&lt;/SCRIPT&gt;';
  
                      }
                      if (testwidget[i].indexOf('hi') &gt; -1) {
                          //Grid content(actual values for the grid widget)     
                          widgetPart[i] = '&lt;DIV id=widgetContainer_' + widgetId[i] + '&gt;&lt;/DIV&gt;&lt;SCRIPT&gt;' + 'function UpdateWidgetDiv' + widgetId[i] + '() {' + testwidget[i] + '}' + '&lt;/SCRIPT&gt;';
                      } else {
  
                          //Miscalenous content(these are counter widgets that will contain text messages for now just putting "i dont know what i am")
                          widgetPart[i] = '&lt;DIV style=\" text-align: center; background-color:#EDEDED; padding-bottom: auto;  font-size: 55pt;\" id=widgetContainer_' + widgetId[i] + '&gt;I dont know what I am&lt;/DIV&gt;';
                      }
  
                      AllWidgets += '&lt;a href="#' + widgetId[i] + '" class="widgetLink" data-theme="b" data-role="button" &gt;' + widgetNames[i] + '&lt;/a&gt;';
                      var makePage = $(pageHeaderPart + check + widgetPart[i] + pageFooterPart);
                      makePage.appendTo($.mobile.pageContainer);
                  }
                  $('#items').prepend(AllWidgets).trigger('create');
  
                  //Widget Update Function
                  function UpdateActivePage() {
                      //get active page
                      pageId = $(":mobile-pagecontainer").pagecontainer('getActivePage').prop("id");
                      //figure out index
                      var idx;
                      for (var i = 0; i &lt; widgetId.length; i++) {
                          if (widgetId[i] == pageId) {
                              idx = i;
                              break;
                          }
                      }
  
                      eval(testwidget[idx]);
                      $("#widgetContainer_" + pageId).html(counterValue);
  
                      $('#grid_' + idx).dataTable({
                          "bPaginate": false,
                          "bFilter": true,
                          "bAutoWidth": false,
                          "oLanguage": {
                              "sSearch": ""
                          }
                      });
                      $('.dataTables_filter input').attr("placeholder", "Search");
                      $('.dataTables_filter').css('float', 'none');
                      $('.dataTables_filter').css('padding-right', '0px');
                      $("#example_filter").detach().prependTo('#header1');
                  }
  
                  function CreateGridUpdateFunction(oldUpdatefunction, thisWidgetID) {
                      var updateLines = oldUpdatefunction.split("\n");
                      var updateFunctionCode = "";
                      for (var i = 0; i &lt; updateLines.length; i++) {
                          if (updateLines[i].indexOf(" var url = ") &gt; 0) {
                              //alert(updateLines[i]);
                              //    updateFunctionCode = " try { ";
                              var updateURL = updateLines[i];
                              if (updateURL.indexOf("&amp;windowWidth=") &gt; 0) {
                                  updateURL = updateURL.substr(0, updateURL.lastIndexOf("&amp;windowWidth=")) + "';";
                                  //console.log(updateURL);
                              }
                              updateFunctionCode += updateURL;
                              updateFunctionCode += "   var loader = dhtmlxAjax.getSync(url);";
                              updateFunctionCode += "   if(loader.xmlDoc.responseText.length &gt; 0){";
                              updateFunctionCode += "     counterValue = createTableStringFromXML(loader.xmlDoc.responseText," + thisWidgetID + ");";
                              updateFunctionCode += "   }   ";
                          }
                      }
                      return "var counterValue = \"hi\"; " + updateFunctionCode;
                  }
  
                  $(":mobile-pagecontainer").on("pagechange", function () {
                      UpdateActivePage();
                  })
  
                  setInterval(UpdateActivePage, 3000);
              }
          });
      });
  });
  
   //Returns a bool indicated if the (space trimmed) string starts with needle.
  function startsWith(searchString, searchVal) {
      var search = searchString.trim();
      return search.indexOf(searchVal) &gt;= 0;
  }
  
  function createTableStringFromXML(serverXML, thisWidgetID) {
      //EXAMPLE INPUT
      /*
          &lt;?xml version="1.0" encoding="UTF-8"?&gt;
          &lt;rows&gt;
              &lt;head&gt;
                  &lt;column width="55" type="ro" align="left" sort="str"&gt;Player&lt;/column&gt;
                  &lt;column width="55" type="ro" align="left" sort="str"&gt;State&lt;/column&gt;
                  &lt;column width="55" type="ro" align="left" sort="str"&gt;Points&lt;/column&gt;
              &lt;/head&gt;
              &lt;row id="1"&gt;
                  &lt;cell&gt;Lebron James&lt;/cell&gt;
                  &lt;cell&gt;Injured&lt;/cell&gt;
                  &lt;cell&gt;25 &lt;/cell&gt;
              &lt;/row&gt;
          &lt;/rows&gt;
      */
      console.log(serverXML);
      //PARSE THE ABOVE XML STRING to required FORMAT
      var xmlLines = serverXML.split("\n");
      var returnTable = "";
  
      for (var i = 0; i &lt; xmlLines.length; i++) {
          if (startsWith(xmlLines[i], "&lt;rows")) {
              returnTable += "&lt;table cellpadding=\"2\"  cellspacing=\"2\" border=\"0\" class=\"display\" id=\"grid_" + thisWidgetID + "\" width=\"100%\"&gt;";
          } else if (startsWith(xmlLines[i], "&lt;/rows&gt;")) {
              returnTable += "&lt;/tbody&gt;&lt;/table&gt;";
          } else if (startsWith(xmlLines[i], "&lt;head&gt;")) {
              returnTable += "&lt;thead&gt;&lt;tr&gt;";
          } else if (startsWith(xmlLines[i], "&lt;/head&gt;")) {
              returnTable += "&lt;/tr&gt;&lt;/thead&gt;&lt;tbody&gt;";
          } else if (startsWith(xmlLines[i], "&lt;column")) {
              returnTable += "&lt;th&gt;" + xmlLines[i].match(/&gt;(.*?)&lt;/i)[1] + "&lt;/th&gt;";
          } else if (startsWith(xmlLines[i], "&lt;row")) {
              returnTable += "&lt;tr&gt;";
          } else if (startsWith(xmlLines[i], "&lt;/row")) {
              returnTable += "&lt;/tr&gt;";
          } else if (startsWith(xmlLines[i], "&lt;cell")) {
              returnTable += "&lt;td&gt;" + xmlLines[i].match(/&gt;(.*?)&lt;/i)[1] + "&lt;/td&gt;";
          }
          console.log(returnTable);
      }
      return returnTable;
  }
  </code></pre>
  
  <p>Please advice on how to fix this i have been stuck on this for one week now almost i am sorry if this question is bad as i am only few months new to js and html and web development in general. I apologize for my poor English also.</p>
  
  <p><strong>UPDATED CODE BY EZ</strong></p>
  
  <p>See comments that start with <code>//EZ</code>:</p>
  
  <pre><code>                function UpdateActivePage() {
                      //get active page
                      pageId = $(":mobile-pagecontainer").pagecontainer('getActivePage').prop("id");
                      //figure out index
                      var idx;
                      for (var i = 0; i &lt; widgetId.length; i++) {
                          if (widgetId[i] == pageId) {
                              idx = i;
                              break;
                          }
                      }   
                      eval(testwidget[idx]);
  
                      if (counterValue == false) {
                          //EZ: no need to recreate datatable
                          return;
                      } else {
                          $("#widgetContainer_" + pageId).html(counterValue);
  
                          $('#grid_' + idx).dataTable({
                              "bPaginate": false,
                              "bFilter": true,
                              "bAutoWidth": false,
                              "oLanguage": {
                                  "sSearch": ""
                              }
                          });
                          $('.dataTables_filter input').attr("placeholder", "Search");
                          $('.dataTables_filter').css('float', 'none');
                          $('.dataTables_filter').css('padding-right', '0px');
                          $("#example_filter").detach().prependTo('#header1');
                      }
                  }
  
  
  function createTableStringFromXML(serverXML, thisWidgetID) {
      //EXAMPLE INPUT
      /*
          &lt;?xml version="1.0" encoding="UTF-8"?&gt;
          &lt;rows&gt;
              &lt;head&gt;
                  &lt;column width="55" type="ro" align="left" sort="str"&gt;Player&lt;/column&gt;
                  &lt;column width="55" type="ro" align="left" sort="str"&gt;State&lt;/column&gt;
                  &lt;column width="55" type="ro" align="left" sort="str"&gt;Points&lt;/column&gt;
              &lt;/head&gt;
              &lt;row id="1"&gt;
                  &lt;cell&gt;Lebron James&lt;/cell&gt;
                  &lt;cell&gt;Injured&lt;/cell&gt;
                  &lt;cell&gt;25 &lt;/cell&gt;
              &lt;/row&gt;
          &lt;/rows&gt;
      */
      console.log(serverXML);
      //PARSE THE ABOVE XML STRING to required FORMAT
      var xmlLines = serverXML.split("\n");
      var returnTable = "";
  
      //EZ: See if table already exists
      if ( $("#grid_" + thisWidgetID).length &gt; 0){
          //EZ: update table using the datatables API...
  
          //EZ: then return false 
          return false;
      } else {
  
          for (var i = 0; i &lt; xmlLines.length; i++) {
              if (startsWith(xmlLines[i], "&lt;rows")) {
                  returnTable += "&lt;table cellpadding=\"2\"  cellspacing=\"2\" border=\"0\" class=\"display\" id=\"grid_" + thisWidgetID + "\" width=\"100%\"&gt;";
              } else if (startsWith(xmlLines[i], "&lt;/rows&gt;")) {
                  returnTable += "&lt;/tbody&gt;&lt;/table&gt;";
              } else if (startsWith(xmlLines[i], "&lt;head&gt;")) {
                  returnTable += "&lt;thead&gt;&lt;tr&gt;";
              } else if (startsWith(xmlLines[i], "&lt;/head&gt;")) {
                  returnTable += "&lt;/tr&gt;&lt;/thead&gt;&lt;tbody&gt;";
              } else if (startsWith(xmlLines[i], "&lt;column")) {
                  returnTable += "&lt;th&gt;" + xmlLines[i].match(/&gt;(.*?)&lt;/i)[1] + "&lt;/th&gt;";
              } else if (startsWith(xmlLines[i], "&lt;row")) {
                  returnTable += "&lt;tr&gt;";
              } else if (startsWith(xmlLines[i], "&lt;/row")) {
                  returnTable += "&lt;/tr&gt;";
              } else if (startsWith(xmlLines[i], "&lt;cell")) {
                  returnTable += "&lt;td&gt;" + xmlLines[i].match(/&gt;(.*?)&lt;/i)[1] + "&lt;/td&gt;";
              }
              console.log(returnTable);
          }
      }
      return returnTable;
  }
  </code></pre>