Skip to content

Commit

Permalink
fix: re called onMaxSelectedRows function
Browse files Browse the repository at this point in the history
  • Loading branch information
johnvente committed Aug 7, 2023
1 parent d81297b commit 1de1586
Show file tree
Hide file tree
Showing 3 changed files with 37 additions and 22 deletions.
25 changes: 24 additions & 1 deletion src/DataTable/index.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -62,7 +62,7 @@ function DataTable({
);
const tableOptions = useMemo(() => {
const updatedTableOptions = {
stateReducer: (newState, action) => {
stateReducer: (newState, action, previousState) => {
switch (action.type) {
// Note: we override the `toggleAllRowsSelected` action
// from react-table because it only clears the selections on the
Expand All @@ -79,6 +79,28 @@ function DataTable({
selectedRowIds: {},
};
}
/* Note: We override the `toggleRowSelected` action from react-table
because we need to preserve the order of the selected rows.
While `selectedRowIds` is an object that contains the selected rows as key-value pairs,
it does not maintain the order of selection. Therefore, we have added the `selectedRowsOrdered` property
to keep track of the order in which the rows were selected.
*/
case 'toggleRowSelected': {
const rowIndex = parseInt(action.id, 10);
const { selectedRowsOrdered = [] } = previousState;

let newSelectedRowsOrdered;
if (action.value) {
newSelectedRowsOrdered = [...selectedRowsOrdered, rowIndex];
} else {
newSelectedRowsOrdered = selectedRowsOrdered.filter((item) => item !== rowIndex);
}

return {
...newState,
selectedRowsOrdered: newSelectedRowsOrdered,
};
}
default:
return newState;
}
Expand Down Expand Up @@ -314,6 +336,7 @@ DataTable.propTypes = {
filters: requiredWhen(PropTypes.arrayOf(PropTypes.shape()), 'manualFilters'),
sortBy: requiredWhen(PropTypes.arrayOf(PropTypes.shape()), 'manualSortBy'),
selectedRowIds: PropTypes.shape(),
selectedRowsOrdered: PropTypes.arrayOf(PropTypes.number),
}),
/** Table options passed to react-table's useTable hook. Will override some options passed in to DataTable, such
as: data, columns, defaultColumn, manualFilters, manualPagination, manualSortBy, and initialState */
Expand Down
7 changes: 4 additions & 3 deletions src/DataTable/utils/getVisibleColumns.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -43,7 +43,7 @@ export const selectColumn = {
/* eslint-disable react/prop-types */
Cell: ({ row }) => {
const {
isSelectable, maxSelectedRows, onMaxSelectedRows, state: { selectedRowIds },
isSelectable, maxSelectedRows, onMaxSelectedRows, state: { selectedRowIds, selectedRowsOrdered },
} = useContext(DataTableContext);
const updatedProps = useConvertIndeterminateProp(row.getToggleRowSelectedProps());
const { index } = row;
Expand All @@ -52,12 +52,13 @@ export const selectColumn = {
const formatMaxSelectedRows = Math.max(0, maxSelectedRows);
const hasMaxSelectedRows = formatMaxSelectedRows === selectedRowsLength;
const disableCheck = isSelectable && hasMaxSelectedRows && !isRowSelected;
const lastRowSelected = selectedRowsOrdered?.[selectedRowsOrdered.length - 1] ?? null;

useEffect(() => {
if (hasMaxSelectedRows && selectedRowIds[index]) {
if (hasMaxSelectedRows && lastRowSelected === index) {
onMaxSelectedRows?.();
}
}, [hasMaxSelectedRows, index, onMaxSelectedRows, selectedRowIds]);
}, [hasMaxSelectedRows, index, isRowSelected, lastRowSelected, onMaxSelectedRows, selectedRowIds]);

return (
<div className="pgn__data-table__controlled-select">
Expand Down
27 changes: 9 additions & 18 deletions src/DataTable/utils/tests/selectColumn.test.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -74,11 +74,9 @@ describe('selectColumn', () => {
it('should render the CheckboxControl when isSelectable is true and maxSelectedRows is not reached', () => {
const contextValue = {};

const { container } = renderWithTestWrapper(contextValue);
const { queryByTestId } = renderWithTestWrapper(contextValue);

const checkbox = container.querySelector(
'[data-testid="datatable-select-column-checkbox-header"]',
);
const checkbox = queryByTestId('datatable-select-column-checkbox-header');

expect(checkbox).toBeInTheDocument();
});
Expand All @@ -88,11 +86,8 @@ describe('selectColumn', () => {
maxSelectedRows: 5,
};

const { container } = renderWithTestWrapper(contextValue);
const checkbox = container.querySelector(
'[data-testid="datatable-select-column-checkbox-header"]',
);

const { queryByTestId } = renderWithTestWrapper(contextValue);
const checkbox = queryByTestId('datatable-select-column-checkbox-header');
expect(checkbox).toBeInTheDocument();
});

Expand All @@ -102,10 +97,8 @@ describe('selectColumn', () => {
maxSelectedRows: 5,
};

const { container } = renderWithTestWrapper(contextValue);
const checkbox = container.querySelector(
'[data-testid="datatable-select-column-checkbox-header"]',
);
const { queryByTestId } = renderWithTestWrapper(contextValue);
const checkbox = queryByTestId('datatable-select-column-checkbox-header');

expect(checkbox).toBeNull();
});
Expand All @@ -123,10 +116,8 @@ describe('selectColumn', () => {

};

const { container } = renderWithTestWrapper(contextValue);
const checkbox = container.querySelector(
'[data-testid="datatable-select-column-checkbox-header"]',
);
const { queryByTestId } = renderWithTestWrapper(contextValue);
const checkbox = queryByTestId('datatable-select-column-checkbox-header');

expect(checkbox).toBeInTheDocument();
});
Expand Down Expand Up @@ -161,7 +152,7 @@ describe('selectColumn', () => {
it('Should call onMaxSelectedRows callback when isSelectable is true and maxSelectedRows has passed the limit', async () => {
const datatableContext = {
...mockDataTableContextValue,
state: { selectedRowIds: { 0: true } },
state: { selectedRowIds: { 0: true }, selectedRowsOrdered: [0] },
};

const [row1] = mockDataTableContextValue.rows;
Expand Down

0 comments on commit 1de1586

Please sign in to comment.