(core) Add dropdown conditions

Summary:
Dropdown conditions let you specify a predicate formula that's used to filter
choices and references in their respective autocomplete dropdown menus.

Test Plan: Python and browser tests (WIP).

Reviewers: jarek, paulfitz

Reviewed By: jarek

Subscribers: dsagal, paulfitz

Differential Revision: https://phab.getgrist.com/D4235
This commit is contained in:
George Gevoian
2024-04-26 16:34:16 -04:00
parent 34c85757f1
commit 3112433a58
86 changed files with 4221 additions and 1060 deletions

View File

@@ -2,12 +2,15 @@ import {ColumnRec, DocModel, IRowModel, refListRecords, refRecord, ViewSectionRe
import {formatterForRec} from 'app/client/models/entities/ColumnRec';
import * as modelUtil from 'app/client/models/modelUtil';
import {removeRule, RuleOwner} from 'app/client/models/RuleOwner';
import { HeaderStyle, Style } from 'app/client/models/Styles';
import {HeaderStyle, Style} from 'app/client/models/Styles';
import {ViewFieldConfig} from 'app/client/models/ViewFieldConfig';
import * as UserType from 'app/client/widgets/UserType';
import {DocumentSettings} from 'app/common/DocumentSettings';
import {DropdownCondition, DropdownConditionCompilationResult} from 'app/common/DropdownCondition';
import {compilePredicateFormula} from 'app/common/PredicateFormula';
import {BaseFormatter} from 'app/common/ValueFormatter';
import {createParser} from 'app/common/ValueParser';
import {Computed} from 'grainjs';
import * as ko from 'knockout';
// Represents a page entry in the tree of pages.
@@ -106,6 +109,9 @@ export interface ViewFieldRec extends IRowModel<"_grist_Views_section_field">, R
/** Label in FormView. By default FormView uses label, use this to override it. */
question: modelUtil.KoSaveableObservable<string|undefined>;
dropdownCondition: modelUtil.KoSaveableObservable<DropdownCondition|undefined>;
dropdownConditionCompiled: Computed<DropdownConditionCompilationResult|null>;
createValueParser(): (value: string) => any;
// Helper which adds/removes/updates field's displayCol to match the formula.
@@ -316,4 +322,21 @@ export function createViewFieldRec(this: ViewFieldRec, docModel: DocModel): void
this.disableModify = this.autoDispose(ko.pureComputed(() => this.column().disableModify()));
this.disableEditData = this.autoDispose(ko.pureComputed(() => this.column().disableEditData()));
this.dropdownCondition = this.widgetOptionsJson.prop('dropdownCondition');
this.dropdownConditionCompiled = Computed.create(this, use => {
const dropdownCondition = use(this.dropdownCondition);
if (!dropdownCondition?.parsed) { return null; }
try {
return {
kind: 'success',
result: compilePredicateFormula(JSON.parse(dropdownCondition.parsed), {
variant: 'dropdown-condition',
}),
};
} catch (e) {
return {kind: 'failure', error: e.message};
}
});
}