-
-
Notifications
You must be signed in to change notification settings - Fork 251
/
Copy pathnative.ts
101 lines (87 loc) · 2.54 KB
/
native.ts
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
import { Comparator, TCell } from '../../types';
import Tabular from '../../tabular';
import {
PipelineProcessor,
PipelineProcessorProps,
ProcessorType,
} from '../processor';
import Row from '../../row';
import log from '../../util/log';
import { inPlaceSort, ISortByObjectSorter } from 'fast-sort';
interface NativeSortProps extends PipelineProcessorProps {
columns: {
index: number;
// 1 ascending, -1 descending
direction?: 1 | -1;
compare?: Comparator<TCell>;
}[];
}
class NativeSort extends PipelineProcessor<Tabular, NativeSortProps> {
protected validateProps(): void {
for (const condition of this.props.columns) {
if (condition.direction === undefined) {
condition.direction = 1;
}
if (condition.direction !== 1 && condition.direction !== -1) {
log.error(`Invalid sort direction ${condition.direction}`);
}
}
}
get type(): ProcessorType {
return ProcessorType.Sort;
}
private compare(cellA: TCell, cellB: TCell): number {
if (cellA > cellB) {
return 1;
} else if (cellA < cellB) {
return -1;
}
return 0;
}
private compareWrapper(a: Row, b: Row): number {
let cmp = 0;
for (const column of this.props.columns) {
if (cmp === 0) {
const cellA = a.cells[column.index].data;
const cellB = b.cells[column.index].data;
if (typeof column.compare === 'function') {
cmp |= column.compare(cellA, cellB) * column.direction;
} else {
cmp |= this.compare(cellA, cellB) * column.direction;
}
} else {
break;
}
}
return cmp;
}
protected _process(data: Tabular): Tabular {
const sortedRows = [...data.rows];
/* sortedRows.sort(this.compareWrapper.bind(this)); */
let sortBys: ISortByObjectSorter<Row>[] = [];
for (const column of this.props.columns) {
let sortBy: ISortByObjectSorter = {};
if (column.direction === -1) {
sortBy.desc = (r: Row): TCell => {
return r.cells[column.index].data;
};
}
else {
sortBy.asc = (r: Row): TCell => {
return r.cells[column.index].data;
};
}
if (typeof column.compare === 'function') {
sortBy.comparer = column.compare;
}
sortBys.push(sortBy);
}
inPlaceSort(sortedRows).by(sortBys);
const sorted = new Tabular(sortedRows);
// we have to set the tabular length manually
// because of the server-side storage
sorted.length = data.length;
return sorted;
}
}
export default NativeSort;