我有一个包含13列的dgrid表。
按降序排序:最大值,然后是最小值,然后是没有值的项。
然而,当我按升序排序时,有没有值的字段,然后是0的字段,然后是没有值的字段,最后是升序值的字段。
我已经查看了源代码,但我无法弄清楚是什么导致了这一点。
这是dgrid排序的错误吗?
这个问题的解决方法是什么?
假设您的列是只读的,您可以在数据源中添加一个字段(参见下面代码中的displayValue
)来反映您的值,但是其中字符串将被替换为负数。
然后,在网格中只放置这个字段,而不是实际字段。并在列的get
函数中显示实值。
我使用了相同的解决方法,在填充了专有名称的列中应用不区分大小写的排序。
require(["dgrid/Grid", "dojo/domReady!"], function (Grid) {
var data = [];
for(var i = 0; i < 3; i++) for(j = 1; j <= 2; j++) data.push({value: i});
for(i = 1; i < 3; i++) data.push({value: ""});
data.forEach(function(item) {
item.displayValue = typeof item.value == "string" ? -1 : item.value;
});
var grid = new Grid({
columns: {
displayValue: {
label: "Value",
get: function(item) { return item.value; }
}
}
}, 'grid');
grid.renderArray(data);
grid.set("sort", "displayValue");
});
<script>
dojoConfig = {
async: true,
packages: [
{
name: 'dgrid',
location: 'https://cdn.rawgit.com/SitePen/dgrid/v1.1.0'
}
]
}
</script>
<script src="https://ajax.googleapis.com/ajax/libs/dojo/1.11.2/dojo/dojo.js"></script>
<link rel="stylesheet" href="https://cdn.rawgit.com/SitePen/dgrid/v1.1.0/css/dgrid.css"/>
<style>
.dgrid-row-table {
height: 24px;
}
</style>
<body>
<div id="grid" style="width:200px;height:210px">
</div>
</body>
=更好的回答是我的上一个帖子,在你的评论之后=
老实说,dgrid(还有dstore)不允许使用自定义排序函数。
下面的模式克服了这个限制。它使用OnDemandGrid
填充dstore
。
例如,此网格的field1
列包含从"g1"到"g20"的值。它们不是按数字排序(默认排序)而是按数字排序(自定义排序基于"g"后面的数字)=> "g1" <"g2"& lt;"g3"& lt;…& lt;"十国集团"& lt;"g11"…
这个自定义排序由comparegXX
回调函数执行:
var comparegXX = function(a, b) {
// 'compare' is a generic comparison function for values of the same type
try {
return compare(parseInt(a.value.substr(1), 10), parseInt(b.value.substr(1), 10));
}
catch(ex) { return compareMixedTypes(a, b); }
}
…并且comparegXX
在其列定义(sort
属性)中被分配给field1
:
field1: {
sort: comparegXX
},
对于field2
也是一样(混合类型排序-字符串和数字-由compareMixedTypes
执行)。
如果你想为一个字段分配另一个自定义排序,编写自定义比较回调函数并将其添加到字段的列定义中:fieldX: {sort: myCompareFunction}
。
注意,存储不应该包含任何名为_newPos
的字段。该字段由doSort
函数创建和使用。它包含应用自定义排序后数据行的新相对位置-网格的新排序基于此字段。
var compare = function(a, b) { return a > b ? 1 : a < b ? -1 : 0; }
// comparison functions for custom sorts
// use a.value and b.value in these functions, not directly a and b
var comparegXX = function(a, b) {
try {
return compare(parseInt(a.value.substr(1), 10), parseInt(b.value.substr(1), 10));
}
catch(ex) { return compareMixedTypes(a, b); }
}
var compareMixedTypes = function(a, b) {
var aType = typeof a.value;
return aType == typeof b.value ? compare(a.value, b.value) :
aType == "string" ? -1 : 1;
}
require(["dstore/Memory", "dgrid/OnDemandGrid", "dojo/domReady!"], function (Memory, OnDemandGrid) {
// populate the store (random values in field2)
var tbl = [];
for(var i = 1; i < 21; i++) {
var item = {id: i};
item.field1 = "g" + i;
item.field2 = (i == 1 || Math.random() < 0.2) ? "" : Math.floor(Math.random() * 10);
tbl.push(item);
}
var store = new Memory( {data: tbl });
var grid = new OnDemandGrid({
collection: store,
columns:
{
id: {},
field1: {
sort: comparegXX
},
field2: {
sort: compareMixedTypes
}
},
}, 'grid');
var lastField = null;
var descending = null;
grid.doSort = function(e) {
// custom sort of the grid, replaces the default sort
var field = e.sort[0].property;
if(lastField == field) descending = !descending;
else {
lastField = field;
if(descending == null) descending = e.sort[0].descending;
}
var sortFunc = grid.column(field).sort;
if(sortFunc) {
// calculate the positions of the rows based on the custom compare function,
// they are stored in the _newPos field, and then the grid is sorted on it
var tmp = [], tmp2 = {};
store.forEach(function(item, i) { tmp.push({value: item[field], pos: i}); });
tmp.sort(sortFunc);
tmp.forEach(function(item, i) { tmp2[item.pos] = i; });
store.forEach(function(item, i) { item._newPos = tmp2[i]; });
grid.set("sort", "_newPos", descending);
}
else grid.set("sort", field, descending);
grid.updateSortArrow([{property: field, descending: descending}]);
}
grid.on("dgrid-sort", function(e) {
grid.doSort(e);
e.preventDefault();
});
// initial sort of the grid, use this instead of grid.set("sort"...)
grid.doSort({sort: [{property: "field1", descending: false}]});
grid.startup();
});
<script>
dojoConfig = {
async: true,
packages: [
{
name: 'dgrid',
location: 'https://cdn.rawgit.com/SitePen/dgrid/v1.1.0'
},
{
name: 'dstore',
location: '//cdn.rawgit.com/SitePen/dstore/v1.1.1'
}
]
}
</script>
<script src="https://ajax.googleapis.com/ajax/libs/dojo/1.11.2/dojo/dojo.js"></script>
<link rel="stylesheet" href="https://cdn.rawgit.com/SitePen/dgrid/v1.1.0/css/dgrid.css" />
<body>
<div id="grid" style="width:300px;height:530px;">
</div>
</body>