我有一个表,使用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();
}
答案 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();
答案 1 :(得分:0)
我的回答与this earlier answer非常相似,建议使用计算的observable来表示已排序的表。对于您的方案,它可能如下所示:
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;
不确定如何存储帖子中的缺失位(例如数据以及如何检索它),所以我只是在那里插入了一些普通数据。 (PS。看起来您的Ajax调用是同步处理的?)
答案 2 :(得分:-2)
在我的意见中你可以做这样的事情......但是
(\w+)
&#13;
gcc
&#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();