Skip to content

Commit

Permalink
[DataGrid] Allow to ignore diacritics when filtering (#10569)
Browse files Browse the repository at this point in the history
  • Loading branch information
cherniavskii committed Nov 2, 2023
1 parent 9ba8e44 commit b0cb729
Show file tree
Hide file tree
Showing 30 changed files with 370 additions and 35 deletions.
63 changes: 63 additions & 0 deletions docs/data/data-grid/filtering/QuickFilteringDiacritics.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,63 @@
import * as React from 'react';
import { DataGrid, GridToolbar } from '@mui/x-data-grid';
import FormControlLabel from '@mui/material/FormControlLabel';
import Switch from '@mui/material/Switch';

const dateFormatter = new Intl.DateTimeFormat('fr-FR', {
day: 'numeric',
month: 'long',
year: 'numeric',
});

const rows = [
{ id: 0, string: 'Café', date: new Date(2023, 1, 1), singleSelect: 'Jalapeño' },
];

const columns = [
{ field: 'string', width: 100 },
{
field: 'date',
type: 'date',
width: 150,
valueFormatter: (params) => dateFormatter.format(params.value),
},
{
field: 'singleSelect',
type: 'singleSelect',
valueOptions: ['Jalapeño'],
},
];

export default function QuickFilteringDiacritics() {
const [filterModel, setFilterModel] = React.useState({
items: [],
quickFilterValues: ['cafe'],
});
const [ignoreDiacritics, setIgnoreDiacritics] = React.useState(true);

return (
<div style={{ width: '100%' }}>
<FormControlLabel
checked={ignoreDiacritics}
onChange={(event) => setIgnoreDiacritics(event.target.checked)}
control={<Switch />}
label="Ignore diacritics"
/>
<div style={{ height: 200, width: '100%' }}>
<DataGrid
key={ignoreDiacritics.toString()}
rows={rows}
columns={columns}
filterModel={filterModel}
onFilterModelChange={setFilterModel}
disableColumnSelector
disableDensitySelector
hideFooter
slots={{ toolbar: GridToolbar }}
slotProps={{ toolbar: { showQuickFilter: true } }}
ignoreDiacritics={ignoreDiacritics}
/>
</div>
</div>
);
}
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
<DataGrid rows={[{ id: 0, value: 'Café' }]} columns={columns} />
69 changes: 69 additions & 0 deletions docs/data/data-grid/filtering/QuickFilteringDiacritics.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,69 @@
import * as React from 'react';
import {
DataGrid,
GridToolbar,
GridColDef,
GridFilterModel,
} from '@mui/x-data-grid';
import FormControlLabel from '@mui/material/FormControlLabel';
import Switch from '@mui/material/Switch';

const dateFormatter = new Intl.DateTimeFormat('fr-FR', {
day: 'numeric',
month: 'long',
year: 'numeric',
});

const rows = [
{ id: 0, string: 'Café', date: new Date(2023, 1, 1), singleSelect: 'Jalapeño' },
];
const columns: GridColDef[] = [
{ field: 'string', width: 100 },
{
field: 'date',
type: 'date',
width: 150,
valueFormatter: (params) => dateFormatter.format(params.value),
},
{
field: 'singleSelect',
type: 'singleSelect',
valueOptions: ['Jalapeño'],
},
];

export default function QuickFilteringDiacritics() {
const [filterModel, setFilterModel] = React.useState<GridFilterModel>({
items: [],
quickFilterValues: ['cafe'],
});
const [ignoreDiacritics, setIgnoreDiacritics] = React.useState(true);

return (
<div style={{ width: '100%' }}>
<FormControlLabel
checked={ignoreDiacritics}
onChange={(event) =>
setIgnoreDiacritics((event.target as HTMLInputElement).checked)
}
control={<Switch />}
label="Ignore diacritics"
/>
<div style={{ height: 200, width: '100%' }}>
<DataGrid
key={ignoreDiacritics.toString()}
rows={rows}
columns={columns}
filterModel={filterModel}
onFilterModelChange={setFilterModel}
disableColumnSelector
disableDensitySelector
hideFooter
slots={{ toolbar: GridToolbar }}
slotProps={{ toolbar: { showQuickFilter: true } }}
ignoreDiacritics={ignoreDiacritics}
/>
</div>
</div>
);
}
4 changes: 4 additions & 0 deletions docs/data/data-grid/filtering/header-filters.md
Original file line number Diff line number Diff line change
Expand Up @@ -72,6 +72,10 @@ Additionally, `slots.headerFilterMenu` could also be used to customize the menu

{{"demo": "CustomHeaderFilterDataGridPro.js", "bg": "inline", "defaultCodeOpen": false}}

## Ignore diacritics (accents)

You can ignore diacritics (accents) when filtering the rows. See [Quick filter - Ignore diacritics (accents)](/x/react-data-grid/filtering/quick-filter/#ignore-diacritics-accents).

## API

- [DataGrid](/x/api/data-grid/data-grid/)
Expand Down
4 changes: 4 additions & 0 deletions docs/data/data-grid/filtering/index.md
Original file line number Diff line number Diff line change
Expand Up @@ -127,6 +127,10 @@ In the example below, the _rating_ column can not be filtered.

{{"demo": "DisableFilteringGridSomeColumns.js", "bg": "inline", "defaultCodeOpen": false}}

## Ignore diacritics (accents)

You can ignore diacritics (accents) when filtering the rows. See [Quick filter - Ignore diacritics (accents)](/x/react-data-grid/filtering/quick-filter/#ignore-diacritics-accents).

## apiRef

The grid exposes a set of methods that enables all of these features using the imperative `apiRef`. To know more about how to use it, check the [API Object](/x/react-data-grid/api-object/) section.
Expand Down
17 changes: 17 additions & 0 deletions docs/data/data-grid/filtering/quick-filter.md
Original file line number Diff line number Diff line change
Expand Up @@ -122,6 +122,23 @@ In the following demo, the quick filter value `"Saint Martin, Saint Lucia"` will

{{"demo": "QuickFilteringCustomizedGrid.js", "bg": "inline", "defaultCodeOpen": false}}

## Ignore diacritics (accents)

In some languages, the letters can have diacritics (accents) - for instance, the letter `é` in French.
By default, these letters are considered different from their non-accented versions when filtering.

To ignore diacritics, set the `ignoreDiacritics` prop to `true`:

```tsx
<DataGrid ignoreDiacritics />
```

{{"demo": "QuickFilteringDiacritics.js", "bg": "inline", "defaultCodeOpen": false}}

:::warning
Note that the `ignoreDiacritics` prop affects all columns and all filter types: [normal filters](/x/react-data-grid/filtering/), [quick filter](/x/react-data-grid/filtering/quick-filter/) and [header filters](/x/react-data-grid/filtering/header-filters/).
:::

## API

- [GridToolbarQuickFilter](/x/api/data-grid/grid-toolbar-quick-filter/)
Expand Down
1 change: 1 addition & 0 deletions docs/pages/x/api/data-grid/data-grid-premium.json
Original file line number Diff line number Diff line change
Expand Up @@ -184,6 +184,7 @@
"default": "false"
},
"hideFooterSelectedRowCount": { "type": { "name": "bool" } },
"ignoreDiacritics": { "type": { "name": "bool" } },
"initialState": { "type": { "name": "object" } },
"isCellEditable": {
"type": { "name": "func" },
Expand Down
1 change: 1 addition & 0 deletions docs/pages/x/api/data-grid/data-grid-pro.json
Original file line number Diff line number Diff line change
Expand Up @@ -163,6 +163,7 @@
"default": "false"
},
"hideFooterSelectedRowCount": { "type": { "name": "bool" } },
"ignoreDiacritics": { "type": { "name": "bool" } },
"initialState": { "type": { "name": "object" } },
"isCellEditable": {
"type": { "name": "func" },
Expand Down
1 change: 1 addition & 0 deletions docs/pages/x/api/data-grid/data-grid.json
Original file line number Diff line number Diff line change
Expand Up @@ -114,6 +114,7 @@
"hideFooter": { "type": { "name": "bool" } },
"hideFooterPagination": { "type": { "name": "bool" } },
"hideFooterSelectedRowCount": { "type": { "name": "bool" } },
"ignoreDiacritics": { "type": { "name": "bool" } },
"initialState": { "type": { "name": "object" } },
"isCellEditable": {
"type": { "name": "func" },
Expand Down
5 changes: 5 additions & 0 deletions docs/translations/api-docs/data-grid/data-grid-premium.json
Original file line number Diff line number Diff line change
Expand Up @@ -343,6 +343,11 @@
"deprecated": "",
"typeDescriptions": {}
},
"ignoreDiacritics": {
"description": "If <code>true</code>, the diacritics (accents) are ignored when filtering or quick filtering. E.g. when filter value is <code>cafe</code>, the rows with <code>café</code> will be visible.",
"deprecated": "",
"typeDescriptions": {}
},
"initialState": {
"description": "The initial state of the DataGridPremium. The data in it is set in the state on initialization but isn&#39;t controlled. If one of the data in <code>initialState</code> is also being controlled, then the control state wins.",
"deprecated": "",
Expand Down
5 changes: 5 additions & 0 deletions docs/translations/api-docs/data-grid/data-grid-pro.json
Original file line number Diff line number Diff line change
Expand Up @@ -305,6 +305,11 @@
"deprecated": "",
"typeDescriptions": {}
},
"ignoreDiacritics": {
"description": "If <code>true</code>, the diacritics (accents) are ignored when filtering or quick filtering. E.g. when filter value is <code>cafe</code>, the rows with <code>café</code> will be visible.",
"deprecated": "",
"typeDescriptions": {}
},
"initialState": {
"description": "The initial state of the DataGridPro. The data in it will be set in the state on initialization but will not be controlled. If one of the data in <code>initialState</code> is also being controlled, then the control state wins.",
"deprecated": "",
Expand Down
5 changes: 5 additions & 0 deletions docs/translations/api-docs/data-grid/data-grid.json
Original file line number Diff line number Diff line change
Expand Up @@ -209,6 +209,11 @@
"deprecated": "",
"typeDescriptions": {}
},
"ignoreDiacritics": {
"description": "If <code>true</code>, the diacritics (accents) are ignored when filtering or quick filtering. E.g. when filter value is <code>cafe</code>, the rows with <code>café</code> will be visible.",
"deprecated": "",
"typeDescriptions": {}
},
"initialState": {
"description": "The initial state of the DataGrid. The data in it will be set in the state on initialization but will not be controlled. If one of the data in <code>initialState</code> is also being controlled, then the control state wins.",
"deprecated": "",
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -461,6 +461,12 @@ DataGridPremiumRaw.propTypes = {
* @default false
*/
hideFooterSelectedRowCount: PropTypes.bool,
/**
* If `true`, the diacritics (accents) are ignored when filtering or quick filtering.
* E.g. when filter value is `cafe`, the rows with `café` will be visible.
* @default false
*/
ignoreDiacritics: PropTypes.bool,
/**
* The initial state of the DataGridPremium.
* The data in it is set in the state on initialization but isn't controlled.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,6 @@ import {
GridAggregatedFilterItemApplier,
GridAggregatedFilterItemApplierResult,
GridColumnRawLookup,
GridApiCommunity,
} from '@mui/x-data-grid-pro/internals';
import { DataGridPremiumProcessedProps } from '../../../models/dataGridPremiumProps';
import { GridGroupingValueGetterParams } from '../../../models/gridGroupingValueGetterParams';
Expand Down Expand Up @@ -58,7 +57,7 @@ interface FilterRowTreeFromTreeDataParams {
rowTree: GridRowTreeConfig;
isRowMatchingFilters: GridAggregatedFilterItemApplier | null;
filterModel: GridFilterModel;
apiRef: React.MutableRefObject<GridApiCommunity>;
apiRef: React.MutableRefObject<GridPrivateApiPremium>;
}

/**
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@ import {
import { GridInitialStatePremium, GridStatePremium } from './gridStatePremium';
import type { GridRowGroupingApi, GridExcelExportApi, GridAggregationApi } from '../hooks';
import { GridCellSelectionApi } from '../hooks/features/cellSelection/gridCellSelectionInterfaces';
import type { DataGridPremiumProcessedProps } from './dataGridPremiumProps';

/**
* The api of `DataGridPremium`.
Expand All @@ -35,5 +36,5 @@ export interface GridApiPremium

export interface GridPrivateApiPremium
extends GridApiPremium,
GridPrivateOnlyApiCommon<GridApiPremium, GridPrivateApiPremium>,
GridPrivateOnlyApiCommon<GridApiPremium, GridPrivateApiPremium, DataGridPremiumProcessedProps>,
GridDetailPanelPrivateApi {}
6 changes: 6 additions & 0 deletions packages/grid/x-data-grid-pro/src/DataGridPro/DataGridPro.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -421,6 +421,12 @@ DataGridProRaw.propTypes = {
* @default false
*/
hideFooterSelectedRowCount: PropTypes.bool,
/**
* If `true`, the diacritics (accents) are ignored when filtering or quick filtering.
* E.g. when filter value is `cafe`, the rows with `café` will be visible.
* @default false
*/
ignoreDiacritics: PropTypes.bool,
/**
* The initial state of the DataGridPro.
* The data in it will be set in the state on initialization but will not be controlled.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,16 +8,16 @@ import {
import {
GridAggregatedFilterItemApplier,
GridAggregatedFilterItemApplierResult,
GridApiCommunity,
passFilterLogic,
} from '@mui/x-data-grid/internals';
import type { GridPrivateApiPro } from '../../../models/gridApiPro';

interface FilterRowTreeFromTreeDataParams {
rowTree: GridRowTreeConfig;
disableChildrenFiltering: boolean;
isRowMatchingFilters: GridAggregatedFilterItemApplier | null;
filterModel: GridFilterModel;
apiRef: React.MutableRefObject<GridApiCommunity>;
apiRef: React.MutableRefObject<GridPrivateApiPro>;
}

export const TREE_DATA_STRATEGY = 'tree-data';
Expand Down
3 changes: 2 additions & 1 deletion packages/grid/x-data-grid-pro/src/models/gridApiPro.ts
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@ import type {
GridRowPinningApi,
GridDetailPanelPrivateApi,
} from '../hooks';
import type { DataGridProProcessedProps } from './dataGridProProps';

/**
* The api of `DataGridPro`.
Expand All @@ -30,5 +31,5 @@ export interface GridApiPro

export interface GridPrivateApiPro
extends GridApiPro,
GridPrivateOnlyApiCommon<GridApiPro, GridPrivateApiPro>,
GridPrivateOnlyApiCommon<GridApiPro, GridPrivateApiPro, DataGridProProcessedProps>,
GridDetailPanelPrivateApi {}
6 changes: 6 additions & 0 deletions packages/grid/x-data-grid/src/DataGrid/DataGrid.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -301,6 +301,12 @@ DataGridRaw.propTypes = {
* @default false
*/
hideFooterSelectedRowCount: PropTypes.bool,
/**
* If `true`, the diacritics (accents) are ignored when filtering or quick filtering.
* E.g. when filter value is `cafe`, the rows with `café` will be visible.
* @default false
*/
ignoreDiacritics: PropTypes.bool,
/**
* The initial state of the DataGrid.
* The data in it will be set in the state on initialization but will not be controlled.
Expand Down
1 change: 1 addition & 0 deletions packages/grid/x-data-grid/src/DataGrid/useDataGridProps.ts
Original file line number Diff line number Diff line change
Expand Up @@ -62,6 +62,7 @@ export const DATA_GRID_PROPS_DEFAULT_VALUES: DataGridPropsWithDefaultValues = {
hideFooterPagination: false,
hideFooterRowCount: false,
hideFooterSelectedRowCount: false,
ignoreDiacritics: false,
logger: console,
logLevel: process.env.NODE_ENV === 'production' ? ('error' as const) : ('warn' as const),
pagination: false,
Expand Down
3 changes: 1 addition & 2 deletions packages/grid/x-data-grid/src/colDef/gridStringOperators.ts
Original file line number Diff line number Diff line change
Expand Up @@ -12,8 +12,7 @@ export const getGridStringQuickFilterFn = tagInternalFilter(
return null;
}
const filterRegex = new RegExp(escapeRegExp(value), 'i');
return (_, row, column, apiRef): boolean => {
const columnValue = apiRef.current.getRowFormattedValue(row, column);
return (columnValue): boolean => {
return columnValue != null ? filterRegex.test(columnValue.toString()) : false;
};
},
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ export const useGridInitialization = <
Api extends GridApiCommon,
>(
inputApiRef: React.MutableRefObject<Api> | undefined,
props: Pick<DataGridProcessedProps, 'signature' | 'logger' | 'logLevel' | 'localeText'>,
props: DataGridProcessedProps,
) => {
const privateApiRef = useGridApiInitialization<PrivateApi, Api>(inputApiRef, props);
useGridLoggerFactory(privateApiRef, props);
Expand All @@ -25,5 +25,7 @@ export const useGridInitialization = <
useGridStrategyProcessing(privateApiRef);
useGridLocaleText(privateApiRef, props);

privateApiRef.current.register('private', { rootProps: props });

return privateApiRef;
};
Loading

0 comments on commit b0cb729

Please sign in to comment.