刷新表而不刷新页面

时间:2016-04-23 18:36:17

标签: javascript html knockout.js

我有一个表,使用knockoutjs显示数组的内容。我希望能够通过单击列的标题对此表进行排序。我的想法是使用javascript .sort()对数组进行排序,然后刷新表而不刷新页面。我不知道如何刷新表而不刷新页面。如果有人能指出我正确的方向,那将是非常感激的!

现在它只是一个html表。有些单元格包含if语句,其他单元格包含整个表格,数据库中有超过80条记录。我不想再进行另一个ajax调用,因为数据库中没有任何变化,只想根据单击的标题对数组进行排序。

我添加了onclick函数,但是我收到了obj未定义的错误。

以下是代码的简化版本:

aspx文件:

<table id="filteredTable">
    <tr>
        <th><button class="btn btn-link btn sm" onclick="SortColumn('TicketTitle')">Title</button></th>
        <th>Priority</th>
    </tr>
<tbody data-bind="foreach: theObject[0]">
    <tr class="tableRow" data-bind="attr: { id: TicketId }">
        <td data-bind="text: TicketTitle"></td>
        <td data-bind="text: TicketPriority"></td>
    </tr>
</tbody>
</table>

js file:

function pageLoad() {
    var url = API_URL + "/api/Ticket/GetTickets";
    var data = Ajax.getData(url);
    var obj = [];
    var tickets = JSON.parse(data.JsonResult);
    obj.Tickets = tickets;
    Tickets.Data = obj;

    var viewModel = {
        theObject: [obj.Tickets]
    };

    ko.applyBindings(viewModel);
}

function SortColumn(column) {
    obj.Tickets.column.sort();
}

3 个答案:

答案 0 :(得分:0)

如果你的表显示了数组的元素(带有淘汰赛的foreach函数),你就不能刷新表...

对数组进行排序会对表格进行排序......

但是,如果您想简化生活,我建议您使用DataTables plugin

使用此插件,您只需在DOM中绘制表格,然后将数据表应用于您绘制的表格...

希望得到这个帮助。

此致

编辑:

试试这个(基于@Jeroen solution):

HTML:     

<table>
    <tr>
        <th>
            <!-- Calling a unnamed function to prevent auto-execute of the function 'changeSort' on binding -->
            <button data-bind="click: function() { resetDir('TicketTitle'); changeSort('TicketTitle'); }">Title</button>
        </th>
        <th>
            <!-- Calling a unnamed function to prevent auto-execute of the function 'changeSort' on binding -->
            <button data-bind="click: function() { resetDir('TicketPriority'); changeSort('TicketPriority'); }">Priority</button>
        </th>
    </tr>
    <tbody data-bind="foreach: Tickets">
        <tr class="tableRow" data-bind="attr: { id: TicketId }">
            <td data-bind="text: TicketTitle"></td>
            <td data-bind="text: TicketPriority"></td>
        </tr>
    </tbody>
</table>

使用Javascript:

function ViewModel(obj) {
    var self = this;

    var sortDir = {
        TicketTitle: "DESC",
        TicketPriority: "DESC",
        LastPressed: ""
    };

    self.Tickets = ko.observableArray(obj.Tickets);

    self.resetDir = function(key) {
        if(sortDir['LastPressed'] != key) sortDir[key] = "DESC";
    }

    self.changeSort = function(newKey) {
        if(sortDir[newKey] == "ASC") sortDir[newKey] = "DESC";
        else sortDir[newKey] = "ASC";

        self.Tickets.sort(function(a, b) {
            if(sortDir[newKey] == "ASC") {
                if(a[newKey] < b[newKey]) return -1;
                if(a[newKey] > b[newKey]) return 1;
                return 0;
            } else {
                if(b[newKey] < a[newKey]) return -1;
                if(b[newKey] > a[newKey]) return 1;
                return 0;
            }
        });

        sortDir['LastPressed'] = newKey;
    };

    self.changeSort("TicketTitle");
}

