Skip to content

Commit

Permalink
fix(mantine, table): add missing property expanded from the state (#3730
Browse files Browse the repository at this point in the history
)
  • Loading branch information
GermainBergeron authored May 28, 2024
1 parent f602812 commit aaa55b1
Show file tree
Hide file tree
Showing 4 changed files with 113 additions and 2 deletions.
2 changes: 2 additions & 0 deletions packages/mantine/src/components/table/Table.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -138,8 +138,10 @@ export const Table = <T,>(props: TableProps<T> & {ref?: ForwardedRef<HTMLDivElem
sorting: store.state.sorting,
pagination: store.state.pagination,
columnVisibility: store.state.columnVisibility,
expanded: store.state.expanded,
},
onGlobalFilterChange: store.setGlobalFilter,
onExpandedChange: store.setExpanded,
onSortingChange: store.setSorting,
onPaginationChange: store.setPagination,
onColumnVisibilityChange: store.setColumnVisibility,
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,88 @@
import {Box} from '@mantine/core';
import {ColumnDef, createColumnHelper} from '@tanstack/table-core';
import {render, screen, userEvent} from '@test-utils';
import {waitFor} from '@testing-library/react';
import {Table} from '../Table';
import {useTable} from '../use-table';

const mockData = [
{
id: 'a',
name: 'John Doe',
body: 'coucou',
},
{
id: 'b',
name: 'Jane Doe',
body: 'coucou 2',
},
] satisfies RowData[];

type RowData = {
id: string;
name: string;
body: string;
};

const columnHelper = createColumnHelper<RowData>();
const baseColumns: Array<ColumnDef<RowData>> = [
columnHelper.accessor('name', {header: 'Name', enableSorting: false}),
Table.CollapsibleColumn as ColumnDef<RowData>,
];

describe('TableCollapsibleColumn', () => {
it('expands the rows when the user clicks on a cell', async () => {
const user = userEvent.setup();
const Fixture = () => {
const store = useTable<RowData>();
return (
<Table
store={store}
data={mockData}
columns={baseColumns}
getRowId={(datum: RowData) => datum.id}
getRowExpandedContent={(datum: RowData) => (
<Box data-testid={`row-content-${datum.id}`}>{datum.body}</Box>
)}
/>
);
};
render(<Fixture />);

expect(screen.queryByTestId('row-content-a')).not.toBeVisible();
expect(screen.queryByTestId('row-content-b')).not.toBeVisible();
await user.click(screen.getByRole('cell', {name: 'Jane Doe'}));

await waitFor(() => expect(screen.getByTestId('row-content-b')).toBeVisible());
expect(screen.queryByTestId('row-content-a')).not.toBeVisible();
expect(screen.getByTestId('row-content-b')).toHaveTextContent('coucou 2');
});

it('expands the rows according to the initial state', () => {
const Fixture = ({expanded}: {expanded: string}) => {
const store = useTable<RowData>({initialState: {expanded: {[expanded]: true}}});
return (
<Table
store={store}
data={mockData}
columns={baseColumns}
getRowId={(datum: RowData) => datum.id}
getRowExpandedContent={(datum: RowData) => (
<Box data-testid={`row-content-${datum.id}`}>{datum.body}</Box>
)}
/>
);
};
const {unmount} = render(<Fixture expanded="b" />);

expect(screen.queryByTestId('row-content-a')).not.toBeVisible();
expect(screen.queryByTestId('row-content-b')).toBeVisible();

// unmount and mount a new component to be able to use initialState
unmount();
render(<Fixture expanded="a" />);

expect(screen.queryByTestId('row-content-a')).toBeVisible();
expect(screen.queryByTestId('row-content-b')).not.toBeVisible();
});
});
17 changes: 16 additions & 1 deletion packages/mantine/src/components/table/use-table.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import {useDidUpdate} from '@mantine/hooks';
import {type PaginationState, type SortingState} from '@tanstack/table-core';
import {type PaginationState, type SortingState, type ExpandedState} from '@tanstack/table-core';
import defaultsDeep from 'lodash.defaultsdeep';
import {useCallback, useMemo, useState} from 'react';
import {type DateRangePickerValue} from '../date-range-picker';
Expand Down Expand Up @@ -38,6 +38,13 @@ export interface TableState<TData = unknown> {
* @default ''
*/
globalFilter: string;

/**
* Current expanded state
*
* @default {}
*/
expanded: ExpandedState;
/**
* Predicates and their current value
*
Expand Down Expand Up @@ -91,6 +98,10 @@ export interface TableStore<TData = unknown> {
* Allows to change the global filter value.
*/
setGlobalFilter: React.Dispatch<React.SetStateAction<TableState<TData>['globalFilter']>>;
/**
* Allows to change the rows expanded state.
*/
setExpanded: React.Dispatch<React.SetStateAction<TableState<TData>['expanded']>>;
/**
* Allows to change the predicates values.
*/
Expand Down Expand Up @@ -211,6 +222,7 @@ export const useTable = <TData>(userOptions: UseTableOptions<TData> = {}): Table
);
const [sorting, setSorting] = useState<TableState<TData>['sorting']>(initialState.sorting as SortingState);
const [globalFilter, setGlobalFilter] = useState<TableState<TData>['globalFilter']>(initialState.globalFilter);
const [expanded, setExpanded] = useState<TableState<TData>['expanded']>(initialState.expanded as ExpandedState);
const [predicates, setPredicates] = useState<TableState<TData>['predicates']>(initialState.predicates);
const [layout, setLayout] = useState<TableState<TData>['layout']>(initialState.layout);
const [dateRange, setDateRange] = useState<TableState<TData>['dateRange']>(initialState.dateRange);
Expand Down Expand Up @@ -265,6 +277,7 @@ export const useTable = <TData>(userOptions: UseTableOptions<TData> = {}): Table
totalEntries,
sorting,
globalFilter,
expanded,
predicates,
layout,
dateRange,
Expand All @@ -276,6 +289,7 @@ export const useTable = <TData>(userOptions: UseTableOptions<TData> = {}): Table
totalEntries,
sorting,
globalFilter,
expanded,
predicates,
layout,
dateRange,
Expand All @@ -290,6 +304,7 @@ export const useTable = <TData>(userOptions: UseTableOptions<TData> = {}): Table
setTotalEntries,
setSorting,
setGlobalFilter,
setExpanded,
setPredicates,
setLayout,
setDateRange,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,13 @@ const columns: Array<ColumnDef<Person>> = [
const Demo = () => {
const data = useMemo(() => makeData(10), []);

const table = useTable<Person>({initialState: {totalEntries: data.length}});
const table = useTable<Person>({
initialState: {
totalEntries: data.length,
// Set the first row to be expanded by default
expanded: {[data[0].id]: true},
},
});

return (
<Table<Person>
Expand Down

0 comments on commit aaa55b1

Please sign in to comment.