@cdx-ui/data-grid 0.3.11 → 0.3.12
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +3 -1
- package/coverage.svg +1 -1
- package/lib/commonjs/DataGrid.js +232 -62
- package/lib/commonjs/DataGrid.js.map +1 -1
- package/lib/commonjs/DataGridFilterPanel.js +420 -0
- package/lib/commonjs/DataGridFilterPanel.js.map +1 -0
- package/lib/commonjs/adapter/columnTypes.js +256 -0
- package/lib/commonjs/adapter/columnTypes.js.map +1 -0
- package/lib/commonjs/adapter/columns.js +132 -4
- package/lib/commonjs/adapter/columns.js.map +1 -1
- package/lib/commonjs/adapter/filterOperators.js +422 -0
- package/lib/commonjs/adapter/filterOperators.js.map +1 -0
- package/lib/commonjs/adapter/pinning.js +101 -0
- package/lib/commonjs/adapter/pinning.js.map +1 -0
- package/lib/commonjs/index.js +26 -0
- package/lib/commonjs/index.js.map +1 -1
- package/lib/commonjs/numberCells.js +280 -0
- package/lib/commonjs/numberCells.js.map +1 -0
- package/lib/commonjs/styles.js +61 -1
- package/lib/commonjs/styles.js.map +1 -1
- package/lib/commonjs/types.js +29 -1
- package/lib/commonjs/types.js.map +1 -1
- package/lib/commonjs/useDataGridTable.js +98 -13
- package/lib/commonjs/useDataGridTable.js.map +1 -1
- package/lib/module/DataGrid.js +237 -67
- package/lib/module/DataGrid.js.map +1 -1
- package/lib/module/DataGridFilterPanel.js +414 -0
- package/lib/module/DataGridFilterPanel.js.map +1 -0
- package/lib/module/adapter/columnTypes.js +240 -0
- package/lib/module/adapter/columnTypes.js.map +1 -0
- package/lib/module/adapter/columns.js +129 -4
- package/lib/module/adapter/columns.js.map +1 -1
- package/lib/module/adapter/filterOperators.js +406 -0
- package/lib/module/adapter/filterOperators.js.map +1 -0
- package/lib/module/adapter/pinning.js +90 -0
- package/lib/module/adapter/pinning.js.map +1 -0
- package/lib/module/index.js +2 -0
- package/lib/module/index.js.map +1 -1
- package/lib/module/numberCells.js +275 -0
- package/lib/module/numberCells.js.map +1 -0
- package/lib/module/styles.js +60 -0
- package/lib/module/styles.js.map +1 -1
- package/lib/module/types.js +28 -0
- package/lib/module/types.js.map +1 -1
- package/lib/module/useDataGridTable.js +99 -14
- package/lib/module/useDataGridTable.js.map +1 -1
- package/lib/typescript/DataGrid.d.ts.map +1 -1
- package/lib/typescript/DataGridFilterPanel.d.ts +17 -0
- package/lib/typescript/DataGridFilterPanel.d.ts.map +1 -0
- package/lib/typescript/adapter/columnTypes.d.ts +32 -0
- package/lib/typescript/adapter/columnTypes.d.ts.map +1 -0
- package/lib/typescript/adapter/columns.d.ts +14 -5
- package/lib/typescript/adapter/columns.d.ts.map +1 -1
- package/lib/typescript/adapter/filterOperators.d.ts +43 -0
- package/lib/typescript/adapter/filterOperators.d.ts.map +1 -0
- package/lib/typescript/adapter/pinning.d.ts +25 -0
- package/lib/typescript/adapter/pinning.d.ts.map +1 -0
- package/lib/typescript/index.d.ts +4 -1
- package/lib/typescript/index.d.ts.map +1 -1
- package/lib/typescript/numberCells.d.ts +46 -0
- package/lib/typescript/numberCells.d.ts.map +1 -0
- package/lib/typescript/styles.d.ts +21 -0
- package/lib/typescript/styles.d.ts.map +1 -1
- package/lib/typescript/types.d.ts +86 -7
- package/lib/typescript/types.d.ts.map +1 -1
- package/lib/typescript/useDataGridTable.d.ts +18 -4
- package/lib/typescript/useDataGridTable.d.ts.map +1 -1
- package/package.json +5 -5
- package/src/DataGrid.tsx +377 -67
- package/src/DataGridFilterPanel.tsx +477 -0
- package/src/adapter/columnTypes.ts +327 -0
- package/src/adapter/columns.test.ts +75 -1
- package/src/adapter/columns.ts +178 -3
- package/src/adapter/filterOperators.test.ts +292 -0
- package/src/adapter/filterOperators.ts +524 -0
- package/src/adapter/pinning.ts +125 -0
- package/src/index.ts +15 -0
- package/src/numberCells.tsx +379 -0
- package/src/styles.ts +75 -0
- package/src/types.ts +114 -7
- package/src/useDataGridTable.test.ts +69 -0
- package/src/useDataGridTable.ts +127 -8
package/README.md
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
# @cdx-ui/data-grid
|
|
2
2
|
|
|
3
|
-
Web DataGrid with
|
|
3
|
+
Web DataGrid with an MUI X–shaped `rows` / `columns` API. TanStack Table is an internal engine — do not import it from consumer code. `gridPolarityNumberColDef` and `gridDeltaNumberColDef` are spreadable `number` column presets for signed numbers and changes.
|
|
4
4
|
|
|
5
5
|
```tsx
|
|
6
6
|
import { DataGrid, type GridColDef } from '@cdx-ui/data-grid';
|
|
@@ -16,3 +16,5 @@ Add the grid's stylesheet to your Tailwind CSS entry, after the components style
|
|
|
16
16
|
```
|
|
17
17
|
|
|
18
18
|
The grid uses a **300px** viewport by default (MUI Data Grid Community). Headers stay visible while rows scroll; pagination stays at the bottom. Override with `className` or `style`, or set `autoHeight` to size the grid to its rows.
|
|
19
|
+
|
|
20
|
+
Pin columns with `pinnedColumns={{ start, end }}`. Deprecated `left` / `right` keys alias `start` / `end`. See the [Data Grid docs](https://design.candescent.com/docs/components/data-grid).
|
package/coverage.svg
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
<svg xmlns="http://www.w3.org/2000/svg" width="108" height="20" role="img" aria-label="coverage:
|
|
1
|
+
<svg xmlns="http://www.w3.org/2000/svg" width="108" height="20" role="img" aria-label="coverage: 87.1%"><title>coverage: 87.1%</title><filter id="blur"><feGaussianBlur stdDeviation="16"/></filter><linearGradient id="s" x2="0" y2="100%"><stop offset="0" stop-color="#bbb" stop-opacity=".1"/><stop offset="1" stop-opacity=".1"/></linearGradient><clipPath id="r"><rect width="108" height="20" rx="3"/></clipPath><g clip-path="url(#r)"><rect width="61" height="20" fill="#555"/><rect x="61" width="47" height="20" fill="#4b0"/><rect width="108" height="20" fill="url(#s)"/></g><g fill="#fff" text-anchor="middle" font-family="Verdana,Geneva,DejaVu Sans,sans-serif" text-rendering="geometricPrecision" font-size="110"><g transform="scale(.1)"><g aria-hidden="true" fill="#010101"><text x="315" y="150" fill-opacity=".8" filter="url(#blur)" textLength="510">coverage</text><text x="315" y="150" fill-opacity=".3" textLength="510">coverage</text></g><text x="315" y="140" textLength="510">coverage</text></g><g transform="scale(.1)"><g aria-hidden="true" fill="#010101"><text x="835" y="150" fill-opacity=".8" filter="url(#blur)" textLength="370">87.1%</text><text x="835" y="150" fill-opacity=".3" textLength="370">87.1%</text></g><text x="835" y="140" textLength="370">87.1%</text></g></g></svg>
|
package/lib/commonjs/DataGrid.js
CHANGED
|
@@ -11,16 +11,20 @@ var _icons = require("@cdx-ui/icons");
|
|
|
11
11
|
var _primitives = require("@cdx-ui/primitives");
|
|
12
12
|
var _utils = require("@cdx-ui/utils");
|
|
13
13
|
var _columns = require("./adapter/columns");
|
|
14
|
+
var _pinning = require("./adapter/pinning");
|
|
15
|
+
var _columnTypes = require("./adapter/columnTypes");
|
|
16
|
+
var _DataGridFilterPanel = require("./DataGridFilterPanel");
|
|
14
17
|
var _styles = require("./styles");
|
|
15
18
|
var _types = require("./types");
|
|
16
19
|
var _useDataGridTable = require("./useDataGridTable");
|
|
17
20
|
var _jsxRuntime = require("react/jsx-runtime");
|
|
18
21
|
const MAX_SKELETON_ROW_COUNT = 10;
|
|
19
22
|
const DEFAULT_WEB_COLUMN_WIDTH = 100;
|
|
20
|
-
const SELECT_COLUMN_WIDTH = 56;
|
|
21
23
|
const WEB_TABLE_CONTAINER_STYLE = {
|
|
22
24
|
overflow: 'visible'
|
|
23
25
|
};
|
|
26
|
+
// Same token as the pinned cells' `border-stroke-secondary` divider.
|
|
27
|
+
const PINNED_EDGE_COLOR = 'var(--color-stroke-secondary)';
|
|
24
28
|
function cellStyle(col, webWidth) {
|
|
25
29
|
if (!col) {
|
|
26
30
|
return undefined;
|
|
@@ -43,36 +47,96 @@ function cellStyle(col, webWidth) {
|
|
|
43
47
|
}
|
|
44
48
|
return Object.keys(style).length > 0 ? style : undefined;
|
|
45
49
|
}
|
|
46
|
-
function
|
|
47
|
-
|
|
50
|
+
function effectiveFlex(column, pinned) {
|
|
51
|
+
if (pinned.has(column.field)) {
|
|
52
|
+
return 0;
|
|
53
|
+
}
|
|
54
|
+
return Math.max(column.flex ?? 0, 0);
|
|
55
|
+
}
|
|
56
|
+
function webColumnWidths(columns, checkboxSelection, pinned = new Set()) {
|
|
57
|
+
const totalFlex = columns.reduce((total, column) => total + effectiveFlex(column, pinned), 0);
|
|
48
58
|
const widths = new Map();
|
|
49
59
|
if (totalFlex === 0) {
|
|
50
60
|
for (const column of columns) {
|
|
51
|
-
if (column.
|
|
61
|
+
if (pinned.has(column.field)) {
|
|
62
|
+
widths.set(column.field, Math.max(column.width ?? _pinning.DEFAULT_PINNED_COLUMN_WIDTH, column.minWidth ?? 0));
|
|
63
|
+
} else if (column.width !== undefined) {
|
|
52
64
|
widths.set(column.field, column.width);
|
|
53
65
|
}
|
|
54
66
|
}
|
|
55
67
|
return widths;
|
|
56
68
|
}
|
|
57
|
-
const fixedWidth = (checkboxSelection ? SELECT_COLUMN_WIDTH : 0) + columns.reduce((total, column) => {
|
|
58
|
-
if ((column
|
|
69
|
+
const fixedWidth = (checkboxSelection ? _pinning.SELECT_COLUMN_WIDTH : 0) + columns.reduce((total, column) => {
|
|
70
|
+
if (effectiveFlex(column, pinned) > 0) {
|
|
59
71
|
return total;
|
|
60
72
|
}
|
|
61
|
-
|
|
73
|
+
const fallback = pinned.has(column.field) ? _pinning.DEFAULT_PINNED_COLUMN_WIDTH : DEFAULT_WEB_COLUMN_WIDTH;
|
|
74
|
+
return total + Math.max(column.width ?? fallback, column.minWidth ?? 0);
|
|
62
75
|
}, 0);
|
|
63
76
|
for (const column of columns) {
|
|
64
|
-
|
|
65
|
-
|
|
77
|
+
const flex = effectiveFlex(column, pinned);
|
|
78
|
+
if (flex > 0) {
|
|
79
|
+
const share = flex / totalFlex;
|
|
66
80
|
const percentage = share * 100;
|
|
67
81
|
const fixedShare = fixedWidth * share;
|
|
68
82
|
const width = `calc(${percentage.toString()}% - ${fixedShare.toString()}px)`;
|
|
69
83
|
widths.set(column.field, column.minWidth === undefined ? width : `max(${column.minWidth.toString()}px, ${width})`);
|
|
70
84
|
} else {
|
|
71
|
-
|
|
85
|
+
const fallback = pinned.has(column.field) ? _pinning.DEFAULT_PINNED_COLUMN_WIDTH : DEFAULT_WEB_COLUMN_WIDTH;
|
|
86
|
+
widths.set(column.field, Math.max(column.width ?? fallback, column.minWidth ?? 0));
|
|
72
87
|
}
|
|
73
88
|
}
|
|
74
89
|
return widths;
|
|
75
90
|
}
|
|
91
|
+
function pinMetaFor(columnId, pinning) {
|
|
92
|
+
const startIndex = pinning.start.indexOf(columnId);
|
|
93
|
+
if (startIndex >= 0) {
|
|
94
|
+
return {
|
|
95
|
+
edge: 'start',
|
|
96
|
+
isEdgeDivider: startIndex === pinning.start.length - 1
|
|
97
|
+
};
|
|
98
|
+
}
|
|
99
|
+
const endIndex = pinning.end.indexOf(columnId);
|
|
100
|
+
if (endIndex >= 0) {
|
|
101
|
+
return {
|
|
102
|
+
edge: 'end',
|
|
103
|
+
isEdgeDivider: endIndex === 0
|
|
104
|
+
};
|
|
105
|
+
}
|
|
106
|
+
return {
|
|
107
|
+
edge: false,
|
|
108
|
+
isEdgeDivider: false
|
|
109
|
+
};
|
|
110
|
+
}
|
|
111
|
+
function mergePinnedStyle(base, pin, offsets, columnId, isHeader) {
|
|
112
|
+
if (!pin.edge || offsets == null) {
|
|
113
|
+
return base;
|
|
114
|
+
}
|
|
115
|
+
const offset = pin.edge === 'start' ? offsets.start.get(columnId) ?? 0 : offsets.end.get(columnId) ?? 0;
|
|
116
|
+
return {
|
|
117
|
+
...base,
|
|
118
|
+
...(0, _pinning.pinnedCellStyle)(pin.edge, offset, isHeader)
|
|
119
|
+
};
|
|
120
|
+
}
|
|
121
|
+
function pinnedClassName(pin, isHeader) {
|
|
122
|
+
if (!pin.edge) {
|
|
123
|
+
return undefined;
|
|
124
|
+
}
|
|
125
|
+
return (0, _utils.cn)((0, _styles.dataGridPinnedSurfaceVariants)({
|
|
126
|
+
header: isHeader
|
|
127
|
+
}), (0, _styles.dataGridPinnedEdgeVariants)({
|
|
128
|
+
edge: pin.isEdgeDivider ? pin.edge : 'none'
|
|
129
|
+
}));
|
|
130
|
+
}
|
|
131
|
+
function BooleanCell({
|
|
132
|
+
value
|
|
133
|
+
}) {
|
|
134
|
+
return /*#__PURE__*/(0, _jsxRuntime.jsx)(_components.Icon, {
|
|
135
|
+
as: value ? _icons.Check : _icons.Close,
|
|
136
|
+
accessibilityLabel: value ? 'Yes' : 'No',
|
|
137
|
+
className: "size-5"
|
|
138
|
+
});
|
|
139
|
+
}
|
|
76
140
|
function defaultCellContent(value) {
|
|
77
141
|
if (value == null) {
|
|
78
142
|
return '';
|
|
@@ -94,28 +158,44 @@ function DefaultLoadingRows({
|
|
|
94
158
|
columns,
|
|
95
159
|
checkboxSelection,
|
|
96
160
|
rowCount,
|
|
97
|
-
columnWidths
|
|
161
|
+
columnWidths,
|
|
162
|
+
orderedColumnIds,
|
|
163
|
+
pinning,
|
|
164
|
+
offsets
|
|
98
165
|
}) {
|
|
166
|
+
const colByField = new Map(columns.map(column => [column.field, column]));
|
|
167
|
+
const ids = orderedColumnIds ?? (checkboxSelection ? [_types.SELECT_COLUMN_ID, ...columns.map(column => column.field)] : columns.map(column => column.field));
|
|
99
168
|
return /*#__PURE__*/(0, _jsxRuntime.jsx)(_jsxRuntime.Fragment, {
|
|
100
169
|
children: Array.from({
|
|
101
170
|
length: rowCount
|
|
102
|
-
}, (_, rowIndex) => /*#__PURE__*/(0, _jsxRuntime.
|
|
171
|
+
}, (_, rowIndex) => /*#__PURE__*/(0, _jsxRuntime.jsx)(_components.Table.Row, {
|
|
103
172
|
className: "pointer-events-none web:hover:bg-surface-primary",
|
|
104
173
|
testID: rowIndex === 0 ? 'data-grid-default-loading-rows' : undefined,
|
|
105
|
-
children:
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
174
|
+
children: ids.map(columnId => {
|
|
175
|
+
const pin = pinMetaFor(columnId, pinning);
|
|
176
|
+
if (columnId === _types.SELECT_COLUMN_ID) {
|
|
177
|
+
return /*#__PURE__*/(0, _jsxRuntime.jsx)(_components.Table.Cell, {
|
|
178
|
+
align: "center",
|
|
179
|
+
className: (0, _utils.cn)((0, _styles.dataGridSelectCellVariants)(), pinnedClassName(pin, false)),
|
|
180
|
+
style: mergePinnedStyle(undefined, pin, offsets, columnId, false),
|
|
181
|
+
children: /*#__PURE__*/(0, _jsxRuntime.jsx)(_components.Skeleton, {
|
|
182
|
+
className: "size-5"
|
|
183
|
+
})
|
|
184
|
+
}, columnId);
|
|
185
|
+
}
|
|
186
|
+
const column = colByField.get(columnId);
|
|
187
|
+
if (!column) {
|
|
188
|
+
return null;
|
|
189
|
+
}
|
|
190
|
+
return /*#__PURE__*/(0, _jsxRuntime.jsx)(_components.Table.Cell, {
|
|
191
|
+
align: (0, _columns.resolveColumnAlign)(column),
|
|
192
|
+
className: (0, _utils.cn)((0, _styles.dataGridCellVariants)(), pinnedClassName(pin, false)),
|
|
193
|
+
style: mergePinnedStyle(cellStyle(column, columnWidths.get(column.field)), pin, offsets, column.field, false),
|
|
194
|
+
children: /*#__PURE__*/(0, _jsxRuntime.jsx)(_components.Skeleton, {
|
|
195
|
+
className: "h-4 w-3/5"
|
|
196
|
+
})
|
|
197
|
+
}, column.field);
|
|
198
|
+
})
|
|
119
199
|
}, rowIndex))
|
|
120
200
|
});
|
|
121
201
|
}
|
|
@@ -148,6 +228,7 @@ function DataGridInner(props) {
|
|
|
148
228
|
rowCount,
|
|
149
229
|
showToolbar = false,
|
|
150
230
|
headerFilters = false,
|
|
231
|
+
pinnedColumns,
|
|
151
232
|
pageSizeOptions = _types.DEFAULT_PAGE_SIZE_OPTIONS,
|
|
152
233
|
noRowsOverlay,
|
|
153
234
|
loadingOverlay,
|
|
@@ -173,6 +254,11 @@ function DataGridInner(props) {
|
|
|
173
254
|
defaultProp: props.defaultFilterModel ?? [],
|
|
174
255
|
onChange: props.onFilterModelChange
|
|
175
256
|
});
|
|
257
|
+
const [filterLogicOperator, setFilterLogicOperator] = (0, _utils.useControllableState)({
|
|
258
|
+
prop: props.filterLogicOperator,
|
|
259
|
+
defaultProp: props.defaultFilterLogicOperator ?? 'and',
|
|
260
|
+
onChange: props.onFilterLogicOperatorChange
|
|
261
|
+
});
|
|
176
262
|
const [quickFilter, setQuickFilter] = (0, _utils.useControllableState)({
|
|
177
263
|
prop: props.quickFilter,
|
|
178
264
|
defaultProp: props.defaultQuickFilter ?? '',
|
|
@@ -186,12 +272,18 @@ function DataGridInner(props) {
|
|
|
186
272
|
const resolvedSortModel = sortModel ?? [];
|
|
187
273
|
const resolvedPagination = paginationModel ?? _types.DEFAULT_PAGINATION_MODEL;
|
|
188
274
|
const resolvedFilterModel = filterModel ?? [];
|
|
275
|
+
const resolvedFilterLogicOperator = filterLogicOperator ?? 'and';
|
|
189
276
|
const resolvedQuickFilter = quickFilter ?? '';
|
|
190
277
|
const resolvedSelection = rowSelectionModel ?? _types.EMPTY_SELECTION;
|
|
278
|
+
const knownFields = (0, _react.useMemo)(() => new Set(columns.map(column => column.field)), [columns]);
|
|
279
|
+
const columnPinning = (0, _react.useMemo)(() => (0, _columns.normalizePinnedColumns)(pinnedColumns, knownFields, checkboxSelection), [pinnedColumns, knownFields, checkboxSelection]);
|
|
280
|
+
const pinningActive = (0, _pinning.isColumnPinningActive)(columnPinning);
|
|
281
|
+
const pinnedFields = (0, _react.useMemo)(() => (0, _pinning.pinnedFieldSet)(columnPinning), [columnPinning]);
|
|
191
282
|
const {
|
|
192
283
|
table,
|
|
193
284
|
setQuickFilter: setQuickFilterWithPageReset,
|
|
194
|
-
setColumnFilter
|
|
285
|
+
setColumnFilter,
|
|
286
|
+
setFilterModel: setFilterModelWithPageReset
|
|
195
287
|
} = (0, _useDataGridTable.useDataGridTable)({
|
|
196
288
|
rows,
|
|
197
289
|
columns,
|
|
@@ -208,10 +300,12 @@ function DataGridInner(props) {
|
|
|
208
300
|
onPaginationModelChange: model => setPaginationModel(model),
|
|
209
301
|
filterModel: resolvedFilterModel,
|
|
210
302
|
onFilterModelChange: model => setFilterModel(model),
|
|
303
|
+
filterLogicOperator: resolvedFilterLogicOperator,
|
|
211
304
|
quickFilter: resolvedQuickFilter,
|
|
212
305
|
onQuickFilterChange: value => setQuickFilter(value),
|
|
213
306
|
rowSelectionModel: resolvedSelection,
|
|
214
|
-
onRowSelectionModelChange: model => setRowSelectionModel(model)
|
|
307
|
+
onRowSelectionModelChange: model => setRowSelectionModel(model),
|
|
308
|
+
columnPinning
|
|
215
309
|
});
|
|
216
310
|
const colByField = (0, _react.useMemo)(() => {
|
|
217
311
|
const map = new Map();
|
|
@@ -220,8 +314,32 @@ function DataGridInner(props) {
|
|
|
220
314
|
}
|
|
221
315
|
return map;
|
|
222
316
|
}, [columns]);
|
|
223
|
-
|
|
224
|
-
const
|
|
317
|
+
(0, _pinning.warnPinnedFlexColumns)(columns, pinnedFields);
|
|
318
|
+
const columnWidths = (0, _react.useMemo)(() => webColumnWidths(columns, checkboxSelection, pinnedFields), [checkboxSelection, columns, pinnedFields]);
|
|
319
|
+
const hasFlexColumns = (0, _react.useMemo)(() => columns.some(column => effectiveFlex(column, pinnedFields) > 0), [columns, pinnedFields]);
|
|
320
|
+
const pinnedOffsets = (0, _react.useMemo)(() => pinningActive ? (0, _pinning.buildPinnedOffsets)(columnPinning, colByField) : null, [pinningActive, columnPinning, colByField]);
|
|
321
|
+
const orderedLeafColumnIds = (0, _react.useMemo)(() => {
|
|
322
|
+
if (!pinningActive) {
|
|
323
|
+
return undefined;
|
|
324
|
+
}
|
|
325
|
+
return [...table.getStartVisibleLeafColumns().map(column => column.id), ...table.getCenterVisibleLeafColumns().map(column => column.id), ...table.getEndVisibleLeafColumns().map(column => column.id)];
|
|
326
|
+
}, [pinningActive, table]);
|
|
327
|
+
const isEmpty = !loading && rows.length === 0;
|
|
328
|
+
const mainScrollStyle = (0, _react.useMemo)(() => {
|
|
329
|
+
if (!pinningActive || pinnedOffsets == null) {
|
|
330
|
+
return undefined;
|
|
331
|
+
}
|
|
332
|
+
const guides = _reactNative.Platform.OS === 'web' && !isEmpty ? (0, _pinning.pinnedEdgeGuidesImage)(pinnedOffsets, PINNED_EDGE_COLOR, _reactNative.I18nManager.isRTL) : undefined;
|
|
333
|
+
// Logical scroll-padding keeps focused cells out from under pinned edges (web).
|
|
334
|
+
return {
|
|
335
|
+
scrollPaddingInlineStart: pinnedOffsets.startTotal,
|
|
336
|
+
scrollPaddingInlineEnd: pinnedOffsets.endTotal,
|
|
337
|
+
...(guides ? {
|
|
338
|
+
backgroundImage: guides,
|
|
339
|
+
backgroundRepeat: 'no-repeat'
|
|
340
|
+
} : {})
|
|
341
|
+
};
|
|
342
|
+
}, [pinningActive, pinnedOffsets, isEmpty]);
|
|
225
343
|
const visibleRows = table.getRowModel().rows;
|
|
226
344
|
const pageCount = Math.max(table.getPageCount(), 1);
|
|
227
345
|
const selectedCount = table.getFilteredSelectedRowModel().rows.length;
|
|
@@ -237,14 +355,20 @@ function DataGridInner(props) {
|
|
|
237
355
|
indeterminate: true
|
|
238
356
|
};
|
|
239
357
|
const accessibleName = ariaLabel ?? label;
|
|
240
|
-
const isEmpty = !loading && rows.length === 0;
|
|
241
358
|
const totalCount = paginationMode === 'server' ? rowCount ?? rows.length : filterableCount;
|
|
242
|
-
const filterValueFor = field =>
|
|
359
|
+
const filterValueFor = field => {
|
|
360
|
+
const value = resolvedFilterModel.find(item => item.field === field)?.value;
|
|
361
|
+
return typeof value === 'string' ? value : '';
|
|
362
|
+
};
|
|
243
363
|
const showToolbarBar = showToolbar || toolbarActions != null;
|
|
364
|
+
const filterPanelColumns = (0, _react.useMemo)(() => columns.filter(column => column.filterable !== false), [columns]);
|
|
365
|
+
const [filterPanelOpen, setFilterPanelOpen] = (0, _react.useState)(false);
|
|
366
|
+
const filterPanelButtonRef = (0, _react.useRef)(null);
|
|
367
|
+
const showFilterPanelButton = showToolbar && filterPanelColumns.length > 0;
|
|
244
368
|
return /*#__PURE__*/(0, _jsxRuntime.jsxs)(_reactNative.View, {
|
|
245
369
|
className: (0, _utils.cn)((0, _styles.dataGridRootVariants)({
|
|
246
370
|
autoHeight
|
|
247
|
-
}), className),
|
|
371
|
+
}), className, filterPanelOpen && 'overflow-visible'),
|
|
248
372
|
style: style,
|
|
249
373
|
...(0, _primitives.mergeDataAttributes)({}, (0, _primitives.dataAttributes)({
|
|
250
374
|
slot: 'data-grid'
|
|
@@ -262,15 +386,43 @@ function DataGridInner(props) {
|
|
|
262
386
|
placeholder: "Search",
|
|
263
387
|
accessibilityLabel: "Search"
|
|
264
388
|
})]
|
|
389
|
+
}) : null, showFilterPanelButton ? /*#__PURE__*/(0, _jsxRuntime.jsx)(_components.IconButton, {
|
|
390
|
+
ref: filterPanelButtonRef,
|
|
391
|
+
as: _icons.FilterList,
|
|
392
|
+
variant: "ghost",
|
|
393
|
+
color: "neutral",
|
|
394
|
+
size: "small",
|
|
395
|
+
accessibilityLabel: "Filters",
|
|
396
|
+
accessibilityState: {
|
|
397
|
+
expanded: filterPanelOpen
|
|
398
|
+
},
|
|
399
|
+
onPress: () => setFilterPanelOpen(open => !open)
|
|
265
400
|
}) : null, toolbarActions ? /*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNative.View, {
|
|
266
401
|
className: (0, _styles.dataGridToolbarActionsVariants)(),
|
|
267
402
|
children: toolbarActions
|
|
268
403
|
}) : null]
|
|
404
|
+
}) : null, showFilterPanelButton && filterPanelOpen ? /*#__PURE__*/(0, _jsxRuntime.jsx)(_DataGridFilterPanel.DataGridFilterPanel, {
|
|
405
|
+
columns: filterPanelColumns,
|
|
406
|
+
filterModel: resolvedFilterModel,
|
|
407
|
+
onFilterModelChange: setFilterModelWithPageReset,
|
|
408
|
+
logicOperator: resolvedFilterLogicOperator,
|
|
409
|
+
onLogicOperatorChange: operator => {
|
|
410
|
+
setFilterLogicOperator(operator);
|
|
411
|
+
if (resolvedPagination.page !== 0) {
|
|
412
|
+
setPaginationModel({
|
|
413
|
+
...resolvedPagination,
|
|
414
|
+
page: 0
|
|
415
|
+
});
|
|
416
|
+
}
|
|
417
|
+
},
|
|
418
|
+
onClose: () => setFilterPanelOpen(false),
|
|
419
|
+
triggerRef: filterPanelButtonRef
|
|
269
420
|
}) : null, /*#__PURE__*/(0, _jsxRuntime.jsxs)(_reactNative.View, {
|
|
270
421
|
className: (0, _styles.dataGridMainVariants)({
|
|
271
422
|
autoHeight,
|
|
272
423
|
overlay: isEmpty || loading && loadingOverlay != null
|
|
273
424
|
}),
|
|
425
|
+
style: mainScrollStyle,
|
|
274
426
|
children: [/*#__PURE__*/(0, _jsxRuntime.jsxs)(_components.Table, {
|
|
275
427
|
className: (0, _utils.cn)((0, _styles.dataGridTableVariants)(), _reactNative.Platform.OS === 'web' && hasFlexColumns ? 'table-fixed' : undefined),
|
|
276
428
|
containerStyle: _reactNative.Platform.OS === 'web' ? WEB_TABLE_CONTAINER_STYLE : undefined,
|
|
@@ -282,25 +434,30 @@ function DataGridInner(props) {
|
|
|
282
434
|
} : {}),
|
|
283
435
|
children: [label ? /*#__PURE__*/(0, _jsxRuntime.jsx)(_components.Table.Caption, {
|
|
284
436
|
children: label
|
|
285
|
-
}) : null, _reactNative.Platform.OS === 'web' && hasFlexColumns ? /*#__PURE__*/(0, _jsxRuntime.
|
|
286
|
-
children:
|
|
437
|
+
}) : null, _reactNative.Platform.OS === 'web' && hasFlexColumns ? /*#__PURE__*/(0, _jsxRuntime.jsx)("colgroup", {
|
|
438
|
+
children: (orderedLeafColumnIds ?? (checkboxSelection ? [_types.SELECT_COLUMN_ID, ...columns.map(column => column.field)] : columns.map(column => column.field))).map(columnId => columnId === _types.SELECT_COLUMN_ID ? /*#__PURE__*/(0, _jsxRuntime.jsx)("col", {
|
|
287
439
|
style: {
|
|
288
|
-
width: SELECT_COLUMN_WIDTH
|
|
440
|
+
width: _pinning.SELECT_COLUMN_WIDTH
|
|
289
441
|
}
|
|
290
|
-
}) :
|
|
442
|
+
}, columnId) : /*#__PURE__*/(0, _jsxRuntime.jsx)("col", {
|
|
291
443
|
style: {
|
|
292
|
-
width: columnWidths.get(
|
|
293
|
-
minWidth:
|
|
444
|
+
width: columnWidths.get(columnId),
|
|
445
|
+
minWidth: colByField.get(columnId)?.minWidth
|
|
294
446
|
}
|
|
295
|
-
},
|
|
447
|
+
}, columnId))
|
|
296
448
|
}) : null, /*#__PURE__*/(0, _jsxRuntime.jsxs)(_components.Table.Header, {
|
|
297
449
|
className: (0, _styles.dataGridHeaderVariants)(),
|
|
298
|
-
children: [
|
|
450
|
+
children: [(pinningActive ? [{
|
|
451
|
+
id: 'pinned',
|
|
452
|
+
headers: [...table.getStartLeafHeaders(), ...table.getCenterLeafHeaders(), ...table.getEndLeafHeaders()]
|
|
453
|
+
}] : table.getHeaderGroups()).map(headerGroup => /*#__PURE__*/(0, _jsxRuntime.jsx)(_components.Table.Row, {
|
|
299
454
|
children: headerGroup.headers.map(header => {
|
|
455
|
+
const pin = pinMetaFor(header.column.id, columnPinning);
|
|
300
456
|
if (header.id === _types.SELECT_COLUMN_ID) {
|
|
301
457
|
return /*#__PURE__*/(0, _jsxRuntime.jsx)(_components.Table.Head, {
|
|
302
458
|
align: "center",
|
|
303
|
-
className: (0, _styles.dataGridSelectHeadVariants)(),
|
|
459
|
+
className: (0, _utils.cn)((0, _styles.dataGridSelectHeadVariants)(), pinnedClassName(pin, true)),
|
|
460
|
+
style: mergePinnedStyle(undefined, pin, pinnedOffsets, header.id, true),
|
|
304
461
|
children: /*#__PURE__*/(0, _jsxRuntime.jsx)(_components.Checkbox, {
|
|
305
462
|
value: "select-all",
|
|
306
463
|
isChecked: headerSelectState.checked,
|
|
@@ -314,7 +471,7 @@ function DataGridInner(props) {
|
|
|
314
471
|
const col = colByField.get(header.column.id);
|
|
315
472
|
const sorted = header.column.getIsSorted();
|
|
316
473
|
const canSort = !disableColumnSorting && header.column.getCanSort();
|
|
317
|
-
const headerAlign = (0, _columns.
|
|
474
|
+
const headerAlign = (0, _columns.resolveColumnHeaderAlign)(col);
|
|
318
475
|
const headerName = col?.headerName ?? header.column.id;
|
|
319
476
|
const SortIcon = sorted === 'asc' ? _icons.KeyboardArrowUp : _icons.KeyboardArrowDown;
|
|
320
477
|
const sortButton = canSort ? /*#__PURE__*/(0, _jsxRuntime.jsx)(_components.IconButton, {
|
|
@@ -334,8 +491,8 @@ function DataGridInner(props) {
|
|
|
334
491
|
}) : null;
|
|
335
492
|
return /*#__PURE__*/(0, _jsxRuntime.jsx)(_components.Table.Head, {
|
|
336
493
|
align: headerAlign,
|
|
337
|
-
className: (0, _styles.dataGridHeadVariants)(),
|
|
338
|
-
style: cellStyle(col, columnWidths.get(header.column.id)),
|
|
494
|
+
className: (0, _utils.cn)((0, _styles.dataGridHeadVariants)(), pinnedClassName(pin, true)),
|
|
495
|
+
style: mergePinnedStyle(cellStyle(col, columnWidths.get(header.column.id)), pin, pinnedOffsets, header.column.id, true),
|
|
339
496
|
...(_reactNative.Platform.OS === 'web' ? {
|
|
340
497
|
title: col?.renderHeader ? undefined : headerName,
|
|
341
498
|
...(canSort ? {
|
|
@@ -356,26 +513,27 @@ function DataGridInner(props) {
|
|
|
356
513
|
}, header.id);
|
|
357
514
|
})
|
|
358
515
|
}, headerGroup.id)), headerFilters ? /*#__PURE__*/(0, _jsxRuntime.jsx)(_components.Table.Row, {
|
|
359
|
-
children: table.getAllLeafColumns().map(column => {
|
|
516
|
+
children: (pinningActive ? [...table.getStartVisibleLeafColumns(), ...table.getCenterVisibleLeafColumns(), ...table.getEndVisibleLeafColumns()] : table.getAllLeafColumns()).map(column => {
|
|
517
|
+
const pin = pinMetaFor(column.id, columnPinning);
|
|
360
518
|
if (column.id === _types.SELECT_COLUMN_ID) {
|
|
361
519
|
return /*#__PURE__*/(0, _jsxRuntime.jsx)(_components.Table.Cell, {
|
|
362
520
|
align: "center",
|
|
363
|
-
className: (0, _styles.dataGridSelectHeadVariants)()
|
|
521
|
+
className: (0, _utils.cn)((0, _styles.dataGridSelectHeadVariants)(), pinnedClassName(pin, true)),
|
|
522
|
+
style: mergePinnedStyle(undefined, pin, pinnedOffsets, column.id, true)
|
|
364
523
|
}, column.id);
|
|
365
524
|
}
|
|
366
525
|
const col = colByField.get(column.id);
|
|
367
|
-
const headerAlign = col?.headerAlign ?? col?.align;
|
|
368
526
|
if (col?.filterable === false) {
|
|
369
527
|
return /*#__PURE__*/(0, _jsxRuntime.jsx)(_components.Table.Head, {
|
|
370
|
-
align: (0, _columns.
|
|
371
|
-
className: (0, _styles.dataGridHeadVariants)(),
|
|
372
|
-
style: cellStyle(col, columnWidths.get(column.id))
|
|
528
|
+
align: (0, _columns.resolveColumnHeaderAlign)(col),
|
|
529
|
+
className: (0, _utils.cn)((0, _styles.dataGridHeadVariants)(), pinnedClassName(pin, true)),
|
|
530
|
+
style: mergePinnedStyle(cellStyle(col, columnWidths.get(column.id)), pin, pinnedOffsets, column.id, true)
|
|
373
531
|
}, column.id);
|
|
374
532
|
}
|
|
375
533
|
return /*#__PURE__*/(0, _jsxRuntime.jsx)(_components.Table.Head, {
|
|
376
|
-
align: (0, _columns.
|
|
377
|
-
className: (0, _styles.dataGridHeadVariants)(),
|
|
378
|
-
style: cellStyle(col, columnWidths.get(column.id)),
|
|
534
|
+
align: (0, _columns.resolveColumnHeaderAlign)(col),
|
|
535
|
+
className: (0, _utils.cn)((0, _styles.dataGridHeadVariants)(), pinnedClassName(pin, true)),
|
|
536
|
+
style: mergePinnedStyle(cellStyle(col, columnWidths.get(column.id)), pin, pinnedOffsets, column.id, true),
|
|
379
537
|
children: /*#__PURE__*/(0, _jsxRuntime.jsx)(_components.Input, {
|
|
380
538
|
size: "small",
|
|
381
539
|
className: (0, _styles.dataGridFilterInputVariants)(),
|
|
@@ -395,15 +553,21 @@ function DataGridInner(props) {
|
|
|
395
553
|
columns: columns,
|
|
396
554
|
checkboxSelection: checkboxSelection,
|
|
397
555
|
rowCount: Math.min(resolvedPagination.pageSize, MAX_SKELETON_ROW_COUNT),
|
|
398
|
-
columnWidths: columnWidths
|
|
556
|
+
columnWidths: columnWidths,
|
|
557
|
+
orderedColumnIds: orderedLeafColumnIds,
|
|
558
|
+
pinning: columnPinning,
|
|
559
|
+
offsets: pinnedOffsets
|
|
399
560
|
}) : isEmpty ? null : visibleRows.map(row => {
|
|
400
561
|
const rowId = (0, _useDataGridTable.resolveRowId)(row.original, getRowId);
|
|
562
|
+
const cells = pinningActive ? [...row.getStartVisibleCells(), ...row.getCenterVisibleCells(), ...row.getEndVisibleCells()] : row.getAllCells();
|
|
401
563
|
return /*#__PURE__*/(0, _jsxRuntime.jsx)(_components.Table.Row, {
|
|
402
|
-
children:
|
|
564
|
+
children: cells.map(cell => {
|
|
565
|
+
const pin = pinMetaFor(cell.column.id, columnPinning);
|
|
403
566
|
if (cell.column.id === _types.SELECT_COLUMN_ID) {
|
|
404
567
|
return /*#__PURE__*/(0, _jsxRuntime.jsx)(_components.Table.Cell, {
|
|
405
568
|
align: "center",
|
|
406
|
-
className: (0, _styles.dataGridSelectCellVariants)(),
|
|
569
|
+
className: (0, _utils.cn)((0, _styles.dataGridSelectCellVariants)(), pinnedClassName(pin, false)),
|
|
570
|
+
style: mergePinnedStyle(undefined, pin, pinnedOffsets, cell.column.id, false),
|
|
407
571
|
children: /*#__PURE__*/(0, _jsxRuntime.jsx)(_components.Checkbox, {
|
|
408
572
|
value: String(rowId),
|
|
409
573
|
isChecked: row.getIsSelected(),
|
|
@@ -421,17 +585,23 @@ function DataGridInner(props) {
|
|
|
421
585
|
value,
|
|
422
586
|
row: row.original,
|
|
423
587
|
field: col.field,
|
|
424
|
-
id: rowId
|
|
588
|
+
id: rowId,
|
|
589
|
+
col
|
|
425
590
|
});
|
|
426
591
|
} else if (col?.valueFormatter) {
|
|
427
592
|
content = col.valueFormatter(value, row.original, col);
|
|
593
|
+
} else if (col?.type === 'boolean' && typeof value === 'boolean') {
|
|
594
|
+
content = /*#__PURE__*/(0, _jsxRuntime.jsx)(BooleanCell, {
|
|
595
|
+
value: value
|
|
596
|
+
});
|
|
428
597
|
} else {
|
|
429
|
-
|
|
598
|
+
const typedText = (0, _columnTypes.getTypedCellText)(col, value, row.original);
|
|
599
|
+
content = typedText !== undefined ? typedText : defaultCellContent(value);
|
|
430
600
|
}
|
|
431
601
|
return /*#__PURE__*/(0, _jsxRuntime.jsx)(_components.Table.Cell, {
|
|
432
|
-
align: (0, _columns.
|
|
433
|
-
className: (0, _styles.dataGridCellVariants)(),
|
|
434
|
-
style: cellStyle(col, columnWidths.get(cell.column.id)),
|
|
602
|
+
align: (0, _columns.resolveColumnAlign)(col),
|
|
603
|
+
className: (0, _utils.cn)((0, _styles.dataGridCellVariants)(), pinnedClassName(pin, false)),
|
|
604
|
+
style: mergePinnedStyle(cellStyle(col, columnWidths.get(cell.column.id)), pin, pinnedOffsets, cell.column.id, false),
|
|
435
605
|
children: content
|
|
436
606
|
}, cell.id);
|
|
437
607
|
})
|