diff --git a/CHANGELOG.md b/CHANGELOG.md index 0faa84ac6..2f12999f1 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -14,8 +14,16 @@ ## 89.0.0-SNAPSHOT - unreleased +### 💥 Breaking Changes (upgrade difficulty: 🟢 LOW - grid column filter specs) + +* `GridFilterModelConfig.fieldSpecs` is no longer an allow-list. Any `filterable` column it omits + now gets a default filter - set `filterable: false` on columns that should have none. + ### 🐞 Bug Fixes +* Fixed `GridFilterModelConfig.fieldSpecs` disabling filters on all other `filterable` columns. + Apps can now pass a spec for just the fields needing custom config, such as a values renderer. + See Breaking Changes above. * Fixed the desktop `SegmentedControl` rendering 2px taller than adjacent buttons when `outlined`. ## 88.1.0 - 2026-10-01 diff --git a/cmp/grid/README.md b/cmp/grid/README.md index 3c7e72ae0..9af477e5f 100644 --- a/cmp/grid/README.md +++ b/cmp/grid/README.md @@ -210,7 +210,8 @@ new GridModel({ filterModel: true, // Default config filterModel: { bind: store, // Filter target (defaults to grid's store) - commitOnChange: true + commitOnChange: true, + fieldSpecs: [{field: 'status', renderer: statusRenderer}] // Optional custom config }, columns: [ {field: 'status', filterable: true}, // Enable filter on specific columns @@ -219,6 +220,10 @@ new GridModel({ }); ``` +A `filterable` column gets a filter with default config even if `fieldSpecs` omits its field, as +long as that field exists in the bound Store or View. +List only the fields that need custom config. Set `filterable: false` to disable a column's filter. + ### Inline Editing ```typescript diff --git a/cmp/grid/Types.ts b/cmp/grid/Types.ts index 2c8d35b3d..4a0848772 100644 --- a/cmp/grid/Types.ts +++ b/cmp/grid/Types.ts @@ -163,6 +163,10 @@ export interface GridFilterModelConfig { * Specifies the fields this model supports for filtering. Should be configs for * {@link GridFilterFieldSpec}, string names to match with Fields in bound Store/View, or * omitted entirely to indicate that all fields should be filter-enabled. + * + * Any `filterable` column with a field not listed here gets a default spec, so this list only + * needs to include fields that require custom config. Set `filterable: false` on a column to + * disable its filter. */ fieldSpecs?: Array; diff --git a/cmp/grid/filter/GridFilterModel.ts b/cmp/grid/filter/GridFilterModel.ts index 5c446e9ca..b69b25dac 100644 --- a/cmp/grid/filter/GridFilterModel.ts +++ b/cmp/grid/filter/GridFilterModel.ts @@ -77,6 +77,14 @@ export class GridFilterModel extends HoistModel { this.commitOnChange = commitOnChange; this.activeFilterIcon = activeFilterIcon ?? GridFilterModel.defaults.activeFilterIcon; this.fieldSpecs = this.parseFieldSpecs(fieldSpecs, fieldSpecDefaults); + + // Ensure every filterable column has a spec, including columns or View fields added later. + // Columns are typically still empty here - the reaction covers the GridModel's setColumns(). + this.addReaction({ + track: () => [gridModel.columns, this.bind.fieldNames], + run: () => this.addColumnFieldSpecs(fieldSpecDefaults), + fireImmediately: true + }); } /** @@ -169,12 +177,29 @@ export class GridFilterModel extends HoistModel { return specs.map(spec => { if (isString(spec)) spec = {field: spec}; - return new GridFilterFieldSpec({ - filterModel: this, - source: bind, - ...fieldSpecDefaults, - ...spec - }); + return this.createFieldSpec(spec, fieldSpecDefaults); + }); + } + + // Add default specs for filterable columns not covered by the configured specs. + private addColumnFieldSpecs(fieldSpecDefaults: Omit) { + const {fieldNames} = this.bind; + this.gridModel.getLeafColumns().forEach(({filterable, field}) => { + if (filterable && fieldNames.includes(field) && !this.getFieldSpec(field)) { + this.fieldSpecs.push(this.createFieldSpec({field}, fieldSpecDefaults)); + } + }); + } + + private createFieldSpec( + spec: GridFilterFieldSpecConfig, + fieldSpecDefaults: Omit + ): GridFilterFieldSpec { + return new GridFilterFieldSpec({ + filterModel: this, + source: this.bind, + ...fieldSpecDefaults, + ...spec }); }