@arbor-education/design-system.components 0.2.1 → 0.2.2
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/CHANGELOG.md +8 -0
- package/dist/components/table/Table.d.ts +2 -0
- package/dist/components/table/Table.d.ts.map +1 -1
- package/dist/components/table/Table.js +20 -4
- package/dist/components/table/Table.js.map +1 -1
- package/dist/components/table/toggleRowSelectionInCurrentRange.d.ts +3 -0
- package/dist/components/table/toggleRowSelectionInCurrentRange.d.ts.map +1 -0
- package/dist/components/table/toggleRowSelectionInCurrentRange.js +132 -0
- package/dist/components/table/toggleRowSelectionInCurrentRange.js.map +1 -0
- package/dist/utils/setAgGridLicenseKey.d.ts +2 -0
- package/dist/utils/setAgGridLicenseKey.d.ts.map +1 -0
- package/dist/utils/setAgGridLicenseKey.js +11 -0
- package/dist/utils/setAgGridLicenseKey.js.map +1 -0
- package/package.json +1 -1
- package/src/components/table/Table.tsx +43 -3
- package/src/components/table/toggleRowSelectionInCurrentRange.ts +169 -0
- package/src/utils/setAgGridLicenseKey.ts +17 -0
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,13 @@
|
|
|
1
1
|
## 0.1.4
|
|
2
2
|
|
|
3
|
+
## 0.2.2
|
|
4
|
+
|
|
5
|
+
### Patch Changes
|
|
6
|
+
|
|
7
|
+
- [#98](https://github.com/arbor-education/design-system.components/pull/98) [`4c10758`](https://github.com/arbor-education/design-system.components/commit/4c10758ba2dd30679d87828b2dada1281c5471a6) Thanks [@angusmglfraser](https://github.com/angusmglfraser)! - MIS-64989 implement drag-select on table
|
|
8
|
+
|
|
9
|
+
- [#102](https://github.com/arbor-education/design-system.components/pull/102) [`6c67a72`](https://github.com/arbor-education/design-system.components/commit/6c67a727f79841d45e5aa599cc79495c6fbf440c) Thanks [@angusmglfraser](https://github.com/angusmglfraser)! - MIS-67025 add ag grid license key
|
|
10
|
+
|
|
3
11
|
## 0.2.1
|
|
4
12
|
|
|
5
13
|
### Patch Changes
|
|
@@ -14,6 +14,8 @@ type TableProps<TData = any> = {
|
|
|
14
14
|
'onTableSettingsReset'?: () => void;
|
|
15
15
|
'onColumnBordersChanged'?: (val: boolean) => void;
|
|
16
16
|
'onTableSpacingChanged'?: (val: TABLE_SPACING) => void;
|
|
17
|
+
'enableSimultaneousRangeAndRowSelection'?: boolean;
|
|
18
|
+
'disableDragSelect'?: boolean;
|
|
17
19
|
} & AgGridReactProps<TData>;
|
|
18
20
|
export declare enum TABLE_SPACING {
|
|
19
21
|
XS = "XS",
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"Table.d.ts","sourceRoot":"","sources":["../../../src/components/table/Table.tsx"],"names":[],"mappings":"AAAA,OAAO,EAAuC,KAAK,OAAO,EAAE,MAAM,oBAAoB,CAAC;AACvF,OAAO,EAAe,KAAK,gBAAgB,EAAE,MAAM,eAAe,CAAC;AAGnE,OAAO,
|
|
1
|
+
{"version":3,"file":"Table.d.ts","sourceRoot":"","sources":["../../../src/components/table/Table.tsx"],"names":[],"mappings":"AAAA,OAAO,EAAuC,KAAK,OAAO,EAAE,MAAM,oBAAoB,CAAC;AACvF,OAAO,EAAe,KAAK,gBAAgB,EAAE,MAAM,eAAe,CAAC;AAGnE,OAAO,EAAmC,KAAK,SAAS,EAAE,MAAM,OAAO,CAAC;AAUxE,OAAO,EAAoB,KAAK,aAAa,EAAE,MAAM,oBAAoB,CAAC;AAK1E,KAAK,UAAU,CAAC,KAAK,GAAG,GAAG,IAAI;IAC7B,kBAAkB,CAAC,EAAE,MAAM,CAAC;IAC5B,aAAa,CAAC,EAAE,MAAM,CAAC;IACvB,WAAW,CAAC,EAAE,OAAO,CAAC;IACtB,eAAe,CAAC,EAAE,SAAS,CAAC;IAC5B,cAAc,CAAC,EAAE,MAAM,CAAC;IACxB,eAAe,CAAC,EAAE,SAAS,CAAC;IAC5B,cAAc,CAAC,EAAE,MAAM,CAAC;IACxB,wBAAwB,CAAC,EAAE,CAAC,GAAG,EAAE,aAAa,KAAK,IAAI,CAAC;IACxD,sBAAsB,CAAC,EAAE,MAAM,IAAI,CAAC;IACpC,wBAAwB,CAAC,EAAE,CAAC,GAAG,EAAE,OAAO,KAAK,IAAI,CAAC;IAClD,uBAAuB,CAAC,EAAE,CAAC,GAAG,EAAE,aAAa,KAAK,IAAI,CAAC;IACvD,wCAAwC,CAAC,EAAE,OAAO,CAAC;IACnD,mBAAmB,CAAC,EAAE,OAAO,CAAC;CAC/B,GAAG,gBAAgB,CAAC,KAAK,CAAC,CAAC;AAM5B,oBAAY,aAAa;IACvB,EAAE,OAAO;IACT,CAAC,MAAM;IACP,CAAC,MAAM;IACP,CAAC,MAAM;CACR;AAED,eAAO,MAAM,oBAAoB;;;;;;;;EAQ/B,CAAC;AAEH,eAAO,MAAM,KAAK;YAAW,UAAU;;;;;;;;;;;;;;;;;;;CAgHtC,CAAC"}
|
|
@@ -3,7 +3,7 @@ import { AllEnterpriseModule, ModuleRegistry } from 'ag-grid-enterprise';
|
|
|
3
3
|
import { AgGridReact } from 'ag-grid-react';
|
|
4
4
|
import { tableTheme } from './tableTheme';
|
|
5
5
|
import classNames from 'classnames';
|
|
6
|
-
import { createContext, useState } from 'react';
|
|
6
|
+
import { createContext, useRef, useState } from 'react';
|
|
7
7
|
import { TableFooter } from './TableFooter';
|
|
8
8
|
import { TableHeader } from './TableHeader';
|
|
9
9
|
import { GridApiContext } from './GridApiContext';
|
|
@@ -14,6 +14,9 @@ import { RowCountInfo } from './pagination/RowCountInfo';
|
|
|
14
14
|
import { BulkActionsDropdown } from './BulkActionsDropdown';
|
|
15
15
|
import { HideColumnsDropdown } from './HideColumnsDropdown';
|
|
16
16
|
import { useTableSettings } from './useTableSettings';
|
|
17
|
+
import { setAgGridLicenseKey } from '../../utils/setAgGridLicenseKey';
|
|
18
|
+
import { toggleRowSelectionInCurrentRange } from './toggleRowSelectionInCurrentRange';
|
|
19
|
+
setAgGridLicenseKey();
|
|
17
20
|
ModuleRegistry.registerModules([AllEnterpriseModule]);
|
|
18
21
|
export var TABLE_SPACING;
|
|
19
22
|
(function (TABLE_SPACING) {
|
|
@@ -32,7 +35,7 @@ export const TableSettingsContext = createContext({
|
|
|
32
35
|
resetSettings: () => { },
|
|
33
36
|
});
|
|
34
37
|
export const Table = (props) => {
|
|
35
|
-
const { 'data-testid': testId, wrapperClassName, headerContent, headerTestId, hasSearch = true, footerContent, footerTestId, onGridReady, onTableSettingsChanged, onTableSettingsReset, onColumnBordersChanged, onTableSpacingChanged, ...rest } = props;
|
|
38
|
+
const { 'data-testid': testId, wrapperClassName, headerContent, headerTestId, hasSearch = true, footerContent, footerTestId, onGridReady, onTableSettingsChanged, onTableSettingsReset, onColumnBordersChanged, onTableSpacingChanged, enableSimultaneousRangeAndRowSelection = false, disableDragSelect = false, onCellSelectionChanged, ...rest } = props;
|
|
36
39
|
const [gridApi, setGridApi] = useState(null);
|
|
37
40
|
const [searchValue, setSearchValue] = useState('');
|
|
38
41
|
const { settings, resetSettings, setHasColumnBorders, setTableSpacing, } = useTableSettings({
|
|
@@ -41,8 +44,14 @@ export const Table = (props) => {
|
|
|
41
44
|
onColumnBordersChanged,
|
|
42
45
|
onTableSpacingChanged,
|
|
43
46
|
});
|
|
47
|
+
const isUsingKeyboardRef = useRef(false);
|
|
44
48
|
const { hasColumnBorders, tableSpacing } = settings;
|
|
45
|
-
return (_jsx(GridApiContext.Provider, { value: gridApi, children: _jsx(TableSettingsContext.Provider, { value: {
|
|
49
|
+
return (_jsx(GridApiContext.Provider, { value: gridApi, children: _jsx(TableSettingsContext.Provider, { value: {
|
|
50
|
+
settings,
|
|
51
|
+
resetSettings,
|
|
52
|
+
setHasColumnBorders,
|
|
53
|
+
setTableSpacing,
|
|
54
|
+
}, children: _jsxs("section", { "data-testid": testId, className: classNames('ds-table__container', wrapperClassName), onMouseDown: () => { isUsingKeyboardRef.current = false; }, onMouseUp: () => { isUsingKeyboardRef.current = false; }, onMouseMove: () => { isUsingKeyboardRef.current = false; }, onKeyDown: () => { isUsingKeyboardRef.current = true; }, onKeyUp: () => { isUsingKeyboardRef.current = true; }, children: [headerContent && (_jsx(TableHeader, { "data-testid": headerTestId, hasSearch: hasSearch, searchValue: searchValue, setSearchValue: setSearchValue, children: headerContent })), _jsx(AgGridReact, { theme: tableTheme.withParams({
|
|
46
55
|
headerRowBorder: hasColumnBorders,
|
|
47
56
|
rowBorder: hasColumnBorders,
|
|
48
57
|
wrapperBorder: hasColumnBorders,
|
|
@@ -60,7 +69,14 @@ export const Table = (props) => {
|
|
|
60
69
|
const { api } = event;
|
|
61
70
|
setGridApi(api);
|
|
62
71
|
onGridReady?.(event);
|
|
63
|
-
}, suppressPaginationPanel: true,
|
|
72
|
+
}, suppressPaginationPanel: true, onCellSelectionChanged: (event) => {
|
|
73
|
+
if ((!disableDragSelect || !enableSimultaneousRangeAndRowSelection) && gridApi && event.finished) {
|
|
74
|
+
toggleRowSelectionInCurrentRange(gridApi, isUsingKeyboardRef.current, disableDragSelect, enableSimultaneousRangeAndRowSelection);
|
|
75
|
+
}
|
|
76
|
+
if (onCellSelectionChanged) {
|
|
77
|
+
onCellSelectionChanged(event);
|
|
78
|
+
}
|
|
79
|
+
}, ...rest, ...(hasSearch && { quickFilterText: searchValue }) }), footerContent && (_jsx(TableFooter, { "data-testid": footerTestId, children: footerContent }))] }) }) }));
|
|
64
80
|
};
|
|
65
81
|
Table.PaginationPanel = PaginationPanel;
|
|
66
82
|
Table.PageSizeSelector = PageSizeSelector;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"Table.js","sourceRoot":"","sources":["../../../src/components/table/Table.tsx"],"names":[],"mappings":";AAAA,OAAO,EAAE,mBAAmB,EAAE,cAAc,EAAgB,MAAM,oBAAoB,CAAC;AACvF,OAAO,EAAE,WAAW,EAAyB,MAAM,eAAe,CAAC;AACnE,OAAO,EAAE,UAAU,EAAE,MAAM,cAAc,CAAC;AAC1C,OAAO,UAAU,MAAM,YAAY,CAAC;AACpC,OAAO,EAAE,aAAa,EAAE,QAAQ,EAAkB,MAAM,OAAO,CAAC;
|
|
1
|
+
{"version":3,"file":"Table.js","sourceRoot":"","sources":["../../../src/components/table/Table.tsx"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,3 @@
|
|
|
1
|
+
import { type GridApi } from 'ag-grid-community';
|
|
2
|
+
export declare const toggleRowSelectionInCurrentRange: (gridApi: GridApi, isUsingKeyboard: boolean, disableDragSelect?: boolean, enableSimultaneousRangeAndRowSelection?: boolean) => void;
|
|
3
|
+
//# sourceMappingURL=toggleRowSelectionInCurrentRange.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"toggleRowSelectionInCurrentRange.d.ts","sourceRoot":"","sources":["../../../src/components/table/toggleRowSelectionInCurrentRange.ts"],"names":[],"mappings":"AAAA,OAAO,EAAuC,KAAK,OAAO,EAAE,MAAM,mBAAmB,CAAC;AActF,eAAO,MAAM,gCAAgC,GAC3C,SAAS,OAAO,EAChB,iBAAiB,OAAO,EACxB,2BAAyB,EACzB,gDAA8C,SAsJ/C,CAAC"}
|
|
@@ -0,0 +1,132 @@
|
|
|
1
|
+
import { SELECTION_COLUMN_ID } from 'ag-grid-community';
|
|
2
|
+
const getIsAnyRangeOutsideOfCheckboxColumn = (selectedCellRanges) => {
|
|
3
|
+
const isAnyRangeOutsideOfCheckboxColumn = selectedCellRanges.findIndex(range => range.columns.length > 1
|
|
4
|
+
|| range.columns[0]?.getId() !== SELECTION_COLUMN_ID) > -1;
|
|
5
|
+
return isAnyRangeOutsideOfCheckboxColumn;
|
|
6
|
+
};
|
|
7
|
+
export const toggleRowSelectionInCurrentRange = (gridApi, isUsingKeyboard, disableDragSelect = false, enableSimultaneousRangeAndRowSelection = false) => {
|
|
8
|
+
// In this callback we hack the range selection to allow dragging on checkboxes
|
|
9
|
+
// to change the value of a range of checkboxes
|
|
10
|
+
//
|
|
11
|
+
// When you click on a cell, a single RangeSelectionChangedEvent is triggered.
|
|
12
|
+
// - We want to toggle the selection for this event
|
|
13
|
+
// - Only one cell will be selected in this case
|
|
14
|
+
// When you click and drag on a cell, several RangeSelectionChangedEvents are triggered.
|
|
15
|
+
// - The first and last ones have finished=true, and we can ignore all the others
|
|
16
|
+
//
|
|
17
|
+
// There isn't an easy way to distinguish between the start of both of these cases, so
|
|
18
|
+
// we treat them both the same: toggle the selection of the starting cell.
|
|
19
|
+
// For the click and drag case, at the end of the drag we then toggle the selection of
|
|
20
|
+
// all cells in the range, apart from the starting cell.
|
|
21
|
+
//
|
|
22
|
+
// There isn't any way to tell from RangeSelectionChangedEvent if the event was triggered
|
|
23
|
+
// by mouse or keyboard, so we maintain a this.isUsingKeyboard value for this purpose
|
|
24
|
+
const selectedCellRanges = gridApi.getCellRanges();
|
|
25
|
+
if (selectedCellRanges === null || selectedCellRanges.length === 0) {
|
|
26
|
+
return;
|
|
27
|
+
}
|
|
28
|
+
if (getIsAnyRangeOutsideOfCheckboxColumn(selectedCellRanges)) {
|
|
29
|
+
if (enableSimultaneousRangeAndRowSelection) {
|
|
30
|
+
return;
|
|
31
|
+
}
|
|
32
|
+
// We want to allow either selecting ranges/rows in the checkbox column,
|
|
33
|
+
// or selecting ranges in the other cells, but not both. This is to keep
|
|
34
|
+
// the bulk row action and bulk cell actions separate
|
|
35
|
+
//
|
|
36
|
+
// We want to allow selecting ranges within the checkbox column
|
|
37
|
+
// So that you can do shift+click to enable several columns, and
|
|
38
|
+
// other similar interractions
|
|
39
|
+
const rows = gridApi.getSelectedRows();
|
|
40
|
+
if (rows.length > 0) {
|
|
41
|
+
// Deselect all the selected rows
|
|
42
|
+
gridApi.deselectAll();
|
|
43
|
+
}
|
|
44
|
+
return;
|
|
45
|
+
}
|
|
46
|
+
if (disableDragSelect) {
|
|
47
|
+
return;
|
|
48
|
+
}
|
|
49
|
+
const { startRow: unsafeStartRow, endRow: unsafeEndRow } = selectedCellRanges[0];
|
|
50
|
+
if (typeof unsafeStartRow === 'undefined'
|
|
51
|
+
|| typeof unsafeEndRow === 'undefined') {
|
|
52
|
+
console.error('undefined start or end row', { unsafeStartRow, unsafeEndRow });
|
|
53
|
+
return;
|
|
54
|
+
}
|
|
55
|
+
// We need to be careful to exclude any pinned rows
|
|
56
|
+
if (unsafeStartRow.rowPinned === 'top'
|
|
57
|
+
|| unsafeStartRow.rowPinned === 'bottom') {
|
|
58
|
+
// If we start on a pinned row just do nothing, as there isn't an initial value to use
|
|
59
|
+
return;
|
|
60
|
+
}
|
|
61
|
+
// startRow will now be safe due to check above
|
|
62
|
+
const startRowIndex = unsafeStartRow.rowIndex;
|
|
63
|
+
// For end row, we shall trim to the fist last row, so you don't have to be
|
|
64
|
+
// really accurate with the mouse
|
|
65
|
+
let endRowIndex = unsafeEndRow.rowIndex;
|
|
66
|
+
if (unsafeEndRow.rowPinned === 'bottom') {
|
|
67
|
+
endRowIndex = gridApi.getDisplayedRowCount() - 1;
|
|
68
|
+
}
|
|
69
|
+
else if (unsafeEndRow.rowPinned === 'top') {
|
|
70
|
+
endRowIndex = 0;
|
|
71
|
+
}
|
|
72
|
+
const startingRowNode = gridApi.getDisplayedRowAtIndex(startRowIndex);
|
|
73
|
+
const isStartingRowNodeSelected = !!startingRowNode?.isSelected();
|
|
74
|
+
if (startRowIndex === endRowIndex) {
|
|
75
|
+
// We do not want to flip the state if we are currently using the keyboard, else
|
|
76
|
+
// navigating to a cell with select it.
|
|
77
|
+
if (!isUsingKeyboard) {
|
|
78
|
+
/**
|
|
79
|
+
* If the drag is started by a click in the cell but outside the checkbox, AG Grid registers it
|
|
80
|
+
* as a CellSelectionChangedEvent and this listener is then fired immediately after the mouseDown.
|
|
81
|
+
*
|
|
82
|
+
* If the drag is started by a click in the cell but inside the checkbox, AG Grid does not register
|
|
83
|
+
* a CellSelectionChangedEvent, so this listener doesn't fire, and is only first triggered once the
|
|
84
|
+
* drag moves the selection into another cell.
|
|
85
|
+
*
|
|
86
|
+
* The key difference between these two cases is that AG Grid will not toggle the cell for mouseDown
|
|
87
|
+
* on the checkbox, it will only do so for mouseDown and mouseUp on the same checkbox, so at the end
|
|
88
|
+
* of a drag on the checkbox row, if the drag started on the checkbox, it will need to be toggled at the
|
|
89
|
+
* end of the drag. If the drag started in a different area of the cell, it will already have been
|
|
90
|
+
* toggled
|
|
91
|
+
*/
|
|
92
|
+
startingRowNode?.setSelected(!isStartingRowNodeSelected);
|
|
93
|
+
startingRowNode?.updateData({
|
|
94
|
+
...startingRowNode.data,
|
|
95
|
+
firstToggledByClickOutsideCheckbox: true,
|
|
96
|
+
});
|
|
97
|
+
}
|
|
98
|
+
return;
|
|
99
|
+
}
|
|
100
|
+
const { smallestIndex, largestIndex } = startRowIndex < endRowIndex
|
|
101
|
+
? {
|
|
102
|
+
smallestIndex: startRowIndex,
|
|
103
|
+
largestIndex: endRowIndex,
|
|
104
|
+
}
|
|
105
|
+
: {
|
|
106
|
+
smallestIndex: endRowIndex,
|
|
107
|
+
largestIndex: startRowIndex,
|
|
108
|
+
};
|
|
109
|
+
const initiallyToggledOutsideCheckbox = startingRowNode?.data.firstToggledByClickOutsideCheckbox;
|
|
110
|
+
// restoring the data on the node to clear the flag set on the cell
|
|
111
|
+
const {
|
|
112
|
+
// eslint-disable-next-line @typescript-eslint/no-unused-vars
|
|
113
|
+
firstToggledByClickOutsideCheckbox: _intentionallyDiscarded, ...initialStartingRowData } = startingRowNode?.data || {};
|
|
114
|
+
startingRowNode?.updateData(initialStartingRowData);
|
|
115
|
+
const shouldInvertNextUpdatedRows = !initiallyToggledOutsideCheckbox && !isUsingKeyboard;
|
|
116
|
+
if (shouldInvertNextUpdatedRows) {
|
|
117
|
+
startingRowNode?.setSelected(!isStartingRowNodeSelected);
|
|
118
|
+
}
|
|
119
|
+
gridApi.forEachNodeAfterFilterAndSort((node, index) => {
|
|
120
|
+
if (index >= smallestIndex
|
|
121
|
+
&& index <= largestIndex
|
|
122
|
+
&& index !== startRowIndex) {
|
|
123
|
+
if (shouldInvertNextUpdatedRows) {
|
|
124
|
+
node.setSelected(!isStartingRowNodeSelected);
|
|
125
|
+
}
|
|
126
|
+
else {
|
|
127
|
+
node.setSelected(isStartingRowNodeSelected);
|
|
128
|
+
}
|
|
129
|
+
}
|
|
130
|
+
});
|
|
131
|
+
};
|
|
132
|
+
//# sourceMappingURL=toggleRowSelectionInCurrentRange.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"toggleRowSelectionInCurrentRange.js","sourceRoot":"","sources":["../../../src/components/table/toggleRowSelectionInCurrentRange.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"setAgGridLicenseKey.d.ts","sourceRoot":"","sources":["../../src/utils/setAgGridLicenseKey.ts"],"names":[],"mappings":"AAQA,eAAO,MAAM,mBAAmB,YAQ/B,CAAC"}
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
import { AgChartsCommunityModule } from 'ag-charts-community';
|
|
2
|
+
import { ModuleRegistry } from 'ag-grid-community';
|
|
3
|
+
import { LicenseManager, IntegratedChartsModule, AllEnterpriseModule, } from 'ag-grid-enterprise';
|
|
4
|
+
export const setAgGridLicenseKey = () => {
|
|
5
|
+
LicenseManager.setLicenseKey('Using_this_{AG_Grid}_Enterprise_key_{AG-076208}_in_excess_of_the_licence_granted_is_not_permitted___Please_report_misuse_to_legal@ag-grid.com___For_help_with_changing_this_key_please_contact_info@ag-grid.com___{Arbor_Education_Partners_Ltd}_is_granted_a_{Single_Application}_Developer_License_for_the_application_{Arbor_MIS}_only_for_{4}_Front-End_JavaScript_developers___All_Front-End_JavaScript_developers_working_on_{Arbor_MIS}_need_to_be_licensed___{Arbor_MIS}_has_been_granted_a_Deployment_License_Add-on_for_{1}_Production_Environment___This_key_works_with_{AG_Grid}_Enterprise_versions_released_before_{16_March_2026}____[v3]_[01]_MTc3MzYxOTIwMDAwMA==8820260fc59099926cf507c1e8018e49');
|
|
6
|
+
ModuleRegistry.registerModules([
|
|
7
|
+
IntegratedChartsModule.with(AgChartsCommunityModule),
|
|
8
|
+
AllEnterpriseModule,
|
|
9
|
+
]);
|
|
10
|
+
};
|
|
11
|
+
//# sourceMappingURL=setAgGridLicenseKey.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"setAgGridLicenseKey.js","sourceRoot":"","sources":["../../src/utils/setAgGridLicenseKey.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,uBAAuB,EAAE,MAAM,qBAAqB,CAAC;AAC9D,OAAO,EAAE,cAAc,EAAE,MAAM,mBAAmB,CAAC;AACnD,OAAO,EACL,cAAc,EACd,sBAAsB,EACtB,mBAAmB,GACpB,MAAM,oBAAoB,CAAC;AAE5B,MAAM,CAAC,MAAM,mBAAmB,GAAG,GAAG,EAAE;IACtC,cAAc,CAAC,aAAa,CAC1B,orBAAorB,CACrrB,CAAC;IACF,cAAc,CAAC,eAAe,CAAC;QAC7B,sBAAsB,CAAC,IAAI,CAAC,uBAAuB,CAAC;QACpD,mBAAmB;KACpB,CAAC,CAAC;AACL,CAAC,CAAC"}
|
package/package.json
CHANGED
|
@@ -2,7 +2,7 @@ import { AllEnterpriseModule, ModuleRegistry, type GridApi } from 'ag-grid-enter
|
|
|
2
2
|
import { AgGridReact, type AgGridReactProps } from 'ag-grid-react';
|
|
3
3
|
import { tableTheme } from './tableTheme';
|
|
4
4
|
import classNames from 'classnames';
|
|
5
|
-
import { createContext, useState, type ReactNode } from 'react';
|
|
5
|
+
import { createContext, useRef, useState, type ReactNode } from 'react';
|
|
6
6
|
import { TableFooter } from './TableFooter';
|
|
7
7
|
import { TableHeader } from './TableHeader';
|
|
8
8
|
import { GridApiContext } from './GridApiContext';
|
|
@@ -13,6 +13,8 @@ import { RowCountInfo } from './pagination/RowCountInfo';
|
|
|
13
13
|
import { BulkActionsDropdown } from './BulkActionsDropdown';
|
|
14
14
|
import { HideColumnsDropdown } from './HideColumnsDropdown';
|
|
15
15
|
import { useTableSettings, type TableSettings } from './useTableSettings';
|
|
16
|
+
import { setAgGridLicenseKey } from 'Utils/setAgGridLicenseKey';
|
|
17
|
+
import { toggleRowSelectionInCurrentRange } from './toggleRowSelectionInCurrentRange';
|
|
16
18
|
|
|
17
19
|
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
18
20
|
type TableProps<TData = any> = {
|
|
@@ -27,8 +29,12 @@ type TableProps<TData = any> = {
|
|
|
27
29
|
'onTableSettingsReset'?: () => void;
|
|
28
30
|
'onColumnBordersChanged'?: (val: boolean) => void;
|
|
29
31
|
'onTableSpacingChanged'?: (val: TABLE_SPACING) => void;
|
|
32
|
+
'enableSimultaneousRangeAndRowSelection'?: boolean;
|
|
33
|
+
'disableDragSelect'?: boolean;
|
|
30
34
|
} & AgGridReactProps<TData>;
|
|
31
35
|
|
|
36
|
+
setAgGridLicenseKey();
|
|
37
|
+
|
|
32
38
|
ModuleRegistry.registerModules([AllEnterpriseModule]);
|
|
33
39
|
|
|
34
40
|
export enum TABLE_SPACING {
|
|
@@ -62,6 +68,9 @@ export const Table = (props: TableProps) => {
|
|
|
62
68
|
onTableSettingsReset,
|
|
63
69
|
onColumnBordersChanged,
|
|
64
70
|
onTableSpacingChanged,
|
|
71
|
+
enableSimultaneousRangeAndRowSelection = false,
|
|
72
|
+
disableDragSelect = false,
|
|
73
|
+
onCellSelectionChanged,
|
|
65
74
|
...rest
|
|
66
75
|
} = props;
|
|
67
76
|
|
|
@@ -81,12 +90,29 @@ export const Table = (props: TableProps) => {
|
|
|
81
90
|
onTableSpacingChanged,
|
|
82
91
|
});
|
|
83
92
|
|
|
93
|
+
const isUsingKeyboardRef = useRef(false);
|
|
94
|
+
|
|
84
95
|
const { hasColumnBorders, tableSpacing } = settings;
|
|
85
96
|
|
|
86
97
|
return (
|
|
87
98
|
<GridApiContext.Provider value={gridApi}>
|
|
88
|
-
<TableSettingsContext.Provider
|
|
89
|
-
|
|
99
|
+
<TableSettingsContext.Provider
|
|
100
|
+
value={{
|
|
101
|
+
settings,
|
|
102
|
+
resetSettings,
|
|
103
|
+
setHasColumnBorders,
|
|
104
|
+
setTableSpacing,
|
|
105
|
+
}}
|
|
106
|
+
>
|
|
107
|
+
<section
|
|
108
|
+
data-testid={testId}
|
|
109
|
+
className={classNames('ds-table__container', wrapperClassName)}
|
|
110
|
+
onMouseDown={() => { isUsingKeyboardRef.current = false; }}
|
|
111
|
+
onMouseUp={() => { isUsingKeyboardRef.current = false; }}
|
|
112
|
+
onMouseMove={() => { isUsingKeyboardRef.current = false; }}
|
|
113
|
+
onKeyDown={() => { isUsingKeyboardRef.current = true; }}
|
|
114
|
+
onKeyUp={() => { isUsingKeyboardRef.current = true; }}
|
|
115
|
+
>
|
|
90
116
|
{headerContent && (
|
|
91
117
|
<TableHeader data-testid={headerTestId} hasSearch={hasSearch} searchValue={searchValue} setSearchValue={setSearchValue}>
|
|
92
118
|
{headerContent}
|
|
@@ -114,6 +140,20 @@ export const Table = (props: TableProps) => {
|
|
|
114
140
|
onGridReady?.(event);
|
|
115
141
|
}}
|
|
116
142
|
suppressPaginationPanel
|
|
143
|
+
onCellSelectionChanged={(event) => {
|
|
144
|
+
if ((!disableDragSelect || !enableSimultaneousRangeAndRowSelection) && gridApi && event.finished) {
|
|
145
|
+
toggleRowSelectionInCurrentRange(
|
|
146
|
+
gridApi,
|
|
147
|
+
isUsingKeyboardRef.current,
|
|
148
|
+
disableDragSelect,
|
|
149
|
+
enableSimultaneousRangeAndRowSelection,
|
|
150
|
+
);
|
|
151
|
+
}
|
|
152
|
+
|
|
153
|
+
if (onCellSelectionChanged) {
|
|
154
|
+
onCellSelectionChanged(event);
|
|
155
|
+
}
|
|
156
|
+
}}
|
|
117
157
|
{...rest}
|
|
118
158
|
{...(hasSearch && { quickFilterText: searchValue })}
|
|
119
159
|
/>
|
|
@@ -0,0 +1,169 @@
|
|
|
1
|
+
import { SELECTION_COLUMN_ID, type CellRange, type GridApi } from 'ag-grid-community';
|
|
2
|
+
|
|
3
|
+
const getIsAnyRangeOutsideOfCheckboxColumn = (
|
|
4
|
+
selectedCellRanges: CellRange[],
|
|
5
|
+
) => {
|
|
6
|
+
const isAnyRangeOutsideOfCheckboxColumn
|
|
7
|
+
= selectedCellRanges.findIndex(
|
|
8
|
+
range =>
|
|
9
|
+
range.columns.length > 1
|
|
10
|
+
|| range.columns[0]?.getId() !== SELECTION_COLUMN_ID,
|
|
11
|
+
) > -1;
|
|
12
|
+
return isAnyRangeOutsideOfCheckboxColumn;
|
|
13
|
+
};
|
|
14
|
+
|
|
15
|
+
export const toggleRowSelectionInCurrentRange = (
|
|
16
|
+
gridApi: GridApi,
|
|
17
|
+
isUsingKeyboard: boolean,
|
|
18
|
+
disableDragSelect = false,
|
|
19
|
+
enableSimultaneousRangeAndRowSelection = false,
|
|
20
|
+
) => {
|
|
21
|
+
// In this callback we hack the range selection to allow dragging on checkboxes
|
|
22
|
+
// to change the value of a range of checkboxes
|
|
23
|
+
//
|
|
24
|
+
// When you click on a cell, a single RangeSelectionChangedEvent is triggered.
|
|
25
|
+
// - We want to toggle the selection for this event
|
|
26
|
+
// - Only one cell will be selected in this case
|
|
27
|
+
// When you click and drag on a cell, several RangeSelectionChangedEvents are triggered.
|
|
28
|
+
// - The first and last ones have finished=true, and we can ignore all the others
|
|
29
|
+
//
|
|
30
|
+
// There isn't an easy way to distinguish between the start of both of these cases, so
|
|
31
|
+
// we treat them both the same: toggle the selection of the starting cell.
|
|
32
|
+
// For the click and drag case, at the end of the drag we then toggle the selection of
|
|
33
|
+
// all cells in the range, apart from the starting cell.
|
|
34
|
+
//
|
|
35
|
+
// There isn't any way to tell from RangeSelectionChangedEvent if the event was triggered
|
|
36
|
+
// by mouse or keyboard, so we maintain a this.isUsingKeyboard value for this purpose
|
|
37
|
+
|
|
38
|
+
const selectedCellRanges = gridApi.getCellRanges();
|
|
39
|
+
if (selectedCellRanges === null || selectedCellRanges.length === 0) {
|
|
40
|
+
return;
|
|
41
|
+
}
|
|
42
|
+
|
|
43
|
+
if (getIsAnyRangeOutsideOfCheckboxColumn(selectedCellRanges)) {
|
|
44
|
+
if (enableSimultaneousRangeAndRowSelection) {
|
|
45
|
+
return;
|
|
46
|
+
}
|
|
47
|
+
// We want to allow either selecting ranges/rows in the checkbox column,
|
|
48
|
+
// or selecting ranges in the other cells, but not both. This is to keep
|
|
49
|
+
// the bulk row action and bulk cell actions separate
|
|
50
|
+
//
|
|
51
|
+
// We want to allow selecting ranges within the checkbox column
|
|
52
|
+
// So that you can do shift+click to enable several columns, and
|
|
53
|
+
// other similar interractions
|
|
54
|
+
const rows = gridApi.getSelectedRows();
|
|
55
|
+
if (rows.length > 0) {
|
|
56
|
+
// Deselect all the selected rows
|
|
57
|
+
gridApi.deselectAll();
|
|
58
|
+
}
|
|
59
|
+
return;
|
|
60
|
+
}
|
|
61
|
+
|
|
62
|
+
if (disableDragSelect) {
|
|
63
|
+
return;
|
|
64
|
+
}
|
|
65
|
+
|
|
66
|
+
const { startRow: unsafeStartRow, endRow: unsafeEndRow }
|
|
67
|
+
= selectedCellRanges[0] as CellRange;
|
|
68
|
+
if (
|
|
69
|
+
typeof unsafeStartRow === 'undefined'
|
|
70
|
+
|| typeof unsafeEndRow === 'undefined'
|
|
71
|
+
) {
|
|
72
|
+
console.error('undefined start or end row', { unsafeStartRow, unsafeEndRow });
|
|
73
|
+
return;
|
|
74
|
+
}
|
|
75
|
+
|
|
76
|
+
// We need to be careful to exclude any pinned rows
|
|
77
|
+
if (
|
|
78
|
+
unsafeStartRow.rowPinned === 'top'
|
|
79
|
+
|| unsafeStartRow.rowPinned === 'bottom'
|
|
80
|
+
) {
|
|
81
|
+
// If we start on a pinned row just do nothing, as there isn't an initial value to use
|
|
82
|
+
return;
|
|
83
|
+
}
|
|
84
|
+
// startRow will now be safe due to check above
|
|
85
|
+
const startRowIndex = unsafeStartRow.rowIndex;
|
|
86
|
+
|
|
87
|
+
// For end row, we shall trim to the fist last row, so you don't have to be
|
|
88
|
+
// really accurate with the mouse
|
|
89
|
+
let endRowIndex = unsafeEndRow.rowIndex;
|
|
90
|
+
if (unsafeEndRow.rowPinned === 'bottom') {
|
|
91
|
+
endRowIndex = gridApi.getDisplayedRowCount() - 1;
|
|
92
|
+
}
|
|
93
|
+
else if (unsafeEndRow.rowPinned === 'top') {
|
|
94
|
+
endRowIndex = 0;
|
|
95
|
+
}
|
|
96
|
+
|
|
97
|
+
const startingRowNode = gridApi.getDisplayedRowAtIndex(startRowIndex);
|
|
98
|
+
const isStartingRowNodeSelected = !!startingRowNode?.isSelected();
|
|
99
|
+
if (startRowIndex === endRowIndex) {
|
|
100
|
+
// We do not want to flip the state if we are currently using the keyboard, else
|
|
101
|
+
// navigating to a cell with select it.
|
|
102
|
+
if (!isUsingKeyboard) {
|
|
103
|
+
/**
|
|
104
|
+
* If the drag is started by a click in the cell but outside the checkbox, AG Grid registers it
|
|
105
|
+
* as a CellSelectionChangedEvent and this listener is then fired immediately after the mouseDown.
|
|
106
|
+
*
|
|
107
|
+
* If the drag is started by a click in the cell but inside the checkbox, AG Grid does not register
|
|
108
|
+
* a CellSelectionChangedEvent, so this listener doesn't fire, and is only first triggered once the
|
|
109
|
+
* drag moves the selection into another cell.
|
|
110
|
+
*
|
|
111
|
+
* The key difference between these two cases is that AG Grid will not toggle the cell for mouseDown
|
|
112
|
+
* on the checkbox, it will only do so for mouseDown and mouseUp on the same checkbox, so at the end
|
|
113
|
+
* of a drag on the checkbox row, if the drag started on the checkbox, it will need to be toggled at the
|
|
114
|
+
* end of the drag. If the drag started in a different area of the cell, it will already have been
|
|
115
|
+
* toggled
|
|
116
|
+
*/
|
|
117
|
+
startingRowNode?.setSelected(!isStartingRowNodeSelected);
|
|
118
|
+
startingRowNode?.updateData({
|
|
119
|
+
...startingRowNode.data,
|
|
120
|
+
firstToggledByClickOutsideCheckbox: true,
|
|
121
|
+
});
|
|
122
|
+
}
|
|
123
|
+
return;
|
|
124
|
+
}
|
|
125
|
+
|
|
126
|
+
const { smallestIndex, largestIndex }
|
|
127
|
+
= startRowIndex < endRowIndex
|
|
128
|
+
? {
|
|
129
|
+
smallestIndex: startRowIndex,
|
|
130
|
+
largestIndex: endRowIndex,
|
|
131
|
+
}
|
|
132
|
+
: {
|
|
133
|
+
smallestIndex: endRowIndex,
|
|
134
|
+
largestIndex: startRowIndex,
|
|
135
|
+
};
|
|
136
|
+
|
|
137
|
+
const initiallyToggledOutsideCheckbox
|
|
138
|
+
= startingRowNode?.data.firstToggledByClickOutsideCheckbox;
|
|
139
|
+
|
|
140
|
+
// restoring the data on the node to clear the flag set on the cell
|
|
141
|
+
const {
|
|
142
|
+
// eslint-disable-next-line @typescript-eslint/no-unused-vars
|
|
143
|
+
firstToggledByClickOutsideCheckbox: _intentionallyDiscarded,
|
|
144
|
+
...initialStartingRowData
|
|
145
|
+
} = startingRowNode?.data || {};
|
|
146
|
+
startingRowNode?.updateData(initialStartingRowData);
|
|
147
|
+
|
|
148
|
+
const shouldInvertNextUpdatedRows
|
|
149
|
+
= !initiallyToggledOutsideCheckbox && !isUsingKeyboard;
|
|
150
|
+
|
|
151
|
+
if (shouldInvertNextUpdatedRows) {
|
|
152
|
+
startingRowNode?.setSelected(!isStartingRowNodeSelected);
|
|
153
|
+
}
|
|
154
|
+
|
|
155
|
+
gridApi.forEachNodeAfterFilterAndSort((node, index) => {
|
|
156
|
+
if (
|
|
157
|
+
index >= smallestIndex
|
|
158
|
+
&& index <= largestIndex
|
|
159
|
+
&& index !== startRowIndex
|
|
160
|
+
) {
|
|
161
|
+
if (shouldInvertNextUpdatedRows) {
|
|
162
|
+
node.setSelected(!isStartingRowNodeSelected);
|
|
163
|
+
}
|
|
164
|
+
else {
|
|
165
|
+
node.setSelected(isStartingRowNodeSelected);
|
|
166
|
+
}
|
|
167
|
+
}
|
|
168
|
+
});
|
|
169
|
+
};
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
import { AgChartsCommunityModule } from 'ag-charts-community';
|
|
2
|
+
import { ModuleRegistry } from 'ag-grid-community';
|
|
3
|
+
import {
|
|
4
|
+
LicenseManager,
|
|
5
|
+
IntegratedChartsModule,
|
|
6
|
+
AllEnterpriseModule,
|
|
7
|
+
} from 'ag-grid-enterprise';
|
|
8
|
+
|
|
9
|
+
export const setAgGridLicenseKey = () => {
|
|
10
|
+
LicenseManager.setLicenseKey(
|
|
11
|
+
'Using_this_{AG_Grid}_Enterprise_key_{AG-076208}_in_excess_of_the_licence_granted_is_not_permitted___Please_report_misuse_to_legal@ag-grid.com___For_help_with_changing_this_key_please_contact_info@ag-grid.com___{Arbor_Education_Partners_Ltd}_is_granted_a_{Single_Application}_Developer_License_for_the_application_{Arbor_MIS}_only_for_{4}_Front-End_JavaScript_developers___All_Front-End_JavaScript_developers_working_on_{Arbor_MIS}_need_to_be_licensed___{Arbor_MIS}_has_been_granted_a_Deployment_License_Add-on_for_{1}_Production_Environment___This_key_works_with_{AG_Grid}_Enterprise_versions_released_before_{16_March_2026}____[v3]_[01]_MTc3MzYxOTIwMDAwMA==8820260fc59099926cf507c1e8018e49',
|
|
12
|
+
);
|
|
13
|
+
ModuleRegistry.registerModules([
|
|
14
|
+
IntegratedChartsModule.with(AgChartsCommunityModule),
|
|
15
|
+
AllEnterpriseModule,
|
|
16
|
+
]);
|
|
17
|
+
};
|