function pageLoad() {
    // Fake data:
    var obj = {
        Tickets: [
            { TicketId: 1, TicketTitle: "Aaa title", TicketPriority: "C. Low" },
            { TicketId: 2, TicketTitle: "Be a title", TicketPriority: "B. Medium" },
            { TicketId: 3, TicketTitle: "Aaa title", TicketPriority: "A. High" },
            { TicketId: 4, TicketTitle: "Baahaha ya", TicketPriority: "A. High" },
            { TicketId: 5, TicketTitle: "C u later", TicketPriority: "B. Medium" }
        ]
    };

    var viewModel = new ViewModel(obj);

    ko.applyBindings(viewModel);
}

pageLoad();

JSFiddle

中测试代码

答案 1 :(得分:0)

我的回答与this earlier answer非常相似,建议使用计算的observable来表示已排序的表。对于您的方案,它可能如下所示:

&#13;
&#13;
function ViewModel(obj) {
  var self = this;
  
  self.Tickets = ko.observableArray(obj.Tickets);
  
  self.sortKey = ko.observable("TicketTitle");
  
  self.changeSort = function(newKey) {
    // TODO: Handle asc/desc here too.
    self.sortKey(newKey);
  };
  
  self.TicketsSorted = ko.computed(function() {
    var key = self.sortKey();
    return self.Tickets().sort(function(a, b) {
      return a[key].localeCompare(b[key]);
    });
  });
}

function pageLoad() {
  // Fake data:
  var obj = { Tickets: [
    { TicketId: 1, TicketTitle: "Aaa title", TicketPriority: "C. Low" },
    { TicketId: 2, TicketTitle: "Be a title", TicketPriority: "B. Medium" },
    { TicketId: 3, TicketTitle: "Aaa title", TicketPriority: "A. High" },
    { TicketId: 4, TicketTitle: "Baahaha ya", TicketPriority: "A. High" },
    { TicketId: 5, TicketTitle: "C u later", TicketPriority: "B. Medium" }
  ] };

  var viewModel = new ViewModel(obj);

  ko.applyBindings(viewModel);
}

pageLoad();
&#13;
td { padding: 2px 5px; background: #eee; }
&#13;
<script src="https://cdnjs.cloudflare.com/ajax/libs/knockout/3.4.0/knockout-min.js"></script>

<table>
  <tr>
    <th>
      <button data-bind="click: changeSort('TicketTitle')">Title</button>
    </th>
    <th>
      <button data-bind="click: changeSort('TicketPriority')">Priority</button>
    </th>
  </tr>
  <tbody data-bind="foreach: TicketsSorted">
    <tr class="tableRow" data-bind="attr: { id: TicketId }">
      <td data-bind="text: TicketTitle"></td>
      <td data-bind="text: TicketPriority"></td>
    </tr>
  </tbody>
</table>
&#13;
&#13;
&#13;

不确定如何存储帖子中的缺失位(例如数据以及如何检索它),所以我只是在那里插入了一些普通数据。 (PS。看起来您的Ajax调用是同步处理的?)

答案 2 :(得分:-2)

在我的意见中你可以做这样的事情......但是

&#13;
&#13;
(\w+)
&#13;
gcc
&#13;
&#13;
&#13;

您可以创建一个函数,并作为回报为您提供所有表数据,并像这样调用函数:function refresh(){ var cont = "<table>"+ "<tr>"+/*use loop */ "<td>"+ "name"+ "</td>"+ "<td>"+ "exe"+ "</td>"+ "</tr>"+ "<tr>"+ "<td>"+ "name2"+ "<td>"+ "exe2"+ "</td>"+ "</td>"+ "</tr>"+ "</table>"; return cont; } document.getElementById("tableContainerID").innerHTML = refresh();

如果您使用jquery,那么这可以帮助您.html();